-
Notifications
You must be signed in to change notification settings - Fork 3
/
GYNotificationCenter.m
150 lines (103 loc) · 4.88 KB
/
GYNotificationCenter.m
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
//
// GYNotificationCenter.m
// WeRead
//
// Created by 王斌 on 16/7/4.
// Copyright © 2016年 tencent. All rights reserved.
//
#import "GYNotificationCenter.h"
#import <pthread.h>
#import <objc/runtime.h>
#define GY_NOTIFICATION_CONTAINER_KEY @"gyNotificationContainerKey"
@implementation GYNotificationCenter
+ (instancetype)defaultCenter {
static GYNotificationCenter *defaultCenter;
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
defaultCenter = [[GYNotificationCenter alloc] init];
});
return defaultCenter;
}
#pragma mark -- add observer
- (void)addObserver:(nonnull id)observer
name:(nonnull NSString *)aName
block:(nonnull GYNotificatioObserverBlock)block {
[self addObserver:observer name:aName object:nil dispatchQueue:nil block:block];
}
- (void)addObserver:(nonnull id)observer
name:(nonnull NSString *)aName
dispatchQueue:(nullable dispatch_queue_t)disPatchQueue
block:(nonnull GYNotificatioObserverBlock)block {
[self addObserver:observer name:aName object:nil dispatchQueue:disPatchQueue block:block];
}
- (void)addObserver:(nonnull id)observer
name:(nonnull NSString *)aName
object:(nullable id)anObject
block:(nonnull GYNotificatioObserverBlock)block {
[self addObserver:observer name:aName object:anObject dispatchQueue:nil block:block];
}
- (void)addObserver:(nonnull id)observer
name:(nonnull NSString *)aName
object:(nullable id)anObject
dispatchQueue:(nullable dispatch_queue_t)disPatchQueue
block:(nonnull GYNotificatioObserverBlock)block {
[self addWithContainerBlock:^(GYNotificationOberverIdentifersContainer *container) {
GYNotificationOberverIdentifer *identifier = [[GYNotificationOberverIdentifer alloc] init];
[identifier congifureWithName:aName withObject:anObject withDispatchQueue:disPatchQueue withBlock:block];
[container addNotificationOberverIdentifer:identifier];
} toObserver:observer];
}
- (void)addWithContainerBlock:(void (^)(GYNotificationOberverIdentifersContainer *container)) block
toObserver:(id)observer {
NotificationPerformLocked(^{
//get container
GYNotificationOberverIdentifersContainer *notificationOberverIdentifersContainer = (GYNotificationOberverIdentifersContainer *)objc_getAssociatedObject(observer, GY_NOTIFICATION_CONTAINER_KEY);
//add to container
if (!notificationOberverIdentifersContainer) {
notificationOberverIdentifersContainer = [[GYNotificationOberverIdentifersContainer alloc] init];
objc_setAssociatedObject(observer, GY_NOTIFICATION_CONTAINER_KEY, notificationOberverIdentifersContainer, OBJC_ASSOCIATION_RETAIN_NONATOMIC);
}
block(notificationOberverIdentifersContainer);
});
}
#pragma mark -- remove observer
- (void)removerObserver:(nonnull id)observer
name:(nonnull NSString *)anName
object:(nullable id)anObject {
NotificationPerformLocked(^{
//get container
GYNotificationOberverIdentifersContainer *notificationOberverIdentifersContainer = (GYNotificationOberverIdentifersContainer *)objc_getAssociatedObject(observer, GY_NOTIFICATION_CONTAINER_KEY);
//add to container
if (notificationOberverIdentifersContainer) {
[notificationOberverIdentifersContainer removeObserverWithName:anName];
}
});
}
- (void)removerObserver:(nonnull id)observer {
NotificationPerformLocked(^{
//get container
GYNotificationOberverIdentifersContainer *notificationOberverIdentifersContainer = (GYNotificationOberverIdentifersContainer *)objc_getAssociatedObject(observer, GY_NOTIFICATION_CONTAINER_KEY);
//add to container
if (notificationOberverIdentifersContainer) {
[notificationOberverIdentifersContainer removeObserver];
}
});
}
#pragma mark - post Notification
- (void)postNotification:(NSNotification *)notification {
[[NSNotificationCenter defaultCenter] postNotification:notification];
}
- (void)postNotificationName:(NSString *)aName object:(nullable id)anObject {
[[NSNotificationCenter defaultCenter] postNotificationName:aName object:anObject];
}
- (void)postNotificationName:(NSString *)aName object:(nullable id)anObject userInfo:(nullable NSDictionary *)aUserInfo {
[[NSNotificationCenter defaultCenter] postNotificationName:aName object:anObject userInfo:aUserInfo];
}
#pragma mark -- helper
static void NotificationPerformLocked(dispatch_block_t block) {
static pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
pthread_mutex_lock(&mutex);
block();
pthread_mutex_unlock(&mutex);
}
@end