做Android开发稍微久一点的都知道,android之前的监听器基本都是setlistener,比如setOnClickListener,setTextChangeListener。
但是后来,android中很多的setlistener都被废弃了,用addlistener来替代,比如上面的setTextChangeListener。
本文主要就是用于探讨setlistener和addlistener的区别。
我们就以setOnClickListener和addTextChangedListener举例
/**
* Register a callback to be invoked when this view is clicked. If this view is not
* clickable, it becomes clickable.
*
* @param l The callback that will run
*
* @see #setClickable(boolean)
*/
public void setOnClickListener(@Nullable OnClickListener l) {
if (!isClickable()) {
setClickable(true);
}
getListenerInfo().mOnClickListener = l;
}
/**
* Adds a TextWatcher to the list of those whose methods are called
* whenever this TextView's text changes.
*
* In 1.0, the {@link TextWatcher#afterTextChanged} method was erroneously
* not called after {@link #setText} calls. Now, doing {@link #setText}
* if there are any text changed listeners forces the buffer type to
* Editable if it would not otherwise be and does call this method.
*/
public void addTextChangedListener(TextWatcher watcher) {
if (mListeners == null) {
mListeners = new ArrayList();
}
mListeners.add(watcher);
}
可以看到,setListener直接是给View中的一个listener赋了值。
代码中:
class ListenerTestActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_listener_test)
btn_test_setListener.setOnClickListener {
Log.e("set1", "1-listener is clicked")
}
btn_test_setListener.setOnClickListener {
Log.e("set2", "2-listener is clicked")
}
}
}
恩, 测试demo我使用的语言是kotlin,这里大家应该看得懂,也不复杂,也不影响结果,就不再写一个java版本了。
11-08 11:10:56.508 16788-16788/com.stanny.xbtest E/set2: 2-listener is clicked
11-08 11:10:57.475 16788-16788/com.stanny.xbtest E/set2: 2-listener is clicked
11-08 11:10:57.866 16788-16788/com.stanny.xbtest E/set2: 2-listener is clicked
可以看到,只有第二个点击事件被调用了,而第一个完全被覆盖了。
et_test_addListener.addTextChangedListener(object : TextWatcher {
override fun afterTextChanged(p0: Editable?) {
}
override fun beforeTextChanged(s: CharSequence?, start: Int, count: Int, after: Int) {
}
override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) {
if (et_test_addListener.text.length == 2) {
Log.e("add1", "1-listener is changed")
}
}
})
et_test_addListener.addTextChangedListener(object : TextWatcher {
override fun afterTextChanged(p0: Editable?) {
}
override fun beforeTextChanged(s: CharSequence?, start: Int, count: Int, after: Int) {
}
override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) {
if (et_test_addListener.text.length == 2) {
Log.e("add2", "2-listener is changed")
}
}
})
这里我给我的输入框添加了两个监听,都是在判断输入文字长度为2时,打印一段log
11-08 11:14:49.050 21397-21397/com.stanny.xbtest E/add1: 1-listener is changed
11-08 11:14:49.050 21397-21397/com.stanny.xbtest E/add2: 2-listener is changed
et_test_addListener.addTextChangedListener(object : TextWatcher {
override fun afterTextChanged(p0: Editable?) {
}
override fun beforeTextChanged(s: CharSequence?, start: Int, count: Int, after: Int) {
}
override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) {
if (et_test_addListener.text.length == 2) {
finish()//修改位置
}
}
})
et_test_addListener.addTextChangedListener(object : TextWatcher {
override fun afterTextChanged(p0: Editable?) {
}
override fun beforeTextChanged(s: CharSequence?, start: Int, count: Int, after: Int) {
}
override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) {
if (et_test_addListener.text.length == 2) {
Log.e("add2", "2-listener is changed")
}
}
})
我们第一个监听直接finish掉当前activity,那么第二个还会执行么
11-08 11:30:48.601 6465-6636/com.stanny.xbtest E/add2: 2-listener is changed
可以看到,即使activity已经被finish掉了,第二个监听仍然会执行
那么,你可能会说了,因为这两个是同时发生的,所以才会出现仍然会执行。好,我们继续
et_test_addListener.addTextChangedListener(object : TextWatcher {
override fun afterTextChanged(p0: Editable?) {
}
override fun beforeTextChanged(s: CharSequence?, start: Int, count: Int, after: Int) {
}
override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) {
if (et_test_addListener.text.length == 2) {
finish()
}
}
})
et_test_addListener.addTextChangedListener(object : TextWatcher {
override fun afterTextChanged(p0: Editable?) {
}
override fun beforeTextChanged(s: CharSequence?, start: Int, count: Int, after: Int) {
}
override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) {
if (et_test_addListener.text.length == 2) {
var timer = Timer()//修改位置
timer.schedule(object : TimerTask() {
override fun run() {
Log.e("add2", "2-listener is changed")
}
}, 1000)
}
}
})
11-08 11:36:02.633 11617-11855/com.stanny.xbtest E/add2: 2-listener is changed
那还有没有什么问题?
有的,因为我们现在只是简单的打印了文字,和当前的activity的数据或者控件都没有联系,所以,会不会是这个原因呢?
et_test_addListener.addTextChangedListener(object : TextWatcher {
override fun afterTextChanged(p0: Editable?) {
}
override fun beforeTextChanged(s: CharSequence?, start: Int, count: Int, after: Int) {
}
override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) {
if (et_test_addListener.text.length == 2) {
finish()
}
}
})
et_test_addListener.addTextChangedListener(object : TextWatcher {
override fun afterTextChanged(p0: Editable?) {
}
override fun beforeTextChanged(s: CharSequence?, start: Int, count: Int, after: Int) {
}
override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) {
if (et_test_addListener.text.length == 2) {
var timer = Timer()
timer.schedule(object : TimerTask() {
override fun run() {
Log.e("add2", "2-listener is changed")
btn_test_setListener.setText("123")//修改位置
}
}, 1000)
}
}
})
可以看到,我在第二个延时操作的时候,不仅仅打印了log,还给一个按钮设置了文字。
因为已经finish了,我们也看不到按钮是否改变了文字,但是,我可以确定,没有产生崩溃,没有报错信息。
那么,我们想知道,这个activity真的已经被finish掉了么?还是说,要等到添加的监听都实现完了才会被finish。
这个问题,等有时间,我再来研究。