Jump to content

Conditional statement


ketongin

Recommended Posts

Hi all,

 

I'm having trouble with a conditional statement and probably you can help me out.

 

1. I have point A and point B pick.

2. How can I know which side my pick 3 lies on point A and point B.

 

Thank you!

 

test.jpg

Edited by ketongin
Link to comment
Share on other sites

One way could be as following ....

 

(and (setq p1 (getpoint "\n Specify Point A :"))
    (setq p2 (getpoint p1 "\n Specify Point B :"))
    (setq p3 (getpoint "\n Specify Point C :"))
)
(cond
 (
  (and (> (cadr p3) (cadr p1)) (< (car p3) (car p2)))
  (princ "\n Point C is on the Left side ")
 )
 (
  (and (> (car p3) (car p1)) (< (cadr p3) (car p2)))
  (princ "\n Point C is on the Right side ")
 )
)

Link to comment
Share on other sites

 
(defun c:test (/ p1 p2 p3 p1_ p2_)
  (setq p1 (getpoint "\nPick Point1")
      p2 (getpoint "\nPick Point2")
      p3 (getpoint "\nPick Point3")
)
  (setq p1_ (polar p1 (angle p1 p2)( / (distance p1 p2) 2))
      p2_ (car (vl-sort (list p1 p2)
   (function (lambda  (y1 y2)
        (> (cadr y1) (cadr y2)))))))
  (if (<= (c:cal "ang(p1_,p2_,p3)") 180)
    (princ "\nUpper Side of P1 P2")
    (princ "\nLower Side of P1 P2")
)
 (princ)
 )

Link to comment
Share on other sites

You have nine possible results for this query, the four compass directions N,S,E,W four quadrants NE SE SW NW or the point is on the line. Is that what you are trying to discern? -David

Link to comment
Share on other sites

;; Side of Ray  -  Lee Mac
;; Args: pt - test point, l1,l2 - points defining ray
;; Returns:
;;  0 if pt lies on ray
;; -1 if pt is right of ray
;;  1 if pt is left of ray

(defun LM:SideOfRay ( pt l1 l2 / x )
   (cond
       (   (equal (setq x (sin (- (angle l1 pt) (angle l1 l2)))) 0.0 1e-14) 0)
       (   (minusp x) -1)
       (   1   )
   )
)

 

Test function:

 

(defun c:test ( / p1 p2 p3 x )
   (if
       (and
           (setq p1 (getpoint "\nPick First Point of Line: "))
           (setq p2 (getpoint p1 "\nPick Second Point of Line: "))
           (setq p3 (getpoint "\nPick Point to Test: "))
       )
       (alert
           (cond
               (   (zerop (setq x (LM:SideOfRay (trans p3 1 0) (trans p1 1 0) (trans p2 1 0))))
                   "Point is on Line."
               )
               (   (minusp x)
                   "Point is to the Right of Line."
               )
               (   "Point is to the Left of Line."   )
           )
       )
   )
   (princ)
)

Edited by Lee Mac
Added test function
Link to comment
Share on other sites

All possible results.

 

You have nine possible results for this query, the four compass directions N,S,E,W four quadrants NE SE SW NW or the point is on the line. Is that what you are trying to discern? -David
Link to comment
Share on other sites

Thank you ALL and to you Lee. Works as I envision it but it only on the WCS. Well it doesn't matter since I'm a having trouble with my points anyway. After I'm done with my routine, I'm planning to make it work on all viewports, so I need a little help with polar points with trans function. Autodesk reference guide just confuse me on trans.

 

If I have point1

(setq pt1 (trans pt1 0 1))
(setq ang angx)
(setq pt1x (polar (polar pt1 (- ang (-pi 90)) 6)  ang 10))[color="red"] <<<-- how to use trans here[/color]

 

I'm having trouble with trans when I get my points via polar. Thanks again.

 

 

 

 

;; Side of Ray  -  Lee Mac
;; Args: pt - test point, l1,l2 - points defining ray
;; Returns:
;;  0 if pt lies on ray
;; -1 if pt is right of ray
;;  1 if pt is left of ray

(defun LM:SideOfRay ( pt l1 l2 / x )
   (cond
       (   (equal (setq x (sin (- (angle l1 pt) (angle l1 l2)))) 0.0 1e-14) 0)
       (   (minusp x) -1)
       (   1   )
   )
)

 

Test function:

 

