skybrush-io / studio-blender

Skybrush Studio for Blender - a Blender addon for designing and validating drone shows
https://skybrush.io
GNU General Public License v3.0
43 stars 30 forks source link

"inside the mesh" is not considering mesh deformations #15

Closed NelloF closed 4 months ago

NelloF commented 6 months ago

I added shape keys to a mesh to change the shape of a light effect over time inside the mesh, but looks like the deformations of geometry is not considered.

image

ntamas commented 6 months ago

Unfortunately I haven't found a way yet to do this via Blender's Python API. The way we do it right now is to convert the mesh into a BVHTree representation so we can do efficient containment checks. The containment check is actually "fake" in some sense: we simply fire three rays from each drone along the three principal axes of the coordinate system, and if all three rays hit the mesh, then we consider the drone to be inside the mesh, otherwise it's considered to be outside. Note that we need to be able to do this super fast in every single frame so there isn't really any CPU time for exact containment checks.

Now, the problem is that the BVHTree representation that I can get out of Blender's Python API does not seem to consider mesh deformations. This is the part of the code where we create the BVHTree:

    def _get_bvh_tree_from_mesh(self) -> Optional[BVHTree]:
        """Returns a BVH-tree data structure from the mesh associated to this
        light effect for easy containment detection, or `None` if the light
        effect has no associated mesh.
        """
        if self.mesh:
            b_mesh = bmesh.new()
            b_mesh.from_mesh(self.mesh.data)
            b_mesh.transform(self.mesh.matrix_world)
            tree = BVHTree.FromBMesh(b_mesh)
            b_mesh.free()
            return tree

If you are familiar with Blender's Python API and can tell me how to obtain a similar data structure after applying the deformations, let me know and I'll happily update the code. (Or, if you know anyone who is familiar enough with the internals of Blender and can help here, let us know).

MartinMerkl commented 5 months ago

@ntamas What is the reason for using BVHTree.FromBMesh instead of BVHTree.FromObject (is it the speed of the check?)? The 2nd option allows to use a deformed mesh. I tried to recreate your check with the global vectors in the attached blender file (there is a script raycast) and it works with a modifier for deforming the mesh.

https://docs.blender.org/api/current/mathutils.bvhtree.html

BVHTREE_CHECK.zip

ntamas commented 5 months ago

There was no particular reason, I am not really familiar with this part of the Blender API and I guess I got scared by the depsgraph argument. There could be other performance implications, though. I'll ask around on Discord to see whether someone has a scene with heavy use of "inside the mesh" light effects as I'd like to test the performance a bit before committing to this change.

MartinMerkl commented 5 months ago

Great. Even if it would mean that checking the object instead of the mesh is slower I think that it would be really great if mesh deformation could affect LED effects and maybe it could be up to the user which check to use on a particular LED effect via some switch/checkbox.

ntamas commented 5 months ago

Okay, so I've started testing this in a separate branch and here are a few catches:

ntamas commented 5 months ago

Work started in a separate branch in https://github.com/skybrush-io/studio-blender/tree/feat/inside-the-mesh-check-with-deforms . Feel free to experiment there and get back to me if you have found a solution to the problems outlined above.

ntamas commented 4 months ago

https://github.com/skybrush-io/studio-blender/tree/feat/inside-the-mesh-check-with-deforms was merged back to main so you can keep on testing this feature on the main branch.