路漫漫其修远兮
01. 手写EventBus框架——源码分析1
02. 手写EventBus框架——源码分析2
03. 手写EventBus框架——动手_整体架构设计
04. 手写EventBus框架——动手_终结
o.O前戏已经足够了,接下来撸 代码了。
主体框架
类设计
EventBus.class
/**
*
* Author: 温利东 on 2017/3/26 10:44.
* blog: http://www.jianshu.com/u/99f514ea81b3
* github: https://github.com/LidongWen
*/
public class EventBus {
private static EventBus ourInstance;
private final Map, CopyOnWriteArrayList> cacheMap;
private final Map
线程枚举类
public enum ThreadMode {
POSTING,
MAIN,
BACKGROUND,
ASYNC
}
注解类
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.METHOD})
public @interface Subscribe {
ThreadMode threadMode() default ThreadMode.POSTING;
//粘性
boolean sticky() default false;
//优先级
int priority() default 0;
}
订阅元元素类 SubscriberMethod ;
/**
*
* Author: 温利东 on 2017/3/23 17:56.
* blog: http://blog.csdn.net/sinat_15877283
* github: https://github.com/LidongWen
*/
public class SubscriberMethod {
final Method method;
final ThreadMode threadMode;
final Class> eventType; //参数
final int priority;
final boolean sticky;
/**
* Used for efficient comparison
*/
String methodString;
public SubscriberMethod( Method method, Class> eventType, ThreadMode threadMode, int priority, boolean sticky) {
this.method = method;
this.threadMode = threadMode;
this.eventType = eventType;
this.priority = priority;
this.sticky = sticky;
}
@Override
public boolean equals(Object other) {
if (other == this) {
return true;
} else if (other instanceof SubscriberMethod) {
checkMethodString();
SubscriberMethod otherSubscriberMethod = (SubscriberMethod) other;
otherSubscriberMethod.checkMethodString();
// Don't use method.equals because of http://code.google.com/p/android/issues/detail?id=7811#c6
return methodString.equals(otherSubscriberMethod.methodString);
} else {
return false;
}
}
private synchronized void checkMethodString() {
if (methodString == null) {
// Method.toString has more overhead, just take relevant parts of the method
StringBuilder builder = new StringBuilder(64);
builder.append(method.getDeclaringClass().getName());
builder.append('#').append(method.getName());
builder.append('(').append(eventType.getName());
methodString = builder.toString();
}
}
@Override
public int hashCode() {
return method.hashCode();
}
}
扩展框架设计_01
以上整体的一个架构就出来了,可以看出来,整体的逻辑都在EventBus类里面,虽然其中都是些伪代码,但代码量还是很大的,那么我们可以抽出一些伪代码作为帮助类;
- 订阅方法查找类;
SubscriberMethodFinder.class
; - 方法执行帮助类;
InvokeHelper.class
;
那么结构就变成这样了
InvokeHelper.class
/**
* 方法执行帮助类
*
* Author: 温利东 on 2017/3/26 11:29.
* blog: http://www.jianshu.com/u/99f514ea81b3
* github: https://github.com/LidongWen
*/
public class InvokeHelper {
public static void post(SubscriberMethod subscriberMethod,Object event, boolean isMainThread) {
switch (subscriberMethod.threadMode) {
case POSTING:
//直接执行
break;
case MAIN:
if (isMainThread) {
//直接执行
} else {
// 放在handler内执行
}
break;
case BACKGROUND:
if (isMainThread) {
//放在后台线程执行
} else {
//执行
}
break;
case ASYNC:
//放在异步线程内执行
break;
default:
//抛异常
throw new IllegalStateException("Unknown thread mode: " + subscriberMethod.threadMode);
}
}
}
SubscriberMethodFinder.class
/**
* 订阅方法查找类
*
* Author: 温利东 on 2017/3/26 11:21.
* blog: http://www.jianshu.com/u/99f514ea81b3
* github: https://github.com/LidongWen
*/
public class SubscriberMethodFinder {
private static final Map, List> METHOD_CACHE = new ConcurrentHashMap<>();
/**
* 查找方法
* @param subscriberClass
* @return
*/
List findSubscriberMethods(Class> subscriberClass) {
return null;
}
}
扩展框架设计_02
- 异步线程
AsyncPoster
- 顺序执行
BackgroundPoster
这下子架构就变成这样了
/**
* //异步线程
*
* Author: 温利东 on 2017/3/26 17:36.
* blog: http://www.jianshu.com/u/99f514ea81b3
* github: https://github.com/LidongWen
*/
public class AsyncPoster implements Runnable {
@Override
public void run() {
}
}
/**
* Posts events in background.
*
* Author: 温利东 on 2017/3/26 17:36.
* blog: http://www.jianshu.com/u/99f514ea81b3
* github: https://github.com/LidongWen
*/
final class BackgroundPoster implements Runnable {
@Override
public void run() {
}
}
还漏了一个 Subscription.class
这里加上
Subscription.class
final class Subscription {
final Object subscriber;
final SubscriberMethod subscriberMethod;
volatile boolean active;
Subscription(Object subscriber, SubscriberMethod subscriberMethod) {
this.subscriber = subscriber;
this.subscriberMethod = subscriberMethod;
active = true;
}
@Override
public boolean equals(Object other) {
if (other instanceof Subscription) {
Subscription otherSubscription = (Subscription) other;
return subscriber == otherSubscription.subscriber
&& subscriberMethod.equals(otherSubscription.subscriberMethod);
} else {
return false;
}
}
@Override
public int hashCode() {
return subscriber.hashCode() + subscriberMethod.methodString.hashCode();
}
}
好了 现在我们简易版EventBus框架结构就搭建起来了。其中没有实现代码,全是伪代码逻辑。其实写到这里,各位都可以自己敲代码来实现具体的功能了。
下一节我们将完成以及完善我们简易版EventBus的功能了。
下一节: 04. 手写EventBus框架——动手_终结
希望我的文章不会误导在观看的你,如果有异议的地方欢迎讨论和指正。
如果能给观看的你带来收获,那就是最好不过了。