我试图创建一个UserControl,它可以让我在网格中编辑一个类型为Dictionary<string,string>
的字典(只是编辑目前为止的条目,而不是添加或删除)。DataGrid更改时,为什么ViewModel中的属性未更新?
每当我的DataGrid绑定到一个词典将其显示为只读网格,所以我decieded创建一个值转换器,将其转换为ObservableCollection<DictionaryEntry>
其中DictionaryEntry
只是一个具有两个属性Key
和Value
类。
这适用于在网格中显示字典,但现在当我对网格进行更改时,我的字典未被更新。我不确定为什么。
我认为这可能是我设置绑定的方式或我的值转换器的问题。如果有人能够说出一些光明,那将是太棒了。
下面是我能做的最小的演示,显示了我在做什么。再次问题是,当我改变网格中的值时,我的MainViewModel
上的MyDictionary
未更新。为什么?
MainViewModel.cs
public class MainViewModel : INotifyPropertyChanged
{
public MainViewModel()
{
_myDictionary = new Dictionary<string, string>()
{
{"Key1", "Value1"},
{"Key2", "Value2"},
{"Key3", "Value3"}
};
}
private Dictionary<string, string> _myDictionary;
public Dictionary<string, string> MyDictionary
{
get
{
return _myDictionary;
}
set
{
if (_myDictionary == value)
return;
_myDictionary = value;
OnPropertyChanged("MyDictionary");
}
}
...
}
MainWindow.xaml
<Window ...>
<Window.Resources>
<local:MainViewModel x:Key="MainViewModel"></local:MainViewModel>
</Window.Resources>
<StackPanel Name="MainStackPanel" DataContext="{Binding Source={StaticResource MainViewModel}}">
<local:DictionaryGrid />
<Button Content="Print Dictionary" Click="PrintDictionary"></Button>
</StackPanel>
</Window>
DictionaryGrid.xaml
<UserControl ...>
<UserControl.Resources>
<testingGrid:DictionaryToOcConverter x:Key="Converter" />
</UserControl.Resources>
<Grid>
<DataGrid ItemsSource="{Binding MyDictionary,
Converter={StaticResource Converter}}"
/>
</Grid>
</UserControl>
个DictionaryToOcConverter.cs
public class DictionaryToOcConverter : IValueConverter
{
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
{
var collection = new ObservableCollection<DictionaryEntry>();
var dictionary = value as Dictionary<string, string>;
if (dictionary != null)
{
foreach (var kvp in dictionary)
collection.Add(new DictionaryEntry { Key = kvp.Key, Value = kvp.Value });
}
return collection;
}
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
{
var dictionary = new Dictionary<string, string>();
var entries = value as ObservableCollection<DictionaryEntry>;
if (entries != null)
{
foreach (var entry in entries)
dictionary.Add(entry.Key, entry.Value);
}
return dictionary;
}
public class DictionaryEntry
{
public string Key { get; set; }
public string Value { get; set; }
}
}
谢谢您的回复。我做了这些改变。内部字典会改变字符串,但它们不会回到我的主视图模型中,我是否错过了一些必须通过IValueConverter返回的内容? ConvertBack方法永远不会被调用,并且不确定调用它的正确方式,当可观察集合发生更改时是否应该调用它,还是必须连接其他的东西? –
我不想将它包含在我的答案中,但价值转换器几乎是一个红鲱鱼。我会把它。如果这些更改正在运行(他们应该这么做!),并且您希望通知位于更深层次的抽象层中,那么VM应该预订每个DictionaryEntry的属性,并实现一个事件处理程序来处理它们。或者只是使用'内部词典'作为虚拟机的物品来源。 –