reprint: http://p.codekk.com/blogs/detail/54cfab086c4761e5001b25381. Function Introduction 1.1 Eventbus
Eventbus is an Android event publish/Subscribe framework that simplifies the delivery of Android events by decoupling publishers and subscribers, where events can be understood as messages, collectively called events in this article. Event delivery can be used to communicate between the four components of Android, as well as the communication between the user's asynchronous thread and the main thread, among others.
Traditional event delivery methods include: Handler, Broadcastreceiver, Interface callbacks, in contrast to Eventbus's advantages are code simplicity, ease of use, and the full decoupling of event publishing and subscriptions.
1.2 Concepts
Event: It can also be called a message, which is represented in the unified event in this article. It is actually an object, which can be a string returned by a network request, a switch state, and so on. 事件类型(EventType)refers to the Class to which the event belongs.
Events are divided into general and Sticky events, and the Sticky event differs from the general event in that when an event is published, a subscriber starts subscribing to that type of event and still receives the most recent Sticky event of that type of event.
Subscriber (Subscriber): Subscribes to an object of an event type. When a publisher publishes such an event, Eventbus executes the subscriber's onEvent function, which is called 事件响应函数 . Subscribers subscribe to an event type via the register interface, and the unregister interface is unsubscribed. Subscribers have priority, high-priority subscribers can cancel the event to continue to the lower priority of the Subscriber distribution, the default all Subscribers priority is 0.
Publisher (publisher): An object that publishes an event and publishes it through the Post interface.
2. Overall design
This project is relatively simple, the overall design please refer to 3.1 订阅者、发布者、EventBus 关系图 and 4.1 类关系图 .
3. Flowchart 3.1 Subscriber, publisher, Eventbus diagram
Eventbus is responsible for storing subscriber, event-related information, and subscribers and publishers are only associated with Eventbus.
3.2 Incident Response Process
Subscribers first call Eventbus's register interface to subscribe to a type of event, and when the publisher publishes events of that type through the Post interface, Eventbus executes the caller's event response function.
4. Detailed design of Class 4.1 diagrams
The above is the Eventbus main class diagram, from which we can also see that most of the classes are directly associated with Eventbus. The upper part is primarily the subscriber-related information, the middle is the Eventbus class, and the following is the call after the publisher publishes the event. For specific class functions, please see the detailed description below.
Class 4.2 Detailed Introduction 4.2.1 Eventbus.java
The Eventbus class is responsible for all externally exposed APIs, where the register (), post (), unregister () functions are combined with custom eventtype and event response functions to complete the core function, see figure 3.2.
Eventbus By default can be obtained by the static function Getdefault, of course, it is necessary or possible to create a new eventbus through the Eventbusbuilder or constructor, each new Eventbus publish and subscribe events are isolated from each other, that is, a The publisher of the Eventbus object publishes the event, and the subscriber in the other Eventbus object does not receive the subscription.
Eventbus external API, mainly consists of two categories:
(1) Register and unregister
Indicates subscription events and unsubscribe, respectively. The register's lowest-level function has three parameters, namely, the Subscriber object, whether it is a Sticky event, and a priority.
private synchronized void register(Object subscriber, boolean sticky, int priority)
PS: Earlier versions of Eventbus also allow custom event response function names, which have been removed in this release.
The Register function flowchart is as follows:
The Register function will first find all the event response functions of the current subscriber according to the Subscriber class name subscriberMethodFinder , then loop through each event response function and execute the following subscribe function in turn:
(2) Subscribe
The Subscribe function is divided into three steps
The first step: the subscriptionsByEventType current subscriber information is inserted into the subscriber queue according to priority by getting the event type all subscriber information queue subscriptionsByEventType ;
The second step: in the typesBySubscriber current subscriber subscribed to all the event queue, save this event to the queue typesBySubscriber for subsequent unsubscribe;
Step Three: Check if this event is a Sticky event, and if yes, stickyEvents remove the event type from the event save queue the last event sent to the current subscriber.
(3) post, Cancel, removestickyevent
The post function is used to publish events, and the Cancel function is used to cancel all event types subscribed by a subscriber, and the Removestickyevent function is used to delete the sticky event.
The Post function flowchart is as follows:
The Post function first gets the post information of the current thread PostingThreadState , which contains the event queue, adds the current event to its event queue, and then loops through each event in the Postsingleevent function publishing queue.
The Postsingleevent function First eventTypesCache gets the parent class and interface type of the event's corresponding type, and no cache finds and inserts the cache. Looping through each of the types and interfaces, call the Postsingleeventforeventtype function to publish each event to each subscriber.
The Postsingleeventforeventtype function subscriptionsByEventType locates the Subscriber queue for the event, and calls the Posttosubscription function to publish events to each Subscriber.
In the Posttosubscription function, the subscriber's threadmode is judged, which determines the mode under which the event response function is executed. There are four categories of Threadmode:
PostThread: The default Threadmode, which indicates that the thread that is performing the Post operation invokes the subscriber's event response method directly, regardless of whether the thread is the main threaded (UI thread). There can be no time-consuming action in the response method when the thread is the main path, otherwise there is a risk of the main thread of the card. Applicable scenario: For the main thread is not required to execute, but if the Post thread is the main path, can not be time-consuming operation;
MainThread: Executes the response method in the main thread. If the publishing thread is the main thread, call the subscriber's event response method directly, otherwise the Handler send message through the main thread is processed in the main thread-invoking the subscriber's event response function. Obviously, MainThread class methods cannot have time-consuming operations to avoid the main thread of the card. Applicable scenario: the operation that must be performed on the main thread;
BackgroundThread: Executes the response method in the background thread. If the publishing thread is not the primary thread, call the subscriber's event response function directly, or start a unique background thread to process. Because background threads are unique, when more than one event occurs, they are placed in the queue and executed sequentially, so the class response method is not performance- PostThread MainThread sensitive, but it is best not to have a heavy time-consuming operation or a light time-consuming operation that is too frequent to cause other operations to wait. Application scenario: The operation is slightly time consuming and not too frequent , that is, the general time-consuming operation can be put here;
Async: A free thread is used to process the publishing thread, regardless of whether it is the thread. And BackgroundThread the difference is that Async all the threads of the class are independent of each other, so there is no problem with the card thread. Scenario: long time-consuming operations, such as network access .
(4) main member variable meaning
1.defaultInstanceThe default Eventbus instance, based onEventBus.getDefault()function to get.
2.DEFAULT_BUILDERThe default Eventbus Builder.
3.eventTypesCacheThe event corresponds to the cache of the type and its parent class and the implemented interface, with EventType as key and the ArrayList of the element as object Value,object the parent class or interface of the EventType. 4.subscriptionsByEventTypeEvent subscriber's save queue, with EventType as key, element asSubscriptionThe ArrayList is Value, whereSubscriptionThe subscriber information is composed of subscriber, Subscribermethod, and priority.
5.typesBySubscriberThe Save queue for the event subscribed by the Subscriber, with subscriber as key, and the element EventType as Value ArrayList.
6.stickyEventsThe Sticky event saves the queue with EventType as the key,event element, so you can see that there will be at most one event present for the same eventtype.
7.currentPostingThreadStatePost information for the current thread, including the event queue, whether it is being distributed, whether it is in the main thread, subscriber information, event instances, or not.
8.mainThreadPoster、backgroundPoster、asyncPosterEvent main thread processor, event Background handler, event asynchronous handler.
9.subscriberMethodFinderThe subscriber responds to the function information store and the lookup class.
10.executorServiceThe thread pool of asynchronous and BackGround processing methods.
11.throwSubscriberExceptionIf an exception is thrown when the event handler exception is called, the default is False, which is recommended by
EventBus.builder().throwSubscriberException(true).installDefaultEventBus()
Open it.
logSubscriberExceptionsIf the exception information is printed when the event handler exception is called, the default is true.
logNoSubscriberMessageswhen no subscribers subscribe to the event to print the log, the default is true.
When the sendSubscriberExceptionEvent event handler exception is called, the Subscriberexceptionevent event is sent, and if the switch is open, the subscriber can
public void onEvent(SubscriberExceptionEvent event)
Subscribes to the event for processing, which defaults to true.
sendNoSubscriberEventwhen there is no event handler for event handling, the Nosubscriberevent event is sent, and if this switch is turned on, subscribers can
public void onEvent(NoSubscriberEvent event)
Subscribes to the event for processing, which defaults to true.
eventInheritanceThe default is True if event inheritance is supported.
4.2.2 Eventbusbuilder.java
Similar to General Builder, for constructing eventbus if you need to set too many parameters. The included properties are also some of the setup parameters of Eventbus, meaning that 4.2.1 EventBus.java the build function is used to create a new Eventbus object, and the Installdefaulteventbus function applies the current settings to the default Eventbus.
4.2.3 Subscribermethodfinder.java
The subscriber responds to the function information store and the lookup class, which is cached by HashMap, with ${subscriberclassname} as the Key,subscribermethod object for the ArrayList of the element as value. The Findsubscribermethods function is used to find the subscriber response function, and if it is not in the cache, it iterates through each of its functions and recursively finds the parent, which is saved to the cache after the lookup succeeds. The traversal and lookup rules are:
A. Traverse Subscriberclass each method;
B. The method does notjava.、javax.、android.These SDK functions begin with theonEventThe beginning, indicating that the event response function may continue, otherwise check the next method;
C. Whether the method is public, and is not ABSTRACT, STATIC, BRIDGE, synthetic decorated, and satisfies the condition continues. where BRIDGE and synthetic are compiler-generated function modifiers;
D. Whether the method has only 1 parameters, and the condition is fulfilled;
E. The method is namedonEventThen the Threadmode isThreadMode.PostThread;
The method is namedonEventMainThreadThen the Threadmode isThreadMode.MainThread;
The method is namedonEventBackgroundThreadThen the Threadmode isThreadMode.BackgroundThread;
The method is namedonEventAsyncThen the Threadmode isThreadMode.Async;
Exceptions are thrown in other cases and are not in the Ignore list (skipmethodverificationforclasses).
F. The only parameter that gets the method is the event type EventType, which constructs Subscribermethod object in ArrayList with this method, Threadmode, EventType.
G. Go back to B the next method of traversing Subscriberclass, if the method traversal ends to H;
H. Go back to A to traverse your parent class, if the parent class traversal ends back to I;
I. If the ArrayList is still empty, throw an exception, otherwise the ArrayList will be value,${subscriberclassname} as key into the cache HashMap. There are two small performance tuning points for finding the event function:
a. 第一次查找后保存到了缓存中,即上面介绍的 HashMap b. 遇到 java. javax. android. 开头的类会自动停止查找
The Skipmethodverificationforclasses property in the class represents a function check that skips which classes are illegal to onEvent begin with, and throws an exception if not skipped.
PS: Prior to this version Eventbus allows the custom event response function name, the cached HashMap key is ${subscriberclassname}.${eventmethodname}, this feature has been removed in this release.
4.2.4 Subscribermethod.java
Subscriber Event response function information, including the response method, thread Mode, event type, and a feature value to compare Subscribermethod equality methodstring A total of four variables, where methodstring is ${ Methodclassname}#${methodname} (${eventtypeclassname}.
4.2.5 Subscription.java
Subscriber information, including Subscriber object, event response method Subscribermethod, priority precedence.
4.2.6 Handlerposter.jva
Event main thread processing, corresponding ThreadMode.MainThread . Inheriting from the Handler,enqueue function puts the event into the queue and takes an event from the queue using the Handler send Message,handlemessage function, which is handled by the Invoke event response function.
4.2.7 Asyncposter.java
Event asynchronous threading, corresponding ThreadMode.Async , inheriting from Runnable. The Enqueue function puts the event into the queue and invokes the thread pool to perform the current task, and the run function takes an event from the queue, and the Invoke event response function is processed.
4.2.8 Backgroundposter.java
Event Background processing, corresponding ThreadMode.BackgroundThread , inheriting from Runnable. The Enqueue function puts the event into the queue and invokes the thread pool to perform the current task, and the run function takes an event from the queue, and the Invoke event response function is processed. Unlike Asyncposter.java, tasks in Backgroundposter are executed sequentially in the same thread, not concurrently.
4.2.9 Pendingpost.java
The Subscriber and event information entity classes, and contains pointers to the next object in the same queue. Reduce the performance cost of the next creation by storing unused objects in the cache.
4.2.10 Pendingpostqueue.java
Maintains a queue with head and tail pointers PendingPost . Handlerposter, Asyncposter, and Backgroundposter all contain a single instance of this queue, representing their respective subscribers and event information queues, entering the queue at the time of the event, and processing a single element from the queue.
4.2.11 Subscriberexceptionevent.java
The Eventbus internal custom event that is sent when an event handler exception is called, is sent via post, and subscribers can subscribe to such events for processing.
4.2.12 Nosubscriberevent.java
When there is no event handler for event handling, Eventbus internal custom events are sent through post, and subscribers can subscribe to such events for processing.
4.2.13 Eventbusexception.java
The Exception, which is encapsulated on top of the runtimeexception, simply overrides the constructor, which is the equivalent of a token, which is the Exception of Eventbus.
4.2.14 Threadmode.java
The thread Mode enumeration class, which represents an event response function that executes thread information, includes,, ThreadMode.PostThread ThreadMode.MainThread ThreadMode.BackgroundThread , and ThreadMode.Async four types.
5. Comparison with Otto
When Otto analysis is complete
76.Android Eventbus Source Parsing