【问题标题】:A custom Textbox - WPF and Xaml自定义文本框 - WPF 和 Xaml
【发布时间】:2013-09-26 13:12:51
【问题描述】:

我想使用 XAML 和一个自定义类创建一个自定义 TextBox,该类具有一个名为 PosType 的 TextBox 附加属性。 PosType 将被渲染在侧面的红色三角形内。

TextBox 应该是一个普通的文本框,从左边有足够的边距,不会拦截其他文本。 这是显示文本框所需外观的图像。

控制类:

public class PosTextBox : TextBox
{
    public string PosType { get; set; }
}

**我写的样式:(与我想要的非常相似,除了这里我使用了边框,其他部分可能不准确。**

xmlns:Pro="clr-namespace:Prox.XamlControls">

<!-- Custom TextBox  -->
<Style x:Key="c1PosTextBox" TargetType="{x:Type Pro:PosTextBox}" >
    <Setter Property="OverridesDefaultStyle" Value="True" />
    <Setter Property="SnapsToDevicePixels" Value="True" />
    <Setter Property="Foreground" Value="White" />
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type Pro:PosTextBox}">

                <Grid>
                    <Border>
                        <Border>
                            <TextBlock Text ="{TemplateBinding Path= Pro:PosType}"></TextBlock>
                            <!--<TextBlock Text ="{TemplateBinding ElementName=Pro:PosTextBox, Path= Pro:PosType}"></TextBlock>-->
                        </Border>
                    </Border>
                    <Border Margin="5,10,5,10">
                        <ContentPresenter  Name="Content" Margin="{TemplateBinding Padding}" RecognizesAccessKey="True" TextBlock.Foreground="White"></ContentPresenter>
                    </Border>
                </Grid>

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

如何创建此自定义文本框并获得所需的外观?

编辑: 请指导我根据我上面提到的相同方法解决小问题。

【问题讨论】:

  • 我认为Adorners 是你要找的
  • 我很确定它可以通过两种方式完成,如果有人愿意分享,我希望听到关于这两种方法的答案。感谢提及这一点
  • 使用装饰器和附加行为来实现这一点,比为每个 UI 功能使用自定义类型(如 PosTextBox)更灵活。
  • 在尝试了一些建议的方法之后,我在这个案例上坚持了下来,根据我的需要,我想要与我在问题中提供的完全相同的方法,如果有人知道我该如何解决我提供的工作代码请以这种方式帮助我。

标签: c# wpf xaml


【解决方案1】:

你可以使用Adorners来做到这一点

装饰器在 UIElement 之上的另一个名为 AdornerLayer 的层中呈现,这可以为您带来所需的效果。

public class PosTypeAdorner : Adorner
{
     private string _posText;

     // Be sure to call the base class constructor. 
     public PosTypeAdorner (UIElement adornedElement, string posText) : base(adornedElement) 
     { 
           _posText = posText;
     }

     // A common way to implement an adorner's rendering behavior is to override the OnRender 
     // method, which is called by the layout system as part of a rendering pass. 
     protected override void OnRender(DrawingContext drawingContext)
     {
          // Draw the red triangle with it's text using the drawingContext here
     }
 }

假设您希望PosType 的文本可绑定,您应该将其设为Dependency property。 使用OnApplyTemplate 将装饰器附加到您的文本框

public class PosTextBox : TextBox
{
    public PosTextBox()
    {
    }

    public static readonly DependencyProperty PosTypeProperty =
        DependencyProperty.Register("PosType", typeof (string), typeof (PosTextBox), new PropertyMetadata(default(string)));

    public string PosType
    {
        get { return (string)GetValue(PosTypeProperty); }
        set { SetValue(PosTypeProperty, value); }
    }

    public override void OnApplyTemplate()
    {
        base.OnApplyTemplate();

        var layer = AdornerLayer.GetAdornerLayer(this);
        var posAdorner = new PosTypeAdorner(this, PosType);

        layer.Add(posAdorner);
    }
}

欲了解更多信息,您可以查看以下链接:

http://www.codeproject.com/Articles/54472/Defining-WPF-Adorners-in-XAML

http://www.nbdtech.com/Blog/archive/2010/06/21/wpf-adorners-part-1-ndash-what-are-adorners.aspx

http://www.nbdtech.com/Blog/archive/2010/06/28/wpf-adorners-part-2-ndash-placing-any-control-on-the.aspx

祝你好运

【讨论】:

  • 感谢您提供的信息,+1,但它不包含绑定到自定义控件的装饰器定义,这有助于我实现这一目标,您能否扩展您的答案。
  • 我尝试围绕这些主题进行游戏,并稍等片刻,如果我没有得到更好的答案会标记它,感谢您扩展它并提供您的解决方案。
  • @Sypress 扩展了我的答案。基本上剩下要做的就是绘制矩形。我从来没有真正实现过我自己的装饰器,只使用现有的装饰器,所以我不能向你发布如何做到这一点的代码,但它应该相当简单,并且在MSDN 上有很好的文档。祝你好运:)
  • 你的答案应该像我说的那样有效,它是一个很好的解决方案,但我仍然渴望找到一个与我提供的类似的正确解决方案,我的一些代码都是基于 Xaml 聚集在一个地方。我会更多地使用你的代码。可能在接下来的 12 小时内将其标记为答案;)
  • @Sypress 听起来不错 :) 不要忘记Adorner 将TextBox 作为其构造函数中的参数,您可以通过this.AdornedElement 访问它并根据它的高度绘制三角形/width/任何其他属性。看,我同意用所有的Drawing shindig 弄脏可能会很讨厌,但它对我们来说效果很好,并且被证明是一个非常好的解决方案。当我们重写我们的 xaml 以获得新的外观和感觉并且不必重写这部分,因为我们用装饰器实现它时,它的真正力量就自我评价了。只是需要考虑的事情:P
猜你喜欢
  • 2019-05-09
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-01-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2010-11-05
相关资源
最近更新 更多