Solved

Resizing form causes flicker/flashing

Posted on 2004-03-23
15
4,718 Views
Last Modified: 2007-12-19
Has anybody experience flickering when the form is being resized, minimized, or maximized? Very frustrating.

private void frmMain_Resize(object sender, System.EventArgs e)
{
   this.Width = this.Height * 2;
}
0
Comment
Question by:hobster
  • 6
  • 5
  • 4
15 Comments
 
LVL 1

Expert Comment

by:trojan2k
ID: 10658848
Hi,

You always get a certain amount of flickering, depending on how many widgets the form has, or if you are overriding the paint method, or you have any ownerdrawn components.

Instead of have that code in your resize eventhandler, why not simply set the frameborder to Fixed3D or FixedSingle ?
0
 
LVL 2

Author Comment

by:hobster
ID: 10659768
One of the requirements is that the user must be able to resize the form. When that happens, all the controls in it get resized also.

When it's resized, there is flicker. This is not the big problem. The big problem is when I minimize the form, then restore it, it flickers alot and then half the form disappears. If I minimize and then restore a 2nd time, you see the whole form. The same problem happens if I maximize the form.
0
 
LVL 1

Expert Comment

by:trojan2k
ID: 10660150
Does this flicker happen if you comment that code out of the resize event handler, and do you have Windows Animations turned on ?
0
 
LVL 2

Author Comment

by:hobster
ID: 10660261
If there's nothing inside the Resize event handler, then there's no flicker. How do I know if I have the animation turned on? I checked the form's properties and couldn't find anything related to it.
0
 
LVL 1

Expert Comment

by:trojan2k
ID: 10660425
I think its in other OSs too but I know how to fix it XP

Bring up the System properties, Go to Advanced and then choose Performance settings. At the top of the list is a check box that says Animate windows when minimizing and maximizing, try unchecking that and putting your code back in.

Because windows animates the frame as its restored, it actually resizes it a number of times, I suspect that because your code is overriding the normal resize and triggering a resize at the same time that windows is resizing your form, it's giving GDI a headache.
0
 
LVL 10

Expert Comment

by:eternal_21
ID: 10660742
Are you specifically trying to maintain a contant aspect ratio for your form (length/width), or are you doing something else in the resize event?
0
 
LVL 2

Author Comment

by:hobster
ID: 10660787
I'm using Win2k Server and can't find this setting.
0
Do You Know the 4 Main Threat Actor Types?

Do you know the main threat actor types? Most attackers fall into one of four categories, each with their own favored tactics, techniques, and procedures.

 
LVL 1

Expert Comment

by:trojan2k
ID: 10660957
0
 
LVL 2

Author Comment

by:hobster
ID: 10661184
I'll have a look at the program.

eternal,

Yes, I'm just trying to resize the form and its controls (buttons, labels, fonts), nothing special. There are a couple of properties that look promising (ex. docking) but after playing with them, I found they weren't adequate. I've searched the web and this flickering problem is pretty prominent but I couldn't find a definite solution.
0
 
LVL 10

Accepted Solution

by:
eternal_21 earned 50 total points
ID: 10661186
Instead of putting your code in the Resize event handler try the following.  Add this code to your form class:

### C#.NET ###

    protected override void WndProc(ref Message m)
    {
      const int WM_EXITSIZEMOVE = 0x232;
      switch(m.Msg)
      {
        case WM_EXITSIZEMOVE:
          ExitSizeMove();
          break;
        default:
          break;
      }
      base.WndProc(ref m);
    }

    void ExitSizeMove()
    {
      // Put your code here.  This code will be called when
      // you form has finished resizing or moving.  It will
      // not be called when the form is maximized or
      // minimized.
      // e.g.:
      // this.Width = this.Height * 2;
    }

###

Call the ExitSizeMove method in your constructor or load event to make sure that the form is sized correctly on startup (if you are setting the height based on the width).
0
 
LVL 2

Author Comment

by:hobster
ID: 10664602
eternal,

When I click the Maximize button, the form's controls didn't get resized. Do you know how to get that working? Thanks.
0
 
LVL 10

Expert Comment

by:eternal_21
ID: 10664658
Just letting you know I received your post - working on it right now!
0
 
LVL 10

Expert Comment

by:eternal_21
ID: 10664883
Okay, here is the new code!  Note that the base.WndProc calls have changed their location because the WM_SYSCOMMAND must be processed by the form BEFORE we try and access the form's size from the FormResized method.

