我正在尝试使用JTree和JTable为电影数据库制作GUI。但是我有问题,当我想从JTable中添加或删除某些行时,我无法弄清楚如何在JTree中显示此更改。我尝试添加kategorieFilmu.add(node)
或kategorieFilmu.remove(row)
,但它不起作用。我还尝试使用panelJTree.repaint
刷新JTree。
的JTable:
protected JScrollPane jTable()
{
vypisFilmu.setRowSorter(sorter);
sorter.setRowFilter(RowFilter.regexFilter(""));
vypisFilmu.setModel(spravaFilmu.getModel());
class ButtonEditor extends DefaultCellEditor {
private static final long serialVersionUID = 1L;
protected JButton button;
private String label;
private boolean isPushed;
public ButtonEditor(JCheckBox checkBox) {
super(checkBox);
button = new JButton();
button.setOpaque(true);
button.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
fireEditingStopped();
}
});
}
public Component getTableCellEditorComponent(JTable table, Object value,
boolean isSelected, int row, int column) {
button.setText(label);
int index = (Integer) vypisFilmu.getValueAt(row, 0);
spravaFilmu.removeRow(index); //DELETE row
spravaFilmu.getFilmy().add(new film("", "", 0, 0,"", false)); //ADD new - without this it trows exception, because one row is missing
panelJTable.repaint();
/*kategorieFilmu.remove(row);
panelJTree.repaint();*/
isPushed = true;
return button;
}
public boolean stopCellEditing() {
isPushed = false;
return super.stopCellEditing();
}
protected void fireEditingStopped() {
super.fireEditingStopped();
}
}
class ButtonRenderer extends JButton implements TableCellRenderer {
private static final long serialVersionUID = 1L;
public ButtonRenderer() {
setOpaque(true);
}
public Component getTableCellRendererComponent(JTable table, Object value,
boolean isSelected, boolean hasFocus, int row, int column) {
if (isSelected) {
setForeground(table.getSelectionForeground());
setBackground(table.getSelectionBackground());
} else {
setForeground(table.getForeground());
setBackground(UIManager.getColor("Button.background"));
}
setText((value == null) ? "" : value.toString());
return this;
}
}
vypisFilmu.getColumn("Smazat").setCellRenderer(new ButtonRenderer());
vypisFilmu.getColumn("Smazat").setCellEditor(new ButtonEditor(new JCheckBox()));
DefaultTableCellRenderer centerRenderer = new DefaultTableCellRenderer();
centerRenderer.setHorizontalAlignment( JLabel.CENTER );
TableColumn column = null;
final JScrollPane panelJTable = new JScrollPane(vypisFilmu);
hlavniOkno.this.add(BorderLayout.CENTER, panelJTable);
return panelJTable;
}
JTree的:
private JTree kategorieFilmu;
protected JScrollPane jTree()
{
kategorieFilmu = new JTree(root);
add(kategorieFilmu);
root.add(akcni);
root.add(animovany);
root.add(drama);
root.add(komedie);
for(int i = 0; i < pocetFilmu;i++)
{
if(spravaFilmu.getFilmy().get(i).getZanr().equals("Akční"))
{
DefaultMutableTreeNode nazevNode = new DefaultMutableTreeNode(spravaFilmu.getFilmy().get(i).getNazev());
akcni.add(nazevNode);
}
else if(spravaFilmu.getFilmy().get(i).getZanr().equals("Animovaný"))
{
DefaultMutableTreeNode nazevNode = new DefaultMutableTreeNode(spravaFilmu.getFilmy().get(i).getNazev());
animovany.add(nazevNode);
}
else if(spravaFilmu.getFilmy().get(i).getZanr().equals("Drama"))
{
DefaultMutableTreeNode nazevNode = new DefaultMutableTreeNode(spravaFilmu.getFilmy().get(i).getNazev());
drama.add(nazevNode);
}
else if(spravaFilmu.getFilmy().get(i).getZanr().equals("Komedie"))
{
DefaultMutableTreeNode nazevNode = new DefaultMutableTreeNode(spravaFilmu.getFilmy().get(i).getNazev());
komedie.add(nazevNode);
}
else {}
}
/****** Select category ******/
kategorieFilmu.getSelectionModel().addTreeSelectionListener(new TreeSelectionListener() {
@Override
public void valueChanged(TreeSelectionEvent e) {
DefaultMutableTreeNode selectedNode = (DefaultMutableTreeNode) kategorieFilmu.getLastSelectedPathComponent();
if(selectedNode.getUserObject().toString() == "Všechny filmy")
{
sorter.setRowFilter(RowFilter.regexFilter(""));
vypisFilmu.setModel(spravaFilmu.getModel());
}
else
{
sorter.setRowFilter(RowFilter.regexFilter(selectedNode.getUserObject().toString()));
vypisFilmu.setModel(spravaFilmu.getModel());
}
}
});
final JScrollPane panelJTree = new JScrollPane(kategorieFilmu);
panelJTree.setPreferredSize(new Dimension(180,520));
hlavniOkno.this.add(BorderLayout.LINE_START, panelJTree);
return panelJTree;
}
的TableModel:
public class spravaFilmu {
private ArrayList<film> filmy = new ArrayList<>();
private TableModel model;
public spravaFilmu()
{
// Testovací data
filmy.add(new film("Expendables: Postradatelní", "Akční", 2010, 103,"Sylvester Stallone", true));
filmy.add(new film("Rivalové", "Akční", 2013, 123,"Ron Howard", true));
filmy.add(new film("Temný rytíř povstal", "Akční", 2012, 158,"Christopher Nolan", true));
filmy.add(new film("Avengers", "Akční", 2012, 143,"Joss Whedon", false));
filmy.add(new film("Skyfall", "Akční", 2012, 143,"Sam Mendes", true));
filmy.add(new film("Expendables 2, The", "Akční", 2012, 103," Simon West ", false));
filmy.add(new film("Iron Man 3", "Akční", 2013, 130,"Shane Black", true));
filmy.add(new film("Raubíř Ralf", "Animovaný", 2012, 97,"Rich Moore", true));
filmy.add(new film("LEGO® příběh", "Animovaný", 2014, 100,"Phil Lord", true));
filmy.add(new film("Croodsovi", "Animovaný", 2013, 90,"Chris Sanders", true));
filmy.add(new film("Ledové království", "Animovaný", 2013, 102,"Chris Buck", true));
filmy.add(new film("Hon", "Drama", 2012, 115,"Thomas Vinterberg", true));
filmy.add(new film("Nespoutaný Django", "Drama", 2012, 165,"Quentin Tarantino", true));
filmy.add(new film("Grandhotel Budapešť", "Komedie", 2014, 100,"Wes Anderson", true));
filmy.add(new film("Vlk z Wall Street", "Komedie", 2013, 180,"Martin Scorsese", true));
filmy.add(new film("Lásky čas", "Komedie", 2013, 123,"Richard Curtis", true));
filmy.add(new film("Stuck in Love", "Komedie", 2012, 97,"Josh Boone", false));
// Definice vlastního modelu JTable
model = new AbstractTableModel() {
private static final long serialVersionUID = 1L;
String[] nazvySloupcu = {"ID", "Název", "Žánr", "Rok", "Délka (min)", "Režie", "Dabing", "Smazat"};
@Override
public String getColumnName(int col) { return nazvySloupcu[col]; }
@Override
public int getRowCount() { return getFilmy().size(); }
@Override
public int getColumnCount() { return nazvySloupcu.length; }
@Override
public Object getValueAt(int row, int col) {
film film = getFilmy().get(row);
switch (col)
{
case 0:
return film.getId();
case 1:
return film.getNazev();
case 2:
return film.getZanr();
case 3:
return film.getRok();
case 4:
return film.getDelka();
case 5:
return film.getRezie();
case 6:
return film.getDabing();
case 7:
return "X";
}
return film;
}
@Override
public boolean isCellEditable(int row, int col) { return true; }
};
}
public ArrayList<film> getFilmy() {
return filmy;
}
public TableModel getModel() {
return model;
}
public void removeRow(int index)
{
filmy.remove(index);
}
}
我会感激任何帮助。
答案 0 :(得分:4)
尝试使用DefaultTreeModel#reload()并调用此方法,如果您已修改此模型所依赖的TreeNodes。模型将通知其所有侦听器模型已在给定节点下更改。
示例代码:
DefaultTreeModel model = (DefaultTreeModel)tree.getModel().getRoot();
model.reload((TreeNode) model.getRoot());
注意:
JTree
中的节点,如@MadProgrammer在以下评论中所建议的那样。有关使用
DefaultTreeModel
的更多信息和示例,请参阅How to Use Trees in The Java Tutorial。请特别查看 Dynamically Changing a Tree 部分。