private int ThreeEdges(Curve[] x) //给定三条曲线,通过数值判断相互之间的关系(0:互不相干,1:有一对有交点,2:有两对有交点,3:封闭三边) { Rhino.Geometry.Intersect.CurveIntersections cin1 = Rhino.Geometry.Intersect.Intersection.CurveCurve(x[0], x[1], 0, 0); Rhino.Geometry.Intersect.CurveIntersections cin2 = Rhino.Geometry.Intersect.Intersection.CurveCurve(x[0], x[2], 0, 0); Rhino.Geometry.Intersect.CurveIntersections cin3 = Rhino.Geometry.Intersect.Intersection.CurveCurve(x[1], x[2], 0, 0); int a = 0; int b = 0; int c = 0; if (cin1.Count == 1) { a = 1; } if (cin2.Count == 1) { b = 1; } if (cin3.Count == 1) { c = 1; } int mm = a + b + c; return(mm); }
////////////////////////////////////////////////////////////////////////////////////////////////////////删除有重合的曲线(只要有重合部分,都删除) public static List <Curve> deleteSameCurve(List <Curve> x, double tolerance) { List <Curve> afterCr = new List <Curve>(); for (int i = 0; i < x.Count; i += 0) { Curve a = x[i]; int notOne = 0; afterCr.Add(a); x.RemoveAt(i); for (int j = 0; j < x.Count; j++) { Curve b = x[j]; Rhino.Geometry.Intersect.CurveIntersections cin = Rhino.Geometry.Intersect.Intersection.CurveCurve(a, b, 0, 0); int mm = cin.Count; double toler = Math.Abs(a.GetLength() - b.GetLength()); Point3d pa = a.PointAtNormalizedLength(0.5); Point3d pb = b.PointAtNormalizedLength(0.5); double distance = Math.Abs(pa.DistanceTo(pb)); if (mm == 1 && toler <= tolerance && distance <= tolerance) { notOne += 1; x.RemoveAt(j); j--; } } if (notOne > 0) { afterCr.RemoveAt(afterCr.Count - 1); } } return(afterCr); }
private List <Plane> IntersectSegment(Curve boundary, Point3d pt1, Point3d pt2, Plane p1, Plane p2, ref bool inside) { Line l = new Line(pt1, pt2); Curve lcrv = l.ToNurbsCurve(); lcrv.Domain = new Interval(0, 1.0); Rhino.Geometry.Intersect.CurveIntersections ci = Rhino.Geometry.Intersect.Intersection.CurveCurve(boundary, lcrv, 1.0, 1.0); List <Plane> planes = new List <Plane>(); if (ci.Count < 1) { //inside = false; return(planes); } if (ci.Count % 2 == 0) { inside = false; } for (int i = 0; i < ci.Count; ++i) { planes.Add(Interpolation.InterpolatePlanes2(p1, p2, ci[i].ParameterB)); } return(planes); }
public static List <Point3d> GetAllCurveIntersections(List <Curve> curves, bool unique) { int numCurves = curves.Count; List <Point3d> allIntersectionPoints = new List <Point3d>(); for (int i = 0; i < numCurves; i++) { for (int j = 0; j < numCurves; j++) { if (j != i) { Rhino.Geometry.Intersect.CurveIntersections ccx = Rhino.Geometry.Intersect.Intersection.CurveCurve(curves[i], curves[j], 0.1, 0.1); for (int k = 0; k < ccx.Count; k++) { if (ccx[k].IsPoint) { allIntersectionPoints.Add(ccx[k].PointA); } } } } } return(unique ? new List <Point3d>(Point3d.CullDuplicates(allIntersectionPoints, 0.1)) : allIntersectionPoints); }
/// <summary> /// This is the method that actually does the work. /// </summary> /// <param name="DA">The DA object is used to retrieve from inputs and store in outputs.</param> protected override void SolveInstance(IGH_DataAccess DA) { List <Curve> curves = new List <Curve>(); double tolerance = 0; if (!DA.GetDataList(0, curves)) { return; } if (!DA.GetData(1, ref tolerance)) { return; } List <Curve> x = curves; List <Curve> afterCr = new List <Curve>(); DataTree <Curve> deleteCr = new DataTree <Curve>(); int index = 0; int branch = DA.Iteration; for (int i = 0; i < x.Count; i++) { if (x[i] == null) { continue; } int notOne = 0; afterCr.Add(x[i]); Curve a = afterCr[afterCr.Count - 1]; x[i] = null; for (int j = 0; j < x.Count; j++) { if (x[j] == null) { continue; } Curve b = x[j]; Rhino.Geometry.Intersect.CurveIntersections cin = Rhino.Geometry.Intersect.Intersection.CurveCurve(a, b, 0, 0); int mm = cin.Count; double toler = Math.Abs(a.GetLength() - b.GetLength()); Point3d pa = a.PointAtNormalizedLength(0.5); Point3d pb = b.PointAtNormalizedLength(0.5); double distance = Math.Abs(pa.DistanceTo(pb)); if (mm == 1 && toler <= tolerance && distance <= tolerance) { notOne += 1; deleteCr.Add(x[j], new GH_Path(0, branch, index)); x[j] = null; } } if (notOne > 0) { deleteCr.Add(afterCr[afterCr.Count - 1], new GH_Path(0, branch, index)); afterCr.RemoveAt(afterCr.Count - 1); index++; } } DA.SetDataList(0, afterCr); DA.SetDataTree(1, deleteCr); }
/// <summary> /// This is the method that actually does the work. /// </summary> /// <param name="DA">The DA object is used to retrieve from inputs and store in outputs.</param> protected override void SolveInstance(IGH_DataAccess DA) { ///////////////////////////////////////////////////////////////////////////////////////////////////声明变量 List <Curve> c = new List <Curve>(); double t1 = 0; double t2 = 0; ///////////////////////////////////////////////////////////////////////////////////////////////////检测输入端是否合理 if (!DA.GetDataList(0, c)) { return; } if (!DA.GetData(1, ref t1)) { return; } if (!DA.GetData(2, ref t2)) { return; } DataTree <Curve> last = new DataTree <Curve>(); DataTree <Point3d> collects = ViperClass.EmptyTree(c.Count); int index = 0; int branch = DA.Iteration; for (int i = 0; i < c.Count; i++) { for (int q = i + 1; q < c.Count; q++) { Rhino.Geometry.Intersect.CurveIntersections result = Rhino.Geometry.Intersect.Intersection.CurveCurve(c[i], c[q], t1, t2); if (result.Count > 0) ////有交集 { for (int k = 0; k < result.Count; k++) ////记录每次相交的t值并分别赋值给两曲线 { collects.Branch(i).Add((result[k].PointA)); collects.Branch(q).Add((result[k].PointB)); } } } } ///////////////////////////////////////////////////////////////////////////////////////////////// for (int i = 0; i < c.Count; i++) { if (collects.Branch(i).Count == 0) { last.Add(c[i], new GH_Path(0, branch, index)); index++; continue; } last.AddRange(ViperClass.SplitByPts(c[i], collects.Branch(i).ToList()), new GH_Path(0, branch, index)); index++; } DA.SetDataTree(0, last); }
public static Curve TrimWithClosedCurve(Curve trimRegion, Curve curve) { //TODO: Confirm that persistent error with Curve.Trim is my fault and not Rhino Compute. Seems to always return null, like Offset. bool curvesIntersect = Confirm.CurvesIntersect(trimRegion, curve, false); if (curve.Degree > 1) { //Current stopgap to compensate for Curve.Trim rebuilds from intersection points. Output is incorrect for nonlinear curves. return(curve); } Console.WriteLine("Curves intersect!"); Console.WriteLine(curve.PointAtStart.ToString()); if (!curvesIntersect) { Console.WriteLine("Trim region and curve do not intersect. Returning original curve."); return(curve); } List <Point3d> trimPoints = new List <Point3d>(); Rhino.Geometry.Intersect.CurveIntersections ccx = Rhino.Geometry.Intersect.Intersection.CurveCurve(trimRegion, curve, 0.1, 0.1); if (ccx.Count != 2) { Console.WriteLine("Not exactly two intersection events. Circulation axis placement is invalid. Returning original curve."); return(curve); } for (int i = 0; i < ccx.Count; i++) { trimPoints.Add(ccx[i].PointB); } Curve trimmedCurve = new LineCurve(trimPoints[0], trimPoints[1]); /* * if (trimmedCurve == null) * { * Console.WriteLine("Damn."); * return curve; * } */ return(trimmedCurve); }
public static Curve BooleanOpenCurve(Curve ClosedC, Curve C, out int result) { PointContainment cont0 = ClosedC.Contains(C.PointAtEnd, Plane.WorldXY, 0.01); PointContainment cont1 = ClosedC.Contains(C.PointAtStart, Plane.WorldXY, 0.01); bool isCurveInsideStart = (cont0 == PointContainment.Inside || cont0 == PointContainment.Coincident); bool isCurveInsideEnd = (cont1 == PointContainment.Inside || cont1 == PointContainment.Coincident); Rhino.Geometry.Intersect.CurveIntersections ci = Rhino.Geometry.Intersect.Intersection.CurveCurve(C, ClosedC, 0.01, 0.01); Interval interval = C.Domain; if (isCurveInsideStart && isCurveInsideEnd) { result = 2; return(C); } else if (isCurveInsideStart && !isCurveInsideEnd) { result = 1; if (ci.Count == 0) { result = 0; return(null); } return(C.Trim(ci[0].ParameterA, interval.T0)); } else if (!isCurveInsideStart && isCurveInsideEnd) { if (ci.Count == 0) { result = 0; return(null); } result = 1; return(C.Trim(interval.T1, ci[0].ParameterA)); } else { if (ci.Count == 2) { result = 1; return(C.Trim(ci[0].ParameterA, ci[1].ParameterA)); } } result = 0; return(null); }
public static Tuple <Point3d, Point3d> CurveCurveIntersectionPoints(Curve C0, Curve C1, double t) { Rhino.Geometry.Intersect.CurveIntersections ci = Rhino.Geometry.Intersect.Intersection.CurveCurve(C0, C1, t, t); Line line = Line.Unset; if (ci.Count > 0) { Rhino.Geometry.Intersect.IntersectionEvent intersection = ci[0]; return(new Tuple <Point3d, Point3d>(intersection.PointA, intersection.PointB)); } return(null); }
public static Tuple <double, double> CurveCurveInter(Curve C0, Curve C1, double t) { Rhino.Geometry.Intersect.CurveIntersections ci = Rhino.Geometry.Intersect.Intersection.CurveCurve(C0, C1, t, t); Line line = Line.Unset; if (ci.Count > 0) { Rhino.Geometry.Intersect.IntersectionEvent intersection = ci[0]; return(new Tuple <double, double>(intersection.ParameterA, intersection.ParameterB)); } return(null); }
/// <summary> /// This is the method that actually does the work. /// </summary> /// <param name="DA">The DA object is used to retrieve from inputs and store in outputs.</param> protected override void SolveInstance(IGH_DataAccess DA) { ///////////////////////////////////////////////////////////////////////////////////////////////////声明变量 Curve curveA = null; List <Curve> curveB = new List <Curve>(); ///////////////////////////////////////////////////////////////////////////////////////////////////检测输入端是否合理 if (!DA.GetData(0, ref curveA)) { return; } if (!DA.GetDataList(1, curveB)) { return; } List <Point3d> pts = new List <Point3d>(); Curve[] crs; for (int i = 0; i < curveB.Count; i++) { Rhino.Geometry.Intersect.CurveIntersections cin = Rhino.Geometry.Intersect.Intersection.CurveCurve(curveA, curveB[i], 0, 0); int mm = cin.Count; if (mm >= 1) { Rhino.Geometry.Intersect.IntersectionEvent[] evt = new Rhino.Geometry.Intersect.IntersectionEvent[mm]; for (int k = 0; k < mm; k++) { evt[k] = cin.ElementAt(k); pts.Add(evt[k].PointA); } } } List <double> ts = new List <double>(); if (pts.Count >= 1) { for (int j = 0; j < pts.Count; j++)////点在curve上的t值 { double t = 0; curveA.ClosestPoint(pts[j], out t); ts.Add(t); } } crs = curveA.Split(ts); DA.SetDataList(0, crs); }
public static Tuple <double, double> CurveCurveIntersection(Curve C0, Curve C1, double t) { //Rhino.RhinoApp.WriteLine("WTF"); Rhino.Geometry.Intersect.CurveIntersections ci = Rhino.Geometry.Intersect.Intersection.CurveCurve(C0, C1, t, t); Line line = Line.Unset; if (ci.Count > 0) { Rhino.Geometry.Intersect.IntersectionEvent intersection = ci[0]; //Rhino.RhinoApp.WriteLine(intersection.ParameterA.ToString() +" " + intersection.ParameterB.ToString()); return(new Tuple <double, double>(intersection.ParameterA, intersection.ParameterB)); } return(null); }
public static CCX CurveCurveIntersectionCCX(Curve C0, Curve C1, double t) { Rhino.Geometry.Intersect.CurveIntersections ci = Rhino.Geometry.Intersect.Intersection.CurveCurve(C0, C1, t, t); Line line = Line.Unset; if (ci.Count > 0) { Rhino.Geometry.Intersect.IntersectionEvent intersection = ci[0]; return(new CCX() { t0 = intersection.ParameterA, t1 = intersection.ParameterB, p0 = intersection.PointA, p1 = intersection.PointB }); } return(null); }
public static List <Point3d> CurveCurveIntersectionAllPts(Curve C0, Curve C1, double t = 0.01) { Rhino.Geometry.Intersect.CurveIntersections ci = Rhino.Geometry.Intersect.Intersection.CurveCurve(C0, C1, t, t); List <Point3d> pts = new List <Point3d>(); Line line = Line.Unset; if (ci.Count > 0) { foreach (Rhino.Geometry.Intersect.IntersectionEvent inter in ci) { pts.Add(inter.PointA); } return(pts); } return(null); }
/// <summary> /// This is the method that actually does the work. /// </summary> /// <param name="DA">The DA object is used to retrieve from inputs and store in outputs.</param> protected override void SolveInstance(IGH_DataAccess DA) { List <Curve> curves = new List <Curve>(); double tolerance = 0; if (!DA.GetDataList(0, curves)) { return; } if (!DA.GetData(1, ref tolerance)) { return; } int num = curves.Count; List <Curve> curs = new List <Curve>(); for (int i = 0; i < num - 2; i++) { for (int j = i + 1; j < num - 1; j++) { Rhino.Geometry.Intersect.CurveIntersections cin = Rhino.Geometry.Intersect.Intersection.CurveCurve(curves[i], curves[j], 0, 0); int mm = cin.Count; if (mm >= 1) { for (int k = j + 1; k < num; k++) { Rhino.Geometry.Intersect.CurveIntersections cin2 = Rhino.Geometry.Intersect.Intersection.CurveCurve(curves[k], curves[j], 0, 0); int nn = cin2.Count; if (nn >= 1) { Curve[] cr3d = { curves[i], curves[j], curves[k] }; Curve[] clr = Curve.JoinCurves(cr3d, tolerance); if (clr[0].IsClosed) { curs.Add(clr[0]); } } } } } } DA.SetDataList(0, curs); }
public List <Curve> SplitCurveByCurves(Curve c, List <Curve> crvs, double tol, out List <Point3d> assPts, List <Point3d> pts = null) { List <double> paras = new List <double>(); foreach (Curve cc in crvs) { Rhino.Geometry.Intersect.CurveIntersections cin = Rhino.Geometry.Intersect.Intersection.CurveCurve(c, cc, tol, tol); if (cin != null) { for (int i = 0; i < cin.Count; ++i) { if (cin[i].IsPoint) { paras.Add(cin[i].ParameterA); } } } } List <Point3d> apts = new List <Point3d>(); if (pts != null) { foreach (Point3d p in pts) { double t; if (c.ClosestPoint(p, out t, tol)) { paras.Add(t); apts.Add(p); } } } if (apts.Count == 0) { assPts = null; } else { assPts = apts; } return(c.Split(paras).ToList()); }
/// <summary> /// This is the method that actually does the work. /// </summary> /// <param name="DA">The DA object can be used to retrieve data from input parameters and /// to store data in output parameters.</param> protected override void SolveInstance(IGH_DataAccess DA) { List <Curve> curves = new List <Curve>(); DA.GetDataList(0, curves); int N = curves.Count; List <Layer> layers = new List <Layer>(); int m = 100; //Create layers foreach (Curve l in curves) { layers.Add(new Layer(l)); } //Calculate the distance from each point to the previous layer for (int i = 1; i < N; i++) { foreach (Target p in layers[i].Nodes) { Plane orthoPlane = new Plane(p.Position, layers[i].LayerCurve.TangentAt(layers[i].CurveParameters[p])); Rhino.Geometry.Intersect.CurveIntersections layerPlane = Rhino.Geometry.Intersect.Intersection.CurvePlane(layers[i - 1].LayerCurve, orthoPlane, 0.001); double h = 1000; foreach (Rhino.Geometry.Intersect.IntersectionEvent e in layerPlane) { if (e.PointA.DistanceTo(p.Position) < h) { h = e.PointA.DistanceTo(p.Position); } } p.H_ = h; } } }
void subSrf(Surface S, ref List <Curve> C, ref List <Surface> Srf, int nGen) { double tol = Rhino.RhinoDoc.ActiveDoc.ModelAbsoluteTolerance; bool inters = false; // check if intersection happened if (nGen > 0) { //loop through curves foreach (Curve Cr in C) { Rhino.Geometry.Intersect.CurveIntersections intEvent = Rhino.Geometry.Intersect.Intersection.CurveSurface(Cr, S, tol, tol); if (intEvent.Count > 0) { inters = true; break; } } if (inters && nGen >= 1) { // if intersection happened and nGens>=1 (last loop) // divide surface //Surface[] Ss = sTrim(ref S); Surface[] Ss = sDiv(ref S); // this seems a tad faster // loop through surfaces foreach (Surface Sdiv in Ss) { // call recursive subsurf subSrf(Sdiv, ref C, ref Srf, nGen - 1); } } else { // if no intersections event occurred then add surface to list Srf.Add(S); } // if nGen =0 (last iteration) add surface to the list } else { Srf.Add(S); } }
protected override void SolveInstance(IGH_DataAccess DA) { List <Curve> CurvesGuide = NGonsCore.Clipper.DataAccessHelper.FetchList <Curve>(DA, "CurvesGuide"); List <Curve> CurvesToSort = NGonsCore.Clipper.DataAccessHelper.FetchList <Curve>(DA, "CurvesToSort"); Grasshopper.DataTree <Curve> dt = new DataTree <Curve>(); int gCount = 0; foreach (Curve g in CurvesGuide) { List <double> t = new List <double>(); List <Curve> cID = new List <Curve>(); int i = 0; foreach (Curve c in CurvesToSort) { Rhino.Geometry.Intersect.CurveIntersections intersection = Rhino.Geometry.Intersect.Intersection.CurveCurve(g, c, 0.01, 0.01); if (intersection.Count > 0) { t.Add(intersection[0].ParameterA); cID.Add(c); } i++; } var tSorted = t.ToArray(); var cIDSorted = cID.ToArray(); Array.Sort(tSorted, cIDSorted); dt.AddRange(cIDSorted, new GH_Path(gCount++)); } DA.SetDataTree(0, dt); }
public static List <Point3d> GetAllCurveIntersections(Curve referenceCurve, List <Curve> otherCurves, bool unique) { //Console.WriteLine("Function called!"); List <Point3d> allIntersectionPoints = new List <Point3d>(); foreach (Curve curve in otherCurves) { Rhino.Geometry.Intersect.CurveIntersections ccx = Rhino.Geometry.Intersect.Intersection.CurveCurve(referenceCurve, curve, 0.1, 0.1); //Console.WriteLine("CCX Run!"); for (int i = 0; i < ccx.Count; i++) { if (ccx[i].IsPoint) { allIntersectionPoints.Add(ccx[i].PointA); } } //Console.WriteLine("Curve"); } if (allIntersectionPoints.Count == 0) { return(allIntersectionPoints); } if (!unique) { return(allIntersectionPoints); } else { return(new List <Point3d>(Point3d.CullDuplicates(allIntersectionPoints, 0.1))); } }
private void MultiCurveSplit(Curve[] CurveArr) { List <Double>[] CurveParametersArr = new List <double> [CurveArr.Length]; for (int i = 0; i < CurveArr.Length; i++) { List <Double> CurveParameters = new List <double>(); Rhino.Geometry.Intersect.CurveIntersections SelfInter = Rhino.Geometry.Intersect.Intersection.CurveSelf(CurveArr[i], MTolerance); for (int a = 0; a < SelfInter.Count; a++) { CurveParameters.Add(SelfInter[a].ParameterA); CurveParameters.Add(SelfInter[a].ParameterB); } for (int j = 0; j < CurveArr.Length; j++) { Rhino.Geometry.Intersect.CurveIntersections CurveInter = Rhino.Geometry.Intersect.Intersection.CurveCurve(CurveArr[i], CurveArr[j], MTolerance, MTolerance); for (int k = 0; k < CurveInter.Count; k++) { CurveParameters.Add(CurveInter[k].ParameterA); } } HashSet <Double> ParametersSet = new System.Collections.Generic.HashSet <Double>(CurveParameters); CurveParametersArr[i] = ParametersSet.ToList(); } for (int i = 0; i < CurveArr.Length; i++) { Curve[] CurveSplit = CurveArr[i].Split(CurveParametersArr[i]); foreach (Curve cs in CurveSplit) { Rhino.RhinoDoc.ActiveDoc.Objects.AddCurve(cs); } Rhino.RhinoDoc.ActiveDoc.Objects.Delete(TempRef[i], true); } }
public static List <Curve> ShatterToSegments(List <Curve> curvesToShatter) { int numCurves = curvesToShatter.Count; List <Point3d> allIntersectionPoints = new List <Point3d>(); for (int i = 0; i < numCurves; i++) { for (int j = 0; j < numCurves; j++) { if (j != i) { Rhino.Geometry.Intersect.CurveIntersections ccx = Rhino.Geometry.Intersect.Intersection.CurveCurve(curvesToShatter[i], curvesToShatter[j], 0.1, 0.1); for (int k = 0; k < ccx.Count; k++) { if (ccx[k].IsPoint) { allIntersectionPoints.Add(ccx[k].PointA); } } } } } List <Point3d> uniqueIntersectionPoints = new List <Point3d>(Point3d.CullDuplicates(allIntersectionPoints, 0.1)); //Console.WriteLine(uniqueIntersectionPoints.Count); List <Curve> allSegments = new List <Curve>(); List <double> validParameters = new List <double>(); foreach (Curve curve in curvesToShatter) { foreach (Point3d point in uniqueIntersectionPoints) { curve.ClosestPoint(point, out double t); Point3d curvePoint = curve.PointAt(t); if (point.DistanceTo(curvePoint) < 0.1) { validParameters.Add(t); } } if (validParameters.Count > 0) { Curve[] segments = curve.Split(validParameters); foreach (Curve segment in segments) { allSegments.Add(segment); } } else { allSegments.Add(curve); } validParameters.Clear(); } return(allSegments); }
/// <summary> /// This is the method that actually does the work. /// </summary> /// <param name="DA">The DA object is used to retrieve from inputs and store in outputs.</param> protected override void SolveInstance(IGH_DataAccess DA) { double span = 0; List <VariableSection> vSect = new List <VariableSection>(); if (!DA.GetData(0, ref span)) { return; } if (!DA.GetDataList(1, vSect)) { return; } int N = vSect.Count; if (N < 2) { AddRuntimeMessage(GH_RuntimeMessageLevel.Error, "VSect needs at least 2 inputs"); return; } Transform mirrorYZ = Transform.Mirror(Plane.WorldYZ); Transform mirrorXZ = Transform.Mirror(Plane.WorldZX); Point3d spPtA = new Point3d(-span * 0.5, 0, 0); Curve spCrv = new Line(spPtA, Plane.WorldXY.XAxis, span).ToNurbsCurve(); Curve spCrvHlf = new Line(spPtA, Plane.WorldXY.XAxis, span * 0.5).ToNurbsCurve(); //if (N < 2) { N = 3; } double[] spCrvDiv = spCrv.DivideByCount(N - 1, true); Plane[] spCrvPln = spCrv.GetPerpendicularFrames(spCrvDiv); for (int i = 0; i < spCrvPln.Length; i++) //reorient planes to align with z-axis { Plane pl = spCrvPln[i]; pl.Rotate(-Math.PI * 0.5, Plane.WorldXY.XAxis); spCrvPln[i] = pl; } List <Point3d> allPts = new List <Point3d>(); List <Curve> crvs = new List <Curve>(); int ptCnt = vSect[0].sctPts.Count; Point3d[,] crvPts = new Point3d[ptCnt, vSect.Count]; //for(int i = 0; i < vSect.Count; i++) { Point3d[] crvPt = new Point3d[vSect.Count]; } for (int i = 0; i < vSect.Count; i++) //moves and reorients points from input i indicates number section, j number curve/point in section { List <Point3d> sctPts = vSect[i].sctPts; Plane sctPln = vSect[i].sctPln; if (sctPts.Count != ptCnt) { AddRuntimeMessage(GH_RuntimeMessageLevel.Error, "Each section needs the same number of points"); return; } Transform reorient = Transform.PlaneToPlane(sctPln, spCrvPln[i]); //foreach (Point3d pt in sctPts) { pt.Transform(reorient); allPts.Add(pt); } //remove when workaround is figured out for (int j = 0; j < sctPts.Count; j++) //separate points to each "row" in a list of arrays { Point3d pt = sctPts[j]; pt.Transform(reorient); crvPts[j, i] = pt; } } int degree = 3; for (int i = 0; i < crvPts.GetLength(0); i++) //creates curves through points { Point3d[] aCrvPts = new Point3d[vSect.Count]; for (int j = 0; j < crvPts.GetLength(1); j++) { aCrvPts[j] = crvPts[i, j]; } Curve crv = Curve.CreateInterpolatedCurve(aCrvPts, degree); crvs.Add(crv); } List <Brep> faces = new List <Brep>(); Brep[] loftFace = Brep.CreateFromLoft(crvs, Point3d.Unset, Point3d.Unset, LoftType.Straight, false); //Brep face1 = new Brep(); //foreach(Brep face in loftFace) { face1 = face.DuplicateBrep(); } Brep face1 = loftFace[0].DuplicateBrep(); Brep face2 = face1.DuplicateBrep(); face2.Transform(mirrorXZ); faces.Add(face1); faces.Add(face2); Curve[] naked1 = face1.DuplicateNakedEdgeCurves(true, false); Curve[] naked2 = face2.DuplicateNakedEdgeCurves(true, false); Curve[] loftCrv1 = new Curve[] { naked1[1], naked2[1] }; Curve[] loftCrv2 = new Curve[] { naked1[3], naked2[3] }; Brep[] face3 = Brep.CreateFromLoft(loftCrv1, Point3d.Unset, Point3d.Unset, LoftType.Straight, false); Brep[] face4 = Brep.CreateFromLoft(loftCrv2, Point3d.Unset, Point3d.Unset, LoftType.Straight, false); faces.Add(face3[0]); faces.Add(face4[0]); Brep[] beamBreps = Brep.JoinBreps(faces, DocumentTolerance()); Brep beam = beamBreps[0].CapPlanarHoles(DocumentTolerance()); int intersects = 0; int a = crvs.Count; for (int i = 0; i < (a - 1); i++) { for (int j = (i + 1); j < a; j++) { Rhino.Geometry.Intersect.CurveIntersections crvCheck = Rhino.Geometry.Intersect.Intersection.CurveCurve( crvs[i], crvs[j], DocumentTolerance(), 0.0); intersects += crvCheck.Count; } } if (intersects > 0) { AddRuntimeMessage(GH_RuntimeMessageLevel.Error, "Beam volume is invalid."); return; } DA.SetDataList(0, spCrvPln); DA.SetDataList(1, crvPts); DA.SetDataList(2, crvs); DA.SetData(3, beam); DA.SetData(4, spCrv); }
private void BakeStoredObjects(Rhino.RhinoDoc rhdoc) { // do we need to add layers? int parent_index = rhdoc.Layers.Find(parent_layer_name, true); if (parent_index < 0) { parent_index = rhdoc.Layers.Add(parent_layer_name, Color.White); } Dictionary <string, int> layer_dict = new Dictionary <string, int>(); if (rhdoc.Layers[parent_index].GetChildren() != null) { foreach (Rhino.DocObjects.Layer l in rhdoc.Layers[parent_index].GetChildren()) { layer_dict.Add(l.Name, l.LayerIndex); } } foreach (string layername in required_layers) { if (!layer_dict.ContainsKey(layername)) { Rhino.DocObjects.Layer childlayer = new Rhino.DocObjects.Layer(); childlayer.ParentLayerId = rhdoc.Layers[parent_index].Id; childlayer.Name = layername; int index = rhdoc.Layers.Add(childlayer); if (index < 0) { AddRuntimeMessage(GH_RuntimeMessageLevel.Error, "Layer creation gone bad!"); } layer_dict.Add(layername, index); } } int group_index = -1; List <Guid> guids = new List <Guid>(); int current_branch_index = -1; for (int n = 0; n < m_obj.Count; n++) { if (m_branch_index[n] != current_branch_index) { group_index = rhdoc.Groups.Add(); current_branch_index = m_branch_index[n]; } object obj = m_obj[n]; Rhino.DocObjects.ObjectAttributes att = m_att[n].Value; att.LayerIndex = layer_dict[m_att[n].layer]; if (obj == null) { continue; } Guid id = new Guid(); Type objectType = obj.GetType(); if (objectType == typeof(Grasshopper.Kernel.Types.GH_Vector)) { AddRuntimeMessage(GH_RuntimeMessageLevel.Warning, "Vectors are confusing things to bake - I'll just make a point at the vector position. If you want to visualize a 'positioned' vector, try giving me a Ray instead."); } if (obj is Grasshopper.Kernel.IGH_BakeAwareData) { Grasshopper.Kernel.IGH_BakeAwareData bakedata = (Grasshopper.Kernel.IGH_BakeAwareData)obj; bakedata.BakeGeometry(rhdoc, att, out id); rhdoc.Groups.AddToGroup(group_index, id); if (guids != null) { guids.Add(id); } // draw fill meshes for closed planar curves if (objectType == typeof(Grasshopper.Kernel.Types.GH_Curve)) { Rhino.Geometry.Curve rh_curve = ((Grasshopper.Kernel.Types.GH_Curve)obj).Value; if ((rh_curve.IsClosed) && (rh_curve.IsPlanar())) { Rhino.Geometry.Intersect.CurveIntersections iev = Rhino.Geometry.Intersect.Intersection.CurveSelf(rh_curve, Rhino.RhinoDoc.ActiveDoc.ModelAbsoluteTolerance); if (iev.Count == 0) { Rhino.Geometry.Mesh mesh = Rhino.Geometry.Mesh.CreateFromPlanarBoundary(rh_curve, Rhino.Geometry.MeshingParameters.Smooth); Grasshopper.Kernel.IGH_BakeAwareData meshbakedata = (Grasshopper.Kernel.IGH_BakeAwareData) new Grasshopper.Kernel.Types.GH_Mesh(mesh); att.PlotWeight = 0.0; meshbakedata.BakeGeometry(rhdoc, att, out id); rhdoc.Groups.AddToGroup(group_index, id); if (guids != null) { guids.Add(id); } } } } continue; } else { AddRuntimeMessage(GH_RuntimeMessageLevel.Warning, "The component does not know how to handle this type of gh_geometry: " + objectType.FullName); continue; } //if (groupIndex != -1) doc.Groups.AddToGroup(groupIndex, id); } rhdoc.Views.Redraw(); }
protected override void SolveInstance(IGH_DataAccess DA) { Brep b = null; List <Line> lns = new List <Line>(); double segLength = -1.0; Vector3d projection = Vector3d.Unset; if (!DA.GetData(0, ref b)) { return; } if (!DA.GetDataList(1, lns)) { return; } if (!DA.GetData(2, ref segLength)) { return; } if (!DA.GetData(3, ref projection)) { return; } projection.Unitize(); sRhinoConverter rhcon = new sRhinoConverter(); Vector3d loadDirection = Vector3d.ZAxis * -1; List <Line> beamlns = new List <Line>(); DataTree <Curve> voronois = new DataTree <Curve>(); DataTree <double> triAreas = new DataTree <double>(); DataTree <Interval> parameters = new DataTree <Interval>(); if (b.Faces.Count == 1) { Surface srf = b.Faces[0].ToNurbsSurface(); Vector3d orinv = srf.NormalAt(srf.Domain(0).Mid, srf.Domain(1).Mid); if (srf.IsPlanar()) { List <Point3d> lpts = new List <Point3d>(); foreach (Line l in lns) { int den = 0; Curve bc = l.ToNurbsCurve(); if (segLength > 0.0) { den = (int)(bc.GetLength() / segLength); } if (den < 3) { den = 3; } Point3d[] segPts; bc.DivideByCount(den, false, out segPts); for (int i = 0; i < segPts.Length; ++i) { lpts.Add(segPts[i]); } lpts.Add(bc.PointAtLength(0.05)); lpts.Add(bc.PointAtLength(bc.GetLength() - 0.05)); } List <Grasshopper.Kernel.Geometry.Voronoi.Cell2> cells = rhcon.GetVoronoiCells(lpts, b); int branchID = 0; foreach (Line ll in lns) { GH_Path bpth = new GH_Path(branchID); beamlns.Add(ll); Curve checkCrv = GetShortenBeamAxis(ll, 0.05).ToNurbsCurve(); checkCrv.Domain = new Interval(0.0, 1.0); for (int i = 0; i < cells.Count; ++i) { if (cells[i] == null) { continue; } Curve cellcrv = cells[i].ToPolyline().ToNurbsCurve(); Curve pushedCell = srf.Pushup(cellcrv, 0.001); Rhino.Geometry.Intersect.CurveIntersections cin = Rhino.Geometry.Intersect.Intersection.CurveCurve(checkCrv, pushedCell, 0.005, 0.005); if (cin != null && cin.Count > 0) { AreaMassProperties amp = AreaMassProperties.Compute(pushedCell); double areaThis = amp.Area; if (projection != Vector3d.Unset) { Plane plTo = new Plane(amp.Centroid, projection); Curve projected = pushedCell.DuplicateCurve(); projected.Transform(Transform.PlanarProjection(plTo)); AreaMassProperties ampProjected = AreaMassProperties.Compute(projected); voronois.Add(projected, bpth); triAreas.Add(ampProjected.Area, bpth); loadDirection = projection; } else { voronois.Add(pushedCell, bpth); triAreas.Add(areaThis, bpth); loadDirection = orinv; } Interval inv = Interval.Unset; if (cin.Count == 1) { if (cin[0].ParameterA < 0.5) { inv = new Interval(0.0, cin[0].ParameterA); } else { inv = new Interval(cin[0].ParameterA, 1.0); } } else if (cin.Count == 2) { inv = new Interval(cin[0].ParameterA, cin[1].ParameterA); } parameters.Add(inv, bpth); } } branchID++; } this.Message = ""; } else { AddRuntimeMessage(GH_RuntimeMessageLevel.Error, "Please use a planar brep"); this.Message = "Please use a planar brep"; } } else { AddRuntimeMessage(GH_RuntimeMessageLevel.Error, "Please use a single face brep"); this.Message = "Please use a single face brep"; } DA.SetDataList(0, beamlns); DA.SetDataTree(1, voronois); DA.SetDataTree(2, triAreas); DA.SetDataTree(3, parameters); DA.SetData(4, loadDirection); }
public static void ClosestCurves(List <Curve> L, double tolerance, ref ClosestCurveT t) { double toleranceEnds = Rhino.RhinoDoc.ActiveDoc.ModelAbsoluteTolerance; t = new ClosestCurveT(); HashSet <long> pairs = new HashSet <long>(); for (int i = 0; i < L.Count; i++) { for (int j = 0; j < L.Count; j++) { //In order to check the same pair again if (i == j) { continue; } long key = (i < j) ? MathUtil.GetKey(i, j) : MathUtil.GetKey(j, i); if (pairs.Contains(key)) { continue; } pairs.Add(key); //Check order bool checkEnds0 = L[i].PointAtStart.DistanceToSquared(L[j].PointAtStart) < toleranceEnds; //connected by ends bool checkEnds1 = L[i].PointAtStart.DistanceToSquared(L[j].PointAtEnd) < toleranceEnds; //connected by ends double t0, t1; if (checkEnds0) { t.T0.Add(0); t.T1.Add(0); t.ID0.Add(-i); t.ID1.Add(-j); t.L0.Add(L[i]); t.L1.Add(L[j]); } else if (checkEnds1) { t.T0.Add(0); t.T1.Add(1); t.ID0.Add(-i); t.ID1.Add(-j); t.L0.Add(L[i]); t.L1.Add(L[j]); } else { Rhino.Geometry.Intersect.CurveIntersections ci = Rhino.Geometry.Intersect.Intersection.CurveCurve(L[i], L[j], tolerance, Rhino.RhinoDoc.ActiveDoc.ModelAbsoluteTolerance); if (ci.Count > 0) { Line line = new Line(ci[0].PointA, ci[0].PointB); t0 = ci[0].ParameterA; t1 = ci[0].ParameterB; //Identify how lines are connected int EndSide0 = (t0 < toleranceEnds || t0 > 1 - toleranceEnds) ? -1 : 1; int EndSide1 = (t1 < toleranceEnds || t1 > 1 - toleranceEnds) ? -1 : 1; t.T0.Add(t0); t.T1.Add(t1); t.ID0.Add(i * EndSide0); t.ID1.Add(j * EndSide1); t.L0.Add(L[i]); t.L1.Add(L[j]); } //Touching - Not Touching //Print(EndSide0.ToString() + " " + EndSide1.ToString()); } } } }
protected override void SolveInstance(IGH_DataAccess DA) { if (!DA.GetData("Workplane", ref Workplane)) { AddRuntimeMessage(GH_RuntimeMessageLevel.Warning, "Workplane missing. Default used (WorldXY)."); } if (!DA.GetData("MachineTool", ref Tool)) { AddRuntimeMessage(GH_RuntimeMessageLevel.Warning, "MachineTool missing. Default used."); } Brep brep = null; DA.GetData("Brep", ref brep); bool male = false; DA.GetData("Male", ref male); bool flip = false; DA.GetData("Flip", ref flip); double angle = 0; DA.GetData("Angle", ref angle); double depth = 0; DA.GetData("Depth", ref depth); double hdepth = depth / 2; double hangle = angle / 360 * Math.PI; Curve[] intersections; Point3d[] intersection_points; Rhino.Geometry.Intersect.Intersection.BrepPlane(brep, Workplane, Rhino.RhinoDoc.ActiveDoc.ModelAbsoluteTolerance, out intersections, out intersection_points); if (intersections.Length < 1) { return; } Curve[] outline_list = Curve.JoinCurves(intersections); if (outline_list.Length < 1) { return; } Curve outline = outline_list[0]; List <Point3d> toolpath_start_points = new List <Point3d>(); BoundingBox bb = intersections[0].GetBoundingBox(Workplane); double max_x = 0; double max_y = 0; for (int i = 0; i < 2; ++i) { for (int j = 0; j < 2; ++j) { for (int k = 0; k < 2; ++k) { max_x = Math.Max(Math.Abs(bb.Corner((i == 1), (j == 1), (k == 1)).X), max_x); max_y = Math.Max(Math.Abs(bb.Corner((i == 1), (j == 1), (k == 1)).Y), max_y); } } } List <Point3d> pts = new List <Point3d>(); double step = Math.Tan(hangle) * depth; Curve[] offsets = outline.Offset(Workplane, step * 2, 0.1, CurveOffsetCornerStyle.Sharp); outline = offsets[0]; int num_grooves = (int)(max_x / step) + 5; if (male) { depth *= -1; } for (int i = -num_grooves; i <= num_grooves; ++i) { pts.Add(new Point3d(step * i, -max_y * 2, hdepth * ((Math.Abs(i) % 2) * 2 - 1))); } #region Toolpath int flipper = flip ? 1 : 0; for (int i = flipper; i < pts.Count; i += 2) { toolpath_start_points.Add(new Point3d(pts[i].X, pts[i].Y, 0.0)); } flipper = flip ? 1 : -1; List <GH_PPolyline> paths = new List <GH_PPolyline>(); List <Point3d> path_points = new List <Point3d>(); List <Tuple <Point3d, Point3d> > path_pairs = new List <Tuple <Point3d, Point3d> >(); for (int i = 0; i < toolpath_start_points.Count; ++i) { Point3d p1 = toolpath_start_points[i]; Point3d p2 = toolpath_start_points[i] + Vector3d.YAxis * max_y * 4; Polyline temp = new Polyline(new Point3d[] { p1, p2 }); temp.Transform(Transform.PlaneToPlane(Plane.WorldXY, Workplane)); Rhino.Geometry.Intersect.CurveIntersections ci = Rhino.Geometry.Intersect.Intersection.CurveCurve(outline, temp.ToNurbsCurve(), 0.1, 0.01); if (ci.Count == 2) { path_pairs.Add(new Tuple <Point3d, Point3d>(ci[0].PointA + Workplane.ZAxis * hdepth * flipper, ci[1].PointB + Workplane.ZAxis * hdepth * flipper)); } } path_points.Add(path_pairs[0].Item1); path_points.Add(path_pairs[0].Item2); double d1, d2; int index = 1; for (int i = 1; i < path_pairs.Count; ++i) { d1 = path_pairs[i].Item1.DistanceTo(path_points[index]); d2 = path_pairs[i].Item2.DistanceTo(path_points[index]); if (d1 > d2) { path_points.Add(path_pairs[i].Item2); path_points.Add(path_pairs[i].Item1); } else { path_points.Add(path_pairs[i].Item1); path_points.Add(path_pairs[i].Item2); } index += 2; } paths.Add(new GH_PPolyline(new PPolyline(path_points, Workplane))); #endregion Polyline poly = new Polyline(pts); Brep grooves = Extrusion.CreateExtrusion(poly.ToNurbsCurve(), Vector3d.YAxis * max_y * 4).ToBrep(); grooves.Transform(Transform.PlaneToPlane(Plane.WorldXY, Workplane)); if (!flip) { List <Brep> srfs = new List <Brep>(); for (int i = 0; i < grooves.Surfaces.Count; ++i) { srfs.Add(Brep.CreateFromSurface(grooves.Surfaces[i].Reverse(0))); } grooves = Brep.MergeBreps(srfs, 0.1); } Brep[] trims = brep.Trim(grooves, 0.1); if (trims.Length < 1) { throw new Exception("Trim failed!"); } Brep final = trims[0]; for (int i = 1; i < trims.Length; ++i) { final.Join(trims[i], 0.1, true); } trims = grooves.Trim(brep, 0.1); for (int i = 0; i < trims.Length; ++i) { final.Join(trims[i], 0.1, true); } DA.SetData("Finger Joint", final); DA.SetDataList("Paths", paths); }
public static List <Polyline> CutMesh(this List <Polyline> plines3D, Plane P) { // Rhino.RhinoApp.WriteLine("H"); double tolerance = Rhino.RhinoDoc.ActiveDoc.ModelAbsoluteTolerance; Transform xform = Transform.PlaneToPlane(P, Plane.WorldXY); Transform xformI = Transform.PlaneToPlane(Plane.WorldXY, P); //Transform to XY Plane Polyline[] plines = new Polyline[plines3D.Count]; for (int i = 0; i < plines.Length; i++) { Polyline pline = new Polyline(plines3D[i]); pline.Transform(xform); plines[i] = pline; } List <Polyline> plinesCulled = new List <Polyline>(); for (int i = 0; i < plines.Length; i++) { bool flag = true; bool[] below = new bool[plines[i].Count]; int counter = 0; for (int j = 0; j < plines[i].Count; j++) { if (plines[i][j].Z < 0) { below[j] = true; flag = false; counter++; } else { below[j] = false; } } //For faces that coincide with plane if (counter != 0 && counter != plines[i].Count) { Curve curve = plines[i].ToNurbsCurve(); Rhino.Geometry.Intersect.CurveIntersections ci = Rhino.Geometry.Intersect.Intersection.CurvePlane(curve, Plane.WorldXY, tolerance * 0.01); List <double> t = new List <double>(); for (int j = 0; j < ci.Count; j++) { t.Add(ci[j].ParameterA); } Curve[] curves = curve.Split(t); foreach (Curve c in curves) { if (c.PointAt(0.5 * (c.Domain.T0 + c.Domain.T1)).Z > tolerance) { Polyline splitPline; if (c.TryGetPolyline(out splitPline)) { splitPline.Add(splitPline[0]); plinesCulled.Add(splitPline); } } } } if (flag) { plinesCulled.Add(plines[i]); } } for (int i = 0; i < plinesCulled.Count; i++) { Polyline plineCopy = plinesCulled[i]; plineCopy.Transform(xformI); plinesCulled[i] = plineCopy; } return(plinesCulled); }
/// <summary> /// This is the method that actually does the work. /// </summary> /// <param name="DA">The DA object is used to retrieve from inputs and store in outputs.</param> protected override void SolveInstance(IGH_DataAccess DA) { Curve vCrv = null; Curve mCrv = null; Interval vDom = new Interval(); Interval mDom = new Interval(); Curve spCrv = null; int N = 0; if (!DA.GetData(0, ref vCrv)) { return; } if (!DA.GetData(1, ref mCrv)) { return; } if (!DA.GetData(2, ref vDom)) { return; } if (!DA.GetData(3, ref mDom)) { return; } if (!DA.GetData(4, ref spCrv)) { return; } if (!DA.GetData(5, ref N)) { return; } if (N < 2) { AddRuntimeMessage(GH_RuntimeMessageLevel.Error, "Input n must be an integer greater than 1"); return; } double L = spCrv.GetLength(); Double[] spCrvDiv = spCrv.DivideByCount(N - 1, true); Plane[] spCrvPl = spCrv.GetPerpendicularFrames(spCrvDiv); List <double> Vu = new List <double>(); List <double> Mu = new List <double>(); List <Point3d> spCrvPts = new List <Point3d>(); List <Point3d> vPts = new List <Point3d>(); List <Point3d> mPts = new List <Point3d>(); List <Point3d> allPts = new List <Point3d>(); for (int i = 0; i < spCrvPl.Length; i++) { Point3d spCrvPt = spCrv.PointAt(spCrvDiv[i]); spCrvPts.Add(spCrvPt); Rhino.Geometry.Intersect.CurveIntersections vInt = Rhino.Geometry.Intersect.Intersection.CurvePlane(vCrv, spCrvPl[i], DocumentTolerance()); Point3d vPt = new Point3d(); if (vInt != null) { vPt = vInt[0].PointA; } else { vPt = vPts[i - 1]; } vPts.Add(vPt); Rhino.Geometry.Intersect.CurveIntersections mInt = Rhino.Geometry.Intersect.Intersection.CurvePlane(mCrv, spCrvPl[i], DocumentTolerance()); Point3d mPt = mInt[0].PointA; mPts.Add(mPt); allPts.Add(spCrvPt); allPts.Add(mPt); allPts.Add(vPt); } //if (mDom.IsDecreasing) { mDom.Swap(); } //if (vDom.IsDecreasing) { vDom.Swap(); } BoundingBox vBb = vCrv.GetBoundingBox(false); Point3d vBbMin = vBb.Min; Point3d vBbMax = vBb.Max; BoundingBox mBb = mCrv.GetBoundingBox(false); Point3d mBbMin = mBb.Min; Point3d mBbMax = mBb.Max; Interval mCrvDom = new Interval(mBbMin.Z, mBbMax.Z); Interval vCrvDom = new Interval(vBbMin.Z, vBbMax.Z); List <Point3d> newMPts = new List <Point3d>(); List <Point3d> newVPts = new List <Point3d>(); double scale = 1; for (int i = 0; i < spCrvPts.Count; i++) { double vPtZ = vPts[i].Z - spCrvPts[i].Z; double vu = remapNum.Remap(vPtZ, vCrvDom, vDom); if (vu == 0) { vu += DocumentTolerance(); } Vu.Add(vu); double mPtZ = mPts[i].Z - spCrvPts[i].Z; double mu = remapNum.Remap(mPtZ, mCrvDom, mDom); if (mu == 0) { mu += DocumentTolerance(); } Mu.Add(mu); Point3d newVPt = new Point3d(spCrvPts[i].X, spCrvPts[i].Y, remapNum.Remap(vu, vDom, vCrvDom)); Point3d newMPt = new Point3d(spCrvPts[i].X, spCrvPts[i].Y, remapNum.Remap(mu, mDom, mCrvDom)); newVPts.Add(newVPt); newMPts.Add(newMPt); } List <Curve> graphs = new List <Curve>(); Curve newVCrv = Curve.CreateInterpolatedCurve(newVPts, 1); graphs.Add(newVCrv); Curve newMCrv = Curve.CreateInterpolatedCurve(newMPts, 1); graphs.Add(newMCrv); DA.SetDataList(0, Vu); DA.SetDataList(1, Mu); DA.SetDataList(2, graphs); //DA.SetDataList(3, allPts); }
/// <summary> /// This is the method that actually does the work. /// </summary> /// <param name="DA">The DA object is used to retrieve from inputs and store in outputs.</param> protected override void SolveInstance(IGH_DataAccess DA) { Curve curveA = null; List <Curve> curveB = new List <Curve>(); if (!DA.GetData(0, ref curveA)) { return; } if (!DA.GetDataList(1, curveB)) { return; } if (curveA.IsClosed == true && curveA.IsPlanar() == true) { List <int> judge = new List <int>(); List <string> answer = new List <string>(); List <Curve> cIn = new List <Curve>(); List <Curve> cOut = new List <Curve>(); List <Curve> cOn = new List <Curve>(); List <Curve> cNo = new List <Curve>(); for (int k = 0; k < curveB.Count; k++) { List <Point3d> pts = Ptsss(curveA); Plane pln = new Plane(pts[0], pts[1], pts[2]); if (curveB[k].IsInPlane(pln) == true) { Point3d ptA = curveB[k].PointAtStart; Point3d ptB = curveB[k].PointAtEnd; Rhino.Geometry.Intersect.CurveIntersections cin = Rhino.Geometry.Intersect.Intersection.CurveCurve(curveA, curveB[k], 0, 0); int AA = curveA.Contains(ptA).GetHashCode(); int BB = curveA.Contains(ptB).GetHashCode(); if (cin.Count >= 1)//相交 { answer.Add("相交"); judge.Add(1); cOn.Add(curveB[k]); } else if (cin.Count == 0 && AA == 2 && BB == 2)//在外 { answer.Add("在外"); judge.Add(2); cOut.Add(curveB[k]); } else if (cin.Count == 0 && AA == 1 && BB == 1)//在内 { answer.Add("在内"); judge.Add(0); cIn.Add(curveB[k]); } } else if (curveB[k].IsInPlane(pln) == false) { answer.Add("curveB与curveA不在同一平面"); judge.Add(1000); cNo.Add(curveB[k]); } } DA.SetDataList(0, answer); DA.SetDataList(1, judge); DA.SetDataList(2, cIn); DA.SetDataList(3, cOn); DA.SetDataList(4, cOut); DA.SetDataList(5, cNo); } else { DA.SetData(0, "curveA必须为封闭的平面曲线"); } }