3

我试图弄清楚为什么当我手动拖动我的窗口时我的 JComponent 会刷新,但是当我调用 repaint 或 revalidate 时它不会刷新。数据已准备好显示,但在我手动调整大小之前它不会显示。任何人都可以就我能做什么提供一些建议,或者这听起来像是不是 Swing 问题,因为我尝试了重新绘制和重新验证?

我注意到的一件奇怪的事情是,如果我有这个代码:

sp.setSize(sp.getSize().width, sp.getSize().height+1);
sp.setSize(sp.getSize().width, sp.getSize().height-1);

如果使用第一行,则 JComponent 将自行刷新。如果我不使用或同时使用这两条线,它就不会,这对我来说似乎很奇怪。

我基本上只是将 JPanel 放在 JDesktopPane 中的 JInternalFrame 中。我正在尝试做的事情有两个主要功能。一个添加新的 JPanel,另一个尝试刷新它,以便新数据显示:

public void addNewSP()
 {
sp = new JInternalFrame("SP");
  sp.setClosable(true);
  sp.setLocation(700, 400); //this should be changed to something based on screen size
  sp.setResizable(true);
  sp.add(popUp);
  this.parentContainer.add(sp, JLayeredPane.DRAG_LAYER);
  sp.pack();
  sp.show();
  sp.setSize(500, 500);
  sp.setPreferredSize(new Dimension(500, 500));
}

public void refreshSP()
 {

  sp.repaint();
  sp.validate();
  sp.repaint();

  sp.validate();
  parentContainer.validate();
  parentContainer.repaint();

  sp.setSize(sp.getSize().width, sp.getSize().height+1);
  sp.setSize(sp.getSize().width, sp.getSize().height-1);
  }
 }

BTW parentContainer 是 JDesktopPane

4

4 回答 4

7

更改容器的内容时​​,您必须同时调用:

  • revalidate()使其重新计算其内容的布局
  • repaint()请求重绘此容器
于 2010-08-30T20:57:51.977 回答
1

但在我手动调整大小之前它不会显示。

我们不知道您的问题的背景,这就是为什么应始终按照前面的建议发布 SSCCE。

一般来说,JComponent 没有首选大小,所以我猜 Swing 认为它不需要绘制组件。当您调整框架大小时,组件可能会添加到 BorderLayout 的中心,因此它会自动调整大小以填充框架的整个空间。

解决方案是给您的组件一个“首选大小”,以便任何布局管理器都可以使用此信息来正确显示组件。

于 2010-08-31T03:29:29.127 回答
0

我假设parentContainer是 JDesktopPane?
你做了什么样的改变sp没有出现?

更改 的大小sp将导致 Swing 从头开始​​重新绘制。这setSize() 就是修复显示器的原因。

最有可能的是,您所做的更改要么没有在 EDT 上发生,要么没有使正确的容器失效。例如,如果您在 中更改组件的可见性,则sp需要调用sp.invalidate()以重新运行布局管理器。

您是否检查过您只是在 EDT 上更改组件(或其模型)?

一个快速测试是使用Substance LAF运行,因为如果您在另一个线程上更改内容,它会抱怨。

于 2010-08-31T16:18:27.640 回答
0

如果您正在修改容器的子组件,您应该调用 jcomponent.validate();

于 2010-08-30T19:24:07.567 回答