mirror of
https://github.com/gnustep/libs-base.git
synced 2025-04-22 16:33:29 +00:00
Declare new methods.
git-svn-id: svn+ssh://svn.gna.org/svn/gnustep/libs/base/trunk@1083 72102866-910b-0410-8b05-ffd578937521
This commit is contained in:
parent
b0645f6d52
commit
8e27da11da
2 changed files with 162 additions and 106 deletions
|
@ -30,7 +30,7 @@
|
|||
This implementation has several advantages over OpenStep's
|
||||
NSNotificationCenter:
|
||||
|
||||
(1) Heavier use of hash tables and the use of LinkedList's make it
|
||||
(1) Heavy use of hash tables and the use of LinkedList's make it
|
||||
faster. Removing from the middle of LinkedList's is much more
|
||||
efficient than removing from the middle of Array's.
|
||||
|
||||
|
@ -38,15 +38,19 @@
|
|||
invocation objects instead of just selectors. Invocation objects
|
||||
are more flexible than selectors in that they can hold more context
|
||||
and, if desired, can call C functions instead of sending a message
|
||||
to an object, (this way you may be able to avoid creating a new
|
||||
to an object; (this way you may be able to avoid creating a new
|
||||
class just to handle certain notifications).
|
||||
|
||||
(3) Instead of sending +defaultCenter, you can simply send -add...,
|
||||
-remove... and -post... messages directly to the class object.
|
||||
(3) Instead of sending +defaultCenter, you can simply send +add...,
|
||||
+remove... and +post... messages directly to the class object.
|
||||
The class uses a static variable directly, instead of taking
|
||||
the time for the extra +defaultCenter method call. It's both
|
||||
easier for the user and more time efficient.
|
||||
|
||||
(4) You can call -addObserver:... with both name and object being
|
||||
nil. This request will receive postings of *all* notifications.
|
||||
Wow.
|
||||
|
||||
Although it offers extra features, the implementation has an
|
||||
OpenStep-style interface also.
|
||||
|
||||
|
@ -54,68 +58,73 @@
|
|||
|
||||
#include <objects/stdobjects.h>
|
||||
#include <objects/LinkedList.h>
|
||||
#include <objects/Array.h>
|
||||
#include <Foundation/NSMapTable.h>
|
||||
#include <objects/NSString.h>
|
||||
|
||||
@interface NotificationDispatcher : NSObject
|
||||
{
|
||||
/* For those observer requests with NAME=nil and OBJECT=nil. */
|
||||
LinkedList *anonymous_nr_list;
|
||||
/* For those observer requests with NAME=nil and OBJECT!=nil. */
|
||||
NSMapTable *object_2_nr_list;
|
||||
/* For those observer requests with NAME!=nil, OBJECT may or may not =nil .*/
|
||||
NSMapTable *name_2_nr_list;
|
||||
|
||||
/* The keys are observers; the values are Array's containing all
|
||||
NotificationInvocation objects associated with the observer key. */
|
||||
NSMapTable *observer_2_nr_array;
|
||||
|
||||
/* `nr' stands for Notification Request Object; the interface for
|
||||
this class is defined in the .m file. One of these is created
|
||||
for each -add... call. */
|
||||
|
||||
/* For those observer requests with NAME=nil and OBJECT=nil. */
|
||||
LinkedList *_anonymous_nr_list;
|
||||
/* For those observer requests with NAME=nil and OBJECT!=nil. */
|
||||
NSMapTable *_object_2_nr_list;
|
||||
/* For those observer requests with NAME!=nil, OBJECT may or may not =nil .*/
|
||||
NSMapTable *_name_2_nr_list;
|
||||
|
||||
/* The keys are observers; the values are Array's containing all
|
||||
NotificationInvocation objects associated with the observer key. */
|
||||
NSMapTable *_observer_2_nr_array;
|
||||
}
|
||||
|
||||
|
||||
/* Adding new observers. */
|
||||
|
||||
/* Register observer to receive future notifications that match NAME
|
||||
and OBJECT. A nil passed as either NAME or OBJECT acts as a wild-card.
|
||||
If NAME is nil, send to the observer all notification pertaining to
|
||||
OBJECT. If OBJECT is nil, send to the observer all notification
|
||||
pertaining to NAME. If both OBJECT and NAME are nil, send to the
|
||||
observer all notifications.
|
||||
/* Register INVOCATION to receive future notifictions that match NAME
|
||||
and OBJECT. A nil passed as either NAME or OBJECT acts as a
|
||||
wild-card. If NAME is nil, the NotificationDispatcher will send to
|
||||
the observer all notification pertaining to OBJECT. If OBJECT is
|
||||
nil, the NotificationDispatcher will send to the observer all
|
||||
notification pertaining to NAME. If both OBJECT and NAME are nil,
|
||||
send to the observer all notifications.
|
||||
|
||||
The notification will be posted by sending -invokeWithObject: to
|
||||
INVOCATION argument. The argument of -invokeWithObject: will be
|
||||
a Notification object. This use of Invocation objects is more
|
||||
The notification will be posted by sending -invokeWithObject: to
|
||||
INVOCATION argument. The argument of -invokeWithObject: will be a
|
||||
Notification object. This use of Invocation objects is more
|
||||
flexible than using a selector, since Invocation's can be set up
|
||||
with more arguments, hold more context, and can be C functions.
|
||||
|
||||
Typically, in cases that INVOCATION is a MethodInvocation, the
|
||||
target of INVOCATION will the OBSERVER, but this is not required.
|
||||
When OBSERVER is not the same as the target, and is non-nil, it can
|
||||
still be useful for organizational help in removing a coherent set
|
||||
of observation requests, when used as an argument to -removeObserver:.
|
||||
|
||||
Neither OBSERVER nor OBJECT are retained; this is so these objects
|
||||
can tell when there are no outstanding non-notification references
|
||||
remaining. If an object may have added itself as an observer, it
|
||||
should call +removeObserver: in its -dealloc method.
|
||||
OBJECT is not retained; this is done so these objects can tell when
|
||||
there are no outstanding non-notification references remaining. If
|
||||
an object may have added itself as an observer, it should call
|
||||
+removeObserver: in its -dealloc method.
|
||||
|
||||
INVOCATION and NAME, however, are retained. */
|
||||
|
||||
- (void) addObserver: observer
|
||||
invocation: (id <Invoking>)invocation
|
||||
name: (id <String>)name
|
||||
object: object;
|
||||
- (void) addInvocation: (id <Invoking>)invocation
|
||||
name: (id <String>)name
|
||||
object: object;
|
||||
|
||||
/* For those that want the simplicity of specifying a selector instead of
|
||||
an invocation as a way to contact the observer.
|
||||
/* Register OBSERVER to receive future notifications that match NAME
|
||||
and OBJECT. A nil passed as either NAME or OBJECT acts as a
|
||||
wild-card. If NAME is nil, the NotificationDispatcher will send to
|
||||
the observer all notification pertaining to OBJECT. If OBJECT is
|
||||
nil, the NotificationDispatcher will send to the observer all
|
||||
notification pertaining to NAME. If both OBJECT and NAME are nil,
|
||||
send to the observer all notifications.
|
||||
|
||||
The notification will be posted by sending -perform:withObject:
|
||||
to the observer, with SEL and OBJECT as arguments.
|
||||
to the observer, with SEL and a Notification object as arguments.
|
||||
|
||||
Comments above about retaining apply here also. */
|
||||
Neither OBSERVER nor OBJECT are retained; this is done so these
|
||||
objects can tell when there are no outstanding non-notification
|
||||
references remaining. If an object may have added itself as an
|
||||
observer, it should call +removeObserver: in its -dealloc method.
|
||||
|
||||
INVOCATION and NAME, however, are retained. */
|
||||
|
||||
- (void) addObserver: observer
|
||||
selector: (SEL)sel
|
||||
|
@ -125,10 +134,9 @@
|
|||
/* Class versions of the above two methods that send these messages
|
||||
to the default NotificationDispatcher for the class. */
|
||||
|
||||
+ (void) addObserver: observer
|
||||
invocation: (id <Invoking>)invocation
|
||||
name: (id <String>)name
|
||||
object: object;
|
||||
+ (void) addInvocation: (id <Invoking>)invocation
|
||||
name: (id <String>)name
|
||||
object: object;
|
||||
+ (void) addObserver: observer
|
||||
selector: (SEL)sel
|
||||
name: (id <String>)name
|
||||
|
@ -138,21 +146,38 @@
|
|||
|
||||
/* Removing observers. */
|
||||
|
||||
/* Remove all notification requests that would be sent to INVOCATION. */
|
||||
|
||||
- (void) removeInvocation: invocation;
|
||||
|
||||
/* Remove the notification requests matching NAME and OBJECT that
|
||||
would be sent to INVOCATION. As with adding an observation
|
||||
request, nil NAME or OBJECT act as wildcards. */
|
||||
|
||||
- (void) removeInvocation: invocation
|
||||
name: (id <String>)name
|
||||
object: object;
|
||||
|
||||
/* Remove all records pertaining to OBSERVER. For instance, this
|
||||
should be called before the OBSERVER is -dealloc'ed. */
|
||||
|
||||
- (void) removeObserver: observer;
|
||||
|
||||
/* Remove the notification requests for the given parameters. As with
|
||||
adding an observation request, nil NAME or OBJECT act as wildcards. */
|
||||
/* Remove the notification requests for the given NAME and OBJECT
|
||||
parameters. As with adding an observation request, nil NAME or
|
||||
OBJECT act as wildcards. */
|
||||
|
||||
- (void) removeObserver: observer
|
||||
name: (id <String>)name
|
||||
object: object;
|
||||
|
||||
/* Class versions of the above two methods that send these messages
|
||||
/* Class versions of the above four methods that send these messages
|
||||
to the default NotificationDispatcher for the class. */
|
||||
|
||||
+ (void) removeInvocation: invocation;
|
||||
+ (void) removeInvocation: invocation
|
||||
name: (id <String>)name
|
||||
object: object;
|
||||
+ (void) removeObserver: observer;
|
||||
+ (void) removeObserver: observer
|
||||
name: (id <String>)name
|
||||
|
@ -160,16 +185,19 @@
|
|||
|
||||
|
||||
|
||||
/* Post NOTIFICATION to all the observers that match its NAME and OBJECT. */
|
||||
/* Post NOTIFICATION to all the observers that match its NAME and OBJECT.
|
||||
The INFO arguent does not have to be a Dictionary. If there is a single
|
||||
object that should be associated with the notification, you can simply
|
||||
pass that single object instead of a Dictionary containing the object. */
|
||||
|
||||
- (void) postNotification: notification;
|
||||
- (void) postNotificationName: (id <String>)name
|
||||
object: object;
|
||||
- (void) postNotificationName: (id <String>)name
|
||||
object: object
|
||||
userInfo: (id <ConstantKeyedCollecting>)info_dictionary;
|
||||
userInfo: info;
|
||||
|
||||
/* Class versions of the above two methods that send these messages
|
||||
/* Class versions of the above three methods that send these messages
|
||||
to the default NotificationDispatcher for the class. */
|
||||
|
||||
+ (void) postNotification: notification;
|
||||
|
@ -177,7 +205,7 @@
|
|||
object: object;
|
||||
+ (void) postNotificationName: (id <String>)name
|
||||
object: object
|
||||
userInfo: (id <ConstantKeyedCollecting>)info_dictionary;
|
||||
userInfo: info;
|
||||
|
||||
@end
|
||||
|
||||
|
|
|
@ -30,7 +30,7 @@
|
|||
This implementation has several advantages over OpenStep's
|
||||
NSNotificationCenter:
|
||||
|
||||
(1) Heavier use of hash tables and the use of LinkedList's make it
|
||||
(1) Heavy use of hash tables and the use of LinkedList's make it
|
||||
faster. Removing from the middle of LinkedList's is much more
|
||||
efficient than removing from the middle of Array's.
|
||||
|
||||
|
@ -38,15 +38,19 @@
|
|||
invocation objects instead of just selectors. Invocation objects
|
||||
are more flexible than selectors in that they can hold more context
|
||||
and, if desired, can call C functions instead of sending a message
|
||||
to an object, (this way you may be able to avoid creating a new
|
||||
to an object; (this way you may be able to avoid creating a new
|
||||
class just to handle certain notifications).
|
||||
|
||||
(3) Instead of sending +defaultCenter, you can simply send -add...,
|
||||
-remove... and -post... messages directly to the class object.
|
||||
(3) Instead of sending +defaultCenter, you can simply send +add...,
|
||||
+remove... and +post... messages directly to the class object.
|
||||
The class uses a static variable directly, instead of taking
|
||||
the time for the extra +defaultCenter method call. It's both
|
||||
easier for the user and more time efficient.
|
||||
|
||||
(4) You can call -addObserver:... with both name and object being
|
||||
nil. This request will receive postings of *all* notifications.
|
||||
Wow.
|
||||
|
||||
Although it offers extra features, the implementation has an
|
||||
OpenStep-style interface also.
|
||||
|
||||
|
@ -54,68 +58,73 @@
|
|||
|
||||
#include <objects/stdobjects.h>
|
||||
#include <objects/LinkedList.h>
|
||||
#include <objects/Array.h>
|
||||
#include <Foundation/NSMapTable.h>
|
||||
#include <objects/NSString.h>
|
||||
|
||||
@interface NotificationDispatcher : NSObject
|
||||
{
|
||||
/* For those observer requests with NAME=nil and OBJECT=nil. */
|
||||
LinkedList *anonymous_nr_list;
|
||||
/* For those observer requests with NAME=nil and OBJECT!=nil. */
|
||||
NSMapTable *object_2_nr_list;
|
||||
/* For those observer requests with NAME!=nil, OBJECT may or may not =nil .*/
|
||||
NSMapTable *name_2_nr_list;
|
||||
|
||||
/* The keys are observers; the values are Array's containing all
|
||||
NotificationInvocation objects associated with the observer key. */
|
||||
NSMapTable *observer_2_nr_array;
|
||||
|
||||
/* `nr' stands for Notification Request Object; the interface for
|
||||
this class is defined in the .m file. One of these is created
|
||||
for each -add... call. */
|
||||
|
||||
/* For those observer requests with NAME=nil and OBJECT=nil. */
|
||||
LinkedList *_anonymous_nr_list;
|
||||
/* For those observer requests with NAME=nil and OBJECT!=nil. */
|
||||
NSMapTable *_object_2_nr_list;
|
||||
/* For those observer requests with NAME!=nil, OBJECT may or may not =nil .*/
|
||||
NSMapTable *_name_2_nr_list;
|
||||
|
||||
/* The keys are observers; the values are Array's containing all
|
||||
NotificationInvocation objects associated with the observer key. */
|
||||
NSMapTable *_observer_2_nr_array;
|
||||
}
|
||||
|
||||
|
||||
/* Adding new observers. */
|
||||
|
||||
/* Register observer to receive future notifications that match NAME
|
||||
and OBJECT. A nil passed as either NAME or OBJECT acts as a wild-card.
|
||||
If NAME is nil, send to the observer all notification pertaining to
|
||||
OBJECT. If OBJECT is nil, send to the observer all notification
|
||||
pertaining to NAME. If both OBJECT and NAME are nil, send to the
|
||||
observer all notifications.
|
||||
/* Register INVOCATION to receive future notifictions that match NAME
|
||||
and OBJECT. A nil passed as either NAME or OBJECT acts as a
|
||||
wild-card. If NAME is nil, the NotificationDispatcher will send to
|
||||
the observer all notification pertaining to OBJECT. If OBJECT is
|
||||
nil, the NotificationDispatcher will send to the observer all
|
||||
notification pertaining to NAME. If both OBJECT and NAME are nil,
|
||||
send to the observer all notifications.
|
||||
|
||||
The notification will be posted by sending -invokeWithObject: to
|
||||
INVOCATION argument. The argument of -invokeWithObject: will be
|
||||
a Notification object. This use of Invocation objects is more
|
||||
The notification will be posted by sending -invokeWithObject: to
|
||||
INVOCATION argument. The argument of -invokeWithObject: will be a
|
||||
Notification object. This use of Invocation objects is more
|
||||
flexible than using a selector, since Invocation's can be set up
|
||||
with more arguments, hold more context, and can be C functions.
|
||||
|
||||
Typically, in cases that INVOCATION is a MethodInvocation, the
|
||||
target of INVOCATION will the OBSERVER, but this is not required.
|
||||
When OBSERVER is not the same as the target, and is non-nil, it can
|
||||
still be useful for organizational help in removing a coherent set
|
||||
of observation requests, when used as an argument to -removeObserver:.
|
||||
|
||||
Neither OBSERVER nor OBJECT are retained; this is so these objects
|
||||
can tell when there are no outstanding non-notification references
|
||||
remaining. If an object may have added itself as an observer, it
|
||||
should call +removeObserver: in its -dealloc method.
|
||||
OBJECT is not retained; this is done so these objects can tell when
|
||||
there are no outstanding non-notification references remaining. If
|
||||
an object may have added itself as an observer, it should call
|
||||
+removeObserver: in its -dealloc method.
|
||||
|
||||
INVOCATION and NAME, however, are retained. */
|
||||
|
||||
- (void) addObserver: observer
|
||||
invocation: (id <Invoking>)invocation
|
||||
name: (id <String>)name
|
||||
object: object;
|
||||
- (void) addInvocation: (id <Invoking>)invocation
|
||||
name: (id <String>)name
|
||||
object: object;
|
||||
|
||||
/* For those that want the simplicity of specifying a selector instead of
|
||||
an invocation as a way to contact the observer.
|
||||
/* Register OBSERVER to receive future notifications that match NAME
|
||||
and OBJECT. A nil passed as either NAME or OBJECT acts as a
|
||||
wild-card. If NAME is nil, the NotificationDispatcher will send to
|
||||
the observer all notification pertaining to OBJECT. If OBJECT is
|
||||
nil, the NotificationDispatcher will send to the observer all
|
||||
notification pertaining to NAME. If both OBJECT and NAME are nil,
|
||||
send to the observer all notifications.
|
||||
|
||||
The notification will be posted by sending -perform:withObject:
|
||||
to the observer, with SEL and OBJECT as arguments.
|
||||
to the observer, with SEL and a Notification object as arguments.
|
||||
|
||||
Comments above about retaining apply here also. */
|
||||
Neither OBSERVER nor OBJECT are retained; this is done so these
|
||||
objects can tell when there are no outstanding non-notification
|
||||
references remaining. If an object may have added itself as an
|
||||
observer, it should call +removeObserver: in its -dealloc method.
|
||||
|
||||
INVOCATION and NAME, however, are retained. */
|
||||
|
||||
- (void) addObserver: observer
|
||||
selector: (SEL)sel
|
||||
|
@ -125,10 +134,9 @@
|
|||
/* Class versions of the above two methods that send these messages
|
||||
to the default NotificationDispatcher for the class. */
|
||||
|
||||
+ (void) addObserver: observer
|
||||
invocation: (id <Invoking>)invocation
|
||||
name: (id <String>)name
|
||||
object: object;
|
||||
+ (void) addInvocation: (id <Invoking>)invocation
|
||||
name: (id <String>)name
|
||||
object: object;
|
||||
+ (void) addObserver: observer
|
||||
selector: (SEL)sel
|
||||
name: (id <String>)name
|
||||
|
@ -138,21 +146,38 @@
|
|||
|
||||
/* Removing observers. */
|
||||
|
||||
/* Remove all notification requests that would be sent to INVOCATION. */
|
||||
|
||||
- (void) removeInvocation: invocation;
|
||||
|
||||
/* Remove the notification requests matching NAME and OBJECT that
|
||||
would be sent to INVOCATION. As with adding an observation
|
||||
request, nil NAME or OBJECT act as wildcards. */
|
||||
|
||||
- (void) removeInvocation: invocation
|
||||
name: (id <String>)name
|
||||
object: object;
|
||||
|
||||
/* Remove all records pertaining to OBSERVER. For instance, this
|
||||
should be called before the OBSERVER is -dealloc'ed. */
|
||||
|
||||
- (void) removeObserver: observer;
|
||||
|
||||
/* Remove the notification requests for the given parameters. As with
|
||||
adding an observation request, nil NAME or OBJECT act as wildcards. */
|
||||
/* Remove the notification requests for the given NAME and OBJECT
|
||||
parameters. As with adding an observation request, nil NAME or
|
||||
OBJECT act as wildcards. */
|
||||
|
||||
- (void) removeObserver: observer
|
||||
name: (id <String>)name
|
||||
object: object;
|
||||
|
||||
/* Class versions of the above two methods that send these messages
|
||||
/* Class versions of the above four methods that send these messages
|
||||
to the default NotificationDispatcher for the class. */
|
||||
|
||||
+ (void) removeInvocation: invocation;
|
||||
+ (void) removeInvocation: invocation
|
||||
name: (id <String>)name
|
||||
object: object;
|
||||
+ (void) removeObserver: observer;
|
||||
+ (void) removeObserver: observer
|
||||
name: (id <String>)name
|
||||
|
@ -160,16 +185,19 @@
|
|||
|
||||
|
||||
|
||||
/* Post NOTIFICATION to all the observers that match its NAME and OBJECT. */
|
||||
/* Post NOTIFICATION to all the observers that match its NAME and OBJECT.
|
||||
The INFO arguent does not have to be a Dictionary. If there is a single
|
||||
object that should be associated with the notification, you can simply
|
||||
pass that single object instead of a Dictionary containing the object. */
|
||||
|
||||
- (void) postNotification: notification;
|
||||
- (void) postNotificationName: (id <String>)name
|
||||
object: object;
|
||||
- (void) postNotificationName: (id <String>)name
|
||||
object: object
|
||||
userInfo: (id <ConstantKeyedCollecting>)info_dictionary;
|
||||
userInfo: info;
|
||||
|
||||
/* Class versions of the above two methods that send these messages
|
||||
/* Class versions of the above three methods that send these messages
|
||||
to the default NotificationDispatcher for the class. */
|
||||
|
||||
+ (void) postNotification: notification;
|
||||
|
@ -177,7 +205,7 @@
|
|||
object: object;
|
||||
+ (void) postNotificationName: (id <String>)name
|
||||
object: object
|
||||
userInfo: (id <ConstantKeyedCollecting>)info_dictionary;
|
||||
userInfo: info;
|
||||
|
||||
@end
|
||||
|
||||
|
|
Loading…
Reference in a new issue