我的小应用程序问题在概念上非常简单。我有一个XML文件,基本上只是将字符串映射到字符串。
冗长的解释警告
示例文件看起来像这样:
<Candies>
<Sees>Box1</Sees>
<Hersheys>Box2</Hersheys>
<Godiva>Box3</Godiva>
</Candies>
虽然我可以使用不同的架构,例如:
<Candies>
<Candy>
<Name>Sees</Name>
<Location>Box1</Location>
</Candy>
</Candies>
......我选择不这样做,因为前者没有任何可预见的不良副作用。
在后面的代码中,我将XML文件的内容加载到带有LINQ的XDocument中。我还定义了一个List变量,因为这是我将GUI数据绑定到的。 CandyLocation看起来像这样:
public class CandyLocation
{
public string Brand { get; set; }
public string Location { get; set; }
}
我的简单GUI就是这样:
<Page
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Height="Auto" Width="Auto">
<Page.Resources>
<DataTemplate x:Key="CandyTemplate">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition></ColumnDefinition>
<ColumnDefinition></ColumnDefinition>
<ColumnDefinition></ColumnDefinition>
</Grid.ColumnDefinitions>
<TextBox Grid.Column="0" Text="{Binding Brand}" Margin="3"></TextBox>
<ComboBox Grid.Column="1" SelectedValue="{Binding Location}" ItemsSource="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type Page}}, Path=DataContext.LocationNames}" Text="{Binding Location, Mode=TwoWay}" Margin="3"></ComboBox>
</Grid>
</DataTemplate>
</Page.Resources>
<DockPanel>
<Button DockPanel.Dock="Bottom" Margin="3" Command="{Binding SaveCandiesCommand}">Apply Changes</Button>
<Button DockPanel.Dock="Bottom" Margin="3" Command="{Binding AddNewCandyCommand}">Add Candy</Button>
<ListBox DockPanel.Dock="Top" ItemsSource="{Binding CandyLocations}" ItemTemplate="{StaticResource CandyTemplate}" />
</DockPanel>
</Page>
所以概述是这样的:
应用程序加载然后使用LINQ加载XML文件。当呈现GUI时,它调用“GetCandyLocations”,它遍历XML数据并使用XML文件的内容填充List对象。在初始加载XML时,GUI正确呈现(即糖果品牌及其位置正确显示),但这就是成功故事结束的地方。
如果我从一个空白的XML文件开始并添加一个品牌,我会通过向我的XDocument根添加一个新的XElement来实现。然后我调用OnPropertyChanged(“CandyLocations”)来进行GUI更新。 Location的初始值为“”,因此用户可以从组合框中选择有效位置。问题是,我无法弄清楚如何正确选择数据绑定,这样我就可以更新XElement值。因此,当我保存糖果位置时,一切都以空白位置值结束。此外,只要用户点击添加糖果,所有以前选择的位置组合框都会被清空。
总结:
谢谢!
答案 0 :(得分:1)
在您的ComboBox上,您可能会在SelectedValue和Text属性之间发生冲突。文本通常仅与IsEditable =“True”一起使用。尝试使用SelectedItem:
<ComboBox SelectedItem="{Binding Location}" ItemsSource="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type Page}}, Path=DataContext.LocationNames}" ></ComboBox>
如果要直接使用XDocument作为数据源,可以使用它(假设XDocument从VM公开为AvailableLocations):
<ComboBox ItemsSource="{Binding Path=AvailableLocations.Root.Elements}" SelectedValue="{Binding Location}"
SelectedValuePath="Value" DockPanel.Dock="Top" DisplayMemberPath="Value"/>
如果您更喜欢显示公司名称,只需将DisplayMemberPath更改为“名称”。
同时尝试使用ObservableCollection而不是CandyLocations的List,这样您就可以在添加或删除项目时获得自动更改通知。