简体   繁体   English

Java Swing:在我告诉组件之前,禁止组件更新启用状态

[英]Java Swing: prevent Components to update enabled state until I tell them to

I have an extensive Gui with many components in it. 我有一个包含许多组件的广泛的Gui。 There is a updateEnable() methods that updates the enable state of all the components based on some configuration. 有一个updateEnable()方法可根据某些配置更新所有组件的启用状态。

I basically first set their enable state to true and then disable some of them (based on the configuration): 我基本上首先将它们的启用状态设置为true,然后禁用其中一些(基于配置):

private void updateEnable() {
  enableAllRec(panel, true);
  // disable some components
}

private void enableAllRec(Container root, boolean b) {
  if (root == null) return;
  for (Component c : root.getComponents()) {
    c.setEnabled(b);
    if (c instanceof Container) enableAllRec((Container) c, b);
  }
}

The reason I do it like that is that some of the components are not stored as member variables and I don't have access to them. 我这样做的原因是某些组件未存储为成员变量,并且我无法访问它们。 They however can change their state because I initialized some of them like this (for example): 但是,它们可以更改其状态,因为我这样初始化了其中的一些(例如):

final JLabel exampleLabel = new JLabel("yoink");
final JCheckBox exampleCheckBox = new JCheckBox("boing");
exampleCheckBox.addItemListener(new ItemListener() {
  @Override
  public void itemStateChanged(ItemEvent e) {
    exampleLabel.setEnable(exampleCheckBox.isSelected());
  }
});

Now my problem is the following: When I call updateEnable() , some of the (stored) Components may flicker because they are enabled and then disabled again after some time. 现在,我的问题如下:当我调用updateEnable() ,某些(存储的)组件可能会闪烁,因为它们已启用,然后在一段时间后再次被禁用。 I would like to prevent that. 我想防止这种情况。 My idea is to somehow prevent the GUI from refreshing until the very end of updateEnable() and then perform an updateUI() . 我的想法是以某种方式阻止GUI刷新到updateEnable() ,然后执行updateUI() But this is not very elegant AND I have no idea how to prevent the GUI from updating. 但这不是很优雅,我也不知道如何防止GUI更新。

Am I missing a very elegant alternative solution for this problem? 我是否为此问题错过了一个非常优雅的替代解决方案?

Thanks a lot, Stefan 非常感谢Stefan

In case your components might be enabled/disabled a few times in a row due to some logical changes and calculations - you should perform that calculation before applying some of the changes to visual components. 如果由于某些逻辑更改和计算而可能连续几次启用/禁用了组件,则应在将某些更改应用于可视组件之前执行该计算。 In that case you will change components state straight into final one. 在这种情况下,您将组件状态直接更改为最终状态。

Ok, my approach seems to work. 好的,我的方法似乎有效。 I just extended the enableAllRec(Container root, boolean b) to include some exclusions: 我只是扩展了enableAllRec(Container root, boolean b)以包括一些排除项:

private void enableAllRec(Container root, boolean defaultState, Set<Component> disableList, Set<Component> enableList) {
  if (root == null) return;
  for (Component c : root.getComponents()) {
    if (disableList != null && disableList.contains(c)) {
      c.setEnabled(false);
      disableList.remove(c);
    } else if (enableList != null && enableList.contains(c)) {
      c.setEnabled(true);
      enableList.remove(c);
    } else c.setEnabled(defaultState);
    if (c instanceof Container) enableAllRec((Container) c, defaultState, disableList, enableList);
  }
}

This way, I can determen all the components that I want to have enabled/disabled for sure, add them to their corresponding sets and thenn call the enableAllRec. 这样,我可以确定要启用/禁用的所有组件,将它们添加到其对应的集合中,然后调用enableAllRec。 Example: 例:

Set<Component> enableList = new HashSet<Component>();
enableList.add(searchFreqButton);
enableList.add(advMeasButton);
enableAllRec(configPanel, false, null, enableList);

Obviously, this is not ideal for large sets, but it is sufficient for my needs (arround 800 Components and the sets contain no more than arround 20-30 components). 显然,这对于大型集合而言并不理想,但足以满足我的需求(大约800个组件,而集合最多包含大约20-30个组件)。 I suspect this method to easily handle larger sets as well. 我怀疑这种方法也可以轻松处理更大的集合。

In the above example, it makes no sense to introduce a disableList (as all components will be disabled by default anyway). 在上面的示例中,引入disableList没有意义(因为默认情况下所有组件都将被禁用)。 So depending on the default value, one can leave out the corresponding set. 因此,根据默认值,可以忽略相应的设置。 This should preferably be done in enableAllRec() of course. 当然,最好应该在enableAllRec()中完成此操作。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM