Click here to Skip to main content
Click here to Skip to main content

A curtain hiding screen updates, and blending old and new content with a nice fade effect

, 13 Jan 2007
Rate this:
Please Sign up or sign in to vote.
Freeze parts of the user interface until all drawings are done, and blend old content with the new one smoothly.

Purpose

Once in a while, you get an extensive screen update to do. I mean that kind of refresh that invalidates many UI components and makes your desktop application look like a loading webpage. During these updates, many components need to be painted one at a time to obtain the final screen. The problem occurs when the update spans multiple paint events thus making techniques like double buffering hard to use. Worst of all, your users keep complaining about this amateur look and, of course, you don’t feel like an amateur. So you dream of a way to hide your work in progress and only show the end result, don’t you?

This is what this component is all about: freezing parts of the user interface until all drawings are done, even for many paint events. And then, just to sweeten things, the new content is smoothly blended with the old one using a nice fade effect. So now, you get it: this is your chance to add a web 2.0 taste to your desktop application.

If that sounds interesting, here is a Visual Studio 2005 C# loading curtain form ready to be integrated into your project. I named it a “curtain” for it is similar to a theatre curtain which hides actors while they are setting up the next scene.

Why not use the double buffering technique?

Maybe, you’ve heard of the Windows Forms DoubleBuffered property and think that it should work just fine. While it may be handy in some situations, it has some limitations for our problem at hand:

  • Not always possible or easy since some components may not be under your control. For example, when you have a COM component that directly draws itself using a device context, the buffering technique is not an option.
  • Doesn’t span multiple paint events. So when multiple components need to be painted, you have to make sure that they do all at the same time or otherwise, you will end up with the webpage loading syndrome.
  • Not easy to target only parts of the screen.
  • No solution out of the box to apply a fade effect (so forget about the web 2.0 spice).
  • Rather heavyweight when all you want is to hide something for a quarter of a second!

How it works conceptually

  1. Just before updating the UI, you put the curtain over the screen area.
  2. The curtain takes a screen snapshot, and displays this still image to the user.
  3. Meanwhile, you do the hard update work, and rearrange the screen without causing your user an epileptic crisis.
  4. When you’re done, you fade the curtain and let the user see your artwork.

How it works in code

  1. Import the curtain into your project. To do so with Visual Studio 2005, go to ‘Project’, then ‘Add existing item’, and browse for the curtain’s file CurtainForm.cs.
  2. Create your curtain object and configure it. If you want to update multiple UI parts at the same time, you just create multiple curtains!
    MT.CurtainForm myCurtain = new MT.CurtainForm();
  3. Show your curtain in front of the control to be updated (most common case):
    myCurtain.Show(myControl);

    Or manually set the area to be updated:

    myCurtain.Bounds = new Rectangle(x, y, width, height);
    myCurtain.Show();
  4. Finally, fade your curtain:
    myCurtain.Fade();

    Or hide it without the fade effect:

    myCurtain.Hide();

Curtain attributes

These settings are very fine grained, and are provided only for the more fanatical of you!

FadeDuration

Indicates the total time of the fade in milliseconds. Personally, I use a 250ms time since it is not too long to be annoying, and just enough to let the user properly see what has been changed.

FrameDuration

This is the animation accuracy or quality. Like the frames per second in video games, and you can use more or less CPU power. You specify the accuracy by setting the duration of each frame in milliseconds. So if you set 50ms per frame, this is equivalent to 20 frames per second.

ClickThrough

Indicates whether the user can click through the curtain while it is fading. This has no effect when not fading since the goal of the curtain is to hide what's going on behind. Useful when using a long fade duration since the user can interact with the new content immediately.

Limitations

Cannot resize the area while displaying the curtain. To avoid resize, I use the following code in the container form:

Before showing the curtain:

MinimumSize = this.Size;
MaximumSize = this.Size;

Once the curtain is hidden:

MinimumSize = new Size(0,0);
MaximumSize = new Size(0,0);

If your window cannot be resized, then this is not an issue for you.

Example project

The example project consists of two groups of listboxes that can be updated. One group using the curtain, and another that doesn’t. The example illustrates the problem when multiple UI components need to be refreshed: they cannot be refreshed all at the same time. If you find that the listbox update is not really a problem (since calling BeginUpdate and EndUpdate will hide intermediate results after all), imagine that instead of listboxes, we have some cool custom controls.

References

Conclusion

This “curtain technique” is lightweight and reusable whatever the UI components that need to be hidden are. I created it while working with the MSHTML component (the Microsoft HTML editor). I needed a way to hide all the webpage loading work, which is a little bit annoying when editing with a desktop application. Of course, I’m a professional.

License

This article has no explicit license attached to it but may contain usage terms in the article text or the download files themselves. If in doubt please contact the author via the discussion board below.

A list of licenses authors might use can be found here

About the Author

Mathieu Jacques
Web Developer
Canada Canada
Software Engineer working at a fun and smart startup company

