我有一个包含多个JCheckBox的Swing应用程序。每个JCheckBox
对应于我的程序中其他类型Foo
的对象。对于Foo
类型的每个对象,我将有一个这样的JCheckBox可供用户单击(它告诉Foo对象它们是否应该在UI上显示)。
我目前正在做的是使用JCheckBox
上的name属性作为对Foo
对象的字符串“name”的引用。我觉得更清洁的解决方案是扩展JCheckBox
以向其添加额外的字段,以便JCheckBox
可以通过简单地存储对它的引用来跟踪它附加到哪个Foo对象。思考?人们是否经常扩展Swing组件,以便他们可以将控制器/视图中的部件链接回模型?我是否会遇到一些可怕的陷阱?
答案 0 :(得分:4)
如果没有其他细节,很难全面了解这个特定的例子。您可以使用操作完成此任务。有关详细信息,请参阅How to Use Actions。这是一个例子:
import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.event.*;
import java.io.IOException;
import java.io.OutputStream;
import java.io.PrintStream;
import java.util.ArrayList;
import java.util.List;
import javax.swing.*;
public class CheckBoxDemo {
static class Foo {
private boolean visible;
private String name;
public Foo(String name) {
this.name = name;
}
public boolean isVisible() {
return visible;
}
public void setVisible(boolean visible) {
this.visible = visible;
System.out.println(getName() + ".setVisible:" + visible);
}
public String getName() {
return name;
}
}
static class FooAction extends AbstractAction {
private Foo foo;
public FooAction(Foo foo) {
super(foo.getName());
this.foo = foo;
}
@Override
public void actionPerformed(ActionEvent e) {
JCheckBox checkBox = (JCheckBox) e.getSource();
foo.setVisible(checkBox.isSelected());
}
}
private static void createAndShowGUI() {
List<Foo> fooList = new ArrayList<Foo>();
fooList.add(new Foo("Foo1"));
fooList.add(new Foo("Foo2"));
fooList.add(new Foo("Foo3"));
JPanel content = new JPanel(new BorderLayout());
JPanel fooPanel = new JPanel();
for (Foo foo : fooList) {
fooPanel.add(new JCheckBox(new FooAction(foo)));
}
content.add(fooPanel, BorderLayout.NORTH);
final JTextArea textArea = new JTextArea();
textArea.setEditable(false);
JScrollPane scrollPane = new JScrollPane(textArea);
scrollPane.setPreferredSize(new Dimension(200, 200));
content.add(scrollPane, BorderLayout.CENTER);
JFrame frame = new JFrame("CheckBoxDemo");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(content);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
// just for brevity of example
System.setOut(new PrintStream(new OutputStream() {
@Override
public void write(int b) throws IOException {
textArea.append(String.valueOf((char) b));
}
}));
}
public static void main(String[] args) {
javax.swing.SwingUtilities.invokeLater(new Runnable() {
public void run() {
createAndShowGUI();
}
});
}
}
答案 1 :(得分:3)
一般规则是不出于应用原因扩展JSomething:它们被设计为使用。
您的上下文听起来像一个绑定方案。 @Max建议(使用操作作为绑定代理)指出了遵循的方向,对于您可能考虑使用绑定框架(如JGoodies或BetterBeansBinding)的更复杂的需求
答案 2 :(得分:0)
这是一个常见的要求,您可以将JCheckbox
扩展为某个JFooCheckBox
,其中包含Foo对象,并且监听器应该处理Foo的显示/隐藏。