我有三个列表视图,第一个显示通用列表,当双击某个元素时,以下两个列表视图应该“分支”出来。例如,第一个列表显示汽车、卡车、自行车。双击“汽车”时,下一个列表视图应显示 SUV、轿车、小型货车等。单击其中一个时,在本例中假设为 SUV,最后一个列表应显示 2023 斯巴鲁森林人、2023 福特探险家等。三个主要可观察对象集合在页面加载时填充,如下所示的引用,因为它们最终必须被过滤。我有所有三个和可观察集合的模型,声明如下:
private ObservableCollection<VehicleGeneral> _vehiclegenerals;
public ObservableCollection<VehicleGeneral> VehicleGenerals
{
get { return _vehiclegenerals; }
set
{
_vehiclegenerals= value;
OnPropertyChanged(nameof(VehicleGenerals));
}
}
上面的集合是所有三个集合的准确定义方式。
这是 Xaml 绑定: 请注意,所有三个列表视图的定义完全如下,当然只是名称和绑定不同。
<ListView
Grid.Row="1"
Grid.ColumnSpan="3"
ItemsSource="{Binding VehicleGenerals,Mode=TwoWay}"
SelectedItem="{Binding VehicleIndex, Mode=TwoWay}"
MouseDoubleClick="ListView_MouseDoubleClickVehicle"
x:Name="VehicleList"
使用 ItemSource:
private VehicleGeneral _vehicleIndex;
public VehicleGeneral VehicleIndex
{
get { return _vehicleIndex; }
set
{
if (value != null)
{
_vehicleIndex= value;
OnPropertyChanged(nameof(VehicleIndex));
SetObjectText(VehicleIndex, null, null); //This can be ignored I'm just setting label text
}
}
}
我确信有一种更简洁的方法可以将值重新分配给可观察的集合,我觉得我已经尝试了所有这些方法,但这就是我现在在代码中更新它的方法。
//Code Behind
private void ListView_MouseDoubleClickVehicle(object sender, MouseButtonEventArgs e)
{
_viewModel.ListDoubleClicked(VehicleList.SelectedIndex);
}
...
//In Viewmodel
public void ListDoubleClicked(int? index)
{
if (index != null )
{
var vehicle = VehicleGeneralHolder[(int)index];
var filtered = VehicleTypeHolder.Where(x => (int)x.VehicleGeneralId == vehicle.Id).ToList();
_vehicleType.Clear();
//_vehicleType = new ObservableCollection<VehicleType>(filtered);
foreach (var item in filtered)
{
_vehicleType .Add(item);
}
}
}
如果需要更多细节,我会很乐意提供,总的来说,我完全不知道为什么这不能按预期工作。
我的主视图模型(其中显示的代码继承的视图模型)具有 INotifyPropertyChanged。我尝试过明确声明绑定为 OneWay 或 TwoWay。以各种不同的方式添加/删除 ObservableCollection 元素。代码有效并且元素被过滤,但由于某种原因,UI 没有反映这些更改。
如果您要使用如下代码:
_vehicleType = new ObservableCollection<VehicleType>(filtered); // Use VehicleType = ... to ensure OnPropertyChanged raised.
(已被注释掉,但您似乎已经尝试过)您可能希望通过属性访问器而不是私有成员来使用它,以确保在侦听 VehicleType 项源的任何内容上引发
OnPropertyChanged
。
至于修改可观察集合本身,代码如下:
_vehicleType.Clear();
foreach (var item in filtered)
{
_vehicleType .Add(item);
}
...应该可以工作,只要 _vehicleType 是
ObservableCollection<VehicleType>
。一个可能的问题是在 ItemSource 引用上使用双向绑定。 WPF 将根据预期的消费者绑定需求默认绑定,您只需在偏离该方向时显式指定绑定方向。您可以尝试将下拉菜单上的绑定调整为默认值:
ItemsSource="{Binding Path=VehicleGenerals}" // Should default to 1-way
SelectedItem="{Binding Path=VehicleIndex}" // Should default to 2-way