sanetmunde Posted April 24, 2018 Posted April 24, 2018 Hi, I want a LISP routine which can insert blocks along the polyline. I have two dynamic blocks. They are 'Straight Duct' and 'Elbow90'. Consider I draw a polyline with three XY coordinates i.e. (1,1) , (1,2) and (2,2) and insert rectangular block with desired 'Width'. Here are list of things I want from LISP program: 1. I want 'Straight Duct' to be inserted at mid-points of '(1,1) & (1,2)' and '(1,2) & (2,2)'. 2. Also, those inserted blocks should be rotated with an angle made by those points with horizontal so that 'Straight Duct' remains along the line. Example, Angle made by line joining points '(1,1) & (1,2)' with horizontal is 90 Deg. Hence, Dynamic Block should be rotated by 90 degree about midpoint. 3. Move the grip of 'Straight Duct' (which facing to open end of polyline) to the open end of polyline. Move other grip of 'Straight Duct' to the length of (150+ Width/2) mm less than the intersection point. 4. Insert 'Elbow90' at the point with polar angle 45 Degree to point of intersection and polar radius (150 + Width/2) mm. Also, the grip of elbow should be moved so that width of 'Elbow90' should be as same as that of 'Straight Duct'. Pls refer the attached file for understanding the problem. Can anyone help me out? HVAC Dynamic Blocks 24.04.2018.dwg Quote
hanhphuc Posted April 25, 2018 Posted April 25, 2018 (edited) Hi, I want a LISP routine which can insert blocks along the polyline....1. I want 'Straight Duct' to be inserted at mid-points of '(1,1) & (1,2)' and '(1,2) & (2,2)'... ... Can anyone help me out? we prefer this volunteering forum is more for discussion than asking for freebies. if you learned then you can solve it yourself in future (defun c:dbtest (/ s doc spc en w r obj pt blk ) ;hanhphuc 25.04.2018 (if (and (tblsearch "Block" "[b][color="purple"]Straight Duct[/color][/b]") (setq doc '(( l / doc) (setq doc (vlax-get-acad-object)) (foreach x l (setq doc (vlax-get doc x)))) spc (doc '(ActiveDocument ActiveLayout Block)) ) (while (not s) (setq s (ssget "_:S:L+." '((0 . "LWPOLYLINE")(-4 . "=" )(70 . 0)))) ) (setq en (ssname s 0)) [color="green"];;; (setq en (car (entsel "\nPlease select LWPOLYLINE.. "))) ;;; (eq (cdr (assoc 0 (entget en))) "LWPOLYLINE")[/color] (progn (initget 7) (setq w (getdist "\nWidth of the duct : ") r (+ (/ w 2.0) 150.) ) (setvar 'filletrad r) (vl-cmdf "_FILLET" "P" en) ) (setq obj (vlax-invoke (vlax-ename->vla-object en) 'explode)) ) (progn (foreach x (mapcar ''((a) (mapcar ''((x) (vlax-get a x)) '(StartPoint EndPoint))) (vl-remove-if ''((x) (/= "AcDbLine" (vla-get-ObjectName x))) obj) ) (setq pt (apply 'mapcar (cons ''((a b)(* 0.5 (+ a b))) x)) blk (vla-InsertBlock spc (vlax-3d-point pt) "[color="purple"][b]Straight Duct[/b][/color]" 1 1 1 (apply 'angle x) ) ) ([color="blue"][b]LM:SETDYNPROPVALUE[/b][/color] blk "[b][color="purple"]Legnth[/color][/b]" (apply 'distance x)) ([color="blue"][b]LM:SETDYNPROPVALUE[/b][/color] blk "[b][color="purple"]Width[/color][/b]" w) (vlax-put blk 'InsertionPoint pt) ) (foreach x (mapcar ''((a) (vlax-get a 'Center)) (vl-remove-if ''((x) (/= "AcDbArc" (vla-get-ObjectName x))) obj) ) [color="green"] ;This is example to draw circle [/color] (entmakex (list '(0 . "CIRCLE") (cons 10 x) (cons 40 [color=red][b]150[/b][/color] ))) [color="green"] ;Try Coding yourself here ... refer to the above example ;Insert block "[b]ELBOW90[/b]" ;You need to identify which quadrant or rotation to suit ;or let other volunteers to guide you :-) [/color] ) ) (progn (alert "\nOops.. please retry! ") (command "start" "explorer \"http://www.cadtutor.net/forum/showthread.php?104092-Inserting-Dynamic-Blocks-along-the-points-of-Polyline-using-LISP\"") ) ) (princ) ) [color="green"];; Get Dynamic Block Property Value - Lee Mac ;; Returns the value of a Dynamic Block property (if present) ;; blk - [vla] VLA Dynamic Block Reference object ;; prp - [str] Dynamic Block property name (case-insensitive)[/color] (defun LM:getdynpropvalue ( blk prp ) (setq prp (strcase prp)) (vl-some '(lambda ( x ) (if (= prp (strcase (vla-get-propertyname x))) (vlax-get x 'value))) (vlax-invoke blk 'getdynamicblockproperties) ) ) [color="green"];; Set Dynamic Block Property Value - Lee Mac ;; Modifies the value of a Dynamic Block property (if present) ;; blk - [vla] VLA Dynamic Block Reference object ;; prp - [str] Dynamic Block property name (case-insensitive) ;; val - [any] New value for property ;; Returns: [any] New value if successful, else nil[/color] (defun LM:setdynpropvalue ( blk prp val ) (setq prp (strcase prp)) (vl-some '(lambda ( x ) (if (= prp (strcase (vla-get-propertyname x))) (progn (vla-put-value x (vlax-make-variant val (vlax-variant-type (vla-get-value x)))) (cond (val) (t)) ) ) ) (vlax-invoke blk 'getdynamicblockproperties) ) ) (vl-load-com) Edited April 25, 2018 by hanhphuc 'mid,ssget,add link,comments,radius=150 Quote
BIGAL Posted April 26, 2018 Posted April 26, 2018 hanhphuc well done but a simpler answer may have been search for "DUCT" I know that a couple of the stars here have some good packages and your right they may not be free. Quote
sanetmunde Posted April 26, 2018 Author Posted April 26, 2018 Thank you for the Response. I have learned some basics and modified a program which can insert blocks along the polyline with required rotation and at required point. Here is the code. (defun C:PtoDB (/ plent plobj coords num pt p1 p2 p3 ang1 ang2 diff width ang3 p4) (setq plent (car (entsel "\nSelect Polyline: ")) plobj (vlax-ename->vla-object plent) coords (vlax-get plobj 'Coordinates); un-differentiated list of X Y [& Z if applicable] coordinate values ); setq (setq num (if (= (cdr (assoc 0 (entget plent))) "LWPOLYLINE") 2 3)) ; LW Polylines have only X & Y; "heavy" 2D & 3D have X Y & Z (repeat (/ (length coords) num) (repeat num ; number of coordinates to separate into a point list (setq pt (append pt (list (car coords))) coords (cdr coords) ) ); repeat ); repeat (setq pt (reverse pt)); list of coordinates divided up into point lists (setq width (getint "Enter the width of duct:")) (setq p1 (list (nth 1 pt) (nth 0 pt) 0)) (setq p2 (list (nth 3 pt) (nth 2 pt) 0)) (setq p3 (list (nth 5 pt) (nth 4 pt) 0)) (setq ang1 (angtos (angle p1 p2))) (setq ang2 (angtos (angle p2 p3))) (setq diff (+ 150 (/ width 2))) (cond ((and (or (> (cadr p2) (cadr p1)) (> (cadr p2) (cadr p3))) (or (> (car p2) (car p1)) (> (car p2) (car p3)))) (setq ang3 (itoa 0)) (setq p4 (list (- (car p2) diff) (- (cadr p2) diff) 0)) ) ((and (or (> (cadr p2) (cadr p1)) (> (cadr p2) (cadr p3))) (or (< (car p2) (car p1)) (< (car p2) (car p3)))) (setq ang3 (itoa 90)) (setq p4 (list (+ (car p2) diff) (- (cadr p2) diff) 0)) ) ((and (or (< (cadr p2) (cadr p1)) (< (cadr p2) (cadr p3))) (or (< (car p2) (car p1)) (< (car p2) (car p3)))) (setq ang3 (itoa 180)) (setq p4 (list (+ (car p2) diff) (+ (cadr p2) diff) 0)) ) ((and (or (< (cadr p2) (cadr p1)) (< (cadr p2) (cadr p3))) (or (> (car p2) (car p1)) (> (car p2) (car p3)))) (setq ang3 (itoa 270)) (setq p4 (list (- (car p2) diff) (+ (cadr p2) diff) 0)) ) ) ;(print ang3) ;(foreach n p4 (print n)) (command "_Insert" "Straight Duct" "_mtp" p1 p2 1 "" ang1) (command "_Insert" "Straight Duct" "_mtp" p2 p3 1 "" ang2) (command "_Insert" "Elbow90" p4 1 "" ang3) ); defun Now, I am working on stretching the grips of dynamic block using LISP. I need to get grips adjusted as per variable "Width". Can you refer some similar thread? Quote
hanhphuc Posted April 27, 2018 Posted April 27, 2018 hanhphuc well done but a simpler answer may have been search for "DUCT" I know that a couple of the stars here have some good packages and your right they may not be free. should thanks to handy functions by Lee save half of coding times! i'm not the HVAC guy, so i can't comment correct or wrong. p/s: as an outsider: explode - double offset filleted lwpolyline does the trick but there must be some reason why using dynamic blocks? Quote
hanhphuc Posted April 27, 2018 Posted April 27, 2018 Thank you for the Response. I have learned some basics and modified a program which can insert blocks along the polyline with required rotation and at required point. Here is the code. (defun C:PtoDB ...) Now, I am working on stretching the grips of dynamic block using LISP. I need to get grips adjusted as per variable "Width". Can you refer some similar thread? Good try. AFAIK autolisp can't make it. It can be done by modifying vla-GetDynamicBlockProperties via VLisp. look at the sub-function by Lee Mac above. for "Straight Duct" - Legnth & Width for "elbow90" - Width1 & Width2 Note: But my version does not support some grips in new version, so you need to try your own p/s : legnth length ,typos? Quote
sanetmunde Posted April 27, 2018 Author Posted April 27, 2018 I already have a program which convert points into polylines with required 'Width'. I want to use Dynamic Block for Data Extraction. VLISP looks difficult to understand. I will try to modify sub-function by Lee Mac and will let you know. Thank you Quote
hanhphuc Posted April 27, 2018 Posted April 27, 2018 (edited) I already have a program which convert points into polylines with required 'Width'. I want to use Dynamic Block for Data Extraction. VLISP looks difficult to understand. I will try to modify sub-function by Lee Mac and will let you know. Thank you i don't think VLISP is difficult as you think, put some time to study you'll find it's magic! example you can calculate mid point block( insertion point ) along polyline with vlax-curve- functions vlax-curve-getdistat.. vlax-curve-getpointat.. vlax-curve-getEndpointat.. etc.. you just need to supply the argument then it works like magic without complex math calculation!! you don't need to modify Lee's function, it works by just supplying required arguments. Lee wrote some others useful dynamic block functions, just look at his website Edited April 27, 2018 by hanhphuc link added Quote
JB1 Posted November 10, 2023 Posted November 10, 2023 Hi. I'm trying to learn Lisp to make plumbing drawings faster using polylines. I do have dynamic blocks which consist of 90 ups, 90 downs, 45's, Wye's, Tee's etc. I'm wondering the best way to go about learning to do this or any videos which could help me to understand how best to go about this task Quote
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.