乐筑天下

搜索
欢迎各位开发者和用户入驻本平台 尊重版权,从我做起,拒绝盗版,拒绝倒卖 签到、发布资源、邀请好友注册,可以获得银币 请注意保管好自己的密码,避免账户资金被盗
查看: 71|回复: 19

[编程交流] 过程选择集

[复制链接]

17

主题

127

帖子

110

银币

初露锋芒

Rank: 3Rank: 3Rank: 3

铜币
85
发表于 2022-7-6 10:38:08 | 显示全部楼层 |阅读模式
我有一个旧的lisp例程,我们一直在使用它来创建DTEXT行之间的正确行距。此例程主要用于处理旧图形中的注释以创建修订。无论出于何种原因,大多数图纸上的注释都是单行的DTEXT,而不是多行文字。更糟糕的是,行距有点到处都是(即行与行之间的间距不同),作为****需要订单的人,这是完全不能接受的。
 
无论如何,这个例程有几个问题影响了它的功能。首先,用户必须按顺序选择每行文本,以正确排序注释。当你有一整张F大小的便笺,并且你必须手动按顺序选择每一行文字时,它会变得非常乏味。
 
其次,用户必须手动输入行间距。这没那么糟糕,但我不想让用户决定。相反,我希望有两个选项,单间距或双间距,让用户从对话框中选择间距,或者只需键入“S”表示单间距,或键入“d”表示双间距(即,命令行看起来像这样:命令:选择间距选项(单/双):)
 
最后,在运行命令后,第一段文本看起来仍然是选中的。见下图。
 
 
113813xxuxvzjmjxotj8ja.jpg
 
按逃生键没有任何作用。用户必须在屏幕上选择其他内容,然后点击ESCAPE将其清除。我意识到这很琐碎,但它让我感到厌烦。
 
在前一段时间的另一篇帖子中,有人向我提到,用快速命令TXT2MTXT将DTEXT行组合成多行文字实体,这将在一个音符内的行之间创建正确的行距。然后我们要做的就是调整音符之间的间距。我把这个小消息传给了我们的团队,这就是我们最近一直在做的事情。
 
