| |
| Gut zu wissen: Hilfreiche Tipps und Tricks aus der Praxis prägnant, und auf den Punkt gebracht für Autodesk Produkte |
Autor
|
Thema: nentsel gc330 (1588 mal gelesen)
|
gmk Mitglied Dipl.-Ing.(FH) Vermessung
Beiträge: 667 Registriert: 23.10.2002 Autocad 2004, WS CadCompass, Normica V2000, WinXP Prof., AMD Athlon 64 X2, 2GB, NVIDIA GeForce 7600GS, HP1055CM
|
erstellt am: 12. Sep. 2007 11:10 <-- editieren / zitieren --> Unities abgeben:
Servus! Ich möchte mit (nentsel) den Wert eines Attributs (insert mit Attributen) auslesen. Ich hatte hierzu schon einmal ein Frage eingestellt: http://ww3.cad.de/foren/ubb/Forum145/HTML/000574.shtml Mit (ENTGET (CAR (NENTSEL))) kann ich prüfen, ob es sich um ein Attribut mit der gewünschten Attributsbezeichnung handelt. Erwische ich jetzt aber beim anklicken ein anderes Element des insert, kann ich über den GC330 den zugehörigen insert-namen ermitteln. Besteht das insert mit den attributen aber selbst wieder aus Blöcken oder Polylinien, oder ist es in einer xref enthalten, komme ich mit der GC330-Methode ja immer nur eine Ebene zurück zum jeweiligen Subelemnt. Kann ich dieses "GC330 Zurückhangeln" irgendwie umgehen oder muss ich den GC330 solange auswerten (evtl.rekursiv), bis ich beim gewünschten insert angekommen bin? Ciao Georg ------------------ http://www.xx-tausend.info Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
fuchsi Mitglied Programmierer c#.net Datawarehouse
Beiträge: 1201 Registriert: 14.10.2003 AutoCad Version 2012 deu/enu <P>Windows 7 64bit
|
erstellt am: 12. Sep. 2007 11:54 <-- editieren / zitieren --> Unities abgeben: Nur für gmk
ich würde einfach statt nentsel entsel verwenden, dann hast du eigentlich immer den übergeordnetsten INSERT und hier schauen, obs es das gewünschte Attribut hat. wenn Du allerdings direkt das Attribut mittels Nentsel wählen möchtest (weil das INSERT mehrere möglich zu bearbeitende Attribute hat) würde ich eher in einer Schleife das nentsel solange wiederholen, biss der Benutzer wirklich ein erlaubtes Attribut gewählt hat. [Diese Nachricht wurde von fuchsi am 12. Sep. 2007 editiert.] Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
gmk Mitglied Dipl.-Ing.(FH) Vermessung
Beiträge: 667 Registriert: 23.10.2002 Autocad 2004, WS CadCompass, Normica V2000, WinXP Prof., AMD Athlon 64 X2, 2GB, NVIDIA GeForce 7600GS, HP1055CM
|
erstellt am: 12. Sep. 2007 12:18 <-- editieren / zitieren --> Unities abgeben:
Servus Fuchsi! Mit entsel kann ich aber leider nur auf Objekte die direkt in der Zeichnung sind zugreifen, bei "insert in insert-Verschachtelungen" oder xrefs geht's halt leider nicht mehr. Natürlich könnte ich eine Schleife einbauen die den Attributsnamen mit abfragt, aber ich möchte eigentlich, dass die Attribute selbst beim anklicken gar nicht am Bildschirm sichtbar sind. Es handelt sich um Aufnahmepunkte aus einer Vermessung und da sind öfters mal viele Punkte dicht aufeinander, so dass man Attribute dem richtigen Block optisch gar nicht zuordnen kann. Ciao Georg ------------------ http://www.xx-tausend.info Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
fuchsi Mitglied Programmierer c#.net Datawarehouse
Beiträge: 1201 Registriert: 14.10.2003 AutoCad Version 2012 deu/enu <P>Windows 7 64bit
|
erstellt am: 12. Sep. 2007 12:55 <-- editieren / zitieren --> Unities abgeben: Nur für gmk
also jetzt bin ich aber komplett verwirrt ! Einerseits möchtest Du Attribute wählen, und andereseits dass diese beim Anclicken gar nicht sichtbar sein müssen! Erkläre doch bitte mal etwas präziser, was Du möchtest, und was die Ausgangslage ist (z.B.: Blockstruktur) ------------------ Ing. Anton Fuchs WWW.FFZELL.AT.TC Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
gmk Mitglied Dipl.-Ing.(FH) Vermessung
Beiträge: 667 Registriert: 23.10.2002 Autocad 2004, WS CadCompass, Normica V2000, WinXP Prof., AMD Athlon 64 X2, 2GB, NVIDIA GeForce 7600GS, HP1055CM
|
erstellt am: 12. Sep. 2007 13:32 <-- editieren / zitieren --> Unities abgeben:
mach ich gerne, ich such' ja eine Lösung :-)) Blockstruktur: Die Geometrie besteht aus x-beliebigen entities (Linie,Polylinie,Bogen,Kreis,Schraffur etc.) In der Blockdefinition hängen mehrere Attribute dran, z.B. Nummer, Höhe usw. Ausgangslage: Das insert befindet sich entweder direkt oder als "insert in insert Verschachtelung" (z.B. in einem unbenannten block) oder als xref in der Zeichnung. Mein Code soll jetzt folgendes machen: Dem Programm wird die gewünschte Atrributsbezeichnung (GC2) des Attributs übergeben dessen Inhalt/Wert (GC1) ich später auslesen möchte. Jetzt Anklicken des Attributs selbst oder (bevorzugt) eines entities des zugehörigen Blocks oder zugehörigen anderen Attributs. Rückgabewert: entweder der Inhalt/Wert des Attributs dessen Attributsbezeichnung ich übergeben habe oder, was mir noch lieber wäre, der entity-name des zugehörigen Blocks. Hoffe es kommt jetzt verständlicher rüber. Ciao Georg ------------------ http://www.xx-tausend.info Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
fuchsi Mitglied Programmierer c#.net Datawarehouse
Beiträge: 1201 Registriert: 14.10.2003 AutoCad Version 2012 deu/enu <P>Windows 7 64bit
|
erstellt am: 12. Sep. 2007 14:13 <-- editieren / zitieren --> Unities abgeben: Nur für gmk
Allerdings gibt dir NENTSEL ja alle übergeordneten Enames zurück (car (entsel)) -> eine Linie in einem Block namesns BLOCK der wiederum in einem Block Namesn TEST liegt, gibt folgendes zurück (<Objektname: 7efd5f28> (795.518 123.181 0.0) ((1.0 0.0 0.0) (0.0 1.0 0.0) (0.0 0.0 1.0) (542.697 6.11219 0.0)) (<Objektname: 7efd5fa0> <Objektname: 7ef9c000> ))
Im fetten Teil, sind alle übergeordneten INSERTS nach ihrer Reihenfolge aufgelistet. Eigentlich brauchst du nur bei diesen enames schauen, ob sie Attribute haben und fertig (setq a1 (nentsel) daten nil) (cond ((= (type a1) 'LIST)
(cond ((= (length a1) 4) ; komplexes Element gewählt (setq a2 (cadddr a1) i 0) ; den fetten teil rausholen (while (and (not daten) (< i (length a2))) (setq ename (nth i a2) i (1+ i)) (while (and (setq ename (entnext ename)) (setq edate (entget ename)) (= (cdr (assoc 0 edate)) "ATTRIB") ) (setq daten (cons (cons (cdr (assoc 2 edate)) (cdr (assoc 1 edate))) daten)) ) ) ) ) ) ) in der Variable Daten hast du dann eine AssocListe aller Attribute des ersten übergeordneten Blocks der Attribute hat. (oder nil wenns kein gibt) [Diese Nachricht wurde von fuchsi am 12. Sep. 2007 editiert.] Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
fuchsi Mitglied Programmierer c#.net Datawarehouse
Beiträge: 1201 Registriert: 14.10.2003 AutoCad Version 2012 deu/enu <P>Windows 7 64bit
|
erstellt am: 12. Sep. 2007 14:21 <-- editieren / zitieren --> Unities abgeben: Nur für gmk
Upps habe vergessen, abzuprüfen, ob nicht eh das Attribut gewählt wurde (setq a1 (nentsel) daten nil) (length a1) (cond ((= (type a1) 'LIST) (cond ((and (setq edate (entget (car a1))) (= (cdr (assoc 0 edate)) "ATTRIB") ) (setq daten (list (cons (cdr (assoc 2 edate)) (cdr (assoc 1 edate))))) ) ((= (length a1) 4) ; komplexes Element gewählt
(setq a2 (cadddr a1) i 0) (while (and (not daten) (< i (length a2))) (setq ename (nth i a2) i (1+ i)) (while (and (setq ename (entnext ename)) (setq edate (entget ename)) (= (cdr (assoc 0 edate)) "ATTRIB") ) (setq daten (cons (cons (cdr (assoc 2 edate)) (cdr (assoc 1 edate))) daten)) ) ) ) ) ) ) ------------------ Ing. Anton Fuchs WWW.FFZELL.AT.TC Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
fuchsi Mitglied Programmierer c#.net Datawarehouse
Beiträge: 1201 Registriert: 14.10.2003 AutoCad Version 2012 deu/enu <P>Windows 7 64bit
|
erstellt am: 12. Sep. 2007 14:51 <-- editieren / zitieren --> Unities abgeben: Nur für gmk
deine fertige Funktion könnte dann in etwa so ausschauen Übergabe ist der Attributname Rückgabe, falls vorhanden, der Elementname des gesuchten Attributes (defun GetAttribut ( pAttName / a1 a2 iAttEname)
(setq a1 (nentsel) iAttEname nil) (length a1) (cond ((= (type a1) 'LIST) (cond ; direkt ein Attribut gewählt -> mal schauen obs das richtige ist ((and (setq edate (entget (car a1))) (= (cdr (assoc 0 edate)) "ATTRIB") (= (cdr (assoc 2 edate)) pAttName) ) (setq iAttEname (car a1)) ) ; ein Attribut in einem nicht verschachtelten Block gewählt aber das falsche ((and (setq edate (entget (car a1))) (= (cdr (assoc 0 edate)) "ATTRIB") (= (length a1) 2) ) (setq ename (ssname (ssadd (car a1) (ssadd)) 0)) (setq ename (nth i a2) i (1+ i)) (while (and (setq ename (entnext ename)) (setq edate (entget ename)) (= (cdr (assoc 0 edate)) "ATTRIB") ) (if (= (cdr (assoc 2 edate)) pAttName) (setq iAttEname ename)) ) ) ; ein komplexes Element gewählt ((= (length a1) 4)
(setq a2 (cadddr a1) i 0) (while (and (not iAttEname) (< i (length a2))) (setq ename (nth i a2) i (1+ i)) (while (and (setq ename (entnext ename)) (setq edate (entget ename)) (= (cdr (assoc 0 edate)) "ATTRIB") ) (if (= (cdr (assoc 2 edate)) pAttName) (setq iAttEname ename)) ) ) ) ) ) ) iAttEname ) ------------------ Ing. Anton Fuchs WWW.FFZELL.AT.TC [Diese Nachricht wurde von fuchsi am 12. Sep. 2007 editiert.] Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
gmk Mitglied Dipl.-Ing.(FH) Vermessung
Beiträge: 667 Registriert: 23.10.2002 Autocad 2004, WS CadCompass, Normica V2000, WinXP Prof., AMD Athlon 64 X2, 2GB, NVIDIA GeForce 7600GS, HP1055CM
|
erstellt am: 12. Sep. 2007 14:56 <-- editieren / zitieren --> Unities abgeben:
|
fuchsi Mitglied Programmierer c#.net Datawarehouse
Beiträge: 1201 Registriert: 14.10.2003 AutoCad Version 2012 deu/enu <P>Windows 7 64bit
|
erstellt am: 12. Sep. 2007 15:01 <-- editieren / zitieren --> Unities abgeben: Nur für gmk
|
fuchsi Mitglied Programmierer c#.net Datawarehouse
Beiträge: 1201 Registriert: 14.10.2003 AutoCad Version 2012 deu/enu <P>Windows 7 64bit
|
erstellt am: 12. Sep. 2007 15:14 <-- editieren / zitieren --> Unities abgeben: Nur für gmk
Mir ist da noch ein kleiner Fehler passiert Die fette Zeile bitte löschen, ist mir beim Kopieren passiert (defun GetAttribut ( pAttName / a1 a2 iAttEname) (setq a1 (nentsel) iAttEname nil) (length a1) (cond ((= (type a1) 'LIST) (cond ; direkt ein Attribut gewählt -> mal schauen obs das richtige ist ((and (setq edate (entget (car a1))) (= (cdr (assoc 0 edate)) "ATTRIB") (= (cdr (assoc 2 edate)) pAttName) ) (setq iAttEname (car a1)) ) ; ein Attribut in einem nicht verschachtelten Block gewählt aber das falsche ((and (setq edate (entget (car a1))) (= (cdr (assoc 0 edate)) "ATTRIB") (= (length a1) 2) ) (setq ename (ssname (ssadd (car a1) (ssadd)) 0)) (setq ename (nth i a2) i (1+ i)) (while (and (setq ename (entnext ename)) (setq edate (entget ename)) (= (cdr (assoc 0 edate)) "ATTRIB") ) (if (= (cdr (assoc 2 edate)) pAttName) (setq iAttEname ename)) ) ) ; ein komplexes Element gewählt ((= (length a1) 4)
(setq a2 (cadddr a1) i 0) (while (and (not iAttEname) (< i (length a2))) (setq ename (nth i a2) i (1+ i)) (while (and (setq ename (entnext ename)) (setq edate (entget ename)) (= (cdr (assoc 0 edate)) "ATTRIB") ) (if (= (cdr (assoc 2 edate)) pAttName) (setq iAttEname ename)) ) ) ) ) ) ) iAttEname ) ------------------ Ing. Anton Fuchs WWW.FFZELL.AT.TC Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
gmk Mitglied Dipl.-Ing.(FH) Vermessung
Beiträge: 667 Registriert: 23.10.2002 Autocad 2004, WS CadCompass, Normica V2000, WinXP Prof., AMD Athlon 64 X2, 2GB, NVIDIA GeForce 7600GS, HP1055CM
|
erstellt am: 12. Sep. 2007 16:25 <-- editieren / zitieren --> Unities abgeben:
Servus Fuchsi! Erstmal vielen Dank für deinen Code. Formatiert blickt man doch gleich besser durch :-) Ich war mit meinen Überlegungen ähnlich weit wie du nur kam ich für den Fall "ein komplexes Element gewählt" nicht recht weiter. Ich glaube hier ist auch bei dir ein Fehler im Code und zwar für den Fall, daß das komplexe Element ein Attribut ist. Dann nämlich steht in der Liste mit den SUB-Blöcken (SETQ a2 (cadddr a1)) als letzter Eintrag nicht der Block drin zu dem das Attrib. gehört sondern der Block eine Ebene höher (Autocad läßt hier anscheinend das seqend unter den Tisch fallen und betrachtet den Block mit den dazugehörigen Attributen als jeweils eigene entities). Evtl. hast du ja dafür noch eine Lösung, ich wußte hier allerdings nicht mehr weiter (... und habe dann versucht über den GC330 an den Block ranzukommen). Ciao Georg ------------------ http://www.xx-tausend.info Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
fuchsi Mitglied Programmierer c#.net Datawarehouse
Beiträge: 1201 Registriert: 14.10.2003 AutoCad Version 2012 deu/enu <P>Windows 7 64bit
|
erstellt am: 13. Sep. 2007 08:34 <-- editieren / zitieren --> Unities abgeben: Nur für gmk
Tatsächlich, genauso wie nentsel beim anclicken eines Attributes in einem NICHT verschachteleten Block eine normale ENTSEL LÖiste zurückgibt, fehlt, beim Ancklicken eines Attributes in einem verschachteleten Block die erste Ebene. Anscheinend aktzepiert Autocad Attribute gleichwertig wie den Block selber, d.h nicht eine Bestandteil des Blockes, sondern auf gleicher Ebene (was es ja auch eigentlich ist). Hier hilft man sich am einfachsten, bis zu SEQEND weiterzusuchen, und beim SEQEND im GC -2 steht der Ename des zugehörigen INSERT ; ein Attribut in einem verschachtelten Block gewählt aber das falsche ((and (setq edate (entget (car a1))) (= (cdr (assoc 0 edate)) "ATTRIB") (= (length a1) 4) ) (setq ename (car a1) ok nil) (while (not ok) (setq ename (entnext ename)) (if (= (cdr (assoc 0 (entget ename))) "SEQEND") (setq ename (cdr (assoc -2 (entget ename))) ok t) ) ) (while (and (setq ename (entnext ename)) (setq edate (entget ename)) (= (cdr (assoc 0 edate)) "ATTRIB") ) (if (= (cdr (assoc 2 edate)) pAttName) (setq iAttEname ename)) ) ) ------------------ [EDIT] Damit wären die Fälle ; ein Attribut in einem nicht verschachtelten Block gewählt aber das falsche ; ein Attribut in einem verschachtelten Block gewählt aber das falsche eigentlich sogar gleich behandelbar ! [Diese Nachricht wurde von fuchsi am 13. Sep. 2007 editiert.] Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
gmk Mitglied Dipl.-Ing.(FH) Vermessung
Beiträge: 667 Registriert: 23.10.2002 Autocad 2004, WS CadCompass, Normica V2000, WinXP Prof., AMD Athlon 64 X2, 2GB, NVIDIA GeForce 7600GS, HP1055CM
|
erstellt am: 13. Sep. 2007 10:12 <-- editieren / zitieren --> Unities abgeben:
Servus Fuchsi! Vielen Dank für deine Bemühungen! Das mit dem GC -2 wußte ich nicht. Super, wieder was dazugelernt! Ich hab hier noch was geändert: ; ein Attribut in einem nicht verschachtelten Block gewählt aber das falsche ((and (setq edate (entget (car a1))) (= (cdr (assoc 0 edate)) "ATTRIB") (= (length a1) 2) ) (setq ename (ssname (ssadd (car a1) (ssadd)) 0)) ;*****eingefügt********* (SETQ ok nil) (while (not ok) (setq ename (entnext ename)) (if (= (cdr (assoc 0 (entget ename))) "SEQEND") (setq ename (cdr (assoc -2 (entget ename))) ok t)) ) ;************** (while (and (setq ename (entnext ename)) (setq edate (entget ename)) (= (cdr (assoc 0 edate)) "ATTRIB") ) (if (= (cdr (assoc 2 edate)) pAttName) (setq iAttEname ename)) ) ) da die Schleife sonst nicht nach dem Block sondern mitten in den Attributen anfängt. Aber wie du schon geschrieben hast kann man die beiden Fälle ; ein Attribut in einem nicht verschachtelten Block gewählt aber das falsche ; ein Attribut in einem verschachtelten Block gewählt aber das falsche ja auch zusammenlegen. Ich hätte noch zwei Fragen zum Programm die nicht die Attribute betreffen (setq a1 (nentsel) iAttEname nil) warum initialisierst du hier iAttEname? (setq ename (ssname (ssadd (car a1) (ssadd)) 0)) warum bildest du einen Auswahlsatz mit einem Element und holst dann wieder das erste Element. Ciao Georg ------------------ http://www.xx-tausend.info Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
fuchsi Mitglied Programmierer c#.net Datawarehouse
Beiträge: 1201 Registriert: 14.10.2003 AutoCad Version 2012 deu/enu <P>Windows 7 64bit
|
erstellt am: 13. Sep. 2007 11:49 <-- editieren / zitieren --> Unities abgeben: Nur für gmk
Zitat: Original erstellt von gmk: (setq a1 (nentsel) iAttEname nil) warum initialisierst du hier iAttEname? [/i]
weil ich oft schlampig bin, und vergesse Variablen im DEFUN Bereich zu deklarieren. Dann könnte in einem 2. Durchlauf die Variable vom 1. Durchlauf schon mit einem Wert belegt seni. Reine Vorsichtsmassnahme Zitat: Original erstellt von gmk: (setq ename (ssname (ssadd (car a1) (ssadd)) 0)) warum bildest du einen Auswahlsatz mit einem Element und holst dann wieder das erste Element. [/i]
Etwas aus Faulheit getrickst. Hier wollte ich mir Eigentlich das Suchen des SEQEND sparen, um über desse GC-2 zum INSERT zu kommen. Hängst du mittels ssadd einen ename eines Attributs zu einem leeren Auswahlsatz dazu, so ist autromatisch der ganze INSERT im Auswahlsatz, und das erste Element wäre wieder unser gesuchtes INSERT. Das ist deshalb so, weil nur wählbare Elemente in einen Auswahlsatz dürfen, und das ist nunmal kein Attribut, sonder der ganze Block. Das geht aber nur, wenn der Block nicht verschatelt ist, sondern so in der zeichnung ist. Deshhalb habe ich dann beim verschachtelten Block, eh das SEQEND suchen eingebaut. aber wie gesagt, einfach die beiden Fälle zusammenfügen. ------------------ Ing. Anton Fuchs WWW.FFZELL.AT.TC [Diese Nachricht wurde von fuchsi am 13. Sep. 2007 editiert.] Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |