Avevo bisogno di un JButton con un menu di stile a discesa allegato. Così ho preso un JPopupMenu e l'ho collegato al JButton nel modo in cui puoi vedere nel codice qui sotto. Che ha bisogno di fare è questo:Mostrare/nascondere un JPopupMenu da un JButton; FocusListener non funziona?
- mostrano la pop-up quando si fa clic
- nascondere se cliccato una seconda volta
- nascondere se un elemento è selezionato nel popup
- nascondere, se l'utente clicca da qualche altra parte sullo schermo
Queste 4 cose funzionano, ma a causa della bandiera booleana che sto usando, se l'utente fa clic da qualche altra parte o seleziona un elemento, devo cliccare due volte sul pulsante prima che mostri di nuovo. Ecco perché ho provato ad aggiungere un FocusListener (che non risponde assolutamente) per correggerlo e impostare il flag false in questi casi.
EDIT: Ultimo tentativo in un posto risposta ...
Ecco gli ascoltatori: (. E 'in una classe che estende JButton, quindi la seconda ascoltatore è in JButton)
// Show popup on left click.
menu.addFocusListener(new FocusListener() {
@Override
public void focusLost(FocusEvent e) {
System.out.println("LOST FOCUS");
isShowingPopup = false;
}
@Override
public void focusGained(FocusEvent e) {
System.out.println("GAINED FOCUS");
}
});
addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
System.out.println("isShowingPopup: " + isShowingPopup);
if (isShowingPopup) {
isShowingPopup = false;
} else {
Component c = (Component) e.getSource();
menu.show(c, -1, c.getHeight());
isShowingPopup = true;
}
}
});
Ho combattuto con questo per troppo tempo adesso. Se qualcuno mi può dare un indizio su cosa c'è di sbagliato in questo, sarebbe fantastico!
Grazie!
Codice:
public class Button extends JButton {
// Icon.
private static final ImageIcon ARROW_SOUTH = new ImageIcon("ArrowSouth.png");
// Unit popup menu.
private final JPopupMenu menu;
// Is the popup showing or not?
private boolean isShowingPopup = false;
public Button(int height) {
super(ARROW_SOUTH);
menu = new JPopupMenu(); // menu is populated somewhere else
// FocusListener on the JPopupMenu
menu.addFocusListener(new FocusListener() {
@Override
public void focusLost(FocusEvent e) {
System.out.println("LOST FOCUS");
isShowingPopup = false;
}
@Override
public void focusGained(FocusEvent e) {
System.out.println("GAINED FOCUS");
}
});
// ComponentListener on the JPopupMenu
menu.addComponentListener(new ComponentListener() {
@Override
public void componentShown(ComponentEvent e) {
System.out.println("SHOWN");
}
@Override
public void componentResized(ComponentEvent e) {
System.out.println("RESIZED");
}
@Override
public void componentMoved(ComponentEvent e) {
System.out.println("MOVED");
}
@Override
public void componentHidden(ComponentEvent e) {
System.out.println("HIDDEN");
}
});
// ActionListener on the JButton
addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
System.out.println("isShowingPopup: " + isShowingPopup);
if (isShowingPopup) {
menu.requestFocus();
isShowingPopup = false;
} else {
Component c = (Component) e.getSource();
menu.show(c, -1, c.getHeight());
isShowingPopup = true;
}
}
});
// Skip when navigating with TAB.
setFocusable(true); // Was false first and should be false in the end.
menu.setFocusable(true);
}
}
Quindi, il problema principale che ho è che focusGained() e focusLost() non vengono mai attivati, anche se continuo a far apparire e scomparire il popup. – Joanis