コンボボックスをViewModelのコレクションにバインドする標準のwpf/mvvmアプリケーションを使用しています。
ドロップダウンからアイテムの選択を解除できるようにする必要があります。つまり、ユーザーは何かを選択でき、後でその選択を解除する(何も選択しない)ことを決定できる必要があります。問題は、バインドされたコレクションに空の要素がないことです
私の最初の考えは、コレクションに新しいアイテムを挿入することでした。その結果、コレクションの上に空のアイテムが表示されます。
ただし、これはハックであり、ビューモデルでそのコレクションを使用するすべてのコードに影響します。
たとえば誰かが書くことになった場合
_myCollection.Frist(o => o.Name == "foo")
これにより、null参照例外がスローされます。
考えられる回避策は次のとおりです。
_myCollection.Where(o => o != null).First(o => o.Name == "foo");
これは機能しますが、そのコレクションを将来使用しても中断が発生しないことを保証する方法はありません。
ユーザーが選択を解除できるように空のアイテムを追加できるようにするための良いパターン/ソリューションは何ですか。(私はCollectionView構造も知っていますが、それは非常に単純なものにはやり過ぎのようです)
アップデート
@hbarckの提案を採用し、CompositeCollectionを実装しました(概念実証)
public CompositeCollection MyObjects {
get {
var col = new CompositeCollection();
var cc1 = new CollectionContainer();
cc1.Collection = _actualCollection;
var cc2 = new CollectionContainer();
cc2.Collection = new List<MyObject>() { null }; // PROBLEM
col.Add(cc2);
col.Add(cc1);
return col;
}
}
このコードは、既存のバインディング(SelectedItemを含む)で機能します。これはすばらしいことです。
これに関する1つの問題は、アイテムが完全にnullの場合、SelectedItemセッターが選択時に呼び出されないことです。
その1行をこれに変更すると:
cc2.Collection = new List<MyObject>() { new MyObject() }; // PROBLEM
セッターが呼び出されますが、選択したアイテムはnullではなく基本的な初期化クラスになります。セッターにコードを追加してチェック/リセットすることはできますが、それは良くありません。