【问题标题】:WPF Binding two levels of UserControlWPF绑定两级UserControl
【发布时间】:2015-11-29 23:39:42
【问题描述】:

让我们稍微解释一下我的问题,我编写了一个应用程序代码,该代码显示了一个带有绑定的用户控件,我试图将其设置为另一个子用户控件。我正在使用已设置为 MainWindow.xaml 的模型。

问题是:

用户控件 innerusercontrol 不显示绑定的变化。我想我犯了一个错误,但我不知道在哪里以及如何修复它。我阅读了几篇文章,但没有人用特定的代码行回答它们。任何机构可以帮助我吗?

我将不胜感激。谢谢

MainWindow.xaml

<Window x:Class="DependencyProperties.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:local="clr-namespace:DependencyProperties"
        Title="MainWindow" Height="350" Width="525">
    <Grid>
        <Grid.ColumnDefinitions>
            <ColumnDefinition/>
        </Grid.ColumnDefinitions>
        <Grid.RowDefinitions>
            <RowDefinition/>
            <RowDefinition Height="3*"/>
            <RowDefinition/>
        </Grid.RowDefinitions>
        <local:DisplayProduct x:Name="ucDisplay" Grid.Row="1" Height="110"/>
        <Button Grid.Row="2" Click="Button_Click">Apply circle visibility false/true</Button>
    </Grid>
</Window>

MainWindow.xaml.cs

public partial class MainWindow : Window
    {
        public static ProductModel product;
        public MainWindow()
        {
            InitializeComponent();
            product = new ProductModel() { IsActivo = true, Descuento = 15.00, Importe = 100.00, Total = 85.00 };
            ucDisplay.DataContext = product;
        }

        private void Button_Click(object sender, RoutedEventArgs e)
        {
            Console.WriteLine("Antes " + product.IsActivo);
            product.IsActivo = !product.IsActivo;
            Console.WriteLine("Despues" + product.IsActivo);
        }
    }

DisplayProductUserControl.xaml

<UserControl x:Class="DependencyProperties.DisplayProductUserControl"
             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:DependencyProperties"
             mc:Ignorable="d" x:Name="win_Display"
             d:DesignHeight="80" d:DesignWidth="500">
    <UserControl.Resources>
        <Style TargetType="TextBlock">
            <Setter Property="FontSize" Value="18"/>
            <Setter Property="FontWeight" Value="Light"/>
        </Style>
    </UserControl.Resources>
    <Grid>
        <Viewbox>
            <Grid Width="{Binding ElementName=win_Display, Path=ActualWidth}" Height="{Binding ElementName=win_Display, Path=ActualHeight}">
                <Grid.ColumnDefinitions>
                    <ColumnDefinition />
                    <ColumnDefinition />
                    <ColumnDefinition />
                </Grid.ColumnDefinitions>
                <Grid.RowDefinitions>
                    <RowDefinition />
                    <RowDefinition />
                </Grid.RowDefinitions>
                <StackPanel Orientation="Horizontal">
                    <TextBlock Text="Price: "/>
                    <TextBlock Text="$"/>
                    <TextBlock Text="{Binding Path=Price}"/>
                </StackPanel>
                <StackPanel Grid.Column="1" Orientation="Horizontal">
                    <TextBlock Text="Discount: "/>
                    <TextBlock Text="$"/>
                    <TextBlock Text="{Binding Path=Discount}"/>
                </StackPanel>
                <StackPanel Grid.Column="2" Orientation="Horizontal">
                    <TextBlock Text="Total: "/>
                    <TextBlock Text="$"/>
                    <TextBlock Text="{Binding Path=Total}"/>
                </StackPanel>
                <local:InnerUserControl Grid.Column="0" Grid.Row="1">
                    <local:InnerUserControl DataContext="{Binding Path=IsActive,RelativeSource={RelativeSource Mode=FindAncestor,AncestorType=UserControl}}"/>
                </local:InnerUserControl>
            </Grid>
        </Viewbox>
    </Grid>
</UserControl>

InnerUserControl *问题就在这里

    <UserControl x:Class="DependencyProperties.InnerUserControl"
                 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" 
                 mc:Ignorable="d"  x:Name="win_inner"
                 d:DesignHeight="40" d:DesignWidth="100">
        <UserControl.Resources>
            <BooleanToVisibilityConverter x:Key="VisibilityConverter"/>
        </UserControl.Resources>
        <Grid Width="{Binding ElementName=win_inner, Path=ActualWidth}">        
                <TextBlock Text="{Binding Path=IsActive}" FontSize="15"/>
**<!-- HERE IS THE PROBLEM I DOESN'T SHOW CHANGES WHEN IsActive is false/true -->**
                <Ellipse Height="{Binding ElementName=win_inner, Path=ActualHeight}" Width="{Binding RelativeSource={RelativeSource Self}, Path=ActualHeight}" Fill="Red"
                         Visibility="{Binding Path=IsActive, Converter={StaticResource VisibilityConverter}}" HorizontalAlignment="Right"></Ellipse>
        </Grid>
    </UserControl>

产品模型

public class ProductModel : INotifyPropertyChanged
{
    private double price;

    public double Price
    {
        get { return price; }
        set { price= value; }
    }

    private double discount;

    public double Discount
    {
        get { return discount; }
        set { discount= value; }
    }

    private double total;

    public double Total
    {
        get { return total; }
        set { total = value; }
    }

    private bool isActive;

    public bool IsActive
    {
        get { return isActive; }
        set { isActive = value; }
    }


    protected void RaisePropertyChanged(string propertyName)
    {
        var handler = PropertyChanged;

        if (handler != null)
        {
            handler(this, new PropertyChangedEventArgs(propertyName));
        }
    }

    public event PropertyChangedEventHandler PropertyChanged;
}

【问题讨论】:

  • 你必须在 IsActive 设置器中调用 RaisePropertyChanged

标签: wpf xaml binding user-controls


【解决方案1】:

就像 dnr3 已经评论过的一样,

在您的“产品模型”类中添加 RaisePropertyChanged 方法。

public bool IsActive
{
    get { return isActive; }
    set 
    { 
        isActive = value; 
        RaisePropertyChanged("IsActive");
    }
}

在获得“PropertyChanged”事件之前,视图永远不会改变。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-06-05
    • 2021-07-19
    • 1970-01-01
    • 1970-01-01
    • 2013-01-20
    • 2014-08-31
    相关资源
    最近更新 更多