这个是在原有代码的基础上修改的,原有的ClearEditText 类,其实就是一个EditText, 在edittext的内容不为空的情况下,显示右边一个“X”就是清空按钮,而这个X基本就是一个drawable,但是这个drawable的出现消失,没有任何动画效果,就是突然蹦出来,个人感觉太生硬! 所以有了如下代码:
public class ClearEditText extends AppCompatEditText implements TextWatcher {
private Drawable mClearDrawable = null;
/**
* 是否开启动画
*/
private boolean isAnimationEnable = true;
/**
* 是否淡出、淡入动画正在执行
*/
private boolean isInFadeOut = false;
private boolean isInFadeIn = false;
/**
* 设置动画时长
*/
private int mDuration = 120;
private int mPreviousLength = 0;
private ValueAnimator fadeOut, fadeIn;
public ClearEditText(Context context) {
this(context, null);
}
public ClearEditText(Context context, AttributeSet attrs) {
this(context, attrs, android.R.attr.editTextStyle);
}
public ClearEditText(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
init();
}
private void init() {
addTextChangedListener(this);
}
@Override
public void setCompoundDrawables(Drawable left, Drawable top, Drawable right, Drawable bottom) {
super.setCompoundDrawables(left, top, null, bottom);
}
public void setDrawable(Drawable drawable) {
if (drawable != null) {
if (mClearDrawable != null
&& drawable == mClearDrawable)
return;
mClearDrawable = drawable;
mClearDrawable.setBounds(
0,
0,
mClearDrawable.getIntrinsicWidth(),
mClearDrawable.getIntrinsicHeight());
doChange();
}
}
@Override
public boolean onTouchEvent(MotionEvent event) {
if (event.getAction() == MotionEvent.ACTION_UP) {
//动画执行过程中不响应点击事件
if (!isInFadeIn && !isInFadeOut && mClearDrawable != null) {
boolean touchable = event.getX() > (getWidth() - getPaddingRight() - mClearDrawable.getIntrinsicWidth())
&& (event.getX() < ((getWidth() - getPaddingRight())));
if (touchable) {
setText("");
}
}
}
return super.onTouchEvent(event);
}
public void setDuration(int duration) {
mDuration = duration;
}
public boolean isAnimationEnable() {
return isAnimationEnable;
}
public void setAnimationEnable(boolean animationEnable) {
isAnimationEnable = animationEnable;
}
private void setClearIconVisible(boolean visible) {
final Drawable[] CompoundDrawables = getCompoundDrawables();
//在字符串变化非常快的时候动画来不及执行
//先取消之前的动画
if (fadeIn != null && isInFadeIn) {
fadeIn.cancel();
isInFadeIn = false;
}
if (fadeOut != null && isInFadeOut) {
fadeOut.cancel();
isInFadeOut = false;
}
if (visible && mClearDrawable != null) {
if (isAnimationEnable) {
mClearDrawable.setAlpha(0);
super.setCompoundDrawables(CompoundDrawables[0],
CompoundDrawables[1], mClearDrawable, CompoundDrawables[3]);
isInFadeIn = true;
fadeIn = ValueAnimator.ofInt(0, 255);
fadeIn.setDuration(mDuration);
fadeIn.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
@Override
public void onAnimationUpdate(ValueAnimator animation) {
int alpha = (int) animation.getAnimatedValue();
mClearDrawable.setAlpha(alpha);
if (alpha == 255) {
isInFadeIn = false;
}
}
});
fadeIn.start();
} else {
isInFadeIn = false;
super.setCompoundDrawables(CompoundDrawables[0],
CompoundDrawables[1], mClearDrawable, CompoundDrawables[3]);
}
} else if (!visible && mClearDrawable != null) {
if (isAnimationEnable) {
isInFadeOut = true;
fadeOut = ValueAnimator.ofInt(255, 0);
fadeOut.setDuration(mDuration);
fadeOut.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
@Override
public void onAnimationUpdate(ValueAnimator animation) {
int alpha = (int) animation.getAnimatedValue();
mClearDrawable.setAlpha(alpha);
if (alpha == 0) {
isInFadeOut = false;
ClearEditText.super.setCompoundDrawables(CompoundDrawables[0],
CompoundDrawables[1], null, CompoundDrawables[3]);
}
}
});
fadeOut.start();
} else {
isInFadeOut = false;
super.setCompoundDrawables(CompoundDrawables[0],
CompoundDrawables[1], null, CompoundDrawables[3]);
}
}
}
private void doChange() {
setClearIconVisible(getText().toString().length() > 0);
}
@Override
public void onTextChanged(CharSequence s, int start, int count,
int after) {
//只有字符串是从有到无,或从无到有才会执行
//比如:字符串长度从1变成2 dochange方法不会执行
if ((mPreviousLength == 0 && s.length() > 0)
|| (mPreviousLength > 0 && s.length() == 0)) {
doChange();
}
}
@Override
public void beforeTextChanged(CharSequence s, int start, int count,
int after) {
mPreviousLength = s.length();
}
@Override
public void afterTextChanged(Editable s) {
}
@Override
protected void onDetachedFromWindow() {
super.onDetachedFromWindow();
release();
}
private void release() {
if (mClearDrawable != null) {
mClearDrawable = null;
}
//必须释放,否则可能退出时动画还在执行,但mClearDrawable
//在上面释放了,所以不释放可能会有空指针异常
if (fadeIn != null) {
fadeIn.cancel();
fadeIn.removeAllUpdateListeners();
fadeIn = null;
}
if (fadeOut != null) {
fadeOut.cancel();
fadeOut.removeAllUpdateListeners();
fadeOut = null;
}
}
}