I’ve hit a wall on what should be a simple problem. I’m creating a polyline from a list of points, and I want to assign it to a layer (specified by a string). the function executes without error, but it doesn’t make the change in the document (by inspection).
What am I doing wrong?
def InsertPolyLine(doc, Points: list, Layer: str):
ob = doc.Objects
rg = Rhino.Geometry
for i in range(len(Points)):
Points[i] = rg.Point3d(Points[i][0], Points[i][1], 0.0)
poly = rg.Polyline()
for p in Points:
poly.Add(p)
if poly.IsValid:
poly = doc.Objects.Find(ob.AddPolyline(poly))
poly.Attributes.LayerIndex = doc.Layers.FindName(Layer).Index
doc.Views.Redraw()
return poly
import Rhino
from Rhino import Geometry as rg
import scriptcontext as sc
import rhinoscriptsyntax as rs
def TestInsertPL(pts,layer_name):
poly=rg.Polyline(pts)
if poly.IsValid:
layer_index=sc.doc.Layers.FindByFullPath(layer_name,False)
if layer_index and layer_index != -1:
attrs=Rhino.DocObjects.ObjectAttributes()
attrs.LayerIndex=layer_index
obj_id=sc.doc.Objects.AddPolyline(poly,attrs)
sc.doc.Views.Redraw()
return obj_id
else:
print("Layer does not exist")
pts=rs.GetPoints("Pick points")
if pts:
result=TestInsertPL(pts,"PointsLayer")
if not result: print("Unable to comply")
Thanks for that. This solution assigns the layer (and other attributes) at the time of creation, which is good enough for my application, but how would you go about changing the layer of an existing polyline?
In my case, I expected to create the polyline, then change it. I’m happy with your solution, but still curious about changing an existing polyline.
Well, once the polyline has been written to the Rhino document, it has an ID - you can then use the rhinoscriptsyntax method rs.ObjectLayer() to change the object layer:
#add the layer if it doesn't already exist
if not rs.IsLayer(new_layer): rs.AddLayer(new_layer)
#change the object layer
rs.ObjectLayer(obj,new_layer)
If you want to stay in RhinoCommon:
import Rhino
from Rhino import Geometry as rg
import scriptcontext as sc
import rhinoscriptsyntax as rs
def TestInsertPL(pts,layer_name):
poly=rg.Polyline(pts)
if poly.IsValid:
layer_index=sc.doc.Layers.FindByFullPath(layer_name,False)
if layer_index and layer_index != -1:
#add the polyline to the document and return the ID
obj_id=sc.doc.Objects.AddPolyline(poly)
#get the object reference from the ID
rhobj=sc.doc.Objects.Find(obj_id)
#change the layer index
rhobj.Attributes.LayerIndex=layer_index
rhobj.CommitChanges()
sc.doc.Views.Redraw()
return obj_id
else:
print("Layer does not exist")
pts=rs.GetPoints("Pick points")
if pts:
result=TestInsertPL(pts,"PointsLayer")
if not result: print("Unable to comply")
In general, once you are dealing with objects in the document with GUID’s, it’s just much easier to use rhinoscriptsyntax.
Thanks for that. So far, I’ve been avoiding rhinoscriptsyntax (just to avoid too many flavours of python), but this is a solid argument for its inclusion.