Visual LISP, AutoLISP and General Customization
cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

polyline clockwise or counter clockwise

13 REPLIES 13
Reply
Message 1 of 14
leipogs23
4726 Views, 13 Replies

polyline clockwise or counter clockwise

How can i test a polyline if its clockwise or counterclockwise?
I have a routine that gets the area of polylines then if clockwise,the area is positive and negative if not. But I dont want to get the area just to test if its clockwise or not.
Any idea?
13 REPLIES 13
Message 2 of 14
Anonymous
in reply to: leipogs23

Hi,

Compute the areas from the coordinates. Positive areas will be
clockwise, negative anti-clockwise.
For each leg: area = (end X - start X) * (End Y + Start Y) /2

Another approach is to offset the polyline be a small distance and
compare the areas of the original and the offset.

Here's an extract from my data of material by gille using a third approach

{code}
;; PolylineAlgebricArea (gile)
;; Returns the algebric (signed) area of a polyline (even with arcs)
;; Area is negative if the polyline is clockwise
;;
;; Argument: a polyline (ename)
;; Posted to NG 18 Mar 2009 by _gille

(defun PolylineAlgebricArea (pl / elst lst tot p0 area)
(setq elst (entget pl))
(while (setq elst (member (assoc 10 elst) elst))
(setq lst (cons (cons (cdar elst) (cdr (cadddr elst))) lst)
elst (cdr elst)
)
)
(setq lst (reverse lst)
tot 0.0
p0 (caar lst)
)
(if (/= 0 (cdar lst))
(setq tot (PolyArcArea (cdar lst) p0 (caadr lst)))
)
(if (equal (car (last lst)) p0 1e-9)
(setq lst (reverse (cdr (reverse lst))))
)
(setq lst (cdr lst))
(while (cadr lst)
(setq area (TriangleArea p0 (caar lst) (caadr lst))
tot (+ area tot)
)
(if (/= 0 (cdar lst))
(setq tot (+ tot (PolyArcArea (cdar lst) (caar lst) (caadr lst))))
)
(setq lst (cdr lst))
)
(if (/= 0 (cdar lst))
(setq tot (+ tot (PolyArcArea (cdar lst) (caar lst) p0)))
)
tot
)

;; TriangleArea (gile)
;; Returns the algebric (signed) area of a triangle (3 points)
;; Area is negative if the points are clockwise
;;
;; Arguments: three 2d points

(defun TriangleArea (p1 p2 p3)
(/ (- (* (- (car p2) (car p1))
(- (cadr p3) (cadr p1))
)
(* (- (car p3) (car p1))
(- (cadr p2) (cadr p1))
)
)
2.0
)
)

;; PolyArcArea (gile)
;; Returns the algebric (signed) area of a polyarc
;; Area is negative if the arc is clockwise
;;
;; Arguments
;; bu : polyarc bulge
;; p1 : start point
;; p2 : end point

(defun PolyArcArea (bu p1 p2 / ang rad cen area)
(setq ang (* 4 (atan bu))
rad (/ (distance p1 p2)
(* 2 (sin (/ ang 2)))
)
area (/ (* rad rad (- ang (sin ang))) 2.0)
)
area
)


{code}

leipogs23 wrote:
> How can i test a polyline if its clockwise or counterclockwise?
> I have a routine that gets the area of polylines then if clockwise,the area is positive and negative if not. But I dont want to get the area just to test if its clockwise or not.
> Any idea?
>
Message 3 of 14
Kent1Cooper
in reply to: leipogs23

http://discussion.autodesk.com/forums/message.jspa?messageID=6107105&tstart=0

among several other threads on the same topic.

--
Kent Cooper


leipogs23 wrote...
How can i test a polyline if its clockwise or counterclockwise?
....
Kent Cooper, AIA
Message 4 of 14
stevor
in reply to: leipogs23

1. Kent, was the concave problem, your right facing Pacman, ever resolved?

2. We used a convex hull prep of the linear pline to bypass inlets in building space boundaries.

3. Arcs could be subdvided into linear segments for additional vertices to accomodate a hull approximation.
S
Message 5 of 14
Anonymous
in reply to: leipogs23

On 3/24/2010 10:54 AM, stevor wrote:
> 1. Kent, was the concave problem, your right facing Pacman, ever resolved?
>
> 2. We used a convex hull prep of the linear pline to bypass inlets in building space boundaries.
>
> 3. Arcs could be subdvided into linear segments for additional vertices to accomodate a hull approximation.
>

