android的事件处理机制

一、基于监听的处理机制

   控件 : 是编程中用到的,按钮就算是一个控件,窗口也是等等

   组件 : 是软件的一部分.软件的组成部分.

   插件 : 网页中用到的,flash插件,没有它浏览器不能播放flash.

 

1. 监听的处理流程

  ·基于监听的事件处理主要涉及3个对象:

  Event Source(事件源):事件发生的场所,通常就是组件,每个组件在不同情况下发生的事件不尽 相同。

  Event (事件):事件封装了界面组件上发生的事件,通常是用户的操作。

  EventListener(事件监听器):负责监听事件源所发生的事件,并对各种事件做出相应的处理。

 

  执行步骤:

    step1:为事件对象添加监听。

    step2:当事件发生时,系统会将事件封装成相应类型的事件对象。

    step3:监听器接收到事件对象后调用相应的事件处理来处理事件。

 

  几个常用的事件监听接口:

clipboard

  • View.OnClickListener:单击事件的事件监听器必须要实现的接口
  • View.OnCreateContextMenuListener:创建上下文菜单的事件监听器必须要实现的接口
  • View.OnFocusChangedListener:焦点改变事件的事件监听器必须实现的接口
  • View.OnKeyListener:按钮事件的事件监听器必须实现的接口
  • View.OnLongClickListener:长单击事件的事件监听器必须要实现接口
  • View.OnTouchListener:触摸事件的事件监听器必须要实现的接口

与普通java方法调用不同的是:普通java程序里的方法是由程序主动调用的,而事件处理中的初见处理器方法是由系统负责调用的

1. 内部类作为事件 监听器类

import android.app.Activity;
import android.content.DialogInterface;
import android.content.DialogInterface.OnClickListener;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.widget.Button;
import android.widget.Toast;
public class MainActivity extends Activity {   private Button Button;   @Override   protected void onCreate(Bundle savedInstanceState) {     super.onCreate(savedInstanceState);     setContentView(R.layout.activity_main);     Button = (android.widget.Button) findViewById(R.id.button);     Button.setOnClickListener(new EnterClickListener());   }
  
class EnterClickListener implements android.view.View.OnClickListener{     @Override     public void onClick(View v) {       Toast.makeText(getApplicationContext(), "内部类形式", Toast.LENGTH_SHORT).show();     }   }
}

 

2. 外部类作为事件监听器类

public class MainActivity extends Activity {  
  private EditText etNumber1;
  private EditText etNumber2;
  private Button btnResult;
  

  @Override   
protected void onCreate(Bundle savedInstanceState) {     super.onCreate(savedInstanceState);     setContentView(R.layout.activity_main);     findView();     btnResult.setOnClickListener(new Claculator(this,etNumber1,etNumber2));   }   private void findView() {     etNumber1 = (EditText) findViewById(R.id.operator1);     etNumber2 = (EditText) findViewById(R.id.operator2);     btnResult = (Button) findViewById(R.id.result);   } } 外部实现类: import android.app.Activity; import android.view.View; import android.view.View.OnClickListener; import android.widget.EditText; import android.widget.Toast; public class Claculator implements OnClickListener {   private Activity activity;   private EditText etNumber1;   private EditText etNumber2;   public Claculator(Activity activity,EditText editText,EditText editText2){   this.activity = activity;   this.etNumber1 = editText;   this.etNumber2 = editText2;  } @Override public void onClick(View v) { int number1 = Integer.parseInt(etNumber1.getText().toString().trim()); int number2 = Integer.parseInt(etNumber2.getText().toString().trim()); int result = number1 + number2; Toast.makeText(activity, "计算结果为:" + result, Toast.LENGTH_SHORT).show(); }

 

3. 匿名内部类作为事件监听器类

public class MainActivity extends Activity {
  private EditText etNumber1;
  private EditText etNumber2;
  private Button btnResult;
  @Override
  protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    findView();
    //btnResult.setOnClickListener(new Claculator(this,etNumber1,etNumber2));//是用外部类
    //是用匿名内部类
    btnResult.setOnClickListener(new OnClickListener() {
      @Override
      public void onClick(View v) {
        int number1 = Integer.parseInt(etNumber1.getText().toString().trim());
        int number2 = Integer.parseInt(etNumber2.getText().toString().trim());
        int result = number1 + number2;
        Toast.makeText(getApplicationContext(), "计算结果为:" + result, Toast.LENGTH_SHORT).show();
      }
    });
  }
  private void findView() {
    etNumber1 = (EditText) findViewById(R.id.operator1);
    etNumber2 = (EditText) findViewById(R.id.operator2);
    btnResult = (Button) findViewById(R.id.result);
  }

 

4.Activity作为事件监听器

public class MainActivity extends Activity implements OnClickListener{
    private EditText etNumber1;
    private EditText etNumber2;
    private Button btnResult;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
      super.onCreate(savedInstanceState);
      setContentView(R.layout.activity_main);
      findView();
      //btnResult.setOnClickListener(new Claculator(this,etNumber1,etNumber2));//是用外部类
      //是用匿名内部类
      /*btnResult.setOnClickListener(new OnClickListener() {
      @Override
      public void onClick(View v) {
        int number1 = Integer.parseInt(etNumber1.getText().toString().trim());
        int number2 = Integer.parseInt(etNumber2.getText().toString().trim());
        int result = number1 + number2;
        Toast.makeText(getApplicationContext(), "计算结果为:" + result, Toast.LENGTH_SHORT).show();
      }
    });*/

    btnResult.setOnClickListener(this);
  }

  private void findView() {
    etNumber1 = (EditText) findViewById(R.id.operator1);
    etNumber2 = (EditText) findViewById(R.id.operator2);
    btnResult = (Button) findViewById(R.id.result);
  }

  @Override
  public void onClick(View v) {
    int number1 = Integer.parseInt(etNumber1.getText().toString().trim());
    int number2 = Integer.parseInt(etNumber2.getText().toString().trim());
    int result = number1 + number2;
    Toast.makeText(getApplicationContext(), "计算结果为:" + result, Toast.LENGTH_SHORT).show();
  }
}

 

