Есть ли способ отправить BOOL в селектор?
[self performSelector:@selector(doSomething:) withObject:YES afterDelay:1.5];
Или я должен использовать NSInvocation? Может ли кто-нибудь написать образец, пожалуйста?
Есть ли способ отправить BOOL в селектор?
[self performSelector:@selector(doSomething:) withObject:YES afterDelay:1.5];
Или я должен использовать NSInvocation? Может ли кто-нибудь написать образец, пожалуйста?
вы можете использовать NSNumber для переноса типов bools:
BOOL myBool = Yes;
NSNumber *passedValue = [NSNumber numberWithBool:myBool];
[self performSelector:@selector(doSomething:) withObject:passedValue afterDelay:1.5];
и в селекторе, чтобы получить значение bool, вы используете:
BOOL value = [recievedObject boolValue];
В случае, если вы не можете изменить сигнатуру целевого метода, чтобы принять NSNumber
вместо BOOL
, вы можете использовать NSInvocation
вместо performSelector
:
MyTargetClass* myTargetObject;
BOOL myBoolValue = YES; // or NO
NSMethodSignature* signature = [[myTargetObject class] instanceMethodSignatureForSelector: @selector( myMethodTakingBool: )];
NSInvocation* invocation = [NSInvocation invocationWithMethodSignature: signature];
[invocation setTarget: myTargetObject];
[invocation setSelector: @selector( myMethodTakingBool: ) ];
[invocation setArgument: &myBoolValue atIndex: 2];
[invocation invoke];
Самый простой способ заключается в следующем:
Если у вас есть метод
-(void)doSomething:(BOOL)flag
и хотите выполнитьSelecor с флагом = НЕТ использовать
[object performSelector:@selector(doSomething:) withObject:nil];
В случае флага = YES вы можете отправить любой объект, например, @YES - номер из bool
[object performSelector:@selector(doSomething:) withObject:@YES];
Примечание: не используйте @NO! Только nil будет интерпретироваться как NO в вашем методе с аргументом bool.
используйте dispatch_after в основном потоке, как это:
dispatch_time_t delayTime = dispatch_time(DISPATCH_TIME_NOW, (_animationDuration+1) * NSEC_PER_SEC);
dispatch_after(delayTime, dispatch_get_main_queue(), ^{
[self completeAnimation:NO];
});
если вы хотите передать NO, и только NO, вы можете вместо этого поставить нуль
[self performSelector:@selector(doSomething:) withObject:0 afterDelay:1.5];
Но помните, просто работайте для нуля, не компилируется с ARC, который запрещает неявное преобразование
Это может быть не самый элегантный, но я создал еще одну процедуру, чтобы вызвать процедуру с bool. Это упрощает выбор селектора и не требует доступа к изменению первоначальной процедуры.
[Добавлено Ash] Здесь образец, который отклоняет значение альфа-приемника при установке логического свойства:
- (void) setVisible:(BOOL)visible
{
_visible = visible;
self.alpha = 0.0;
}
- (void) setVisibleUsingNSNumber:(NSNumber *)visible
{
self.visible = [visible boolValue];
}
Затем вы можете запустить это после задержки таким образом:
[self performSelector:@selector(setVisibleUsingNSNumber:)
withObject:[NSNumber numberWithBool:YES]
afterDelay:0.5];
Обратите внимание, что в наши дни также можно использовать Grand Central Dispatch, и в этом случае вы можете использовать стандартный метод setter внутри блока в обход всего этого дополнительного кода. Тем не менее, гораздо проще отменить вызов performSelector, чем обнаруживать отмену в рамках выполнения отложенного блока.
Другой способ сделать это - передать nil
для NO
и anything else
для YES
[self performSelector: @selector (doSomething:) withObject: nil];
doSomething для параметра BOOL будет иметь значение NO
-
[self performSelector: @selector (doSomething:) withObject: [NSNumber numberWithBool: YES]];
doSomething для параметра BOOL будет иметь значение YES
-
[self performSelector: @selector (doSomething:) withObject: [NSNumber numberWithBool: NO]];
doSomething для параметра BOOL будет иметь значение YES (даже прошло число с NO)
Вы не можете отправлять аргументы в селектор, подобный этому.
Возможно, вы захотите посмотреть следующий ответ:
видел, как этот трюк формирует другой пост, но передайте nil для NO и self для YES.
С литералами objective-C это может быть выражено менее подробным.
[self performSelector:@selector(doSomething:) withObject:@(YES) afterDelay:1.5];
Обратите внимание на @(YES)
i.s.o. YES
Если вы передаете параметры BOOL в статическом, вы можете использовать следующее.
------ > Чтобы передать "НЕТ":
[self performSelector:@selector(doSomething:) withObject:0 afterDelay:1.5];
Теперь получите результат после TimeInterval:
-(void)doSomething:(BOOL)isDoSomething
{
NSLog([email protected]"Do Something":@"Don't Do Any Thing");
}
Здесь вы получите " Do Do Do Any Thing" в журнале.
------ > Чтобы передать "YES":
[self performSelector:@selector(doSomething:) withObject:@"1" afterDelay:1.5];
Теперь получите результат после TimeInterval:
-(void)doSomething:(BOOL)isDoSomething
{
NSLog([email protected]"Do Something":@"Don't Do Any Thing");
}
Здесь вы получите " Do Something" в журнале.
Вместо того, чтобы полагаться на NSInvocation или изменять метод использования NSNumber, это можно сделать гораздо более элегантно, создав представление, например:
@interface CLLocationManager(CompatibleView)
@property (nonatomic) BOOL allowsBackgroundLocationUpdates;
@end
@implementation SampleClass
- (void)sampleFunc:(CLLocationManager *)locationManager {
if ([locationManager respondsToSelector:@selector(setAllowsBackgroundLocationUpdates:)]) {
locationManager.allowsBackgroundLocationUpdates = YES;
}
}
@end
Попробуйте обернуть свой bool в NSNumber: [NSNumber numberWithBool:myBool]
И вы можете вернуть его с помощью [myNumber boolValue]
Я делаю так:
[_button performSelector:@selector(setUserInteractionEnabled:) withObject:[NSString stringWithFormat:@"YES"] afterDelay:nil];