Felix9 Posté(e) le 15 septembre 2022 Posté(e) le 15 septembre 2022 Bonjour, Tout est dans le titre je souhaiterais une routine Lisp qui me permette de faire pareil que la commande inverser texte c'est à dire, Je sélectionne plusieurs blocs et j'aimerais leur appliquer une rotation de +200gons par rapport à leur rotation actuelle ex : mon bloc a une rotation de 132.1215g, le Lisp change en 332.1215g par rapport au point d'insertion du bloc. J'aurais voulu la faire mais je ne m'y connais pas du tout et je ne vois pas du tout comment la faire Merci bcp à tous, Félix Citer
lecrabe Posté(e) le 15 septembre 2022 Posté(e) le 15 septembre 2022 Hello Voici un Lisp "BROT" qui fait une rotation de TOUS les Blocs selectionnes par rapport a leur rotation originale ! Et dans le meme fichier, il y a aussi IDEM "BECH" pour l Echelle des Blocs ... Routines : "BROT" et "BECH" - MERCI Gilles ! Bye, lecrabe PS: LSP extrait de mon stock de 3001 routines BROT____BECH.lsp Citer Autodesk Expert Elite Team
Luna Posté(e) le 15 septembre 2022 Posté(e) le 15 septembre 2022 (modifié) Coucou, Essaye ceci (non testé) : (defun c:RBx (/ r jsel i name entl rot) (if (null (setq r (getreal "\nValeur ajoutée pour la rotation <200> : "))) (setq r 200) ) (and (setq jsel (ssget '((0 . "INSERT")))) (repeat (setq i (sslength jsel)) (setq name (ssname jsel (setq i (1- i))) entl (entget name) rot (cdr (assoc 50 entl)) ) (entmod (subst (cons 50 (+ rot (angtof (vl-princ-to-string r) (getvar "AUNITS")))) (assoc 50 entl) entl)) ) ) (princ) ) Edit: Ou tout simplement les routines de Gile, précieusement conservées dans la bibliothèque de @lecrabe 😉 Bisous, Luna Modifié le 15 septembre 2022 par Luna Citer
Felix9 Posté(e) le 15 septembre 2022 Auteur Posté(e) le 15 septembre 2022 il y a 7 minutes, Luna a dit : Coucou, Essaye ceci (non testé) : (defun c:RBx (/ r jsel i name entl rot) (if (null (setq r (getreal "\nValeur ajoutée pour la rotation <200> : "))) (setq r 200) ) (and (setq jsel (ssget '((0 . "INSERT")))) (repeat (setq i (sslength jsel)) (setq name (ssname jsel (setq i (1- i))) entl (entget name) rot (cdr (assoc 50 entl)) ) (entmod (subst (cons 50 (+ rot (angtof (vl-princ-to-string r) (getvar "AUNITS")))) (assoc 50 entl) entl)) ) ) (princ) ) Edit: Ou tout simplement les routines de Gile, précieusement conservées dans la bibliothèque de @lecrabe 😉 Bisous, Luna Salut Luna et merci, Bon on doit pas être très loin du résultat attendu, ca m'ajoute seulement 100gons 90° et non 200° 180° De plus c'est possible de sélectionner le texte avant ou après le lancement de la commande ? Merci bcp !! Citer
Luna Posté(e) le 15 septembre 2022 Posté(e) le 15 septembre 2022 Je viens de tester rapidement (avec AUNITS en degrés décimaux et aussi en grades) et chat fonctionne très bien chez moi... J'ai mis 200 comme valeur par défaut (à supposer que AUNITS = 2 (grades), et si AUNITS = 0 (degrés décimaux) il faut mettre 180. Et le (ssget) sans méthode spécifiée permet la pré-sélection si tu as PICKFIRST = 1. Donc si tu sélectionnes tes blocs en amont, le programme posera la question de la rotation puis utilisera ta pré-sélection directement. De plus tu as un filtre actif sur la sélection/pré-sélection pour que seuls les blocs soient considérés. En tout cas, j'ai pas de soucis de mon côté >w< As-tu essayé les programmes proposés par @lecrabe pour voir si cela te convient mieux éventuellement ? Bisous, Luna Citer
Felix9 Posté(e) le 15 septembre 2022 Auteur Posté(e) le 15 septembre 2022 il y a 44 minutes, Luna a dit : Je viens de tester rapidement (avec AUNITS en degrés décimaux et aussi en grades) et chat fonctionne très bien chez moi... J'ai mis 200 comme valeur par défaut (à supposer que AUNITS = 2 (grades), et si AUNITS = 0 (degrés décimaux) il faut mettre 180. Et le (ssget) sans méthode spécifiée permet la pré-sélection si tu as PICKFIRST = 1. Donc si tu sélectionnes tes blocs en amont, le programme posera la question de la rotation puis utilisera ta pré-sélection directement. De plus tu as un filtre actif sur la sélection/pré-sélection pour que seuls les blocs soient considérés. En tout cas, j'ai pas de soucis de mon côté >w< As-tu essayé les programmes proposés par @lecrabe pour voir si cela te convient mieux éventuellement ? Bisous, Luna Je t'assure que ça me le tourne seulement de 90° ... Pourtant j'ai bien AUNIT=2.. tu aurais une idée ? J'avais regardé mais pas trouvé quelque chose qui me correspondait 100% 😉 EDIT : C'est bon il faut que je mette un angle de 300 par contre pour que ça me fasse un demi tour.. Dernière chose, je ne voudrais pas avoir a valider la rotation par exemple je sélectionne mes blocks, je lance la commande et ca tourne direct c'est possible ? Citer
Felix9 Posté(e) le 15 septembre 2022 Auteur Posté(e) le 15 septembre 2022 il y a une heure, lecrabe a dit : Hello Voici un Lisp "BROT" qui fait une rotation de TOUS les Blocs selectionnes par rapport a leur rotation originale ! Et dans le meme fichier, il y a aussi IDEM "BECH" pour l Echelle des Blocs ... Routines : "BROT" et "BECH" - MERCI Gilles ! Bye, lecrabe PS: LSP extrait de mon stock de 3001 routines BROT____BECH.lsp 1 Ko · 0 téléchargement Je n'avais pas vu ta réponse, merci, je voudrais juste que la rotation soit fixée à 200grade comme ça je clic sur un icone personnalisé, je sélectionne, je valide et hop tout est inversé Citer
Luna Posté(e) le 15 septembre 2022 Posté(e) le 15 septembre 2022 Peux-tu me fournir un .dwg d'exemple dans lequel cela ne fonctionne pas...car mathématiquement parlant, je suis perplexe >n< Ensuite, pour ta demande il suffit de faire moins, moi je propose un programme qui puisse être utile à tous ^^" Donc pour supprimer la question, il suffit de remplacer (if (null (setq r (getreal "\nValeur ajoutée pour la rotation <200> : "))) (setq r 200) ) par (setq r 200) et c'est tout... Voir plus proprement (pour conserver la possibilité si jamais) en rajoutant uniquement un point-virgule sur la ligne 1 et 3 (pour conserver la 2 uniquement) : ; (if (null (setq r (getreal "\nValeur ajoutée pour la rotation <200> : "))) (setq r 200) ; ) Bisous, Luna Citer
lecrabe Posté(e) le 15 septembre 2022 Posté(e) le 15 septembre 2022 Hello NON la routine BROT ne fixe pas une facteur de rotation quelque soit la rotation originale ! Sinon je suis aussi perplexe que Luna ! Bye, lecrabe Citer Autodesk Expert Elite Team
Felix9 Posté(e) le 16 septembre 2022 Auteur Posté(e) le 16 septembre 2022 Salut Luna, voici le dwg la lisp chargée j'ai rajouté 300 pour l'inversion Et merci bcp pour le reste !!! J'essaie tout à l'heure, Par contre ça ne fonctionne pas sur le bloc rouge ... pourquoi ? Merci Lecrabe pour ta réponse La bise Exemple.dwg Citer
Luna Posté(e) le 16 septembre 2022 Posté(e) le 16 septembre 2022 Oki, je viens de tester sur ton .dwg et.....bah le soucis ne vient pas de moi !! C'est ton .dwg qui a un soucis mais je n'arrive pas à comprendre la raison. En clair dans un fichier vierge, j'ai (si le format est un grade, degrés, radians, ...) (angtof "0") 0.0 Mais sur ton fichier j'ai (angtof "0") 1.5708 donc à cause de ce décalage d'un demi pi, cela fausse les rotations bien évidemment.... Je viens potentiellement de trouver une explication : NORTHDIRECTION ! Est-ce une variable système qui te parle ? Si oui, je ne peux rien y faire car je penser pouvoir faire (setq r (angtof (vl-princ-to-string r) (getvar "AUNITS"))) (+ r (getvar "NORTHDIRECTION")) mais malheureusement, peut importe la valeur de NORTHDIRECTION (si on lance la commande associée en tant qu'utilisateur) la ligne (getvar "NORTHDIRECTION") renvoie toujours 0.0 ! Donc je ne peux pas y faire grand chose pour prendre en compte cela, car cette variable influe directement la liste DXF des entités (par rapport à la palette des propriétés). Autrement, pour ce qui est du bloc rouge, le programme fonctionne mais je n'avais pas prévu les blocs avec attributs donc il faut rajouter un ATTSYNC pour les blocs Bisous, Luna 1 Citer
Felix9 Posté(e) le 16 septembre 2022 Auteur Posté(e) le 16 septembre 2022 il y a 3 minutes, Luna a dit : Oki, je viens de tester sur ton .dwg et.....bah le soucis ne vient pas de moi !! C'est ton .dwg qui a un soucis mais je n'arrive pas à comprendre la raison. En clair dans un fichier vierge, j'ai (si le format est un grade, degrés, radians, ...) (angtof "0") 0.0 Mais sur ton fichier j'ai (angtof "0") 1.5708 donc à cause de ce décalage d'un demi pi, cela fausse les rotations bien évidemment.... Je viens potentiellement de trouver une explication : NORTHDIRECTION ! Est-ce une variable système qui te parle ? Si oui, je ne peux rien y faire car je penser pouvoir faire (setq r (angtof (vl-princ-to-string r) (getvar "AUNITS"))) (+ r (getvar "NORTHDIRECTION")) mais malheureusement, peut importe la valeur de NORTHDIRECTION (si on lance la commande associée en tant qu'utilisateur) la ligne (getvar "NORTHDIRECTION") renvoie toujours 0.0 ! Donc je ne peux pas y faire grand chose pour prendre en compte cela, car cette variable influe directement la liste DXF des entités (par rapport à la palette des propriétés). Autrement, pour ce qui est du bloc rouge, le programme fonctionne mais je n'avais pas prévu les blocs avec attributs donc il faut rajouter un ATTSYNC pour les blocs Bisous, Luna Ha ouais c'est bizarre elle est définie a 100 chez moi et comme tu dis peu importe la valeur il faut que ma lisp soit a 300 pour que ça fonctionne... Bref c'est tout ce que je voulais, Non cette variable ne me dit rien du tout... dernière interrogation ? (setq jeusel (ssget '((0 . "TEXT,MTEXT,INSERT"))) incr 0 ) ;******************************************* (if (= (cdr (assoc 66 entcodes)) 1) ; si c'est un bloc avec attributs (progn (setq angobj (JBR2G (cdr (assoc 50 entcodes))) angrot (- 400 (- angvue angobj)) ) (command "_.rotate" entname "" (cdr (assoc 10 entcodes)) angrot) ) (progn (setq entcodes (subst (cons 50 (JBG2R angvue)) (assoc 50 entcodes) entcodes)) (entmod entcodes) ) ) (setq incr (1+ incr)) ) j'ai trouvé ça et je n'ai pas besoin de faire ATTSYNC avec cette lisp tu sais pk ? Citer
Luna Posté(e) le 16 septembre 2022 Posté(e) le 16 septembre 2022 Parce que la rotation est effectuée par la commande ROTATION si le bloc possède des attributs, autrement on modifie la liste DXF de l'entité pour appliquer la rotation sans utiliser de (command), car l'utilisation de cette fonction ralenti considérablement le temps d'exécution du programme ! Le code que je t'ai fourni, comme je l'ai précisé, est non testé car écrit à la va-vite en 2min. Donc forcément je ne me suis pas amusé à prévoir tous les cas de figures comme je ferais dans des programmes plus complexes. Bisous, Luna Citer
bonuscad Posté(e) le 16 septembre 2022 Posté(e) le 16 septembre 2022 En reprenant le code de @Luna sous cette forme, cela va mieux? (defun c:RBx ( / r jsel i name entl rot) (defun update_block (block_record ang pt / s_e dxf_e) (if (/= (getvar "ATTMODE") 1) (setvar "ATTMODE" 1)) (setq s_e block_record) (while (/= (cdr (assoc 0 (entget (setq s_e (entnext s_e))))) "SEQEND") (setq dxf_e (entget s_e)) (if (eq (cdr (assoc 0 dxf_e)) "ATTRIB") (progn (entmod (setq dxf_e (subst (cons 10 (polar pt (+ (angle pt (cdr (assoc 10 dxf_e))) (- ang (cdr (assoc 50 dxf_e)))) (distance pt (cdr (assoc 10 dxf_e))))) (assoc 10 dxf_e) dxf_e))) (entmod (setq dxf_e (subst (cons 50 ang) (assoc 50 dxf_e) dxf_e))) ) ) ) (entupd block_record) ) (if (null (setq r (getorient (strcat "\nValeur ajoutée pour la rotation <" (angtos (+ pi (getvar "ANGBASE")))"> : ")))) (setq r pi) ) (and (setq jsel (ssget '((0 . "INSERT")))) (repeat (setq i (sslength jsel)) (setq name (ssname jsel (setq i (1- i))) entl (entget name) rot (cdr (assoc 50 entl)) ) (entupd (cdar (entmod (subst (cons 50 (+ rot r)) (assoc 50 entl) entl)))) (update_block name (+ rot r) (cdr (assoc 10 entl))) ) ) (princ) ) Citer Choisissez un travail que vous aimez et vous n'aurez pas à travailler un seul jour de votre vie. - Confucius
Luna Posté(e) le 16 septembre 2022 Posté(e) le 16 septembre 2022 Coucou @bonuscad, Quand je vois toutes les fonctions auxquelles je n'ai pas pensé, je me sens un peu bête... ^^" C'est de suite un peu plus propre 😉 Merci, Luna Citer
Felix9 Posté(e) le 16 septembre 2022 Auteur Posté(e) le 16 septembre 2022 il y a 21 minutes, bonuscad a dit : En reprenant le code de @Luna sous cette forme, cela va mieux? (defun c:RBx ( / r jsel i name entl rot) (defun update_block (block_record ang pt / s_e dxf_e) (if (/= (getvar "ATTMODE") 1) (setvar "ATTMODE" 1)) (setq s_e block_record) (while (/= (cdr (assoc 0 (entget (setq s_e (entnext s_e))))) "SEQEND") (setq dxf_e (entget s_e)) (if (eq (cdr (assoc 0 dxf_e)) "ATTRIB") (progn (entmod (setq dxf_e (subst (cons 10 (polar pt (+ (angle pt (cdr (assoc 10 dxf_e))) (- ang (cdr (assoc 50 dxf_e)))) (distance pt (cdr (assoc 10 dxf_e))))) (assoc 10 dxf_e) dxf_e))) (entmod (setq dxf_e (subst (cons 50 ang) (assoc 50 dxf_e) dxf_e))) ) ) ) (entupd block_record) ) (if (null (setq r (getorient (strcat "\nValeur ajoutée pour la rotation <" (angtos (+ pi (getvar "ANGBASE")))"> : ")))) (setq r pi) ) (and (setq jsel (ssget '((0 . "INSERT")))) (repeat (setq i (sslength jsel)) (setq name (ssname jsel (setq i (1- i))) entl (entget name) rot (cdr (assoc 50 entl)) ) (entupd (cdar (entmod (subst (cons 50 (+ rot r)) (assoc 50 entl) entl)))) (update_block name (+ rot r) (cdr (assoc 10 entl))) ) ) (princ) ) C'est 100% ce que je voulais.. Un immense merci @bonuscad du coup tu sais d'où venait le fait que le 200g ne fonctionnait pas pour moi ? Merci à toi aussi @Luna Citer
Invité bonuscad Posté(e) le 16 septembre 2022 Posté(e) le 16 septembre 2022 Citation du coup tu sais d'où venait le fait que le 200g ne fonctionnait pas pour moi ? Tout venait de là : (getvar "ANGBASE") Pour être plus explicite ton dessin est défini en grade avec l'origine des angles au Nord et tournant dans le sens Horaire (je n'ai d’ailleurs pas vérifier cela vu que 200 c'est la moitié du cercle entier, donc ça ne change rien, mais pour des valeurs quelconques cela ne sera peut être pas correct, dans ce cas s'appuyer sur la variable ANGDIR) La base d'Autocad fonctionne en radians avec l'origine à l'Est et dans le sens anti-horaire, il faut faire les conversions adéquates! Citer
Invité bonuscad Posté(e) le 16 septembre 2022 Posté(e) le 16 septembre 2022 il y a une heure, Luna a dit : Coucou @bonuscad, Quand je vois toutes les fonctions auxquelles je n'ai pas pensé, je me sens un peu bête... ^^" C'est de suite un peu plus propre 😉 Merci, Luna Franchement avec la qualité de tes réponses et les codes que tu publies, il n'y a pas de quoi se sentir bête... On passe parfois à côté de choses évidentes, ou on prends des voies tortueuse, et cela m'arrive aussi 🥲 Citer
Olivier Eckmann Posté(e) le 16 septembre 2022 Posté(e) le 16 septembre 2022 Bonjour @Luna, A regarder aussi la différence entre un getangle et un getorient qui tient compte ou pas de cette direction. Sinon, il faut effectivement faire les calculs en fonction des variables ANGBASE et ANGDIR Olivier Citer
Luna Posté(e) le 16 septembre 2022 Posté(e) le 16 septembre 2022 @Olivier Eckmann, Yes j'avoue que je n'ai pas encore été confronté à la récupération de valeur angulaire au cours de mes pérégrinations donc je connaissais ANGBASE et ANGDIR (notamment à cause de SNAPANG) mais sans vraiment y prêter attention...Mais c'est bon à savoir pour les prochaines fois ! il y a 14 minutes, Invité bonuscad a dit : Franchement avec la qualité de tes réponses et les codes que tu publies, il n'y a pas de quoi se sentir bête... On passe parfois à côté de choses évidentes, ou on prends des voies tortueuse, et cela m'arrive aussi Vui j'avoue que j'ai souvent tendance à me torturer l'esprit devant des problèmes simplissimes parfois xD Mais bon, au final cela devient limite une signature dans le langage de programmation. Lorsque je lis les programmes de LeeMac par exemple, on le reconnaît très vite ^^ En tous cas, j'aime beaucoup la fonction (update_block) pour limiter l'utilisation de ATTSYNC, je ne savais pas que l'on pouvait le faire ainsi ! C'est souvent le soucis que j'ai parfois, savoir dans quels cas la fonction (command) est obligatoire et dans lesquels elle peut être habilement contournée. Bisous, Luna Citer
Messages recommandés