In objective-c I have a code in .h file:
typedef void(^SocketConnectionLost)();
typedef void(^SocketIOCallback)(id argsData);
@interface SocketConnection
@property (strong, nonatomic) SocketIO *socketIO;
@property (strong, nonatomic) NSMutableArray *socketConnectionLosts;
-(void)sendEventWithName:(NSString*)eventName
withData:(id)data
onConnectionLost:(SocketConnectionLost)connectionLost
onAnswer:(SocketIOCallback)answer;
@end
And I have a code in .m file:
@implementation SocketConnection
- (void)init {
self.socketIO = [[SocketIO alloc] initWithDelegate:self];
[self.socketIO setReturnAllDataFromAck: YES];
[self.socketIO connectToHost:kSocketHost onPort:kSocketPort withParams:params];
}
- (void) socketIODidDisconnect:(SocketIO *)socket
disconnectedWithError:(NSError *)error {
for(ServerRequestConnectionLost connectionLost in self.socketConnectionLosts)
if(connectionLost)
connectionLost();
[self.socketConnectionLosts removeAllObjects];
}
-(void)sendEventWithName:(NSString*)eventName
withData:(id)data
onConnectionLost:(SocketConnectionLost)connectionLost
onAnswer:(SocketIOCallback)answer {
[self.socketConnectionLosts addObject:connectionLost];
[self.socketIO sendEvent:eventName withData:data andAcknowledge:^(id argsData) {
if(connectionLost)
[self.socketConnectionLosts removeObject:connectionLost];
if(answer)
answer(argsData);
}];
}
@end
Please help me reproduce this code in Swift, I don't understand how to create, add and remove Swift blocks with Array on NSArray
This is how I try to create some block in Swift:
var someBlock: ()->()
var connectionLosts = NSMutableArray()
connectionLosts.append(someBlock)
Compiler show me the error: Type '()->()' doesn't confirm to protocol 'AnyObject'
Then I need to remove someBlock from the array, like [self.socketConnectionLosts removeObject:connectionLost] in obj-c and I don't understand how to do it with Swift array.
You don't have to use an objective-c array, just a swift array. Check this out:
typealias ClosureType = () -> ()
var someClosure: ClosureType = { println("Closure executed") }
var array = [ClosureType]()
array.append(someClosure)
array[0]()
If you run that in playground, the last line will print Closure executed
.
The reason why a NSArray
doesn't work is that it is bridged as an array of AnyObject
in swift - but AnyObject
is an instance of any class type, and obviously a closure is not a class.
As for removing an item from an array, that's a more complicated issue. find
cannot be used because it requires the array type to implement the Equatable
protocol, but closures don't implement it, and they cannot be extended.
Maybe rather than using an array you can use a dictionary, with a key type that makes sense for you depending on your app logic - such as a textual name, an enum, etc. For example, if you use an enum:
enum ClosureEnum {
case TEST_ELEMENT
}
var dict = [ClosureEnum:ClosureType]()
dict[.TEST_ELEMENT] = someClosure
dict[.TEST_ELEMENT]!()
Note the !
in dict[.TEST_ELEMENT]!()
, required because a lookup in a dictionary always return an optional. You can use forced unwrapping like that, or enclose it in an optional binding for safer code.
To remove an element, just use the proper method:
dict.removeValueForKey(.TEST_ELEMENT)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With