Java repaint()方法只能工作一次
我目前正在从事一个gui项目,该项目正在管理一个sql数据库。我目前正在添加、删除日志并显示mysql中存在的表。问题是,面板上的“添加”和“删除”按钮应该在添加或删除记录时重新绘制/刷新该面板上的表,但是在测试时,我发现“重新绘制”方法在第一次使用按钮后不会刷新表。什么会导致这个问题?提前谢谢Java repaint()方法只能工作一次,java,swing,repaint,Java,Swing,Repaint,我目前正在从事一个gui项目,该项目正在管理一个sql数据库。我目前正在添加、删除日志并显示mysql中存在的表。问题是,面板上的“添加”和“删除”按钮应该在添加或删除记录时重新绘制/刷新该面板上的表,但是在测试时,我发现“重新绘制”方法在第一次使用按钮后不会刷新表。什么会导致这个问题?提前谢谢 public JTabbedPane addComponentToPane() { //Container pane = new Container(); JTabbed
public JTabbedPane addComponentToPane() {
//Container pane = new Container();
JTabbedPane tabbedPane = new JTabbedPane();
JPanel card1 = new JPanel();
JPanel card2 = new JPanel();
JPanel card3 = new JPanel();
JPanel card4 = new JPanel();
JPanel card5 = new JPanel();
JPanel card6 = new JPanel();
JPanel card7 = new JPanel();
JPanel card8 = new JPanel();
card1.setLayout(new BorderLayout());
card2.setLayout(new BorderLayout());
card3.setLayout(new BorderLayout());
card4.setLayout(new BorderLayout());
card5.setLayout(new BorderLayout());
card6.setLayout(new BorderLayout());
card7.setLayout(new BorderLayout());
card8.setLayout(new BorderLayout());
JScrollPane actor = new JScrollPane(createTables("actor"));
card1.add(actor, BorderLayout.CENTER);
card3.add(createTables("address"), BorderLayout.CENTER);
card4.add(createTables("category"), BorderLayout.CENTER);
card5.add(createTables("city"), BorderLayout.CENTER);
card6.add(createTables("country"), BorderLayout.CENTER);
card7.add(createTables("customer"), BorderLayout.CENTER);
card8.add(createTables("film"), BorderLayout.CENTER);
JButton button = new JButton("Yeni Kayıt");
button.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
addRecord("actor");
card1.remove(actor);
card1.add(createTables("actor"), BorderLayout.CENTER);
card1.validate();
card1.repaint();
}
});
JButton delButton = new JButton("Kayıt sil");
delButton.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
delRecord("actor");
card1.remove(actor);
card1.add(createTables("actor"), BorderLayout.CENTER);
card1.validate();
card1.repaint();
}
});``
card1.add(button, BorderLayout.SOUTH);
card1.add(delButton, BorderLayout.EAST);
tabbedPane.addTab("Şirketler", null, card1, "şirket tanımları");
tabbedPane.addTab("Sorumlular", card2);
tabbedPane.addTab("Varlık Grupları", card3);
tabbedPane.addTab("Bilgi Varlıkları", card4);
tabbedPane.addTab("Varlık Değerleri", card5);
tabbedPane.addTab("Açıklıklar", card6);
tabbedPane.addTab("Tehditler", card7);
tabbedPane.addTab("Ek-A", card8);
//pane.add(tabbedPane, BorderLayout.CENTER);
return tabbedPane;
}
createtables方法从sql表创建Jtable
private JScrollPane createTables(String tablename) {
Connection con = null;
Statement statement = null;
ResultSet result = null;
String query;
JScrollPane jsp = null;
try {
Class.forName("com.mysql.jdbc.Driver").newInstance();
con = DriverManager.getConnection("jdbc:mysql://localhost:3306/sakila", "root", "root");
statement = con.createStatement();
query = "select * from " + tablename;
result = statement.executeQuery(query);
ResultSetMetaData rsmt = result.getMetaData();
int columnCount = rsmt.getColumnCount();
Vector column = new Vector(columnCount);
for (int i = 1; i <= columnCount; i++) {
column.add(rsmt.getColumnName(i));
}
Vector data = new Vector();
Vector row = new Vector();
while (result.next()) {
row = new Vector(columnCount);
for (int i = 1; i <= columnCount; i++) {
row.add(result.getString(i));
}
data.add(row);
}
defTableModel = new DefaultTableModel(data, column);
table = new JTable(defTableModel) {
@Override
public boolean isCellEditable(int row, int column) {
return false;
}
;
};
//table.setAutoCreateRowSorter(true);
TableRowFilterSupport.forTable(table).searchable(true).apply();
table.setRowSelectionAllowed(true);
jsp = new JScrollPane(table);
}
catch (Exception e) {
e.printStackTrace();
// JOptionPane.showMessageDialog(null, "ERROR");
}
finally {
try {
statement.close();
result.close();
con.close();
}
catch (Exception e) {
//JOptionPane.showMessageDialog(null, "ERROR CLOSE");
}
}
return jsp;
}
我可以看到代码中有几个不一致之处: 未将actor变量设置为操作侦听器中添加的组件。 第一次添加新的JScrollPanecreateTablesactor时,然后只添加createTablesactor。
1可能是导致问题的原因。我认为问题在于对参与者的引用:
card1.remove(actor);
card1.add(createTables("actor"), BorderLayout.CENTER);
在这里,变量actor在card1中没有更多的引用。为了不丢失此引用,您应该在两种actionPerformed方法中执行以下操作:
card1.remove(actor);
actor = new JScrollPane(createTables("actor"));
card1.add(actor, BorderLayout.CENTER);
您可以尝试调用revalidate;重新油漆;而不是验证;重新油漆;我已经试过了,但是谢谢你的建议。你能发布你的createTables函数吗?更好的是,您能发布一个吗?我已经添加了createTables函数。更新表时应该不需要显式调用repaint。更改表格模型,表格将更新。发布一个or。这不是问题所在。我必须这样做,因为我必须在数据库更改时重新创建表。如果我再次添加actor变量,则不会再次调用该函数,并且会添加旧表,因为它不是动态的。@Sertage说得更清楚了。如果您不能使用actor,因为它需要是final,那么您可以将其设置为类的成员变量,或者在action listener中使用removeAll而不是remove。我认为将actor变量设置为成员变量并不是一个合适的解决方案,因为这只是一种情况,removeAll函数还可以从面板中删除不必要的按钮。你能想出一个方法,我可以删除只是表?谢谢。一种黑客方法是使用getComponents并在面板中搜索表。我使用了这段代码,它可以工作。只是为了进一步使用:Component[]components=card1.getComponents;forComponent组件:如果组件实例为JScrollPane card1.removecomponent,则为组件;我想你已经发现了问题所在,但我仍然没有解决方案,因为我在尝试引用actor变量时出错,说从内部类引用的局部变量必须是final这是一个愚蠢的问题,但使变量final是可行的选项吗?