【UWP】仅在TextBlock文本溢出时显示Tooltip
前言
这是我今天在回答SO问题时偶然遇到的,觉得可能还比较通用,就记录下来以供参考。
通常,我们使用ToolTip
最简单的方式是这样:
<TextBlock Text="Test"
ToolTipService.ToolTip="Test"
/>
这样在光标悬浮在TextBlock
上方时,会显示一个提示条,但是这似乎又违背了一个设计原则:
ToolTip作为提示,应该仅在当前内容显示不全,且用户有意愿查看完整内容时作为替代元素出现
这很好理解,如果TextBlock
足以显示所有文本内容,那么显示Tooltip
显然是多此一举的事情。但UWP并没有对这种常见的情况进行自动处理,比如将TextBlock
在文本溢出时自动显示Tooltip
作为一个默认行为,所以我们就需要自己来实现这个操作。
思路
我能想到的思路是借助TextBlock.IsTextTrimmed
属性,在True
的时候设置Tooltip的值为TextBlock.Text
,在False
的时候设置Tooltip
的值为null
。
但在实际创建的时候,我发现这很难做到,原因如下:
- Converter的
ConverterParameter
属性是一个简单对象(object),无法通过绑定进行传值(只有DependencyProperty
才能使用绑定),这意味着我无法在绑定IsTextTrimmed
的同时通过ConverterParameter
属性传入Text的值 - 我也不能直接在Converter内绑定
TextBlock
本身,目标太大,而我只想要IsTextTrimmed
属性改变时进行判断.
综上,在查找一些资料后,我决定改造一下Converter
本身。
解决方法
Converter
public class TrimConverter : DependencyObject, IValueConverter
{
public string Text
{
get { return (string)GetValue(TextProperty); }
set { SetValue(TextProperty, value); }
}
public static readonly DependencyProperty TextProperty =
DependencyProperty.Register("Text", typeof(string), typeof(TrimConverter), new PropertyMetadata(""));
public object Convert(object value, Type targetType, object parameter, string language)
{
bool isTrim = System.Convert.ToBoolean(value);
return isTrim ? Text : null;
}
public object ConvertBack(object value, Type targetType, object parameter, string language)
{
throw new NotImplementedException();
}
}
我在Converter内部创建了一个DependencyProperty
用来存放TextBlock.Text
的值。
使用
<Page.Resources>
<local:TrimConverter x:Key="TrimConverter" Text="{Binding ElementName=TestBlock,Path=Text}"/>
</Page.Resources>
...
<TextBlock MaxWidth="100" TextTrimming="CharacterEllipsis"
x:Name="TestBlock"
ToolTipService.ToolTip="{Binding ElementName=TestBlock,
Path=IsTextTrimmed,
Converter={StaticResource TrimConverter}}"/>
在XAML界面中完成绑定后,实测可以解决我的需求。
但是这个解决方法并不完美,它有一个问题:
和TextBlock本身耦合,由于Text值需要绑定,只能一个TextBlock创建一个Converter,不能够复用
实现在TextBlock文本溢出时显示Tooltip有多种实现方式,我只提出了一种,以供参考。