Java3D - Picking

TRX

Mitglied
Hi @All,

ich bin immer noch am programmieren meines Projektes (Satelliten Tracking) und hab Probleme mit dem Picking.

Ich will, dass er mir den Namen des Satelliten zurückgibt wenn ich auf den entsprechenden Satelliten klicke. Mir wurde gesagt, dass wäre mit Picking möglich...

Ich hab es jetzt schon soweit hingekriegt, dass er mir die Klasse des angeklickten Objects anzeigt, was mir aber nicht viel bringt da alle Satelliten über die gleiche Klasse erzeugt werden.

Gibts ne Möglichkeit das Ergebnis genauer zu bekommen, z.B die BranchGroup oder den Namen der Textur oder so etwas?

Gruß
TRX

P.S: Geht des überhaupt mit Picking oder muss ich da was anderes benutzen?
 
Zuletzt bearbeitet von einem Moderator:

TRX

Mitglied
Was ich grad auch noch bemerkt habe, ist dass ich weder die Appearance noch die Bounds auslesen kann obwohl ich beide Capability Flags gesetzt habe...

Fehler bei den Bounds:
Exception in thread "AWT-EventQueue-0" javax.media.j3d.CapabilityNotSetException: Node: no capability to read user bounds
at javax.media.j3d.Shape3D.getBounds(Shape3D.java:747)
at satsys.SatelliteSystem$MouseCmd.mouseClicked(SatelliteSystem.java:225)
at java.awt.AWTEventMulticaster.mouseClicked(AWTEventMulticaster.java:252)
at java.awt.Component.processMouseEvent(Component.java:6351)
at java.awt.Component.processEvent(Component.java:6113)
at java.awt.Component.dispatchEventImpl(Component.java:4714)
at java.awt.Component.dispatchEvent(Component.java:4544)
at java.awt.EventQueue.dispatchEvent(EventQueue.java:635)
at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:296)
at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:211)
at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:201)
at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:196)
at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:188)
at java.awt.EventDispatchThread.run(EventDispatchThread.java:122)

Zudem kommt egal was ich anklicke, als Klasse javax.media.j3d.Shape3D ist das normal?
 
Zuletzt bearbeitet:

Marco13

Top Contributor
Wenn er sagt, dass die Capability nicht gesetzt ist, liegt das mit an Sicherheit grenzender Wahrscheinlichkeit daran, dass die Capability nicht gesetzt ist.
Und "fast alles", was man bei Java3D auf dem Bildschirm sieht, sind Shape3D-Objekte. Poste ggf. mal mehr Infos, am besten als KSKB...
 

TRX

Mitglied
das mit dem KSKB wird nicht ganz so einfach klappen, aber ich versuch mal ein bisschen code beispiele zu posten:
So wird des erste Satellit erzeugt ( ist im Moment einfach ne Kugel)
Java:
Appearance satAppear = new Appearance();
    	satAppear.setTexture(new TextureLoader("textures/" + satdatobj.getName() + ".png",satsys).getTexture());
    	
    	Sphere sat = new Sphere(0.006f, Sphere.GENERATE_NORMALS | Sphere.GENERATE_TEXTURE_COORDS ,100,satAppear);
    	sat.setPickable(true);
    	//sat.setCapability(Primitive.ENABLE_GEOMETRY_PICKING);
		//sat.setCapability(Primitive.ENABLE_PICK_REPORTING);
    	//sat.setCapability(Primitive.ALLOW_BOUNDS_READ);
    	sat.setCapability(Shape3D.ALLOW_GEOMETRY_READ);
    	sat.setCapability(Shape3D.ALLOW_GEOMETRY_WRITE);
    	sat.setCapability(Shape3D.ALLOW_BOUNDS_READ);
    	sat.setCapability(Shape3D.ALLOW_APPEARANCE_READ);
    	sat.setCapability(Shape3D.ALLOW_APPEARANCE_WRITE);
		sat.setCapability(Shape3D.ENABLE_PICK_REPORTING);
		sat.setCapability(Geometry.ALLOW_INTERSECT);
		sat.setCapability(Appearance.ALLOW_TEXTURE_READ);



Das ist der MouseListener der ein PickCanvas aus der createScene Funktion übergeben bekommt:
Java:
class MouseCmd extends MouseAdapter {
		
		PickCanvas pickCanvas;
		
		
		public MouseCmd(PickCanvas pickCanvas){
			this.pickCanvas = pickCanvas;
		}
		
