5

I'm trying to understand when to use revalidate/repaint/pack.

Surprisingly I haven't found much detailed under-the-hood documentation (feel free to link).

So far I have understood that this is all the responsibility of the RepaintManager.

  • paint/repaint refer to what sees as dirty/clean
  • pack/validate/revalidate refer to what is valid

This article on Oracle explains that calling a repaint enqueues a job on the Event Dispatcher Thread that will in turn call paintImmediately() on the component (this redraws the component).

This trail indicates that to be or not to be valid is associated with the LayoutManager. And that this is all about the size of the component rather than the content.

  1. Is it true that you should call revalidate when you move/resize your component and repaint when you change it's contents?
  2. Is the pack() method really a deprecated thing that you should never call?
  3. Are any of the above claims wrong?
kotoko
  • 599
  • 2
  • 6
  • 22

1 Answers1

6

Here are a few basic cases where you need to invoke those methods (I cover the basics but I may have missed a few other cases where calling those methods would be required).

  1. You should call revalidate() on a container when you have either: added one or more component, removed one or more components, changed the constraints of one or more contained components (constraints or XXXSize(), although the latter is not recommended), changed the LayoutManager of the container.
  2. You should call repaint() whenever you want that component (and its descendants) to be repainted. Eventually, this will call paintComponent() (for basic widgets this will delegate to XXXUI.paint()), paintBorder() and paintChildren() (at least in Swing)
  3. pack() actually sets the size of a window to its preferred size. You should usually call this right before making the window visible. You may call it later on but this will give a weird user experience (I don't know many applications that resize their windows once displayed)

The main advantage of using revalidate() and repaint() is that they can coalesce themselves. This means that if you call several times repaint(), the painting will only be performed once.

Guillaume Polet
  • 47,259
  • 4
  • 83
  • 117
  • Could you define paint in terms of what changes it implies? I starting to doubt I completely understand what it means. – kotoko Jan 15 '13 at 16:42
  • 1
    @kotoko I am not sure I am getting what kind of answer your looking for (wrt your comment). When you paint (implementation of the `paintComponent()` method), it means that you draw lines, circles (filled or not), rectangles (filled or not), images, text, etc... (all the operations you can actually invoke on a `Graphics/Graphics2D`). – Guillaume Polet Jan 15 '13 at 16:50
  • I was trying to understand what methods triggered what. Now I get it (rule of thumb): layout/component related operation affects if valid (your 1.); Graphics/Graphics2D operations affects if dirty. – kotoko Jan 15 '13 at 17:41
  • I have found one example that goes against what you said: splitPane with a holder Panel, when I do removeAll() on the holder panel nothing gets updated until I do repaint. – kotoko Jan 16 '13 at 16:06
  • @kotoko How does it contradicts what I am stating in my answer? What I may have not directly said is that almost any time you call `revalidate()`, `repaint()` should also be called right after (the opposite is not true though) – Guillaume Polet Jan 16 '13 at 16:17