Event handling mit JComponents

MariusMeier

Mitglied
Hallo zusammen

Hier habe ich meinen Code:
Code:
public class RComp extends JComponent {

	Image resistor = null;
    double value = 0;
    double percent = 0;
    private JPanel panel;
    public JTextField changeValue;

    public RComp(String vRcomp,double value,double percent,int x,int y,JPanel panel) {
    	this.panel = panel;
        this.value = value;
        this.percent = percent;
        
        if(vRcomp.equals("V")) {
        	resistor = getToolkit().getImage("D:/Work_Java/Projekt2/src/ch/fhnw/NikRCKas1/GUI/VResistor.jpg");
        }
        else {
        	resistor = getToolkit().getImage("D:/Work_Java/Projekt2/src/ch/fhnw/NikRCKas1/GUI/HResistor.jpg");
        }
        
        this.setBounds(x,y,80,80); // 123,123 min. auf Bildgröße ändern 
        
        this.addMouseListener(new RCompMouseListener("res1",this.panel));
    }

    public void paintComponent(Graphics g) {
         super.paintComponent(g);
         g.drawImage(resistor, 0, 0, this);
    }
    
    ////////////////////////////////////////////////////
    class RCompMouseListener implements MouseListener {
		
		private String actualEvent;
		
		public RCompMouseListener(String actualEvent,JPanel panel) {
			this.actualEvent = actualEvent;
		}
		
		public void mouseReleased(MouseEvent e) {
			if(actualEvent.equals("res1")) {
				JTextField changeValue = new JTextField();
				changeValue.setBounds(200, 200, 100, 10);
				panel.add(changeValue);
				System.out.println("Res1");
			}
		}
		
		public void mousePressed(MouseEvent e) {
			
				
		}
		
		public void mouseClicked(MouseEvent e) {
			
		}
		
		public void mouseEntered(MouseEvent e) {
			
		}
		
		public void mouseExited(MouseEvent e) {
			
		}
	}
    
}

Wenn ein Objekt von RComp erstellt wird übergebe ich dem Konstruktor verschiedene Werte. Auch gebe ich das aktuelle Panel an auf dem gezeichnet wird. Im Konstruktor sieht man dass dann alle einzelnen Bilder einen ActionListener erhalten.
Wenn ich jetzte auf das Bild klicke sollte doch ein JTextField() an der Position 200,200 erscheinen.... tut es aber nicht.... was mache ich da falsch? Vorschläge?

MFG Marius Meier
 
Hallo,

warum übergibst du hier panel

Code:
public RCompMouseListener(String actualEvent,JPanel panel) { ... }
wenn du hier aus der inneren Klasse das panel der umgebenden Klasse nutzt

Code:
panel.add(changeValue);
wozu dient das

Code:
public void mouseReleased(MouseEvent e) {
			if(actualEvent.equals("res1")) { ...

so wie du es hier verwendest ist der Ausdruck immer true.

und ohne ein validate() des Panels wird deine neue Komponente
nicht auf die Oberfläche gebracht !

Gruß JAdix

PS : Lösche mal meinen "123,123"-Kommentar aus dem Code :)
 
Hallo

Ehm ja das einte Panel im Konstuktor ist zu viel. Das Panel objekt brauche ich einfach dass die umgebung weiss wo sie die JTextField() Componente hinzeichnet.

Ja ich weiss dass es immer true gibt.... schlussendlich sollte die ganze Applikation so sein dass ich mehrere RComp erstelle wobei sich das EventHandlig dann voneinander unterscheiden sollte. Nicht dass alle das gleiche tun.... aber wie soll man das realisieren? Hast du nen Vorschlag?

WIe meinst du dass ich das panel mit validate() überprüfen soll damit überhaupt die Komponente ins JPanel gelangt? Beispiel?

MFG Marius Meier
 
Hallo,

in der Java-API heißt es so schön :

Validates this container and all of its subcomponents.

The validate method is used to cause a container to lay out its subcomponents again.
It should be invoked when this container's subcomponents are modified
(added to or removed from the container, or layout-related information changed)
after the container has been displayed.

Soll da heißen, wenn du was an den Komponenten drehst, solange dieser Angezeigt wird,
validiere den Container ! Und da JPanel ein solcher ist ... !

Code:
panel.validate();

Dieses stößt dann alles weitere an und deine ChangeValue-Komponente sollte auf dem JPanel erscheinen.

BERICHTIGUNG : validate() bezieht sich natürlich auf das LayoutManagement, also dass neu ausrichten der Komponenten
und führt nicht automatisch zum neu Zeichnen der Komponente !


Zum Eventhandling : Bekommt jede RComp später den ein und den selben MouseListener verpasst ?
Dann musst du die Quelle mit e.getSource() ermitteln !

Bekommt jede RComp seinen eigenen Listener ist immer klar von welcher Komponente das Event stammt,
nämlich von dem, an dem der Listener angemeldet ist.
In diese Richtung scheint mir dein Code momentan ausgerichtet zu sein !

Gruß JAdix
 
Zuletzt bearbeitet:
Hallo zusammen

Also dass min validate() hat nicht funktioniert... es passiert einfach nichts! Aber wenn ich anstatt validate() panel.repaint() verwende wird das JTextField gezeichnet. Ist irgendwie komisch nicht?

Also wegen dem MouseListener... Jede Istanz von der Klasse RComp erhält ja seinen eigenen MouseListener. Ich will später damit erreichen, dass ich Beispielsweise auf den Widerstand R1 klicken kann und seinen Widerstandswert ändern kann. Dabei darf aber nur der Widerstandswert ändern den ich angeklickt habe. Sollte ich das anderst lösen?

MFG Marius Meier
 
Ich habe noch ein anderes Problem: Wenn ich das JTextField direkt auf das Bitmap zeichne, dann kann ich nicht ins JTextField schreiben.... hat das was mit dem Focus zu tun oder mit dem Layer.... ? Wenn ich auf das JTextField klicke zeichnet mir die Anwendung das JTextField neu obwohl das ja dieses Textfeld oberhalb meiner Bitmap liegt.... wieso ist das so? Was kann man machen?

MFG Marius Meier
 
Hallo,

deine RComp-Komponenten dürfen nicht mehr auf die eintreffenden Events reagieren, sobald
du ein Textfeld geöffnet hast, solange bis das Textfeld wieder von der Oberfläche genommen wird.

Du solltest also ein Flag setzen um dieses zu steuern !

Gruß JAdix
 
Du solltest das Problem in einen eigenen Thread schreiben, so findet ja keiner deine Frage.

Vorschlag: Solange das Textfeld den Fokus hat, soll nicht neugezeichnet werden, dann könnte es klappen.
 
Hehe, ja das mit nem neuen Thread wäre besser gewesen ;)

Mh ich habe das nicht mit einem Flag gelöst sondern ganz einfach den focus gesetzt:

Code:
public void mouseReleased(MouseEvent e) {
			if(actualEvent.equals("res1")) {
				changeValue = new JTextField();
				changeValue.setBounds(10, 10, 100, 20);
				panel.add(changeValue);
				
				panel.repaint();
				changeValue.requestFocus();
				System.out.println("Res1");
			}
		}

Einfacher gehts glaub ich nicht.

MFG Marius Meier
 
Zurück