Y a-t-il un moyen facile de retarder un appel de méthode pendant 1 seconde?
J'ai un UIImageView
qui réagit à un événement tactile. Lorsque le toucher est détecté, certaines animations se produisent dans l'application. Après une seconde, je veux appeler une autre méthode. Dans ce cas, je ne peux pas utiliser le sélecteur animationDidStop
.
performSelector:withObject:afterDelay:
Vous pouvez aussi utiliser un bloc
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, 1 * NSEC_PER_SEC), dispatch_get_main_queue(), ^{
[object method];
});
La plupart du temps, vous voudrez utiliser dispatch_get_main_queue, bien que s'il n'y a pas d'interface utilisateur dans la méthode, vous pouvez utiliser un file d'attente globale .
Modifier:
Swift 3 version:
DispatchQueue.main.asyncAfter(deadline: .now() + 1) {
object.method()
}
De même, DispatchQueue.global().asyncAfter(...
pourrait également être une bonne option.
La meilleure façon de faire est:
[self performSelector:@selector(YourFunctionName)
withObject:(can be Self or Object from other Classes)
afterDelay:(Time Of Delay)];
vous pouvez également passer nil en tant que paramètre withObject.
exemple :
[self performSelector:@selector(subscribe) withObject:self afterDelay:3.0 ];
Il y a déjà beaucoup de réponses et elles sont toutes correctes. Si vous souhaitez utiliser le dispatch_after
, vous devez rechercher l'extrait de code inclus dans le Code Snippet Library
en bas à droite (où vous pouvez sélectionner les éléments UI
.).
Il vous suffit donc d'appeler cet extrait en écrivant dispatch dans le code:
Vous pouvez utiliser le sélecteur de performance après que la méthode de délai de 0,1 seconde soit appelée pour le code suivant.
[self performSelector:@selector(InsertView) withObject:nil afterDelay:0.1];
Vous pouvez aussi:
[UIView animateWithDuration:1.0
animations:^{ self.view.alpha = 1.1; /* Some fake chages */ }
completion:^(BOOL finished)
{
NSLog(@"A second lapsed.");
}];
Dans ce cas, vous devez simuler des modifications dans certaines vues pour que l'animation fonctionne. C'est hacky en effet, mais j'aime les trucs en bloc. Ou résumez la réponse @mcfedr ci-dessous.
waitFor(1.0, ^
{
NSLog(@"A second lapsed");
});
typedef void (^WaitCompletionBlock)();
void waitFor(NSTimeInterval duration, WaitCompletionBlock completion)
{
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, duration * NSEC_PER_SEC),
dispatch_get_main_queue(), ^
{ completion(); });
}
Tu peux le faire
[self performSelector:@selector(MethodToExecute) withObject:nil afterDelay:1.0 ];
Swift 2.x
let delayTime = dispatch_time(DISPATCH_TIME_NOW, Int64(1 * Double(NSEC_PER_SEC)))
dispatch_after(delayTime, dispatch_get_main_queue()) {
print("do some work")
}
Swift 3.x - & - Swift 4
DispatchQueue.main.asyncAfter(deadline: .now() + 1.0) {
print("do some work")
}
ou passer un escaping closure
func delay(seconds: Double, completion: @escaping()-> Void) {
DispatchQueue.main.asyncAfter(deadline: .now() + seconds, execute: completion)
}
Il existe une solution Swift 3 de la solution vérifiée:
self.perform(#selector(self.targetMethod), with: self, afterDelay: 1.0)
Et il y a la méthode
@objc fileprivate func targetMethod(){
}
Utiliser dans Swift 3
perform(<Selector>, with: <object>, afterDelay: <Time in Seconds>)