Aller au contenu

Joindre 3D polylignes selon calques


Messages recommandés

Posté(e)

Bonjour à tous.

 

Serait il possible à partir du lisp de Gile de, au lieu de sélectionner soi-même les polylignes 3D à joindre, sélectionner de manière automatique tous les polylignes 3D d'un même calque et de les joindre si elles sont jointives sinon non et ceci pour tous les calques d'un dessin autocad ?

 

 

 
;; Join3dPoly (gile)
;; Joint les objets sélectionnés en une polyligne 3d s'ils sont jointifs
;; La polyligne est créée avec les propriétés courantes (calque, couleur, ...)

(defun c:Join3dPoly (/ Space ss lst plst olst n 3p)
 (vl-load-com)
 (or *acdoc*
     (setq *acdoc* (vla-get-ActiveDocument (vlax-get-acad-object)))
 )
 (setq	Space (if (= (getvar "CVPORT") 1)
	(vla-get-PaperSpace *acdoc*)
	(vla-get-ModelSpace *acdoc*)
      )
 )
 (while (not (ssget '((-4 . "		       (0 . "LINE")
	       (-4 . "		       (0 . "POLYLINE")
	       (70 . 8)
	       (-4 . "AND>")
	       (-4 . "		       (0 . "LWPOLYLINE")
	       (70 . 0)
	       (-4 . "AND>")
	       (-4 . "OR>")
	      )
      )
 )
 )
 (vlax-for obj	(setq ss (vla-get-ActiveSelectionSet *acdoc*))
   (cond
     ((= (vla-get-ObjectName obj) "AcDbLine")
      (setq lst (cons
	   (cons obj
		 (list (vlax-get obj 'StartPoint)
		       (vlax-get obj 'EndPoint)
		 )
	   )
	   lst
	 )
      )
     )
     ((= (vla-get-ObjectName obj) "AcDbPolyline")
      (setq lst (cons (cons obj (PlinePoints obj)) lst))
     )
     ((= (vla-get-ObjectName obj) "AcDb3dPolyline")
      (setq lst
      (cons
	(cons obj (3d-coord->pt-lst (vlax-get obj 'Coordinates)))
	lst
      )
      )
     )
   )
 )
 (while (and lst (< (length olst) 2))
   (setq plst (cdar lst)
  olst (list (caar lst))
  lst  (cdr lst)
  n    0
   )
   (while (and lst (< n (length lst)))
     (cond
((equal (cadar lst) (last plst) 1e-9)
 (setq plst (append plst (cddar lst))
       olst (cons (caar lst) olst)
       lst  (cdr lst)
       n    0
 )
)
((equal (last (cdar lst)) (car plst) 1e-9)
 (setq plst (append (cdar lst) (cdr plst))
       olst (cons (caar lst) olst)
       lst  (cdr lst)
       n    0
 )
)
((equal (cadar lst) (car plst) 1e-9)
 (setq plst (append (reverse (cdar lst)) (cdr plst))
       olst (cons (caar lst) olst)
       lst  (cdr lst)
       n    0
 )
)
((equal (last (cdar lst)) (last plst) 1e-9)
 (setq plst (append plst (cdr (reverse (cdar lst))))
       olst (cons (caar lst) olst)
       lst  (cdr lst)
       n    0
 )
)
(T
 (setq lst (append (cdr lst) (list (car lst)))
       n   (1+ n)
 )
)
     )
   )
 )
 (if (and (= 1 (setq n (length olst))) (< 1 (vla-get-Count ss)))
   (princ "\nObjets non jointifs.")
   (progn
     (vla-StartUndoMark *acdoc*)
     (vlax-invoke Space 'add3dPoly (apply 'append plst))
     (if (= 1 n)
(princ "\n1 objet a été transformé en polyligne 3d.")
(princ (strcat "\n"
	       (itoa n)
	       " objets ont été joints en une polyligne 3d."
       )
)
     )
     (mapcar 'vla-delete olst)
     (vla-EndUndoMark *acdoc*)
   )
 )
 (vla-delete ss)
 (princ)
)

;;; 3d-coord->pt-lst
;;; Convertit une liste de coordonnées 3D en liste de points
;;; (3d-coord->pt-lst '(1.0 2.0 3.0 4.0 5.0 6.0)) -> ((1.0 2.0 3.0) (4.0 5.0 6.0))

(defun 3d-coord->pt-lst	(lst)
 (if lst
   (cons (list (car lst) (cadr lst) (caddr lst))
  (3d-coord->pt-lst (cdddr lst))
   )
 )
)

;;; PlinePoints
;;; Retourne la liste des sommets (coordonnées SCG) de la polyligne (ename ou vla-object)

(defun PlinePoints (pl / sub)
 (vl-load-com)
 (or (= (type pl) 'VLA-OBJECT)
     (setq pl (vlax-ename->vla-object pl))
 )

 (defun sub (l e n)
   (if	l
     (cons (trans (list (car l) (cadr l) e) n 0)
    (sub (cddr l) e n)
     )
   )
 )

 (sub (vlax-get pl 'Coordinates)
      (vla-get-Elevation pl)
      (vlax-get pl 'Normal)
 )
)

 

En effet, j'ai un plan autocad de restitution qui pèse plus de 100Mo avec un nombre de polylignes important et j'aimerais automatiser certaines procédures.

 

Je n'ariive pas non plus à lister moi même la liste des calques d'un dessin autocad avec la fonction getlayer.ou a moins que cette fonction serve à choisir le calque courant..

 

Merci par avance de votre aide.

Chris_mtp

Posté(e)

Re,

 

Voilà, je n'ai pas testé en profondeur, mais ça semble marcher

 

(defun c:AutoJoinByLayer (/ *error* lock lst ss pl1 lst1 pt lst2 pl2)
 (vl-load-com)
 (or *acad* (setq *acad* (vlax-get-acad-object)))
 (or *acdoc* (setq *acdoc* (vla-get-ActiveDocument *acad*)))
 (or *layers* (setq *layers* (vla-get-Layers *acdoc*)))

 (defun *error* (msg)
   (or	(= msg "Fonction annulée")
(princ (strcat "\nErreur: " msg))
   )
   (vla-ZoomPrevious *acad*)
   (vla-EndUndoMark *acdoc*)
   (princ)
 )

 (vla-StartUndoMark *acdoc*)
 (vla-zoomExtents *acad*)
 (vlax-for lay	*layers*
   (if	(ssget "_X"
       (list '(0 . "POLYLINE")
	     '(70 . 8)
	     (cons 8 (vla-get-Name lay))
       )
)
     (progn
(and (= (vla-get-Lock lay) :vlax-true)
     (setq lock T)
     (vla-put-Lock lay :vlax-false)
)
(setq lst nil)
(vlax-for poly (setq ss (vla-get-ActiveSelectionSet *acdoc*))
  (setq lst (cons poly lst))
)
(vla-delete ss)
(while (cdr lst)
  (setq	pl1  (car lst)
	lst  (cdr lst)
	lst1 (3d-coord->pt-lst (vlax-get pl1 'Coordinates))
	pt   (last lst1)
  )
  (while
    (and
      (or
	(and
	  (setq	ss (ssget "_C"
			  (trans pt 0 1)
			  (trans pt 0 1)
			  (list	'(0 . "POLYLINE")
				'(70 . 8)
				(cons 8 (vla-get-Name lay))
			  )
		   )
	  )
	  (setq ss (ssdel (vlax-vla-object->ename pl1) ss))
	  (= 1 (sslength ss))
	)
	(and
	  (not
	    (vlax-put pl1
		      'Coordinates
		      (apply 'append (setq lst1 (reverse lst1)))
	    )
	  )
	  (setq pt (last lst1))
	  (setq	ss (ssget "_C"
			  (trans pt 0 1)
			  (trans pt 0 1)
			  (list	'(0 . "POLYLINE")
				'(70 . 8)
				(cons 8 (vla-get-Name lay))
			  )
		   )
	  )
	  (setq ss (ssdel (vlax-vla-object->ename pl1) ss))
	  (= 1 (sslength ss))
	)
      )
      (setq pl2 (vlax-ename->vla-object (ssname ss 0)))
      (setq lst2 (3d-coord->pt-lst (vlax-get pl2 'Coordinates)))
      (or (equal pt (car lst2) 1e-9)
	  (and (setq lst2 (reverse lst2))
	       (equal pt (car lst2) 1e-9)
	  )
      )
    )
     (vlax-put
       pl1
       'Coordinates
       (apply 'append (setq lst1 (append lst1 (cdr lst2))))
     )
     (vla-update pl1)
     (setq lst (vl-remove pl2 lst))
     (vla-delete pl2)
     (setq pt (last lst2))
  )
)
(and lock
     (not (setq lock nil))
     (vla-put-Lock lay :vlax-true)
)
     )
   )
 )
 (vla-ZoomPrevious *acad*)
 (vla-EndUndoMark *acdoc*)
 (princ)
) 

Gilles Chanteau - gileCAD - GitHub
Développements sur mesure pour AutoCAD

Posté(e)

Merci Gile pour ce lisp modifie

 

Je l'ai testé dans diverses config comme des poly 2d joint à des poly 3d, des poly 3d non jointives, des poly 3d jointives d'un même calque et appartenant à des calques différents.

Et franchement, il n'y a pas de problème. Le lisp marche à merveille et dans tous les cas de figure.

 

Merci encore qui je pense va rendre service à plus d'un.

 

Chris_mtp.

Créer un compte ou se connecter pour commenter

Vous devez être membre afin de pouvoir déposer un commentaire

Créer un compte

Créez un compte sur notre communauté. C’est facile !

Créer un nouveau compte

Se connecter

Vous avez déjà un compte ? Connectez-vous ici.

Connectez-vous maintenant
×
×
  • Créer...

Information importante

Nous avons placé des cookies sur votre appareil pour aider à améliorer ce site. Vous pouvez choisir d’ajuster vos paramètres de cookie, sinon nous supposerons que vous êtes d’accord pour continuer. Politique de confidentialité