5. 绑定到组件事件属性

<Button
  android:paddingTop="20dp"
  android:id="@+id/result"
  android:layout_width="wrap_content"
  android:layout_height="wrap_content"
  android:text="结果"
  android:onClick="getResult"/>
public void getResult(View view){   int number1 = Integer.parseInt(etNumber1.getText().toString().trim());   int number2 = Integer.parseInt(etNumber2.getText().toString().trim());   int result = number1 + number2;   Toast.makeText(getApplicationContext(), "计算结果为:" + result, Toast.LENGTH_SHORT).show(); }

 

二、基于回调事件

1.回调机制与监听机制

如果说事件监听机制是一种委托的事件处理,那么回调机制则与之相反,对于基于事件的处理模型来说,事件源与事件监听器是统一的,或者说是事件监听器完全消失了,当用户在UI组件上触发某个事件时,组建自己特定的方法将会负责处理事件

为了使回调方法机制类处理UI组件上发生的事件,开发者需要为该组件提供对应的事件处理方法,而java是一种静态语言,无法为某个对象动态的添加方法,因此只能继续是用UI组件类,并通过重写该类的事件处理的方法来实现

  1. 新建一个工程,布局文件很简单,就一个textview,MainActivity.java中重写了onKeyDown和onKeyUp方法

代码如下

package cn.aiyuan1996.huidiao;
import android.app.Activity;
import android.os.Bundle;
import android.view.Gravity;
import android.view.KeyEvent;
import android.view.Menu;
import android.view.MenuItem;
import android.widget.TextView;
import android.widget.Toast;
public class MainActivity extends Activity {
  private TextView text;
  @Override   
protected void onCreate(Bundle savedInstanceState) {     super.onCreate(savedInstanceState);     setContentView(R.layout.activity_main);     text = (TextView) findViewById(R.id.text);   }   public void showText(String string){     text.setText(string);   }   public void showToast(String string){     Toast toast = Toast.makeText(this, string, Toast.LENGTH_LONG);     toast.setGravity(Gravity.TOP, 0, 100);     toast.show();   }   @Override   public boolean onKeyDown(int keyCode, KeyEvent event) {     switch (keyCode) {     case KeyEvent.KEYCODE_0:       showText("你按下了数字键0");       break;     case KeyEvent.KEYCODE_BACK:       showText("你按下了返回键");       break;     default:       break;   }   return super.onKeyDown(keyCode, event); }
  @Override   
public boolean onKeyUp(int keyCode, KeyEvent event) {     switch (keyCode) {     case KeyEvent.KEYCODE_0:       showToast("你松开了数字键0");       break;     case KeyEvent.KEYCODE_BACK:       showToast("你松开了返回键");       break;     default:       break;     }     text.setText("你没有按下任何键");     return super.onKeyUp(keyCode, event);   } }

 

几乎所有基于回调的事件都有一个boolean类型的返回值,发方法用于标识该处理方法是否能够完全处理该事件

  (1),如果处理事件的回调方法返回的值为true,则表明该处理方法已完全处理该事件,且事件不会被传播出去

  (2),如果处理事件的回调方法返回的值为false,则表明该处理方法并未完全处理该事件,且事件会被传播出去

 

对于基于回调的事件传播而言,某组件上所发生的事件不仅能触发该组件上的回调方法,也会触发该组件所在的activity类的回调方法-只要事件传播到该activity类

 

基于回调触摸事件处理

 屏幕事件的处理方法onTouchEvent(),该方法的返回值与键盘响应事件相同,都是当程序完整的处理的该事件,且不希望其他回调方法再次处理该事件时返回true,否则返回false .

  1)屏幕被按:下MotionEvent.getAction()==MotionEvent.ACTION_DOWN

  2)离开屏幕:MotionEvent.getAction()==MotionEvent.ACTION_UP

  3)在屏幕中拖动:MotionEvent.getAction()==MotionEvent.ACTION_MOVE

 

Handler类简介

Handler类主要有两个作用:在新启动的线程中发送消息,在主线程中获取和处理消息

只能通过回调的方法来实现-开发者只需要重写Handler类中处理的消息的方法即可,当新启动的线程发送消息时,消息会发送到与之关联的MessageQueue,而Handler会不断的从MessageQueue中获取并处理消息-这将导致Handler中的处理消息的方法被回调

下面是Handler类中常用的几个方法

public class MainActivity extends Activity {
  int[] imgList = new int[]{R.drawable.a,R.drawable.b,R.drawable.c,R.drawable.d,R.drawable.e,R.drawable.f};
  int currentIndex = 0;
  @Override
  protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    final ImageView imageView = (ImageView) findViewById(R.id.image);
    final Handler handler = new Handler(){
      @Override
      public void handleMessage(Message msg) {
        if(msg.what == 0x123){
          //动态修改图片
          currentIndex++;
          imageView.setImageResource(imgList[currentIndex%imgList.length]);
      }
    }
  };

  if(currentIndex <= imgList.length){
    new Timer().schedule(new TimerTask() {
      @Override
      public void run() {
        handler.sendEmptyMessage(0x123);
      }
    }, 0,1200);

  }
}

 

posted @ 2018-08-03 10:44  vvning  阅读(436)  评论(0编辑  收藏  举报