今天我們開發時發生了「靈異事件」
各位看倌請看一下這段 code
view.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
GG.d("RDBG:onClick() => view.isClickable()="
+view.isClickable()+" / id="+view.getId());
}
});
然後觸發點擊輸出如下
你沒看錯,我們在 onClick 裡面印出 view 的 clickable 竟然是 false
見鬼了,這不合邏輯呀
都不行 click 了,還怎麼觸發 onClick method ?
講到這裡,有經驗的看倌們會說
一定是 setOnClickListener() 的順序錯了
各位可以看下方的原碼
public void setOnClickListener(@Nullable OnClickListener l) {
if (!isClickable()) {
setClickable(true);
}
getListenerInfo().mOnClickListener = l;
}
沒錯,若 setClickable(false) 是在 setOnClickListener() 前使用的話
setOnClickListener 時會自動幫您改回 true
必竟不能 click 的話,設監聽要幹麻,是吧?
但這也無法解釋此問題
因為我們在 onClick 裡面印出來的的確是 false
也就是說它不是被改掉的,而是真的 false,卻可點擊
為了找出問題原因
我們點進原碼一探究竟
終於在 View.dispatchTouchEvent() 中找到一點蛛絲馬跡
ListenerInfo li = mListenerInfo;
if (li != null && li.mOnTouchListener != null
&& (mViewFlags & ENABLED_MASK) == ENABLED
&& li.mOnTouchListener.onTouch(this, event)) {
result = true;
}
只有在符合 mOnTouchListener != null 而且 enabled 的情況下
才會執行 mOnTouchListener.onTouch()
所以我回頭 call setEnabled(false)
成功 !!!
不過這個方法是封鎖了全部的 touch 事件 ( ex: 長按、拖曳…等 )
之後再來研究有沒有更佳的解法。
文章標籤
全站熱搜
留言列表