web-dev-qa-db-ja.com

WPF DataGridのレンダリングが非常に遅い

カスタマイズされたDataGridとWPFの標準のDataGridの両方を使用してみました。私はそれらを手作業で、そしてバインディングを通して投入しようとしました。どちらの場合でも、それらは遅いです。

ユーザーがボタンをクリックし、適切なデータを含むDataGridが表示されるシーンがあります。現在、概念実証モードであり、サンプルデータのみを使用しています。 10行のテーブルを持つDataSetがあります。

ボタンをクリックしたときにDataGridにデータを添付しないと、空のDataGridがすぐに表示され、ユーザーは遅延を知覚できません。 10行(6列)のデータを追加するとすぐに、遅延は約2秒であり、ユーザーには非常に顕著です。

空のグリッドを表示するためだけに、空のデータを入力することも試みましたが、同じくらい遅いです。

for (int i = 0; i < 10; i++)
    _dataGrid.Items.Add("");

ボタンがクリックされてからDataGridを描画するためにすべてのコードが実行されるまでのティックをカウントするタイマーを配置します。これは約20ミリ秒なので、コードは非常に高速に実行されますが、画面上では大きな遅れが発生します。 GridViewを試してみましたが、画面上で非常に高速にレンダリングされます。

複雑なシナリオを使用し、数千の行を使用する低速のDataGrid描画のさまざまなレポートを聞いたことがありますが、これは空のデータで満たされた6列10行のように簡単です。

読み取り専用表示の場合、GridViewはDataGridの同様に実行可能なオプションですか?


更新

これが私のコラムの作成です。

                DataGridTextColumn column = new DataGridTextColumn();
                column.ColumnWidthChanged += new ColumnWidthChangedEventHandler(column_ColumnWidthChanged);

                column.Header = entity.GetPropertyValue("ColumnLabel");
                column.Binding = new Binding(entity.GetPropertyValue("Tag"));
                column.Width = new DataGridLength(entity.GetPropertyDouble("DisplaySize"));
                _dataGrid.Columns.Add(column);

これは、10行のDataSetをバインドする方法です。

                _dataGrid.ItemsSource = ds.Tables[0].DefaultView;
                _dataGrid.DataContext = ds.Tables[0];

何が違うかわからない。

32
David Gunther

あなたは持っています:

  • 有効VirtualizingStackPanel.VirtualizationModeグリッドの場合?そうでない場合-設定してみてください。
  • DataGridにVirtualizingStackPanel.IsVirtualizing = "true"を設定します
  • StackPanelコンテナでグリッドをラップしましたか?はいの場合-削除してみてください。
  • 外部のScrollViewerコントロールによってグリッドをラップしましたか?はいの場合-削除してみてください。

もう1つのポイントは、grid.Itemsコレクションに各アイテムを追加する代わりに、アイテムコレクション全体を一度にバインドできますか?

32
sll

DataGridパフォーマンスの問題に関する一般的なヒント:DataGridに問題があり、ウィンドウのサイズ変更、列の並べ替えなどの後、文字通り更新に数秒かかり、実行中にウィンドウUIをロックしました( 1000行、5列)。

WPFのサイジング計算に関する問題(バグ?)になりました。 RowDefinitionHeight="Auto"を使用してグリッドに配置しました。これにより、おそらくすべての列と行のサイズを測定することにより、実行時にDataGridのサイズを再計算しようとしました(私が理解しているように)グリッド全体を埋めます。これを何らかの方法でインテリジェントに処理することになっていますが、この場合はそうではありません。

これが関連する問題であるかどうかを簡単に確認するには、テスト中にDataGridのHeightプロパティとWidthプロパティを固定サイズに設定し、再度実行してみます。パフォーマンスが回復した場合、次のオプションの中に永続的な修正が含まれる場合があります。

  • 含まれる要素のサイズを相対(*)または固定値に変更します
  • DataGridのMaxHeightおよびMaxWidthを、通常の使用で得られるよりも大きい固定値に設定します
  • 異なるサイズ変更戦略(GridDockPanelなど)で別のコンテナタイプを試してください。
24
TripleAntigen

