Aligning text to line

Discussion in 'AutoCAD' started by kboykool, Dec 1, 2004.

  1. kboykool

    kboykool Guest

    The following is being reposted from AutoCAD 2004 Discussion Group at the recommendation of a user:

    I did a search on this DG for "text align" and didn't find what I was seeking. I also tried ToolPac's align annotation to segment, but it behaved in a bizarre fashion.

    I have columns of right and left justified text I wish to align to lines I create. I'm not using a line orthagonal to the WCS, so setting the X or Y coordinate the same is not an option.

    Most of the discussion on this topic aligns text WITH a line. (i.e. the text takes on the same rotation angle as the line) Basically, I want to align the text such that the line passes through all of the text entities' insertion points, but not with same rotation.

    I hope I've explained myself. Thanks in advance for any input.

    Kenny Anderson

    (remove e'x'es to reply)
     
    kboykool, Dec 1, 2004
    #1
  2. kboykool

    ECCAD Guest

    Try this one.
    ;; Draw a Line, Align Text to it..
    ;;
    (defun C:AlignText ( / osm ort p1 p2 lobj ent ename obj ss c text_ent txt rx dx np )
    (setvar "CMDECHO" 0)
    (setq osm (getvar "osmode"))
    (setq ort (getvar "orthomode"))
    (setvar "OSMODE" 0); NONE
    (setvar "ORTHOMODE" 0); turn Off Ortho
    (setq p1 (getpoint "\nPick point for Alignment Line:"))
    (setq p2 (getpoint p1 "\nPick end point for Line:"))
    (command "_line" p1 p2 "")
    (setq lobj (ssget "L"))
    (setq ent (ssname lobj 0))
    (setq ename (entget ent))
    (setq obj (list ent p1)); entsel type object
    ;;
    (setq ss nil)
    (prompt "\nPick the Text to Align:")
    (setq ss (ssget))
    (if ss
    (progn
    (setvar "OSMODE" 128); PERp
    (setq c 0)
    (repeat (sslength ss)
    (setq text_ent (ssname ss c))
    (setq txt (entget text_ent))
    (setq ip (cdr (assoc 10 txt))); present location
    (setvar "LASTPOINT" ip)
    (setq RX (osnap (cadr obj) "_per"))
    (setq DX (distance RX IP))
    (setq np (polar ip (angle IP RX) DX))
    (command "_move" text_ent "" ip np)
    (setq c (+ c 1))
    ); repeat
    ); progn
    ); if
    (setvar "osmode" osm)
    (setvar "orthomode" ort)
    (princ)
    ); function

    Bob
     
    ECCAD, Dec 1, 2004
    #2
  3. kboykool

    kboykool Guest

    Great routine, Bob. Do you mind if I look at the code and try to add some functionality? There are two things I'd like to add.

    1) This routine appears to align the left side of the text, regardless of the justification/insertion point. I'd like to maintain the justification, and thus align through the insertion point.

    2) While the text rotation doesn't change, it appears the entities shift somewhat based on the angle of the line relative to the text rotation. I'd like to move the text in the direction of its rotation.

    I don't even know if it's possible to do what I want, but I thought I'd ask first.

    It's a great routine and for the majority of the text I'll be aligning, this will be very effective. In this particular case, I'm just looking for a bit more. (Aren't we always!?)

    Thanks for your help and quick response.
     
    kboykool, Dec 1, 2004
    #3
  4. kboykool

    ECCAD Guest

    ;; Draw a Line, Align Text to it..
    ;;
    (defun C:AlignText ( / osm ort p1 p2 lobj ent ename obj ss c text_ent txt rx dx np )
    (setvar "CMDECHO" 0)
    (setq osm (getvar "osmode"))
    (setq ort (getvar "orthomode"))
    (setvar "OSMODE" 0); NONE
    (setvar "ORTHOMODE" 0); turn Off Ortho
    (setq p1 (getpoint "\nPick point for Alignment Line:"))
    (setq p2 (getpoint p1 "\nPick end point for Line:"))
    (command "_line" p1 p2 "")
    (setq lobj (ssget "L"))
    (setq ent (ssname lobj 0))
    (setq ename (entget ent))
    (setq obj (list ent p1)); entsel type object
    ;;
    (setq ss nil)
    (prompt "\nPick the Text to Align:")
    (setq ss (ssget))
    (if ss
    (progn
    (setvar "OSMODE" 128); PERp
    (setq c 0)
    (repeat (sslength ss)
    (setq text_ent (ssname ss c))
    (setq txt (entget text_ent))
    (setq just (cdr (assoc 72 txt))); justification
    (if (/= just 0)
    (setq ip (cdr (assoc 11 txt))); Right end
    (setq ip (cdr (assoc 10 txt))); present location
    ); if
    (setvar "LASTPOINT" ip)
    (setq RX (osnap (cadr obj) "_per"))
    (setq DX (distance RX IP))
    (setq np (polar ip (angle IP RX) DX))
    (command "_move" text_ent "" ip np)
    (setq c (+ c 1))
    ); repeat
    ); progn
    ); if
    (setvar "osmode" osm)
    (setvar "orthomode" ort)
    (princ)
    ); function

    This one checks justification (assoc 72 txt)..if not a 0,
    uses (assoc 11 txt), left endpoint..

    Bob
     
    ECCAD, Dec 1, 2004
    #4
  5. kboykool

    ECCAD Guest

    2) While the text rotation doesn't change, it appears the entities shift somewhat based on the angle of the line relative to the text rotation. I'd like to move the text in the direction of its rotation.<<
    If you 'align' to a 'line' ------ what if that line is 'perp' to
    the (angle) of the text insertion..we can only do just so much..

    Have fun with it.

    Bob
     
    ECCAD, Dec 1, 2004
    #5
  6. kboykool

    kboykool Guest

    I nominate you for the "beautiful man" award. Thanks so much.
     
    kboykool, Dec 1, 2004
    #6
  7. kboykool

    ECCAD Guest

    I been called a lot of things...but not (that).
    :)

    Bob
     
    ECCAD, Dec 1, 2004
    #7
  8. kboykool

    kboykool Guest

    I see your point. That would be more complex and probably be a whole new routine altogether. It'll be something for me to work on in my (ha ha) "free time". Thanks again.
     
    kboykool, Dec 1, 2004
    #8
  9. kboykool

    GaryDF Guest

    Try this one....

    Gary

    ;;;Written By : Peter Jamtgaard

    (defun c:ATX ()
    (princ "\n* Select Dtext to be Aligned: *")
    (setq SSET (ssget))
    (princ "\n* Enter [V]ertical or [H]orizontal <H>: *")
    (setq PROMPT1 (strcase (substr (getstring) 1 1)))
    (princ "* Pick alignment point: *")
    (setq PT1 (getpoint))
    (if (or (= PROMPT1 "H") (= PROMPT1 ""))
    (setq YLOC (cadr PT1)
    PROMPT1 "H")
    (setq XLOC (car PT1)
    PROMPT1 "V"))
    (setq C 0)
    (repeat (sslength SSET)
    (setq ENT (ssname SSET C))
    (if (/= ENT nil)
    (progn
    (setq ED (entget ENT))
    (setq TYPE1 (cdr (assoc 0 ED)))
    (if (or (= TYPE1 "INSERT") (= TYPE1 "TEXT"))
    (progn
    (if (= PROMPT1 "H")
    (progn
    (setq INSP (cdr (assoc 10 ED)))
    (setq YLOC2 (cadr INSP))
    (command "move" ENT "" "0,0" (strcat "@0," (rtos (- YLOC YLOC2) 2
    4))))
    (progn (setq INSP (cdr (assoc 10 ED)))
    (setq XLOC2 (car INSP))
    (command
    "move"
    ENT
    ""
    "0,0"
    (strcat "@" (rtos (- XLOC XLOC2) 2 4) ",0"))))))))
    (setq C (+ C 1))))





    I also tried ToolPac's align annotation to segment, but it behaved in a bizarre
    fashion.
    create. I'm not using a line orthagonal to the WCS, so setting the X or Y
    coordinate the same is not an option.
    takes on the same rotation angle as the line) Basically, I want to align the text
    such that the line passes through all of the text entities' insertion points, but
    not with same rotation.
     
    GaryDF, Dec 2, 2004
    #9
  10. kboykool

    Stewart Guest

    Here is the one I use daily....

    (defun TLJerr (s)
    (if (/= s "Function cancelled")
    (princ (strcat "\nError: " s))
    )
    (setq txt_ss nil)
    (setvar "orthomode" old_orth)
    (setvar "snapang" old_snap)
    (setq *error* olderr)
    (princ)
    )

    (defun C:TJ (/ olderr txt_ss new_72 new_73 jtyp t_justx jcode old_10 old_11
    elist old_orth align_p1 align_p2 qaly loops item_name old_snap item_name
    sample_angle ref_pnts ref_ang ref_dist old_10
    old_ta new_pt tljerr
    )

    ;(setq *error* nil)
    (setq olderr *error* *error* TLJerr)
    (setq old_orth (getvar "orthomode"))
    (setq old_snap (getvar "snapang"))

    (setq txt_ss (ssget (list (cons -4 "<or") (cons 0 "ATTDEF") (cons 0
    "TEXT") (cons -4 "or>"))))
    (cond ((= nil txt_ss) (princ "Null input invalid")))

    (cond ((/= txt_ss nil)
    (initget 1 "L C M R TL TR TC ML MR")
    (setq jtyp (getkword "\nEnter New Justification
    <L/C/M/R/TL/TR/TC/ML/MR>: "))
    )
    )

    (cond ((= jtyp "L") (setq new_72 0) (setq new_73 0)))
    (cond ((= jtyp "C") (setq new_72 1) (setq new_73 0)))
    (cond ((= jtyp "M") (setq new_72 4) (setq new_73 0)))
    (cond ((= jtyp "R") (setq new_72 2) (setq new_73 0)))

    (cond ((= jtyp "TL") (setq new_72 0) (setq new_73 3)))
    (cond ((= jtyp "TR") (setq new_72 2) (setq new_73 3)))
    (cond ((= jtyp "TC") (setq new_72 1) (setq new_73 3)))

    (cond ((= jtyp "ML") (setq new_72 0) (setq new_73 2)))
    (cond ((= jtyp "MR") (setq new_72 2) (setq new_73 2)))

    (cond ((/= nil txt_ss)
    ;;
    ;;ALIGN?
    ;;
    (cond ((= nil t_just) (setq t_just "No")))
    (initget 0 "Yes No")
    (setq t_justx (getkword (strcat "\nJustify Along a Line? <" t_just
    ">: ")))
    (cond ((/= nil t_justx) (setq t_just t_justx)))

    (cond ((= "Yes" t_just)
    (setq item_name (ssname txt_ss 0))
    (setq sample_angle (cdr (assoc 50 (entget item_name))))
    (cond ((and
    (not (equal 0.0 sample_angle 0.001))
    (not (equal pi sample_angle 0.001))
    (not (equal (/ pi 2.0) sample_angle 0.001))
    (not (equal (+ (/ pi 2.0) pi) sample_angle 0.001))
    (not (equal (* 2.0 pi) sample_angle 0.001))
    )
    (setvar "snapang" sample_angle)
    )
    )

    (setvar "orthomode" 1)
    (setq align_p1 (getpoint "\npick first alignment point: "))
    (setq align_p2 (getpoint align_p1 "\npick second alingment
    point: "))
    (setvar "orthomode" old_orth)
    (cond ((/= nil old_snap) (setvar "snapang" old_snap)))

    )
    )
    ;;
    ;;DO IT
    ;;
    (setq loops 0)
    (princ (strcat "\nSelected " (itoa (sslength txt_ss)) " entities.
    \nProcessing entity: "))

    (while (/= nil (setq item_name (ssname txt_ss 0)))

    (setq loops (1+ loops))
    (prin1 loops)
    ;;
    ;;Modify Text Justification
    ;;
    (setq elist (entget item_name))
    (setq old_10 (cdr (assoc 10 elist)))

    (setq elist (subst (cons 72 new_72)
    (assoc 72 elist)
    elist
    )
    )
    (setq elist (subst (cons 73 new_73)
    (assoc 73 elist)
    elist
    )
    )
    (entmod elist)
    ;;
    ;;Modify insertion point
    ;;
    (setq elist (entget item_name))

    (setq new_10 (cdr (assoc 10 elist)))
    (setq new_11 (cdr (assoc 11 elist)))
    (cond ((= nil new_11) (setq new_11 (list 0.0 0.0 0.0))))

    (setq ref_ang (angle new_10 old_10))
    (setq ref_dist (distance new_10 old_10))
    (setq new_10 (polar new_10 ref_ang ref_dist))
    (setq new_11 (polar new_11 ref_ang ref_dist))

    (setq elist (subst (cons 10 new_10)
    (assoc 10 elist)
    elist
    )
    )
    (setq elist (subst (cons 11 new_11)
    (assoc 11 elist)
    elist
    )
    )
    ;;
    ;;Align along the line
    ;;
    (entmod elist)

    (cond ((= "Yes" t_just)
    (setq elist (entget item_name))
    (setq old_ta (cdr (assoc 50 elist)))
    (if (and (= 0 (cdr (assoc 72 elist))) (= 0 (cdr (assoc 73
    elist))))
    (progn
    (setq new_pt (cdr (assoc 10 elist)))
    (setq new_pt (inters new_pt (polar new_pt (+ pi
    old_ta) 1.0) align_p1 align_p2 nil))
    (setq elist (subst (cons 10 new_pt)
    (assoc 10 elist)
    elist
    )
    )
    )
    (progn
    (setq new_pt (cdr (assoc 11 elist)))
    (setq new_pt (inters new_pt (polar new_pt old_ta 1.0)
    align_p1 align_p2 nil))
    (setq elist (subst (cons 11 new_pt)
    (assoc 11 elist)
    elist
    )
    )
    )
    )
    )
    )
    (entmod elist)

    (setq txt_ss (ssdel item_name txt_ss))
    (repeat (strlen (itoa loops)) (princ (chr 8)))
    )
    (prin1 "Finished")
    )
    )
    (terpri)
    (setq *error* olderr)
    (princ)
    )


    --
    Stewart


    seeking. I also tried ToolPac's align annotation to segment, but it behaved
    in a bizarre fashion.
    create. I'm not using a line orthagonal to the WCS, so setting the X or Y
    coordinate the same is not an option.
    text takes on the same rotation angle as the line) Basically, I want to
    align the text such that the line passes through all of the text entities'
    insertion points, but not with same rotation.
     
    Stewart, Dec 2, 2004
    #10
  11. kboykool

    GaryDF Guest

    Stewart

    Thanks, this a great routine. I will use this one. Added some
    modifications, check it out. Are you the author? Made changes
    to the Yes No cond.........

    Gary

    (defun TLJerr (s)
    (if (/= s "Function cancelled")
    (princ (strcat "\nError: " s " *")))
    (setq txt_ss nil)
    (setvar "orthomode" old_orth)
    (setvar "snapang" old_snap)
    (setq *error* olderr)
    (princ))

    (defun DTEXTJUSTIT (/ olderr txt_ss new_72 new_73 jtyp t_justx jcode old_10
    old_11 elist
    old_orth align_p1 align_p2 qaly loops item_name old_snap
    item_name
    sample_angle ref_pnts ref_ang ref_dist old_10 old_ta new_pt
    tljerr)
    (prompt "\n* Dtext Justify and Alignment *")
    ;;(setq *error* nil)
    (setq olderr *error*
    *error* TLJerr)
    (setq old_orth (getvar "orthomode"))
    (setq old_snap (getvar "snapang"))
    (setq txt_ss (ssget
    (list (cons -4 "<or") (cons 0 "ATTDEF") (cons 0 "TEXT") (cons -4
    "or>"))))
    (cond ((= nil txt_ss) (princ "\n* Null Input Invalid *")))
    (cond ((/= txt_ss nil)
    (initget 0 "L C M R TL TR TC ML MR")
    (setq jtyp (getkword
    "\n* Enter New Justification <L> ''L/C/M/R/TL/TR/TC/ML/MR''
    : "))))
    (cond ((or (= jtyp "L") (= jtyp nil)) (setq new_72 0) (setq new_73 0)))
    (cond ((= jtyp "C") (setq new_72 1) (setq new_73 0)))
    (cond ((= jtyp "M") (setq new_72 4) (setq new_73 0)))
    (cond ((= jtyp "R") (setq new_72 2) (setq new_73 0)))
    (cond ((= jtyp "TL") (setq new_72 0) (setq new_73 3)))
    (cond ((= jtyp "TR") (setq new_72 2) (setq new_73 3)))
    (cond ((= jtyp "TC") (setq new_72 1) (setq new_73 3)))
    (cond ((= jtyp "ML") (setq new_72 0) (setq new_73 2)))
    (cond ((= jtyp "MR") (setq new_72 2) (setq new_73 2)))
    (cond
    ((/= nil txt_ss)
    ;;
    ;;ALIGN?
    ;;
    (cond ((= nil t_just) (setq t_just "Yes")))
    (initget 0 "Yes No")
    (setq t_justx (getkword (strcat "\n* Justify Along a Line? <" t_just ">:
    ")))
    (cond ((= "No" t_justx) (setq t_just t_justx))
    ((or (= t_just "Yes")(= t_justx "Yes"))
    (setq t_just "Yes")
    (setq item_name (ssname txt_ss 0))
    (setq sample_angle (cdr (assoc 50 (entget item_name))))
    (cond ((and (not (equal 0.0 sample_angle 0.001))
    (not (equal pi sample_angle 0.001))
    (not (equal (/ pi 2.0) sample_angle 0.001))
    (not (equal (+ (/ pi 2.0) pi) sample_angle 0.001))
    (not (equal (* 2.0 pi) sample_angle 0.001)))
    (setvar "snapang" sample_angle)))
    (setvar "orthomode" 1)
    (setq align_p1 (getpoint "\n* Pick First Alignment Point:"))
    (setq align_p2 (getpoint align_p1 "\n* Pick Second Alingment Point
    <Warning: Line cannot be Horizontal> :"))
    (setvar "orthomode" old_orth)
    (cond ((/= nil old_snap) (setvar "snapang" old_snap)))))
    ;;
    ;;DO IT
    ;;
    (setq loops 0)
    (princ (strcat "\n* Selected "
    (itoa (sslength txt_ss))
    " entities...Processing entity: "))
    (while (/= nil (setq item_name (ssname txt_ss 0)))
    (setq loops (1+ loops))
    (prin1 loops)
    ;;
    ;;Modify Text Justification
    ;;
    (setq elist (entget item_name))
    (setq old_10 (cdr (assoc 10 elist)))
    (setq elist (subst (cons 72 new_72) (assoc 72 elist) elist))
    (setq elist (subst (cons 73 new_73) (assoc 73 elist) elist))
    (entmod elist)
    ;;
    ;;Modify insertion point
    ;;
    (setq elist (entget item_name))
    (setq new_10 (cdr (assoc 10 elist)))
    (setq new_11 (cdr (assoc 11 elist)))
    (cond ((= nil new_11) (setq new_11 (list 0.0 0.0 0.0))))
    (setq ref_ang (angle new_10 old_10))
    (setq ref_dist (distance new_10 old_10))
    (setq new_10 (polar new_10 ref_ang ref_dist))
    (setq new_11 (polar new_11 ref_ang ref_dist))
    (setq elist (subst (cons 10 new_10) (assoc 10 elist) elist))
    (setq elist (subst (cons 11 new_11) (assoc 11 elist) elist))
    ;;
    ;;Align along the line
    ;;
    (entmod elist)
    (cond
    ((or (= "Yes" t_just)(= "Yes" t_justx))
    (setq elist (entget item_name))
    (setq old_ta (cdr (assoc 50 elist)))
    (if (and (= 0 (cdr (assoc 72 elist))) (= 0 (cdr (assoc 73 elist))))
    (progn (setq new_pt (cdr (assoc 10 elist)))
    (setq new_pt (inters new_pt
    (polar new_pt (+ pi old_ta) 1.0)
    align_p1
    align_p2
    nil))
    (setq elist (subst (cons 10 new_pt) (assoc 10 elist) elist)))
    (progn (setq new_pt (cdr (assoc 11 elist)))
    (setq
    new_pt (inters new_pt (polar new_pt old_ta 1.0) align_p1
    align_p2 nil))
    (setq elist (subst (cons 11 new_pt) (assoc 11 elist)
    elist))))))
    (entmod elist)
    (setq txt_ss (ssdel item_name txt_ss))
    (repeat (strlen (itoa loops)) (princ (chr 8))))
    (prin1 "Finished")(princ " *")))
    (terpri)
    (setq *error* olderr)
    (princ))
    (princ)
     
    GaryDF, Dec 3, 2004
    #11
  12. kboykool

    Stewart Guest

    Not the original, he has passed on, so I inherited allot of his stuff in
    various stages of completion this particular one 90% done so unfortunately I
    can't take the credit for this one. The only thing I did see glancing at it
    is the line can be horizontal as long as the text is rotated. I think if you
    want to put in a warning you might want to word it something along "WARNING
    line must be perpendicular to text" or something along those lines.
     
    Stewart, Dec 3, 2004
    #12
  13. kboykool

    GaryDF Guest

    Thanks for the tip.

    Gary


     
    GaryDF, Dec 3, 2004
    #13
Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments (here). After that, you can post your question and our members will help you out.