Android仿微信带清除功能的输入框ClearEditText的实现
2016-03-23 19:15
666 查看
转载请注明出处:/article/7707986.html
今天跟大家分享一个控件ClearEditText-带清除功能的输入框。其实这个控件在IOS中很简单,只需要设置属性即可,但是在Android中就变得不是那么容易了。先说说我自己的设计思路:首先,输入框右边得加一个删除图标;其次,删除图标的显示和隐藏(当我们的输入框有内容输入了并且有焦点,我们显示删除图标;当输入框没有焦点,我们也隐藏图标;当输入框中没有内容了,我们隐藏删除图标);再次,点击删除图标,我们清空输入框中的内容,并隐藏删除图标。
那么下面我们来看看具体要怎么去实现呢?第一个问题就是我们怎么去给输入框右边添加删除图标,这个方法有多种,比如可以采用线性布局左边放一个EditText,右边放一个ImageView;设置EditText的属性值android:drawableRight。我采用的是后面的方法,就是直接给EditText设置属性值,这样我们的图标问题就解决了。下面我们来看一下效果图(为了好看点,drawableLeft我也设置了一个图标):
好了,接下来遇到问题了,就是android本身没有方法去对右边删除图标进行点击监听,那我们有没有办法间接的去实现它呢?当然是有的。我们其实可以通过EditText的Touch事件,来判断用户是否点击了删除图标的区域,如果是则表明点击了删除图标,否则就没有点击删除图标。下面我们看代码是怎么去实现这一过程的:
大于输入框左侧到clear图标左侧的距离,小与输入框左侧到clear图标右侧的距离,我们则认为是点击clear图标.
*getWidth():得到控件的宽度
* event.getX():抬起时的坐标(该坐标是相对于控件本身而言的)
* getTotalPaddingRight():clear图标左边缘至控件右边缘的距离
* getPaddingRight():clear图标右边缘至控件右边缘的距离
于是: getWidth() - getTotalPaddingRight()表示:
控件左边到clean的图标左边缘的区域 ;getWidth() - getPaddingRight()表示: 控件左边到clear图标右边缘的区域 。所以这两者之间的区域刚好是clear图标的区域。
setClearIconVisible()方法中,是利用setCompoundDrawables()方法来为ClearEditText绘制左右图标的,从而来控制clear图标的显示和隐藏。
setOnFocusChangeListener(this)是给控件设置了焦点改变监听。如果控件失去焦点,则隐藏clear图标,如果有焦点且内容长度不为0则显示图标。
addTextChangedListener(this)是给控件设置了内容改变监听。当控件有文字输入或删除就会调用相应的回调方法。
好了,下面我们来使用这个带清除功能的控件。
先写一个布局,如下:
今天跟大家分享一个控件ClearEditText-带清除功能的输入框。其实这个控件在IOS中很简单,只需要设置属性即可,但是在Android中就变得不是那么容易了。先说说我自己的设计思路:首先,输入框右边得加一个删除图标;其次,删除图标的显示和隐藏(当我们的输入框有内容输入了并且有焦点,我们显示删除图标;当输入框没有焦点,我们也隐藏图标;当输入框中没有内容了,我们隐藏删除图标);再次,点击删除图标,我们清空输入框中的内容,并隐藏删除图标。
那么下面我们来看看具体要怎么去实现呢?第一个问题就是我们怎么去给输入框右边添加删除图标,这个方法有多种,比如可以采用线性布局左边放一个EditText,右边放一个ImageView;设置EditText的属性值android:drawableRight。我采用的是后面的方法,就是直接给EditText设置属性值,这样我们的图标问题就解决了。下面我们来看一下效果图(为了好看点,drawableLeft我也设置了一个图标):
好了,接下来遇到问题了,就是android本身没有方法去对右边删除图标进行点击监听,那我们有没有办法间接的去实现它呢?当然是有的。我们其实可以通过EditText的Touch事件,来判断用户是否点击了删除图标的区域,如果是则表明点击了删除图标,否则就没有点击删除图标。下面我们看代码是怎么去实现这一过程的:
package com.wuping.clearedittext; import android.content.Context; import android.graphics.drawable.Drawable; import android.text.Editable; import android.text.TextWatcher; import android.util.AttributeSet; import android.widget.EditText; import android.view.MotionEvent; import android.view.View; import android.view.View.OnFocusChangeListener; public class ClearEditText extends EditText implements OnFocusChangeListener, TextWatcher { /* 右边删除图标的引用 */ private Drawable mClearDrawable; /* 输入框是否有焦点 */ private boolean hasFocus; 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 defStyleAttr) { super(context, attrs, defStyleAttr); init(); } private void init() { mClearDrawable = getResources().getDrawable(R.drawable.clear); mClearDrawable.setBounds(0, 0, mClearDrawable.getIntrinsicWidth(), mClearDrawable.getIntrinsicHeight()); // 删除图标默认隐藏 setClearIconVisible(false); // 设置输入框焦点改变监听 setOnFocusChangeListener(this); // 设置输入框中内容发生改变监听 addTextChangedListener(this); } /** * 当visible为true时,删除图标显示,当visible为false时,图标隐藏 * @param visible */ private void setClearIconVisible(boolean visible) { Drawable rightDrawable = visible ? mClearDrawable : null; setCompoundDrawables(getCompoundDrawables()[0], getCompoundDrawables()[1], rightDrawable, getCompoundDrawables()[3]); } @Override public boolean onTouchEvent(MotionEvent event) { switch (event.getAction()) { case MotionEvent.ACTION_UP: if (getCompoundDrawables()[2] != null) { boolean isClear = (event.getX() > (getWidth() - getTotalPaddingRight())) && (event.getX() < (getWidth() - getPaddingRight())); if (isClear) { setText(""); } } break; default: break; } return super.onTouchEvent(event); } /** * 当控件的焦点发生改变时会调用该方法。 * 当控件有焦点并且内容长度不为0则显示clear图标,否则隐藏。 */ @Override public void onFocusChange(View v, boolean hasFocus) { this.hasFocus = hasFocus; if(hasFocus){ setClearIconVisible(getText().length() > 0); }else{ setClearIconVisible(false); } } /** * 当控件的有内容改变时调用此方法。 * 有焦点并且内容长度不为0则显示clear图标,否则隐藏。 */ @Override public void onTextChanged(CharSequence text, int start, int lengthBefore, int lengthAfter) { if(hasFocus){ setClearIconVisible(text.length() > 0); } } @Override public void beforeTextChanged(CharSequence s, int start, int count, int after) { // TODO Auto-generated method stub } @Override public void afterTextChanged(Editable s) { // TODO Auto-generated method stub } }看onTouchEvent()方法:当我们触摸抬起(就是ACTION_UP的时候)的范围
大于输入框左侧到clear图标左侧的距离,小与输入框左侧到clear图标右侧的距离,我们则认为是点击clear图标.
*getWidth():得到控件的宽度
* event.getX():抬起时的坐标(该坐标是相对于控件本身而言的)
* getTotalPaddingRight():clear图标左边缘至控件右边缘的距离
* getPaddingRight():clear图标右边缘至控件右边缘的距离
于是: getWidth() - getTotalPaddingRight()表示:
控件左边到clean的图标左边缘的区域 ;getWidth() - getPaddingRight()表示: 控件左边到clear图标右边缘的区域 。所以这两者之间的区域刚好是clear图标的区域。
setClearIconVisible()方法中,是利用setCompoundDrawables()方法来为ClearEditText绘制左右图标的,从而来控制clear图标的显示和隐藏。
setOnFocusChangeListener(this)是给控件设置了焦点改变监听。如果控件失去焦点,则隐藏clear图标,如果有焦点且内容长度不为0则显示图标。
addTextChangedListener(this)是给控件设置了内容改变监听。当控件有文字输入或删除就会调用相应的回调方法。
好了,下面我们来使用这个带清除功能的控件。
先写一个布局,如下:
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent"> <com.wuping.clearedittext.ClearEditText android:id="@+id/password" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_marginLeft="10dp" android:layout_marginRight="10dp" android:layout_marginTop="10dp" android:singleLine="true" android:inputType="text" android:hint="输入密码" android:drawableLeft="@drawable/password" android:drawableRight="@drawable/clear" /> <com.wuping.clearedittext.ClearEditText android:layout_below="@id/password" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_marginLeft="10dp" android:layout_marginRight="10dp" android:layout_marginTop="10dp" android:singleLine="true" android:inputType="text" android:hint="确认密码" android:drawableLeft="@drawable/password" android:drawableRight="@drawable/clear" /> </RelativeLayout>直接运行程序,就可以了。效果我就不演示了,大家可以自己写个Demo测试,有什么问题请评论提出,谢谢。
相关文章推荐
- 微信accesstoken回调
- 微信高仿
- Android工具类— 分享到QQ(QQ空间)、微信(朋友圈)
- 微信公众号(服务号)接入开发(1)
- 微信公众平台接口开发-验证机制
- Jeewx捷微 , 免费微信公众账号管家系统发布,采用JAVA语言
- 银联支付、支付宝支付、微信支付三大支付
- 微信公众平台测试号
- ionic 完美仿微信摇一摇
- 微信博客
- Android仿微信图片上传,可以选择多张图片,缩放预览,拍照上传等
- 自定义ViewGroup打造微信朋友圈之九宫图效果
- 微信支付接口遇到的问题解决
- 微信,是怎么过来的
- 微信,是怎么过来的
- 微信入门 ——《微…
- 【小程序】使用io流实现对字符串的编码和解码
- 使用Ping++为你的Wordpress博客一键集成支付功能的插件使用图文教程
- iOS 自定义微信分享底部弹出选择界面
- 微信JS-SDK实现自定义分享功能,分享给朋友,分享到QQ,分享到微博