1. 程式人生 > 實用技巧 >Android事件處理

Android事件處理

Android事件處理

  • 掌握回撥機制的事件處理方法,學會處理相關事件
  • 掌握基於監聽介面機制的事件處理方法,學會處理相關事件
  • 掌握手勢的建立、到處與識別的相關知識,可以實現手勢識別的功能
  • 掌握Handler訊息機制原理,會使用Handler進行執行緒間通訊
graph TB Android中的事件-->鍵盤事件 & 觸控事件 Android中的事件處理機制-->居於回撥機制的事件處理 & 基於監聽介面的事件處理

1.基於回撥機制的事件處理

當用戶與UI控制元件發生某個事件(如按下、滑動、雙擊事件)時,程式會呼叫控制元件自己特定的方法處理該事件,這個處理過程就是基於回撥機制的事件處理。


Android系統提供的回撥方法:

方法 說明
boolean onKeyDown(int keyCode,KeyEvent event) 當用戶在該控制元件上按下某個鍵時觸發的方法
boolean onKeyUp(int keyCode,KeyEvent event) 當用戶在該控制元件上鬆開某個鍵時觸發的方法
boolean onTouchEvent(MotionEvent event) 當用戶在該控制元件上觸發觸控事件時觸發的方法
boolean onFocusChanged(MotionEvent event) 當用戶在該控制元件上的焦點發生改變時觸發的方法

這些回撥機制的事件處理方法都有一個boolean型別的返回值,這個返回值用與標記當前事件是否已經處理完畢

  • 當返回為true時,表示已經完整處理了 事件,並不希望其它的回撥方法再次進行處理
  • 當返回為false時,表示並沒有完全處理完事件,更希望其它的回撥方法繼續對其進行處理

(1)onKeyDown()方法

public boolean onKeyDown(int keyCode,KeyEvent event)
  • keyCode:表示被按下的鍵值(鍵盤碼)

(2)onKeyUp()方法

public boolean onKeyDown(int keyCode,KeyEvent event)

​ onKeyDown()方法和onKeyUp()方法是介面KeyEvent.Callback中的抽象方法。Android中的所有View都實現了KeyEVent.Callback介面並重寫了onKeyDown()方法

/*示例程式碼
通過onKeyDown()方法來屏幕後退鍵以及在該方法中通過Toast來提示使用者增加音量的資訊
*/
public class MainActivity extends AppCompatActivity{
    protected void onCreate(Bundle savedInstanceState){
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);	//設定頁面佈局
    }
    public boolean onKeyDown(int keyCode,KeyEvent event){
        if(keyCode==KeyEvent.KEYCODE_BACK){		//點選了後退鍵
            Toast.makeText(this,"點選了後退鍵",Toast.LENGHT_SHORT).show();
            	return true;	//遮蔽後退鍵
        }else if(keyCode==KeyEvent.KEYCODE_VOLUME_UP){		//點選了音量增加鍵
            Toast.makeText(this,"音量增加",Toast.LENGHT_SHORT).show();
            	return true;
        }
        return super.onKeyDown(keyCode,event);
    }
}

​ Android裝置可用物理按鍵及其觸發事件:

物理按鍵 KeyEvent 說明
電源鍵 KEYCODE_POWER 啟動或喚醒裝置,將介面切換到鎖定的螢幕
後退鍵 KEYCODE_BACK 返回到前一個介面
Home鍵 KEYCODE_HOME 返回到Home介面
相機鍵 KEYCODE_CAMERA 啟動相機
音量鍵 KEYCODE_VOLUME_UP 控制當前上下文音量(如音樂播放器,手機鈴聲,通話音量等)
KEYCODE_VOLUME_DOWN

(3)onTouchEvent()方法

​ 該方法是在View類中定義的,並且所有的View的子類中全部重寫了onTouchEvent()方法

public boolean OnTouchEvent(MotionEvent event)

​ 當螢幕被觸控時,會自動呼叫onTouchEvent()方法來處理事件,通過該方法中的event.getAction()方法的值來判斷觸控事件。

​ 一般情況下,onTouchEvent()方法處理的事件分為三種:

描述
ACTION_DOWN 螢幕被按下
ACTION_UP 螢幕被彈起
ACTION_MOVE 在螢幕中拖動
public class MainActivity extends AppCompatActivity {
    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        MyButton button = new MyButton(this);	//建立一個自定義的Button物件
        button.setText("hello");		//設定Button控制元件的文字
        button.setTextSize(20);			//設定Button控制元件的文字大小
        button.setAllCaps(false);		//設定Button控制元件原樣輸出文字
        setContentView(button);			//將按鈕設定到介面上
    }
    class MyButton extends Button{		//自定義一個Button控制元件
        public MyButton(Context context){
            super(context);
        }
        public boolean onTouchEvent(MotionEvent event){		//重寫觸控事件的處理方法
            switch (event.getAction()){
                case MotionEvent.ACTION_DOWN:
                    Toast.makeText(MainActivity.this,"被按下",Toast.LENGTH_SHORT).show();
                    break;
                case MotionEvent.ACTION_UP:
                    Toast.makeText(MainActivity.this,"被彈起",Toast.LENGTH_SHORT).show();
                    break;
                case MotionEvent.ACTION_MOVE:
                    Toast.makeText(MainActivity.this,"被拖動",Toast.LENGTH_SHORT).show();
                    break;
            }
            return super.onTouchEvent(event);
        }

    }
}

