[SOLVED] Issue with ray penetrating through some parts of a mesh

Hi

In my block terrain editor, I am encountering with raycasting issue where a ray penetrates through the mesh in some places and returns the wrong collision.

See the issue in this video

I have tried both manual raycasting the terrain node like this

    private CollisionResult getCollisionResult() {
        CollisionResults collisionResults = new CollisionResults();
        Vector2f cursor = getApplication().getInputManager().getCursorPosition();
        Ray ray = getPickRay(cursor);
        blockNode.collideWith(ray, collisionResults);
        return collisionResults.size() > 0 ? collisionResults.getClosestCollision() : null;
    }

    private Ray getPickRay(Vector2f cursor) {
        Camera cam = getApplication().getCamera();
        if (getApplication().getInputManager().isCursorVisible()) {
            Vector3f clickFar = cam.getWorldCoordinates(cursor, 1);
            Vector3f clickNear = cam.getWorldCoordinates(cursor, 0);
            ray.setOrigin(clickNear);
            ray.setDirection(clickFar.subtractLocal(clickNear).normalizeLocal());
        } else {
            ray.setOrigin(cam.getLocation());
            ray.setDirection(cam.getDirection());
        }
        ray.setLimit(500);
        return ray;
    }

or using Lemur CursorEventControl

CursorEventControl.addListenersToSpatial(blockNode, new TerrainClickListener());

and inside cursorMoved() I update pointers

        @Override
        public void cursorMoved(CursorMotionEvent event, Spatial target, Spatial capture) {
            collision = event.getCollision();
            updateBlockPointer(collision);
        }

with no luck.

Seems this issue is happening with quad shaped blocks.

Any hint on why this happens and probably how I can solve it?

If I need to provide more details, please let me know.

Edit:
Note both grass and dirt blocks are batched to a single mesh inside the chunk. (sharing the same material)

Edit2:
And in case this helps, here is the mesh info of grass block shape

-----vertex count=4
-----Positions:
(0.5, 1.0, -0.5)
(-0.5, 1.0, -0.5)
(0.5, 1.0, 0.5)
(-0.5, 1.0, 0.5)

------Traingles = 2
------Indecies = 6
0, 1, 2
1, 3, 2

------UVs:4
(0.5002586, 3.1626225E-4)
(0.62469053, 3.1626225E-4)
(0.5002586, 0.12471366)
(0.62469053, 0.12471366)

------Normals:4
(0.0, 1.0, -0.0)
(0.0, 1.0, -0.0)
(0.0, 1.0, -0.0)
(0.0, 1.0, -0.0)

------Tangents:4
(-1.0, 0.0, -0.0, -1.0)
(-1.0, 0.0, -0.0, -1.0)
(-1.0, 0.0, -0.0, -1.0)
(-1.0, 0.0, -0.0, -1.0)
1 Like

when you place this new blocks, are you sure you make “updateModelBound();” on their geom?

or maybe its some mictrotime while replacing mesh?

or last guess, maybe it collide with “displayed grid/quad to place below mouse”?

Similar to oxplay, my first reaction would be: make sure you clear collision data when you update the mesh. Make sure you update the mesh bound and update the geometry bound.

Added this after creating/updating a chunk node every time but it did not help. :frowning:

chunkNode.depthFirstTraversal(new SceneGraphVisitorAdapter() {
    public void visit(Geometry geom) {
        geom.getMesh().clearCollisionData();
        geom.getMesh().updateBound();
        geom.updateModelBound();
    }
});

This is the log of CollisionResult, the Y value is 2 on the surface I am moving mouse (the grass surface in video) but as you see in log in some cases contactPoint Y value becomes 1 which means ray penetrated through the top face and hitting the behind face.

Could it be because some vertecies have a normal with a -0.0 (instead of 0.0) in their X or Z components?

collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.464325, 2.0, -19.761354), contactNormal=(0.0, 1.0, -0.0), distance=8.5140915, triangleIndex=224]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.558613, 2.0, -20.539349), contactNormal=(0.0, 1.0, 0.0), distance=8.816672, triangleIndex=223]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.561996, 1.9999995, -20.66542), contactNormal=(0.0, 1.0, -0.0), distance=8.869691, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.561996, 1.9999995, -20.66542), contactNormal=(0.0, 1.0, -0.0), distance=8.869691, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.561996, 1.9999995, -20.66542), contactNormal=(0.0, 1.0, -0.0), distance=8.869691, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.561996, 1.9999995, -20.66542), contactNormal=(0.0, 1.0, -0.0), distance=8.869691, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.561996, 1.9999995, -20.66542), contactNormal=(0.0, 1.0, -0.0), distance=8.869691, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.562378, 2.0, -20.67954), contactNormal=(0.0, 1.0, -0.0), distance=8.875719, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.562378, 2.0, -20.67954), contactNormal=(0.0, 1.0, -0.0), distance=8.875719, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.562378, 2.0, -20.67954), contactNormal=(0.0, 1.0, -0.0), distance=8.875719, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.563522, 2.0, -20.722021), contactNormal=(0.0, 1.0, -0.0), distance=8.893961, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.563904, 2.0, -20.736223), contactNormal=(0.0, 1.0, -0.0), distance=8.900097, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.565052, 1.9999995, -20.778934), contactNormal=(0.0, 1.0, -0.0), distance=8.918655, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.565434, 2.0, -20.793219), contactNormal=(0.0, 1.0, -0.0), distance=8.924898, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.56582, 1.9999995, -20.807522), contactNormal=(0.0, 1.0, -0.0), distance=8.931168, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.541622, 2.0, -20.863972), contactNormal=(0.0, 1.0, -0.0), distance=8.953042, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.516594, 2.0, -20.891918), contactNormal=(0.0, 1.0, -0.0), distance=8.962503, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.632996, 1.0, -21.422579), contactNormal=(0.0, 1.0, 0.0), distance=10.1001625, triangleIndex=200]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.466476, 2.0, -20.962498), contactNormal=(0.0, 1.0, -0.0), distance=8.988451, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.466476, 2.0, -20.962498), contactNormal=(0.0, 1.0, -0.0), distance=8.988451, triangleIndex=222]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.45446, 2.0, -21.00579), contactNormal=(0.0, 1.0, 0.0), distance=9.006717, triangleIndex=221]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.403423, 2.0000005, -21.047821), contactNormal=(0.0, 1.0, 0.0), distance=9.020555, triangleIndex=221]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.33945, 2.0, -21.119148), contactNormal=(0.0, 1.0, 0.0), distance=9.047175, triangleIndex=221]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.30079, 2.0, -21.162094), contactNormal=(0.0, 1.0, 0.0), distance=9.063633, triangleIndex=221]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.262093, 2.0, -21.205301), contactNormal=(0.0, 1.0, 0.0), distance=9.08054, triangleIndex=221]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.33168, 1.0, -21.79227), contactNormal=(0.0, 1.0, 0.0), distance=10.241097, triangleIndex=200]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.21022, 1.9999995, -21.278284), contactNormal=(0.0, 1.0, -0.0), distance=9.11091, triangleIndex=220]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.197433, 2.0, -21.322918), contactNormal=(0.0, 1.0, -0.0), distance=9.131316, triangleIndex=220]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.197678, 2.0, -21.353123), contactNormal=(0.0, 1.0, -0.0), distance=9.14592, triangleIndex=220]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.27351, 1.000001, -21.925524), contactNormal=(0.0, 1.0, 0.0), distance=10.300485, triangleIndex=200]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.24393, 1.0, -21.94154), contactNormal=(0.0, 1.0, 0.0), distance=10.306047, triangleIndex=200]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.078934, 1.9999995, -21.409565), contactNormal=(0.0, 1.0, -0.0), distance=9.164904, triangleIndex=220]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.98605, 1.9999995, -21.45197), contactNormal=(0.0, 1.0, 0.0), distance=9.18015, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.946125, 1.9999995, -21.45063), contactNormal=(0.0, 1.0, 0.0), distance=9.177378, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.905907, 2.0, -21.495152), contactNormal=(0.0, 1.0, 0.0), distance=9.197448, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.892513, 1.9999995, -21.510015), contactNormal=(0.0, 1.0, 0.0), distance=9.204226, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.892513, 1.9999995, -21.510015), contactNormal=(0.0, 1.0, 0.0), distance=9.204226, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.879204, 2.0, -21.509518), contactNormal=(0.0, 1.0, 0.0), distance=9.203391, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.879204, 2.0, -21.509518), contactNormal=(0.0, 1.0, 0.0), distance=9.203391, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.865906, 2.0000005, -21.509094), contactNormal=(0.0, 1.0, 0.0), distance=9.202609, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.839302, 2.0000005, -21.492746), contactNormal=(0.0, 1.0, 0.0), distance=9.193399, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.839302, 2.0000005, -21.492746), contactNormal=(0.0, 1.0, 0.0), distance=9.193399, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.83945, 2.0, -21.477415), contactNormal=(0.0, 1.0, 0.0), distance=9.185802, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.83974, 1.9999995, -21.44689), contactNormal=(0.0, 1.0, 0.0), distance=9.170733, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.813713, 1.9999995, -21.400202), contactNormal=(0.0, 1.0, 0.0), distance=9.14682, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.813713, 1.9999995, -21.400202), contactNormal=(0.0, 1.0, 0.0), distance=9.14682, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.81404, 2.0, -21.369905), contactNormal=(0.0, 1.0, 0.0), distance=9.132051, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.81404, 2.0, -21.369905), contactNormal=(0.0, 1.0, 0.0), distance=9.132051, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.81404, 2.0, -21.369905), contactNormal=(0.0, 1.0, 0.0), distance=9.132051, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.81404, 2.0, -21.369905), contactNormal=(0.0, 1.0, 0.0), distance=9.132051, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.81404, 2.0, -21.369905), contactNormal=(0.0, 1.0, 0.0), distance=9.132051, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.81404, 2.0, -21.369905), contactNormal=(0.0, 1.0, 0.0), distance=9.132051, triangleIndex=267]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-35.94659, 1.0, -21.880033), contactNormal=(0.0, 1.0, 0.0), distance=10.258493, triangleIndex=246]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.06539, 1.0, -21.833485), contactNormal=(-0.0, 1.0, 0.0), distance=10.242191, triangleIndex=201]
collision:CollisionResult[geometry=ground-3-surface (Geometry), contactPoint=(-36.144108, 1.9999995, -21.23104), contactNormal=(0.0, 1.0, -0.0), distance=9.083392, triangleIndex=220]

