2017-01-25 2 views
0

Я бил головой с раздражающим срывом в течение последних двух дней и надеялся, что кто-то может пролить свет.AVPlayer ускоренная перемотка вперед/назад с движением панорамирования

Базовая настройка: У меня есть AVPlayerLayer с игроком, пан жест распознаватель в представлении, и я хочу, чтобы пользователь мог красть их пальцами взад и вперед, и видео будет стремиться соответственно.

Улов: Я хотел бы, если пользователь снова поднимает палец и помещает его в любом месте на экране для перемотки вперед или назад, чтобы возобновить в точной тот же кадр, где она была прервана, и продолжать прогрессировать от там.

Я видел эти два вопроса: Pan Gesture with AVPlayer и Pan to seek AVPlayer

Я попытался предложение от Apple здесь: https://developer.apple.com/library/content/qa/qa1820/_index.html а, но проблема в том, что всякий раз, когда я начинаю новый жест панорамирования, игрок прыжки несколько кадров, а затем возобновляется.

Мой последний подход состоял в том, чтобы установить текущее время после завершения этапа завершения поиска, а затем я попытаюсь добавить к нему новое время поиска.

Вот мои настройки:

self.item = [AVPlayerItem playerItemWithURL:resource]; 
self.player = [AVPlayer playerWithPlayerItem:self.item]; 
self.playerLayer = [AVPlayerLayer playerLayerWithPlayer:self.player]; 

[self.view.layer addSublayer:self.playerLayer]; 
self.playerLayer.frame = self.view.bounds; 

UIPanGestureRecognizer *recognizer = [[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(swipe:)]; 

[self.view addGestureRecognizer:recognizer]; 

И мой жест обработки распознаватель:

- (void)swipe:(UIPanGestureRecognizer *)paramRecognizer 
{ 
    switch(paramRecognizer.state) { 
     // case UIGestureRecognizerStateBegan: 
     case UIGestureRecognizerStateChanged: 
     { 
      [self.player pause]; 

      CGPoint translation = [paramRecognizer translationInView:self.view]; 

      float horizontalTranslation = translation.x; 

      float durationInSeconds = CMTimeGetSeconds(self.player.currentItem.asset.duration); 

      //I'd like to be able to swipe across the whole view. 
      float translationLimit = self.view.bounds.size.width; 
      float minTranslation = 0; 
      float maxTranslation = translationLimit; 

      if (horizontalTranslation > maxTranslation) { 
       horizontalTranslation = maxTranslation; 
      } 

      if (horizontalTranslation < minTranslation) { 
       horizontalTranslation = minTranslation; 
      } 

     float timeToSeekTo = [self normalize:horizontalTranslation 
           andMinDelta:minTranslation 
           andMaxDelta:maxTranslation 
           andMinDuration:0 
           andMaxDuration:durationInSeconds]; 

      if(CMTIME_IS_VALID(self.currentTime)){ 
       float seconds = self.currentTime.value/self.currentTime.timescale; 

       [self.player seekToTime:CMTimeMakeWithSeconds(seconds+timeToSeekTo, self.player.currentTime.timescale) 
         toleranceBefore:kCMTimeZero 
         toleranceAfter:kCMTimeZero completionHandler:^(BOOL finished) 
       { 
        if(finished) 
        self.currentTime = self.player.currentItem.currentTime; 
       }]; 
      } 
      else 
      { 
       [self.player seekToTime:CMTimeMakeWithSeconds(timeToSeekTo, 
                   self.player.currentTime.timescale) toleranceBefore:kCMTimeZero 
         toleranceAfter:kCMTimeZero completionHandler:^(BOOL finished) { 
          if(finished) 
        self.currentTime = self.player.currentItem.currentTime; 
       }]; 
      } 

     } 
      break; 
    } 
} 

Метод нормализуют заключается в следующем:

- (float) normalize:(float)delta 
    andMinDelta:(float)minDelta 
    andMaxDelta:(float)maxDelta 
andMinDuration:(float)minDuration 
andMaxDuration:(float)maxDuration{ 

float result = ((delta - minDelta) * (maxDuration - minDuration)/(maxDelta - minDelta) + minDuration); 
return result; 

}

Любая помощь быть экстремальным приветствуется!

+0

слегка запутанная формулировка вы говорите, если вы начинаете paning на 3,00 секунде и сказать, пан 2 точек затем поднимите, он должен играть 5,00 или 3,00 снова? – SeanLintern88

+0

@ SeanLintern88It должен снова сыграть в 3.0, извините, очистил его –

+0

OK, чтобы уточнить, вы были бы в 3.0, будучи панорамированием и скрабом назад/вперед, а затем на .end вернемся к 3.0? Но во время скраб-видео плавно переходите назад/вперед на основе кастрюли? Если да, то в чем именно проблема? – SeanLintern88

ответ

0

На UIGestureRecognizerStateBeganCMTime экономии через от AVPlayer затем сделать ваше изменения дельты панорамирования, а затем на UIGestureRecognizerStateEnded просто стремится вернуться к первоначальному сэкономленному времени?

Только примечание для более плавных поисков не остановить воспроизведение видео, установите скорость в 0.

+0

Вы действительно правы, я заметил проблему после прочтения вашего комментария, если вы посмотрите на мой пример кода, я устанавливал начальное время поиска под UIGestureRecognizerStateChanged, а не UIGestureRecognizerStateBegan, поэтому почему я наблюдал начальный рывок, когда пользователь начал салфетки. –

+0

Также используйте скорость паузы, а не паузу, это делает поиск более жидким. – SeanLintern88

Смежные вопросы