How to fix flicker in a WinForms form?

2019-01-17 21:43发布

I am constantly drawing frames, and I need the form to not flicker. How do I accomplish this?

public partial class Form1 : Form
{
    Image[] dude = new Image[3];
    static int renderpoint = 0;
    int lastimage = 0;

    public Form1()
    {
        dude[1] = new Bitmap(@"snipe1.bmp");
        dude[0] = new Bitmap(@"snipe0.bmp");

        InitializeComponent();
    }

    private void Form1_Shown(object sender, EventArgs e)
    {
        MainLoop();
    }

    private void MainLoop()
    {
        double FPS = 10;

        long ticks1 = 0;
        long ticks2 = 0;
        double interval = (double)Stopwatch.Frequency / FPS;

        while (true)
        {
            ticks2 = Stopwatch.GetTimestamp();
            if (ticks2 >= ticks1 + interval)
            {
                ticks1 = Stopwatch.GetTimestamp();

                MoveGraphics();
                this.Refresh(); 
            }

            Thread.Sleep(1); 
        }
    }

    private void Form1_Paint(object sender, PaintEventArgs e)
    {
        Graphics g = e.Graphics;
        Rectangle rect = new Rectangle(renderpoint, 0, 100, 100);
        Color lowcolor = Color.FromArgb(0, 128, 64);
        Color highcolor = Color.FromArgb(0, 128, 64);

        ImageAttributes imageAttr = new ImageAttributes();
        imageAttr.SetColorKey(lowcolor, highcolor);

        if (lastimage == 1)
        {
            lastimage = 0;
            g.DrawImage(dude[1], rect, 0, 0, 100, 100, GraphicsUnit.Pixel, imageAttr);
        }
        else
        {
            lastimage = 1;
            g.DrawImage(dude[0], rect, 0, 0, 100, 100, GraphicsUnit.Pixel, imageAttr);
        }  
    }

    void MoveGraphics()
    {
        if (renderpoint > 950)
        {
            renderpoint = 0;
        }
        else
        {
            renderpoint += 10;
        }
    }
}

There's the current code. Suggestions?

2条回答
【Aperson】
2楼-- · 2019-01-17 22:17

Paste this into your Form1 constructor:

this.DoubleBuffered = true;
查看更多
冷血范
3楼-- · 2019-01-17 22:27
  1. Do your rendering in the Paint event handler
  2. Disable automatic erasing of the background.
  3. Enable double buffering either via the Styles or manually.
  4. When you want to repaint, call Invalidate

If you're trying to pull of smooth animation, then may I recommend jumping ship to WPF, OpenGL, or XNA. GDI+ was not designed for animation (the Windows message loop is not a real-time system, so you will always have jittering).

查看更多
登录 后发表回答