From ce84c14c1de9429f1a0115a3ca777069a37d3f2d Mon Sep 17 00:00:00 2001 From: Victor Doval <10011941+vicdoval@users.noreply.github.com> Date: Sat, 26 Jun 2021 13:17:32 +0200 Subject: [PATCH] Raycaster checks (#4186) * raycaster checks * node docstring --- docs/nodes/analyzer/raycaster_lite.rst | 14 +++++++---- nodes/analyzer/raycaster_lite.py | 32 +++++++++++++++++++------- 2 files changed, 34 insertions(+), 12 deletions(-) diff --git a/docs/nodes/analyzer/raycaster_lite.rst b/docs/nodes/analyzer/raycaster_lite.rst index f0e76af181..d04df51e11 100644 --- a/docs/nodes/analyzer/raycaster_lite.rst +++ b/docs/nodes/analyzer/raycaster_lite.rst @@ -4,12 +4,12 @@ Raycast Functionality ------------- -Functionality is almost completely analogous to the two built-in blender operators -``bpy.context.scene.ray_cast`` and ``object.ray_cast``. +Functionality is almost completely analogous to the two built-in blender operators +``bpy.context.scene.ray_cast`` and ``object.ray_cast``. Ray is casted from "start" vector to "end" vector and can hit polygons of input objects. -see docs: -`bpy.types.Object.ray_cast `_ and +see docs: +`bpy.types.Object.ray_cast `_ and `bpy.types.Scene.ray_cast `_ @@ -41,6 +41,12 @@ Output sockets | Success | ``True`` or ``False`` if ray doesn't hit any polygon. | +------------------------+----------------------------------------------------------------------------------------+ +Advanced parameters (N-Panel) +---------------------------- + +**Safe Check**: Checks the mesh for unreferenced polygons (slows the node but prevents some Blender crashes) + +**All Triangles**: Enable if all the incoming faces are triangles to improve the performance of the algorithm Usage ----- diff --git a/nodes/analyzer/raycaster_lite.py b/nodes/analyzer/raycaster_lite.py index 5bdf630dd6..abaa61bd74 100644 --- a/nodes/analyzer/raycaster_lite.py +++ b/nodes/analyzer/raycaster_lite.py @@ -19,13 +19,16 @@ import bpy from sverchok.node_tree import SverchCustomTreeNode from sverchok.data_structure import (updateNode, match_long_cycle as C) -from mathutils.bvhtree import BVHTree +from sverchok.utils.bvh_tree import bvh_tree_from_polygons # zeffii 2017 8 okt # airlifted from Kosvor's Raycast nodes.. class SvRaycasterLiteNode(bpy.types.Node, SverchCustomTreeNode): - ''' svmesh to Raycast ''' + """ + Triggers: Raycast on Mesh + Tooltip: Cast rays from arbitrary points on to a mesh a determine hiting location, normal at hitpoint, ray legngth and index of the hitted face. + """ bl_idname = 'SvRaycasterLiteNode' bl_label = 'Raycaster' bl_icon = 'OUTLINER_OB_EMPTY' @@ -33,7 +36,19 @@ class SvRaycasterLiteNode(bpy.types.Node, SverchCustomTreeNode): start: bpy.props.FloatVectorProperty(default=(0,0,0), size=3, update=updateNode) direction: bpy.props.FloatVectorProperty(default=(0,0,-1), size=3, update=updateNode) - + all_triangles: bpy.props.BoolProperty( + name='All Triangles', + description='Enable to improve node performance if all inputted polygons are triangles', + default=False, + update=updateNode) + safe_check: bpy.props.BoolProperty( + name='Safe Check', + description='When disabled polygon indices refering to unexisting points will crash Blender but makes node faster', + default=True) + + def draw_buttons_ext(self, context, layout): + layout.prop(self, 'all_triangles') + layout.prop(self, 'safe_check') def sv_init(self, context): si = self.inputs.new so = self.outputs.new @@ -50,17 +65,18 @@ def sv_init(self, context): so('SvStringsSocket', 'Success') @staticmethod - def svmesh_to_bvh_lists(v, f): + def svmesh_to_bvh_lists(v, f, all_tris, safe_check): for vertices, polygons in zip(*C([v, f])): - yield BVHTree.FromPolygons(vertices, polygons, all_triangles=False, epsilon=0.0) + yield bvh_tree_from_polygons(vertices, polygons, all_triangles=all_tris, epsilon=0.0, safe_check=safe_check) def process(self): L, N, I, D, S = self.outputs RL = [] + if not any([s.is_linked for s in self.outputs]): + return + vert_in, face_in, start_in, direction_in = C([sock.sv_get(deepcopy=False) for sock in self.inputs]) - vert_in, face_in, start_in, direction_in = C([sock.sv_get() for sock in self.inputs]) - - for bvh, st, di in zip(*[self.svmesh_to_bvh_lists(vert_in, face_in), start_in, direction_in]): + for bvh, st, di in zip(*[self.svmesh_to_bvh_lists(vert_in, face_in, self.all_triangles, self.safe_check), start_in, direction_in]): st, di = C([st, di]) RL.append([bvh.ray_cast(i, i2) for i, i2 in zip(st, di)])