【问题标题】:UserControl Dependencyproperty not updating through bindingUserControl Dependencyproperty 未通过绑定更新
【发布时间】:2012-12-06 18:21:37
【问题描述】:

我正在创建一个 Windows 8 应用程序,过去几天我一直在努力使用自定义用户控件。我真的不知道出了什么问题。

奇怪的是,当我在代码中更改 Source 时,dependencyproperty 调用 propertychanged 事件,但绑定没有更新。

这是我的代码:

GamePage.xaml.cs

public sealed partial class GamePage
    {
        GamePageViewModel viewModel;

        public GamePage()
        {
            this.InitializeComponent();
            viewModel = new GamePageViewModel();
        }
    }  

GamePage.xaml

<common:LayoutAwarePage x:Class="WordSearcher.GamePage"
                        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:common="using:WordSearcher.Common"
                        xmlns:controls="using:WordSearcher.Controls"
                        xmlns:ignore="http://www.ignore.com"
                        mc:Ignorable="d ignore"
                        d:DesignHeight="768"
                        d:DesignWidth="1366"
                        DataContext="{Binding GamePageViewModel, Source={StaticResource Locator}}">
<StackPanel Orientation="Horizontal">
        <StackPanel.Background>
            <ImageBrush ImageSource="Assets/Wood.jpg" Stretch="UniformToFill"/>
        </StackPanel.Background>
<controls:PuzzleControl Source="{Binding Path=PuzzleData}"/>

    </StackPanel>
</common:LayoutAwarePage>

GamePageViewModel.cs

public class GamePageViewModel : ViewModelBase
    {
        private List<string> _puzzleData;

        public List<string> PuzzleData
        {
            get
            {
                return _puzzleData;
            }
            set
            {
                this._puzzleData = value;
                RaisePropertyChanged("PuzzleData");
            }
        }

        public GamePageViewModel()
        {
            SetNewData();
        }

        private async void SetNewData()
        {
            await SomeManager.Prepare();
            PuzzleData = SomeManager.Create(20);
        }
    }

PuzzleControl.xaml.cs

<UserControl
    x:Class="WordSearcher.Controls.PuzzleControl"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local="using:WordSearcher.Controls"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    mc:Ignorable="d"
    d:DesignHeight="500"
    d:DesignWidth="500">

    <Grid x:Name="puzzleGrid" 
          Width="500" 
          Height="500"
          >

    </Grid>
</UserControl>

PuzzleControl.xaml.cs

public sealed partial class PuzzleControl : UserControl
    {

        public static readonly DependencyProperty SourceProperty =
            DependencyProperty.Register("Source", typeof(ObservableCollection<string>), typeof(PuzzleControl), new PropertyMetadata(null, PropertyChanged));

        private static void PropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            //
            // not called from binding
            //
            ((PuzzleControl)d).OnItemsSourcePropertyChanged(e);
        }

        private void OnItemsSourcePropertyChanged(DependencyPropertyChangedEventArgs e)
        {
            Source = (ObservableCollection<string>)e.NewValue;
            SetGridData();
        }

        public ObservableCollection<string> Source
        {
            get
            {
                return (ObservableCollection<string>)GetValue(SourceProperty);
            }
            set
            {
                SetValue(SourceProperty, value);
            }
        }

        public PuzzleControl()
        {
            this.InitializeComponent();
            CreateRowsAndColumns();
        }

        private void CreateRowsAndColumns()
        {
            //create rows and columns in puzzleGrid
            //works fine
        }

        private void SetGridData()
        {
            //fill puzzleGrid with data
            //works fine
        }
    }

有人知道我的代码有问题吗?因为当我把 Source = new ObservableCollection();在 PuzzleData 的构造函数中,PropertyChanged 事件将引发。与 DataContext 有什么关系吗?

提前谢谢!

【问题讨论】:

    标签: binding user-controls windows-8 mvvm-light dependency-properties


    【解决方案1】:

    我不确定,

    但是你设置了&lt;controls:PuzzleControl Source="{Binding Path=PuzzleData}"/&gt;

    PuzzleData = List<string>
    

    和

    Source = ObservableCollection<string>
    

    如果绑定甚至第一次工作(它显然是这样做的),那么可能是源以某种方式设置为 List&lt;string&gt; 而不是ObservableCollection&lt;string&gt;。这可能就是您的依赖属性方法 (PropertyChanged) 没有被调用的原因,因为它已注册到 ObservableCollection&lt;string&gt;。

    但这纯属猜测,没有测试过。


    在我得到他的代码并对其进行审查后,我发现 PuzzleData 从未真正设置过,这就是错误... 误报.....

    【讨论】:

      【解决方案2】:

      您确定绑定上下文吗?又如何绑定对象?如果你在gridview中使用你的用户控件,DataContext会改变,并且根页面的Datacontext不同。

      <controls:PuzzleControl Source="{Binding Path=DataContext.PuzzleData}"/>
      

      如果你使用子控件,你的用户控件;像这样绑定 ElementName 属性:

      <controls:PuzzleControl Source="{Binding Path=DataContext.PuzzleData, ElementName=pageRoot}"/>
      

      如果您不确定,请在调试时通过断点跟踪 DataContext 绑定值。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2012-06-06
        • 2011-10-27
        • 2013-06-03
        • 2011-05-18
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多