Permalink
Browse files

A whole bunch more stuff. Nearly got a nice API built up for the stat…

…e machine itself.
  • Loading branch information...
1 parent 7bde333 commit 03421a40beb4659557ad2fb209f3718e4110ef2a Jim Dovey committed Jun 28, 2011

Large diffs are not rendered by default.

Oops, something went wrong.
@@ -47,15 +47,44 @@
+ (AQAppStateMachine *) appStateMachine;
// core notification API— everything else funnels through these functions
-- (void) notifyForChangesToStateBitAtIndex: (NSUInteger) index usingBlock: (void (^)(void)) block;
-- (void) notifyForChangesToStateBitsInRange: (NSRange) range usingBlock: (void (^)(void)) block;
-- (void) notifyForChangesToStateBitsInRange: (NSRange) range maskedWithInteger: (NSUInteger) mask
+- (void) notifyForChangesToStateBitAtIndex: (NSUInteger) index
+ usingBlock: (void (^)(void)) block;
+
+- (void) notifyForChangesToStateBitsInRange: (NSRange) range
+ usingBlock: (void (^)(void)) block;
+- (void) notifyForChangesToStateBitsInRange: (NSRange) range
+ maskedWithInteger: (NSUInteger) mask
usingBlock: (void (^)(void)) block;
-- (void) notifyForChangesToStateBitsInRange: (NSRange) range maskedWith64BitInteger: (UInt64) mask
+- (void) notifyForChangesToStateBitsInRange: (NSRange) range
+ maskedWith64BitInteger: (UInt64) mask
usingBlock: (void (^)(void))block;
-- (void) notifyForChangesToStateBitsInRange: (NSRange) range maskedWithBits: (AQBitfield *) mask
+- (void) notifyForChangesToStateBitsInRange: (NSRange) range
+ maskedWithBits: (AQBitfield *) mask
usingBlock: (void (^)(void)) block;
+- (void) notifyForEqualityOfStateBitsInRange: (NSRange) range
+ toIntegerValue: (NSUInteger) value
+ block: (void (^)(void)) block;
+- (void) notifyForEqualityOfStateBitsInRange: (NSRange) range
+ to64BitValue: (UInt64) value
+ block: (void (^)(void)) block;
+- (void) notifyForEqualityOfStateBitsInRange: (NSRange) range
+ toValue: (AQBitfield *) value
+ usingBlock: (void (^)(void)) block;
+
+- (void) notifyForEqualityOfStateBitsInRange: (NSRange) range
+ maskedWith: (NSUInteger) mask
+ toIntegerValue: (NSUInteger) value
+ block: (void (^)(void)) block;
+- (void) notifyForEqualityOfStateBitsInRange: (NSRange) range
+ maskedWith: (UInt64) mask
+ to64BitValue: (UInt64) value
+ block: (void (^)(void)) block;
+- (void) notifyForEqualityOfStateBitsInRange: (NSRange) range
+ maskedWith: (AQBitfield *) mask
+ toValue: (AQBitfield *) value
+ block: (void (^)(void)) block;
+
@end
/*!
@@ -35,7 +35,8 @@
#import "AQAppStateMachine.h"
#import "AQRange.h"
-#import "AQStateMatchingDescriptor.h"
+#import "AQStateMaskMatchingDescriptor.h"
+#import "AQStateMaskedEqualityMatchingDescriptor.h"
#import <dispatch/dispatch.h>
@implementation AQAppStateMachine
@@ -88,18 +89,25 @@ - (void) dealloc
- (void) _runNotificationBlocksForChangeInRange: (NSRange) range
{
- for ( AQStateMatchingDescriptor * match in _matchDescriptors )
+ for ( AQStateMaskMatchingDescriptor * match in _matchDescriptors )
{
- if ( [match matchesRange: range] == NO )
+ if ( [match isKindOfClass: [AQStateMaskedEqualityMatchingDescriptor class]] )
+ {
+ if ( [(AQStateMaskedEqualityMatchingDescriptor *)match matchesBitfield: _stateBits] == NO )
+ continue;
+ }
+ else if ( [match matchesRange: range] == NO )
+ {
continue;
+ }
dispatch_block_t block = (dispatch_block_t)[_notifierLookup objectForKey: [match uniqueID]];
if ( block != nil )
block();
}
}
-- (void) _notifyForChangesToStatesMatchingDescriptor: (AQStateMatchingDescriptor *) desc
+- (void) _notifyForChangesToStatesMatchingDescriptor: (AQStateMaskMatchingDescriptor *) desc
usingBlock: (void (^)(void)) block
{
[_matchDescriptors addObject: desc];
@@ -120,7 +128,7 @@ - (void) notifyForChangesToStateBitAtIndex: (NSUInteger) index usingBlock: (void
- (void) notifyForChangesToStateBitsInRange: (NSRange) range usingBlock: (void (^)(void)) block
{
// create match descriptor and store it
- AQStateMatchingDescriptor * desc = [[AQStateMatchingDescriptor alloc] initWithRange: range matchingMask: nil];
+ AQStateMaskMatchingDescriptor * desc = [[AQStateMaskMatchingDescriptor alloc] initWithRange: range matchingMask: nil];
[self _notifyForChangesToStatesMatchingDescriptor: desc usingBlock: block];
#if !USING_ARC
[desc release];
@@ -131,7 +139,7 @@ - (void) notifyForChangesToStateBitsInRange: (NSRange) range
maskedWithInteger: (NSUInteger) mask
usingBlock: (void (^)(void)) block
{
- AQStateMatchingDescriptor * desc = [[AQStateMatchingDescriptor alloc] initWith32BitMask: mask forRange: range];
+ AQStateMaskMatchingDescriptor * desc = [[AQStateMaskMatchingDescriptor alloc] initWith32BitMask: mask forRange: range];
[self _notifyForChangesToStatesMatchingDescriptor: desc usingBlock: block];
#if !USING_ARC
[desc release];
@@ -141,7 +149,7 @@ - (void) notifyForChangesToStateBitsInRange: (NSRange) range
- (void) notifyForChangesToStateBitsInRange: (NSRange) range maskedWith64BitInteger: (UInt64) mask
usingBlock: (void (^)(void))block
{
- AQStateMatchingDescriptor * desc = [[AQStateMatchingDescriptor alloc] initWith64BitMask: mask forRange: range];
+ AQStateMaskMatchingDescriptor * desc = [[AQStateMaskMatchingDescriptor alloc] initWith64BitMask: mask forRange: range];
[self _notifyForChangesToStatesMatchingDescriptor: desc usingBlock: block];
#if !USING_ARC
[desc release];
@@ -152,7 +160,76 @@ - (void) notifyForChangesToStateBitsInRange: (NSRange) range
maskedWithBits: (AQBitfield *) mask
usingBlock: (void (^)(void)) block
{
- AQStateMatchingDescriptor * desc = [[AQStateMatchingDescriptor alloc] initWithRange: range matchingMask: mask];
+ AQStateMaskMatchingDescriptor * desc = [[AQStateMaskMatchingDescriptor alloc] initWithRange: range matchingMask: mask];
+ [self _notifyForChangesToStatesMatchingDescriptor: desc usingBlock: block];
+#if !USING_ARC
+ [desc release];
+#endif
+}
+
+- (void) notifyForEqualityOfStateBitsInRange: (NSRange) range
+ toIntegerValue: (NSUInteger) value
+ block: (void (^)(void)) block
+{
+ AQStateMaskedEqualityMatchingDescriptor * desc = [[AQStateMaskedEqualityMatchingDescriptor alloc] initWith32BitValue: value forRange: range];
+ [self _notifyForChangesToStatesMatchingDescriptor: desc usingBlock: block];
+#if !USING_ARC
+ [desc release];
+#endif
+}
+
+- (void) notifyForEqualityOfStateBitsInRange: (NSRange) range
+ to64BitValue: (UInt64) value
+ block: (void (^)(void)) block
+{
+ AQStateMaskedEqualityMatchingDescriptor * desc = [[AQStateMaskedEqualityMatchingDescriptor alloc] initWith64BitValue: value forRange: range];
+ [self _notifyForChangesToStatesMatchingDescriptor: desc usingBlock: block];
+#if !USING_ARC
+ [desc release];
+#endif
+}
+
+- (void) notifyForEqualityOfStateBitsInRange: (NSRange) range
+ toValue: (AQBitfield *) value
+ usingBlock: (void (^)(void)) block
+{
+ AQStateMaskedEqualityMatchingDescriptor * desc = [[AQStateMaskedEqualityMatchingDescriptor alloc] initWithRange: range matchingValue: value];
+ [self _notifyForChangesToStatesMatchingDescriptor: desc usingBlock: block];
+#if !USING_ARC
+ [desc release];
+#endif
+}
+
+- (void) notifyForEqualityOfStateBitsInRange: (NSRange) range
+ maskedWith: (NSUInteger) mask
+ toIntegerValue: (NSUInteger) value
+ block: (void (^)(void)) block
+{
+ AQStateMaskedEqualityMatchingDescriptor * desc = [[AQStateMaskedEqualityMatchingDescriptor alloc] initWith32BitValue: value forRange: range matchingMask: mask];
+ [self _notifyForChangesToStatesMatchingDescriptor: desc usingBlock: block];
+#if !USING_ARC
+ [desc release];
+#endif
+}
+
+- (void) notifyForEqualityOfStateBitsInRange: (NSRange) range
+ maskedWith: (UInt64) mask
+ to64BitValue: (UInt64) value
+ block: (void (^)(void)) block
+{
+ AQStateMaskedEqualityMatchingDescriptor * desc = [[AQStateMaskedEqualityMatchingDescriptor alloc] initWith64BitValue: value forRange: range matchingMask: mask];
+ [self _notifyForChangesToStatesMatchingDescriptor: desc usingBlock: block];
+#if !USING_ARC
+ [desc release];
+#endif
+}
+
+- (void) notifyForEqualityOfStateBitsInRange: (NSRange) range
+ maskedWith: (AQBitfield *) mask
+ toValue: (AQBitfield *) value
+ block: (void (^)(void)) block
+{
+ AQStateMaskedEqualityMatchingDescriptor * desc = [[AQStateMaskedEqualityMatchingDescriptor alloc] initWithRange: range matchingValue: value withMask: mask];
[self _notifyForChangesToStatesMatchingDescriptor: desc usingBlock: block];
#if !USING_ARC
[desc release];
@@ -249,53 +326,37 @@ - (void) notifyChangesToStateMachineValuesWithName: (NSString *) name
[self notifyForChangesToStateBitsInRange: range.range maskedWithBits: mask usingBlock: block];
}
-@end
-
-@implementation AQAppStateMachine (MultipleEnumerationNotifications)
+- (void) notifyEqualityOfStateMachineValuesWithName: (NSString *) name
+ toInteger: (NSUInteger) value
+ usingBlock: (void (^)(void)) block
+{
+ AQRange * range = [_namedRanges objectForKey: name];
+ if ( range == nil )
+ return; // nonexistent named range
+
+
+}
-- (void) notifyChangesToStateMachineValuesWithNames: (NSArray *) names
- matchingMasks: (NSArray *) masks
+- (void) notifyEqualityOfStateMachineValuesWithName: (NSString *) name
+ toUInt64: (NSUInteger) value
usingBlock: (void (^)(void)) block
{
- NSParameterAssert([names count] == [masks count]);
- NSParameterAssert(block != nil);
+ AQRange * range = [_namedRanges objectForKey: name];
+ if ( range == nil )
+ return; // nonexistent named range
- NSMutableArray * ranges = [NSMutableArray new];
- [names enumerateObjectsUsingBlock: ^(__strong id obj, NSUInteger idx, BOOL *stop){[ranges addObject: obj];}];
- NSMutableArray * bitmasks = [NSMutableArray new];
- [masks enumerateObjectsUsingBlock: ^(__strong id obj, NSUInteger idx, BOOL *stop) {
- if ( [obj isKindOfClass: [AQBitfield class]] )
- {
- [bitmasks addObject: obj];
- }
- else if ( [obj isKindOfClass: [NSNumber class]] )
- {
- AQBitfield * field = [AQBitfield new];
- UInt64 bits = [obj unsignedLongLongValue];
- for ( NSUInteger i = 0; i > 0; i++, bits >>= 1 )
- {
- if ( (bits & 1) == 1 )
- [field setBit: 1 atIndex: i];
- }
-
- [bitmasks addObject: field];
- }
- else
- {
- // throw an exception, but only on debug builds
- NSAssert(NO, @"Invalid object type in masks array: %@", NSStringFromClass([obj class]));
- }
- }];
+}
+
+- (void) notifyEqualityOfStateMachineValuesWithName: (NSString *) name
+ toBits: (AQBitfield *) bits
+ usingBlock: (void (^)(void)) block
+{
+ AQRange * range = [_namedRanges objectForKey: name];
+ if ( range == nil )
+ return; // nonexistent named range
+
- AQStateMatchingDescriptor * desc = [[AQStateMatchingDescriptor alloc] initWithRanges: ranges
- matchingMasks: bitmasks];
- [self _notifyForChangesToStatesMatchingDescriptor: desc usingBlock: block];
-#if !USING_ARC
- [ranges release];
- [bitmasks release];
- [desc release];
-#endif
}
- (BOOL) bitIsSetAtIndex: (NSUInteger) index forName: (NSString *) name
@@ -329,7 +390,7 @@ - (BOOL) bitsSetAtIndexes: (NSIndexSet *) indexes forName: (NSString *) name
*stop = YES;
}
}];
-
+
#if !USING_ARC
[test release];
#endif
@@ -357,6 +418,100 @@ - (BOOL) bitValuesForName: (NSString *) name matchBits: (AQBitfield *) bits
@end
+@implementation AQAppStateMachine (MultipleEnumerationNotifications)
+
+- (void) notifyChangesToStateMachineValuesWithNames: (NSArray *) names
+ matchingMasks: (NSArray *) masks
+ usingBlock: (void (^)(void)) block
+{
+ NSParameterAssert([names count] == [masks count]);
+ NSParameterAssert(block != nil);
+
+ NSMutableArray * ranges = [NSMutableArray new];
+ [names enumerateObjectsUsingBlock: ^(__strong id obj, NSUInteger idx, BOOL *stop){[ranges addObject: obj];}];
+
+ NSMutableArray * bitmasks = [NSMutableArray new];
+ [masks enumerateObjectsUsingBlock: ^(__strong id obj, NSUInteger idx, BOOL *stop) {
+ if ( [obj isKindOfClass: [AQBitfield class]] )
+ {
+ [bitmasks addObject: obj];
+ }
+ else if ( [obj isKindOfClass: [NSNumber class]] )
+ {
+ AQBitfield * field = [AQBitfield new];
+ UInt64 bits = [obj unsignedLongLongValue];
+ for ( NSUInteger i = 0; i > 0; i++, bits >>= 1 )
+ {
+ if ( (bits & 1) == 1 )
+ [field setBit: 1 atIndex: i];
+ }
+
+ [bitmasks addObject: field];
+ }
+ else
+ {
+ // throw an exception, but only on debug builds
+ NSAssert(NO, @"Invalid object type in masks array: %@", NSStringFromClass([obj class]));
+ }
+ }];
+
+ AQStateMaskMatchingDescriptor * desc = [[AQStateMaskMatchingDescriptor alloc] initWithRanges: ranges
+ matchingMasks: bitmasks];
+ [self _notifyForChangesToStatesMatchingDescriptor: desc usingBlock: block];
+#if !USING_ARC
+ [ranges release];
+ [bitmasks release];
+ [desc release];
+#endif
+}
+
+- (void) notifyEqualityOfStateMachineValuesWithNames: (NSArray *) names
+ matchingMasks: (NSArray *) masks
+ toValues: (NSArray *) values
+ usingBlock: (void (^)(void)) block
+{
+ NSParameterAssert([names count] == [masks count]);
+ NSParameterAssert(block != nil);
+
+ NSMutableArray * ranges = [NSMutableArray new];
+ [names enumerateObjectsUsingBlock: ^(__strong id obj, NSUInteger idx, BOOL *stop){[ranges addObject: obj];}];
+
+ NSMutableArray * bitmasks = [NSMutableArray new];
+ [masks enumerateObjectsUsingBlock: ^(__strong id obj, NSUInteger idx, BOOL *stop) {
+ if ( [obj isKindOfClass: [AQBitfield class]] )
+ {
+ [bitmasks addObject: obj];
+ }
+ else if ( [obj isKindOfClass: [NSNumber class]] )
+ {
+ AQBitfield * field = [AQBitfield new];
+ UInt64 bits = [obj unsignedLongLongValue];
+ for ( NSUInteger i = 0; i > 0; i++, bits >>= 1 )
+ {
+ if ( (bits & 1) == 1 )
+ [field setBit: 1 atIndex: i];
+ }
+
+ [bitmasks addObject: field];
+ }
+ else
+ {
+ // throw an exception, but only on debug builds
+ NSAssert(NO, @"Invalid object type in masks array: %@", NSStringFromClass([obj class]));
+ }
+ }];
+
+ AQStateMaskedEqualityMatchingDescriptor * desc = [[AQStateMaskedEqualityMatchingDescriptor alloc] initWithRanges: ranges masks: bitmasks matchingValues: values];
+ [self _notifyForChangesToStatesMatchingDescriptor: desc usingBlock: block];
+#if !USING_ARC
+ [ranges release];
+ [bitmasks release];
+ [desc release];
+#endif
+}
+
+@end
+
@implementation AQAppStateMachine (InteriorThingsICantHelpMyselfFromExposing)
- (NSRange) underlyingBitfieldRangeForName: (NSString *) name
Oops, something went wrong.

0 comments on commit 03421a4

Please sign in to comment.