ListViewコントロールの操作


データが選択されたときに処理する

ListViewコントロールでデータが選択されると、ItemClickイベントが発生します。このとき、引数Itemには選択されたListItemオブジェクトが格納されます。

Private Sub ListView1_ItemClick(ByVal Item As MSComctlLib.ListItem)
    MsgBox Item & vbCrLf & Item.SubItems(1) & vbCrLf & Item.SubItems(2)
End Sub

また、現在選択されているデータはSelectedItemプロパティで取得できます。

データの削除

データを削除するには、ListItemsコレクションのRemoveメソッドを実行します。引数は、削除したいデータのIndex値です。ここでは、もう1つコマンドボタンを追加して、そちらに削除のコードを記述しました。

Private Sub CommandButton2_Click()
    With ListView1
        If MsgBox("現在選択されている " & .SelectedItem & " を削除しますか?", 36) = vbYes Then
            .ListItems.Remove .SelectedItem.Index
        End If
    End With
End Sub

                  ↓

データの変更

実行中にデータを変更するには、StartLabelEditメソッドを実行します。考え方はTreeViewコントロールと同じですから、詳しい解説は「TreeViewコントロール:Excelでの使用例」をご覧ください。

TreeViewコントロールと同様に、[F2]キーが押されたら、選択しているデータを編集するには、次のようにします。

Private Sub ListView1_KeyUp(KeyCode As Integer, ByVal Shift As Integer)
    If KeyCode = 113 Then ListView1.StartLabelEdit
End Sub

データを並べ替える

Windows標準のインターフェイスでは、ListViewコントロールを表形式で使うとき、列見出しをクリックするとデータがソートされます。ListViewコントロールに、データをソートする機能はありますが、クリックされた列で自動的にはソートできません。

まず、列をソートするには次のようにします。

  1. SortKeyプロパティに、ソートの基準となる列番号を指定する
  2. SortOrderプロパティに、ソートの並び順(昇順/降順)を指定する
  3. Sortedプロパティに、Trueを設定する

列見出しがクリックされるとColumnClickイベントが発生します。このとき、引数ColumnHeaderには、クリックされたColumnHeaderオブジェクトが格納されます。そこで、クリックされた列(ColumnHeaderオブジェクト)のIndex値-1をSortKeyプロパティに指定します。

次に、SortOrderプロパティに昇順(lvwAscending)か降順(lvwDescending)を指定して、SortedプロパティにTrueを指定します。

Private Sub ListView1_ColumnClick(ByVal ColumnHeader As MSComctlLib.ColumnHeader)
    With ListView1
        .SortKey = ColumnHeader.Index - 1
        .SortOrder = .SortOrder Xor lvwDescending
        .Sorted = True
    End With
End Sub

クリックされた列は引数ColumnHeaderに格納されます。注意しなければいけないのは、クリックされたColumnHeaderオブジェクトのIndex値と、SortKeyプロパティに指定する列の数え方です。ColumnHeaderオブジェクトのIndex値は、左端を1として数えますが、SortKeyプロパティに指定する列は左端を0から数えます。そこで、マイナス1(-1)しているわけです。

SortOrderプロパティに定数lvwAscendingを指定すると昇順でソートされ、定数lvwDescendingを指定すると降順でソートされます。定数lvwAscendingの実体は0で、定数lvwDescendingの実体は1です。

どちらかの定数を指定して、昇順または降順でソートするだけでもよいのですが、できれば「現在昇順だったら降順に、降順だったら昇順に」とトグル的に動作させたいです。だって、多くのアプリはそうなってるから。

SortOrderプロパティに、TrueまたはFlaseを指定するのでしたら簡単です。Not演算子を使って、

        .SortOrder = Not .SortOrder

とすればOKです。ところが、指定する定数はlvwAscending(0)かlvwDescending(1)。0か1です。ここでは「0だったら1、1だったら0」という処理を行う必要があります。まぁ、Ifとか使って、

        If .SortOrder = lvwAscending Then
            .SortOrder = lvwDescending
        Else
            .SortOrder = lvwAscending
        End If

みたくやってもいいのですが、なんか冗長で美しくありません。そこで、こんなときは排他的論理和のXor演算子を使います。排他的論理和についての詳細な解説は、ネットで数学系のサイトなどを検索してください。結果だけ言うと、次のように働く演算子です。

P Q P Xor Q
TRUE TRUE FALSE
TRUE FALSE TRUE
FALSE TRUE TRUE
FALSE FALSE FALSE

0 Xor 1は「1」、1 Xor 1は「0」となります。