# JWindow schließen bei einem Klick außerhalb der Anwendung?



## Hilefoks (25. Mai 2007)

Moin,

wie kann ich ein JWindow dazu bringen sich zu schließen wenn der Anwender z.B. auf den Desktop klickt? Ich habe es mit nem FocusListener probiert, hat aber leider nicht funktioniert? 

MfG,
Hilefoks


----------



## JPKI (25. Mai 2007)

Mit der Methode windowDeactivated(WindowEvent) von WindowListener?

```
jdialog.addWindowListener(new WindowAdapter() {
 public void windowDeactivated(WindowEvent e) {
  jdialog.dispose();
 }
});
```


----------



## Hilefoks (25. Mai 2007)

JPKI hat gesagt.:
			
		

> Mit der Methode windowDeactivated(WindowEvent) von WindowListener?


Nee - WindowListener hatte ich auch probiert, sorry.


----------



## JPKI (25. Mai 2007)

Müsste aber klappen...?
Welches Betriebssystem benutzt du?
Welche JRE?


----------



## André Uhres (25. Mai 2007)

Was hast du im JWindow drin? Wenn keine fokusierbare Komponente drin ist (z.B. ein JButton), 
dann kann es imho nicht funktionieren mit dem FocusListener.
*EDIT:*oder mit einem JLabel oder JPanel drin müsste es auch funktionieren, wenn du
ihn auf setFocusable(true) setzt. 
*EDIT 2:*Oder vielleicht den JWindow selbst auf setFocusable(true) setzen.


----------



## JPKI (25. Mai 2007)

Poste bitte mal den Versuch mit dem Window-Listener!


----------



## Hilefoks (25. Mai 2007)

JPKI hat gesagt.:
			
		

> Müsste aber klappen...?
> Welches Betriebssystem benutzt du?
> Welche JRE?


Gentoo, KDE 3.5.7 und Sun JDK 1.6.0.



			
				André Uhres hat gesagt.:
			
		

> Was hast du im JWindow drin? Wenn keine fokusierbare Komponente drin ist (z.B. ein JButton),
> dann kann es imho nicht funktionieren mit dem FocusListener.
> *EDIT:*oder mit einem JLabel oder JPanel drin müsste es auch funktionieren, wenn du
> ihn auf setFocusable(true) setzt.
> *EDIT 2:*Oder vielleicht den JWindow selbst auf setFocusable(true) setzen.


Da steckt neben anderen sowohl ein JPanel als auch ein JLabel drin... allerdings habe ich das mit dem FocusListener dann auch schnell wieder verworfen weil es eh nicht das ist was ich möchte. Das Fenster soll nicht bei verlusst des Focus, sondern erst beim Klick mit der Maus verschwinden - egal ob dieser Klick im Fenster (das ist natürlich einfach) oder ausserhalb passiert.



			
				JPKI hat gesagt.:
			
		

> Poste bitte mal den Versuch mit dem Window-Listener!


Wenig späktakulär - so etwa:

```
public class Main extends JWindow implements WindowListener {
	
	public static void main(String[] args) throws IOException {
		new Main();
	}

	public Main() {
		setSize(200, 200);
		addWindowListener(this);
		JButton b=new JButton("exit");
		b.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				dispose();
				System.exit(0);
			}
		});
		add(b);
		setEnabled(true);
		setVisible(true);
	}

	public void windowDeactivated(WindowEvent e) {
		System.out.println("JA!");
	}

	public void windowActivated(WindowEvent e) {}
	public void windowClosed(WindowEvent e) {}
	public void windowClosing(WindowEvent e) {}
	public void windowDeiconified(WindowEvent e) {}
	public void windowIconified(WindowEvent e) {}
	public void windowOpened(WindowEvent e) {}
}
```

MfG,
Hilefoks


----------



## merlin2 (25. Mai 2007)

