0
点赞
收藏
分享

微信扫一扫

Android 消息机制之初识Handler [ 六 ]

Android 消息机制深入源码分析 [ 一 ]
Android 消息机制之 ThreadLocal 深入源码分析 [ 二 ]
Android 消息机制之 Looper 深入源码分析 [ 三 ]
Android 消息机制之 Message 与消息对象池的深入源码分析 [ 四 ]
Android 消息机制之 MessageQueue 深入源码分析 [ 五 ]
Android 消息机制之初识Handler [ 六 ]
Android 消息机制之 Handler 发送消息的深入源码分析 [ 七 ]
Android 消息机制之 MessageQueue.next() 消息取出的深入源码分析 [ 八 ]
Android 消息机制之消息的其他处理深入源码分析 [ 九 ]
Android 消息机制总结 [ 十 ]

前几章分解学习了 ThreadLocal, Looper, Message, MessageQueue 等相关的知识, 本章节开始正式学习 Android 中消息机制的重中之重 Handler. 那么让我们正式开始学习吧.

1. 什么是 Handler

  • Handler 是一个可以通过关联一个消息队列来发送和处理消息, 发送或处理 Runnable 对象的一个处理程序.
  • 每个 Handler 都关联一个单个的线程和消息队列. 当我们创建一个新的 Handler 的时候, 它就绑定到一个线程上或者线程上的消息队列, 从那个时候起, 这个 Handler 就将为这个消息队列提供消息或者 Runnable 对象处理消息队列释放出来的消息或者 Runnable 对象.

2. Handler 有什么用

  • 安排消息和 Runnable 对象在未来执行.
  • 将用户的一个动作放在不同的线程上执行.

3. 构造函数

Handler 的构造函数一共有七个, 六个是有参, 一个无参的, 所有的构造函数都为 public

  • 1.public Handler()
  • 2.public Handler(Callback callback)
  • 3.public Handler(Looper looper)
  • 4.public Handler(Looper looper, Callback callback)
  • 5.public Handler(boolean async)
  • 6.public Handler(Callback callback, boolean async)
  • 7.public Handler(Looper looper, Callback callback, boolean async)

这七个构造函数, 又将分为两类. 分别为两个参数的 1. 2. 5. 6 和 三个参数的 3. 4. 7. 接下来将对这个构造函数逐个分析学习.

1. public Handler()

public Handler() {
    this(null, false);
}
  • 解析:

2. public Handler(Callback callback)

public Handler(Callback callback) {
    this(callback, false);
}
  • 解析:

5. public Handler(boolean async)

public Handler(boolean async) {
    this(null, async);
}
  • 解析:

 
以上是一个无参和两个有参的, 1. 2. 5. 但是他们归根结底调用的都是构造函数 6. 所以现在一起看下构造函数 6.
 
6. public Handler(Callback callback, boolean async)

public Handler(Callback callback, boolean async) {
    if (FIND_POTENTIAL_LEAKS) {
        final Class<? extends Handler> klass = getClass();
        //如果是匿名类, 内部类, 局部类,且没有声明 static,则存在内存泄露风险,所以打印日志进行提醒
        if ((klass.isAnonymousClass() || klass.isMemberClass() || klass.isLocalClass()) &&(klass.getModifiers() & Modifier.STATIC) == 0) {
            Log.w(TAG, "The following Handler class should be static or leaks might occur: " +
                klass.getCanonicalName());
        }
    }
    //获得当前线程的 Looper
    mLooper = Looper.myLooper();
    //如果当前线程没有 Looper,则说明没有还没有调用 Looper.loop,抛异常
    if (mLooper == null) {
        throw new RuntimeException("Can't create handler inside thread " + Thread.currentThread() + " that has not called Looper.prepare()");
    }
    //把 Looper 的 Queue 赋值给 Handler 的 mQueue
    mQueue = mLooper.mQueue;
    //赋值给 callback
    mCallback = callback;
    //赋值  mAsynchronous
    mAsynchronous = async;
}
  • 解析:

 
下面是三个参数的构造函数.
3. public Handler(Looper looper)

public Handler(Looper looper) {
  this(looper, null, false);
}
  • 解析

4. public Handler(Looper looper, Callback callback)

public Handler(Looper looper, Callback callback) {
    this(looper, callback, false);
}

7. public Handler(Looper looper, Callback callback, boolean async)

public Handler(Looper looper, Callback callback, boolean async) {
    mLooper = looper;
    mQueue = looper.mQueue;
    mCallback = callback;
    mAsynchronous = async;
}
  • 解析:

 
综合 7 个构造函数, 可以发现其实构造函数的本质都是给下面四个本地变量赋值

  • mLooper
  • mQueue
  • mCallback
  • mAsynchronous

构造函数总结

  • 如果 Handler 的构造中没有给 Looper, 则使用默认的 Looper, 也就是在当前线程 ThreadLocal 中关联的 Looper.
    通过 ThreadLocal.Looper.mQueue 来给 Handler.mQueue 赋值.
    实现 Handler, Looper, MessageQueue 三者的绑定.
  • 通过构造函数来设置 Callback 的回调接口, 不设置则为 null.
  • 通过 mAsynchronous 来控制是同步还是异步, 而 mAsynchronous的默认值为 false. mAsynchronous 可以通过构造函数来设置.

 
最后来说一下回调接口, 也就是 Handler.Callback 接口

public interface Callback {
    public boolean handleMessage(Message msg);
}
  • 官方翻译:
  • 理解
class myHandler extends Handler{
    public myHandler(@Nullable Callback callback) {
        super(callback);
    }
    @Override
    public void handleMessage(@NonNull Message msg) {
        Log.e("myHandler","___what=" + msg.what);
        super.handleMessage(msg);
    }
}

public class MainActivity extends AppCompatActivity {

    Button button1,button2;
    private static  myHandler handler = new myHandler(new Handler.Callback() {
        @Override
        public boolean handleMessage(@NonNull Message msg) {
            if(msg.what == 100){
                Log.e("myHandler","___Callback=" + msg.what);
                return true;
            }
            return  false;
        }
    });


    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        button1 = findViewById(R.id.button1);
        button2 = findViewById(R.id.button2);
        button1.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Message message = Message.obtain();
                message.what = 100;
                handler.sendMessage(message);
            }
        });
        button2.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Message message = Message.obtain();
                message.what = 1000;
                handler.sendMessage(message);
            }
        });
    }
}
  • 点击 button1, 打印的是 ___Callback=100, 拦截了消息
  • 点击 button2, 打印的是 ___what=1000, 接收到了消息.

这是我对 Callback.handleMessage 的简单理解. 平时我们估计都不会经常用到这个 Callback, 估计一般用到的都是无参的 Handler.

本章对 Handler 的初识就到这里就结束了, 下一章会开始 Handler 对消息的发送进行分析和学习.

举报

相关推荐

0 条评论