带有内容周围控件的ContentControl

本文关键字:控件 ContentControl 周围 | 更新日期: 2023-09-27 18:03:45

我想在WPF中创建一个可以包含一个元素的自定义ContentControl。这很简单,我做过很多次了。但是这里我想让内容控件的底部和左边都有标尺。我希望这些控件可以从后面的代码访问。我不知道该怎么走下去。我考虑了一个模板,但然后标尺控件将不容易访问。我还考虑过创建一个具有类似content的依赖属性的UserControl,但是对于该控件的用户来说,XAML并不像使用内容控件那样简单。

谢谢。

带有内容周围控件的ContentControl

可以使用模板部件。你可以在这个页面上看到一个完整的例子:

http://msdn.microsoft.com/en-us/library/ee330302 (v = vs.110) . aspx

从这个例子中,CustomControl是如何声明模板部分的:

[TemplatePart(Name = "UpButtonElement", Type = typeof(RepeatButton))] [...] public class NumericUpDown : Control [...]

以及如何访问它们:

  public override void OnApplyTemplate()
    {
        UpButtonElement = GetTemplateChild("UpButton") as RepeatButton;
        [...]
    }

您所要求的是能够以常用的两种不同方式使用内容,但同时使用一个控件。你可以这样做,但只需要2个不同的内容属性。您可以定义自己的次要内容属性集,但从HeaderContentControl派生要容易得多,它已经为您提供了Header属性。

为了允许控件的用户像普通的ContentControl一样对待它,并且只是将内容包含在标签中,您可以使用Header内容作为您定义UserControl样式的部分,并且可以从代码后访问。在该内容中,您可以在任何想要接收外部Content的地方放置ContentPresenter。然后你还需要调整ControlTemplate,只显示Header的内容(Content将在Header部分内,记住)。

<HeaderedContentControl x:Class="WpfApp.MyRulerControl"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:local="clr-namespace:WpfApp">
    <HeaderedContentControl.Template>
        <ControlTemplate TargetType="{x:Type local:MyRulerControl}">
            <Border Background="{TemplateBinding Background}">
                <ContentPresenter ContentSource="Header"/>
            </Border>
        </ControlTemplate>
    </HeaderedContentControl.Template>
    <HeaderedContentControl.Header>
        <StackPanel>
            <Border x:Name="Ruler1" Height="20"/>
            <ContentPresenter
                Content="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type local:MyRulerControl}}, Path=Content}"
                ContentTemplate="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type local:MyRulerControl}}, Path=ContentTemplate}"/>
            <Border x:Name="Ruler2" Height="20"/>
        </StackPanel>
    </HeaderedContentControl.Header>
</HeaderedContentControl>

现在你可以像平常一样使用控件了:

<local:MyRulerControl>
    <TextBlock Text="External content here"/>
</local:MyRulerControl>

您也可以从code-behind:

获取Header部分中的任何内容。
    public MyRulerControl()
    {
        InitializeComponent();
        Ruler1.Background = Brushes.Red;
        Ruler2.Background = Brushes.Blue;
    }