Double Buffering in SWT

To draw the contents of a custom widget in SWT, you have to implement a PaintListener. The paint method is the only place where you have access to the widget’s GC (aka “Graphic Context”), which provides the actual drawing methods.Paint events are handled in the Display thread. This means, the UI is not responding while you are drawing. If you do complex calculations while drawing, this results in flickering.

To prevent this flickering and to keep the UI responsive, the usual approach is to use double buffering: you use two buffers, one is used for drawing and one is visible. When you are finished with drawing a complete frame, you swap the two buffers: the buffer for drawing is now visible and vice versa.

In SWT, you don’t have an explicit buffer you are working on, but you have the GC which provides the methods to manipulate the contents of the buffer. You get the GC instance for your widget visible on the screen as part of the PaintEvent that is provided to the paint callback method. To obtain an independent GC for drawing, you have to do a little trick: create an Image with the size of your widget. For this Image, you can create a GC instance which is usable independently of the UI thread.

Putting all pieces together, you use two Image instances which are used alternating for drawing and showing. The paint callback method just draws the one image that is currently used for showing to the GC of the widget.

SWT snippet 48 shows a basic version of this approach. For Vex, I started to implement a more gerneral version, applicable to Scrollable instances, that uses a dedicated rendering thread for drawing: the DoubleBufferedRenderer.


The DoubleBufferedRenderer handles the paint events for an instance of Scrollable using double buffering as described above. It allows you to schedule a list of IRenderStep instances, a simple functional interface to implement the distinct steps of your drawing logic, that depend on access to the GC.

Internally, the execution of the render steps happens in a dedicated rendering thread. When all steps are executed, a redraw of the widget is triggered. The finished Image is then used in the paint callback method until a new image is ready.


Example: When the control is resized, we have to layout the content and paint it. Therefor we schedule two IRenderStep instances:

renderer.schedule(layoutContent(), paintContent());

To make it more readible, I put the creation of the IRenderStep into factory methods, which return an anonymous implementation:

private IRenderStep layoutContent() {
   return new IRenderStep() {
     public void render(final Graphics graphics) {

The anonymous class looks cumbersome. In Java 8 this can be expressed in a much more elegant way, but unfortunately the Eclipse platform is still on Java 6.

For more examples of how DoubleBufferedRenderer can be used, you should have a look at the implementation of BoxWidget.


This all is still work in progress. For example the schedule method does not queue the lists of IRenderStep instances, it just knows about the currently executed list of steps and the following list of steps. Each call to schedule overwrites the latter.

Also the usage of threads is still very ineffective. If you have multiple widgets, each using its own instance of DoubleBufferedRenderer, each one will run its own thread. Using a thread pool or more sophisticated techniques will help here.

If you still want to give it a try, there is one dependency to Vex that you have to be aware of: IRenderStep provides an instance of Graphics, an abstraction of the graphics framework in use. For use outside of Vex, you can just replace this with an instance of GC.

The Maintenance Analogy

In engineering, maintenance means to tear a machine apart, clean it, replace broken parts, oil it and put everything together as it was before. Maintenance is needed to ensure the longevity, the quality of service and also the safety of a machine.

Some people say, that this is not needed for software. Bits do not wear out or break and bits do not need recurrent lubrication. You know what: they are right. This is not what happens in software development. But, as with many other analogies in software development, it is not that easy. You have to think about the goal of maintenance instead: make sure that the software is useful for a long time. Useful means in terms of software, that you are able to change the behavior of the software, either to fix bugs, or to react to changes in the requirements of the software.

Some people say, if you practice clean code development with due diligence, the software is always in shape for changes. But concepts, structures and algorithms wear out over time. When requirements change, the existing implementation does not fit anymore. The many small changes that accumulate over time dillute the original architecture. While the code in detail might be in perfect clean shape, the bigger picture will show some flaws after a certain period.

Some day you will come into the situation where you have to take apart your application and replace some of its parts with better fitting implementations. This is for sure. The problem most of the time is to realize this situation and actually do what is necessary instead of taking a shortcut. And this is the secret of successful software maintenance. Its not about fixing bugs and adding new features until a single change is more expensive than writing everything from scratch. Its mainly about doing those changes that keep the big picture in shape. Its about being able to fix bugs and add new features forever.

By the way: having clean code makes maintenance much much easier, because you only have to take care of the big picture’s shape. If you don’t do clean code development, start now! No really, do it! Now!