然而,随着我对学习lisp的深入研究,我决定修改现有的行距lisp例程,以纳入我上面列出的想法。问题是我不知道如何使用选择集。我在这里找到了下面的代码(来自Alanjt),我认为这有帮助:
  1. (if (setq ss (ssget '((0 . "TEXT"))))
  2. (vl-sort
  3.    ((lambda (i / lst)
  4.       (while (setq e (ssname ss (setq i (1+ i))))
  5.         (setq lst (cons e lst))
  6.       )
  7.     )
  8.      -1
  9.    )
  10.    (function (lambda (a b) (> (caddr (assoc 10 (entget a))) (caddr (assoc 10 (entget b))))))
  11. )
  12. )

 
 
以下是我们的行距lisp中的代码:
  1. ; TXTSPC command is for adjusting the spacing between existing TEXT
  2. ; By G. Ramesh, NPCC, Abu Dhabi.
  3. (defun C:TXTSPC (/ d e1 elist fpt el1 el2 sp1 sp2 r-ang dis dif i)
  4. (setvar "highlight" 1)
  5. (command ".undo" "g")
  6. (setq d (getdist "\nSpacing required between lines: "))
  7. (prompt
  8.    "\nSelect the TEXT entities one by one starting from the top . . ."
  9. )
  10. (setq e1    (entsel "\nSelect first TEXT: ")
  11. elist '()
  12. i     0
  13. )
  14. (while e1
  15.    (redraw (car e1) 3)
  16.    (setq elist (append elist (list (car e1)))
  17.   e1 (entsel "\nSelect next TEXT: ")
  18.    )
  19. )
  20. (foreach n elist (redraw n 1))
  21. (setq el1 (entget (nth 0 elist)))
  22. (if (/= (cdr (assoc 72 el1)) 0)
  23.    (setq code 11)
  24.    (setq code 10)
  25. )
  26. (setq fpt (cdr (assoc code el1)))
  27. (repeat (1- (length elist))
  28.    (setq el1 (entget (nth i elist))
  29.   el2 (entget (nth (1+ i) elist))
  30.   sp1 (cdr (assoc code el1))
  31.   sp2 (cdr (assoc code el2))
  32.   r-ang (cdr (assoc 50 el1))
  33.   dis (- (cadr sp1) (cadr sp2))
  34.   dif (- d dis)
  35.   sp2 (polar fpt (- r-ang (/ pi 2)) (* (1+ i) d))
  36.   el2 (subst (append (list code) sp2) (assoc code el2) el2)
  37.   i (1+ i)
  38.    )
  39.    (entmod el2)
  40. )
  41. (foreach n elist (redraw n 1))
  42. (command ".undo" "end")
  43. (prin1)
  44. )

 
 
我可以得到一些关于如何合并选择集的提示吗?在选择集中,实体根据其垂直位置与上述代码进行处理?我知道这是一篇很长的帖子,如果你读到这里,我很感激。
 
朗尼
回复

使用道具 举报

26

主题

1495

帖子

20

银币

初露锋芒

Rank: 3Rank: 3Rank: 3

铜币
118
发表于 2022-7-6 10:43:26 | 显示全部楼层
假设:
 
所有文本都具有相同的对齐方式、文本高度、字体等
您希望所有文本左X轴对齐
您只想调整Y轴值
1.5 X文本高度的间距有点标准,
您需要该值的一倍或两倍
 
-大卫
回复

使用道具 举报

17

主题

127

帖子

110

银币

初露锋芒

Rank: 3Rank: 3Rank: 3

铜币
85
发表于 2022-7-6 10:44:57 | 显示全部楼层
大卫,
 
你所有的假设都是正确的。我知道还有很多更强大的文本对齐和间距例程。Lee Mac的动态文本对齐工具是一个很棒的程序,它只是我们所需要的。此外,我正在努力学习lisp,所以弄清楚如何修改现有的现实世界问题将有助于成为一名更好的程序员。
 
朗尼
回复

使用道具 举报

26

主题

1495

帖子

20

银币

初露锋芒

Rank: 3Rank: 3Rank: 3

铜币
118
发表于 2022-7-6 10:50:53 | 显示全部楼层
事实上,你已经选择了一个非常难对付的1
 
逻辑需要遵循:
[列表]
  • 仅选择“文本”实体
  • 逐步通过集合
  • 找到最大Y值
  • 记录所有Y值及其各自实体的名称
  • 排序Y值并记录实体名称
  • 逐步遍历排序集
  • 根据预设的X轴和下降的Y轴值输入每个排序实体的点值
    [/列表]
     
    这不是一个真正简单的过程。
     
    修改现有代码可能是一个真正的挑战。有时候最好从头开始
     
     
    下面是我将如何开始这1的方法
     
    1. [b][color=BLACK]([/color][/b]initget 1 [color=#2f4f4f]"Single Double"[/color][b][color=BLACK])[/color][/b]
    2. [b][color=BLACK]([/color][/b]setq ys [b][color=FUCHSIA]([/color][/b]getkword [color=#2f4f4f]"\nSpacing Style - Single/Double:   "[/color][b][color=FUCHSIA])[/color][/b][b][color=BLACK])[/color][/b]
    3. [b][color=BLACK]([/color][/b]and [b][color=FUCHSIA]([/color][/b]setq i -1
    4.            ss [b][color=NAVY]([/color][/b]ssget '[b][color=MAROON]([/color][/b][b][color=GREEN]([/color][/b]0 . [color=#2f4f4f]"TEXT"[/color][b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]
    5.       [b][color=FUCHSIA]([/color][/b]while [b][color=NAVY]([/color][/b]setq en [b][color=MAROON]([/color][/b]ssname ss [b][color=GREEN]([/color][/b]setq i [b][color=BLUE]([/color][/b]1+ i[b][color=BLUE])[/color][/b][b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b]
    6.              [b][color=NAVY]([/color][/b]setq ed [b][color=MAROON]([/color][/b]entget en[b][color=MAROON])[/color][/b]
    7.                   p10 [b][color=MAROON]([/color][/b]cdr [b][color=GREEN]([/color][/b]assoc 10 ed[b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b]
    8.              [b][color=NAVY]([/color][/b]cond [b][color=MAROON]([/color][/b][b][color=GREEN]([/color][/b]not maxy[b][color=GREEN])[/color][/b]
    9.                     [b][color=GREEN]([/color][/b]setq maxy [b][color=BLUE]([/color][/b]cadr p10[b][color=BLUE])[/color][/b]
    10.                           maxe en[b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b]
    11.                    [b][color=MAROON]([/color][/b][b][color=GREEN]([/color][/b]> [b][color=BLUE]([/color][/b]cadr p10[b][color=BLUE])[/color][/b] maxy[b][color=GREEN])[/color][/b]
    12.                     [b][color=GREEN]([/color][/b]setq maxy [b][color=BLUE]([/color][/b]cadr p10[b][color=BLUE])[/color][/b]
    13.                           maxe en[b][color=GREEN])[/color][/b][b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b]
    14.              [b][color=NAVY]([/color][/b]setq yl [b][color=MAROON]([/color][/b]cons [b][color=GREEN]([/color][/b]cons [b][color=BLUE]([/color][/b]cadr p10[b][color=BLUE])[/color][/b] en[b][color=GREEN])[/color][/b] yl[b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b]
    15.       [b][color=FUCHSIA]([/color][/b]setq fd [b][color=NAVY]([/color][/b]entget maxe[b][color=NAVY])[/color][/b]
    16.             xp [b][color=NAVY]([/color][/b]car [b][color=MAROON]([/color][/b]assoc 10 fd[b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b]
    17.             yp [b][color=NAVY]([/color][/b]cadr [b][color=MAROON]([/color][/b]assoc 10 fd[b][color=MAROON])[/color][/b][b][color=NAVY])[/color][/b][b][color=FUCHSIA])[/color][/b][b][color=BLACK])[/color][/b]

     
     
    这将给出起始X和Y值xp yp
    和实体列表yl
     
    这将需要一个很好的工作来冲洗出来-大卫
  • 回复

    使用道具 举报

    17

    主题

    127

    帖子

    110

    银币

    初露锋芒

    Rank: 3Rank: 3Rank: 3

    铜币
    85
    发表于 2022-7-6 10:53:08 | 显示全部楼层
    嗯,我现在不想太容易,是吗眨眼:
     
    谢谢你让我开始。
     
    朗尼
    回复

    使用道具 举报

    114

    主题

    1万

    帖子

    1万

    银币

    中流砥柱

    Rank: 25

    铜币
    543
    发表于 2022-7-6 10:55:51 | 显示全部楼层
    在我看来,我倾向于使用VL来处理这个解决方案,因为它有助于实现更简洁的解决方案——我可能会这样处理。
     
     
    我不想只给你解决方案,所以也许在你尝试后向下滚动。
     
    1. < Scroll down to see solution >
    2. (defun c:test ( / ss )
    3. (vl-load-com)
    4. ;; © Lee Mac 2010
    5. (if (setq ss (ssget "_:L" '((0 . "TEXT"))))
    6.    (
    7.      (lambda ( i / e l p h a )
    8.        (while (setq e (ssname ss (setq i (1+ i))))
    9.          (setq l (cons (entget e) l ))
    10.        )
    11.        (setq l
    12.          (vl-sort l
    13.            (function
    14.              (lambda ( a b )
    15.                (> (cadr (LM:GetTextInsertion a)) (cadr (LM:GetTextInsertion b)))
    16.              )
    17.            )
    18.          )
    19.        )
    20.        (setq p (LM:GetTextInsertion (car l)) h (* 1.5 (dxf 40 (car l))) a (/ (* 3 pi) 2.))
    21.        (
    22.          (lambda ( j )
    23.            (while (setq l (cdr l))
    24.              (LM:PutTextInsertion (car l) (polar p a (* (setq j (1+ j)) h)))
    25.            )
    26.          )
    27.          0
    28.        )
    29.      )
    30.      -1
    31.    )
    32. )
    33. (princ)
    34. )
    35. (defun dxf ( code lst ) (cdr (assoc code lst)))
    36. (defun LM:GetTextInsertion ( eList )
    37. ;; © Lee Mac 2010
    38. (dxf
    39.    (if (vl-every 'zerop
    40.          (mapcar 'dxf '(72 73) (list elist elist))
    41.        )
    42.      10 11
    43.    )
    44.    eList
    45. )
    46. )
    47. (defun LM:PutTextInsertion ( eList point / code )
    48. ;; © Lee Mac 2010
    49. (setq code
    50.    (if (vl-every 'zerop
    51.          (mapcar 'dxf '(72 73) (list elist elist))
    52.        )
    53.      10 11
    54.    )
    55. )
    56. (entupd
    57.    (cdr
    58.      (assoc -1
    59.        (entmod
    60.          (subst (cons code point) (assoc code elist) elist
    61.          )
    62.        )
    63.      )
    64.    )
    65. )
    66. )
    回复

    使用道具 举报

    54

    主题

    3755

    帖子

    3583

    银币

    后起之秀

    Rank: 20Rank: 20Rank: 20Rank: 20

    铜币
    438
    发表于 2022-7-6 10:58:11 | 显示全部楼层
    Lee发布了一个很好的解决方案,但由于我已经编写了它,我还是会与大家分享。我走了边界盒路线。
     
    顺便说一句,李很酷。
     
    1. <Scroll to see>
    2. (defun c:ALT (/ foo lst)
    3. ;; Align TEXT objects
    4. ;; Alan J. Thomspon, 08.02.10
    5. (vl-load-com)
    6. (defun foo (o / a b)
    7.    (vla-getboundingbox o 'a 'b)
    8.    (vlax-safearray->list a)
    9. )
    10. (if (and (setq lst (vl-sort ((lambda (/ ss l)
    11.                                 (if (setq ss (ssget "_:L" '((0 . "TEXT"))))
    12.                                   (progn
    13.                                     (vlax-for x (setq ss (vla-get-activeselectionset
    14.                                                            (cond (*AcadDoc*)
    15.                                                                  ((setq *AcadDoc*
    16.                                                                          (vla-get-activedocument (vlax-get-acad-object))
    17.                                                                   )
    18.                                                                  )
    19.                                                            )
    20.                                                          )
    21.                                                 )
    22.                                       ;; (XYZ, height, object)
    23.                                       (setq l (cons (list (foo x) (vla-get-height x) x) l))
    24.                                     )
    25.                                     (vla-delete ss)
    26.                                     l
    27.                                   )
    28.                                 )
    29.                               )
    30.                              )
    31.                              (function (lambda (a b) (> (cadar a) (cadar b))))
    32.                     )
    33.           )
    34.           (not (initget 0 "Single Double"))
    35.           (setq *ALT:Space*
    36.                  (cond ((getkword (strcat "\nSpecify spacing [single/Double] <"
    37.                                           (cond (*ALT:Space*)
    38.                                                 ((setq *ALT:Space* "Single"))
    39.                                           )
    40.                                           ">: "
    41.                                   )
    42.                         )
    43.                        )
    44.                        (*ALT:Space*)
    45.                  )
    46.           )
    47.      )
    48.    ((lambda (d m)
    49.       (foreach x (cdr lst)
    50.         (vla-move (caddr x)
    51.                   (vlax-3d-point (car x))
    52.                   (vlax-3d-point (polar (caar lst) (* pi 1.5) (setq d (+ d (* m (cadr x))))))
    53.         )
    54.       )
    55.     )
    56.      0.
    57.      (if (eq *ALT:Space* "Single")
    58.        1.5
    59.        3.
    60.      )
    61.    )
    62. )
    63. (princ)
    64. )
    回复

    使用道具 举报

    114

    主题

    1万

    帖子

    1万

    银币

    中流砥柱

    Rank: 25

    铜币
    543
    发表于 2022-7-6 11:01:19 | 显示全部楼层
    干杯,伙计-你也发了一些不错的代码。我没想到会这么做
     
    我认为你的代码的优点是,它将以与对齐无关的等距定位文本,而我的代码将等距定位插入点我想这取决于运算的预期结果。
     
    回复

    使用道具 举报

    17

    主题

    127

    帖子

    110

    银币

    初露锋芒

    Rank: 3Rank: 3Rank: 3

    铜币
    85
    发表于 2022-7-6 11:05:01 | 显示全部楼层
    太棒了我会试试这两个家伙。谢谢
     
     
    在我今天早些时候计划这一例行活动时,我按照以下逻辑思考:
    [列表]
  • 获取间距(单或双)并存储在变量“sp”中
  • 获取选择集
  • 将集合放入名为“list1”的待处理列表中
  • 根据最大的“Y”坐标值将列表处理到最小,并放入新列表“list2”
  • 获取新列表的第一个实体(即具有最大“Y”坐标值的实体),并将“Y”值存储到变量“ybase”中
  • 使用一个论坛进行FOREACH评估,该论坛将为列表中的每个实体提供新的Y值,其中每个值将增加指定间距的一个因子,然后放置在新列表“list3”中
  • 根据与“ybase”相关的“list3”将实体移动到新的“Y”位置
    在不深入研究任何一个示例代码的情况下,就逻辑而言,这听起来是否正确?
  • 回复

    使用道具 举报

    114

    主题

    1万

    帖子

    1万

    银币

    中流砥柱

    Rank: 25

    铜币
    543
    发表于 2022-7-6 11:08:29 | 显示全部楼层
    避免VL路由所面临的问题是,您无法访问排序函数,因此必须实现自己的排序算法,最有可能的是冒泡排序。
     
    vl排序函数在这方面更快,因为它很可能使用arx实现一种快速排序算法。
     
    回复

    使用道具 举报

    发表回复

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

    本版积分规则

    • 微信公众平台

    • 扫描访问手机版

    • 点击图片下载手机App

    QQ|关于我们|小黑屋|乐筑天下 繁体中文

    GMT+8, 2025-3-6 16:56 , Processed in 0.841179 second(s), 75 queries .

    © 2020-2025 乐筑天下

    联系客服 关注微信 帮助中心 下载APP 返回顶部 返回列表