Low.handler class analysis of the message Loop Mechanism of Android

Source: Internet
Author: User

The logoff class indicates that the logoff class is used to run a message loop for a thread. The Thread is not associated with the message loop by default. The Thread class exits after the content of the run () method is executed, that is to say, after the thread finishes its work, it will end. There is no concept of loop. Call the prepare () method of The logoff class to create a message loop for the current thread and call the loop () method to process information until the loop ends. Most of the interactions with message loops are carried out through the Handler class. The following is a typical implementation: copy the code class LooperThread extends Thread {public Handler mHandler; public void run () {loid. prepare (); mHandler = new Handler () {public void handleMessage (Message msg) {// process incoming messages here}; Looper. loop () ;}} copy the code Handler class description Handler class is used to send and process messages and Runnable objects associated with thread Message queues (MessageQueue. Each Handler object is associated with only one thread and the message queue of this thread. All Handler objects in a specific thread will receive the same method. (This is a one-to-many relationship ). When you create a new Handler object, it will be bound to the Message Queue of the thread/thread that created it, starting from that moment, it will pass messages and runnable objects to the message queue and execute them when they come out of the queue. Handler has two main purposes: 1. Reasonably schedule messages and runnable objects so that they will be executed at a certain point in the future. 2. Queue an action in a non-current thread. A message is scheduled through a series of post and sendMessage methods. The post method allows you to queue some Runnable objects in the message queue and call them when they are received. (In fact, the post method encapsulates runnable objects in the message, then implement it through the sendMessage method). The post method includes: post (Runnable r) postAtFrontOfQueue (Runnable r) postAtTime (Runnable r, Object token, long uptimeMillis) postAtTime (Runnable r, long uptimeMillis) postDelayed (Runnable r, long delayMillis) The sendMessage method allows you to join a Message object (Message) that contains a bundle data. Then, handleMessage (Message) of Handler) method. (You need to implement a sub-class of Handler ). SendMessage methods include: sendEmptyMessage (int what) sendEmptyMessageAtTime (int what, long uptimeMillis) messages (int what, long delayMillis) sendMessage (Message msg) messages (Message msg) sendMessageAtTime (Message msg, long uptimeMillis) sendMessageDelayed (Message msg, long delayMillis) a thread corresponds to a logoff and has a Message queue, but can be associated with multiple Handlers. Communication between the UI thread and non-UI thread when an application process is created, the main thread of the application process establishes a message queue, manipulate top-level application objects (such as activities and broadcast receivers) and any windows they create. Because of efficiency considerations, all views and widgets are NOT thread-safe, so related operations are forced to be placed in the same thread, so as to avoid the problem caused by multithreading. This thread is the main thread, that is, the UI thread. You can create your own thread and communicate with the main thread of the application through a Handler object. If you connect a Handler to your UI thread, the code that processes the message will be executed in the UI thread. Communication between the new thread and the UI thread is implemented by calling the post or sendMessage method of the Handler object related to the main thread from your new thread, the given Runnable or Message will be processed in the Handler Message queue at the appropriate time. In general, there are five ways to communicate with the UI thread from a non-UI thread: Activity. runOnUiThread (Runnable) View. post (Runnable) View. postDelayed (Runnable, long) also uses Handler or AsyncTask. For more information, see the previous blog post: http://www.cnblogs.com/mengdd/p/3418780.html message loop message processing mechanism, messages are stored in a message queue, and threads enter an infinite loop around this queue until the program exits. If there is a message in the queue, the thread will fetch the message and distribute it to the corresponding Handler for processing. If there is no message in the queue, the thread will enter the idle waiting state, wait for the next message to arrive. Android's main thread cyclically creates an Android program. The entry point can be considered as android. app. main () method of the ActivityThread class (source code 2.3.3): copy the public static final void main (String [] args) {// other codes... // create a main thread loop logoff. prepareMainLooper (); if (sMainThreadHandler = null) {sMainThreadHandler = new Handler ();} ActivityThread thread = new ActivityThread (); thread. attach (false); // other codes... // enter the current thread (this is the main thread at this time) message loop logoff. loop (); // other code S... thread. detach (); // other codes...} copy the code in this main () method to create a main thread loop for the program. The primary thread creation method prepareMainLooper () in the logoff class: copy the code/*** Initialize the current thread as a loaliz, marking it as an application's * main Looper. the main logoff for your application is created by the * Android environment, so you shoshould never need to call this function * yourself. {@ link # prepare ()} */public static final void prepareMainLooper () {prepare (); setmainlodes (mylodes (); // other codes ...} Copy the code above this method is specifically called for the main thread that creates the application, other threads should not call this method, but should call the prepare () method. After the logoff object of the main thread is created, it will exist in mmainlogoff, a member variable of the logoff class. You can use a get method to obtain: copy the code/*** Returns the application's main logoff, which lives in the main thread of * the application. */public synchronized static final loal getMainLooper () {return mMainLooper;} after the code is copied, other threads in the program can obtain the message loop object of the main thread to communicate with the main thread. The thread creates a message loop: logoff. when a prepare () non-primary thread creates a message loop, it calls the prepare () method of The logoff class. In fact, the method for creating the primary thread also calls the prepare method: copy the code/*** Initialize the current thread as a looper. this gives you a chance to * create handlers that then reference this logoff, before actually starting * the loop. be sure to call {@ link # loop ()} after calling this method, and * end it by calling {@ link # quit ()}. */public static final void prepare () {if (SThreadLocal. get ()! = Null) {throw new RuntimeException ("Only one logoff may be created per thread");} sThreadLocal. set (new logoff ();} copy the Code. This method will call the logoff class's private constructor to create a logoff class object. Copy the code private logoff () {// private constructor, and call // create Message Queue mQueue = new MessageQueue () in the prepare () method; mRun = true; // The current Thread mThread = Thread. currentThread () ;}copy the code into the message loop: logoff. loop (), whether it is the main thread or not, you need to call the logoff loop () method after prepare. It can be seen as entering the message loop: copy the code/*** Run the message queue in this thread. be sure to call {@ link # quit ()} to * end the loop. */public static final void loop () {// enter the message loop Looper me = myLooper (); M EssageQueue queue = me. mQueue; while (true) {// retrieve the Message from the queue msg = queue. next (); // might block if (msg! = Null) {if (msg.tar get = null) {// No target is a magic identifier for the quit message. return;} // other codes... // send the message msg.tar get. dispatchMessage (msg); // the target of the message is a Handler object // other codes... // release and clear msg. recycle () ;}}copy code message distribution and processing -- a message loop is created before Handler and enters this loop. But how does one add and process messages in the message queue? Is through Handler. Handler constructor: Handler has several constructor loads. If the logoff class object parameter is not provided during the constructor, The logoff object of the current thread is obtained, that is, the message loop of the current thread is used as the message loop associated with the Handler. As mentioned above, not all threads have a message loop. If the current thread does not have a message loop and the logoff object is not specified when the Handler object is constructed, a runtime exception will be thrown: mlogoff = logoff. myLooper (); if (mloexception = null) {throw new RuntimeException ("Can't create handler inside thread that has not called loled. prepare () ");} if no exception is thrown, after the Handler object is constructed, it is associated with the corresponding logoff instance and Message Queue instance to complete binding. Message sending: THE post method and sendMessage method of the Handler object are essentially message sending methods (the post method basically calls the sendMessage method ). To send a message is to place the message in a proper position in the message queue and set the target of the message as the Handler object. (Here we will add the message to the queue, and we will not discuss the thread wake-up issues in depth ). Can be added, there are some corresponding removal methods. Message Processing: In the logoff. loop () method above, the dispatchMessage () method of the message object target (the Handler object that sends the message) is called. Copy the code/*** Handle system messages here. */public void dispatchMessage (Message msg) {// first, process the Message's own callback and call its run method if (msg. callback! = Null) {handleCallback (msg);} else {// second, the annotation for calling the Handler self-reserved interface object // This member variable declaration is as follows: /*** Callback interface you can use when instantiating a Handler to * avoid having to implement your own subclass of Handler. */if (mCallback! = Null) {if (mCallback. handleMessage (msg) {return ;}// Finally, call the handleMessage method to process the message. This method is null in the Handler class. The subclass can override this method handleMessage (msg );}} the handleMessage () method of the copy code Handler class is implemented as null by default:/*** Subclasses must implement this to receive messages. */public void handleMessage (Message msg) {} the code above also explains why a Message Queue can be associated with many Handler objects, because although there is only one queue, however, the target of the message is the Handler object that was added to the message. Therefore, when a message is processed in the queue, the Handler object sent to it is also found, and the corresponding dispatchMessage () method is called, and then the handleMessage () method is called () or the handleMessage () method of the mCallback member.

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.