Community
ObjectARX
cancel
Showing results for
Show  only  | Search instead for
Did you mean:

## regarding create perpendicular ray

8 REPLIES 8
SOLVED
Message 1 of 9
386 Views, 8 Replies

## regarding create perpendicular ray

hi i have closed polyline in the drawing now i want to create a perpendicular ray from each line to outside polyline

8 REPLIES 8
Message 2 of 9
in reply to: jignesh.rana

So you have a closed polyline that contains only lines, right?
First you have to find out whether your polyline runs clockwise (cw) or counter-clockwise (ccw).
This can be done easily by calculating the sum of the signed angles between the lines. If the sum is +2PI (+360°) it is ccw if it is -2PI (-360°) it is cw. For three AcGePoint3d p1, p2, p3 the signed angle can be calculated like this:

``````AcGeVector3d v12(p2-p1);
AcGeVector3d v23(p3-p2);
double signedAngle = v12.angleTo(v23, AcGeVector3d::kZAxis); // 0..2PI
if (signedAngle > PI)
signedAngle -= 2*PI; // -PI..+PI
``````

For the ray you need a starting point pt and a direction vector v.

Let ps and pe be start/endpoint of a segment.

``````AcGePoint3d ps, pe;  // in
bool ccw; // in

AcGeVector3d v, vse(pe - ps);
AcGeVector3d v(-vse.y, vse.x, vse.z);
//v points to the left side of [ps-->pe] which is the outside if clockwise
if (ccw)
v = -v;
AcGePoint3d pt(ps + 0.5*vse);
AcDbRay *ray = new AcDbRay()
ray->setBasePoint(pt);
v.normalize();
ray->setUnitDir(v);

``````

Thomas Brammer ● Software Developer ● imos AGLinkedIn
If an answer solves your problem please [ACCEPT SOLUTION]. Otherwise explain why not.

Message 3 of 9
in reply to: tbrammer

first thing from where to take 3 points p1,p2 and p3

second thing is i want to get perpendicular outside ray

something is missing in logic

Message 4 of 9
in reply to: jignesh.rana

I explained:

1. how to determine whether the polygon runs cw or ccw. Full function code is below.
2. how to construct a ray "to the outside" when you know whether the polygon is cw or ccw.

All you have to do is write loops and put the parts together.

Each point of the closed polygon has a predecessor and a successor. In (p1, p2, p3) p1 is the predecessor of p2 and p3 is it's successor. In a closed poylgon the successor of the last point is the first point. ps, pe stand for start-/endpoint of a line segment.

So this is ist all together:

``````// 1.) Clockwise or counter-clockwise?
double TurtleAngle(const AcGePoint3dArray &p)
{
double sumAngles = 0.0; // out
int iPrev, iNext;
int N = p.length();
for (int i=0; i<N; ++i)
{
iPrev = i-1;
iNext = i+1;
if (iPrev < 0)
iPrev = N-1;
if (iNext >= N)
iNext = 0;
const AcGePoint3d &p1 = p[iPrev];
const AcGePoint3d &p2 = p[i];
const AcGePoint3d &p3 = p[iNext];
AcGeVector3d v12(p2-p1);
AcGeVector3d v23(p3-p2);
double signedAngle = v12.angleTo(v23, AcGeVector3d::kZAxis); // 0..2PI
if (signedAngle > PI)
signedAngle -= 2*PI; // -PI..+PI
sumAngles += signedAngle
}
return sumAngles;
}

void CreateRays(const AcGePoint3dArray &p)
{
// 1.) Clockwise or counter-clockwise?
double ang = TurtleAngle(p);
bool ccw = (ang > 0.0);

// 2.) Create rays
int N = p.length();
for (int i=0; i<N; ++i)
{
int iNext = i+1;
if (iNext >= N)
iNext = 0;
const AcGePoint3d &ps = p[i];
const AcGePoint3d &pe = p[iNext];

// Edited 03.20.2023: This must be within the for loop!
AcGeVector3d v, vse(pe - ps);
AcGeVector3d v(-vse.y, vse.x, vse.z);
//v points to the left side of [ps-->pe] which is the outside if clockwise
if (ccw)
v = -v;
AcGePoint3d pt(ps + 0.5*vse);
AcDbRay *ray = new AcDbRay();
ray->setBasePoint(pt);
v.normalize();
ray->setUnitDir(v);
postToDb(ray); // add the ray to the DB
}
}``````

Maybe I should have named the points p, pPrev and pNext.

Just implement a loop that runs for

Thomas Brammer ● Software Developer ● imos AGLinkedIn
If an answer solves your problem please [ACCEPT SOLUTION]. Otherwise explain why not.

Message 5 of 9
in reply to: tbrammer

first thing is how to access pe and ps out side the loop ?

second thing is to consider only last pe and ps from all points(p) ?

Message 6 of 9
in reply to: jignesh.rana

The complete code is in my previous reply. See function CreateRays(AcGePoint3dArray &p).

I just edited the code because a part of it had to be moved into the for {} loop. It should be clear now.

Thomas Brammer ● Software Developer ● imos AGLinkedIn
If an answer solves your problem please [ACCEPT SOLUTION]. Otherwise explain why not.

Message 7 of 9
in reply to: tbrammer

but how could you assume all points (p) are in sequance ?

because it is possible if p[i] is 1st line segment start or end point in polyline and p[iNext] will be 3rd or 4th or any other no. of segment's point then how this logic will work ?

Message 8 of 9
in reply to: jignesh.rana

You wrote: ".. i have closed polyline in the drawing".

So you have all the polyline vertex points in a sequence.

iNext is always the index of the vertex that follows to i: Either i+1 or 0 if i is the index of the last vertex.

Thomas Brammer ● Software Developer ● imos AGLinkedIn
If an answer solves your problem please [ACCEPT SOLUTION]. Otherwise explain why not.

Message 9 of 9
in reply to: tbrammer

thank you so much sir it' working fine

Can't find what you're looking for? Ask the community or share your knowledge.