web-dev-qa-db-ja.com

Windowsフォームアプリのちらつき

たくさんのコントロールを備えたアプリがあります。また、特に起動時に大量のちらつきが発生します。

私はこれを適用しました 修正 それに。

    protected override CreateParams CreateParams
    {
        get
        {
            CreateParams cp = base.CreateParams;
            cp.ExStyle |= 0x02000000;   // WS_EX_COMPOSITED
            return cp;
        }
    } 

これはうまく機能しました-ちらつきはかなり信じられないほど減少しました。ただし、副作用として、ウィンドウの右上にある[最小化]、[最大化]、および[閉じる]ボタンは、マウスを移動したりクリックしたりしてもアニメーション化されません(ただし、これらは機能します)。これにより、アプリにハング感が生じます。

最大化、最小化、および閉じるボタンの使いやすさを維持しながら、WS_EX_COMPOSITEDを維持するにはどうすればよいですか?

これはWindowsXPで発生します。 @fallenidolが指摘したように、これはWindows7の問題ではありません。

22
AngryHacker

私はそれを考え出した。秘訣は、フォームが表示された後にWS_EX_COMPOSITEDフラグを削除することです。私のブログでの完全な説明とコード:

Windowsフォームアプリケーションでちらつきを取り除く方法

14
AngryHacker

私はこの質問が少し古いことを知っていますが、決して遅くなるよりはましです。リンクした元の例を使用して、サイズ変更時にオンに切り替え、次にオフに切り替えて他のすべてを完全に描画する例を考え出しました。うまくいけば、それは他の人がこの問題の解決策を探すのに役立つでしょう。 OPが知っているように、DoubleBufferingだけのプロパティでは、ちらつきの問題は解決されません。

これは、ユーザーがフォームのサイズを変更したときにちらつきを停止するための回避策ですが、DataGridView、NumericUpDownなどのコントロールの描画を台無しにすることはありません。フォーム名が「Form1」の場合:

int intOriginalExStyle = -1;
bool bEnableAntiFlicker = true;

public Form1()
{
    ToggleAntiFlicker(false);
    InitializeComponent();
    this.ResizeBegin += new EventHandler(Form1_ResizeBegin);
    this.ResizeEnd += new EventHandler(Form1_ResizeEnd);
}

protected override CreateParams CreateParams
{
    get
    {
        if (intOriginalExStyle == -1)
        {
            intOriginalExStyle = base.CreateParams.ExStyle;
        }
        CreateParams cp = base.CreateParams;

        if (bEnableAntiFlicker)
        {
            cp.ExStyle |= 0x02000000; //WS_EX_COMPOSITED
        }
        else
        {
            cp.ExStyle = intOriginalExStyle;
        }

        return cp;
    }
} 

private void Form1_ResizeBegin(object sender, EventArgs e)
{
    ToggleAntiFlicker(true);
}

private void Form1_ResizeEnd(object sender, EventArgs e)
{
    ToggleAntiFlicker(false);
}

private void ToggleAntiFlicker(bool Enable)
{
    bEnableAntiFlicker = Enable;
    //hacky, but works
    this.MaximizeBox = true;
}
8
John Suit

次のコードを試してください。これは、メインフォームとその他のカスタムユーザーコントロールで行う必要があります。

        // Enable double duffering to stop flickering.
        this.SetStyle(ControlStyles.DoubleBuffer, true);
        this.SetStyle(ControlStyles.AllPaintingInWmPaint, true);
        this.SetStyle(ControlStyles.UserPaint, true);
        this.SetStyle(ControlStyles.SupportsTransparentBackColor, false);
        this.SetStyle(ControlStyles.Opaque, false);
        this.SetStyle(ControlStyles.OptimizedDoubleBuffer, true);
        this.SetStyle(ControlStyles.ResizeRedraw, true);
4
pmcilreavy

この投稿に出くわしたところ、少し古いことに気づきました。しかし、私は自分のフォームで同じ問題を抱えており、(とにかくXPの場合)エレガントでないソリューションが視覚スタイルを有効にしていないように見えることを発見しました。

0
Tebc

DoubleBufferedと呼ばれる標準のWindowsフォームコントロールプロパティを試してみてください。 http://msdn.Microsoft.com/en-us/library/system.windows.forms.control.doublebuffered.aspx

0
Kru