【问题标题】:UWP How to create user control that hosts content?UWP 如何创建承载内容的用户控件?
【发布时间】:2018-12-09 05:40:28
【问题描述】:

我在尝试实现一件非常微不足道的事情时感到非常沮丧(或者至少,我期望的事情应该是微不足道的......)

我有一个需要自定义切换按钮的要求,为此我需要创建一个承载切换按钮的用户控件,并承载该用户控件中描述的内容。我做了一个小程序来演示“需求”。

<local:MyUserControl1>
    <TextBlock>Just an example</TextBlock>
</local:MyUserControl1>

MyUserControl1 如下所示:

<UserControl
    x:Class="App2.MyUserControl1"
    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" Name="Bla" d:DesignHeight="300" d:DesignWidth="400">
    <UserControl.Resources>
        <Style TargetType="ToggleButton">
            <Setter Property="Template">
                <Setter.Value>
                    <ControlTemplate>
                        <Grid>
                            <Ellipse Width="300" Height="300" Fill="Blue"/>
                            <ContentPresenter Content="{Binding ElementName=Bla, Path=MainContent}"/>
                        </Grid>
                    </ControlTemplate>
                </Setter.Value>
            </Setter>
        </Style>
    </UserControl.Resources>

    <ToggleButton/>
</UserControl>

后面的代码:

    public static DependencyProperty MainContentProperty = DependencyProperty.Register(
        "MainContent",
        typeof(object),
        typeof(MyUserControl1),
        null);

    public object MainContent
    {
        get => GetValue(MainContentProperty);
        set => SetValue(MainContentProperty, value);
    }

当我运行应用程序时,会显示文本,但样式/切换按钮被忽略/未应用/无论如何。

视觉树确认我做错了:

我查看了许多其他相关的 SO Q&A,但我仍然不知道如何以我想要的方式使其工作。

【问题讨论】:

    标签: c# uwp controltemplate


    【解决方案1】:

    您的代码应该可以工作,只是没有显示ContentPropertyAttribute 应该在的位置。您能否确保 MyUserControl1 已识别其内容属性,看看是否有帮助。

    [ContentProperty(Name = "MainContent")]
    public sealed partial class MyUserControl1 : UserControl
    ...
    

    更新

    下面有完整的代码,用 Win 10 Pro 1803、build 17134、NETCore 6.2.2 测试。

    请注意,您可以在 UserControl.Resources 或外部资源中定义控件模板,以将其与“主”UI 布局分开,或者将其保留在 ToggleButton.Template 中以减少 XAML 的几行。

    UserControlWithContent.xaml

    <UserControl
        x:Class="SmallTests2018.UserControlWithContent"
        x:Name="Self"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
    
        <ToggleButton>
            <ToggleButton.Template>
                <ControlTemplate>
                    <Grid>
                        <Ellipse Width="300" Height="300" Fill="Blue"/>
                        <ContentPresenter
                            HorizontalAlignment="Center"
                            VerticalAlignment="Center"
                            Content="{Binding MainContent, ElementName=Self, FallbackValue='{}{ content }'}" />
                    </Grid>
                </ControlTemplate>
            </ToggleButton.Template>
        </ToggleButton>
    </UserControl>
    

    UserControlWithContent.xaml.cs

    using Windows.UI.Xaml;
    using Windows.UI.Xaml.Controls;
    using Windows.UI.Xaml.Markup;
    
    namespace SmallTests2018
    {
        [ContentProperty(Name = "MainContent")]
        public sealed partial class UserControlWithContent : UserControl
        {
            public UserControlWithContent()
            {
                this.InitializeComponent();
            }
    
            public static DependencyProperty MainContentProperty =
                DependencyProperty.Register("MainContent", typeof(object), typeof(UserControlWithContent), null);
    
            public object MainContent
            {
                get => GetValue(MainContentProperty);
                set => SetValue(MainContentProperty, value);
            }
        }
    }
    

    UserControlWithContentPage.xaml

    <Page
        x:Class="SmallTests2018.UserControlWithContentPage"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:local="using:SmallTests2018"
        Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
    
        <Viewbox>
            <local:UserControlWithContent>
                <TextBlock FontSize="32" Foreground="Yellow">Just an example</TextBlock>
            </local:UserControlWithContent>
        </Viewbox>
    </Page>
    

    页面 XAML 设计器屏幕截图

    【讨论】:

    • 好吧,由于基于您的代码的方法对我有用,我将在此处发布完整的代码,以防万一它可能对某人有所帮助。
    • 哈!一点一点地复制,这也适用于我的电脑。我在风格上使用的方法当时似乎不起作用。您的方式我也不必(/不允许)使用&lt;UserControl.MainContent&gt; 标签定义主页中的内容。无论如何,这很好地完成了工作!谢谢,那我下次再用:)
    猜你喜欢
    • 1970-01-01
    • 2019-05-08
    • 1970-01-01
    • 2010-10-19
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-05-09
    • 1970-01-01
    相关资源
    最近更新 更多