TheSwamp

Code Red => .NET => Topic started by: teslaxx on March 21, 2012, 05:45:23 AM

Title: A problem which implies a polyline
Post by: teslaxx on March 21, 2012, 05:45:23 AM
I know that title wasn't very suggestive, but I didn't know how to formulate it. :)

So I have a polyline of 100 km with lots of vertices. I want that from 50 m(or other distance) to add a line with a DBtext beside it.

The issue: I have the startpoint of the polyline. How to find the points which are at 50 m from each other and WHICH ARE ON THE POLYLINE. Any ideas? Do I have a propriety of the polyline which could help me? :)

I found this : http://through-the-interface.typepad.com/through_the_interface/2012/01/testing-whether-a-point-is-on-an-autocad-polyline-using-net.html but I don't think is a good idea for my problem.
Title: Re: A problem which implies a polyline
Post by: Kerry on March 21, 2012, 06:27:02 AM

Have a look at

public virtual Point3d GetPointAtDist(double value);
 
Declaring Type: Autodesk.AutoCAD.DatabaseServices.Curve
Assembly: Acdbmgd, Version=18.2.0.0

 
Title: Re: A problem which implies a polyline
Post by: teslaxx on March 22, 2012, 03:18:53 AM
Yes Kerry, is working. Thank you.

Now, I have another problem. How can I create, using these points, perpendicular lines on the polyline?

One method I could think of is creating an offset of the polyline, getting the points using your GetPointAtDist and after that, based on these obtained points and using the method GetClosestPointTo from the original polyline, I create the lines.

Another solution? Maybe a simpler one? :)
Title: Re: A problem which implies a polyline
Post by: gile on March 22, 2012, 07:27:21 AM
Hi,

Assuming pl is the polyline, pt is a point on pl, dist the distance from pl for perpendicular point.
Non tested code
Code - C#: [Select]
  1. Vector3d vec = pl.GetFirstDerivative(pt); // a Vector3d along polyline direction at this point.
  2. vec.TransformBy(Matrix3d.Rotation(Math.PI / 2.0, pl.Normal, Point3d.Origin)) // rotates the vector 90°
  3. perpPt = pt + vec * dist // gets a point perpendicular to pl at pt
Title: Re: A problem which implies a polyline
Post by: teslaxx on March 22, 2012, 09:08:22 AM
Thank you gile for your answer. :)
I've tried your suggestion, but I think omit something. :)

Code - C#: [Select]
  1. Line line = new Line(new Point3d(0,0,0), new Point3d(10,0,0) );
  2. blockTableRecord.AppendEntity(line);
  3. transaction.AddNewlyCreatedDBObject(line, true);
  4.  
  5. Point3d point3D = line.GetPointAtDist(5);
  6. Vector3d vec = line.GetFirstDerivative(point3D); // a Vector3d along polyline direction at this point.
  7. vec.TransformBy(Matrix3d.Rotation(Math.PI / 2.0, line.Normal, Point3d.Origin)); // rotates the vector 90°
  8. Point3d perpPt = point3D + vec * 10; // gets a point perpendicular to pl at pt
  9. line = new Line(point3D, perpPt);
  10.  
  11. blockTableRecord.AppendEntity(line);
  12. transaction.AddNewlyCreatedDBObject(line, true);

