Android攻城狮Handler简介

Handler是什么?
Handler是Android提供的一套用来更新UI的机制,也是一套消息处理机制,可以通过它发送消息,也可以通过它处理消息。
所有Activity生命周期回调的方法(例如onCreate()、onDestory()等等),都是通过handler机制去发送消息的,然后根据不同的消息(message)做相应的分支处理。例如发送一个消息给 Framework,告知需要调用onCreate()或onDestory()方法。实际上在 Framework 当中,Activity的交互大部分都是用AMS(Activity Manager Service)做处理的。整个应用程序的核心的一个类就是 Activity Thread,Activity Thread就是通过handler机制接收到 Activity Manager Service发送的有关Activity生命周期的管理的消息(比如启动)。

为什么要使用Handler?
Android在设计的时候,就封装了一套消息的创建、传递、处理机制,如果不遵循这样的机制,就没有办法更新UI信息,并且会抛出异常信息。这样的机制便包含Handler机制。
1. 我们要创建一个handler的时候,它会和默认的一个线程进行绑定,而这个默认的线程当中就有一个MessageQueue(消息队列)。
2. handler的两个用途:(1)定时发送一个Messages或者Runnables对象;(2)可以在一个线程当中去处理并执行一个Action的动作。
3. 主线程运行一个消息队列,并管理着一些顶级的应用对象(top-level application objects),包括Activity、Broadcast Receiver等等,这些对象默认都是创建在Activity Thread(也就是我们常说的UI线程或者主线程)当中。
Handler的示例,实现图片轮播。
代码实现
1. 在主布局中定义一个ImageView控件。
2. 在 MainActivity 中创建并初始化ImageView,定义一个图片数组 images 和数组下标索引 index,创建一个Handler对象。
3. 创建一个内部类 MyRunnable 实现 Runnable 接口,重写 run() 方法:
   public void run() {
       index++;
       index = index%3; // 图片轮播(一般是通过ViewPager实现图片轮播)
       imageView.setImageResource(images[index]);
       handler.postDelayed(myRunnable,1000); // 每隔一秒换一次图片
   }
4. 在onCreste()方法中调用handler,也就是在主线程中调用handler:
   handler.postDelayed(myRunnable,1000);
  1 public class MainActivity extends ActionBarActivity {
  2      private Handler handler1 = new Handler();
  3     private Handler handler2 = new Handler(new Callback() {
  4
  5         @Override
  6         public boolean handleMessage(Message msg) {
  7             // TODO Auto-generated method stub
  8             Toast.makeText(getApplicationContext(), "1", 1).show();
  9             return false;// 若设为true则后边不执行
 10         }
 11     }) {
 12
 13         public void handleMessage(Message msg) {
 14             // TODO Auto-generated method stub
 15             Toast.makeText(getApplicationContext(), "2", 1).show();
 16         }
 17
 18     };
 19
 20
 21     private Handler handler3 = new Handler() {
 22         public void handleMessage(android.os.Message msg) {
 23             // textView.setText(""+msg.arg1+"-"+msg.arg2);
 24             textView.setText("" + msg.obj);
 25         };
 26     };
 27
 28
 29     private TextView textView;
 30     private ImageView imageView;
 31     private int Image[] = { R.drawable.a, R.drawable.b, R.drawable.c };
 32     private int index;
 33
 34     @Override
 35     protected void onCreate(Bundle savedInstanceState) {
 36         super.onCreate(savedInstanceState);
 37         setContentView(R.layout.fragment_main);
 38         textView = (TextView) findViewById(R.id.textview);
 39         imageView = (ImageView) findViewById(R.id.imageView1);
 40         new Thread() {
 41             public void run() {
 42                 try {
 43                     Thread.sleep(2000);
 44                     // (1)
 45                     // Message message=new Message();
 46                     // message.arg1=88;
 47                     // message.arg2=100;
 48
 49                     // (2)
 50                     Message message = handler3.obtainMessage();
 51
 52                     Person person = new Person();
 53                     person.age = 23;
 54                     person.name = "zy";
 55                     message.obj = person;
 56                     // handler.sendMessage(message);//(1)
 57                     message.sendToTarget();// (2)
 58
 59                 } catch (InterruptedException e) {
 60                     // TODO Auto-generated catch block
 61                     e.printStackTrace();
 62                 }
 63             };
 64         }.start();
 65
 66         /*
 67          * new Thread() {
 68          * public void run() {
 69          * try { Thread.sleep(1000);
 70          * handler.post(new Runnable() {
 71          *
 72          * @Override
 73          * public void run() {
 74          *  // TODO Auto-generated method stub
 75          * textView.setText("更新线程"); } });
 76          *
 77          * } catch (InterruptedException e) { // TODO Auto-generated catch block
 78          * e.printStackTrace(); } }; }.start();
 79          */
 80
 81         handler1.postDelayed(myRunnable, 1000);// 1000:一秒钟换一次
 82
 83     }
 84
 85     MyRunnable myRunnable = new MyRunnable();
 86 //图片循环播放
 87     class MyRunnable implements Runnable {
 88
 89         @Override
 90         public void run() {
 91             // TODO Auto-generated method stub
 92             index++;
 93             index = index % 3;
 94             imageView.setImageResource(Image[index]);
 95             handler1.postDelayed(myRunnable, 1000);
 96         }
 97     }
 98
 99     class Person {
100         public int age;
101         public String name;
102
103         @Override
104         public String toString() {
105             // TODO Auto-generated method stub
106             return "name=" + name + "age=" + age;
107         }
108     }
109
110     public void click(View view) {
111         handler1.removeCallbacks(myRunnable);
112         handler2.sendEmptyMessage(1);
113     }
114
115 }
Android为什么要设计只能通过Handler机制更新UI呢?
最根本的目的就是解决多线程并发的问题。
1. 假如在一个Activity当中,有多个线程去更新UI,并且都没有加锁机制,那么会产生什么样子的问题?
--> 更新界面混乱。
2. 如果对更新UI的操作都进行加锁处理的话又会产生什么样子的问题?
--> 性能下降。
正是对以上问题的考虑,Android给我们提供了一套更新UI的机制,我们只需遵循这样的机制就可以了,根本不用去关心多线程(并发)的问题,所有的更新UI的操作,都是在主线程的消息队列中去“轮询”处理的。