(4)onFocusChanged()方法

​ 該方法只能在View中重寫。

public void onFocusChanged(boolean gainFocus,int direction,Rect previouslyFocusedRect)
  • gainFocus:表示觸發該事件的View是否獲得了焦點,當控制元件獲取焦點時,引數gainFocus的值為true,否則為false
  • direction:表示焦點移動的方向,用數值來表示
  • previouslyFocusedRect:表示在觸發事件的View的座標系中,前一個獲得焦點的矩形區域。如果該引數不可用,則設定為null

2.基於監聽介面的事件處理

在事件監聽的處理模型中主要設計3個方面:

  • Event Source(事件源):事件發生的場所,通常是各個元件
  • Event(事件):封裝了介面元件發生的特定事情(通常指使用者的一次操作),如果程式需要獲取介面元件發生事件的相關資訊,可以通過Event物件獲取
  • Event Listener(事件監聽器):負責監聽事件源發生的事件,並對各種事件作出相應的響應
graph TB A[外部操作]-->|2.觸發事件源上的事件|B[Event Source] B-->|3.生成事件物件|C[Event] C-->|4.觸發事件監聽器,射箭本身作為引數傳入到事件處理器|D[EventListener] D-->|5.呼叫事件處理器處理事件|E1[事件處理器] D-->|1.將事件監聽器註冊到事件源|B

監聽的一般步驟

  1. 獲取普通介面元件(事件源),即被監聽的物件
  2. 實現事件監聽器類
  3. 事件呼叫setXxxListener()方法,將事件監聽器物件註冊給普通元件(事件源)

View類中的內部介面

介面名稱 說明
View.OnClickListener 單擊事件的事件監聽器必須實現的介面
View.OnLongClickListener 長按事件的事件監聽器必須實現的介面
View.onFocusChangeListener 焦點改變事件的事件監聽器必須實現的介面
View.OnKeyListener 按鍵事件的事件監聽器必須實現的介面
View.OnTouchListener 觸控事件的事件監聽器必須實現的介面

1.OnClickListener介面

​ 該介面中需要實現的方法的定義方式:

public void onClick(View v)
/*示例程式碼*/
public class MainActivity extends AppCompatActivity implements View.OnClickListener{
   	private Button button;
    protected void onCreate(Bundle SavedInstanceState){
        super.onVreate(SavedInstanceState);
        setContentView(R.layout.activity_main);		//設定MainActivity對應的佈局檔案
        button = (Button) findViewById(R.id.button);	//獲取介面上的按鈕控制元件
        button.setOnClickListener(this);	//註冊監聽器
    }
    public void onClick(View v){	 //實現點選事件的監聽方法
    	if(v==button){				//判斷點選的控制元件是否時button
            Toast.makeText(MainActivity.this,"點選了按鈕",Toast.LENGTH_SHORT).show();
        }
    }
}

​ ??????????????????

​ 通過匿名內部類實現OnClickListener介面

/*示例程式碼*/
public class MainActivity extends AppCompatActivity implements View.OnClickListener{
   	private Button button;
    protected void onCreate(Bundle SavedInstanceState){
        super.onVreate(SavedInstanceState);
        setContentView(R.layout.activity_main);		//設定MainActivity對應的佈局檔案
        button = (Button) findViewById(R.id.button);	//獲取介面上的按鈕控制元件
        	
        	//通過匿名內部類來實現OnClickListener介面
        button.setOnClickListener(new View.OnClickListener(){
             public void onClick(View v){	 
    			if(v==button){				
           			 Toast.makeText(MainActivity.this,"點選了按鈕",Toast.LENGTH_SHORT).show();
       			 }
  		 	}
        });
    }  
}

2.OnLongClickListener介面

​ 該介面需要實現的方法的定義方式:

public boolean onLongClick(View view)

3.OnFocusChangeListener介面

​ 該介面需要實現的方法的定義方式:

public boolean onFocusChange(View v,boolean hasFocus)
  • v:表示觸發焦點發生改變事件的事件源
  • hasFoucs:表示v是否獲取焦點

4.OnKeyListener介面

​ 該介面需要實現的方法的定義方式:

public boolean onKey(View v,int keyCode,KeyEvent keyEvent)
  • keyCode:表示鍵盤的鍵盤碼
  • keyEvent:表示鍵盤事件封裝類的物件,其中包含了事件的詳細資訊(例如:發生的事件,事件型別等資訊)

5.OnTouchListener介面

public boolean onTouch(View v,MotionEvent motionEvent)
  • motionEvent:表示事件封裝類的物件,其中包含了觸控事件的詳細資訊(例如:發生的事件,事件型別等資訊)