-
Compteur de contenus
1 113 -
Inscription
-
Dernière visite
-
Jours gagnés
42
Type de contenu
Profils
Forums
Calendrier
Blogs
Tout ce qui a été posté par Luna
-
Il y a 10 types de personnes dans le monde : celles qui comptent en binaire et les autres
Luna a répondu à un(e) sujet de (gile) dans Débuter en LISP
C'est tout bonnement magnifique !!! En revanche, la fonction (dec->transparency) peut s'écrire sans le (if) car elle est identique à ma fonction donc (fix (/ (- 255 (lsh (lsh 16777216 24) -24)) 2.55)) retourne 100 Donc pas la peine de vérifier l'octet le plus gauche :3 Autrement l'utilisation du (logior) démontre parfaitement que je n'ai pas encore compris son utilisation parfaitement ^^" Mais comme chat, je ne serais plus enquiquinée par ce fameux code DXF 440, donc merci beaucoup à vous deux ! Bisous, Luna -
Coucou, Un exercice sans difficulté de programmation en tant que tel, mais le but étant de réfléchir "autrement". On a tous eu besoin à un moment donné eu besoin de récupérer la liste des sommets d'une polyligne et pour ce faire, on a chacun(e) sa méthode :3 Cependant je me suis bien souvent demandé, existe-t-il une solution plus rapide ? Pour simplifier le challenge, l'exercice se porte uniquement sur les LWPOLYLINE, car les SPLINE, LINE, POLYLINE, ARC, etc ne possède pas les mêmes approches de programmation selon les objets. On peut prendre n'importe quel langage (en revanche je ne sais pas s'il existe un moyen d'utiliser un BenchMark sur plusieurs type de langage différent...?) histoire de comparer également les simplicités d'écriture selon les langages. La liste retournée doit contenir l'ensemble des sommets de la polyligne, dans le sens de lecture de la polyligne (donc le sommet de départ au début, le dernier à la fin) et le but étant de trouver une version qui permet d'aller suffisamment vite en fonction du nombre de sommets. J'ai généré sur le fichier ci-joint 4 polylignes ayant respectivement 10, 100, 1 000 et 10 000 sommets qui serviront de base (pour que tout le monde est la même). Le nombre de lignes importe peu, la vitesse d'exécution servira de comparaison. Concernant le Benchmark, j'utilise le BenchMark de Michael Puckett mais si vous en avez un autre, dite le histoire de maximiser les points communs pour la comparaison. Pour le temps de réponse, disons que je posterais mes versions ce we mais il n'y a pas de limite de temps 😜 Bisous, Luna get-pt-list.dwg BenchMark (Michael Puckett).lsp
-
Il y a 10 types de personnes dans le monde : celles qui comptent en binaire et les autres
Luna a répondu à un(e) sujet de (gile) dans Débuter en LISP
En revanche lorsque la valeur est DuBloc, ta fonction retourne 6579400 ce qui n'est pas l'idéal :3 Je n'avais en effet pas remarqué qu'un pas de 10 pour la transparence correspondait à un pas de 25.5 pour la valeur binaire... Belle remarque ! Il est vrai que le résultat, même si concluant, ne me satisfait pas totalement >n< c'est quelque peu frustrant de ne pas comprendre la logique de cette notation ! Après tout la transparence pourrait parfaitement être spécifiée directement avec sa valeur affichée mais au lieu de cela, il s'agit d'un nombre binaire dont on utilise les bits 25 (ou 24 pour DuBloc) à 1, puis les bits 0 à 7. A quoi servent ces bits non-utilisés ? A quoi sert le bit 24/25 ? Quelle serait la valeur supposée pour "DuCalque" (en couleur DuBloc = 0 et DuCalque = 256 par exemple) ? ... Il est vrai qu'avoir une formation pourrait éclaircir quelques zones d'ombre vui mais de là à en trouver une qui puisse répondre aussi à des questions propres à AutoCAD, difficile à dire :S Bisous, Luna -
Il y a 10 types de personnes dans le monde : celles qui comptent en binaire et les autres
Luna a répondu à un(e) sujet de (gile) dans Débuter en LISP
Merci @(gile) je comprends mieux maintenant en effet ! Je me disais bien qu'AutoCAD avait tout de même prévu une solution pour spécifier des valeurs binaires dans la liste de filtre sans passer par une écriture lourde. Le pire c'est que j'ai lu le cours de LeeMac il y a 1-2 semaines sur la fonction (ssget) et je suis complètement passé à côté de ces opérateurs de comparaison ! >n< Du coup (je sais je suis lourde) pour filtrer une transparence spécifique, comment doit-on s'y prendre ? J'avais essayé avec un (lsh) de 32 bit mais cela ne fonctionne pas...Donc j'ai essayé de décortiquer le problème depuis l'écriture binaire : ;; if Transparency = DuCalque ;; -> code DXF 440 (facultatif) non présent ;; if Transparency = DuBloc ;; -> (440 . 16777216) soit 0001 0000 0000 0000 0000 0000 0000 en notation binaire ;; if Transparency = 0 ;; -> (440 . 33554687) soit 0010 0000 0000 0000 0000 1111 1111 en notation binaire ;; if Transparency = 10 ;; -> (440 . 33554661) soit 0010 0000 0000 0000 0000 1110 0101 en notation binaire ;; if Transparency = 20 ;; -> (440 . 33554636) soit 0010 0000 0000 0000 0000 1100 1100 en notation binaire ;; if Transparency = 30 ;; -> (440 . 33554610) soit 0010 0000 0000 0000 0000 1011 0010 en notation binaire ;; if Transparency = 40 ;; -> (440 . 33554585) soit 0010 0000 0000 0000 0000 1001 1001 en notation binaire ;; if Transparency = 50 ;; -> (440 . 33554559) soit 0010 0000 0000 0000 0000 0111 1111 en notation binaire ;; if Transparency = 60 ;; -> (440 . 33554534) soit 0010 0000 0000 0000 0000 0110 0110 en notation binaire ;; if Transparency = 70 ;; -> (440 . 33554508) soit 0010 0000 0000 0000 0000 0100 1100 en notation binaire ;; if Transparency = 80 ;; -> (440 . 33554483) soit 0010 0000 0000 0000 0000 0011 0011 en notation binaire ;; if Transparency = 90 ;; -> (440 . 33554457) soit 0010 0000 0000 0000 0000 0001 1001 en notation binaire Donc j'ai bien vu que les bits 8 à 23 sont non-utilisés, du coup je suis partie sur l'hypothèse que l'on peut "ignorer" le(s) bit(s) 24 et 25 en faisant un décalage de 20 vers la gauche, puis vers la droite : ;; if Transparency = 0 ;; -> (lsh (lsh 33554687 20) -20) retourne 255 ;; et ;; if Transparency = 90 ;; -> (lsh (lsh 33554457 20) -20) retourne 25 ;; Autrement dit la plus proche supposition que j'ai pu faire c'est : ;; Notons la valeur de la transparence du code 440 "Tsp" (defun Dec->Transparency (Tsp) (fix (/ (* 100 (- 255 (lsh (lsh Tsp 20) -20))) 255.0)) ) ;; Ainsi fait j'obtiens bien les résultats suivants : ;; (dec->Transparency 33554687) retourne 0 ;; (dec->Transparency 33554661) retourne 10 ;; (dec->Transparency 33554636) retourne 20 ;; (dec->Transparency 33554579) retourne 42 ;; (dec->Transparency 33554483) retourne 80 ;; (dec->Transparency 33554457) retourne 90 ;; (dec->Transparency 16777216) retourne 100 (= DuBloc) ;; Cependant je n'arrive pas à comprendre la présence du bit 25 et 24, ni même quelle est la ;; solution un peu plus "directe" pour la conversion... ;; Car du coup je ne sais pas comment faire l'inverse...étant donné que la fonction (fix) me ;; donne la partie entière du résultat de la division mais en partant de la partie entière, ;; je ne peux pas en déterminer les décimales nécessaires... Donc même si j'arrive à obtenir un résultat concluant dans un sens, je ne peux pas faire la transposition dans l'autre sens à cause de cette fonction (fix)... As-tu déjà étudier ce code DXF 440 pour pouvoir le comparer à des valeurs connues ou pas du tout ? Bisous, Luna -
En effet, ne l'utilisant jamais (notamment parce que je ne m'y suis jamais intéressée) je l'ai oublié malheureusement :3 Bien qu'il s'agisse d'un simple exemple il faudrait dans ce cas prendre les deux valeurs (1 ou 129) (ssget '( (-4 . "<OR") (-4 . "<AND") (0 . "INSERT") (8 . "Calque#") (-4 . "AND>") (-4 . "<AND") (0 . "LWPOLYLINE") (90 . 4) (-4 . "<OR") (70 . 1) (70 . 129) (-4 . "OR>") (-4 . "AND>") (-4 . "OR>") ) ) ;; Sélectionne soit les blocs situés sur les calques nommés "Calque0", "Calque1", "Calque2", ;; "Calque3", "Calque4", "Calque5", "Calque6", "Calque7", "Calque8" ou "Calque9" OU BIEN les ;; polylignes fermées possédant 4 sommets. PS : j'avais également mal orthographié la fermeture de mon "OR>" :S Bisous, Luna
-
Court, simple, efficace ! 😉 Faudrait que je regarde comment fonctionne les macros, chat peut suffire parfois par rapport au LISP ^^" Bisous, Luna
-
Vui, j'ai testé rapidement chat ne modifie pas l'objet voilà tout (pas d'erreur en soit donc pas de sushis !), en revanche étant donné que j'entmod uniquement à la fin, si le type de ligne n'existe pas, la couleur n'est pas forcée non plus donc à modifier éventuellement selon les besoins de chacun :3 Bisous, Luna
-
Coucou, Essaye ceci (non testé) : (defun c:Force>COLOR+LTYPE (/ jsel i name entlist co lt n subprop) (defun subprop (entlist tag value) (if (assoc tag entlist) (subst (cons tag value) (assoc tag entlist) entlist ) (append entlist (list (cons tag value)) ) ) ) (if (setq n 0 co 252 lt "Cache" jsel (ssget) ) (progn (repeat (setq i (sslength jsel)) (setq name (ssname jsel (setq i (1- i))) entlist (entget name) entlist (subprop entlist 62 co) entlist (subprop entlist 6 lt) entlist (vl-remove-if '(lambda (x) (member (car x) '(420 430)) ) entlist ) ) (if (entmod entlist) (setq n (1+ n))) ) (prompt (strcat "\nUn total de " (itoa n) " / " (itoa (sslength jsel)) " objets ont été modifiés avec succès." ) ) ) ) (princ) ) Il n'y a pas de vérification sur l'existence du type de ligne dans le dessin mais je doute que cela soit nécessaire. La couleur et le type de ligne sont définis en argument pour pouvoir les modifier à tout moment depuis l'IDE. J'ai également ajouté la suppression des codes 420 et 430 au cas où (je ne sais pas comment se comporte l'entité si on modifie son code 62 alors qu'elle possède un code 420 et/ou 430. Tu peux également te remove le (prompt) si pas besoin (c'est juste par habitude que je fais chat) Bisous, Luna
-
Les opérateurs logiques AND, OR, XOR sont peu utilises et souvent ils sont utilisés ensemble par exemple : (ssget '( (-4 . "<OR") (-4 . "<AND") (0 . "INSERT") (8 . "Calque#") (-4 . "AND>") (-4 . "<AND") (0 . "LWPOLYLINE") (90 . 4) (70 . 1) (-4 . "AND>") (-4 . "<OR") ) ) ;; Sélectionne soit les blocs situés sur les calques nommés "Calque0", "Calque1", "Calque2", ;; "Calque3", "Calque4", "Calque5", "Calque6", "Calque7", "Calque8" ou "Calque9" OU BIEN les ;; polylignes fermées possédant 4 sommets. Bisous, Luna
-
La fonction (quote), également notée ' permet de lire une expression sans l'évaluer donc c'est pour cela que les listes écrites en dur, on utilise cette fonction (quote) command: (setq lst (list 1 2 3)) (1 2 3) command: (setq lst '(1 2 3)) (1 2 3) command: (setq lst (1 2 3)) ; erreur: fonction incorrecte: 1 ;; Si on ne met pas de quote ou qu'on n'utilise pas (list), AutoCAD va vouloir évaluer la ;; liste comme s'il s'agissait d'une fonction, induisant ici une erreur command: (setq a 1) (1 2 3) command: (setq lst (list a 2 3)) (1 2 3) command: (setq lst '(a 2 3)) (A 2 3) command: (setq lst (a 2 3)) ; erreur: fonction incorrecte: A ;; Si l'on a besoin d'injecter une variable dans la liste, la fonction (quote) ne fonction plus ;; car elle ne va pas évaluer la variable A en utilisant sa valeur. ;; La fonction (quote) est également souvent utilisée pour les fonctions d'ordre supérieur comme ;; (mapcar), (vl-sort), (vl-remove-if), ... car le but étant de spécifier en argument une fonction ;; sans qu'elle soit évaluée comme argument (on a besoin de l'expression telle quelle, et non sa ;; valeur). Après c'est uniquement un "raccourci" d'écriture donc si tu ne comprends pas parfaitement son utilisation, utilise ce que tu connais et maîtrise le avant d'avancer un peu plus :3 Au début ce n'est pas toujours évident de percevoir toutes les subtilités et comme il n'existe jamais qu'une seule et unique vérité, le plus simple est de progresser pas à pas en consolidant les bases :3 Les cours de (gile) et didier sont excellents pour débuter et consolider les bases au maximum et pour ce qui est de la maîtrise, il n'y a qu'en forgeant qu'on devient forgeron :) Bon courage ! Bisous, Luna
-
Juste pour ton information, les codes DXF -4 ne sont pas nécessaire dans ta liste des filtres de la fonction (ssget) :3 (ssget (list '(-4 . "<AND") '(0 . "INSERT") '(8 . "01 BA Rupteurs L10") '(-4 . "AND>"))) ;; Equivaut à (ssget '((-4 . "<AND") (0 . "INSERT") (8 . "01 BA Rupteurs L10") (-4 . "AND>"))) ;; Equivaut à (ssget (list '(0 . "INSERT") '(8 . "01 BA Rupteurs L10"))) ;; Equivaut à (ssget '((0 . "INSERT") (8 . "01 BA Rupteurs L10"))) ;; On peut ici s'épargner des (-4 . "<AND>") car la liste fonctionne naturellement selon une logique AND ;; et comme ta liste de filtres n'est pas variable, tu peux également t'épargner la fonction (list) ;; suivie de plusieurs ' (= (quote)) pour chaque filtre, une seule ' (= (quote)) suffit ! Bisous, Luna
-
Pas de soucis ! Je remarque que tu as enlevé la vérification sur l'EffectiveName du bloc, donc faut juste s'assurer que dans tes calques "01 BA Rupteurs*" tu n'as pas d'autres blocs :3 Autrement chat fait plaisir de voir des personnes venir pour quelques explications pour trouver la solution par soi-même ! Il n'y a que comme chat qu'on progresse de toutes façons Bisous, Luna
-
En effet la gestion par calques et la version la plus simple et efficace pour la séparation des objets ! Après rien n'exclu le fait de créer des blocs identiques mais avec une dénomination différente (pour séparer vos rupteurs en façade et en acrotères) ou bien de passer par des visibilités au sein du bloc (mais moins pratique pour un SELECTSIMILAR par exemple) :3 Ainsi il ne restera plus qu'à faire une séparation des bâtiments via les calques (chat divise par deux le nombre de calques). Pour ce qui est des jeux de sélection, tu as déjà de nombreuses formations sur le net ("Introduction à AutoLISP" de (gile), "Da-Code" de didier, AfraLISP, ...) mais cela n'a rien de bien sorcier :3 Il faut voir cela comme une liste nommée que l'on parcours à l'aide de fonctions d'itération comme (while) ou (repeat) : ;; Version avec (while) (if (setq i 0 jsel (ssget)) ; Initialisation du compteur i à 0 (premier entité dans le jeu de sélection (while (< i (sslength jsel)) ; Démarrage de la boucle (setq name (ssname jsel i)) ; Récupération du nom de l'entité à l'indice i du jeu de sélection ... (setq i (1+ i)) ; Incrémentation du compteur i de 1 par rapport à sa valeur précédente ) ; Fin de la boucle ) ;; -> On parcours le jeu de sélection en partant de la première entité (= 0), jusqu'à la dernière (= (n-1)) avec n le nombre d'objets sélectionnés ;; Version avec (repeat) (if (setq jsel (ssget)) (repeat (setq i (sslength jsel)) ; Démarrage de la boucle et initialisation du compteur i correspondant au nombre d'entités (setq name (ssname jsel (setq i (1- i)))) ; Récupération du nom d'entité à l'indice i et incrémentation de i de -1 ... ) ; Fin de la boucle ) ;; -> On parcours le jeu de sélection en partant de la dernière entité (= (n-1)), jusqu'à la première (= 0) avec n le nombre d'objets sélectionnés ;; PS : Si l'on utilise la fonction (ssdel) permettant de supprimer un objet du jeu de sélection, la version (while) devra incrémenter l'indice i uniquement si l'objet n'est pas supprimé du jeu de sélection (décalage de la numérotation des objets au sein du jsel de 1 vers la gauche en cas de suppression). Ce souci n'est pas préssent dans la version (repeat) car on démarre de la dernière entité donc même si la numérotation change, seules les objets déjà traités sont impactés. A part chat qui reste quasiment tout le temps identique, il y a juste à programmer le reste entité par entité comme tu l'as fait dans ton programme :3 Bisous, Luna
-
Coucou, Vouih en effet toujours filtrer selon le code DXF 0 = "INSERT" lorsqu'on gère des blocs, cela permet d'esquiver un grand nombre de soucis ! Juste en précision du message de @(gile) ci-dessus, il faut se méfier des entités RESEAUX, car malheureusement ils sont eux aussi considérés comme des "INSERT" mais ils ne possèdent pas la propriété "BlockTableRecord/Name" (ils sont anonymisés). Donc si ton .dwg possède (ou risque de posséder) des entités RESEAU, je te suggère d'ajouter une condition sur une propriété commune entre les blocs et les réseaux : ;; En passant par la propriété "ClassName" équivalente à "AcDbAssociativeRectangularArray", etc pour des réseaux et "" pour des blocs dynamiques/standards (if (and (= (cdr (assoc 0 (entget ent))) "INSERT") (= (getpropertyvalue ent "ClassName") "") (= (getpropertyvalue ent "BlockTableRecord/Name") "01_BA_Rupteur") ) ... ) ;; En passant par une fonction de gestion d'erreur (if (and (= (cdr (assoc 0 (entget ent))) "INSERT") (not (vl-catch-all-error-p (setq name (vl-catch-all-apply 'getpropertyvalue (list ent "BlockTableRecord/Name"))))) (= name "01_BA_Rupteur") ) ... ) ;; En passant par les fonctions Visual LISP (if (and (= (cdr (assoc 0 (entget ent))) "INSERT") (vlax-property-available-p (vlax-ename->vla-object ent) 'EffectiveName) (= (vlax-get-EffectiveName (vlax-ename->vla-object ent)) "01_BA_Rupteur") ) ... ) Autrement, pas besoin de filtrer ces entités casse-tête ! :3 Sinon, si tu as besoin de faire cette démarche sur plusieurs blocs portant le même nom, ne serait-il pas plus simple de faire une boucle (while) sur un jeu de sélection au lieu de devoir sélectionner les blocs un par un manuellement ? Bisous, Luna
-
Je ne les sélectionnes pas il me semble (mais chat fonctionne >w<) Je peux te proposer ceci : (defun GetTabOrder->list (/ layout-list layout) (vlax-for layout (vla-get-layouts (vla-get-activedocument (vlax-get-acad-object))) (setq layout-list (cons (cons (vla-get-name layout) (vla-get-taborder layout)) layout-list)) ) (vl-sort layout-list '(lambda (l1 l2) (< (cdr l1) (cdr l2)))) ) (defun SetTabOrder (lst / layout layout-list) (if (and (= (length lst) (length (setq layout-list (cdr (GetTabOrder->list))))) (mapcar '(lambda (layout) (vla-put-taborder (vla-item (vla-get-layouts (vla-get-activedocument (vlax-get-acad-object))) (car layout) ) (cdr layout) ) ) lst ) ) T nil ) ) (defun List->SetTabOrder (f / layout i) (setq i 0) (mapcar '(lambda (layout) (cons layout (setq i (1+ i))) ) (vl-sort (mapcar 'car (cdr (GetTabOrder->list))) f ) ) ) Il n'est pas possible de spécifier une liste tronquée lorsqu'on re-définit le tab-order des layouts (sinon si tu places une présentation entre la 2 et 3, tu auras 2 fois une présentation avec un tab-order de 3) donc c'est pour cela que je n'ai pas d'argument de liste. Cependant avec les 3 fonctions ci-dessus, tu peux spécifier la manière dont tu souhaites trier tes présentations depuis la fonction (List->SetTabOrder) (la fonction de tri correspond à la fonction que (vl-sort) utilise comme argument donc avec une ' !) et s'applique sur la liste de l'ensemble des présentations (donc une liste d'atomes de type string). En terme d'utilisation, c'est comme ceci : (settaborder (list->settaborder '>)) ;; return T if successful, nil if not. ;; Les présentations ont été trié dans l'ordre décroissant (alphanumérique de base de la fonction (vl-sort)) à partir du nom de ces dernières (settaborder (list->settaborder '<)) ;; return T if successful, nil if not. ;; Les présentations ont été trié dans l'ordre croissant (alphanumérique de base de la fonction (vl-sort)) à partir du nom de ces dernières (settaborder (list->settaborder '(lambda (l1 l2) (< (substr x (- (strlen l1) 2)) (substr x (- (strlen l2) 2)))))) ;; return T if successful, nil if not. ;; Les présentations ont été trié dans l'ordre croissant (alphanumérique de base de la fonction (vl-sort)) à partir des 3 derniers caractères du nom des présentations Je pense que cela devrait répondre à ton besoin pour l'insérer dans ton programme et ajuster le tri de la liste correctement. Pour info le (cdr (GetTabOrder->list)) c'est pour éjecter la présentation "Model" de la liste car elle doit être à 0 impérativement donc on n'y touche pas :3 Si jamais tu ne sais pas ce que tu tri, je te laisse regarder ce que retourne (GetTabOrder->list) et (mapcar 'car (cdr (GetTabOrder->list))) :3 Bisous, Luna
-
En effet, LeeMac est une pointure et référence en terme de développements UserFriendly ! J'avais complètement oublié ce programme :3 Par contre, il n'est pas une référence pour "récupérer" des bouts de codes de ses programmes ou du moins, pas lorsqu'on débute (à côté de personnes comme LeeMac ou (gile), nous sommes toutes et tous des débutants xD) donc à voir selon tes besoins :3 Bisous, Luna
-
Vouih, je m'en serais bien passé (parce que du coup le (grread) tourne deux fois) mais c'est un mal nécessaire :3 C'est le même principe que pour la méthode native : on spécifie le segment/sommet à partir duquel on veut travailler, puis on ajoute le point. Sauf que là le segment peut être différent entre plusieurs polylignes donc bon... ^^" Mais j'avoue que ce n'était pas forcément très clair de prime abord ! Bon ben chat me rassure un peu alors ! Bon théoriquement ce n'est rien de plus qu'une matrice mais j'avoue que j'ai besoin de "voir" la matrice pour comprendre les calculs à faire donc le visual j'ai un peu du mal car on obtient toujours des #<safearray...> ce qui complexifie un peu la lecture... (ce n'est que très récemment que j'ai appris qu'avec l'espion on pouvait "parcourir" les VLA-Object par un double-clic donc par exemple d'écrire (vlax-get-acad-object), l'espionner et parcourir toutes les propriétés disponibles pour récupérer une infos utiles comme par exemple la liste des layers, layouts, etc). Bref j'apprends toujours mais le Visual me fait un peu peur donc je préfère approfondir mes connaissances en LISP pour maîtriser à minima un langage avant d'en apprendre de nouveaux ! Entre rien savoir sur tout ou tout savoir sur rien, je préfère partir de rien xD Il me semble surtout que les (append) sont beaucoup plus lent à l'exécution que des (cons) et (reverse) mais je n'en suis pas sûre du tout pour être honnête...^^" Il faudrait faire un benchmark pour vérifier mais bon, c'est du pinaillage sur un programme pas complet ^^ En tous cas, merci de prendre du temps pour chercher un développement fonctionnel :3 Bisous, Luna
-
Coucou @(gile) ! Merci du partage :3 Cependant AddVtx et DelVtx ne fonctionne que pour une unique entité linéaire...Mais si c'est applicable pour une entité, c'est applicable pour un ensemble en généralisant quelques inputs :) Bisous, Luna
-
Coucou, Pour l'un de mes programmes, j'utilise ceci pour remettre les présentations dans l'ordre : (defun get-init-layout-pos (/ i tabs lay-list lay Init_Pos-list) (vl-load-com) (setq i 0 tabs (vla-get-layouts (vla-get-activedocument (vlax-get-acad-object))) lay-list (layoutlist) ) (foreach lay (reverse lay-list) (setq Init_Pos-list (cons (cons lay (vla-get-taborder (vla-item tabs lay))) Init_Pos-list)) ) Init_Pos-list ) (defun set-layout-pos (/ i d tabs Init_Pos lay-list lay lay-move) (vl-load-com) (setq i 0 d 0 tabs (vla-get-layouts (vla-get-activedocument (vlax-get-acad-object))) lay-list (layoutlist) Init_Pos (get-init-layout-pos) ) (foreach lay lay-list (vla-put-taborder (vla-item tabs lay) (setq i (1+ i))) (if (/= (cdr (assoc lay Init_Pos)) i) (setq d (1+ d) lay-move (cons lay lay-move) ) ) ) (prompt (strcat "\nUn total de " (itoa (length lay-list)) " présentations ont été prises en compte." "\nSur les " (itoa (length lay-list)) ", " (itoa (length lay-move)) " présentations ont changé de position." "\nVoici la liste des présentations ayant été déplacé :" (DXF_List lay-move "\"\n - \"" "left" t nil) "\n" ) ) ) A voir si cela peut t'aider... Tu peux également essayer de regarder sur CadTutor ou TheSwamp pour avoir plus d'idées/exemples pour l'adapter au mieux à tes besoins :3 Bisous, Luna
-
Coucou, Du coup tu as opté pour supprimer la seconde boucle permettant de spécifier le point à ajouter ^^" Même si chat ajoute un (grread), cela permet de spécifier un nouveau point proche d'un autre segment que celui spécifié par exemple, autrement on est obligé d'ajouter un point situé entre la projection deux sommets du segment, ce qui peut s'avérer limitant à l'utilisation, nan ? :S Je me doutais que tu passerais par les fonction (vlax-curve), mais je viens (enfin !) de comprendre la définition d'un paramètre, ce qui me facilite grandement la récupération des sommets d'un segment !! 0w0 Nettement plus simple que de récupérer la liste des points et de regarder la position du point sélectionner par rapport à la liste ^^ Pour la modification des polylignes, je ne maîtrise pas du tout les safe-array &Co donc je ne sais pas vraiment quelle est le plus rapide et/ou simple entre (entmod) et (vla-add-vertex)... Qu'est-ce qui pose problème ? Il suffit d'ajouter le point devant les autres non ? Bon après je réfléchis en modification de liste DXF donc je ne sais pas si c'est pareil pour les fonctions vlax-* :3 Je ne me suis pas non plus posée la question dans le cas où, la polyligne est fermée :S Juste une question, pourquoi utiliser la fonction (append) au lieu de (cons) pour la création de ta liste de points ? Bisous, Luna
-
Ooooohhh merci beaucoup !!! C'est tellement mieux ainsi !!! Et c'est gratuit, quoi de plus parfait :3 Encore merci ♥ Bisous, Luna
-
Vouih en effet c'est une bonne remarque, mais il me semble que récupérer le segment "courant" est un peu plus long et l'avantage de ne pas se pré-occuper du sens de la polyligne c'est que l'entmod est simple. J'essaierai de regarder ce que chat donne pour une sélection de segments communs, mais du coup cela risque d'être plus compliquer à optimiser... De plus cela soulève plusieurs questions, comme par exemple lorsqu'on veut ajouter un sommet à la fin d'une polyligne ou si on clique sur un sommet (pouvant appartenir à 1, 2 voire plusieurs segments), quel segment choisir ? bref, les sommets était plus simple ^^" Lors de mes essais, en ayant seulement 100 objets sur le dessin (et en en modifiant qu'une seule !), le logo de chargement était visible et à 1000, les fps dropent instantanément... Donc en vrai je ne suis même pas sûre que son utilisation soit...viable à la longue ! Bisous, Luna
-
Coucou, Vui, normalement pour ajouter un sommet à une polyligne, il suffit d'utiliser le menu d'un vertex pour spécifier le "point de départ" et le segment sera déterminé en fonction du sens de la polyligne (en amont ou en aval de ce point). Ici le fonctionnement est identique, je ne peux pas spécifier un "segment de départ" étant donné que le but du programme est de pouvoir ajouter un point commun à un ensemble de polylignes. Donc ce que je fais c'est de demander un point de départ qui s'adaptera pour chaque polyligne. C'est l'équivalent d'un osnap sur les extrémités mais à l'échelle d'un dessin. Donc le plus simple selon moi pour récupérer ce point de départ c'est de récupérer le sommet le plus proche du point spécifié pour chaque polyligne et d'afficher le segment impacté en fonction du sens de la polyligne. C'est un peu comme si on cliquait sur le vertex d'un point et qu'on ajoute le sommet depuis le menu dynamique sauf qu'on le fait pour plusieurs polylignes en même temps donc je récupère le point et non le segment pour la première sélection. Cependant j'ai remarqué que plus le .dwg possède un grand nombre d'objets et plus le rafraîchissement est long et lag. Et ce, même si l'on effectue la commande sur une seule entité, ce qui est très frustrant... Donc il faudrait vraiment que j'optimise le programme au maximum pour limiter le nombre d'itérations et de boucle à chaque déplacement de la souris mais ce n'est pas simple... Bref un programme utile mais très vite saturé par le nombre d'objets situés dans le .dwg >n< Petite question : Comment fais-tu le screencast ? Car cela peut s'avérer plus efficace que des mots parfois :3 Bisous, Luna
-
Un simple MTEXT ou TEXT n'est pas suffisant pour l'insertion d'un champs dynamique ? De plus il faut forcément ré-attribuer la fenêtre à chaque nouvelle référence de texte car le champ est rattaché au handle si je ne me trompe pas ? Bisous, Luna
-
Que se soit en LISP ou sous forme de macro, si le SCU n'existe pas, tu auras une erreur, mais bon le principal c'est que cela fonctionne correctement chez toi ! Bisous, Luna
