明经CAD社区

 找回密码
 注册

QQ登录

只需一步,快速开始

搜索
查看: 5735|回复: 22

[已解答] 简单操作不堪重负,深夜求急诊!!--平行图块自动连线

[复制链接]
发表于 2014-5-17 01:50 | 显示全部楼层 |阅读模式
15明经币
水专业的喷头连管道,以及画一些辅助线(便于施工定位),用天正画断然能自动连管线,但是辅助线还是无能为力,对于不用天正的同行来说,工作量更是繁重,故再次翘首以盼一个巧夺天工的lisp程序来解决这个枯燥而重复繁琐的简单劳动!!!
附件: 您需要 登录 才可以下载或查看,没有账号?注册

最佳答案

查看完整内容

我刚看到你图纸上还有一个不输入方向的要求;替换下面的函数大概可以满足要求 其实是个偷懒的办法,高飞鸟的分治求点集最短距离算法最靠谱
发表于 2014-5-17 01:50 | 显示全部楼层
我刚看到你图纸上还有一个不输入方向的要求;替换下面的函数大概可以满足要求
其实是个偷懒的办法,高飞鸟的分治求点集最短距离算法最靠谱
  1. (defun assistLine  (/ dir1 dir2 ss enlst ptlst dirlistpt)
  2.    (if (not (setq en (car (entsel "\n 选择样例喷头"))))
  3.     (setq blkName "j_pt1");
  4.     (setq blkName (cdr (assoc 2 (entget en))))
  5.   )
  6.    (princ "\n 框选喷头范围")

  7.   (setq ss (ssget (list '(0 . "INSERT") (cons 2 blkName))))
  8.   (setq enlst (ss->lst ss))
  9.   (setq
  10.     ptlst (mapcar '(lambda (en) (car (MJ:Massoc 10 (entget en))))
  11.                   enlst
  12.                   )
  13.     )
  14.   (setq dirlistpt(list(car ptlst) (cadr ptlst) (caddr ptlst)))
  15.   (setq distanclst (list (apply ' distance (list(car ptlst)(cadr ptlst))) (apply ' distance (list (car ptlst)(caddr ptlst)))))
  16.   (if (= 0 (vl-position (apply 'min distanclst)distanclst))(setq dir1 (mapcar '-      (car ptlst)    (cadr ptlst)    ))(setq dir1 (mapcar '-      (car ptlst)    (cadr ptlst)    )))
  17. ;;;  (setvar "osmode" 4)
  18. ;;;  (setq dirlinent (entget(car(entsel"\n 选择方向线"))))
  19.   (setq dir2 (MAT:Rot90 dir1))
  20.   (setvar "osmode" 0)
  21.   
  22.                                  
  23. (toDraw (makeDirPts ptlst dir1))
  24.   (toDraw (makeDirPts ptlst dir2))
  25.   )
回复

使用道具 举报

 楼主| 发表于 2014-5-17 15:29 | 显示全部楼层
自己顶一下,盼高手来相助
回复

使用道具 举报

发表于 2014-5-30 23:25 | 显示全部楼层


本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?注册

x
回复

使用道具 举报

发表于 2014-5-30 23:37 | 显示全部楼层

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?注册

x
回复

使用道具 举报

发表于 2014-5-31 11:42 | 显示全部楼层
本帖最后由 Gu_xl 于 2014-5-31 11:56 编辑

这只需对坐标进行简单的排序分组即可,以下提供一个点表坐标排序函数样例:
  1. ;;点表按Y方向从大到小,X方向从小到大排序,即(横向)自上而下,自左而右排序分组
  2. ;;pts 点表 tol 容差值
  3. (defun sortPts-row (pts tol / LST L)
  4.   (setq  pts
  5.    (vl-sort
  6.      pts
  7.      '(lambda (a b)
  8.         (if (equal (cadr a) (cadr b) tol)
  9.     (< (car a) (car b)) ;_ X方向从小到大排序
  10.     (> (cadr a) (cadr b)) ;_ Y方向从大到小
  11.         )
  12.       )
  13.    )
  14.   )
  15.   ;;对pts进行分组
  16.   (setq  lst nil
  17.   l   (list (car pts))
  18.   pts (cdr pts)
  19.   )
  20.   (while pts
  21.     (if  (equal (cadar pts) (cadar l) tol)
  22.       (setq l  (cons (car pts) l)
  23.       pts  (cdr pts)
  24.       )
  25.       (setq lst  (cons l lst)
  26.       l  (list (car pts))
  27.       pts  (cdr pts)
  28.       )
  29.     )
  30.   )
  31.   (setq lst (cons l lst)) ;_ 以按行分好组的点表
  32. )

点表按X方向从小到大,Y方向小到大排序,即(纵向)自左而右、自下而上排序,原理和上面相同,请自己参照写出;
非水平方向的,只需先对坐标转换到非水平方向的UCS坐标即可,或者采用矩阵来进行坐标变换,可参照高飞鸟的矩阵相关帖子。
完整的程序完成,需要你自己来完成!
实际演示效果:




本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?注册

x
回复

使用道具 举报

发表于 2014-5-31 18:27 | 显示全部楼层
Gu_xl 发表于 2014-5-31 11:42
这只需对坐标进行简单的排序分组即可,以下提供一个点表坐标排序函数样例:

点表按X方向从小到大,Y方向 ...

经典啊 谢谢老大们的无私奉献
回复

使用道具 举报

 楼主| 发表于 2014-5-31 22:14 | 显示全部楼层
Gu_xl 发表于 2014-5-31 11:42
这只需对坐标进行简单的排序分组即可,以下提供一个点表坐标排序函数样例:

点表按X方向从小到大,Y方向 ...

非常感谢G版的再次发力,现在很需要这个功能,非常感谢!
回复

使用道具 举报

 楼主| 发表于 2014-5-31 22:23 | 显示全部楼层
xyp1964 发表于 2014-5-30 23:37

院长,你第二个演示中的效果我这里怎么出不来呢?横平竖直的倒是可以

点评

随手写的,后面又做了补充  发表于 2014-5-31 23:01
回复

使用道具 举报

发表于 2014-6-5 23:37 | 显示全部楼层
来看看我榨出来的脑汁
老顾的排序太高大上了,看不懂。
突然想到直接画构造线然后打断的法子,
一试之下没想到交点打断那么复杂还特别慢。
榨了三四天才榨出这个东西来。借用了各大的函数;自己写的难看,好在还能用。
30*30个喷头大概在9秒左右

  1. ;;示例 (MJ:Massoc 10 (entget (car (entsel))))
  2. ;; Notes:特别适合多段线各顶点;作者      
  3. (defun MJ:Massoc (key alist)
  4.   (apply
  5.     'append
  6.     (mapcar '(lambda (x)
  7.                (if (eq (car x) key)
  8.                  (list (cdr x))
  9.                )
  10.              )
  11.             alist
  12.     )
  13.   )
  14. )
  15. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  16. ;;[功能] 选择集->图元列表 By caiqs          ;
  17. (defun ss->lst (ss / retu)
  18.   (setq retu (apply 'append (ssnamex ss)))
  19.   (setq retu (vl-remove-if-not '(lambda (x) (= (type x) 'ENAME)) retu))
  20. )
  21. ;;;判断平面上的三点是否共线By highflybir               ;
  22. ;;;----------------------------------------------------;
  23. ;;;功能: 判断平面上的三点是否共线                      ;
  24. ;;;输入: 三点 P1,P2,P3                                 ;
  25. ;;;输出: T 说明三点共线,否则不共线                    ;
  26. ;;;----------------------------------------------------;
  27. (defun ptAtLine? (p1 p2 p3 / a b c eps)
  28.   (setq eps 1e-6)
  29.   (setq a (distance p2 p3))
  30.   (setq b (distance p3 p1))
  31.   (setq c (distance p1 p2))
  32.   (or (equal (+ a b) c eps)
  33.       (equal (+ b c) a eps)
  34.       (equal (+ c a) b eps)
  35.   )
  36. )
  37. ;;; 旋转一个向量或者点90度By highflybird               ;
  38. (defun MAT:Rot90 (vec)
  39.   (vl-list* (- (cadr vec)) (car vec) (cddr vec))
  40. )
  41. ;;==============================================================;
  42. (defun sortbydistance (tlst / resortedalst clst alst xlst sortedalst outer inner)
  43.   (while (> (length tlst) 2)
  44.     (setq clst
  45.            (cons
  46.              (mapcar '(lambda (x) (distance (car tlst) x)) (cdr tlst))
  47.              clst
  48.            )
  49.     )
  50.     (setq tlst (cdr tlst))
  51.   )
  52.   (setq clst (cons (list (apply 'distance tlst)) clst))
  53.   (setq clst (reverse clst))                ;点到其余各点距离
  54.   (setq alst (apply 'append clst))        ;摊平

  55.   (setq xlst (makepart clst))

  56.   (setq sortedalst (vl-sort-i alst '>))        ;从大到小

  57.   (foreach vp sortedalst
  58.     (setq outer (getpart vp xlst))        ;外层的位置即第几个区间
  59.     (setq inner (vl-position (nth vp alst) (nth outer clst)))
  60.                                         ;内层的位置
  61.     (setq resortedalst
  62.            (cons (cons outer (+ outer inner 1)) resortedalst)
  63.     )
  64.   )
  65.   resortedalst
  66. )
  67. ;;==============================================================;
  68. (defun makepart        (clst / i low up xlst indexlst)
  69.   (setq        i    0
  70.         low  0
  71.         up   -1
  72.         xlst nil
  73.   )
  74.   (setq indexlst (mapcar 'length clst))
  75.   (repeat (length indexlst)
  76.     (setq up (+ (1+ up) (1- (nth i indexlst))))
  77.     (setq xlst (cons (cons low up) xlst))
  78.     (setq low (1+ up))

  79.     (setq i (1+ i))
  80.   )
  81.   (setq xlst (reverse xlst))
  82. )
  83. ;;==============================================================;
  84. (defun getpart (num xlst / i q)
  85.   (setq i 0)
  86.   (foreach part        xlst
  87.     (if        (and (>= num (car part)) (<= num (cdr part)))
  88.       (setq q i)
  89.       (setq i (1+ i))
  90.     )

  91.   )
  92.   q
  93. )

  94. ;;==============================================================;
  95. (defun makeDirPts (ptlst dir / aline ent p1 p2 sumaline)

  96.   (while ptlst
  97.     (setq aline nil)
  98.     (setq p1 (car ptlst))
  99.     (setq p2 (mapcar '+ p1 dir))
  100.     (setq aline (cons p1 aline))
  101.     (setq ptlst (cdr ptlst))
  102.     (foreach pt        ptlst
  103.       (if (ptAtLine? pt p1 p2)
  104.         (progn
  105.           (setq aline (cons pt aline))
  106.           (setq ptlst (vl-remove-if '(lambda (x) (equal pt x)) ptlst))
  107.         )
  108.       )
  109.     )
  110.     (setq sumaline (cons aline sumaline))
  111.   )
  112.   sumaline
  113. )
  114. ;;==============================================================;
  115. (defun toDraw (dir1pts / tyu culst i finaldrawpts templst newtyu)

  116.   (foreach ptlst dir1pts
  117.     (setq leng (length ptlst))                ;ptlst是一条线上的点表
  118.     (setq
  119.       tyu (cons (cons (sortbydistance ptlst) (list (1- leng))) tyu)
  120.     )
  121.   )

  122.   (setq        newtyu (mapcar '(lambda        (onetyu)
  123.                           (setq ls (car onetyu))
  124.                           (setq newonetyu nil)
  125.                           (repeat (last onetyu)
  126.                             (setq newonetyu (cons (car ls) newonetyu))
  127.                             (setq ls (cdr ls))
  128.                           )
  129.                           newonetyu
  130.                         )
  131.                        tyu
  132.                )
  133.   )
  134.   (setq        finaldrawpts
  135.          (mapcar '(lambda (aNewtyu aDir1pts)
  136.                     (mapcar '(lambda (aptpair)
  137.                                (list (nth (car aptpair) aDir1pts)
  138.                                      (nth (cdr aptpair) aDir1pts)))
  139.                             aNewtyu))
  140.                  newtyu
  141.                  dir1pts)


  142.         )
  143.   (foreach ps finaldrawpts
  144.     (foreach oneps ps
  145.       (vl-cmdf "LINE"
  146.                (car oneps)
  147.                (cadr oneps)
  148.                ""
  149.       )

  150.     )
  151.   )
  152. )
  153. ;;==============================================================;
  154. (defun assitLinemain
  155.        (/ dir dir90 ss enlst ptlst blkName dir1pts dir2pts)
  156.   (if (not (setq en (car (entsel "\n 选择样例喷头"))))
  157.     (setq blkName "j_pt1");这里,你懂的!
  158.     (setq blkName (cdr (assoc 2 (entget en))))
  159.   )
  160.   (setvar "osmode" 4)
  161.   (setq        dir (mapcar '-
  162.                     (getpoint "\n 点取辅助线方向点1")
  163.                     (getpoint "\n 点取辅助线方向点2")
  164.             )
  165.   )
  166.   (setq dir90 (MAT:Rot90 dir))
  167.   (setvar "osmode" 0)
  168.   (princ "\n 框选喷头范围")

  169.   (setq ss (ssget (list '(0 . "INSERT") (cons 2 blkName))))
  170.   (setq enlst (ss->lst ss))
  171.   (setq        ptlst (mapcar '(lambda (en) (car (MJ:Massoc 10 (entget en))))
  172.                       enlst
  173.               )
  174.   )                               
  175.   
  176.   (toDraw (makeDirPts ptlst dir))
  177.   (toDraw (makeDirPts ptlst dir90))
  178. )
  179. ;;==============================================================;
  180. (defun c:tt (/ oldOs)
  181.   (setq oldOs (getvar "osmode"))
  182.   (assitLinemain)
  183.   (setvar "osmode" oldOs)
  184. )
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 注册

本版积分规则

小黑屋|手机版|CAD论坛|CAD教程|CAD下载|联系我们|关于明经|明经通道 ( 粤ICP备05003914号 )  
©2000-2023 明经通道 版权所有 本站代码,在未取得本站及作者授权的情况下,不得用于商业用途

GMT+8, 2024-4-27 13:03 , Processed in 0.644840 second(s), 26 queries , Gzip On.

Powered by Discuz! X3.4

Copyright © 2001-2021, Tencent Cloud.

快速回复 返回顶部 返回列表