Comments and Discussions

 
GeneralVery easy to use - thanks! PinmemberRavi Bhavnani7-Jul-11 10:12 
GeneralAwesome! PinmemberDiamonddrake14-Dec-10 16:16 
GeneralVERY INTERESTING PinmemberJohnny J.8-Oct-09 1:58 
GeneralRe: VERY INTERESTING PinmemberJohnny J.8-Oct-09 2:03 
GeneralForm is shown in Alt-Tab menu Pinmembermiggedy2-Jul-09 5:02 
GeneralUsing AnimateWindow instead of Opacity with timer PinmemberRobert Kindl11-Jun-09 4:28 
GeneralPROBLEM: Drawing content flickers through curtain Pinmemberrayinny1-Aug-07 15:43 
GeneralReturning to a previous window PinmemberMiki Watts4-Jun-07 20:03 
GeneralRe: Returning to a previous window PinmemberMathieu Jacques5-Jun-07 3:03 
QuestionCan't quite get this to work... PinmemberMiki Watts31-May-07 5:50 
AnswerRe: Can't quite get this to work... PinmemberMiki Watts31-May-07 6:44 
QuestionNice control - minor bug? PinmemberDavidjwong9-Apr-07 16:08 
AnswerRe: Nice control - minor bug? PinmemberMathieu Jacques10-Apr-07 3:22 
GeneralRe: Nice control - minor bug? PinmemberDavidjwong10-Apr-07 11:15 
GeneralBUG!! (If RightToLeft changed.) Pinmemberbrian.hawley24-Feb-07 16:21 
GeneralRe: BUG!! (If RightToLeft changed.) PinmemberMathieu Jacques26-Feb-07 3:22 
GeneralWin32Exception: The handle is invalid [Revisited] PinmemberIgor Velikorossov5-Feb-07 19:06 
GeneralRe: Win32Exception: The handle is invalid [Revisited] PinmemberMathieu Jacques6-Feb-07 3:30 
QuestionAutoClose feature / dispose resources ? PinmemberCarlosMMartins23-Jan-07 22:31 
AnswerRe: AutoClose feature / dispose resources ? PinmemberMathieu Jacques24-Jan-07 3:32 
GeneralRe: AutoClose feature / dispose resources ? PinmemberCarlosMMartins24-Jan-07 3:58 
GeneralRe: AutoClose feature / dispose resources ? PinmemberMathieu Jacques24-Jan-07 4:29 
GeneralRe: AutoClose feature / dispose resources ? PinmemberCarlosMMartins24-Jan-07 4:56 
Generalgood code Pinmembermohsen ahmadian21-Jan-07 20:10 
GeneralVery Fancy! Pinmembercrucify17-Jan-07 19:31 
GeneralGreat article PinmemberCarlosMMartins17-Jan-07 3:12 
GeneralCode Update - Thanks to Igor Velikorossov PinmemberMathieu Jacques15-Jan-07 3:20 
GeneralRe: Code Update - Thanks to Igor Velikorossov PinmemberQuentin Pouplard16-Jan-07 8:33 
GeneralRe: Code Update - Thanks to Igor Velikorossov PinmemberMathieu Jacques16-Jan-07 11:01 
GeneralWin32Exception: The handle is invalid [modified] PinmemberIgor Velikorossov10-Jan-07 14:09 
GeneralRe: Win32Exception: The handle is invalid PinmemberMathieu Jacques11-Jan-07 4:21 
GeneralRe: Win32Exception: The handle is invalid PinmemberIgor Velikorossov11-Jan-07 10:56 
Generaldual screen problem PinmemberFabrice Deshayes aka Xtream16-Dec-06 6:48 
GeneralRe: dual screen problem PinmemberMathieu Jacques18-Dec-06 3:51 
GeneralBegin/EndUpdate Method PinmemberRHarding_19-Dec-06 12:55 
GeneralRe: Begin/EndUpdate Method PinmemberQuentin Pouplard10-Dec-06 6:18 
GeneralRe: Begin/EndUpdate Method PinmemberMathieu Jacques10-Dec-06 9:46 
GeneralRe: Begin/EndUpdate Method PinmemberQuentin Pouplard11-Dec-06 9:51 
GeneralRe: Begin/EndUpdate Method PinmemberMathieu Jacques12-Dec-06 3:52 
GeneralCode update PinmemberMathieu Jacques9-Dec-06 4:42 
GeneralRe: Code update PinmemberQuentin Pouplard9-Dec-06 6:50 
GeneralProblem with code PinmemberH_R_O26-Sep-06 0:02 
GeneralRe: Problem with code PinmemberMathieu Jacques26-Sep-06 10:51 
GeneralRe: Problem with code PinmemberMathieu Jacques2-Oct-06 8:59 
GeneralRe: Problem with code PinmemberH_R_O12-Dec-06 21:59 
GeneralGreat! PinmemberCoyotelapa19-Sep-06 0:39 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.

| Advertise | Privacy | Mobile
Web03 | 2.8.140709.1 | Last Updated 14 Jan 2007
Article Copyright 2006 by Mathieu Jacques
Everything else Copyright © CodeProject, 1999-2014
Terms of Service
Layout: fixed | fluid