```
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import java.io.*;

public class Main2 extends JFrame implements WindowListener {

   public static void main(String[] args) throws IOException {
      new Main2();
   }

   public Main2() {
      setSize(200, 200);
      addWindowListener(this);
      JButton b=new JButton("exit");
      b.addActionListener(new ActionListener() {
         public void actionPerformed(ActionEvent e) {
            dispose();
            System.exit(0);
         }
      });
      add(b);
      setEnabled(true);
      setUndecorated(true);
      setVisible(true);
   }

   public void windowDeactivated(WindowEvent e) {
      System.out.println("JA!");
   }

   public void windowActivated(WindowEvent e) {}
   public void windowClosed(WindowEvent e) {}
   public void windowClosing(WindowEvent e) {}
   public void windowDeiconified(WindowEvent e) {}
   public void windowIconified(WindowEvent e) {}
   public void windowOpened(WindowEvent e) {}
}
```
So funktioniert es. Ist jetzt zwar ein JFrame, sieht aber gleich aus.


----------



## Hilefoks (25. Mai 2007)

merlin2 hat gesagt.:
			
		

> So funktioniert es. Ist jetzt zwar ein JFrame, sieht aber gleich aus.


Danke, aber nicht ganz - jetzt würde sich das Fenster immer schließen wenn es den Focus verliert.


----------



## merlin2 (25. Mai 2007)

Das hat es bei mir nicht getan!
Und überhaupt - warum sollte es das tun?


----------



## André Uhres (25. Mai 2007)

merlin2 hat gesagt.:
			
		

> ..warum sollte es das tun?





			
				Hilefoks hat gesagt.:
			
		

> ..Das Fenster soll nicht bei verlusst des Focus, sondern erst *beim Klick mit der Maus verschwinden*
> - egal ob dieser Klick im Fenster (das ist natürlich einfach) oder ausserhalb passiert..



@merlin2: Wenn das Fenster "*deactivated*" wurde, dann weiss man nicht, ob das durch *Mausklick *geschah oder nicht.


----------



## JPKI (26. Mai 2007)

Hilefoks hat gesagt.:
			
		

> Das Fenster soll nicht bei verlusst des Focus, sondern erst beim Klick mit der Maus verschwinden
> - egal ob dieser Klick im Fenster (das ist natürlich einfach) oder ausserhalb passiert


Wenn der Focus egal ist, ist mouseClicked() von MouseListener angebracht. Das Verlassen des Fensters kannst du mit mouseExited() überprüfen.
Edit: Schwachsinn, Hilefoks will ja, dass das Fenster auch bei einem Klick geschlossen wird, wenn es deaktiviert ist und keinen Fokus hat, oder ???:L ? Dann wär das was ich da oben geschrieben hab natürlich Schwachsinn :?:  ???:L  :bahnhof:


----------



## Hilefoks (26. Mai 2007)

JPKI hat gesagt.:
			
		

> Edit: Schwachsinn, ...


 Sorry - Ja ;-)



			
				JPKI hat gesagt.:
			
		

> ...Hilefoks will ja, dass das Fenster auch bei einem Klick geschlossen wird, wenn es deaktiviert ist und keinen Fokus hat, oder ???:L ? Dann wär das was ich da oben geschrieben hab natürlich Schwachsinn :?:  ???:L  :bahnhof:


Richtig - ich möchte das sich das Fenster auch dann schließt wenn es deaktiviert ist und keinen Fokus hat. Ich habe aber noch Hoffnung das jemand eine gute Idee hat das hinzubekommen - irgendwie steckt diese Funktionalität ja in den Tiefen von Java, schließlich kann ein Popup eines Systray das ja auch....?!

MfG,
Hilefoks


----------



## André Uhres (26. Mai 2007)

>Das Fenster soll nicht bei Verlust des Focus .. verschwinden.

>Ich möchte daß sich das Fenster auch dann schließt, wenn es .. keinen Fokus hat.

@Hilefoks: Du hast deine Erfordernisse zwar schon wiederholt geändert,
aber falls du dich jetzt doch für das letztere der beiden oben genannten entscheiden willst: 
das geht mit FocusListener.


----------



## Hilefoks (26. Mai 2007)

André Uhres hat gesagt.:
			
		

> @Hilefoks: Du hast deine Erfordernisse zwar schon wiederholt geändert...


Hab ich...? Möglich, aber:


> Richtig - ich möchte das sich das Fenster *auch dann* schließt wenn es deaktiviert ist und keinen Fokus hat.


"auch dann" bezog sich auf den klick ohne das das Fenster den Focus besitzt... 

