如何为 EditText 的 "textColorHint" 属性 设置动画?

How to animate the "textColorHint" property of an EditText?

我想在我的编辑文本中为提示的颜色设置动画,但以下方法似乎不起作用。

fun animateHintTextColorChange(et: EditText, colorFromResId: Int, colorToResId: Int) {
        val colorFrom = ContextCompat.getColor(et.context, colorFromResId)
        val colorTo = ContextCompat.getColor(et.context, colorToResId)
        val animator = ObjectAnimator.ofInt(et, "textColorHint", colorFrom, Color.RED)
        animator.setEvaluator(ArgbEvaluator())
        animator.start()
    }

创建自定义跨度

import android.text.TextPaint;
import android.text.style.CharacterStyle;
import android.text.style.UpdateAppearance;


public class CustomSpan extends CharacterStyle implements UpdateAppearance {

    private int color;

    public int getColor() {
        return color;
    }

    public void setColor(int color) {
        this.color = color;
    }

    public CustomSpan() {

    }

    @Override
    public void updateDrawState(TextPaint paint) {
        paint.setColor(color);

    }
}

然后使用ObjectAnimator

    final EditText editText = (EditText) this.findViewById(R.id.edit_text);

    CustomSpan span = new CustomSpan();

    final String text = getResources().getString(R.string.edit_hint);

    final SpannableString spannableString = new SpannableString(text);

    int start = 0;
    int end = text.length();
    spannableString.setSpan(span, start, end, 0);



    int colorFrom = Color.BLACK;
    int colorTo = Color.RED;
    int duration = 2000;

    final ObjectAnimator objectAnimator = ObjectAnimator.ofInt(
            span, CHANGE_COLOR_PROPERTY,  colorFrom, colorTo);

    objectAnimator.setEvaluator(new ArgbEvaluator());
    objectAnimator.setDuration(duration);
    objectAnimator.start();

    objectAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
        @Override
        public void onAnimationUpdate(ValueAnimator animation) {
           editText.setHint(spannableString);
        }
    });

自定义属性

private static final Property<CustomSpan, Integer> CHANGE_COLOR_PROPERTY
        = new Property<CustomSpan, Integer>(Integer.class, "CHANGE_COLOR_PROPERTY") {

    @Override
    public void set(CustomSpan span, Integer value) {
        span.setColor(value);
    }
    @Override
    public Integer get(CustomSpan object) {
        return object.getColor();
    }
};

注意:如果你的持续时间很慢,你会看到一些从开始颜色到结束颜色的中间颜色。

更新:我还建议查看 MutableForegroundSpan @ http://flavienlaurent.com/blog/2014/01/31/spans/

感谢@Nikola Despotoski 的提示,我找到了解决方案。

fun animateHintTextColorChange(editText: EditText, colorFrom: Int, colorTo: Int, startDelay: Long = 0) : Animator {
        val animator = ValueAnimator.ofObject(ArgbEvaluator(), colorFrom, colorTo)
        animator.duration = DURATION_MEDIUM
        animator.startDelay = startDelay
        animator.addUpdateListener { animator -> editText.setHintTextColor(animator.animatedValue as Int) }

        return animator
    }