//This function gets the 5 points on the passed line and adds those points //to passed point array (pointList) static public void BreakLine(ref Line line, ref Point3dCollection pointList) { LineSegment3d lineseg = new LineSegment3d(line.StartPoint, line.EndPoint); var pointArray = lineseg.GetSamplePoints(5); bool bReverse = false; //Whether to bReverse the reading of points from line, this case is valid //only if this function is called for line segment of polyline. if (pointList.Count > 0) { Point3d currentPoint = pointList[pointList.Count - 1]; if (currentPoint != line.StartPoint) { bReverse = true; } } int nLength = pointArray.Length; int nIndex = 0; if (bReverse == false) { while (nIndex < nLength) { if (pointList.Contains(pointArray[nIndex].Point) == false) { pointList.Add(pointArray[nIndex].Point); DBPoint point = new DBPoint(pointArray[nIndex].Point); point.ColorIndex = 1; point.SetDatabaseDefaults(); TGpoints.Add(point); } nIndex++; } } else { nIndex = nLength; while (nIndex > 0) { nIndex = nIndex - 1; if (pointList.Contains(pointArray[nIndex].Point) == false) { pointList.Add(pointArray[nIndex].Point); DBPoint point = new DBPoint(pointArray[nIndex].Point); point.ColorIndex = 1; point.SetDatabaseDefaults(); TGpoints.Add(point); } } } }
/// <summary> /// Process point below over the scanLine /// </summary> /// <param name="scanLine">Eeference line used to generate /// points</param> /// <param name="densityOfPoints">Number of points /// per AutoCAD unit of drawing</param> /// <param name="increaseOnStep">Reprocess when a step /// is identified. Used to control recursion</param> private static void ProcessScanLine(LineSegment3d scanLine, int densityOfPoints, bool increaseOnStep) { PointOnCurve3d[] pointsOnDatum = scanLine.GetSamplePoints( (int)(scanLine.Length * densityOfPoints)); Point3d lastPointAdded = Point3d.Origin; foreach (PointOnCurve3d pointOnDatumCurve in pointsOnDatum) { Point3d pointOnDatum = new Point3d( pointOnDatumCurve.Point.ToArray()); double elevationOnSurface = (_surface != null ? _surface.FindElevationAtXY(pointOnDatum.X, pointOnDatum.Y) : // up to elevation of the reference surface _upperLimit); // up to the limit Point3d pointOnSurface = new Point3d( pointOnDatum.X, pointOnDatum.Y, elevationOnSurface); // check if this point is below the solid // by how many hits a vertical line from // this point hit the solid. The lower // Z value is the one. LinearEntity3d lineEnt = new LineSegment3d( pointOnDatum, pointOnSurface); Hit[] hits = _brepSolid.GetLineContainment(lineEnt, 1); if (hits != null) { double lowerZ = hits[0].Point.Z; //double.MaxValue; //foreach (Hit h in hits) //{ // if (h.Point.Z < lowerZ) // lowerZ = h.Point.Z; // h.Dispose(); //} Point3d pointToAdd = new Point3d( pointOnDatum.X, pointOnDatum.Y, lowerZ); _newPoints.Add(pointToAdd); // increase density on steps (big change on elevation)? // ToDo: Need to implement that on the other direction. // This is working only over the scan line direction, // but is also required on the perpendicular if (increaseOnStep) { //skip very first point if (lastPointAdded.DistanceTo(Point3d.Origin) != 0) { if (pointToAdd.DistanceTo(lastPointAdded) > ((1.0 / densityOfPoints) * 10)) { double scanLineElevation = scanLine.StartPoint.Z; Point3d scanLinePt1 = new Point3d( lastPointAdded.X, lastPointAdded.Y, scanLineElevation); Point3d scanLinePt2 = new Point3d( pointToAdd.X, pointToAdd.Y, scanLineElevation); LineSegment3d increaseScanLine = new LineSegment3d( scanLinePt1, scanLinePt2); ProcessScanLine(increaseScanLine, densityOfPoints * 10, false); increaseScanLine.Dispose(); } } lastPointAdded = pointToAdd; } } pointOnDatumCurve.Dispose(); } }