【问题标题】:Custom Control binding issue (Windows universal 10)自定义控件绑定问题(Windows 通用 10)
【发布时间】:2016-03-23 15:01:17
【问题描述】:

我正在尝试将自定义控件的参数绑定到列表。但是它在错误的 ViewModel 中搜索。它在我的控件 (ViewModelUserControlVM) 的 ViewModel 中搜索,而不是在我的控件所在页面的 ViewModel 中搜索。

用户控件 xaml

 <UserControl.DataContext>
    <vm:ViewModelUserControlVM/>
</UserControl.DataContext>

<ListView Name="lst">
    <ListView.ItemsPanel>
        <ItemsPanelTemplate>
            <StackPanel Orientation="Horizontal"/>
        </ItemsPanelTemplate>
    </ListView.ItemsPanel>
</ListView>

后面的用户控制代码

    public object ItemsSource
    {
        get
        {
            return (object)GetValue(ItemsSourceProperty);
        }
        set
        {
            SetValue(ItemsSourceProperty, value);
        }
    }

    public static readonly DependencyProperty ItemsSourceProperty = DependencyProperty.Register
        (
        "ItemsSource",
        typeof(object),
        typeof(FlipListview),
        new PropertyMetadata(
            new object(),
            new PropertyChangedCallback(OnItemsSourceChanged)
        )
    );

主页 xaml

    <local:CustomControl ItemsSource="{Binding list, Mode=TwoWay}">

编辑

mainpage.xaml

<Page.DataContext>
    <vm:MainPageVM/>
</Page.DataContext>

MainPageVM

    public class MainPageVM : ViewModelBase
    {
    public List<Model> list { get; set; }
    public RelayCommand SelectedItemCommand { get; set; }

    public Model SelectedItem { get; set; }

    public MainPageVM()
    {
        SelectedItem = new Model();
        SelectedItemCommand = new RelayCommand(SelectedItem);

        list = new List<Model>();

        for (int i = 0; i < 5; i++)
        {
            list.Add(new Model("url" + i, "title" + i, "desc" + i));
        }
        RaisePropertyChanged(() => list);
    }
   }

后面的用户控制代码

        public CustomControl()
        {
        this.InitializeComponent();
        }

提前致谢。

【问题讨论】:

    标签: c# wpf mvvm binding win-universal-app


    【解决方案1】:

    如果您的 UserControl 的 DataContext 是 ViewModelUserControlVM,则其中的任何绑定都将查找该 DataContext。如果您需要将父控件绑定到依赖属性以从其(父控件)DataContext 传递某些内容,则可以将 UserControls 主面板(Grid、StackPanel 等)的 DataContext 设置为您的 ViewModelUserControlVM。这将导致控件本身在可视化树中“向上”查找以查找 DataContext。在这种情况下,您的 MainPage 的视图模型。

    您共享的部分代码显示您正在尝试将 ItemsSource 依赖项属性绑定到 MainPage 中的某些内容,但随后通过将整个 UserControl 的 DataContext 分配给不同的视图模型来覆盖 UserControl 的 DataContext。

    更完整的代码会支持或质疑这一理论。

    下方更新

    感谢您提供额外的代码。目前还不清楚最终目标是什么——例如,选定的项目被提及,但没有被使用,我们不知道用户控件的视图模型的相关性。所以,我把一些东西放在一起,它只是在主视图模型中显示一个列表,并绑定到一个正在寻找该类型列表的用户控件。我希望它可以帮助你到达你想要去的地方...... (注意:我使用了 MVVMLight 库)

    MainPageVM:

    public class MainPageVM : ViewModelBase
        {
            private List<Model> _list = new List<Model>();
            public List<Model> list
            {
                get { return _list; }
                set { Set(ref _list, value); }
            }
    
    
    
            public MainPageVM()
            {
                for (int i = 0; i < 5; i++)
                {
                    list.Add(new Model("url" + i, "title" + i, "desc" + i));
                }
                RaisePropertyChanged(() => list);
            }
        }
    

    MainPage xaml(DataContext 是 MainVM):

    <Page
        x:Class="App8.MainPage"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:local="using:App8"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        mc:Ignorable="d">
        <Page.DataContext>
            <local:MainPageVM />
        </Page.DataContext>
    
        <Grid Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
            <local:CustomControl ItemsSource="{Binding list, Mode=OneWay}" />
        </Grid>
    </Page>
    

    CustomControl 后面的代码(注意 ctor 中的 datacontext 设置 - 控件的 DataContext 是使用它的任何内容,但 LayoutRoot 网格内的控件将使用控件的依赖属性):

    public CustomControl()
            {
                this.InitializeComponent();
                LayoutRoot.DataContext = this;
            }
    
    
    
            public List<Model> ItemsSource
            {
                get { return (List<Model>)GetValue(ItemsSourceProperty); }
                set { SetValue(ItemsSourceProperty, value); }
            }
    
            // Using a DependencyProperty as the backing store for ItemsSource.  This enables animation, styling, binding, etc...
            public static readonly DependencyProperty ItemsSourceProperty =
                DependencyProperty.Register("ItemsSource", typeof(List<Model>), typeof(CustomControl), new PropertyMetadata(null, new PropertyChangedCallback(OnItemsSourceChanged)));
    
            private static void OnItemsSourceChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
            {
    
            }
        }
    

    自定义控件 xaml:

    <UserControl
        x:Class="App8.CustomControl"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:local="using:App8"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        mc:Ignorable="d"
        d:DesignHeight="300"
        d:DesignWidth="400">
    
        <Grid x:Name="LayoutRoot">
            <ListView Name="lst" ItemsSource="{Binding ItemsSource, Mode=OneWay}" 
                      DisplayMemberPath="Url">
            </ListView>
        </Grid>
    </UserControl>
    

    简而言之,ListView 的 itemsource 绑定到任何 CustomControl 的 ItemsSource 依赖属性。 CustomControl 的 ItemsSource 的 DataContext 是 DataContext 使用该控件的任何内容。希望对你有帮助。

    【讨论】:

    • 它很接近,但现在我在 CustomControl 中的绑定不起作用。它是我应用于 Listview 的样式中的控件中的绑定。
    • 我正在尝试解决问题。在加载事件中,我正在这样做。 Style templatedControl = ((CustomControl)sender).lst.Style; SetterBaseCollection 设置 = 模板控制.Setters;列表 列表 = set.ToList(); Setter setter = (Setter)list[13];但是我无法在该设置器中获得控件。这是一个控制模板。
    【解决方案2】:

    也许它会像这样工作:

     <local:CustomControl ItemsSource="{x:Bind ViewModel.list, Mode=TwoWay}">
    

    您可以找到有关 x:Bind here 的更多信息

    【讨论】:

    • 我不喜欢使用 x:bind,因为它不使用 ViewModel。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-05-29
    • 2018-02-17
    • 2017-07-30
    • 1970-01-01
    相关资源
    最近更新 更多