ブログ Googleで見つけたのは、ある種の解決策を提供してくれました。著者が言ったように、私はGroupStyleを無効にし、レンダリング速度の問題は解決しました。しかし、グループ化が必要でした。著者は言った

VirtualizingPanel.IsVirtualizingWhenGrouping

.NET 4.5に追加されます。だから私はそれをtrueに設定しました。グループ化により、レンダリングが高速になりました。問題は...スクロールがぎくしゃくしていることです。容認できないほどぎくしゃくではなく、顕著にぎくしゃくしています。 2000以上のノードを展開してTreeViewを作成しようとしたときに、同様の問題が発生しました。仮想化なしでは、レンダリングは遅くなりましたが、スクロールはスムーズでした。仮想化では、レンダリングは高速でしたが、スクロールはぎくしゃくしていました。

なぜ私たちは両方を持てないのですか...

12
Damn Vegetables

私の場合、DataGridCell ControlTemplateでレンダリング速度が遅くなる問題がありました。

TextBlock(選択可能なテキストではない)またはTextBoxを読み取り専用モードで使用する場合、大きなデータセットの相対的な読み込み速度は大きく異なることに注意してください。

読み込み時間59秒:

<Style TargetType="{x:Type DataGridCell}" x:Key="DataGridCellTextStyle">
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type DataGridCell}">
                    <TextBox IsReadOnly="True" Text="{Binding Mode=OneWay}"/> 
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>

読み込み時間21秒:

<Style TargetType="{x:Type DataGridCell}" x:Key="DataGridCellTextStyle">
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type DataGridCell}">
                     <ContentPresenter Content="{Binding}" />
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>

読み込み時間16秒:

<Style TargetType="{x:Type DataGridCell}" x:Key="DataGridCellTextStyle">
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type DataGridCell}">
                    <TextBlock Text="{Binding}"></TextBlock>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>
10
Evalds Urtans

まあ少し追加(私はその非常に古いトピックを知っていますが、それでも誰かを助けます)...

私は試した

EnableColumnVirtualization="True" VirtualizingPanel.VirtualizationMode="Recycling"
EnableRowVirtualization="True" 

dataGrid(AutoGenerateColumns="True")DataTable.DefaultView()にバインドし、速度に影響を与えませんでしたが、速度と行間のナビゲーションには依然として恐ろしいものでした。それより、DataGridの固定の高さと幅を設定するソリューションを思いつきました。さらに、私も設定します

RowHeight="23" 
ScrollViewer.HorizontalScrollBarVisibility="Visible"
ScrollViewer.VerticalScrollBarVisibility="Visible"

これにより、私のページは非常に高速に塗りつぶされます... 2分ではなく、10〜12秒かかります。

それが誰かを助けることを願っています。

注:.Net 4.5を使用しています

4
Nirav Raval

約200行10列のdatagridのスクロールが非常に遅く、ぎくしゃくしてためらいがあったSurface Pro 3があります。

私はそれがネットワークだと思っていましたが、実際には、コントロールの背景が無地に設定されていても、グラフィックスカードがデータグリッド自体のドロップシャドウ効果に追いつくことができませんでした。

私はその効果をコメントアウトし、4〜5倍速くなりました。

お役に立てれば。

1
user3515346

私にとっては:

<Setter Property='ScrollViewer.CanContentScroll' Value='False' />

これをスタイルから削除すると、レンダリングが高速になりました。

1
waxingsatirical

私は1000行5列でレンダリングに7-10秒かかっていたという大きな問題を抱えていましたが、解決策は https://www.elegant-software.net/2014/05/performance-of -the-wpf-datagrid.html グリッドを即座にロードしました!

<DataGrid
   EnableRowVirtualization="True"
   EnableColumnVirtualization="True">
1
Nick

バインドされたデータグリッドにも同じ問題があり、最初の読み込みでは高速ですが、2番目と2番目の読み込みでは遅いことがわかります。コードを追加すると

_DataGrid.ItemsSource = Nothing_そしてTableAdapter.Fill(Mydataset.MyStoredProcedure,....) DataGrid.ItemsSource=Mydataset.MyStoredProcedureそれは非常に高速になりました

0
SLAVICA