WPF 通过触发器更改 UserControl 中的 ContentTemplate [英] WPF Changing ContentTemplate in UserControl by Trigger

查看:59
本文介绍了WPF 通过触发器更改 UserControl 中的 ContentTemplate的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

期望

我的控件应该如图 1.单击标题为第二"的按钮后,控件的内容是否会发生变化,如图 2.在这个图中状态应该是在发送 key 后再次变回 content 输入文本框.

My control should appear as shown in Figure 1. After clicking on the button titled "Second" should contents of the control change, as shown in Figure 2. In this figure the state should be content again to change back after sending the key Enter the text box.

解决方案

我创建了两个 DataTemplate.这些 DataTemplate 应根据 IsEditable 属性的变化而变化.默认 DataTemplate 称为 CompactDataTemplate,应在 IsEditable 值等于 FALSE 时使用.当 IsEditable 变为 TRUE 时,应使用 EditableDataTemplate.

I created two DataTemplate. These DataTemplates should change based on changes in the properties IsEditable. Default DataTemplate is called CompactDataTemplate and should be used when the value IsEditable is equal FALSE. When the IsEditable turns TRUE, the EditableDataTemplate should be used.

文件TestUserControl.xaml

<UserControl x:Class="JP4.Controls.TestControl"
         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" 
         d:DesignHeight="26" d:DesignWidth="200" Style="{DynamicResource TestControlStyle}">
<UserControl.Resources>

CompactDataTemplate

<DataTemplate x:Key="CompactDataTemplate" DataType="{x:Type UserControl}">
    <StackPanel Orientation="Horizontal">
        <Button Content="First Button" />
        <Button Content="Second Button" Click="SecondButton_Click" />
    </StackPanel>
</DataTemplate>

可编辑数据模板

<DataTemplate x:Key="EditableDataTemplate" DataType="{x:Type UserControl}">
    <StackPanel Orientation="Horizontal">
        <TextBox Text="Press enter" />
    </StackPanel>
</DataTemplate>

TestControlStyle 包含在 IsEditable 已更改时应触发的触发器

TestControlStyle contains trigger that should firing in case IsEditable has been changed

<Style x:Key="TestControlStyle" TargetType="{x:Type UserControl}">
        <Setter Property="ContentTemplate" Value="{StaticResource CompactDataTemplate}" />
        <Setter Property="Template">
            <Setter.Value>
                <ControlTemplate TargetType="{x:Type UserControl}">
                    <Border BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" Background="{TemplateBinding Background}" Padding="{TemplateBinding Padding}" SnapsToDevicePixels="true">
                        <ContentPresenter HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}" VerticalAlignment="{TemplateBinding VerticalContentAlignment}"/>
                    </Border>
                    <ControlTemplate.Triggers>
                        <DataTrigger Binding="{Binding IsEditable}" Value="true">
                            <Setter Property="ContentTemplate" Value="{StaticResource EditableDataTemplate}" />
                        </DataTrigger>
                    </ControlTemplate.Triggers>
                </ControlTemplate>

            </Setter.Value>
        </Setter>
    </Style>
</UserControl.Resources>

</UserControl>

文件TestUserControl.xaml.cs

using System.ComponentModel;
using System.Windows;
using System.Windows.Controls;

namespace TestControl
{
/// <summary>
/// Interaction logic for TestControl.xaml
/// </summary>
public partial class TestUserControl : UserControl, INotifyPropertyChanged, INotifyPropertyChanging
{
    /// <summary>
    /// Constructors
    /// </summary>
    public TestUserControl()
    {
        InitializeComponent();
    }

    // Properties
    private bool _IsEditable;

    public bool IsEditable
    {
        get { return _IsEditable; }
        set
        {

            _IsEditable = value;
            NotifyPropertyChanged("IsEditable");
        }
    }

    // Controls events
    private void SecondButton_Click(object sender, RoutedEventArgs e)
    {
        IsEditable = true;
    }

    private void TextBox_KeyDown(object sender, System.Windows.Input.KeyEventArgs e)
    {
        if (e.Key == System.Windows.Input.Key.Enter)
            IsEditable = false;
    }

    // INotifyPropertyChanged implementation
    public void NotifyPropertyChanged(string propertyName)
    {
        if (PropertyChanged != null)
            PropertyChanged.Invoke(this, new PropertyChangedEventArgs(propertyName));
    }

    public void NotifyPropertyChanging(string propertyName)
    {
        if (PropertyChanging != null)
            PropertyChanging.Invoke(this, new PropertyChangingEventArgs(propertyName));
    }

    public event PropertyChangedEventHandler PropertyChanged;

    public event PropertyChangingEventHandler PropertyChanging;


  }
}

MainWindow.xaml

<Window
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local="clr-namespace:TestControl" x:Class="TestControl.MainWindow"
    Title="MainWindow" Height="170" Width="328">
    <Grid>
        <local:TestUserControl HorizontalAlignment="Left" Margin="76,57,0,0" VerticalAlignment="Top" Width="148"/>
    </Grid>
</Window>

最后MainWindow.xaml.cs

using System.Windows;

namespace TestControl
{
/// <summary>
/// Interaction logic for MainWindow.xaml
/// </summary>
public partial class MainWindow : Window
{
    public MainWindow()
    {
        InitializeComponent();
    }
}
}

希望,现在很清楚了,我想要什么.我想更改我的 UserControlContentTemplate.此更改应由正在监视属性 IsEditable 的触发器触发.

Hope, now it is clear, what I want. I want to change ContentTemplate of my UserControl. This change should be fired by trigger that is watching property IsEditable.

问题

IsEditable 属性正在更改,但触发器未触发.问题出在哪里?

The IsEditable property is changing, but the trigger is not firing. Where is the problem?

很抱歉我之前的帖子不清楚.

可以从与 Figures 相同的位置下载所有项目文件,只需将文件名更改为 TestControl.zip(不能发布两个以上的链接)

推荐答案

已解决!!!

我只是把 ContentControl 作为我的用户控件的内容

I just put as the content of my user control ContentControl

<ContentControl Style="{StaticResource UserControlStyle1}" />

ContentControl 的样式如下所示:

Style of the ContentControl looks like this:

<Style x:Key="UserControlStyle1" TargetType="{x:Type ContentControl}">

这里定义了默认模板

        <Setter Property="ContentTemplate" Value="{StaticResource CompactStyle}" />
        <Setter Property="Template">
            <Setter.Value>
                <ControlTemplate TargetType="{x:Type ContentControl}">
                    <Border BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" Background="{TemplateBinding Background}" Padding="{TemplateBinding Padding}" SnapsToDevicePixels="true">
                        <ContentPresenter HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}" VerticalAlignment="{TemplateBinding VerticalContentAlignment}"/>
                    </Border>

这是一个运行良好的触发器

Here is the trigger that is working pretty well

                    <ControlTemplate.Triggers>
                        <DataTrigger Binding="{Binding IsEditable, RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type local:PathNavigator}}}"  Value="True">
                            <Setter Property="ContentTemplate" PresentationTraceSources.TraceLevel="High" Value="{StaticResource EditableStyle}"  />
                        </DataTrigger>
                    </ControlTemplate.Triggers>
                </ControlTemplate>

            </Setter.Value>
        </Setter>
    </Style>

当然,我从 UserControl 中删除了样式

Of course, I removed the style from UserControl

这篇关于WPF 通过触发器更改 UserControl 中的 ContentTemplate的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