### C#.NET ###

  protected override void WndProc(ref Message m)
  {
    const int WM_EXITSIZEMOVE = 0x232;
    const int WM_SYSCOMMAND = 0x112;

    switch(m.Msg)
    {
      case WM_EXITSIZEMOVE: // Form is moved or resized

        base.WndProc(ref m);
        FormResized();
        break;

      case WM_SYSCOMMAND: // System command (maximize, minimize, restore, etc.)

        base.WndProc(ref m);
       
        const int SC_MAXIMIZE = 0xF030;
        const int SC_MINIMIZE = 0xF020;
        const int SC_RESTORE = 0xF120;

        switch(m.WParam.ToInt32())
        {
          case SC_MAXIMIZE: // Form is maximized by control
          case SC_MAXIMIZE + 2: // Form is maximized by title bar
            FormResized();
            break;

          case SC_MINIMIZE: // Form is minimized by control
            //FormResized();
            break;

          case SC_RESTORE: // Form is restored by control
          case SC_RESTORE + 2: // Form is restored by title bar
            FormResized();
            break;

          default:
            break;
        }
        break;

      default:

        base.WndProc(ref m);
        break;
    }
  }

  void FormResized()
  {
    // Put your code here.  This code will be called when
    // you form has finished resizing or moving, has been
    // maximized, or restored.  Remove the comments
    // above and it will be called when minimized as well.
    // e.g.:
    // this.Width = this.Height * 2;
  }

###

Just out of curiosity, are you actually controlling the aspect ratio of your form (e.g.: this.Width = this.Height * 2)?
0
 
LVL 2

Author Comment

by:hobster
ID: 10672556
Cool, it works. And yes, I am controlling the form's aspect ratio. Thanks very much.
0
 
LVL 10

Expert Comment

by:eternal_21
ID: 10680795
I don't know if this is any help, but I thought the "aspect ratio" was a cool idea for a winform...  The problem with this.Width = this.Height * 2, is found when you try and change the Width of the form... nothing happens!  I thought we could watch the form and see which direction changed the most (length or width) and then size the form accordingly.  Here is what I came up with:

    private System.Drawing.Size prevSize;

    protected override void OnLoad(EventArgs e)
    {
      this.prevSize = this.Size;
      // OnLoad implementation
      base.OnLoad (e);
    }

    void ExitSizeMove()
    {
      const double aspectRatio = 2d; // 2:1 aspect ratio

      double prevSizeHRatio, prevSizeWRatio;
      prevSizeHRatio = (double)this.Height / (double)this.prevSize.Height - 1;
      prevSizeWRatio = (double)this.Width / (double)this.prevSize.Width - 1;
      if(Math.Abs(prevSizeHRatio) > Math.Abs(prevSizeWRatio))
        this.Width = (int)((double)this.Height * aspectRatio);
      else
        this.Height = (int)(this.Width / (double)aspectRatio);
      this.prevSize = this.Size;
    }

I also wrote a function to resize a form to a specific aspect ratio with the same area: (This one was my first attempt...)

    void SetAspectRatio(double ratio)
    {
      double x, y;
      x = Math.Sqrt(this.Size.Width * this.Size.Height * ratio);
      y = x / ratio;
      this.Size = new System.Drawing.Size((int)x, (int)y);
    }

you can call it like: SetAspectRatio(2d), but I didn't like the way it worked when resizing the form.  The only thing that SetAspectRatio would be good for is to call in the OnLoad method BEFORE you initialize your prevSize variable.
0

Featured Post

IT, Stop Being Called Into Every Meeting

Highfive is so simple that setting up every meeting room takes just minutes and every employee will be able to start or join a call from any room with ease. Never be called into a meeting just to get it started again. This is how video conferencing should work!

Join & Write a Comment

Introduction                                                 Was the var keyword really only brought out to shorten your syntax? Or have the VB language guys got their way in C#? What type of variable is it? All will be revealed.   Also called…
Introduction Hi all and welcome to my first article on Experts Exchange. A while ago, someone asked me if i could do some tutorials on object oriented programming. I decided to do them on C#. Now you may ask me, why's that? Well, one of the re…
Excel styles will make formatting consistent and let you apply and change formatting faster. In this tutorial, you'll learn how to use Excel's built-in styles, how to modify styles, and how to create your own. You'll also learn how to use your custo…
This video explains how to create simple products associated to Magento configurable product and offers fast way of their generation with Store Manager for Magento tool.

759 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

16 Experts available now in Live!

Get 1:1 Help Now