Creating Offset Text LISP

Creating Offset Text LISP

Anonymous
Not applicable
3,481 Views
14 Replies
Message 1 of 15

Creating Offset Text LISP

Anonymous
Not applicable

Hi All,

 

Can someone please help or provide a Lisp routine that will offset text (or Mtext) from a line / polyline. 

 

For example, I want to offset road chainages a user input distance from the centreline (line/pline) along which they correspond. Ideally this would be offsetting the text/mtext from its chosen justification grip point, perpendicular to their alignment (based on the CL). Please refer below example:

infoBB6HT_3-1612314934901.png

 

I wish to have both pieces off text (Ch520 & Ch540) be selected and shifted by their RHS grip point to the offset line position. I note that I can simply copy and move them in this instance because the line is straight... however I want to be able to apply this for when the alignment is curving etc.

 

Any and all assistance is appreciated. 

 

Thanks

0 Likes
Accepted solutions (1)
3,482 Views
14 Replies
Replies (14)
Message 2 of 15

ВeekeeCZ
Consultant
Consultant
Accepted solution

This routine might help you. It moves texts in a direction relative to the current text angle.

 

; -----
(defun c:MoveInDirection ( / *error* ss dst i ang en wcsang pc)
  ;; BeekeeCZ 2018/11
  (defun *error* (errmsg)
    (if (not (wcmatch errmsg "Function cancelled,quit / exit abort,console break,end"))
      (princ (strcat "\nError: " errmsg)))
    (setvar 'cmdecho 1)
    (vla-endundomark adoc)
    (princ))
  
  
  ; John Uhden
  (defun wcsang (ang) (angle (trans '(0 0 0) 1 0) (trans (polar '(0 0 0) ang 1e6) 1 0)))
  ;(defun ucsang (ang) (angle (trans '(0 0 0) 0 1) (trans (polar '(0 0 0) ang 1e6) 0 1))) ; just to be complete.
  
  (vla-startundomark (setq adoc (vla-get-activedocument (vlax-get-acad-object))))
  (setvar 'cmdecho 0)
  
  (or *mid-sid*
      (setq *mid-sid* "Angle"))
  
  (if (and (setq ss (ssget ":L" '((0 . "INSERT,*TEXT"))))
	   (setq dst (getdist "\nSpecify distance: "))
	   (not (initget 1 "2-left 4-right 6-down 8-up Angle"))
	   (setq *mid-sid* (getkword (strcat "\nSpecify angle/direction to move to [4-left/6-right/2-down/8-up/Angle] <" *mid-sid* ">: ")))
	   (setq ang (cond ((= "4-right" *mid-sid*) 	pi)
			   ((= "8-up" 	 *mid-sid*) 	(/ pi 2))
			   ((= "6-down"  *mid-sid*) 	0.)
			   ((= "2-left"  *mid-sid*) 	(* 1.5 pi))
			   ((= "Angle" 	 *mid-sid*)	(getangle "\nSpecify angle: "))))
	   )
    (repeat (setq i (sslength ss))
      (setq ed (entget (ssname ss (setq i (1- i)))))
      (setq pc (if (and (= "TEXT" (cdr (assoc 0 ed)))
			(not (= 0 (cdr (assoc 72 ed)) (cdr (assoc 73 ed)))))
		 11
		 10))
      (entmod (subst (cons pc (polar (cdr (assoc (if (and (= "TEXT" (cdr (assoc 0 ed)))
							  (not (= 0 (cdr (assoc 72 ed)) (cdr (assoc 73 ed)))))
						   11
						   10)
						 ed))
				     (+ ang (if (= "MTEXT" (cdr (assoc 0 ed)))
					      (wcsang (cdr (assoc 50 ed)))
					      (cdr (assoc 50 ed))))
				     dst))
		     (assoc pc ed)
		     ed))))
  (*error* "end")
  )

 

Message 3 of 15

pbejse
Mentor
Mentor

@Anonymous wrote:

Hi All,

Can someone please help or provide a Lisp routine that will offset text (or Mtext) from a line / polyline. ..


Another

(defun c:MoveIt (/ ss d dir ang i e rot)
  (if
    (and
      (setq ss (ssget ":L" '((0 . "TEXT,MTEXT"))))
      (setq d (getdist "\nSpecify offset distance: "))
      (not (initget "F B"))
      (setq dir (cond ((getkword "\nChoose direction [Forward/Back] <Forward>:"))
		  ("F")))
      (setq ang	(if (Eq dir "F")  0.0 pi)
      )
    )
     (repeat (setq i (sslength ss))
       (setq e (vlax-ename->vla-object (ssname ss (setq i (1- i)))))
       (setq rot (vlax-get e 'Rotation) ip (vlax-get e 'InsertionPoint))
       (Vlax-put e 'InsertionPoint (polar ip (+ ang rot) d)
       )
     )
  )(princ)
)

HTH

0 Likes
Message 4 of 15

Anonymous
Not applicable

Thankyou both for your assistance - exactly what I was looking for!

 

Appreciate your help.

 

Kind regards

0 Likes
Message 5 of 15

anton.chmidtMDYV8
Participant
Participant

Could you help me to add this function to my current lisp, it is annoyng how text is sitting on top of line almost without any offset, is it really that text and mtext dont have properties value for "offset from base point"?  Because offset from basepoint would be actually even better for me, I would like to basepoint to be on line and text just naturally couple of millimetter avobe the line

(defun c:ROTATEANDMOVE ( / e)
  (c:torient)
  (if (setq e (ssname (ssget "_P") 0))
    (progn
      (setvar 'cmdecho 0)
      (command-s "_.justifytext" e "" "_BC")
      (command-s "_.move" e "" "_non" (trans (cdr (assoc (if (wcmatch (cdr (assoc 0 (entget e))) "TEXT,ATTDEF") 11 10) (entget e))) 0 1) pause)
      (setvar 'cmdecho 1)))
  (princ)
  )

 

antonchmidtMDYV8_0-1658826973690.png

 

0 Likes
Message 6 of 15

ВeekeeCZ
Consultant
Consultant

AutoCAD does not work with pictures, post a dwg.

0 Likes
Message 7 of 15

anton_chmidt
Advocate
Advocate

Not sure if I am allowed to, but do you need a .dwg since  its just about adding tiny offset from line During my lisp. Or better yet text offset from its own basepoint withoout moving the actual handle/basepoint of said text

0 Likes
Message 8 of 15

Kent1Cooper
Consultant
Consultant

I get exactly that kind of difference with the difference between CENTER and BOTTOM CENTER justification:

Kent1Cooper_0-1658839151633.png

Bottom Center accounts for the possibility of descenders, even if the contents don't include any characters that descend.

Kent Cooper, AIA
0 Likes
Message 9 of 15

anton_chmidt
Advocate
Advocate
Looks perfect but works only with text, not mtext. Now If we could do same for mtext that would be great. My code alreadt Justify BOTTOM CENTER, but 90% I use it with Mtext so didit even notice how good it look on text
0 Likes
Message 10 of 15

Kent1Cooper
Consultant
Consultant

@anton_chmidt wrote:
Looks perfect but works only with text, not mtext. ... but 90% I use it with Mtext ....

I suggest, if your example image is representative of what you work with, that you switch to using plain Text.  There's no earthly reason for using Mtext for something like that.  The M stands for Multi-line, after all -- in single-line things like that, if you don't need internal formatting such as stacked fractions, or color or font changes for a portion of the content, or tracking, it only wastes memory [Mtext takes more for the same content].

Kent Cooper, AIA
0 Likes
Message 11 of 15

anton_chmidt
Advocate
Advocate

There could be scenarios where second line is needed. Also lisp could be used in many other situations where I dont even stop to think about it, if its text and needed to be rotated and moved, just use this command.

But maybe it could ask at the end if user wants to convert Mtext to text, with (No) being a default. Yet that would be a big compromise in my mind, since I for some reason  hate "Text" and see it as something that only slow you down in compare to Mtext. If you ever need to use it for multi line, you cant. I have seen so many multi-line sentences or even texts containing >10 lines of text all made with separate test objects and then just manually lined up by eye, it hurt my mind. 



But I suppose its just in my head, its educating to hear some good arguments for  "Text" though.

 

0 Likes
Message 12 of 15

Sea-Haven
Mentor
Mentor

10 lines of text TXT2MTXT built in. 

0 Likes
Message 13 of 15

anton_chmidt
Advocate
Advocate
I know, but those also have some shapes inserted mid sentences so its like TEXT △ TEXT. So While TXT2MTXT is great and I use it alot, it wont work there well
0 Likes
Message 14 of 15

Kent1Cooper
Consultant
Consultant

So if it's plain Text or an Attribute definition, it would already be taken care of by the BC justification.  It's only if it's Mtext that you would want to Move it.  Since Help for both the (polar) AutoLisp function and the LASTPOINT System Variable both claim to be in current-UCS terms, I hope [without testing] that the (trans) part isn't needed for the second point of the Move displacement.  Try replacing your (command-s "_.move" ... line with this [untested]:

      (setq edata (entget e))
      (if (member '(0 . "MTEXT") edata); needed only for Mtext
        (command-s "_.move" e ""
          "_non" (trans (cdr (assoc 10 edata)) 0 1); first point of displacement
          "_non"
          (polar ; second point of displacement
            (getvar 'lastpoint)
            (+ (cdr (assoc 50 edata)) (/ pi 2)); "up" relative to rotation
            (/ (cdr (assoc 40 edata)) 4); 1/4 of text height
          ); polar
        ); command-s
      ); if

The 1/4 of the text height distance is my arbitrary choice -- change the 4 if you want something different.

Kent Cooper, AIA
Message 15 of 15

cristianmicha9FNV7
Observer
Observer

THANK YOU! 

0 Likes