2012-03-18 60 views
1

我使用带有propertyChangeListener的JPanel,并希望它根据每当特定变量model发生更改时自行重新渲染。我为同一代码如下 -
Java swing - Jpanel不会自我渲染/重新绘制

public class LabelMacroEditor extends JPanel implements PropertyChangeListener { 

    private static final long serialVersionUID = 1L; 
    private LabelMacroModel model; 

    public LabelMacroEditor(LabelMacroModel bean) { 

     this.model = bean; 
     model.addPropertyChangeListener(this); 
     setupComponents(); 
     validate(); 
     setVisible(true); 
    } 

    public void setupComponents() 
    { 

     Box allButtons = Box.createVerticalBox(); 
     JScrollPane macroModelScroller = new JScrollPane(allButtons); 
     macroModelScroller.setPreferredSize(new Dimension(300, 200)); 
     for(MacroModel macroModel : model.getMacroModelList()) 
     { 
      LabelMacroEditorEditableEntity macroEditorEntity = new LabelMacroEditorEditableEntity(macroModel); 
      Box entityBox = Box.createHorizontalBox(); 
      entityBox.add(macroEditorEntity.getUpButton()); 
      entityBox.add(Box.createHorizontalStrut(15)); 
      entityBox.add(macroEditorEntity.getMacroDetailsButton()); 
      entityBox.add(Box.createHorizontalStrut(15)); 
      entityBox.add(macroEditorEntity.getDownButton()); 

      allButtons.add(entityBox); 
     } 
     add(macroModelScroller); 
    } 

    @Override 
    public void propertyChange(PropertyChangeEvent arg0) { 
     revalidate(); 
     repaint(); 
    } 
} 

当我使用调试模式在eclipse中我可以看到,每当有变化model它激发了呼叫propertyChange,它也运行在revalidaterepaint但只有JPanel显示保持不变。它似乎没有让自己放弃。 我在这里失踪的任何基本的东西?

编辑:

属性IM变化的一个例子代码段如下 -

labelMacroModel.addMacroModel(addedMacroModel); 

其中labelMacroModel是类型LabelMacroModel的和addedMacroModel是类型Macro

的现在相关部分LabelMacroModel类火灾财产变更如下 -

private List<MacroModel> macroModelList;// this is the list of all MacroModels 
public void addMacroModel(MacroModel macroModel) { 
     macroModelList.add(macroModel); 

     pcs.fireIndexedPropertyChange("LabelMacroModel", macroModelList.size(), null, macroModel); 
    } 
+0

*“我在这里错过的任何基本的东西?”*一个SSCCE让我感兴趣? – 2012-03-18 18:42:01

+0

你能举一个你改变的例子属性吗? – 2012-03-18 18:44:23

+0

@PerryMonschau - 我编辑过,以提供改变属性的代码片段。 – ping 2012-03-18 18:53:15

回答

4

它不清楚如何更改面板中的组件。如果面板未更新,则重绘/重新验证将不起作用。我认为如果你没有修改组件布局的方式,你不应该需要显式调用重新验证/重新绘制。 JButton.setText应该例如改变按钮的标签而不需要调用重画。

+0

这是否意味着我宁愿做一个removeAll();然后一个setupComponents();而不是使用重新验证和重绘? – ping 2012-03-18 18:54:49

+2

不可以。如果您修改组件中的文本,它应显示而不调用repaint。通常在修改组件的布局时需要重新验证。 – 2012-03-18 19:22:49

+0

不确定 - 请参阅我的回答 – davidfrancis 2012-03-18 23:00:32

2

为了扩大上述AKJ的答案,我认为你应该重建你的物业变化的组件。所以做一个删除所有然后读取是做到这一点的一种方法。一旦你得到了这个工作,你可以更有选择地将模型更新推入到GUI中,例如,如果添加了新条目,那么只需添加一个新组件来反映这一点。尽管如此,remove all/readd对很多情况都很好。 HTH。

+0

这两个答案都是有效的,1+票。我认为这取决于重新创建GUI组件的成本。 – 2012-03-19 00:24:17