实现仿Iphone的带删除按钮的自定义的EditText

来源:互联网 发布:医院体检软件 编辑:程序博客网 时间:2024/06/05 19:11

这里写图片描述

效果图如上,同时,要是输入内容为null的话,在你提交内容的时候,会出现左右摇换的动画效果。

首先我们要自定义一个MyEditText extends EditText;

/** * @类描述:带清楚按钮的editText输入框 * @创建时间:2015年2月7日-上午11:25:08 * @修改人: * @修改时间: * @修改备注: * @版本: */public class MyEditText extends EditText implements          OnFocusChangeListener, TextWatcher {     /**     * @说明:清空按钮显示图标     * @名称:mClearDrawable     * @类型:Drawable     */        private Drawable mClearDrawable;     /**     * @说明:控件是否获得焦点     * @名称:hasFoucs     * @类型:boolean     * */    private boolean hasFoucs;    public MyEditText (Context context) {         this(context, null);     }     public MyEditText (Context context, AttributeSet attrs) {         /**注意这里android.R.attr.editTextStyle **/        this(context, attrs, android.R.attr.editTextStyle);     }     public MyEditText (Context context, AttributeSet attrs, int defStyle) {        super(context, attrs, defStyle);        init();    }    /**     * @方法说明:初始化控件数据     * @方法名称:init     * @返回值:void     */    private void init() {         /**获取EditText的DrawableRight,假如没有设置我们就使用默认的图片**/        mClearDrawable = getCompoundDrawables()[2];         if (mClearDrawable == null) {         /** throw new NullPointerException("You can add drawableRight attribute in XML");**/            mClearDrawable = getResources().getDrawable(R.drawable.delete_selector);         }         mClearDrawable.setBounds(                        0, 0,                         mClearDrawable.getIntrinsicWidth(),                         mClearDrawable.getIntrinsicHeight());         /**默认设置隐藏图标**/        setClearIconVisible(false);         /**设置焦点改变的监听**/        setOnFocusChangeListener(this);         /**设置输入框里面内容发生改变的监听**/        addTextChangedListener(this);     }     /**     * 因为我们不能直接给EditText设置点击事件,所以我们用记住我们按下的位置来模拟点击事件     * 当我们按下的位置 在  EditText的宽度 - 图标到控件右边的间距 - 图标的宽度  和     * EditText的宽度 - 图标到控件右边的间距之间我们就算点击了图标,竖直方向就没有考虑     */    @Override     public boolean onTouchEvent(MotionEvent event) {        if (event.getAction() == MotionEvent.ACTION_UP) {            if (getCompoundDrawables()[2] != null) {                boolean touchable = event.getX() > (getWidth() - getTotalPaddingRight())                        && (event.getX() < ((getWidth() - getPaddingRight())));                if (touchable) {                    this.setText("");                }            }        }        return super.onTouchEvent(event);    }    /**     * @重写方法名:onFocusChange     * @父类:@see android.view.View.OnFocusChangeListener#onFocusChange(android.view.View, boolean)     * @方法说明:当ClearEditText焦点发生变化的时候,判断里面字符串长度设置清除图标的显示与隐藏**/    @Override     public void onFocusChange(View v, boolean hasFocus) {         this.hasFoucs = hasFocus;        if (hasFocus) {             setClearIconVisible(getText().length() > 0);         } else {             setClearIconVisible(false);         }     }     /**     * @方法说明:设置清除图标的显示与隐藏,调用setCompoundDrawables为EditText绘制上去     * @方法名称:setClearIconVisible     * @param visible     * @返回值:void     */  protected void setClearIconVisible(boolean visible) {         Drawable right = visible ? mClearDrawable : null;         setCompoundDrawables(getCompoundDrawables()[0],                 getCompoundDrawables()[1], right, getCompoundDrawables()[3]);     }    /**     * @重写方法名:onTextChanged     * @父类:@see android.widget.TextView#onTextChanged(java.lang.CharSequence, int, int, int)     * @方法说明:主要监控输入框,当存在内容时候,显示删除的按钮     */      @Override     public void onTextChanged(CharSequence s, int start, int count,             int after) {                 if(hasFoucs){                    setClearIconVisible(s.length() > 0);                }    }     @Override     public void beforeTextChanged(CharSequence s, int start, int count,             int after) {     }     @Override     public void afterTextChanged(Editable s) {     }     /**     * @方法说明:设置摇换动画     * @方法名称:setShakeAnimation     * @返回值:void     **/    public void setShakeAnimation(){        this.setAnimation(shakeAnimation(5));    }    /**     * @方法说明:摇换的动画     * @方法名称:shakeAnimation     * @param counts一秒钟摇换多少次     * @return     * @返回值:Animation     */      public static Animation shakeAnimation(int counts){        Animation translateAnimation = new TranslateAnimation(0, 10, 0, 0);        translateAnimation.setInterpolator(new CycleInterpolator(counts));        translateAnimation.setDuration(1000);        return translateAnimation;    }}

现在我们看看第二个构造函数里面的那个xml属性,这里我们并没有自己写这些属性,而是调用的系统中的属性,那我们来看看系统的源码:

<!-- Default EditText style. --><attr name="editTextStyle" format="reference" />

此处,从我自己的理解来说,就是从外部引入editText外部样式属性,而此处我们并没有自定义生成attrs.xml,而是引用系统本身存在的这些属性;

那我们如何在xml中引用这个自定义的控件呢?

<com.lzp.widget.MyEditText            android:id="@+id/sign_note"            android:layout_width="fill_parent"            android:layout_height="wrap_content"            android:layout_marginLeft="20dp"            android:layout_marginRight="20dp"            android:background="@drawable/login_edit_normal"            android:drawableRight="@drawable/delete_selector"                       android:hint="消息发送限定100字以内"            android:maxLength="101" ></com.lzp.widget.MyEditText>

现在我们注意下,引用自定义的控件时候,我们往往要

<包名.自定义类名    ......></包名.自定义类名>

最后,我们在xxx.java文件中引入我们的工程属性。

     MyEditText editText = (MyEditText) findViewById(R.id.sign_note);    ((Button) findViewById(R.id.button))                .setOnClickListener(new OnClickListener() {                    @Override                    public void onClick(View v) {                        if (TextUtils.isEmpty(editText.getText())) {                            // 设置晃动                            username.setShakeAnimation();                            // 设置提示                            showToast("不能为空");                            return;                        }                        ...                    }        });

最后,声明下,本篇博文只是自己作为知识巩固,以及整理收集。不喜勿喷!谢谢!

0 0
原创粉丝点击