Handler的原理是什么?
面试经典问题:Looper、Handler、Message(或MessageQueue)三者间的关系?
一、Handler封装了消息的发送(主要是将消息发送给谁(默认是Handler自己),以及什么时候发送)。
Looper:
1.内部包含一个消息队列 MessageQueue,所有的 Handler 发送的消息都走向(加入)这个消息队列。
2.Looper.Looper方法,就是一个死循环,不断地从 MessageQueue 取得消息,如果有消息就处理消息,没有消息就阻塞。
二、MessageQueue
MessageQueue 就是一个消息队列,可以添加消息,并处理消息。
三、Handler 也很简单,内部会跟 Looper 进行关联,也就是说,在 Handler 的内部可以找到 Looper,找到了 Looper 也就找到了 Message。在 Handler 中发送消息,其实就是向 MessageQueue 队列中发送消息。

总结:Handler 负责发送消息,Looper 负责接收 Handler 发送的消息,并直接把消息回传给 Handler 自己,MessageQueue就是一个存储消息的容器。
				
时间: 2024-11-09 02:26:57

Android攻城狮Handler简介的相关文章

创业公司求IOS、Android攻城狮一枚

地点:北京CBD附近(地铁1号线大望路) 魅力值:送珍贵期权 你要会: 1. IOS或者Android开发 2.能够处理类似微视/秒拍的视频录制功能 3.熟悉json 4.做过第三方登录 5.爱学习 6.no zuo 7.工作经验不限 如果你适合,就别再犹豫,发简历到[email protected](饶先生),或者加TA QQ随便骚扰,TA正在求骚扰 创业公司求IOS.Android攻城狮一枚,布布扣,bubuko.com

Android攻城狮 Android中更新UI的几种方式

Android中更新UI的几种方式: 1. Activity 的 runOnUiThread() 2. Handler 的 post() 3. Handler 的 sendMessage() 4. View 的 post() 1 public class FiveActivity extends Activity { 2 3 private TextView textView; 4 5 private Handler handler = new Handler() { 6 public void

Android攻城狮基础动画

Android基础动画 1. Tween Animation 变换动画 2. Frame Animation 帧动画 3. Layout Animation 布局动画 4. Property Animation 属性动画 Tween Animation(变换动画)在Android中又被分为四种: Alpha:渐变透明度动画 Scale:渐变尺寸缩放动画 Translate:位置移动动画 Rotate:旋转动画 Tween Animation共同属性: 1. Duration:动画持续时间(单位:

Android攻城狮四种基础动画

AlphaAnimation(透明动画) 1.xml文件 <set xmlns:android="http://schemas.android.com/apk/res/android"> <!-- 渐变动画,表示从透明度10%到100%,持续时间为1秒 --> <alpha android:fromAlpha="0.1" android:toAlpha="1" android:duration="1000&

Android攻城狮动画组合

组合动画 案例一(续播1): 两个动画A和B,先播放动画A,设置A的AnimationListener(会重写3个方法),当其中一个方法onAnimationEnd()触发,也就是当A播放完毕的时候,开始播放B.核心代码如下: Animation loadAnimation = AnimationUtils.loadAnimation( this, R.anim.translate ); image.startAnimation(loadAnimation); // 开启动画A Animatio

Android攻城狮布局动画

LayoutAnimation(布局动画) 为View Groups添加动画 使用LayoutAnimationController 如图,给一个listView设置动画,使用了新的方法:setLayoutAnimation(). setOrder(LayoutAnimationController.XXXX)是设置动画的顺序,例如 ORDER.RANDOM 表示一个随机的顺序. listView就相当于一个View Groups,是一个容纳了很多View的(集合)视图组.然后我们通过布局动画把

Android攻城狮GridView(主菜单)

GridView布局文件声明GridViewjava里创建GridView 配置 1.准备数据源 2.新建适配器(SimpleAdapter) 3.GridView加载适配器 4.GridView配置监听器(OnItemClickListener) gridView实现过程: 1.准备数据源 dataList=new ArrayList<Map<String,Object>>(); 2.新建适配器(SimpleAdapter) adapter=new SimpleAdapter(t

百度面试android攻城狮

今天就在今天,是我的百度第二次面试,(实习生只有两次面试)我这次表现极度不好,不但没有回答好我自己的android问题,当然我的基础知识也没回答好.我怀着悲痛的心情把题目写给大家,因为面试面试的不好,所以印象深刻,所以我全能回忆起来,希望对大家有帮助!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!今天面试官,非常亲切,因为提前了一点,所以征求了我的意见,我说可以. 总共的问题分为四部分 下面详细介绍 android的 部分 1.问了我做过的一个外卖app,问了我

Android攻城狮认识ContextMenu

什么是ContextMenu? 例如Windows系统的右键菜单,在Android中长按某个文件夹,会跳出菜单,这个菜单就是ContextMenu. ContextMenu与OptionMenu的区别 1. OptionMenu对应的是activity,一个activity只能拥有一个选项菜单: 2. ContextMenu对应的是View,每一个View都可以设置上下文菜单: 3. 一般情况下ContextMenu常用于ListView或者GridView. ContextMenu创建方法 首