4

I'm attempting to bind a Dictionary to a ListView who's item template constist of a grid with 2 textboxes. Ideally I'd like to be able to modify both the key and the value of the KeyValuePair displayed in the ListView . Is that possible?

Vadim Kotov
  • 8,084
  • 8
  • 48
  • 62
Maciek
  • 19,435
  • 18
  • 63
  • 87
  • Yes, but i can't figure a way to do this without an intemedite class, like a ViewModel. Is it of paramount importance that you bind directly to the dictionary? – angrifel Dec 03 '09 at 22:47
  • It's preferred. The dictionary is supposed to hold my application's settings and such. – Maciek Dec 03 '09 at 22:59

2 Answers2

2

If you look at the KeyValuePair implementation it is a struct with both Key and Value as readonly Properties so my guess is that it's not possible to make a TwoWay binding in this case.

If you make a class that inherits INotifyPropertyChange that handles dictionary add and remove items when you change the key or that only change the value when you are changing the value perhaps it works.

jmayor
  • 2,725
  • 4
  • 29
  • 37
  • Hello, I'm having trouble accessing that link. – Maciek Dec 03 '09 at 23:00
  • OK I refreshed the link, go there and click on each of the Key and Value properties and you'll see they are readonly, only the get is implemented – jmayor Dec 03 '09 at 23:10
2

What you're looking for is something akin to an ObservableCollection<T> but for a dictionary. A bit of Googling found the following from Dr. WPF on building an ObservableDictionary:

Pros and Cons

The benefit to using an observable dictionary, of course, is that the dictionary can serve as the ItemsSource for a databound control and you can still access the dictionary in code the same way you access any other dictionary. It is truly an indexed dictionary of objects. There are certainly some limitations inherent in the very idea of making a dictionary observable. Dictionaries are built for speed. When you impose the behaviors of an observable collection on a dictionary so that the framework can bind to it, you add overhead.

Also, a dictionary exposes its Values and Keys collections through separate properties of the same name. These collections are of types Dictionary<TKey, TValue>.ValueCollection and Dictionary<TKey, TValue>.KeyCollection, respectively. These CLR-defined collections are not observable. As such, you cannot bind to the Values collection or to the Keys collection directly and expect to receive dynamic collection change notifications. You must instead bind directly to the observable dictionary.

Now, you may run into a problem with updating the Key, as you would then need to somehow convince the dictionary to Move your item. I would suggest taking Dr. WPF's ObservableDictionary and instead using a KeyedCollection as the backing store. That way the Key is derived from the Item itself, and updates move the object in the ObservableDictionary automatically.

user7116
  • 63,008
  • 17
  • 141
  • 172
  • I've seen that ObservableDictionary before, but I've had no luck 2-way binding to it, mostly due to Key being readonly – Maciek Dec 04 '09 at 08:46
  • It's for that reason you should use the KeyedCollection, which derives the key from the item. That way you bind to the Item's property that contains the key and the dictionary will update accordingly (maybe). – user7116 Dec 04 '09 at 14:46