我正在尝试将自定义控件的参数绑定到列表。 但是它会在错误的ViewModel中搜索。 它在我的控件的ViewModel(ViewModelUserControlVM)中搜索,而不是我的控件所在页面的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(); }提前致谢。
i'm trying to bind a parameter of my custom control to a list. However it searches in the wrong ViewModel. It searches in te ViewModel of my control(ViewModelUserControlVM) and not the the ViewModel of the page where my control is located.
user control xaml
<UserControl.DataContext> <vm:ViewModelUserControlVM/> </UserControl.DataContext> <ListView Name="lst"> <ListView.ItemsPanel> <ItemsPanelTemplate> <StackPanel Orientation="Horizontal"/> </ItemsPanelTemplate> </ListView.ItemsPanel> </ListView>User control code behind
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) ) );Mainpage xaml
<local:CustomControl ItemsSource="{Binding list, Mode=TwoWay}">edit
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); } }User control code behind
public CustomControl() { this.InitializeComponent(); }thanks in advance.
最满意答案
如果UserControl的DataContext是ViewModelUserControlVM,则其中的任何绑定都将查找该DataContext。 如果需要父控件绑定到依赖项属性以从其(父控件)DataContext传递某些内容,则可以将UserControls主面板的DataContext(Grid,StackPanel等)设置为ViewModelUserControlVM。 这将使控件本身在可视树中看起来“向上”以找到DataContext。 在这种情况下,您的MainPage的viewmodel。
您共享的部分代码似乎是您尝试将ItemsSource依赖项属性绑定到MainPage中的某些内容,但随后通过将整个UserControl的DataContext分配给不同的viewmodel来覆盖UserControl的DataContext。
更完整的代码将支持或反对这一理论。
更新如下
感谢您提供额外的代码。 目前还不清楚最终目标是什么 - 例如,提到了所选项目但未使用,我们不知道用户控件的viewmodel的相关性。 所以,我把一些简单地显示在主视图模型中的列表并绑定到正在查找该类型列表的usercontrol。 我希望它能帮助你找到你要去的地方......(注意:我使用了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) { } }CustomControl 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。 我希望它可以帮助你。
If the DataContext of your UserControl is ViewModelUserControlVM, any Bindings in it will look to that DataContext. If you need a parent control to bind to the dependency property to pass something from its (the parent control) DataContext, you can set the DataContext of the UserControls main panel (Grid, StackPanel, etc.) to your ViewModelUserControlVM. This will cause the control itself to look "upwards" in the visual tree to find a DataContext. In this case, your MainPage's viewmodel.
It appears by the partial code you have shared that you are attempting to Bind the ItemsSource dependency property to something in the MainPage, but then overriding the UserControl's DataContext by assigning the entire UserControl's DataContext to a different viewmodel.
More complete code would support or contest this theory.
update below
Thank you for the additional code. It is still unclear what the ultimate goal is - for example, the selected item is mentioned, but not used and we don't know the relevance of the user control's viewmodel. So, I threw together a little something that simply shows a list in the main viewmodel and binds to a usercontrol that is looking for a list of that type. I hope it helps get you where you are trying to go... (note: I used the MVVMLight library)
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 is the 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 code behind (note the datacontext setting in the ctor - DataContext of control is whatever is using it, but the controls inside the LayoutRoot grid will use the control's dependency properties):
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) { } }CustomControl 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>In a nutshell, the ListView's itemsource is bound to whatever CustomControl's ItemsSource dependency property is. CustomControl's ItemsSource's DataContext is whatever DataContext is using the control. I hope it helps you out.
更多推荐
list,public,control,xaml,电脑培训,计算机培训,IT培训"/> <meta name="desc
发布评论