I tried without grid also but yet the same issue happens. Also from the log (I provided above), it appears that only collides with ground-3-surface geometry which is inside the chunk node and is not interrupted by other geometries.

Normals are not used during collision detection other than filling in the answer. Collisions are done directly on the mesh.

The most likely cause of issues like this is that your mesh has two vertexes that should be exactly the same but are only really-very-nearly the same.

Even if it’s a jme bug somewhere, it’s going to be very hard to track. Step one would be to capture enough information from the ‘bad hit’ to recreate it in code on purpose. Then further debugging and isolation can happen… maybe even eventually providing a test case for the community.

Early in JME3’s development, there was a bounding box collision bug that was preventing certain rare collisions with single quad meshes… I tracked it down and fixed it in exactly the way I describe above. Found the ray that caused the problem, just created code that did that every time… then drilled deeper and deeper (debugger or logging).

2 Likes

Hmm, yes could be this. Neighbor blocks in the grid will always have duplicate vertices on overlapping edges.

Finally managed to solve this issue by a applying a simple trick and thanks to Lemur. :slightly_smiling_face:

I added a cursor listener to the block pointer (the yellow wire box) to consume the cursor events while the mouse is hovering on it, so terrain won’t get notified about the collisions. If the mouse moves out of the block pointer (the wire box) then the terrain cursor listener will get notified of collision events and with the first correct hit, block pointer position will be updated to new location and will start to consume the events until cursor gets out again.

3 Likes