		public void mouseClicked(MouseEvent e) 
		{ 
		    pickCanvas.setShapeLocation(e); 
		    PickResult result = pickCanvas.pickClosest(); 
		    if (result == null) { 
		       System.out.println("Nichts ausgewählt"); 
		    } else { 
		       Primitive p = (Primitive)result.getNode(PickResult.PRIMITIVE); 
		       Shape3D s = (Shape3D)result.getNode(PickResult.SHAPE3D); 
		       if (p != null) { 
		          System.out.println(p.getClass().getName()); 
		       } else if (s != null) { 
		             System.out.println(s.getClass().getName());
		             System.out.println(s.getAppearance());
		             //System.out.println(s.getBounds());
		       } else{ 
		          System.out.println("null1"); 
		       } 
		    } 
		} 

	}

Wenn ihr noch weitere Infos braucht einfach sagen...

Ich benötige irgendwie den Namen des Satelliten, also habe ich mir gedacht, dass ich mir die Appearance hol, weil da in der Textur der Name steckt...
Oder geht des auch einfacher?
 

aze

Bekanntes Mitglied
Es gibt eine Methode die heißt setUserData().Mit der kann man jeden Knoten im Scenegraphen ein Java Object injezieren.In deinen Fall würde es ja ausreichen wenn dies ein String ist.Also beim erstellen des Satelliten so etwas machen wie setUserData("satellit 1") machen und dann beim Picking getUserdata() auf das Pickingergebnis anwenden.
 

TRX

Mitglied
@aze:
deine idee klingt schon mal gut, habs jetzt auch mal implementiert, allerdings liefert es immer null zurück egal was ich anklicke.
(hab werte bei der erde und bei den satelliten gesetzt)

Hast du ne ahnung an was das liegen könnte?

Anfügung:
ich hab mir jetzt ma den Scenegraphpath des results ausgeben lassen:
result.getSceneGraphPath();

Folgende Ausgabe bei klicken auf verschiedene Objekte:
javax.media.j3d.Locale@64e265d0 : javax.media.j3d.Shape3D
LocalToVworld Transform:
0.13222459242574738, -0.010019782759938367, -0.9911691384982124, 0.0
0.7781035739310648, 0.6205183907259516, 0.09752822671708536, 0.0
0.6140614671134714, -0.7841278790633062, 0.08984422008194051, 0.0
0.0, 0.0, 0.0, 1.0

javax.media.j3d.Locale@64e265d0 : javax.media.j3d.Shape3D
LocalToVworld Transform:
0.13878298501550007, -0.010019782759938367, -0.9902721277626828, 0.0
0.7774409128170997, 0.6205183907259516, 0.10267693922682905, 0.0
0.6134532664745556, -0.7841278790633062, 0.09390718357707749, 0.0
0.0, 0.0, 0.0, 1.0

javax.media.j3d.Locale@64e265d0 : javax.media.j3d.Shape3D
LocalToVworld Transform:
0.15186746775235, -0.010019782759938367, -0.9883500777517714, 0.0
0.7760149889026161, 0.6205183907259516, 0.11294982854943941, 0.0
0.6121576669755606, -0.7841278790633062, 0.10201205830057376, 0.0
0.0, 0.0, 0.0, 1.0

javax.media.j3d.Locale@64e265d0 : javax.media.j3d.Shape3D
LocalToVworld Transform:
0.1687115420195186, -0.010019782759938367, -0.9856145390277276, 0.0
0.7739744992168653, 0.6205183907259516, 0.12617607274312226, 0.0
0.6103276907951979, -0.7841278790633062, 0.11244367089473051, 0.0
0.0, 0.0, 0.0, 1.0

Ist da alles in Ordnung
 
Zuletzt bearbeitet:

aze

Bekanntes Mitglied
Probiere mal statt :

Java:
Shape3D s = (Shape3D)result.getNode(PickResult.SHAPE3D);

dies hier

Java:
BranchGroup bg = (BranchGroup)result.getNode(PickResult.BRANCHGROUP);

Dann sollte es funktionieren.

ansonsten könnte es helfen jedem Shape3D Objekt einen String zu injezieren der den Satelliten beschreibt.
 

TRX

Mitglied
habs mal so probiert:
System.out.println(result.getNode(PickResult.BRANCH_GROUP).getUserData());
liefert aber eine NullPointerExeption
 

aze

Bekanntes Mitglied
Ich glaub du must beim Konstruktor vom MouseCmd neben dem Canvas auch noch eine Branchgroup angeben auf der das Picking erfolgen soll,in deinen Fall aso wohl die gesamte Scene !
 

TRX

