none
WPF DataGrid.SelectedItemsコレクションを解析したい RRS feed

  • 質問

  •  

        WPF DataGridで選択された複数の行を削除するプログラムを作成しています。

      Dim i As Integer

      i = Me.DataGrid1.SelectedItems.Count 'これは読み取れている

      'Me.DataGrid1.SelectedItemsのコレクションを読み取りたい
      Debug.Print(Me.DataGrid1.SelectedItems.GetType.FullName)
      '結果:System.Windows.Controls.SelectedItemCollection

      '↓ コンパイルエラーが出る
       Dim ar1 As System.Windows.Controls.SelectedItemCollection      
       'エラー    1    'System.Windows.Controls.SelectedItemCollection' は 'Friend' であるため、
       'このコンテキストではアクセスできません。   

    これをコレクションととして読み取ることができれば、行を削除することができると考えていますが、読み取る方法がわかりません。解決方法を御教授下さい。
    よろしくお願い致します。

    2017年1月8日 7:10

回答

  • 失礼いたしました。以下のコードでとりあえず動いています。

    Dim selectedItems = Me.dataGrid.SelectedItems
    
    Dim items As Array = Array.CreateInstance(GetType(DataRowView), selectedItems.Count)
    
    Me.dataGrid.SelectedItems.CopyTo(items, 0)
    
    For Each item As DataRowView In items
        item.Row.Delete()
    Next
    
    Me.dataGrid.ItemsSource = Nothing
    Me.dataGrid.ItemsSource = table.DefaultView
    もし、table.DefaultViewをItemsSourceに直接与えるのではなく、バインディングを使っているのであれば、そこは読み替えて下さい。


    ★良い回答には回答済みマークを付けよう! MVP - .NET  http://d.hatena.ne.jp/trapemiya/

    2017年1月10日 3:16
    モデレータ

すべての返信

  • Me.DataGrid1.SelectedItemsが正にコレクションですので、このコレクションの要素を全て削除すれば良いですよ。
    DataGridにどのように要素を渡しているのかわかりませんので、具体的な削除方法はアドバイスできませんが、通常はデータソース側で削除します。

    ★良い回答には回答済みマークを付けよう! MVP - .NET  http://d.hatena.ne.jp/trapemiya/

    2017年1月8日 7:17
    モデレータ
  • 少し具体例を出しておきます。

    SelectedItemsを元に削除すると、削除する度にSelectedItemsが変化することになり、うまく行かなくなるんじゃないかと思います。
    よって、SelectedItemsをまずコピーし、そのコピーを削除リストとして、それに従って削除すれば良いです。

    以下の例はLINQで処理していますが、考え方は同じです。

    Collection was modified when trying to remove selected items of datagrid
    http://stackoverflow.com/questions/29675086/collection-was-modified-when-trying-to-remove-selected-items-of-datagrid

    LINQに不慣れな場合は、以下のようにしてみて下さい。ただし、コード未検証です。

    dim items = Me.DataGrid1.SelectedItems
    
    For Each item In items
        DtataGridのデータソース元.Remove(item)
    Next


    ★良い回答には回答済みマークを付けよう! MVP - .NET  http://d.hatena.ne.jp/trapemiya/


    2017年1月8日 7:37
    モデレータ
  • 御回答ありがとうございます。

    DataGrid1.ItemsSourceはSQLサーバーから読み取ったので、DataView形式です。

    Dim tbv As  DataView
     
    tbv = Me.DataGrid1.ItemsSource

    For Each item In items
        tbv.Remove(item)
    Next

    教えていただいたコーディングを行うと、上の様になると思いますが、DataViewにはRemoveメソッドがなく、コンパイルできません。
    どうしたら良いでしょうか。

    2017年1月8日 8:13
  • itemはおそらくDataRowView型だと思いますので、そのRowプロパティがデータテーブルの行を指しています。
    よって以下のどちらかで削除することになります。
    item.Row.Delete()
    または、
    データテーブル.Rows.Remove(item.Row)

    後でデータベース上からも削除するのであれば、Deleteメソッドを使って下さい。詳しくは以下を参考にして下さい。

    DataRow の削除
    https://msdn.microsoft.com/ja-jp/library/03c7a3zb.aspx

    #出先なものでコードの検証ができず申し訳ないです。


    ★良い回答には回答済みマークを付けよう! MVP - .NET  http://d.hatena.ne.jp/trapemiya/


    2017年1月8日 10:15
    モデレータ
  • trapemiyaさん、御回答ありがとうございます。

    教えていただいた方法では結局コンパイルが通らず、以下の様にして解決しました。

            Dim i, j As Integer
            Dim tbv As DataView

            tbv = Me.DataGrid1.ItemsSource
            tbv.AllowDelete = True

            '選択された行のコレクション
            Dim items = Me.DataGrid1.SelectedItems

            For j = items.Count - 1 To 0 Step -1
                For i = tbv.Count - 1 To 0 Step -1
                    If tbv.Item(i) Is items(j) Then
                        tbv.Delete(i)   'これ以外に行を消す方法は見つからない
                        Exit For
                    End If
                Next
            Next

    どうもありがとうございました。

    2017年1月10日 2:38
  • 失礼いたしました。以下のコードでとりあえず動いています。

    Dim selectedItems = Me.dataGrid.SelectedItems
    
    Dim items As Array = Array.CreateInstance(GetType(DataRowView), selectedItems.Count)
    
    Me.dataGrid.SelectedItems.CopyTo(items, 0)
    
    For Each item As DataRowView In items
        item.Row.Delete()
    Next
    
    Me.dataGrid.ItemsSource = Nothing
    Me.dataGrid.ItemsSource = table.DefaultView
    もし、table.DefaultViewをItemsSourceに直接与えるのではなく、バインディングを使っているのであれば、そこは読み替えて下さい。


    ★良い回答には回答済みマークを付けよう! MVP - .NET  http://d.hatena.ne.jp/trapemiya/

    2017年1月10日 3:16
    モデレータ