Firstly I have my line which starts from 0,0,0 to 10,0,0 and the second line which starts at 5,0,0 and ends at 105,0,0 , so the line which should be perpendicular is not. ( 5,0,0 a - 105,0,0 )
Title: Re: A problem which implies a polyline
Post by: fixo on March 22, 2012, 11:10:42 AM
This will get you started, found it in my codes,
partially borrowed from Thorsten Kaefer's program
Code - C#: [Select]
  1.     //FH
  2.  
  3.     public static void CurveLabeling()
  4.         {
  5.            // thanks to Thorsten Kaefer
  6.             Document doc = acadApp.DocumentManager.MdiActiveDocument;
  7.  
  8.             Database db = doc.Database;
  9.  
  10.             Editor ed = doc.Editor;
  11.  
  12.             Matrix3d ucs = ed.CurrentUserCoordinateSystem;
  13.  
  14.             TypedValue[] filter = { new TypedValue((int)DxfCode.Start, "LWPOLYLINE") };
  15.  
  16.             SelectionFilter filterSset = new SelectionFilter(filter);
  17.  
  18.             PromptSelectionOptions pso = new PromptSelectionOptions();
  19.  
  20.             pso.SingleOnly = true;//comment this if you want to label multiple polylines
  21.  
  22.             pso.MessageForAdding = "Select a single polyline >> ";
  23.  
  24.             PromptSelectionResult psr = ed.GetSelection(pso, filterSset);
  25.  
  26.             if (psr.Status != PromptStatus.OK)
  27.                 return;
  28.  
  29.             Transaction tr = db.TransactionManager.StartTransaction();
  30.  
  31.             using (tr)
  32.             {
  33.                 try
  34.                 {
  35.                     BlockTableRecord btr = (BlockTableRecord)tr.GetObject(db.CurrentSpaceId, OpenMode.ForWrite);
  36.  
  37.                     ObjectId[] ids = psr.Value.GetObjectIds();
  38.  
  39.                     double theight = db.Textsize;
  40.  
  41.                     if (theight == 0)
  42.  
  43.                         theight = db.Dimtxt;
  44.  
  45.                     for (int i = 0; i < ids.Length; i++)
  46.                     {
  47.                         Autodesk.AutoCAD.DatabaseServices.Polyline pline = tr.GetObject(ids[i], OpenMode.ForRead) as Autodesk.AutoCAD.DatabaseServices.Polyline;
  48.  
  49.                         double step = 50.0;// change step to suit
  50.  
  51.                         double leng = pline.Length;
  52.  
  53.                         double num = (int)(leng / step);
  54.  
  55.                         double ang;
  56.  
  57.                         int n = 1;
  58.  
  59.                         Plane plan = pline.GetPlane();
  60.  
  61.                         Line ln = null;
  62.  
  63.                         DBText txt = null;
  64.  
  65.                         Vector3d vect = new Vector3d();
  66.  
  67.                         Vector3d vec = new Vector3d();
  68.  
  69.                         Point3d ptxt = new Point3d();
  70.  
  71.                         Point3d ppt = new Point3d();
  72.  
  73.                         for (n = 0; n < num+1; n++)
  74.                         {
  75.                              ptxt = pline.GetPointAtDist(step*n);
  76.  
  77.                              vec = pline.GetFirstDerivative(ptxt).GetPerpendicularVector();
  78.  
  79.                              ppt = (ptxt + vec * 10.0).TransformBy(ucs);
  80.                        
  81.                             ln = new Line(ptxt, ppt);
  82.  
  83.                            btr.AppendEntity(ln);
  84.  
  85.                            tr.AddNewlyCreatedDBObject(ln, true);
  86.  
  87.                             vect = ln.GetFirstDerivative(ppt).GetPerpendicularVector();
  88.                          
  89.                              txt = new DBText();
  90.  
  91.                             txt.Position = ppt;
  92.  
  93.                             txt.TextString = string.Format("{0:f2}", n*step);
  94.  
  95.                             txt.HorizontalMode = TextHorizontalMode.TextCenter;
  96.  
  97.                             txt.VerticalMode = TextVerticalMode.TextBottom;
  98.  
  99.                             txt.AlignmentPoint = ppt;
  100.  
  101.                             ang = ln.Angle + Math.PI;
  102.  
  103.                             if ((ang > Math.PI / 2) || (ang < Math.PI * 1.5))
  104.  
  105.                                 ang = ang + Math.PI;
  106.                             txt.Rotation = ang;
  107.  
  108.                             btr.AppendEntity(txt);
  109.  
  110.                             tr.AddNewlyCreatedDBObject(txt, true);
  111.  
  112.                         }
  113.  
  114.                          ptxt = pline.EndPoint;
  115.  
  116.                          vec = pline.GetFirstDerivative(ptxt).GetPerpendicularVector();
  117.  
  118.                          ppt = (ptxt + vec * 10.0).TransformBy(ucs);
  119.  
  120.                          ln = new Line(ptxt, ppt);
  121.  
  122.                         btr.AppendEntity(ln);
  123.  
  124.                         tr.AddNewlyCreatedDBObject(ln, true);
  125.  
  126.                         vect = ln.GetFirstDerivative(ppt).GetPerpendicularVector();
  127.  
  128.                         txt = new DBText();
  129.  
  130.                         txt.Position = ppt;
  131.  
  132.                         txt.TextString = string.Format("{0:f2}", leng);
  133.  
  134.                         txt.HorizontalMode = TextHorizontalMode.TextCenter;
  135.  
  136.                         txt.VerticalMode = TextVerticalMode.TextBottom;
  137.  
  138.                         txt.AlignmentPoint = ppt;
  139.  
  140.                         ang = ln.Angle + Math.PI;
  141.  
  142.                         if ((ang > Math.PI / 2) || (ang < Math.PI * 1.5))
  143.  
  144.                             ang = ang + Math.PI;
  145.  
  146.                         txt.Rotation = ang;
  147.  
  148.                         btr.AppendEntity(txt);
  149.  
  150.                         tr.AddNewlyCreatedDBObject(txt, true);
  151.  
  152.                         db.TransactionManager.QueueForGraphicsFlush();
  153.  
  154.                     }
  155.  
  156.                     tr.Commit();
  157.                 }
  158.                 catch (Autodesk.AutoCAD.Runtime.Exception ex)
  159.                 {
  160.                     MessageBox.Show(string.Format(
  161.                     "Error:\n{0}\nTrace:\n{1}", ex.Message, ex.StackTrace));
  162.                 }
  163.             }
  164.         }
  165.  

~'J'~

edit:kdub - code formatting =csharp
Title: Re: A problem which implies a polyline
Post by: teslaxx on March 23, 2012, 04:19:27 AM
Thank fixo for providing me the Thorsten Kaefer's program. :D

It's working. :)
Title: Re: A problem which implies a polyline
Post by: fixo on March 23, 2012, 11:01:45 AM
You're quite welcome
Cheers :)

~'J'~