在Java中调用“父”组件的方法

时间:2009-01-09 18:19:37

标签: java class methods

我认为最好在示例程序代码中显示以下情况。我有一个扩展JPanel的Java类。在这个类中有两个对象,还有两个JPanels。其中一个JPanel个对象是JTable个对象。我为这个检测到双击的JTable添加了一个监听器。当它检测到双击时,我想在顶级类中触发一个方法。如何在Java中引用此方法?

public class TopPanel extends JPanel {

  JPanel OnePanel;
  JPanel TwoPanel;

  public void MethodToFire;

}

public class OnePanel extends JPanel {

  JTable TheTable;

}

public class TheTable extends JTable {

  public TheTable {
    this.addMouseListener(new MouseAdapter(){
      public void mouseClicked(MouseEvent e){
          if (e.getClickCount() == 2){ SYNTAX CALLING THE METHOD IN TopPanel  }
      }
    } );
  }
}

5 个答案:

答案 0 :(得分:7)

解决此问题的一种方法是使用合成而不是继承。您可以将JPanel传递给JTable的子类。


public class TopPanel extends JPanel 
{
  private TheTable table;

  public TopPanel()
  {
    table = new TheTable(this);
  }

  public void methodToFire() { }
}

public class TheTable extends JTable 
{
  private TopPanel panel;

  public TheTable(TopPanel panel)
  {
    this.panel = panel;

    this.addMouseListener(new MouseAdapter() {
      public void mouseClicked(MouseEvent e) {
        doThing();
      }
    } );
  }

  private void doThing()
  {
    this.panel.methodToFire(); 
  }
}

答案 1 :(得分:4)

要访问Outer类的方法,您需要使用Outer.this.method()的语法。

因此,在这种情况下,要从侦听器访问“TheTable”类的方法,您应该使用TheTable.this.callMethod()

我认为TopPanel已将TheTable添加到其中。在这种情况下,您可以执行以下操作:

mouseClicked(...) {
   TopTable t = (TopTable)TheTable.this.getParent();
   t.MethodToFire();
}

这是对这个问题的直接回答,不一定是“最好”的方法。类型安全的组合方法将是一个更好的长期解决方案。

答案 2 :(得分:2)

好像你正在走一条路 - 为什么不做最外层的一切呢?毕竟,这是听众存在的一个原因:


    public class TopPanel {
        public TopPanel() {
            // Construct everything here
            OnePanel.TheTable.addMouseListener(new MouseAdapter(){
              public void mouseClicked(MouseEvent e){
                 if (e.getClickCount() == 2){ MethodToFire }
              }
              } );

        }

    }

答案 3 :(得分:2)

当您按下鼠标时,您可以使您的TheTable触发事件,TopPanel可以监听。这样做的好处是不会使Table和Panel类彼此依赖。

代码涉及更多,但解耦可能是值得的。

public class TopPanel extends JPanel 
{
  private TheTable table;

  public TopPanel()
  {
    table = new TheTable(this);
    table.addTheTableListener(new TheTableListener() {
      public void tableSelected() {  // or tableSelected(TableSelectionEvent e) if you want to make a TableSelectionEvent
        methodToFire();
      }
    });
  }

  public void methodToFire() { }
}

public class TheTable extends JTable 
{
  private TopPanel panel;
  private EventListenerList listeners;

  public TheTable(TopPanel panel)
  {
    this.panel = panel;
    listeners = new EventListenerList();

    this.addMouseListener(new MouseAdapter() {
      public void mouseClicked(MouseEvent e) {
        fireTableSelected();
      }
    } );
  }

  public void addTheTableListener(TheTableListener l) {
    listeners.add(l);
  }

  // also write removeListener

  private void fireTableSelected()
  {
    for (TheTableListener l : listeners) {
      l.tableSelected(); 
  }
}

public interface TheTableListener extends EventListener
{
    public void tableSelected();
}

答案 4 :(得分:0)

我不认为Java有这样做的直接语法,除非你开始玩反射(这当然是可能的,但我不认为它非常干净)。

在您想要进行调用的位置,您的“this”指的是MouseAdapter的匿名子类。

最干净的方法可能是创建一个私有方法,让我们在TheTable中调用它,并让适配器调用该函数。

现在,因为方法X在TheTable中,它不知道它在一个面板内,所以它没有任何方法来激活该功能。如果您确定每个表都在一个面板中,那么您可以向Table类添加一个面板引用字段,在创建它时初始化它(您可能需要在OnePanel上修改构造函数),然后从中调用TheTable中的方法。

如果您最终尝试探索不属于JPanel的面板方法,则可能需要创建并传递接口。