SATOXのシテオク日記

~ふもっふ、ふもふも~

ListViewの仮想表示モード その2

さてさて、興味のない方には申し訳ないですけども、本日もListViewのVirtualModeのネタです。
なんとか選択されているListViewItemの取得が出来るようになりました。

■選択アイテムの問題
キモとなるのは次の2点。
(1)「ListView.ListViewItemCollection」でコレクションの保持
(2)「ListView.SelectedIndexCollection」でセレクションの保持
通常のListViewがListViewItemを管理するためにしていること仮想表示モードでは「ユーザがやる」ということになりそうです。
具体的には以下のサンプルを参照。
デザインソースは割愛されているので適宜作成して貼り付けて下さい。登場人物としては、次の通り。
ListView listViewVirtual;
ListView.ListViewItemCollection listViewItemCollection;
ListView.SelectedIndexCollection listViewItemSelection;

public partial class Form1 : Form
{
  private ListViewItem[] listViewItem = new ListViewItem[10000];
  private ListView.ListViewItemCollection listViewItemCollection;
  private ListView.SelectedIndexCollection listViewItemSelection;

  public Form1()
  {
    InitializeComponent();
    InitializeListView();
  }

  private void InitializeListView()
  {
    this.listViewItemCollection = new ListView.ListViewItemCollection(this.listViewVirtual);
    this.listViewItemSelection = new ListView.SelectedIndexCollection(this.listViewVirtual);
    this.listViewVirtual.VirtualMode = true;
    this.listViewVirtual.VirtualListSize = listViewItem.Length;

    for (Int32 lp = 0; lp < listViewItem.Length; lp++) {
      listViewItem[lp] = new ListViewItem("item" + lp.ToString());
    }
  }

  private void listViewVirtual_RetrieveVirtualItem(object sender, RetrieveVirtualItemEventArgs e)
  {
    e.Item = this.listViewItem[e.ItemIndex];
  }

  private void listViewVirtual_SelectedIndexChanged(object sender, EventArgs e)
  {
    if (this.listViewItemSelection.Count > 0) {
      Console.WriteLine("---- ListViewItem Selection ----");
      foreach (Int32 index in this.listViewItemSelection) {
        Console.WriteLine(String.Format("index = {0} : {1}", 
            index.ToString(), this.listViewItemCollection[index]));
      }
    }
  }
}

SelectedIndexChangedイベント関数内で選択されているListViewItemを取得することが出来ます。

■アイテムを選択させるには
では、プログラムからアイテムを選択させるにはどうしたらいいのでしょうか。
「選択できねー」とずっと悩んでいたのですが、ボタン押下時に選択させていたため、コントロールのフォーカスが移って選択状態が無効になっていたのが問題でした(笑)。
HiddenSelectionプロパティをFalseにするか、選択時にListViewにフォーカスを当てる必要があるわけです。

  private void button1_Click(object sender, EventArgs e)
  {
  	this.listViewVirtual.Focus();
  	// Select 10 listview items
  	for (Int32 lp = 0; lp < 10; lp++) {
    this.listViewItemSelection.Add(lp);
//    this.listViewVirtual.SelectedIndices.Add(lp);
//    this.listViewItem[lp].Selected = true;
	}
  }

「this.listViewItemSelection.Add」でも「this.listViewVirtual.SelectedIndices.Add」でも「this.listViewItem[n].Selected」でも選択可能です。SelectedIndexChangedイベントもしっかり来ます。
あとは、今のシステムにどうやって入れるか……大改造が必要かも。。。



あれ?ListViewItemCollectionはいらない??