Reputation: 3
How to execute a block asynchronously before statement in same method?
The return always execute before block, but if that the commit always equals to No.
I want the block execute before return.
How can I do it?
I try dispatch_semaphore_t
but checkVerifyCode
is in main thread.
I can't block the main thread.
-(BOOL)checkVerifyCode
{
__block BOOL commit = NO;
[SMSSDK commitVerificationCode:self.verificationNum.text phoneNumber:self.phoneNumber.text zone:@"86" result:^(NSError *error) {
if (error) {
NSString *errInfo = [error.userInfo objectForKey:@"commitVerificationCode"];
MBProgressHUD *hud = [MBProgressHUD showHUDAddedTo:self.view animated:YES];
[hud setMode:MBProgressHUDModeText];
[hud setLabelText:@"验证码输入错误"];
[hud setLabelText:errInfo];
hud.color = [UIColor clearColor];
hud.labelColor = [UIColor colorWithRed:118/255.f green:214/255.f blue:255/255.f alpha:0.8f];
hud.detailsLabelColor = [UIColor colorWithRed:118/255.f green:214/255.f blue:255/255.f alpha:0.8f];
hud.margin = 10.f;
hud.yOffset = -100.f;
hud.removeFromSuperViewOnHide = YES;
[hud hide:YES afterDelay:3];
NSDictionary *dict = [NSDictionary dictionaryWithObject:[NSNumber numberWithBool:commit] forKey:@"bool"];
[self performSelectorOnMainThread:@selector(setCommit:) withObject:dict waitUntilDone:NO];
}else
{
NSDictionary *dict = [NSDictionary dictionaryWithObject:[NSNumber numberWithBool:commit] forKey:@"bool"];
[self performSelectorOnMainThread:@selector(setCommit:) withObject:dict waitUntilDone:NO];
commit = YES;
}
}];
return commit;
}
Upvotes: 0
Views: 118
Reputation: 105
Rather than return the value 'commit' like you are currently doing, pass into the method a completion block that takes a 'bool' as a parameter. Then the caller would be able to pass code into 'verifyCheckCode' and have it asynchronously executed.
Upvotes: 0
Reputation: 162722
You are effectively asking to make an asynchronous method synchronous. And since your call to the checkVerifyCode
method is on the main thread, that would require blocking the main thread (which, as noted, is bad idea).
Instead, you should move to having some method somewhere which you can call to update based on the result of the asynchronous method.
I.e.:
checkVerifyCode
to return void
and _
[self _checkVerifyDone:commit];
And, if you really need it on the main queue:
dispatch_async(dispatch_get_main_queue(), ^{
[self _checkVerifyDone:commit];
});
Upvotes: 1
Reputation: 2579
You can dispatch the entire function to a separate queue, then use dispatch_semaphore
to block that queue until the result is returned.
What's your higher level goal here? It seems like a dispatch_notify_group
might be what you're looking for, but it's hard to tell from your question. I understand the problem you're trying to solve, but what is the big picture?
Upvotes: 0