Hi guys,
the issue that I am posting here is a little extended, but I will try to be as clear as possible. I also think its proper to clarify that I am developing my own Zero Touch Nodes in Visual Studio.
The problem I am having is due to a very strange behavior causing Revit and Dynamo to freeze for ever. When I try to run my code in debug mode, Visual Studio after a 1-2 mins gives me the following error .
This happens when I try to run a method to create Direct Shapes from solids within a larger method, which I will post further below as well.
Here is the Direct Shape method:
private static void CreateDirectShape( Autodesk.Revit.DB.Document doc, Autodesk.DesignScript.Geometry.Solid volume, string json, string name)
{
TransactionManager.Instance.EnsureInTransaction(doc);
try
{
IList<GeometryObject> solids = volume.ToRevitType();
Autodesk.Revit.DB.DirectShape ds = Autodesk.Revit.DB.DirectShape.CreateElement(doc, directShapeIDCategory);
ds.SetShape(solids);
ds.get_Parameter(_bip_properties).Set(json);
ds.Name = "Area volume for " + name;
}
catch (Exception ex)
{
throw new ArgumentException(ex.ToString());
}
TransactionManager.Instance.TransactionTaskDone();
}
Here is the main method which is wrapped in a Dynamo Node. I removed some parts for simplicity, so dont be surprised if you dont see consistency with certain variables. CreateDirectShape()
is used in the last part of GetAreasByProperties()
.
[Autodesk.DesignScript.Runtime.MultiReturn(new[] { "Volumnes","Heights", "Boundary Curve", "Area Names"})]
public static Dictionary<string, object> GetAreasByProperties(List<wrappedRevitElement> areaObjects, wrappedRevitLevel level, List<wrappedRevitElement> levelObjects, string inputAreaName,
bool filterByName, bool filterByLevel)
{
// Get current document
Autodesk.Revit.DB.Document doc = DocumentManager.Instance.CurrentDBDocument;
// Initilaize transaction
// TransactionManager.Instance.EnsureInTransaction(doc);
if (filterByName == true && filterByLevel == true)
{
XYZ firstCrvSrtPoint = new XYZ();
Area areaObj = null;
foreach (var item in revitElements)
{
if (item.Category.Name == "Areas")
{
areaObj = item as Area;
areaObjectElevations.Add(areaObj.Level.Elevation);
areaObjectsTemp.Add(areaObj);
if (areaObjectName == inputAreaName && areaObj.Level.Name == revitLevel.Name)
{
areaNames.Add(areaObj.Name);
List<XYZ> BoundaryCrvSegmentEndpoints = new List<XYZ>();
if (areaObj.Area <= 0) throw new ArgumentException("Area Element must have an Area greater than 0!");
else
{
string json = CreateJsonFromElementProperties(areaObj);
JsonStrings.Add(json);
IList<IList<BoundarySegment>> boundSegments = areaObj.GetBoundarySegments(bOptions);
for (int i = 0; i < boundSegments.Count; i++)
{
IList<BoundarySegment> data = boundSegments[i];
int count = 0;
for (int j = 0; j < data.Count; j++)
{
crvs.Add(data[j].GetCurve().ToProtoType());
count++;
if (count == 1)
{
Curve c = data[j].GetCurve();
firstCrvSrtPoint = c.GetEndPoint(0);
c.Dispose();
}
Curve unwrappedRevitCurve = data[j].GetCurve();
BoundaryCrvSegmentEndpoints.Add(unwrappedRevitCurve.GetEndPoint(0)); // 0 index for start point
// Dispose unwrappedRevitCurve Revit curve
unwrappedRevitCurve.Dispose();
}
}
}
BoundaryCrvSegmentEndpoints.Add(firstCrvSrtPoint);
boundary.Add(PolyLine.Create(BoundaryCrvSegmentEndpoints).ToProtoType());
//dispose points after used to create polyline
foreach (XYZ point in BoundaryCrvSegmentEndpoints)
{
point.ToPoint().Dispose();
}
}
}
else
{
throw new ArgumentException("Your Elements need to be of Category of type Area!");
}
}
bOptions.Dispose();
firstCrvSrtPoint.ToPoint().Dispose();
if (boundary.Count == 1)
{
unwrappedRevitLevel nextLevelUp = GetNextLevelUp(areaObj, levelObjects);
double nextLevelUpElevation = nextLevelUp.Elevation * 304.8; // convert decimal feet to mm
double areaObjElevation = areaObj.Level.Elevation * 304.8; // convert decimal feet to mm
double extrusionHeight = nextLevelUpElevation - areaObjElevation;
heights.Add(extrusionHeight);
// Create volumes
for (int i = 0; i < boundary.Count; i++)
{
Autodesk.DesignScript.Geometry.Solid solid = boundary[i].ExtrudeAsSolid(Autodesk.DesignScript.Geometry.Vector.ZAxis(), extrusionHeight);
CreateDirectShape(doc, solid, JsonStrings[i], areaNames[i]);
volumes.Add(solid);
}
}
}
}
Its also puzzling to see that when I wrote a totally independent test method, wrapped in its own dynamo Node, the corresponding Direct Shape was added succesfully to the current Revit document. Here it is for reference:
public static void CreateDirectShapeB(bool run, double width, double height)
{
// Get current document
Autodesk.Revit.DB.Document doc = DocumentManager.Instance.CurrentDBDocument;
// Initilaize transaction
TransactionManager.Instance.EnsureInTransaction(doc);
if (run)
{
try
{
List<XYZ> pts = new List<XYZ>();
XYZ center = XYZ.Zero;
XYZ topRightCorn = center + new XYZ(width, width, 0);
XYZ bottomRightCorn = center + new XYZ(width, width*-1, 0);
XYZ topLeftCorn = center + new XYZ(width*-1, width, 0);
XYZ bottomLeftCorn = center + new XYZ(width * -1, width * -1, 0);
pts.Add(topRightCorn);
pts.Add(topLeftCorn);
pts.Add(bottomLeftCorn);
pts.Add(bottomRightCorn);
pts.Add(topRightCorn);
Autodesk.DesignScript.Geometry.PolyCurve bounds = PolyLine.Create(pts).ToProtoType();
var solid = bounds.ExtrudeAsSolid(Autodesk.DesignScript.Geometry.Vector.ZAxis(), height);
Autodesk.Revit.DB.DirectShape ds = Autodesk.Revit.DB.DirectShape.CreateElement(doc, directShapeIDCategory);
ds.SetShape(solid.ToRevitType());
}
catch (Exception ex)
{
throw new ArgumentException(ex.ToString());
}
}
TransactionManager.Instance.TransactionTaskDone();
}
I hope I was clear enough (: Any help would be great!