Aber nochmal: Ich möchte das sich das Fenster bei einem klick des Anwenders schließt, auch dann wenn es nicht den Focus besitzt. Das Fenster öffnet sich und egal wo der Anwender klickt, das Fenster soll sich schließen. Nicht aber schon dann wenn es nur den Focus verliert. Also so wie es z.B. ein PopupMenu eines TrayIcons macht.

MfG,
Hilefoks


----------



## Hilefoks (26. Mai 2007)

Beispiel-Code:

```
public class Main {
	TrayIcon trayIcon;
	PopupMenu rpopup;
	JWindow lpopup;

	public static void main(String[] args) throws AWTException {
		new Main();
	}

	Main() throws AWTException {
		SystemTray tray=SystemTray.getSystemTray();
		trayIcon=new TrayIcon(new ImageIcon("").getImage(), "TestApp");
		trayIcon.setImageAutoSize(true);

		rpopup=new PopupMenu();
		rpopup.add(new MenuItem("Foo"));
		rpopup.add(new MenuItem("Bar"));

		lpopup=new JWindow();
		lpopup.add(new JButton("Bla"));
		lpopup.setSize(200, 50);
		
		trayIcon.setPopupMenu(rpopup);

		trayIcon.addMouseListener(new TrayIconMouseListener());
		tray.add(trayIcon);
	}

	class TrayIconMouseListener extends MouseAdapter {
		boolean showLPopup=true;

		public void mouseClicked(MouseEvent e) {
			if(e.getButton()==1) {
				if(showLPopup) {
					showLPopup=false;
					lpopup.setLocation((int) (e.getPoint().getX()-lpopup.getSize().getWidth()), (int) (e.getPoint().getY()-lpopup.getSize().getHeight()));
					lpopup.setVisible(true);
				}
				else { showLPopup=true; lpopup.setVisible(false); }
			}
			else if(e.getButton()==2)
				System.exit(0);
		}
	}
}
```

Das PopuMenu verhält sich hier so wie ich möchte... öffnet man es und klickt anschließend auf den Desktop, dann schließt es sich wieder. Das gleiche verhalten möchte ich auch für das JWindow implementieren, weiß aber nicht wie.

MfG,
Hilefoks


----------



## JPKI (27. Mai 2007)

Wenn du noch andere Sprachen außer Java kannst, könntest du da eventuell was über JNI drehen...


----------



## Hilefoks (27. Mai 2007)

JPKI hat gesagt.:
			
		

> Wenn du noch andere Sprachen außer Java kannst, könntest du da eventuell was über JNI drehen...


Ja schon... aber irgendwie gefällt mir dieser Ansatz nicht... es ist ein wenig wie "mit Kanonen auf Spatzen schießen". Aber ich mach mir darüber noch ein paar Gedanken. Das Problem an dieser Lösung ist eben das ganze dann auch plattformunabhängig zu realisieren bzw. das dann auch testen zu können - ich besitze weder MacOS noch Windows. 

Kann ich ein PopupMenu (kein JPopupMenu) unsichtbar machen?


----------



## thE_29 (27. Mai 2007)

```
public class Main extends JWindow implements WindowListener{

   public static void main(String[] args) throws IOException {
      new Main();
   }

   public Main() {
      setSize(200, 200);
      addWindowListener(this);
      JButton b=new JButton("exit");
      b.addActionListener(new ActionListener() {
         public void actionPerformed(ActionEvent e) {
            dispose();
            System.exit(0);
         }
      });
      JComboBox bla = new JComboBox();
      bla.addItem("BLA 1");
      bla.addItem("BLA 2");
      add(bla);
//      add(b);

      setEnabled(true);
      setVisible(true);
   }

   public void windowDeactivated(WindowEvent e) {
      System.out.println("JA!");
   }

   public void windowActivated(WindowEvent e) {}
   public void windowClosed(WindowEvent e) {}
   public void windowClosing(WindowEvent e) {}
   public void windowDeiconified(WindowEvent e) {}
   public void windowIconified(WindowEvent e) {}
   public void windowOpened(WindowEvent e) {}
}
```

Hier geht das Popupmenu bei mir aber nicht zu!

Anscheinend ist das PopupMenu sein sehr merkürdiges Window oder eben gar keines


----------



## Hilefoks (28. Mai 2007)

thE_29 hat gesagt.:
			
		

> Hier geht das Popupmenu bei mir aber nicht zu!


Aber ich möchte das es zu geht. ;-)


----------