Mitglied
hab ich eigentlich gemacht:
Java:
// Picking
        PickCanvas pickCanvas = new PickCanvas(canvas, objRoot); 
        pickCanvas.setMode(PickCanvas.BOUNDS); 

	canvas.addMouseListener(new MouseCmd(pickCanvas));

ich weiß allerdings nicht ob es hinderlich ist, wenn man wie ich die einzelnen Satelliten in einzelne BranchGroups packt und diese dann an die "Root" BranchGroup hängt.
 

aze

Bekanntes Mitglied
Vlt hilt es statt

Java:
pickCanvas.setMode(PickCanvas.BOUNDS);

das hier zu verwenden:

Java:
pickCanvas.setMode(PickCanvas.GEOMETRY);

Ansonsten weiss ich leider auch nicht mehr weiter
 

TRX

Mitglied
funktioniert leider auch nicht....

So langsam verzweifel ich an dem Scheiß!

Gibts doch nciht das des so schwierig ist..


Hat noch jemand ne Idee worans liegen könnte?

Anfügung:
Hab jetzt einen Teil des Fehlers entdeckt...
Er gab mir immer null aus, weil ich bei dem einzigen Shape3d Objekt das ich in meiner Programmierung keinen Wert gesetzt hatte.
Diese Objekt ist die Umlaufbahn..
Wenn ich also der Umlaufbahn des Satelliten einen Wert zuweise gibt er mir, egal wohin ich klicke ( ob umlaufbahn oder die leere des raums oder die erde) den wert einer namen einer bahn aus ...
Dabei will ich dass er nur einen Wert ausgibt wenn ich auf die Sphere klicke...
Aber anscheinend überlagern die Sphere3d der Umlaufbahnen alles andere..
Kann man das verhindern?
 
Zuletzt bearbeitet:

TRX

Mitglied
Gelöst!

Für alle die so ein Problem auch mal haben sollten:
Mein Problem war dass andere Objekte die eigentlichen Objekte die ich picken wollte überlagert haben und ich sie deshalb nicht picken konnte.
Lösung:
alle unnötigen Objekte vom Picking ausschließen per:
objekt.setPickable(false);


Danke an Alle für die Unterstützung!
 
Ähnliche Java Themen
  Titel Forum Antworten Datum
H Java3D, ViewP Translattform soll sich nach einerformgroup richten. AWT, Swing, JavaFX & SWT 5
S Java3D: Ikosaeder mit unterschiedlich gefärbten Flächen AWT, Swing, JavaFX & SWT 3
K Fullscreen Java3D AWT, Swing, JavaFX & SWT 5
T 3D-Grafik (Java3D) Aus einem Objekt einer Szene (Würfel, Ebene) die wichtigen Randkoordinaten auslesen AWT, Swing, JavaFX & SWT 3
T Erstellung einer ShadowMap mit Java3D AWT, Swing, JavaFX & SWT 6
S Hilfe beim Lernprozess von java3d AWT, Swing, JavaFX & SWT 20
K 3D-Grafik Textur Java3d AWT, Swing, JavaFX & SWT 5
S 3D-Grafik Grafikprogramm mit Java3D AWT, Swing, JavaFX & SWT 14
B 3D-Grafik Punkt in JAVA3D darstellen AWT, Swing, JavaFX & SWT 2
B Java3D Szenegraph Export als VRML, .X3D, .OBJ, .POV, U3D oder PLY AWT, Swing, JavaFX & SWT 4
E Java3D im FSEM AWT, Swing, JavaFX & SWT 5
K Java3D - Startposition ? AWT, Swing, JavaFX & SWT 5
M 3D-Grafik Java3D-Application als executable .jar exportieren (Eclipse) AWT, Swing, JavaFX & SWT 5
I 3D-Grafik Java3D RAM AWT, Swing, JavaFX & SWT 3
S 3D-Grafik Java3D und was noch? AWT, Swing, JavaFX & SWT 3
E 3D-Grafik Java3D AWT, Swing, JavaFX & SWT 5
L 3D-Grafik Java3D - Alle SceneGraphObjects geordnet erhalten AWT, Swing, JavaFX & SWT 2
S Java3D in ein JPanel integrieren mit Netbeans 6.8 AWT, Swing, JavaFX & SWT 4
S Java3D: Alle Objekte in BranchGroup löschen während Laufzeit AWT, Swing, JavaFX & SWT 3
C java3D - sichtbare Kanten eines Shape3D AWT, Swing, JavaFX & SWT 2

Ähnliche Java Themen


Oben