(defun c:test ( / p1 p2 p3 x )
   (if
       (and
           (setq p1 (getpoint "\nPick First Point of Line: "))
           (setq p2 (getpoint p1 "\nPick Second Point of Line: "))
           (setq p3 (getpoint "\nPick Point to Test: "))
       )
       (alert
           (cond
               (   (zerop (setq x (LM:SideOfRay (trans p3 1 0) (trans p1 1 0) (trans p2 1 0))))
                   "Point is on Line."
               )
               (   (minusp x)
                   "Point is to the Right of Line."
               )
               (   "Point is to the Left of Line."   )
           )
       )
   )
   (princ)
)

Link to comment
Share on other sites

You're welcome ketongin :)

 

You would need to provide a little more information about what you are trying to achieve - I can't determine much from the few lines of code you have posted (e.g. how is pt1 obtained, etc)

Link to comment
Share on other sites

Sorry about that. I'm really confuse and can't really understand trans function with polar points even after reading about it. Perhaps this simple example will make me understand it more. Thanks Lee.

 

(setq pt1 (trans (getpoint) 0 1))
(setq pt2 ((getpoint) 0 1))
(setq ang (angle pt1 pt2))

(setq pt1a (polar (polar pt1 (- ang (-pi 90)) 6)  ang 10)) [color="red"]<<-- trans this point[/color]
(setq pt1b (polar (polar pt1 (+ ang (-pi 90)) 6)  ang 10)) [color="red"]<<-- trans this point[/color]

Edited by ketongin
*polar points
Link to comment
Share on other sites

How do you want the result to be displayed? For example, if you are creating Lines, the resultant points need to be defined in WCS, whereas if you are creating LWPolylines they need to be in OCS, or if you are using grvecs / grdraw to display something, in UCS.

 

The following is an example using Lines.

 

This will work in all UCS for which the UCS plane is parallel to the WCS plane; to account for ALL UCS planes, more transformations are required, but we'll start off easy:

 

(defun c:test ( / _line pt1 pt2 pt1a pt1b ang )

   (defun _line ( a b ) (entmakex (list (cons 0 "LINE") (cons 10 a) (cons 11 b))))
   
   (if
       (and
           (setq pt1 (getpoint "\nPt1: "))
           (setq pt2 (getpoint "\nPt2: " pt1))
       )
       (progn
           ;; 'getpoint' returns points in UCS
           ;; pt1 = UCS
           ;; pt2 = UCS

           ;; 'angle' returns the angle measured from
           ;; the X-Axis of the current construction plane.

           (setq ang (angle pt1 pt2))

           ;; Now to calculate the points using the polar function:

           (setq pt1a
               (polar
                   (polar pt1 (- ang (/ pi 2.)) 6.0)
                   ang
                   10.0
               )
           )
           (setq pt1b
               (polar
                   (polar pt1 (+ ang (/ pi 2.)) 6.0)
                   ang
                   10.0
               )
           )

           ;; Lines are defined in WCS, so now we transform all points
           ;; from UCS to WCS:

           (setq pt1  (trans pt1  1 0)
                 pt1a (trans pt1a 1 0)
                 pt1b (trans pt1b 1 0)
           )

           ;; Display the result:

           (_line pt1 pt1a)
           (_line pt1 pt1b)
       )
   )
   (princ)
)

Link to comment
Share on other sites

Thank you Lee, I've learned a lot on this tutorial, If Autodesk made their explanation like your's that would be much simpler for us newbies. And by the way can I steal your niffty code. I always been using (entmakex) each time I'm creating a line.

 

 (defun _line ( a b ) (entmakex (list (cons 0 "LINE") (cons 10 a) (cons 11 b))))

 

So I don't need (setq pt1 (trans (getpoint) 0 1))?

 

How do you want the result to be displayed? For example, if you are creating Lines, the resultant points need to be defined in WCS, whereas if you are creating LWPolylines they need to be in OCS, or if you are using grvecs / grdraw to display something, in UCS.

 

The following is an example using Lines.

 

This will work in all UCS for which the UCS plane is parallel to the WCS plane; to account for ALL UCS planes, more transformations are required, but we'll start off easy:

 

