4

我发现了一些奇怪的东西:我有一个带有两个数据网格的表单,它们绑定到同一个集合。根据 Xaml 中数据网格的顺序,行为会有所不同。

这按预期工作(存在用于添加的额外行):

<DockPanel>
    <DockPanel DockPanel.Dock="Right">
        <Label Content="ReadOnlyView" DockPanel.Dock="Top"/>
        <DataGrid ItemsSource="{Binding Persons}" IsReadOnly="True" />
    </DockPanel>
    <DockPanel>
        <Label Content="EditorView" DockPanel.Dock="Top" />
        <DataGrid ItemsSource="{Binding Persons}" IsReadOnly="False" CanUserAddRows="True" />
    </DockPanel>
</DockPanel>

以这种方式排列 xaml 让我感到困惑(没有额外的添加行)

<DockPanel>
    <DockPanel>
        <Label Content="EditorView" DockPanel.Dock="Top" />
        <DataGrid ItemsSource="{Binding Persons}" IsReadOnly="False" CanUserAddRows="True" />
    </DockPanel>
    <DockPanel DockPanel.Dock="Right">
        <Label Content="ReadOnlyView" DockPanel.Dock="Top"/>
        <DataGrid ItemsSource="{Binding Persons}" IsReadOnly="True" />
    </DockPanel>
</DockPanel>

下面是我为此使用的虚拟 ViewModel:

public class PersonsViewModel
{
    public PersonsViewModel()
    {
        Persons = new ObservableCollection<Person>
                    {
                        new Person {Name = "Johan"},
                        new Person {Name = "Dave"},
                    };
    }

    public ObservableCollection<Person> Persons { get; private set; }
}

public class Person
{
    public string Name { get; set; }
}

我的问题是这种行为的原因是什么?

4

1 回答 1

2

一个很好的问题约翰!我的猜测是,由于您没有明确地为它提供 a CollectionViewSource,因此自动生成的 cvs byDataGrid在两者之间共享,因为您指的是同一来源。

因此,当您发出两个IsReadOnly分配并作为共享源时,最后一个设置获胜,两者都DataGrid显示相同的效果。

为了证实我的猜测,我已经使用了此代码,并且DataGrids当您明确提供它们以供使用时,其行为与您所期望的一样CollectionViewSource

<Window x:Class="WpfApplication1.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="MainWindow" Height="350" Width="525">
    <Window.Resources>
        <CollectionViewSource Source="{Binding Persons}" x:Key="cvs1" />
        <CollectionViewSource Source="{Binding Persons}" x:Key="cvs2" />
    </Window.Resources>
    <DockPanel>
        <DataGrid ItemsSource="{Binding Source={StaticResource ResourceKey=cvs1}}" IsReadOnly="False" CanUserAddRows="True" />
        <DataGrid ItemsSource="{Binding Source={StaticResource ResourceKey=cvs2}}" IsReadOnly="True" />
    </DockPanel>
</Window>

编辑:进一步的测试表明行为可以被描述为奇怪!我无法解释为什么这会产生三个只读 DG

<DataGrid ItemsSource="{Binding Persons}" IsReadOnly="True" />
<DataGrid ItemsSource="{Binding Persons}" IsReadOnly="False" />
<DataGrid ItemsSource="{Binding Persons}" IsReadOnly="True" />

但这会产生交替的只读和可编辑 DG:

<DataGrid ItemsSource="{Binding Persons}" IsReadOnly="True" />
<DataGrid ItemsSource="{Binding Persons}" IsReadOnly="False" />
<DataGrid ItemsSource="{Binding Persons}" IsReadOnly="True" />
<DataGrid ItemsSource="{Binding Persons}" IsReadOnly="False" />

所以我想上面的 CVS 最好被描述为这种奇怪行为的解决方法,这样你就可以实现你真正想要的。

编辑 2:在更多真假组合之后,我注意到的唯一一致的事情是,如果 Last IsReadOnlyinDataGrid设置为 True,则所有其他都DataGrids变为只读。但是如果最后一个设置为 false,那么所有其他 DataGrid 的行为都将根据它们自己的 IsReadOnly 设置进行。这种行为可能是由于这个MSDN 位

If a conflict exists between the settings at the DataGrid, column,
or cell levels, a value of true takes precedence over a value of false.
于 2012-12-11T11:51:20.797 回答