Bug 280943 - Ball bounces off wall underneath bridge
Summary: Ball bounces off wall underneath bridge
Status: RESOLVED FIXED
Alias: None
Product: kolf
Classification: Applications
Component: general (show other bugs)
Version: 1.10
Platform: Ubuntu Linux
: NOR normal
Target Milestone: ---
Assignee: Stefan Majewsky
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2011-08-28 16:14 UTC by Ben Klein
Modified: 2011-10-03 10:13 UTC (History)
1 user (show)

See Also:
Latest Commit:
Version Fixed In: 4.8


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Ben Klein 2011-08-28 16:14:33 UTC
Version:           1.10
OS:                Linux

On the 6th hole of the Really Easy course, the ball gets to the end of the bridge after 1 shot. However, when I hit it down the center of the bridge, it bounces off the wall underneath, preventing it from going into the hole.

Reproducible: Always

Steps to Reproduce:
See Details field.

Actual Results:  
The ball appeared to bounce off the end of the bridge (actually the wall underneath)

Expected Results:  
The ball should go into the triangle-shaped area at the other end and, ideally, into the hole.

OS: Linux (i686) release 2.6.38-11-generic
Compiler: cc
Comment 1 Stefan Majewsky 2011-10-03 00:18:34 UTC
SVN commit 1256966 by majewsky:

Keep objects with FixedZValue magically changing its Z value.

I discovered this inexplicable behavior while debugging bug 280943: The
wall in question has a Z value of 100, although the Z behavior for walls
is configured as (FixedZValue, 5). 100 is the Z value for struts. What's
going on there?
CCBUG: 280943

 M  +3 -0      canvasitem.cpp  


WebSVN link: http://websvn.kde.org/?view=rev&revision=1256966
Comment 2 Stefan Majewsky 2011-10-03 00:39:33 UTC
Meh. I hoped to have solved all collision bugs relating to Z ordering. Maybe some background will help you to see why this stuff is problematic.

Kolf traditionally did all physics itself, and was quite bad at it. After some refactoring, we now have *two* physics engines working behind the scenes: Box2D handles rigid-body collisions (like bouncing off walls), while Kolf itself does behavioral collisions (like teleporting in a blackhole, or changing a ball's direction on a slope).

The wall+bridge case lies in between: The wall is obviously a simple rigid-body collision, while the bridge's behavior is to raise the ball above any walls. To do that, Box2D asks Kolf whether certain objects (ball+wall in this case) may collide. The problem then seems to boil down to Box2D asking way too early whether the objects may collide. This may have to do with the wall being a bit diagonal.

Now it gets really funny: In principle, I have a patch in my local checkout which fixes this problem, by basically interrupting ball-wall collision at a later point in time. Problem is, this patch removes completely any collision with walls arranged around a bridge. (In other words, the collision is interrupted too often rather than too seldom now.)

As you see, this code puts me in an awful situation where fixing any bug can potentially open the metaphorical can of worms. I have another idea for working around this, though, which I'll try tomorrow.
Comment 3 Stefan Majewsky 2011-10-03 10:13:02 UTC
SVN commit 1257072 by majewsky:

Fix some more Z-ordering bugs with static struts and b2ContactListener.

As described in bug 280943, the problem is that the old b2ContactFilter
implementation detected wall-ball collisions too early (when the AABBs
of the participating objects touched for the first time). Especially for
diagonal walls, the ball has not yet been strutted when ShouldCollide()
is called.

This problem is solved by switching from b2ContactFilter to
b2ContactListener, which kicks in only when a collision has really been
detected. (The contact is then disabled if appropriate, as recommended
by the Box2D manual.)

This solution unfortunately introduces a new problem: Walls around
RectangleItems are now invisible for balls coming from inside the
RectangleItem (e.g. bridges and windmills). Actually I have no idea why
this problem didn't appear previously. I solve this by introducing the
notion of "static struts": The rectangle item is the static strut for
its walls and raises them all, even if they are not colliding with the
rectangle item (WindmillGuard, you're an a**hole).

BUG: 280943
FIXED-IN: 4.8

 M  +19 -2     canvasitem.cpp  
 M  +5 -0      canvasitem.h  
 M  +10 -9     game.cpp  
 M  +5 -10     obstacles.cpp  
 M  +1 -2      obstacles.h  


WebSVN link: http://websvn.kde.org/?view=rev&revision=1257072