(defun c:test ( / _line pt1 pt2 pt1a pt1b ang )

   (defun _line ( a b ) (entmakex (list (cons 0 "LINE") (cons 10 a) (cons 11 b))))
   
   (if
       (and
           (setq pt1 (getpoint "\nPt1: "))
           (setq pt2 (getpoint "\nPt2: " pt1))
       )
       (progn
           ;; 'getpoint' returns points in UCS
           ;; pt1 = UCS
           ;; pt2 = UCS

           ;; 'angle' returns the angle measured from
           ;; the X-Axis of the current construction plane.

           (setq ang (angle pt1 pt2))

           ;; Now to calculate the points using the polar function:

           (setq pt1a
               (polar
                   (polar pt1 (- ang (/ pi 2.)) 6.0)
                   ang
                   10.0
               )
           )
           (setq pt1b
               (polar
                   (polar pt1 (+ ang (/ pi 2.)) 6.0)
                   ang
                   10.0
               )
           )

           ;; Lines are defined in WCS, so now we transform all points
           ;; from UCS to WCS:

           (setq pt1  (trans pt1  1 0)
                 pt1a (trans pt1a 1 0)
                 pt1b (trans pt1b 1 0)
           )

           ;; Display the result:

           (_line pt1 pt1a)
           (_line pt1 pt1b)
       )
   )
   (princ)
)

Link to comment
Share on other sites

Thank you Lee, I've learned a lot on this tutorial, If Autodesk made their explanation like your's that would be much simpler for us newbies.

 

Thanks, I'm glad it was comprehensible. :)

 

And by the way can I steal your niffty code. I always been using (entmakex) each time I'm creating a line.

 

 (defun _line ( a b ) (entmakex (list (cons 0 "LINE") (cons 10 a) (cons 11 b))))

 

You can use it if you wish.

 

So I don't need (setq pt1 (trans (getpoint) 0 1))?

 

No, since getpoint returns points in UCS, not WCS.

 

If you needed the point in WCS, you would use:

 

(trans (getpoint "\nPoint: ") 1 0)

Link to comment
Share on other sites

I only realize just now that geomcal is not pre-loaded on a drawing session,

 

(defun c:test (/ p1 p2 p3 p1_ p2_)
 [color=blue][b](if (not (member "geomcal.arx" (arx)))
   (arxload "geomcal")
 )
[/b][/color]  (setq p1 (getpoint "\nPick Point1")
p2 (getpoint "\nPick Point2")
p3 (getpoint "\nPick Point3")
 )
 (setq p1_ (polar p1 (angle p1 p2) (/ (distance p1 p2) 2))
p2_ (car (vl-sort (list p1 p2)
    (function (lambda (y1 y2)
         (> (cadr y1) (cadr y2))
       )
    )
  )
    )
 )
 (if (<= (c:cal "ang(p1_,p2_,p3)") 180)
   (princ "\nUpper Side of P1 P2")
   (princ "\nLower Side of P1 P2")
 )
 (princ)
)

 

is it the same case for newer cad versions? :?

Link to comment
Share on other sites

You can also use the area of a triangle...

 

(defun AT:TriangleArea (a b c)
 ;; Returns area of three provided points
 ;; If returned value is negative, last point (c) exists on right side of a-b vector
 ;; Alan J. Thompson, 06.09.10
 (/ (- (* (- (car b) (car a)) (- (cadr c) (cadr a)))
       (* (- (cadr b) (cadr a)) (- (car c) (car a)))
    )
    2.
 )
)

Link to comment
Share on other sites

Thanks pBe. I'll also include this on my artillery of sub routines. How can I live without you guys. Thank you very much!

 

I only realize just now that geomcal is not pre-loaded on a drawing session,

 

(defun c:test (/ p1 p2 p3 p1_ p2_)
 [color=blue][b](if (not (member "geomcal.arx" (arx)))
   (arxload "geomcal")
 )
[/b][/color]  (setq p1 (getpoint "\nPick Point1")
p2 (getpoint "\nPick Point2")
p3 (getpoint "\nPick Point3")
 )
 (setq p1_ (polar p1 (angle p1 p2) (/ (distance p1 p2) 2))
p2_ (car (vl-sort (list p1 p2)
    (function (lambda (y1 y2)
         (> (cadr y1) (cadr y2))
       )
    )
  )
    )
 )
 (if (<= (c:cal "ang(p1_,p2_,p3)") 180)
   (princ "\nUpper Side of P1 P2")
   (princ "\nLower Side of P1 P2")
 )
 (princ)
)

 

is it the same case for newer cad versions? :?

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Unfortunately, your content contains terms that we do not allow. Please edit your content to remove the highlighted words below.
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...