0

我有一些区域形式的分层数据,其中包含包含入口的系统 我的 WPF 应用程序有一个以入口作为属性的行程列表。UI 是一个拆分窗口,其中包含一个 ListControl 和一个绑定到 ListView.SelectedItem 属性的“详细信息”控件,如下所示:(为简洁而编辑的代码,仅显示相关部分)

<local:ListView x:Name="listView"/>
<local:DetailsView DataContext="{Binding ElementName=listView, Path=SelectedItem}"/>

详细信息视图由属性的 ComboBox 组成,其中包括:

<ComboBox Name="comboRegion" SelectionChanged="Region_Changed"
    ItemsSource="{Binding ElementName=main, Path=Regions, Mode=OneWay}" DisplayMemberPath="Name"
    SelectedItem="{Binding Region, Mode=OneWay}"/>
<ComboBox Name="comboSystem" SelectionChanged="System_Changed"
    ItemsSource="{Binding ElementName=main, Path=Systems, Mode=OneWay}" DisplayMemberPath="Name"
    SelectedItem="{Binding System, Mode=OneWay}"/>
<ComboBox ItemsSource="{Binding ElementName=main, Path=Entrances, Mode=OneWay}" DisplayMemberPath="Name"
    SelectedItem="{Binding Enter}"/>

Trip.Enter 是我要编辑的属性,Trip.Region 和 Trip.System 是只读的,是从 Trip.Enter 计算的。main.Regions、main、systems 和 main.Entrances 是控件的本地列表,具有以下代码:

    public IEnumerable<Region> Regions { get; private set; }
    public IEnumerable<CaveSystem> Systems { get; private set; }
    public IEnumerable<Entrance> Entrances { get; private set; }

    private void Region_Changed(object sender, SelectionChangedEventArgs e)
    {
        Region = comboRegion.SelectedItem as Region;
        Systems = (region != null ? region.Systems : null);
        NotifyPropertyChanged("Systems");
    }

    private void System_Changed(object sender, SelectionChangedEventArgs e)
    {
        ... Equivalent to Region_Changed except updates Entrances ...
    }

Regions 列表是静态的,因此只填充一次。选择新区域后,系统列表将重新填充新列表。选择新系统(也作为更改区域的级联)时,将重新填充入口列表。

到现在为止还挺好。这按预期工作,在列表视图中选择行程会将其详细信息绑定到组合框。更改组合框中的值,使用新列表更新相应的“较低级别”框。最后,选择一个入口会更新记录本身(列表视图会相应更新)

问题是:当我在列表视图中选择一条新记录时,新记录中的值出现在组合框中,但也被复制到最后选择的记录中。

我认为问题在于,更改详细信息视图的数据上下文会导致绑定全部更新。我认为这会依次发生,但更改所选区域会在较低级别的组合框中产生连锁反应,这也会发生变化。我认为,在那个时候,他们仍然受制于旧唱片。

任何人都可以提出解决这个问题的方法吗?

4

2 回答 2

0

您可以尝试使用策略模式。不要更改您的数据上下文,而是在您的数据上下文中更改类。在这个内部类中,您可以拥有工作逻辑,但您的数据上下文将是相同的。例子:

public interface InnerDataContext
{
   public CaveSystem System{get;}
}

public class DataContext
{
   private InnerDataContext dc;

   public CaveSystem
   { get{ return dc.System; }}
}

您可以根据需要更改内部数据上下文,并且它不会抛出更新值。

于 2012-06-28T15:47:54.740 回答
0

好的,找到了解决办法!我将绑定更改为

UpdateSourceTrigger=LostFocus

这意味着仅当用户在组合框中选择新值时才更新对象,而不是在由于更改数据上下文而更新组合框时。

于 2012-06-29T14:00:52.177 回答