StartPoint of Curve in Python

Hi guys,

i started learning Python and have a very basic problem. How do i get the Startpoint of a curve. Can i use Design Script syntax?
I think i first have to convert the curve in a Python readable type?

Thanks for the help!

Laurin

1 Like

Curve.GetEndPoint(0) or GetEndPoint(1)

GetEndPoint(0"or1") doesn’t work but PointAtParameter(0) works

2 Likes

GetEndPoint is a Revit API method for Revit points.
curve1.EndPoint

you can’t use designscript syntax in Python - thats why they are different languages.

The method Curve.EndPoint() - is really an instance method of the curve class, so you call it on Curve instances, like curve1.

In DS we also transform these into statically callable methods so it’s easy to call them both ways, but python of course does not do this.

4 Likes

Hi @Michael_Kirschner2,

thanks for replying!
Am i still using the wrong syntax? Bc all the methods from the dir(surface1) and dir(curve1) are not working. Or do i have to convert the surface/curve first?

Thanks again!

The error says:
TypeError: ‘Surface’ object is not subscriptable

Try to convert the lines first. In a separate pythonscript.
Import:
clr.AddReference(“RevitNodes”)
import Revit
clr.ImportExtensions(Revit.Elements)
clr.ImportExtensions(Revit.GeometryConversion)
from Revit import GeometryConversion as gp

Add .ToRevitType() after each dynamo curve.
Im not sure if this also works on surfaces.

You dont need to unwrap dynamo lines.
You also cannot mix ProtoGeometry calls with Revit API calls within one python node.

why do you think thats the case? There should be no reason you can’t mix these calls in a single python context.

@laurin.ernstMA6Q3 - the error means you can’t do surface1[0] because surface1 is a surface not a list of surfaces.

What I meant is that you can combine dynamo commands and api commands within one dynamo Script but not in one Python node .This is my experience so far. If you know a way to mix dynamo commands and api commands in one python node please let me know. It has to do with the imported references. For example if you import revit api in a python node it doesnt recognise the designscript point.bycoordinates() command anymore in that same node, because it is another language. What works is create dynamo geometry in one node and then input it in a second python node. In the second one you can then import api methods.

Okay, very interesting!
Thanks @wouter.hilhorst. This information helps alot.
Do you know if there is any documentation for the Autodesk DesignScript library?

If you select a node from the library, select it, and then you right click on the background around the node (not on the node) you get an option ‘node to code’. That can be copied to a python script

Oh i mean a documentation of all the methods of the library.
Like for example the numpy library has a really nice documentation:
https://numpy.org/doc/

I only found a library for the revit api, not for design script.

This is not the case - my guess is that you are are encountering a namespace collision and need to use fully namespaced methods.

For example, the collision between Dynamo Curve and Revit.db.curve

prefix these types with the full namespace:
Autodesk.DesignScript.Geometry and Autodek.Revit.db

It makes sense you might have trouble if you try to do:
from xyzNamespace import * on both modules as you’ll have a bunch of types with the same short name. Instead refer to the classes by their full names.

3 Likes

Thanks, I didnt know that!

You sure can mix the two, as long as you are converting to the appropriate types first for the appropriate method call (so if you are calling a method in the Revit API, then convert to RevitType, conversely, if you are calling a DS Method, then convert to DSType). For example, take a look at the python code below…

import clr

clr.AddReference('ProtoGeometry')
from Autodesk.DesignScript import Geometry as geom # I am using geom as a keyword here to avoid Type name clashes. For DS Types, use "geom." i.e. geom.Line.ByStartPointEndPoint(). You should have intellisense still, but it is almost exactly the same as the Dynamo Library TreeView... 

clr.AddReference("RevitServices")
import RevitServices
from RevitServices.Persistence import DocumentManager
doc =  DocumentManager.Instance.CurrentDBDocument

# You require this for Converting between Revit/DS Types...
clr.AddReference("RevitNodes")
import Revit
clr.ImportExtensions(Revit.Elements)
clr.ImportExtensions(Revit.GeometryConversion)

