[英]FlowControl in ActionListener method in Java When JButton Clicked
[英]Java JButton pass method call to actionlistener
我试图将方法名称传递给动作侦听器,以便它可以在没有50个if语句的情况下调用该方法。 我知道在C ++中有函数指针,但是在Java中这不是问题。 java中是否有一种方法可以使某些东西
actionPerfomed(ActionEvent e){
String command = e.getSource().getActionCommand()
//use command to look up a method on the implementing class
//and call it without an if
所有需要调用的方法都没有返回值,也没有需要传递给它们的值,它们可以从拥有它的框架中获取所有需要的信息。 我认为反射是一种有效的选择,但是我在Java中的使用经验有限,而且我从没读过任何有关它的文章。
这是针对框架构想的,因此可以将ActionListener从项目中剥离出来,并且几乎不需要修改就可以重用。 我正在与其他人一起在我的工作中开发的框架一起工作,该框架使用C#进行编写,并且编写了这个人在编写时所从事的工作。 因此,我尝试创建它的Java实现,因为C#具有其局限性(Windows)。
您可以通过几种方法来实现,一种可能是设计一个通用接口,所有“命令”都需要实现该接口,只有一个方法,然后您的ActionListener
就可以执行。
例如...
public interface Command {
public void execute();
}
然后,您的UI中将有一个Map
,该Map
会将actionCommand
映射到Command
的实例。
public class ... extends ... {
private Map<String, Command> commands = new HashMap<>(25);
//...
现在,您可以拥有一个不错的“添加”方法,该方法将允许您动态添加命令,为每个新命令创建一个新的JButton
或根据需要在类中JButton
设置它
然后在ActionListener
,您只需获取actionCommand
属性,在Map
查找Command
,然后execute
如果有效)
@Override
public void actionPerformed(ActionEvent e) {
Command cmd = commands.get(e.getActionCommand());
if (cmd != null) {
cmd.execute();
}
}
例如...
package javaapplication659;
import java.awt.EventQueue;
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.Insets;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.HashMap;
import java.util.Map;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
public class TestCommand {
public static void main(String[] args) {
new TestCommand();
}
public TestCommand() {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
ex.printStackTrace();
}
JFrame frame = new JFrame("Testing");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(new TestPane());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}
public class TestPane extends JPanel {
private Map<String, Command> commands = new HashMap<>(25);
private ActionListener actionListener;
private GridBagConstraints gbc;
public TestPane() {
setLayout(new GridBagLayout());
gbc = new GridBagConstraints();
gbc.gridwidth = GridBagConstraints.REMAINDER;
gbc.fill = GridBagConstraints.HORIZONTAL;
gbc.insets = new Insets(1, 1, 1, 1);
actionListener = new ActionHandler();
add("Take over the world", new Command() {
@Override
public void execute() {
System.out.println("Take over the world");
}
});
add("Quwell up rising", new Command() {
@Override
public void execute() {
System.out.println("Bring the boot down");
}
});
add("Buy milk", new Command() {
@Override
public void execute() {
System.out.println("Buy milk");
}
});
}
public void add(String text, Command cmd) {
JButton btn = new JButton(text);
btn.addActionListener(actionListener);
commands.put(text, cmd);
add(btn, gbc);
}
public class ActionHandler implements ActionListener {
@Override
public void actionPerformed(ActionEvent e) {
Command cmd = commands.get(e.getActionCommand());
if (cmd != null) {
cmd.execute();
}
}
}
}
public interface Command {
public void execute();
}
}
现在,这是一个非常基本的示例,并且根据您的需求可能会更复杂,但是它展示了基本思想
这不是一个完美的解决方案,但是尽管我可以在这里说一下...
JButtonSpecial是我的课程,扩展了JButton。 JButtonSpecial将包含您要传递给ActionListener的方法。 然后您可以做类似的事情,
button=new JButtonSpecial("Click Here");
button.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e) {
JButtonSpecial tmpButton = (JButtonSpecial)e.getSource();
tmpButton.yourCustomMethod();//this method will be defined in JButtonSpecial
}
});
我同意您将要在其中对方法名称进行硬编码,但是您可以在对象之间更改方法的实现...
Java没有函数指针,因此您将必须执行以下操作:
private JButton button = new JButton("Click me!");
public YourClass()
{
...
button.setActionCommand("foo");
button.addActionListener(this);
...
}
public void actionPerformed(ActionEvent e)
{
String command = e.getActionCommand();
if(command.equals("foo"))
foo();
else if(...)
}
另外, e.getSource().getActionCommand()
会给您带来语法错误。 getActionCommand()
是ActionEvent
的方法,并且getSource()
返回一个对象,因此您可以执行e.getActionCommand()
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.