1. ホーム
  2. .net

[解決済み] 2画面のうち1画面のDataGridViewのひどい再描画パフォーマンス

2023-06-20 05:16:14

質問

実は解決しているのですが、後学のために投稿します。

私は、デュアル モニター システム上の DataGridView で非常に奇妙な問題に遭遇しました。この問題は、コントロールの再描画が非常に遅くなることとして現れます ( 完全な再描画に 30 秒かかるような ) が、片方の画面に表示されているときだけです。もう一方の画面では、再描画の速度は正常です。

私は Nvidia 8800 GT と最新の非ベータ ドライバ (175. something) を使用しています。ドライバのバグなのでしょうか?私はこの特殊な構成で生活しなければならないので、それは空中に置いておきます。(ATIカードでは発生しませんが...)

描画速度はセルの内容とは関係なく、カスタム描画はまったくパフォーマンスを向上させません - 単なるベタ長方形の描画の場合でも。

ElementHost (System.Windows.Forms.Integration 名前空間) をフォームに配置すると、問題が修正されることが後でわかりました。それはいじくり回す必要はなく、DataGridView があるフォームの子であればよいのです。また、サイズも 可視 プロパティが真である限り、(0, 0)にサイズ変更することができます。

私は、アプリケーションに.NET 3/3.5の依存関係を明示的に追加したくありません。私は、反射を使用して実行時にこのコントロールを作成するメソッドを作成します(もし可能であれば)。それは動作し、少なくとも、必要なライブラリを持っていないマシン上では優雅に失敗し、ただ遅くなることに戻ります。

この方法はまた、アプリの実行中に修正を適用することができ、WPF ライブラリが私のフォーム上で何を変更しているかを簡単に見ることができます (Spy++ を使用します)。

多くの試行錯誤の後、(フォームだけでなく) コントロール自体でダブル バッファリングを有効にすると、問題が修正されることに気づきました!


したがって、DataGridViewをベースとしたカスタムクラスを作成し、そのダブルバッファリングを有効にする必要があります。これだけです。

class CustomDataGridView: DataGridView
{
    public CustomDataGridView()
    {
        DoubleBuffered = true;
    }
}

グリッドのすべてのインスタンスがこのカスタムバージョンを使用している限り、すべてはうまくいきます。もし、これが原因でサブクラスのソリューションを使用できない状況に陥った場合 (コードがない場合)、そのコントロールをフォームに注入してみることもできると思います :) ( とはいえ、依存関係をもう一度避けるために、リフレクションを使用して外部から DoubleBuffered プロパティを強制的に適用しようとする可能性が高いでしょう。 ).

このような些細なことが私の時間の多くを費やしたことは悲しいことです...。

どのように解決するのですか?

DataGridViewをベースにしたカスタムクラスを作成し、DoubleBufferingを有効にする必要があります。それだけです。


class CustomDataGridView: DataGridView
{
    public CustomDataGridView()
    {
        DoubleBuffered = true;
    } 
}

グリッドのすべてのインスタンスがこのカスタムバージョンを使用している限り、すべてはうまくいきます。もし、サブクラスのソリューションを使用できないような状況に陥った場合 (コードがない場合)、そのコントロールをフォームに注入することができると思います :) 。(しかし、私は、もう一度依存を避けるために、外部からDoubleBufferedプロパティを強制するためにリフレクションを使用することを試みる可能性が高いでしょう)。

このような些細なことが私の時間の多くを費やしたことは悲しいことです...。

注:回答を答えにすることで、質問に回答済みと表示できるようにすること