Existe-t-il un moyen de savoir si une AVPlayer
lecture est bloquée ou a atteint la fin?
106
Existe-t-il un moyen de savoir si une AVPlayer
lecture est bloquée ou a atteint la fin?
Pour recevoir une notification pour atteindre la fin d'un élément (via Apple ):
[[NSNotificationCenter defaultCenter]
addObserver:<self>
selector:@selector(<#The selector name#>)
name:AVPlayerItemDidPlayToEndTimeNotification
object:<#A player item#>];
Et pour suivre la lecture, vous pouvez:
« suivre l' évolution de la position de la tête de lecture dans un objet AVPlayer » en utilisant addPeriodicTimeObserverForInterval: file: usingBlock: ou addBoundaryTimeObserverForTimes: file: usingBlock: .
L'exemple vient d'Apple:
// Assume a property: @property (retain) id playerObserver;
Float64 durationSeconds = CMTimeGetSeconds([<#An asset#> duration]);
CMTime firstThird = CMTimeMakeWithSeconds(durationSeconds/3.0, 1);
CMTime secondThird = CMTimeMakeWithSeconds(durationSeconds*2.0/3.0, 1);
NSArray *times = [NSArray arrayWithObjects:[NSValue valueWithCMTime:firstThird], [NSValue valueWithCMTime:secondThird], nil];
self.playerObserver = [<#A player#> addBoundaryTimeObserverForTimes:times queue:NULL usingBlock:^{
// Passing NULL for the queue specifies the main queue.
NSString *timeDescription = (NSString *)CMTimeCopyDescription(NULL, [self.player currentTime]);
NSLog(@"Passed a boundary at %@", timeDescription);
[timeDescription release];
}];
-replaceCurrentItemWithPlayerItem:
, et que vous ne le gérez pas correctement. Une manière plus fiable pour moi est de suivreAVPlayer
le statut de KVO en utilisant KVO. Voir ma réponse ci-dessous pour plus de détails: stackoverflow.com/a/34321993/3160561AVPlayerItemFailedToPlayToEndTimeNotification
Vous pouvez dire qu'il joue en utilisant:
Extension Swift 3:
la source
- [AVPlayer setRate:-1.0]
), car il-1.0
est inférieur à 0.Dans iOS10, il existe une propriété intégrée pour cela maintenant: timeControlStatus
Par exemple, cette fonction lit ou met en pause le avPlayer en fonction de son état et met à jour le bouton lecture / pause de manière appropriée.
Quant à votre deuxième question, pour savoir si l'avPlayer a atteint la fin, la chose la plus simple à faire serait de mettre en place une notification.
Lorsqu'il arrive à la fin, par exemple, vous pouvez le faire revenir au début de la vidéo et réinitialiser le bouton Pause sur Lecture.
Ces exemples sont utiles si vous créez vos propres contrôles, mais si vous utilisez un AVPlayerViewController, les contrôles sont intégrés.
la source
rate
n'est PAS le moyen de vérifier si une vidéo est en cours de lecture (elle pourrait se bloquer). De la documentation derate
:Mots clés «désir de jouer» - un taux de
1.0
ne signifie pas que la vidéo est en cours de lecture.La solution depuis iOS 10.0 est d'utiliser
AVPlayerTimeControlStatus
ce qui peut être observé sur laAVPlayer
timeControlStatus
propriété.La solution antérieure à iOS 10.0 (9.0, 8.0, etc.) consiste à lancer votre propre solution. Un taux de
0.0
signifie que la vidéo est mise en pause. Lorsquerate != 0.0
cela signifie que la vidéo est en cours de lecture ou est bloquée.Vous pouvez découvrir la différence en observant le temps du joueur via:
func addPeriodicTimeObserver(forInterval interval: CMTime, queue: DispatchQueue?, using block: @escaping (CMTime) -> Void) -> Any
Le bloc renvoie l'heure actuelle du joueur
CMTime
, donc une comparaison delastTime
(l'heure qui a été reçue pour la dernière fois du bloc) etcurrentTime
(l'heure à laquelle le bloc vient d'être signalé) dira si le joueur joue ou est bloqué. Par exemple, silastTime == currentTime
etrate != 0.0
, alors le joueur a calé.Comme indiqué par d'autres, déterminer si la lecture est terminée est indiqué par
AVPlayerItemDidPlayToEndTimeNotification
.la source
Une alternative plus fiable
NSNotification
consiste à vous ajouter en tant qu'observateur à larate
propriété du joueur .Vérifiez ensuite si la nouvelle valeur du taux observé est zéro, ce qui signifie que la lecture s'est arrêtée pour une raison quelconque, comme atteindre la fin ou bloquer en raison d'un tampon vide.
Par
rate == 0.0
exemple, pour savoir exactement ce qui a provoqué l'arrêt de la lecture, vous pouvez effectuer les vérifications suivantes:Et n'oubliez pas de faire arrêter votre lecteur lorsqu'il atteint la fin:
self.player.actionAtItemEnd = AVPlayerActionAtItemEndPause;
la source
AVPlayerItemFailedToPlayToEndTimeNotification
. Si cette erreur se produit, n'atteindra jamais l'heure de fin. Ou en lisant la réponse de maz, ajoutez à votre code une vérificationplayer.error != nil
, auquel cas la lecture s'est "terminée" en raison d'une erreur.AVPlayerItemDidPlayToEndTimeNotification
?Pour Swift :
AVPlayer :
Mise à jour : la
player.rate > 0
condition a été modifiéeplayer.rate != 0
car si la vidéo est lue à l'envers, elle peut être négative grâce à Julian pour l'avoir signalé.Remarque : Cela pourrait ressembler à la réponse ci-dessus (Maz), mais dans Swift '! Player.error' me donnait une erreur de compilation, vous devez donc vérifier l'erreur en utilisant 'player.error == nil' dans Swift. (Parce que la propriété d'erreur n'est pas de type 'Bool')
AVAudioPlayer:
AVQueuePlayer:
la source
player.rate = -1.0
), car -1,0 est inférieur à 0.Extension Swift basée sur la réponse de Maz
la source
La version Swift de la réponse de maxkonovalov est la suivante:
et
Merci maxkonovalov!
la source
nil
! Mais j'ai besoin de savoir quand la vue commence (pas se termine). Un moyen de faire ça?Actuellement, avec swift 5, le moyen le plus simple de vérifier si le lecteur est en cours de lecture ou en pause est de vérifier la variable .timeControlStatus .
la source
la source
la source