未触发 JPopupMenu 操作
JPopupMenu action not triggered
这是我所拥有的(简化版)。 (我是这样找到代码的):
class CustomPopup extends JPopupMenu {
public CustomPopup() {}
@Override
public void setVisible(boolean visible)
{
// Case 1:
//if (visible) super.setVisible(visible);
// Case 2:
super.setVisible(visible);
}
}
class CustomPanel extends JPanel {
// .../...
public CustomPanel() {
setSize(200, 200);
addMouseListener( new MouseAdapter(){
@Override
public void mousePressed( MouseEvent e ){
onMousePressed( e );
}
});
}
public void onMousePressed( MouseEvent e )
{
JPopupMenu pop = new JPopupMenu();
pop.add( new AbstractAction( "foo" )
{
@Override
public void actionPerformed( ActionEvent e )
{
// do stuff
System.out.println("this is executed");
}
});
pop.show( e.getComponent(), e.getX(), e.getY() );
}
}
public class TestPopup extends JFrame {
CustomPanel _pp;
CustomPopup _cpop;
public TestPopup () {
setDefaultCloseOperation(EXIT_ON_CLOSE);
setSize(333, 333);
_cpop = new CustomPopup();
_pp = new CustomPanel();
_cpop.add(_pp);
addMouseListener( new MouseAdapter(){
@Override
public void mousePressed( MouseEvent e ){
_cpop.show(e.getComponent(), 0, 0);
}
});
}
public static void main(String[] args) {
java.awt.EventQueue.invokeLater(new Runnable() {
public void run() {
(new TestPopup()).setVisible(true);
}
});
}
}
弹出菜单显示自定义面板。与它交互时,它会显示带有选项列表的经典弹出菜单。
我的问题是 CustomPopup
没有按预期自行关闭。罪魁祸首显然是 setVisible
的覆盖,但是如果我删除覆盖方法(或注释掉条件),我会遇到另一个问题:永远不会调用添加到 pop
上的 actionPerformed
方法。
第一种情况:
CustomPopup
打开
- 我点击里面的东西
JPopupMenu
打开 并且 CustomPopup
保持可见
- 我点击了新菜单的一个项目
- 触发
Action
第二种情况:
CustomPopup
打开
- 我点击里面的东西
JPopupMenu
打开,CustomPopup
隐藏
- 我点击了新菜单的一个项目
Action
未触发
我的结论是 CustomPopup
必须可见才能触发操作,即使我真的不明白为什么。所以我的问题是:如何以不破坏默认 JPopupMenu
行为的方式保持 CustomPopup
打开,或者如何在隐藏 CustomPopup
的情况下正确触发操作?
看起来弹出窗口的父级必须可见才能触发操作(对我来说听起来很合理)。所以除了最后一步之外,你已经做了所有让它工作的事情:自己关闭自定义弹出窗口。这是代码:
class CustomPopup extends JPopupMenu {
public CustomPopup() {}
@Override
public void setVisible(boolean visible)
{
// Case 1:
if (visible) super.setVisible(visible);
// Case 2:
// super.setVisible(visible);
}
public void makeInvisible() {
super.setVisible(false);
}
}
class CustomPanel extends JPanel {
// .../...
public CustomPanel() {
setSize(200, 200);
addMouseListener( new MouseAdapter(){
@Override
public void mousePressed( MouseEvent e ){
onMousePressed( e );
}
});
}
public void onMousePressed( MouseEvent e )
{
JPopupMenu pop = new JPopupMenu();
pop.add( new AbstractAction( "foo" )
{
@Override
public void actionPerformed( ActionEvent e )
{
// do stuff
System.out.println("this is executed");
Component comp = (Component) e.getSource();
if (comp != null && comp.getParent() instanceof JPopupMenu) {
JPopupMenu popupMenu = (JPopupMenu) comp.getParent();
if (popupMenu.getInvoker() instanceof CustomPanel) {
CustomPopup cpop = (CustomPopup) popupMenu.getInvoker().getParent();
cpop.makeInvisible();
}
}
}
});
pop.show( e.getComponent(), e.getX(), e.getY() );
}
}
public class TestPopup extends JFrame {
CustomPanel _pp;
CustomPopup _cpop;
public TestPopup () {
setDefaultCloseOperation(EXIT_ON_CLOSE);
setSize(333, 333);
_cpop = new CustomPopup();
_pp = new CustomPanel();
_cpop.add(_pp);
addMouseListener( new MouseAdapter(){
@Override
public void mousePressed( MouseEvent e ){
_cpop.show(e.getComponent(), e.getX(), e.getY());
}
});
}
public static void main(String[] args) {
java.awt.EventQueue.invokeLater(new Runnable() {
public void run() {
(new TestPopup()).setVisible(true);
}
});
}
}
这是我所拥有的(简化版)。 (我是这样找到代码的):
class CustomPopup extends JPopupMenu {
public CustomPopup() {}
@Override
public void setVisible(boolean visible)
{
// Case 1:
//if (visible) super.setVisible(visible);
// Case 2:
super.setVisible(visible);
}
}
class CustomPanel extends JPanel {
// .../...
public CustomPanel() {
setSize(200, 200);
addMouseListener( new MouseAdapter(){
@Override
public void mousePressed( MouseEvent e ){
onMousePressed( e );
}
});
}
public void onMousePressed( MouseEvent e )
{
JPopupMenu pop = new JPopupMenu();
pop.add( new AbstractAction( "foo" )
{
@Override
public void actionPerformed( ActionEvent e )
{
// do stuff
System.out.println("this is executed");
}
});
pop.show( e.getComponent(), e.getX(), e.getY() );
}
}
public class TestPopup extends JFrame {
CustomPanel _pp;
CustomPopup _cpop;
public TestPopup () {
setDefaultCloseOperation(EXIT_ON_CLOSE);
setSize(333, 333);
_cpop = new CustomPopup();
_pp = new CustomPanel();
_cpop.add(_pp);
addMouseListener( new MouseAdapter(){
@Override
public void mousePressed( MouseEvent e ){
_cpop.show(e.getComponent(), 0, 0);
}
});
}
public static void main(String[] args) {
java.awt.EventQueue.invokeLater(new Runnable() {
public void run() {
(new TestPopup()).setVisible(true);
}
});
}
}
弹出菜单显示自定义面板。与它交互时,它会显示带有选项列表的经典弹出菜单。
我的问题是 CustomPopup
没有按预期自行关闭。罪魁祸首显然是 setVisible
的覆盖,但是如果我删除覆盖方法(或注释掉条件),我会遇到另一个问题:永远不会调用添加到 pop
上的 actionPerformed
方法。
第一种情况:
CustomPopup
打开- 我点击里面的东西
JPopupMenu
打开 并且CustomPopup
保持可见- 我点击了新菜单的一个项目
- 触发
Action
第二种情况:
CustomPopup
打开- 我点击里面的东西
JPopupMenu
打开,CustomPopup
隐藏- 我点击了新菜单的一个项目
Action
未触发
我的结论是 CustomPopup
必须可见才能触发操作,即使我真的不明白为什么。所以我的问题是:如何以不破坏默认 JPopupMenu
行为的方式保持 CustomPopup
打开,或者如何在隐藏 CustomPopup
的情况下正确触发操作?
看起来弹出窗口的父级必须可见才能触发操作(对我来说听起来很合理)。所以除了最后一步之外,你已经做了所有让它工作的事情:自己关闭自定义弹出窗口。这是代码:
class CustomPopup extends JPopupMenu {
public CustomPopup() {}
@Override
public void setVisible(boolean visible)
{
// Case 1:
if (visible) super.setVisible(visible);
// Case 2:
// super.setVisible(visible);
}
public void makeInvisible() {
super.setVisible(false);
}
}
class CustomPanel extends JPanel {
// .../...
public CustomPanel() {
setSize(200, 200);
addMouseListener( new MouseAdapter(){
@Override
public void mousePressed( MouseEvent e ){
onMousePressed( e );
}
});
}
public void onMousePressed( MouseEvent e )
{
JPopupMenu pop = new JPopupMenu();
pop.add( new AbstractAction( "foo" )
{
@Override
public void actionPerformed( ActionEvent e )
{
// do stuff
System.out.println("this is executed");
Component comp = (Component) e.getSource();
if (comp != null && comp.getParent() instanceof JPopupMenu) {
JPopupMenu popupMenu = (JPopupMenu) comp.getParent();
if (popupMenu.getInvoker() instanceof CustomPanel) {
CustomPopup cpop = (CustomPopup) popupMenu.getInvoker().getParent();
cpop.makeInvisible();
}
}
}
});
pop.show( e.getComponent(), e.getX(), e.getY() );
}
}
public class TestPopup extends JFrame {
CustomPanel _pp;
CustomPopup _cpop;
public TestPopup () {
setDefaultCloseOperation(EXIT_ON_CLOSE);
setSize(333, 333);
_cpop = new CustomPopup();
_pp = new CustomPanel();
_cpop.add(_pp);
addMouseListener( new MouseAdapter(){
@Override
public void mousePressed( MouseEvent e ){
_cpop.show(e.getComponent(), e.getX(), e.getY());
}
});
}
public static void main(String[] args) {
java.awt.EventQueue.invokeLater(new Runnable() {
public void run() {
(new TestPopup()).setVisible(true);
}
});
}
}