RayShoot, MeshRay

How do I transform Breps to IEnumerable[GeometryBase] ?

Thank you!

https://developer.rhino3d.com/api/RhinoCommon/html/M_Rhino_Geometry_Intersect_Intersection_RayShoot.htm

RayShoot expects an enumerable (for example, a list) of Breps rather than a single Brep.

yes, but if i set type hint to list then i get:
expected IEnumerable[GeometryBase], got list

Please can you post a sample that can be tested?

This might be a RhinoCommon/IronPython edge case I think, where you might need to build a System.Collections.Generic.List[Rhino.Geometry.GeometryBase]() first, Add() your element, then call that same method.

1 Like

Thanks @piac,

I uploaded the file. I remember getting stuck into this before. I don’t know how to transform a list of breps into IEnumerable[GeometryBase]

IEnumerable.gh (12.8 KB)

Ok I got it:
geometry type hint = GeometryBase but as Item access.

and then the code looks like this:

import rhinoscriptsyntax as rs
import Rhino
import System

ray = Rhino.Geometry.Ray3d(rayStart, rayVec)

geo = System.Collections.Generic.List[Rhino.Geometry.GeometryBase]()

geo.Add(geometry)

a = Rhino.Geometry.Intersect.Intersection.RayShoot(ray,geo,maxReflections)

Still doesn’t solve my problem though because now I get each brep separately so the ray bounces for each of them separate, instead of bouncing between them…

You can do it this way:

__author__ = "b.chipara"
__version__ = "2019.10.30"

import rhinoscriptsyntax as rs
import Rhino
import scriptcontext as sc
from System.Collections.Generic import List

ray = Rhino.Geometry.Ray3d(rayStart, rayVec)

newlist = List[Rhino.Geometry.GeometryBase]()
for g in geometries: newlist.Add(g)

a = Rhino.Geometry.Intersect.Intersection.RayShoot(ray,newlist,maxReflections)


rays.gh (11.2 KB)

2 Likes

Ok, got it.
used a for loop to place each brep in the list, rather than creating a list for each brep with that brep inside - as I was doing above.

Thanks!

Yes, the thing is that it expects exactly a type, not a “normal” Python list.

For clarity, I’m thinking, will it be better if the GHPython component would have IEnumerable[GeometryBase] as a type hint, so it will automatically transform a “normal” Python list of geometry into a type?
I don’t know which other functions expect it…

This was done this way because Python users usually want to deal with Python lists. This is more a side-case of IronPython integration. Now that you know it, it will be easily to handle it.

Ray3D doesn’t work with trimmed surfaces :frowning: such a disappointment.
I have to find the one that works with meshes…

I don’t know who wrote the wrapper. Maybe @dale or @stevebaer can help.

It’s on the to-do list.

https://mcneel.myjetbrains.com/youtrack/issue/RH-13351

– Dale

Thanks @dale,
I see some interesting applications for this but it has been on the list for quite some time.

Is there another method for this? Something that works with meshes maybe?

You can get the first hit using Rhino.Geometry.Intersect.Intersection.MeshRay, but you’ll have to implement further bounces from here yourself. If you have issues implementing the second overload, here’s an example:

Edit: My first topic on Discourse was also related to this issue :older_man:

1 Like

Thanks @AndersDeleuran,

Something like this, but in a loop?
If I want to bounce it several times…

import Rhino as rc
from System import Array
import clr
import rhinoscriptsyntax as rs

def meshRayIntersect(mesh,point,vector):
    
    """ Intersect a mesh with a ray, including intersected mesh face IDs """

    ray = rc.Geometry.Ray3d(point,vector)
    faceIDs = clr.StrongBox[Array[int]]()
    rayP = rc.Geometry.Intersect.Intersection.MeshRay(mesh,ray,faceIDs)
    if rayP >= 0.0:
        rayPt = ray.PointAt(rayP)
        faceIDs = list(faceIDs.Value)
        return rayPt,faceIDs
    else:
        return None, None

def ref(v,n):
   """ Calculate reflection vector """
    d = rs.VectorDotProduct(v,n)
    ref = rs.VectorReverse(v-(2*d*n))
    return ref


XPt, XIDs = meshRayIntersect(MyMesh,MyPoint,MyVector)

normal_list =  rs.MeshFaceNormals(MyMesh)
facenormal = normal_list[XIDs[0]]

reflex_vec = ref(MyVector,facenormal)


Raybouncing_3_mesh.gh (11.0 KB)

1 Like

Yes exactly, shove that in a loop and you should be good :slight_smile:

Hi @dale,

Would it be possible to expose the MeshRay functionality as RhinoScript method for V7 ?
It has a potential to speed up a lot of tools we have that currently rely either on mesh/line intersection or PointPick but have to filter out all the results just to get the first ray bounce, which is what I am after 99% of cases.

thank you,

–jarek

1 Like