Jump to content

Lisp routine to calculated weighted centroid of seperate lines


Monty Lisp

Recommended Posts

Hi All,

 

I'm trying to get the coordinates of a centroid of multiple seperate lines. It should be a centre of gravity of lines, but taking the length as weight. (So the sum of each line's midpoint x-coordinate times its length, divided by sum of all lengths, and the same for the y-coordinate).

 

Somehow I cannot find anywhere an example to do this yet I have the feeling it shouldn't be too difficult. I'm not too familiar with LISP but as autocad LT 2024 has the ability to load LISP files I suddenly see so many tiny processes which I can automate ;)

 

I hope someone can help me, 

 

Kind regards,

Monty Lisp

Link to comment
Share on other sites

Hello and welcome!

Try this:

(defun c:pp()
  (setq ssl (ssget '((0 . "LINE"))) xg 0 yg 0 zg 0 lt 0)
  (repeat (setq i (sslength ssl))
    (setq el (entget (ssname ssl (setq i (1- i))))
	  p1 (cdr (assoc 10 el)) p2 (cdr (assoc 11 el))
	  x1 (car p1) x2 (car p2) xm (/ (+ x1 x2) 2.0)
	  y1 (cadr p1) y2 (cadr p2) ym (/ (+ y1 y2) 2.0)
	  z1 (caddr p1) z2 (caddr p2) zm (/ (+ z1 z2) 2.0)
	  l (distance p1 p2)
	  xg (+ xg (* xm l)) yg (+ yg (* ym l)) zg (+ zg (+ zg l))
	  lt (+ lt l)
	  )
    )
    (setq ssl nil)
    (setq w (list (/ xg lt) (/ yg lt) (/ zg lt)))    
  )

For sure the masters around here will post shorter and more elegant code, I tried to write the program step by step. Post again if you need more clarifications...

Link to comment
Share on other sites

59 minutes ago, fuccaro said:

Hello and welcome!

Try this:

(defun c:pp()
  (setq ssl (ssget '((0 . "LINE"))) xg 0 yg 0 zg 0 lt 0)
  (repeat (setq i (sslength ssl))
    (setq el (entget (ssname ssl (setq i (1- i))))
	  p1 (cdr (assoc 10 el)) p2 (cdr (assoc 11 el))
	  x1 (car p1) x2 (car p2) xm (/ (+ x1 x2) 2.0)
	  y1 (cadr p1) y2 (cadr p2) ym (/ (+ x1 x2) 2.0)
	  z1 (caddr p1) z2 (caddr p2) zm (/ (+ z1 z2) 2.0)
	  l (distance p1 p2)
	  xg (+ xg (* xm l)) yg (+ yg (* ym l)) zg (+ zg (+ zg l))
	  lt (+ lt l)
	  )
    )
    (setq w (list (/ xg lt) (/ yg lt) (/ zg lt)))
    (setq ssl nil)
  )

For sure the masters around here will post shorter and more elegant code, I tried to write the program step by step. Post again if you need more clarifications...

 

Thanks! Such a quick answer. There was a tiny error for y1 (you use x1 and x2 again but with my limited knowledge of LSP I updated it to y1 and y2 and it worked!) 

 

I'll dissect the code and see if i can learn some LISP as this saves me quite some time! 

  • Thanks 1
Link to comment
Share on other sites

When you need say mid of 2 points this is handy as you dont need to work out X & Y values.

 

Both these do the same

(setq mp (mapcar '/ (mapcar '+ p1 p2) '(2.0 2.0 2.0))) ; divide by 2
(setq mp (mapcar '* (mapcar '+ p1 p2) '(0.5 0.5 0.5))) ; Multiply by 0.5

 

Link to comment
Share on other sites

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.

Guest
Unfortunately, your content contains terms that we do not allow. Please edit your content to remove the highlighted words below.
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...