Xamarin 使用 DataTrigger 根据数据形成条件格式

问题描述

我正在 Xamarin Forms 中开发聊天应用程序,并尝试根据消息是传入消息还是传出消息添加条件格式。

这是我的 XAML:

               <Frame 
                    Margin="1"
                    Padding="0"
                    x:Name="FrameRef"
                    x:DataType="model:ChatMessage">
                    <Frame 
                        CornerRadius="10"
                        Padding="7"
                        BackgroundColor="LightBlue"
                        HasShadow="false"
                        Margin="10,10,80,0">
                        <Frame.Triggers>
                            <DataTrigger
                                targettype="Frame"
                                Binding="{Binding Source={x:Reference FrameRef},Path=x:DataType.From}" Value="+1456456456">
                                <Setter Property="BackgroundColor" Value="Yellow"/>
                            </DataTrigger>
                        </Frame.Triggers>

当我使用 Path="Margin" 和 Value="1" 时,它会起作用。

我现在正在尝试使其路径为 x:DataType="model:ChatMessage" 并检查“发件人”字段(指示消息是传入还是传出)。

解决方法

我不确定 Data Trigger 是否非常适合此应用程序,因为您实际上依赖于数据类型,而不是真正依赖于另一个字段的内容本身。来自文档:

DataTrigger 类适用于检查其他控件上的值,以及添加它的控件上的任何属性。

您可能想要的是一个值转换器,它可以处理定位静态资源并根据消息类型为您应用样式。完整的 Microsoft 文档 here

在您的 XAML 元素上,您将执行以下操作:

<Frame Style="{Binding foo,Converter={StaticResource FooToStyleConverter}}"/>

您的转换器的工作方式如下:

public class FooToStyleConverter : IValueConverter
{
    public object Convert(object value,Type targetType,object parameter,CultureInfo culture)
    {
        var someValue = (DataTye)value; // Convert 'object' to whatever type you are expecting

        // evaluate the converted value
        if (someValue.From != null && someValue.From == Enum.SomeoneElse)
            return (Style)App.Current.Resources["StyleReceived"]; // return the desired style indicating the message is from someone else

        return (Style)App.Current.Resources["StyleSent"]; // return a style indicating the message is from the sender
    }
    
    public object ConvertBack(object value,CultureInfo culture)
    {
        // Usually unused,but inverse the above logic if needed
        throw new NotImplementedException();
    }
}

最后,将转换器设置为 App.xaml 中的静态资源(或页面上的本地资源),以便您的页面可以正确引用它

<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
             xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
             xmlns:local="clr-namespace:DataBindingDemos">
    <ContentPage.Resources>
         <ResourceDictionary>
              <local:FooToStyleConverter x:Key="FooToStyleConverter" />
              ....