使用 iValueConverter 格式化 TextBlock 的部分文本 [英] Format part of the text of TextBlock using iValueConverter

查看:18
本文介绍了使用 iValueConverter 格式化 TextBlock 的部分文本的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想将文本块的部分文本加粗.这是我在 IValueConverter 中尝试过的,但似乎不起作用.

I want to make part of the text of a textblock bold. This is what i tried in the IValueConverter but it does not seem to work.

public class Highlighter : IValueConverter
    {


        public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
        {
            if (value == null)
            {
                return null;
            }

            return "Question1:<Bold>Answer1</Bold>, Question2:<Bold>Answer2</Bold>, Question3:<Bold>Answer3</Bold>";

        }

        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            throw new NotImplementedException();
        }
    }

这不会使答案变粗.

这就是我在 XAML 中使用它的方式.

This is how i am using it in XAML.

<TextBlock Height="Auto" Width="Auto" MaxHeight="64" Text="{Binding Path=QuestionAnswer, Mode=OneWay, Converter={x:Static Highlighter}}" />

有没有办法通过格式化文本或将 TextBlock 发送到转换器来实现这一点?

Is there a way i can achieve this by formatting the text or by sending the TextBlock to the converter?

推荐答案

使用 TextBlock 控件绝对可行,但考虑到您可能想要切换到其他控件(ItemsControl 例如).

It is definitely possible to do with TextBlock control, but considering all the efforts you might want to switch to other control (ItemsControl for example).

无论如何,这是一个解决方案.实际上有几个问题需要解决:

Anyway, here is a solution. There are actually several problems to solve:

  1. TextBlock.Text 属性为 string,您不能为其分配预格式化的文本
  2. TextBlock.Inlines 可以接受格式化文本,但它是只读属性
  3. 您必须自己格式化文本(可能有一些简单的方法可以解析带有标签的文本并将格式化输出生成为 Inline 对象的集合,但我不知道)
  1. TextBlock.Text property is string, and you can't assign preformatted text to it
  2. TextBlock.Inlines can accept formatted text, but it is read-only property
  3. You'll have to format text yourself (probably there are easy ways to parse text with tags and produce formatted output as a collection of Inline objects, but I don't know any)

您可以创建一个附加属性来处理前两个问题:

You can create an attached property to deal with the first 2 problems:

public static class TextBlockEx
{
    public static Inline GetFormattedText(DependencyObject obj)
    {
        return (Inline)obj.GetValue(FormattedTextProperty);
    }

    public static void SetFormattedText(DependencyObject obj, Inline value)
    {
        obj.SetValue(FormattedTextProperty, value);
    }

    public static readonly DependencyProperty FormattedTextProperty =
        DependencyProperty.RegisterAttached(
            "FormattedText",
            typeof(Inline),
            typeof(TextBlockEx),
            new PropertyMetadata(null, OnFormattedTextChanged));

    private static void OnFormattedTextChanged(
        DependencyObject o,
        DependencyPropertyChangedEventArgs e)
    {
        var textBlock = o as TextBlock;
        if(textBlock == null) return;

        var inline = (Inline)e.NewValue;
        textBlock.Inlines.Clear();
        if(inline != null)
        {
            textBlock.Inlines.Add(inline);
        }
    }
}

XAML 会稍微改变:

XAML would change just a bit:

<TextBlock local:TextBlockEx.FormattedText="{Binding Path=QuestionAnswer,
                                                     Mode=OneWay,
                                                     Converter={x:Static Highlighter}}" />

请注意,您需要在 XAML 中的 xmlns:local="clr-namepace:<namespace_name>" 中声明 TextBlockEx 的位置映射您的命名空间.

Note that you'll need to map you namespace where TextBlockEx is declared in xmlns:local="clr-namepace:<namespace_name>" in XAML.

现在需要在转换器中构造格式化文本而不是纯文本来解决最后一个问题:

Now you need to construct formatted text in converter instead of plain text to solve the last problem:

public object Convert(object value, Type targetType, object parameter,
    CultureInfo culture)
{
    if(value == null)
    {
        return null;
    }

    var span = new Span();
    span.Inlines.Add(new Run("Question1: "));
    span.Inlines.Add(new Run("Answer1") { FontWeight = FontWeights.Bold });
    span.Inlines.Add(new Run(", "));

    span.Inlines.Add(new Run("Question2: "));
    span.Inlines.Add(new Run("Answer2") { FontWeight = FontWeights.Bold });
    span.Inlines.Add(new Run(", "));

    span.Inlines.Add(new Run("Question3: "));
    span.Inlines.Add(new Run("Answer3") { FontWeight = FontWeights.Bold });

    return span;
}

这篇关于使用 iValueConverter 格式化 TextBlock 的部分文本的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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