Here is Evgeniy Elpanov's solution, adapted very slightly to return
"clockwise" or "counter-clockwise" instead of just T or nil.

It works correctly on the right-facing PacMan figure, and flips the
result for a mirrored polyline.

gile said it was brilliant -- good enough for me.

-Bill
Message 6 of 14
Kent1Cooper
in reply to: leipogs23

Yes -- the routine attached to the same post as the Pacman image *does* return the correct drawing direction for such shapes. [The description of the problem was only there in explanation of why the routine turned out to be longer than I had thought it might -- it was not a situation that the routine doesn't interpret correctly.]

--
Kent Cooper


stevor wrote...
1. Kent, was the concave problem, your right facing Pacman, ever resolved?
....
Kent Cooper, AIA
Message 7 of 14
Anonymous
in reply to: leipogs23

On 3/24/2010 11:11 AM, Bill Gilliss wrote:
>
> Here is Evgeniy Elpanov's solution, adapted very slightly to return
> "clockwise" or "counter-clockwise" instead of just T or nil.
>
>
>

A caveat:

One figure that the Elpanov solution will not work reliably on is shown
in red in the attached image. The (vlax-curve-getClosestPointTo)
function returns only two *distinct* points, at the top and bottom of
the figure, instead of four as expected, and thus the main LWCL function
always returns "clockwise" regardless of the direction the polyline was
drawn.
Message 8 of 14
Anonymous
in reply to: leipogs23

If you use DOSLib, you can just call dos_plinewinding.

- Dale

"leipogs23" wrote in message news:6359711@discussion.autodesk.com...
> How can i test a polyline if its clockwise or counterclockwise?
> I have a routine that gets the area of polylines then if clockwise,the
> area is positive and negative if not. But I dont want to get the area just
> to test if its clockwise or not.
> Any idea?
Message 9 of 14
Anonymous
in reply to: leipogs23

On 3/24/2010 12:35 PM, Dale Fugier wrote:
> If you use DOSLib, you can just call dos_plinewinding.
>
> - Dale

Well, in ACA 2010, (dos_plinewinding) returns the opposite of what the
documentation says, and I can't erase the polyline afterwards. Very
strange. Can anyone confirm?

I've emailed McNeel.
Message 10 of 14
trickyfish75
in reply to: leipogs23

Could you please explain how you get the area calculation to return negative values or post your routine for returning negative areas? All of my polyline loops are given positive areas, regardless of the direction they were drawn.
Message 11 of 14
_gile
in reply to: leipogs23

Hi,

You can try the 'PolylineAlgebricArea' routine in the first reply.


Gilles Chanteau
Programmation AutoCAD LISP/.NET
GileCAD
GitHub

Message 12 of 14
EricLLB
in reply to: _gile

Hello,

 

It seems like the routine posted in the first reply is exactly what I am looking for to save me a lot of time, but unfortunately when I load it into AutoCAD 2010 I get nothing.  Is there some sort of formatting change that needs to be made? I am pretty new to AutoLISP and would appreciate any help getting this routine to run very much.

 

Thanks,

Message 13 of 14
nikoloz
in reply to: Anonymous

Thanks for this formula. I've saved a lot of development time with this 🙂

 

Nikoloz Asatiani

 

Message 14 of 14
Lee_Mac
in reply to: trickyfish75

Here is my solution:

 

;; List Clockwise-p  -  Lee Mac
;; Returns T if the point list is clockwise oriented

(defun LM:ListClockwise-p ( lst )
    (minusp
        (apply '+
            (mapcar
                (function
                    (lambda ( a b )
                        (- (* (car b) (cadr a)) (* (car a) (cadr b)))
                    )
                )
                lst (cons (last lst) lst)
            )
        )
    )
)

 

 

Test function:

 

(defun c:test ( / e )
    (if (setq e (ssget "_+.:E:S" '((0 . "LWPOLYLINE"))))
        (LM:ListClockwise-p
            (apply 'append
                (mapcar
                    (function
                        (lambda ( x )
                            (if (= 10 (car x)) (list (cdr x)))
                        )
                    )
                    (entget (ssname e 0))
                )
            )
        )
    )
)

 

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

Post to forums  

”Boost