clr.AddReference("RevitAPI")
from Autodesk.Revit.DB import *

def tolist(obj1):
	if hasattr(obj1,"__iter__"): return obj1
	else: return [obj1]

# Some Curve Based Element (e.g. Structural Framing Element)...
elem = tolist(UnwrapElement(IN[0]))[0]

# Getting the Revit Curve of the Element...
rvtCrv = elem.Location.Curve

# Getting the Revit Curves Start Point via Revit API...
rvtStartPoint = rvtCrv.GetEndPoint(0)

# Converting the Revit curve to a DS Curve...
dsCrv = rvtCrv.ToProtoType()

# Getting the DS Curves StartPoint via the DS Types StartPoint Property...
dsStartPoint = dsCrv.StartPoint

# Creating a new DS Line by Start Point End Point where Start Point is a RevitType XYZ from the Revit Curve and then converted to DS Point via the .ToPoint() Extension Method. And using the DS Curves EndPoint Property... 
otherCrv = geom.Line.ByStartPointEndPoint(rvtCrv.GetEndPoint(0).ToPoint(), dsCrv.EndPoint)

# NOTE: See how I used the keyword 'geom' to shortcut to Autodesk.DesignScript.Geometry, this should help you avoid Type name clashing Revit API and DS Types...

# Returns a List of the Revit Type Curve, its Type, the Revit StartPoint and its Type. Then the DS Curve, its Types, its StartPoint and its Type, and finally, the DS Line we created as otherCrv...
OUT = [[rvtCrv, rvtCrv.GetType(), rvtStartPoint, rvtStartPoint.GetType()], [dsCrv, dsCrv.GetType(), dsStartPoint, dsStartPoint.GetType()]], otherCrv

As for documentation of the DS Methods, they are almost identical to the Dynamo Library TreeView, so Geometry.Line.ByStartPointEndPoint would be the same as Geometry > Line > StartPointEndPoint, this is probably why there is no need for documentation like the Revit API Docs as the Dynamo Library sort of is already.

6 Likes

a pretty viable short term solution is fuget.org - which uses nuget packages - https://www.fuget.org/packages/DynamoVisualProgramming.ZeroTouchLibrary/2.7.0.9206/lib/net48/ProtoGeometry.dll/Autodesk.DesignScript.Geometry/Circle

1 Like

Hi,

Thanks for the clear explanation! Thats very usefull.

Do you know if there is also a way to see how the Dynamo-nodes (that interact directly with Revit) use the Revit API?

I can image it is usefull to combine Dynamo nodes that create or interact with dynamo geometry together with Revit api methods.

Dynamo also has a lot of very handy nodes that interact with revit geometry, Like rotating familys, changing paramters, etc…

They must also use the API library for this, I guess?

It feels a bit like a detour to use these nodes in a python script because you can also directly use API methods…

Wouter Hilhorst

Verzonden vanuit Mail voor Windows 10

You’re welcome @wouter.hilhorst!

Sure, check out the Github for DynamoRevit, I have taken you to the Revit Nodes specifically. This is all in C#, but you can get a feel for how the Revit API is being leveraged.

Generally, when interacting with revit, it’s better to stick purely to the Revit API, but you can use the DS for revit nodes too, but you’ll need to convert to DSType and might incur a performance hit (not sure if it does for sure though). And yes, when manipulating revit elements, the DS for Revit nodes use the Revit API. The only times you would need DS Geometry nodes are when you are really dealing with Geometry, revit has very little in the way of a geometry manipulation library and can get quite verbose and mathy. For example, projecting a curve to a surface or plane, while this sounds simple in dynamo, in the revit api, not so much. This is one thing that makes Dynamo very powerful IMO.

As for rotating elements, updating parameters etc etc, this is super easy with the Revit API. Entry level stuff as there are very solid methods and utility classes just for these.

2 Likes