如何在 XAML 代码中创建支持其中其他元素的 UserControl

Posted

技术标签:

【中文标题】如何在 XAML 代码中创建支持其中其他元素的 UserControl【英文标题】:How to create UserControl which support other element inside it in XAML code 【发布时间】:2020-02-09 01:09:47 【问题描述】:

我喜欢在我的UserControl 中插入其他FrameworkElements,但如果我在XAML 代码中这样做,控件将无法正常工作。 (我需要像Panel/Grid 类型control)。换句话说,它失去了contents。如何解决这个问题呢?我找到了一些示例,但这些示例在 UWP 中不起作用。我想保持以下示例非常简单,以说明我的意思和需要。

XAML

<!--THE CONTROL-->
<local:TestControl Width="300" Height="300">
    <!--LIKE TO ADD THIS ONE INSIDE THE CONTROL-->
    <TextBlock Text="Some Text"></TextBlock>
</local:TestControl>

用于控制的 XAML

<UserControl
    x:Class="MyApp.TestControl"
    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"
    mc:Ignorable="d"

    d:DesignHeight="300"
    d:DesignWidth="400">

    <Grid Background="DarkGray" BorderBrush="Black" BorderThickness="2" CornerRadius="10"></Grid>
</UserControl>

代码隐藏

namespace MyApp

    public sealed partial class TestControl : UserControl
    
        public TestControl()
        
            this.InitializeComponent();
        
    

【问题讨论】:

通过覆盖 Content 属性 怎么做? (覆盖内容) public override UIElement Content get /*... right code fx redirect to other control content ...*/ set /*... same strory as with getter ... too broad for SO ..*/ ? 【参考方案1】:

UserControl 替换为模板控件。

    创建一个名为 TestControl 的类,该类继承自 ContentControl

    public sealed class TestControl : ContentControl
    
        public TestControl() => DefaultStyleKey = typeof(TestControl);
    
    

    在您的项目中创建一个themes 文件夹,并将一个名为generic.xamlResourceDictinonary 添加到此文件夹中。 themes/generic.xaml 名称对于框架能够找到它很重要。在此文件中,您为控件定义了一个模板:

    <Style TargetType="local:TestControl">
        <Setter Property="Template">
            <Setter.Value>
                <ControlTemplate TargetType="local:TestControl">
                    <Grid Background="DarkGray" BorderBrush="Black" BorderThickness="2" CornerRadius="10">
                        <ContentPresenter />
                    </Grid>
                </ControlTemplate>
            </Setter.Value>
        </Setter>
    </Style>
    

    像以前一样创建控件的实例:

    <local:TestControl Width="300" Height="300">
        <!--LIKE TO ADD THIS ONE INSIDE THE CONTROL-->
        <TextBlock Text="Some Text"></TextBlock>
    </local:TestControl>
    

TextBlock 将在 ContentPresenter 元素位于 ControlTemplate 中的位置结束。

有关如何创建自定义控件的更多信息,请参阅@Jerry Nixon 的MSDN Magazine article。

【讨论】:

太棒了!我很欣赏这个答案。清晰有效!

以上是关于如何在 XAML 代码中创建支持其中其他元素的 UserControl的主要内容,如果未能解决你的问题,请参考以下文章

如何在 Rider 中创建 XAML + CodeBehind 对?

如何在 XAML 中公开控件以便在其他类中看到

如何将 xaml 模板打包成 nuget 包以供其他开发人员重用?

以编程方式寻址在 xaml 中创建的画布

winui中创建自定义控件库的正确方法

我应该如何阅读键盘输入以在 WPF 中创建 2D 游戏?