wpf 如何在UserControls中使用DataBindings(在页面中有效,但在uc中无效)

ykejflvf  于 2023-06-07  发布在  其他
关注(0)|答案(1)|浏览(445)

关于这一点有几个问题,但我对这个主题了解得太少,无法理解我错过了什么。
这是我第一次在WPF中工作,我想创建几个子模块(我认为是所谓的UserControls),以使XAML更容易阅读,并将所有内容作为自己的一部分,并可能可重用。
我在网上看了一个YouTube视频,得到了下面的代码:
XAML

<Window x:Class="WpfApp1.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:WpfApp1"
        mc:Ignorable="d"
        Title="MainWindow" Height="450" Width="800">
    <StackPanel>
        <ListView ItemsSource="{Binding Items}" />
    </StackPanel>
</Window>

代码隐藏

using System.Collections.ObjectModel;
using System.Windows;

namespace WpfApp1
{    
    public partial class MainWindow : Window
    {
        private ObservableCollection<string> _items;
        public ObservableCollection<string> Items
        {
            get { return _items; }
            set { _items = value; }
        }
        public MainWindow()
        {
            DataContext = this;
            _items = new ObservableCollection<string>();
            InitializeComponent();
            Items.Add("Item 1");
            Items.Add("Item 2");
        }
    }
}

它正确地呈现了包含这两个项的ListView
现在我基本上只是复制了逻辑。我在子文件夹“Components”中创建了一个新的UserControl:
XAML

<UserControl x:Class="WpfApp1.Components.ExampleComponent"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
             xmlns:local="clr-namespace:WpfApp1.Components"
             mc:Ignorable="d" 
             d:DesignHeight="450" d:DesignWidth="800">
    <Grid>
        <ListView ItemsSource="{Binding OtherItems}" />
    </Grid>
</UserControl>
using System.Collections.ObjectModel;
using System.Windows.Controls;

namespace WpfApp1.Components
{    
    public partial class ExampleComponent : UserControl
    {
        private ObservableCollection<string> _otherItems;

        public ObservableCollection<string> OtherItems
        {
            get { return _otherItems; }
            set { _otherItems = value; }
        }

        public ExampleComponent()
        {
            _otherItems = new ObservableCollection<string>();
            InitializeComponent();

            OtherItems.Add("Other 1");
            OtherItems.Add("Other 2");
        }
    }
}

然后我在主窗口的StackPanel中添加了以下行:

<Components:ExampleComponent />

和/或

xmlns:Components="clr-namespace:WpfApp1.Components"

作为附加的Window属性。
我现在得到的是第一个ListView和它下面的第二个
我想知道为什么这不起作用,以及我如何修复它。

x759pob2

x759pob21#

您忘记设置UserControlDataContext

public ExampleComponent()
{
    _otherItems = new ObservableCollection<string>();
    InitializeComponent();
    DataContext = this; //<--

    OtherItems.Add("Other 1");
    OtherItems.Add("Other 2");
}

注意,UserControl一般来说应该从其父元素继承DataContext
然后,您可以直接绑定到父窗口的Items集合:

<ListView ItemsSource="{Binding Items}" />

您可以使用RelativeSource绑定到UserControl本身的特定属性,而不是设置UserControlDataContext属性并打破继承链:

<ListView ItemsSource="{Binding OtherItems,
    RelativeSource={RelativeSource AncestorType=UserControl}}" />

相关问题