mateus Posté(e) le 15 juillet 2013 Posté(e) le 15 juillet 2013 Bonsoir à tous, je poste ce sujet car j'ai un soucis avec mon code pour l'instant je voudrais insérer mon premier bloc sur ma droite après l'avoir crée. Mais le problème c'est qu'il ne s'insère pas comme je le voudrais, il y a un problème au niveau de l'angle que j'ai calculé (gisement) voici mon code ci-dessous : (defun c:MAIN () (setq alignementEnCours (ALIGNEMENT)) (setq ListeDecal (DECAL_RESEAU alignementEncours)) (setq premierCandelabre (getpoint "\n cliquez sur le premier candélabre " ) projectionCandelabre (PROJECTION premierCandelabre (car ListeDecal) (cadr ListeDecal) (caddr ListeDecal) (cadddr ListeDecal) ) ) (setq decalageCandelabre (getdist "\n Indiquez le décalage des candélabres" ) ) (setq gisRadian (GISEMENT (car ListeDecal) (cadr ListeDecal) (caddr ListeDecal) (cadddr ListeDecal) ) ) (setq gisGrade (rad2grad gisRadian)) (ASSISTANT decalageCandelabre projectionCandelabre gisGrade) ) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Alignement;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (defun ALIGNEMENT () (setq 1erPoint (getpoint "\nsélectionner le premier point de votre alignement" ) ; sélection du premier point de l'alignement 2emePoint (getpoint "\nsélectionner le deuxième point de votre alignement" ) ; sélection du deuxième point de l'alignement ) (command "polylign" 1erPoint 2emePoint "") ;tracé de l'alignement (cdar (entget (entlast))) ;récupère le nom de l'entité "Alignement" ) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; DECAL_RESEAU;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (defun DECAL_RESEAU (AL) (command "décaler" (getdist "\nvaleur de décalage du réseau") AL (getpoint "\nCliquer sur le côté du réseau") "" ) ; décalage de l'alignement pour réseau (setq nomEntité (entlast)) ;mise en variable de la poly décalée = réseau (setq listeDXF (entget nomEntité)) ;récupère la liste DXF de la polylign "réseau" (setq xa (cadr (assoc 10 listeDXF))) ;récupère le x du premier sommet (setq ya (caddr (assoc 10 listeDXF))) ;récupère le y du premier sommet (setq xb (cadr (assoc 10 (cdr (member (assoc 10 listeDXF) listeDXF))) ) ) ;récupère le x du deuxième sommet (setq yb (caddr (assoc 10 (cdr (member (assoc 10 listeDXF) listeDXF))) ) ) ;récupère le y du deuxième sommet (list xa ya xb yb) ) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; PROJECTION;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (defun PROJECTION (C xa ya xb yb) ;avec ;C= point à projeter sur la droite ;P= projeté orthonormal ;r= paramètre indiquant l'emplacement de P sur la droite ;L= module de la droite (setq xc (car C)) (setq yc (cadr C)) (setq L (sqrt (+ (* (- xb xa) (- xb xa)) (* (- yb ya) (- yb ya))))) (setq r (/ (- (* (- ya yc) (- ya yb)) (* (- xa xc) (- xb xa))) (* L L) ) ) (setq PX (+ xa (* r (- xb xa)))) ; abscisse du projeté orthonormal (setq PY (+ ya (* r (- yb ya)))) ; ordonné du projeté orthonomal ;(setq P (list PX PY) ) (list PX PY) ) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; GISEMENT;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (defun GISEMENT (xa ya xb yb) (atan (/ (abs ;valeur absolue (- xb xa) ) (abs (- yb ya) ) ) ) ) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Assistant;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (defun ASSISTANT (decal 1erCandelabre gisGrade / p1 p2 p3 p4 p5 p6 p7) ;;decal, 1erCandelabre, gisGrade -->arguments et p1 à p7 sont les variables locales. (if (not (tblsearch "BLOCK" "assistant")) (progn (command "zoom" "f" "-5,15,0" "-5,-15,0" "") (command "ortho" "a" "") (setq p1 '(0 0 0) p2 (polar p1 (/ pi 2) decal) p3 (polar p2 pi 2) p4 (polar p2 0 2) p5 (polar p1 (- (/ pi 2)) decal) p6 (polar p5 pi 2) p7 (polar p5 0 2) ) (command "polylign" p1 p2 p3 p4 p2 p1 p5 p6 p7 "") (setq ent (entlast)) (command "zoom" "et" "") (command "ortho" "i" "") (command "_block" "assistant" p1 ent "") ) ;;progn ) (command "inserer" "assistant" 1erCandelabre 1 1 gisGrade "") ) (defun rad2grad (gisRadian) (/ (* gisRadian 200) pi) ) Je sais que Giles, si tu passes par ici, tu m'as déjà conseillé de ne pas relancer des routines mais c'est juste que j'aimerai vraiment utiliser les fonctions préalablement crées pour que je sente que je contrôle le maximum de choses et que je comprenne ce que je fais. Le bloc s'insère mais pas perpendiculairement à la droite. Merci à vous
mateus Posté(e) le 16 juillet 2013 Auteur Posté(e) le 16 juillet 2013 Le gisement est toujours donné en grade et calcul l'angle entre deux points par rapport à l'axe des ordonnées. Il doit y avoir un soucis par apport à cette axe des ordonnées justement. Je me demande sur quel axe il se base pour faire le gisement....
mateus Posté(e) le 16 juillet 2013 Auteur Posté(e) le 16 juillet 2013 J'ai regardé à nouveau ce matin et en fait j'ai bêtement vu mon erreur, il ne faut pas que j'utilise le gisement entre mes deux points pour placer perpendiculairement à ma droite mes blocs. Du coup il faut que je cherche un autre moyen , par contre bizarrement le gisement entre mes deux points ne vaut pas exactement l'angle d'orientation d'insertion de mon bloc je n'ai pas trop compris à ce niveau bref il faut que je cherche un autre moyen pour placer mes blocs perpendiculairement :)
mateus Posté(e) le 16 juillet 2013 Auteur Posté(e) le 16 juillet 2013 Et j'ai rien dis pour le gisement c'est le même angle <_<
mateus Posté(e) le 16 juillet 2013 Auteur Posté(e) le 16 juillet 2013 Est ce que quelqu'un aurait une idée pour que je puisse insérer mon bloc perpendiculairement à ma droite ? Merci d'avance
mateus Posté(e) le 16 juillet 2013 Auteur Posté(e) le 16 juillet 2013 Une solution serait que je place mon scu local sur ma droite, que je règle au préalable les angles en degrés et que j'insère mon bloc à 90 degrés de ma droite. Mais si je pouvais trouver une meilleure méthode ça serait l'idéale... :unsure:
didier Posté(e) le 17 juillet 2013 Posté(e) le 17 juillet 2013 coucou je ne te suis pas dans ton code!!! mais je pense que si tu définis ton bloc avec une rotation de 100 grades dès le départ ce sera réglé. amicalement Éternel débutant... Mon site perso : Programmer dans AutoCAD
mateus Posté(e) le 17 juillet 2013 Auteur Posté(e) le 17 juillet 2013 Bonjour Didier :) Oui je comprends j'ai mis la totalité de mon programme désolé en fait c'est juste que je demande à l'utilisateur qui trace une droite avec deux points en guise d'alignement à une route. Cet alignement est décalée pour obtenir le réseau des luminaires et après je voudrais placer mes luminaires mais c'est clair que je pars dans des trucs mais ça doit être un truc tout bête... Merci en tout cas !
mateus Posté(e) le 17 juillet 2013 Auteur Posté(e) le 17 juillet 2013 J'essai avec ce bout de code : (defun ORIENTATION (listeDecal / angl) (setq pta (list (car ListeDecal) (cadr ListeDecal)) ptb (list (caddr ListeDecal) (cadddr ListeDecal)) ) (setq angl (angle 'pta 'ptb)) (+ angl (/ pi 2 )) ) avec pta et ptb mes deux points de la droite, je voudrai que la fonction retourne le résultat de l'angle entre ces deux points + 90 degrés mais on m'affiche cette erreur : ; erreur: type d'argument incorrect: point 2D/3D: PTA Merci par avance
-Olivier- Posté(e) le 17 juillet 2013 Posté(e) le 17 juillet 2013 Bonjour Mogo,Pourquoi as-tu une apostrophe devant PTA et PTB ?Olivier
mateus Posté(e) le 17 juillet 2013 Auteur Posté(e) le 17 juillet 2013 j'ai regardé dans l'aide et c'était inscrit comme cela mais j'ai même essayant sans et ça n'a pas marché non plus :/
mateus Posté(e) le 17 juillet 2013 Auteur Posté(e) le 17 juillet 2013 Bonsoir , je n'arrive toujours pas à calculer mon angle entre mes deux points de la droite :/ il me prend en compte que le pi/2 j'ai l'impression mais quand j'ajoute un espion sur ma variable "angl" elle vaut "nil" je ne comprends pas <_< (defun ORIENTATION (listeDecal / angl) (setq pta (list (car ListeDecal) (cadr ListeDecal)) ptb (list (caddr ListeDecal) (cadddr ListeDecal)) ) (setq angl (angle pta ptb)) (+ angl (/ pi 2 )) )
mateus Posté(e) le 17 juillet 2013 Auteur Posté(e) le 17 juillet 2013 Bon j'ai réussi mais bizarrement j'ai pas compris pk ça fonctionne comme cela. (defun ORIENTATION (listeDecal / angl) (setq pta (list (car ListeDecal) (cadr ListeDecal)) ptb (list (caddr ListeDecal) (cadddr ListeDecal)) ) (angle pta ptb) ) (defun radianDegre (angl); argument qui est égal à orient (l'angle en radian entre les deux points de la droite) (* (/ angl pi) 180.0)); conversion de l'angle en radian en degré ) En fait j'ai juste récupéré les deux points de ma droite, utilisé la commande "angle" entre ces deux derniers. et j'ai convertit l'angle retourné en radian en degré avec la fonction ci-dessus. Pour moi je pensais qu'il fallait rajouter 90 degrés à l'angle entre ces deux points, mais la conversion des radians en degrés à suffit pour obtenir une insertion perpendiculaire du block. Si quelqu'un peut m'expliquer je veux bien :) Bonne soirée !
mateus Posté(e) le 21 juillet 2013 Auteur Posté(e) le 21 juillet 2013 Bonjour à tous , Je suis sérieusement bloqué pour le calcul du point sur ma droite. J'ai rentré dans mon lisp la formule du "gisement" et du "calcul du point" mais après coup je me suis rendu compte qu'il y avait plusieurs cas possible pour le "calcul du point" soit 4 cas (voir "formule d'obtention d'un point P2 à partir d'un point P1". En effet mon programme fonctionne dans une seule condition: il faut que ma droite soit compris dans les x et y positifs. Concrètement, j'aimerai dire à mon programme : si ta droite est comprise dans les x et y positifs -->valeurs de "cos" et "sin" sont positivessi ta droite est comprise dans les x positifs et les y négatifs --> valeur de cos positive et valeur de sin négativesi ta droite est comprise dans les x négatifs et les y négatifs --> valeur de cos et sin négativeset enfin si ta droite est comprise dans les x négatifs et y positifs --> valeur de cos négatif et valeur de sin positive Voici mon code de gisement et calcul du point actuel : ;________________________________________________________________________________________ GISEMENT________________________________________________________________________________________________ (defun GISEMENT (xa ya xb yb) ; avec: xa et ya coordonnées du point A de la droite // xb et yb sont les coordonnées du point B de la droite (atan (/ (abs ;valeur absolue (- xb xa) ) (abs (- yb ya) ) ) ) ) ;________________________________________________________________________________________CALCULPOINT________________________________________________________________________________________________ (defun CALCULPOINT (PX PY module gis / QX QY) ;;avec ;;PX : abscisse du premier luminaire ;;PY : ordonnée du premier luminaire ;;module: distance entre les deux points ;;gis: gisement AB ;;QX abscisse du prochain point recherché ;;QY ordonné du prochain point recherché (setq QX (+ PX (* module (sin gis)))) (setq QY (+ PY (* module (cos gis)))) (list QX QY) ) Merci par avance
mateus Posté(e) le 21 juillet 2013 Auteur Posté(e) le 21 juillet 2013 je pense avoir trouvé mais il faudrai que je puisse récupérer le signe d'une variable je pensais a faire comme cela : (defun CALCULPOINT (ListeDecal PX PY module gis / xa ya xb yb deltaX deltaY QX QY) ;;avec ;;PX : abscisse du premier luminaire ;;PY : ordonné du premier luminaire ;;module: distance entre les deux points ;;gis: gisement AB les deux points de la droite ;;xa: abscisse du pta ;;ya: ordonnée du pta ;;xb: abscisse du ptb ;;yb: ordonnée du ptb ;;QX abscisse du prochain point recherché ;;QY ordonné du prochain point recherché (setq xa (car ListeDecal) ya (cadr ListeDecal) xb (caddr ListeDecal) yb (cadddr ListeDecal) ) ;je récupère ici les coordonnées des deux points de la droite (setq deltaX(- xb xa) deltaY(- yb ya) ) ;calcul des delta x et y ;ici je souhaiterai dire : si deltaX et deltaY sont positifs alors --> formule 1 si deltaX est positif et deltaY et négatif alors --> formule2 si deltaX et deltaY sont négatifs alors --> formule3 sinon si deltaX est négatif et deltaY est positif alors --> formule4 ;;formule1 (setq QX (+ PX (* module (sin gis)))) (setq QY (+ PY (* module (cos gis)))) (list QX QY) )
(gile) Posté(e) le 21 juillet 2013 Posté(e) le 21 juillet 2013 Salut, Je t'avais monté ici comment utiliser la fonction native angle. Cette fonction retourne l'angle en radians dans le sens anti-horaire (trigonométrique) entre l'axe X et le vecteur défini par les deux points.C'est sous cette forme qu'AutoCAD effectue en interne tous les calculs d'angle.C'est donc la valeur à utiliser excepté avec la fonction command. Je t'avais montré aussi dans la même réponse comment convertir cet angle en unités courantes et en tenant compte des variables ANGDIR et ANGBASE avec les fonctions angtos et atof.;; Retourne le gisement entre deux points ;; L'angle retourné est exprimé en unités courantes en prenant ;; en compte les valeurs de ANGBASE et ANGDIR (defun gisement (p1 p2) (atof (angtos (angle p1 p2) (getvar "AUNITS") 16)) )Si c'est pour utiliser directement avec la fonction command, il n'est pas nécessaire d'appeler atof (command accepte les arguments numériques sous forme de chaîne.Attention aussi avec command à ce que les points passés en argument soient définis dans le SCU courant (ce qui est le cas s'ils proviennent du résultat d'un appel à getpoint. Gilles Chanteau - gileCAD - GitHub Développements sur mesure pour AutoCAD
mateus Posté(e) le 21 juillet 2013 Auteur Posté(e) le 21 juillet 2013 Bonjour Gile , j'avais bien compris ces fonctions là. Je vais essayer de m'expliquer différemment parce que on ne s'est pas bien compris. J'essai de calculer et placer les luminaires sur une droite qui est en vérité mon réseau d'éclairage suivant l'entraxe désiré par l'utilisateur. Je suis encore dans la partie test de mon programme. Ma démarche a été la suivante (et j'aimerai pour l'instant rester dans cette démarche car je comprends bien mon programme) j'ai commencé par demander à l'utilisateur de tracer une droite en deux points (pta ptb) --> 1ère fonctionEnsuite j'ai décalé cet alignement pour en avoir le réseau d'éclairage.J'ai demandé où est ce que l'utilisateur voulait placer son premier candélabre , j'en ai fait la projection.Je demande l'entraxe des candélabres et le décalage de ces derniers par rapport au réseau principal.je calcul l'angle entre mes deux points de droite (pta ptb) avec la commande (angle) justement que je laisse en radianJe crée la fonction tangente et la met en variable.je calcule le côté opposé de l'angle calculé juste avant.La fonction module qui est la distance entre le premier candélabre et mon prochain.Je calcul le gisement avec la formule mathématique que je laisse également en radian.Et pour finir je calcul le prochain candélabre à l'aide de la fonction "CALCULPOINT" j'utilise alors volontairement la formule du gisement car elle se base par rapport à l'axe des ordonné et que c'est cette formule qui m'est demandé pour la formule du calcul du point. Seulement il y a 4 cas de figures pour utiliser cette formule (document joint en post #15) c'est pour cela que je demandais de l'aide pour pouvoir récupérer le signe d'une variable pour pourvoir faire des conditions et donc, choisir la formule approprié au cas de figure. mon programme actuel fonctionne dans le cas ou le deltaX et deltaY sont compris entre 0 et 100 grades.Il me reste 3 autres cas à traiter. Si tu pouvois m'aider sur ce cas de figure Gile, je t'en serai reconnaissant. Bonne soirée Ps: ci-joint : mon lisp actuelboucle abscisse block_V3.LSP
mateus Posté(e) le 21 juillet 2013 Auteur Posté(e) le 21 juillet 2013 Néanmoins j'ai quand même essayé avec ta formule du gisement que tu m'as envoyé dans ton dernier post qui utilise la fonction "angle" "atof" "angtos". Je l'ai remplacé par ma fonction gisement et ensuite j'ai essayé avec la fonction calcul du POINT les points ne sont pas alignés il y a le deuxième point qui est au dessus du premier. Voilà j'aimerai juste que tu m'aides dans mon cas de figure. Merci :)
(gile) Posté(e) le 21 juillet 2013 Posté(e) le 21 juillet 2013 Excuse moi, mais il y a trop de choses que je comprends pas. Programmer c'est exprimer un algorithme dans un langage de programmation et là, j'ai l'impression que tu as du mal à simplement l'exprimer en français... Pourquoi utilises-tu un "gisement" quand pour "parler" à AutoCAD l'angle devrait faire l'affaire (avec polar) ? Pourquoi t'obstines-tu à utiliser une formule qui n'est opérante que dans un cas sur quatre ? Gilles Chanteau - gileCAD - GitHub Développements sur mesure pour AutoCAD
mateus Posté(e) le 21 juillet 2013 Auteur Posté(e) le 21 juillet 2013 Désolé si je ne me fait pas bien comprendre, j'essai simplement de faire fonctionner mon programme. J'ai essayé egalement de le faire avec (polar) mais mon deuxième point se retrouve au dessus du premier aussi :( (defun GISEMENT (ListeDecal / pta ptb) (setq pta(list(car ListeDecal)(cadr ListeDecal))) (setq ptb(list(caddr ListeDecal)(cadddr ListeDecal))) (atof (angtos (angle pta ptb) (getvar "AUNITS") 16)) ) ;________________________________________________________________________________________ CALCUL POINT________________________________________________________________________________________________ (defun CALCULPOINT (PX PY module gis / P Q) ;avec P : premierCandelabre ; Q : prochain point (setq P(list PX PY)) (setq Q (polar P gis module)) ) ci-joint le lisp avec polarboucle abscisse block_V3.LSP
mateus Posté(e) le 21 juillet 2013 Auteur Posté(e) le 21 juillet 2013 J'ai réussi Giles désolé de te faire perdre du temps j'étais perdu dans mes formules avec polar, ça marche bien et c'est plus simple ...
(gile) Posté(e) le 21 juillet 2013 Posté(e) le 21 juillet 2013 On ne se comprend vraiment pas... Quand tu utilises une fonction (comme polar), regarde dans l'aide ! La fonction polar s'utilise avec un angle en radians mesuré depuis l'axe X (abscisses) dans le sens trigonométrique (comme celui retourné par la fonction angle).C'est pourquoi je disais : Pourquoi utilises-tu un "gisement" quand pour "parler" à AutoCAD l'angle devrait faire l'affaire (avec polar) ? Si tu tiens absolument à utiliser un gisement (un angle le plus souvent exprimé en grades mesuré depuis l'axe des Y (ordonnées) en sens horaire), ce qui n'a de ses que si tu l'utilises avec sur un poste dont tu es certain que les variables ANGDIR, ANGBASE et AUNITS sont correctement paramétrées, convertir un angle (tel que retourné par la fonction angle) en un gisement exprimé en radians est un simple problème arithmétique. Il suffit de soustraire l'angle à 2.5 * pi radians (soit 1 tour 1/4 ou 450 degrés ou 500 grades). Pour être sûr d'avoir un résultat entre 0 et 2 * pi on peut même prendre le modulo de la division du résultat par 2 * pi. ;; Convertit un angle en gisement (ou inversement) ;; Les deux angle sont exprimés en radians (defun angle<->gisement (a) (rem (- (* 2.5 pi) a) (* 2 pi)) ) Gilles Chanteau - gileCAD - GitHub Développements sur mesure pour AutoCAD
mateus Posté(e) le 21 juillet 2013 Auteur Posté(e) le 21 juillet 2013 Je sais pas pourquoi je suis parti dans le calcul de tangente côté opposé et etc... j'ai simplifié mon code et avec la fonction polar ça marche très bien merci à toi Giles. par contre du coup je ne converti par mon angle avec l'angle courant d'autocad parce que j'utilise la fonction cos pour calculer mon module et comme la fonction cos demande un angle en radian. Cela n'empêche que ça fonctionne bien comme ça. (defun ORIENTATION (listeDecal / pta ptb) (setq pta (list (car ListeDecal) (cadr ListeDecal)) ptb (list (caddr ListeDecal) (cadddr ListeDecal)) ) (angle pta ptb) ;renvoit l'angle entre pta et ptb en radian ) ;________________________________________________________________________________________ MODULE________________________________________________________________________________________________ (defun HYPO (orient entraxeCandelabre) (/ entraxeCandelabre(cos orient)) ) ;________________________________________________________________________________________ CALCUL POINT________________________________________________________________________________________________ (defun CALCULPOINT (PX PY module orient / P Q) ;avec P : premierCandelabre ; Q : prochain point (setq P(list PX PY)) (setq Q (polar P orient module)) ) Merci beaucoup Giles maintenant il faut que je fasse une boucle sur l'abscisse. Je vais essayer ça. Bonne soirée à toi
didier Posté(e) le 22 juillet 2013 Posté(e) le 22 juillet 2013 Coucou c'est classique des gens qui débutent dans la prog, je ne te manque pas de respect Mogoau fil du temps le code se complexifie et il faut savoir se remettre en cause et quelquefois repartir sur des bases plus saines depuis le débutpour Mogopose sur le papier les différentes étapes de ce que tu veux obtenir et comment le ferais-tu "à la main"tu vas voir que des étapes sont inutiles et du coup la lumière viendra sur toi amicalement Éternel débutant... Mon site perso : Programmer dans AutoCAD
Messages recommandés
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 compteSe connecter
Vous avez déjà un compte ? Connectez-vous ici.
Connectez-vous maintenant