You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

在MAUI中通过样式使用IconTintColorBehavior的解决方案

MAUI中通过样式统一配置IconTintColorBehavior着色方案

编辑说明:感谢H.A.H指明方向,正确方案在文末!

我在MAUI项目中使用IconTintColorBehavior实现图标着色效果,已验证手动在页面内设置颜色可正常生效,现在希望通过资源字典中的样式统一配置着色颜色,避免重复代码。

尝试过的两种无效方案

方案1:直接给IconTintColorBehavior定义样式

样式资源字典代码:

<Style TargetType="tk:IconTintColorBehavior">
    <Setter Property="TintColor" Value="{AppThemeBinding Light={StaticResource Yellow100Accent}, Dark={StaticResource Blue200Accent}}"/>
</Style>

页面使用代码:

<Image Source="logo_transparent.svg" Aspect="AspectFit">
    <Image.Behaviors>
        <tk:IconTintColorBehavior/>
    </Image.Behaviors>
</Image>

结果:图标显示为纯白色,推测样式未生效,行为使用了默认的白色着色值。


方案2:继承IconTintColorBehavior实现自定义行为

自定义行为代码:

public class IconThemeColorBehavior : IconTintColorBehavior
{
    public static readonly BindableProperty AttachBehaviorProperty =
    BindableProperty.CreateAttached("AttachBehavior", typeof(bool), typeof(IconThemeColorBehavior), false, propertyChanged: OnAttachBehaviorChanged);

    public static bool GetAttachBehavior(BindableObject view)
    {
        return (bool)view.GetValue(AttachBehaviorProperty);
    }

    public static void SetAttachBehavior(BindableObject view, bool value)
    {
        view.SetValue(AttachBehaviorProperty, value);
    }

    static void OnAttachBehaviorChanged(BindableObject view, object oldValue, object newValue)
    {
        Entry entry = view as Entry;
        if (entry == null)
        {
            return;
        }

        bool attachBehavior = (bool)newValue;
        if (attachBehavior)
        {
            entry.Behaviors.Add(new IconThemeColorBehavior());
        }
        else
        {
            Behavior toRemove = entry.Behaviors.FirstOrDefault(b => b is IconThemeColorBehavior);
            if (toRemove != null)
            {
                entry.Behaviors.Remove(toRemove);
            }
        }
    }
}

样式资源字典代码:

<Style x:Key="ThemedIconStyle" TargetType="Image">
    <Setter Property="utils:IconThemeColorBehavior.TintColor" Value="{AppThemeBinding Light={StaticResource Yellow100Accent}, Dark={StaticResource Blue200Accent}}"/>
</Style>

页面使用代码:

<Image Source="logo_transparent.svg" Aspect="AspectFit" Style="{StaticResource ThemedIconStyle}"/>

结果:图标保持原始颜色,未应用着色效果。


正确方案:自定义集成IconTintColorBehavior的Image控件

创建继承自Image的自定义控件,内置IconTintColorBehavior的逻辑,支持通过绑定属性设置着色颜色,方便在样式中统一配置:

using CommunityToolkit.Maui.Behaviors;

namespace MauiUtils
{
    public class ImageTintColor : Image
    {
        public static readonly BindableProperty TintColorProperty =
        BindableProperty.Create(nameof(TintColor), typeof(Color), typeof(ImageTintColor), propertyChanged: OnTintColorChanged);

        public Color TintColor
        {
            get => (Color)GetValue(TintColorProperty);
            set => SetValue(TintColorProperty, value);
        }

        static void OnTintColorChanged(BindableObject bindable, object oldValue, object newValue)
        {
            var control = (ImageTintColor)bindable;
            var tintColor = control.TintColor;

            if (control == null)
            {
                return;
            }

            // 移除已存在的着色行为
            Behavior toRemove = control.Behaviors.FirstOrDefault(b => b is IconTintColorBehavior);
            if (toRemove is not null)
            {
                control.Behaviors.Remove(toRemove);
            }

            // 添加新的着色行为
            if (newValue is not null)
            {
                IconTintColorBehavior tintBehavior = new IconTintColorBehavior
                {
                    TintColor = tintColor
                };
                control.Behaviors.Add(tintBehavior);
            }

            // 注:注释的这段代码实际无作用
            // void OnHandlerChanged(object s, EventArgs e)
            // {
            //     OnTintColorChanged(control, oldValue, newValue);
            //     control.HandlerChanged -= OnHandlerChanged;
            // }
        }
    }
}

使用方式:在样式资源字典中为自定义控件配置TintColor,即可全局统一图标着色:

<Style TargetType="utils:ImageTintColor">
    <Setter Property="TintColor" Value="{AppThemeBinding Light={StaticResource Yellow100Accent}, Dark={StaticResource Blue200Accent}}"/>
</Style>

页面中直接使用自定义控件:

<utils:ImageTintColor Source="logo_transparent.svg" Aspect="AspectFit"/>

内容来源于Stack Exchange,提问作者GChapX

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.12 04:00:54