Here I have a list of lines and I am trying to loop through each of them and extract parallel ones. (check each line against one another). The second step is to then put these parallel lines into separate list and check if these intersect at more than 2 points (overlap). if yes then put them in a separate list.
Can anyone provide me with guidance on how to approach this. I believe the first step of checking parallelism is the most confusing.
Line.Direction > Vector.AngleAboutAxis > Modulo (% is the symbol) of 180 > Vector.AngleAboutAxis > List.GroupByKey
Normalize to direction vector of the line, and compare the vectors of the two lines
This is likely ideal for smaller datasets - and ks a great shout out. But as the data set grows you’ll run into performance issues as you have to test all objects against all other objects (N^2) instead of testing all objects once and grouping them (N). While the action of comparing vectors with the ‘is parallel node’ is fast, you still have a quadratic complexity (or near enough for now) that the other option is higher performing as your dataset grows.
can you please explain what should go in the inputs of Vector.AngleAboutAxis?
Can you explain this in a little detail? i am still a little confused. very new to this
I was trying to understand this solution as well Find which lines are parallel
What type of element are you working with? It’s likely you want to pull the location line, or the curve… Flatten the list of curves if not. Be sure you only have one curve per element.
Assuming. You are working in plan. To start the angle about axis, the first vector is the line direction. The second is the global X axis (Vector.XAxis), and the last is the global Z axis (Vector.ZAxis).
I am bringing in a list of lines
If those are line elements (such as detail lines or model lines) there is a CurveElement class in the library which has a node along the lines of CurveElement.Curve or LocationCurve or similar.
Hi, i am not understanding why are we using curves and why cant lines be used. Even if we extract curves, there are still going to be lines with (start point, endpoint and direction). I would like to understand the concept and logic behind this approach.
I do see that the way the list comes out is slightly different - bY curves. But you can flatten the lines too and get the same format
Flattening the lines also works - no list level though you want it completely flat. The drawback to that is you are more than doubling the amount of memory used as Dynamo has to remember the data the way you pull it at first, and then the way you manipulate it.
The good news is that from either the flattened list or the directly quarried list you can pull the direction of the line and then get the angle from the X axis and progress from there.
A Python solution using Linq with a custom bi-directional representation
code (IronPython3 or PythonNet3)
import sys
import clr
import System
from System import Array
from System.Collections.Generic import List, IList, Dictionary, HashSet
clr.AddReference('ProtoGeometry')
import Autodesk.DesignScript.Geometry as DS
from Autodesk.DesignScript.Geometry import *
clr.AddReference("System.Core")
clr.ImportExtensions(System.Linq)
import time
def bi_direction_representation(line):
v1 = line.Direction.Normalized()
v2 = v1.Reverse()
lst_vect = sorted([v1, v2], key = lambda v : (v.X, v.Y, v.Z))
vect_repr = "|".join([f"Vect({v.X:.2f},{v.Y:.2f},{v.Z:.2f})" for v in lst_vect])
return vect_repr.replace("-0.00", "0.00")
ds_lines = List[DS.Curve](IN[0])
t1 = time.time()
groups = ds_lines.GroupBy[DS.Curve, System.String](System.Func[DS.Curve, System.String](
lambda c : bi_direction_representation(c)))\
.Select(System.Func[System.Object, System.Object](lambda x : x.ToList()))\
.ToList()
elapse_time = time.time() - t1
OUT = f"{elapse_time=:.2f}s", groups
then you can search for overlapped lines in each group using the DoesIntersect()
method,
3 Likes