本帖最后由 夏生生 于 2025-4-19 12:21 编辑
更新了一下,采用算点法,避免了原来的视口问题,最好用这个
采用作图法,容易出现视口问题,也就是图元在视口外的时候捕捉不到点
(以下为正确示例)
 - (defun c:tt (/ xty-tan xty-acos ang dis1 dis2 en1 en2 en3 en4 m pt pt1 pt2 pt3 pt4 pt5 pt6 pt7 pt8 pta r1 r2)
- (defun xty-tan (ang)
- ((lambda (x)
- (if (equal 0. x 1e-14)
- nil
- (/ (sin ang) x))) (cos ang)))
- (defun xty-acos (num)
- (if (zerop num)
- (* pi 0.5)
- (atan (sqrt (- 1.0 (* num num))) num)))
- (setq pt '(0 0 0)
- pta (getpoint "\n插入点:")
- r1 (getreal "\n两圆半径:")
- dis1 (* 0.5 (getreal "\n两圆心距:"))
- ***tt-kword*** (if ***tt-kword***
- ***tt-kword***
- "Off"))
- (vl-cmdf "circle" "none" (polar pt pi dis1) r1)
- (setq en1 (vlax-ename->vla-object (entlast)))
- (vl-cmdf "circle" "none" (polar pt 0 dis1) r1)
- (setq en2 (vlax-ename->vla-object (entlast)))
- (vl-cmdf "zoom"
- "w"
- (list (* 3 (- 0 r1 dis1)) (* 3 (- 0 r1 dis1)))
- (list (* 3 (+ r1 dis1)) (* 3 (+ r1 dis1))))
- (initget "Off Ang Rad")
- (setq m (getkword
- (strcat "\n已知条件[偏线距(Off)/夹角(Ang)/半径(Rad)]<"
- ***tt-kword***
- ">")))
- (if (null m)
- (setq m ***tt-kword***))
- (setq ***tt-kword*** m)
- (cond ((eq m "Off")
- (setq dis2 (getreal "\n偏线距:")))
- ((eq m "Ang")
- (setq ang (getreal "\n夹角(角度):")
- ang (* pi (/ ang 180.))
- dis2 (+ (* r1 (cos ang))
- (* (+ (* r1 (sin ang)) dis1) (xty-tan (* 0.5 ang))))))
- ((eq m "Rad")
- (setq r2 (getreal "\n外接圆半径:")
- ang (- (* 0.5 pi) (xty-acos (/ dis1 (- r2 r1))))
- dis2 (+ (* r1 (cos ang))
- (* (+ (* r1 (sin ang)) dis1) (xty-tan (* 0.5 ang)))))))
- (vl-cmdf "line"
- "none"
- (mapcar '+ pt (list (- dis1) dis2 0))
- "none"
- (mapcar '+ pt (list dis1 dis2 0))
- "")
- (setq en3 (vlax-ename->vla-object (entlast)))
- (setq pt7 (list 0 dis2 0)
- pt4 (list 0 (- dis2) 0)
- pt2 (list (- 0 r1 dis1) 0 0)
- pt6 (list (+ r1 dis1) 0 0))
- (vl-cmdf "circle" "3p" "tan" pt2 "tan" pt6 "tan" pt7)
- (setq en4 (vlax-ename->vla-object (entlast)))
- (setq pt1 (vlax-safearray->list
- (vlax-variant-value (vla-intersectwith en1 en4 acExtendBoth))))
- (setq pt7 (vlax-safearray->list
- (vlax-variant-value (vla-intersectwith en2 en4 acExtendBoth))))
- (setq pt8 (vlax-safearray->list
- (vlax-variant-value (vla-intersectwith en3 en4 acExtendBoth))))
- (setq pt3 (list (car pt1) (- (cadr pt1)) (caddr pt1)))
- (setq pt5 (list (car pt7) (- (cadr pt7)) (caddr pt7)))
- (setq pt1 (mapcar '+ pt1 pta))
- (setq pt2 (mapcar '+ pt2 pta))
- (setq pt3 (mapcar '+ pt3 pta))
- (setq pt4 (mapcar '+ pt4 pta))
- (setq pt5 (mapcar '+ pt5 pta))
- (setq pt6 (mapcar '+ pt6 pta))
- (setq pt7 (mapcar '+ pt7 pta))
- (setq pt8 (mapcar '+ pt8 pta))
- (foreach n (list en1 en2 en3 en4) (vla-delete n))
- (vl-cmdf "arc" "none" pt1 "none" pt2 "none" pt3)
- (vl-cmdf "arc" "none" pt3 "none" pt4 "none" pt5)
- (vl-cmdf "arc" "none" pt5 "none" pt6 "none" pt7)
- (vl-cmdf "arc" "none" pt7 "none" pt8 "none" pt1)
- (vl-cmdf "zoom" "p")
- (princ))
用算点算的,公式推错了,这个代码就作为错误示例放在这里吧,警示后人
(以下为错误示例)
 - (defun c:tt (/ xty-acos ang dis1 dis2 m pt pt1 pt2 pt3 pt4 pt5 pt6 pt7 pt8 pta r1 r2)
- (defun xty-acos (num)
- (if (zerop num)
- (* pi 0.5)
- (atan (sqrt (- 1.0 (* num num))) num)))
- (setq pt '(0 0 0)
- pta (getpoint "\n插入点:")
- r1 (getreal "\n两圆半径:")
- dis1 (* 0.5 (getreal "\n两圆心距:"))
- ***tt-kword*** (if ***tt-kword***
- ***tt-kword***
- "Off"))
- (initget "Off Ang Rad")
- (setq m (getkword
- (strcat "\n已知条件[偏线距(Off)/夹角(Ang)/半径(Rad)]<"
- ***tt-kword***
- ">")))
- (if (null m)
- (setq m ***tt-kword***))
- (setq ***tt-kword*** m)
- (cond ((eq m "Ang")
- (setq ang (getreal "\n夹角(角度):")
- ang (* pi (/ ang 180.))
- dis2 (+ r1 (* 0.5 dis1 (sin (* 0.5 ang))))))
- ((eq m "Off")
- (setq dis2 (getreal "\n偏线距:")
- ang (- (* 0.5 pi) (xty-acos (/ (* 2. (- dis2 r1)) dis1)))))
- ((eq m "Rad")
- (setq r2 (getreal "\n外接圆半径:")
- ang (- (* 0.5 pi) (xty-acos (/ dis1 (- r2 r1))))
- dis2 (+ r1 (* 0.5 dis1 (sin (* 0.5 ang)))))))
- (setq pt1 (polar pt pi dis1)
- pt1 (polar pt1 (+ (* 0.5 pi) ang) r1)
- pt1(mapcar'+ pt1 pta))
- (setq pt2 (polar pt pi (+ r1 dis1))pt2(mapcar'+ pt2 pta))
- (setq pt3 (polar pt pi dis1)
- pt3 (polar pt3 (- (* 1.5 pi) ang) r1)pt3(mapcar'+ pt3 pta))
- (setq pt4 (polar pt (* 1.5 pi) dis2)pt4(mapcar'+ pt4 pta))
- (setq pt5 (polar pt 0 dis1)
- pt5 (polar pt5 (+ (* 1.5 pi) ang) r1)pt5(mapcar'+ pt5 pta))
- (setq pt6 (polar pt 0 (+ r1 dis1))pt6(mapcar'+ pt6 pta))
- (setq pt7 (polar pt 0 dis1)
- pt7 (polar pt7 (- (* 0.5 pi) ang) r1)pt7(mapcar'+ pt7 pta))
- (setq pt8 (polar pt (* 0.5 pi) dis2)pt8(mapcar'+ pt8 pta))
- (vl-cmdf"arc""none" pt1 "none"pt2 "none"pt3)
- (vl-cmdf"arc""none" pt3 "none"pt4 "none"pt5)
- (vl-cmdf"arc""none" pt5 "none"pt6 "none"pt7)
- (vl-cmdf"arc""none" pt7 "none"pt8 "none"pt1)
- (princ))
|