Swift iOS -Как управлять Notification.Name.AVPlayerItemDidPlayToEndTime для разных видео в нескольких классах - PullRequest
0 голосов
/ 24 июня 2018

Мое приложение воспроизводит видео в течение нескольких vcs, используя AVFoundation.Например, FirstController воспроизводит видео, затем пользователь может нажать на SecondController, который также воспроизводит видео, а затем он может нажать на ThirdController, который также воспроизводит видео ... То же самое применимо, если их вкладки переключения.В TabOne, TabTwo и TabThree есть видеоэкран.

Вместо того, чтобы устанавливать весь код playLayer, связанный с AVFoundation, в каждом классе, я создал один класс, содержащий AVPlayerViewController(), и добавил этот класс в каждый vc, используяaddChildViewController().

Проблема в том, что у меня есть один класс, который управляет AVFoundation. Notification.Name.AVPlayerItemDidPlayToEndTime, который получает уведомление, когда проигрыватель заканчивает играть, не может отличить одно видео на одном и другом видео в другом.Например, после окончания воспроизведения видео я показываю кнопку воспроизведения.Если видео на первой вкладке воспроизводится, когда я переключаюсь на TabTwo, я приостанавливаю это видео, после того, как видео на TabTwo заканчивается и появляется кнопка replayButton, если я переключаюсь обратно на TabOne, кнопка replayButton также появится на экране TabOne (он долженпокажите кнопку паузы).

Проблема в том, что у меня есть разные экземпляры AVFoundationManager, но все экземпляры обращаются к одному showReplayButton() function, который срабатывает при срабатывании уведомления.

Как я могу обойти это?

Я знаю, что могу проверить parent AVFoundationManager, чтобы выяснить, какой родитель управляет им и использовать это внутри функции showReplayButton(), но я не знаю, какойпроверьте, чтобы он работал на нем.

AVFoundationManager:

class AVFoundationManager: UIViewController {

    ....

    override func viewDidLoad() {
        super.viewDidLoad()
        configureAVPlayerController()
    }

    func configureAVPlayerController() {

        let avPlayerVC = AVPlayerViewController()
        avPlayerVC.player = player
        avPlayerVC.view.frame = view.bounds
        avPlayerVC.showsPlaybackControls = false
        avPlayerVC.videoGravity = AVLayerVideoGravity.resizeAspectFill.rawValue
        addChildViewController(avPlayerVC)
        view.addSubview(avPlayerVC.view)
        avPlayerVC.didMove(toParentViewController: self)

        player?.replaceCurrentItem(with: playerItem!)
        player?.play()

        NotificationCenter.default.addObserver(self, selector: #selector(showReplayButton), name: NSNotification.Name.AVPlayerItemDidPlayToEndTime, object: nil)

        playerItem?.addObserver(self, forKeyPath: #keyPath(AVPlayerItem.status),
                            options: [.old, .new],
                            context: &itemContext)
    }

    @obj func showReplayButton(){

        // if self.parent ... run a bool on the parent and enclose these two in the paranthesis?
        pausePlayButton.isHidden = true
        replayButton.isHidden = false
    }
}

TabOneClass:

let avFoundationManager = AVFoundationManager()
addChildViewController(avFoundationManager)
avFoundationManager.didMove(toParentViewController: self)

TabTwoClass:

let avFoundationManager = AVFoundationManager()
addChildViewController(avFoundationManager)
avFoundationManager.didMove(toParentViewController: self)

FirstController (root) вTabThree:

let avFoundationManager = AVFoundationManager()
addChildViewController(avFoundationManager)
avFoundationManager.didMove(toParentViewController: self)

SecondController (дочерний) в TabThree:

let avFoundationManager = AVFoundationManager()
addChildViewController(avFoundationManager)
avFoundationManager.didMove(toParentViewController: self)

Ответы [ 2 ]

0 голосов
/ 28 июня 2018

Я получил ответ отсюда

Внутри уведомления вместо установки последнего аргумента object на nil установите его на player.currentItem:

как это:

NotificationCenter.default.addObserver(self, selector: #selector(showReplayButton),
                                     name: NSNotification.Name.AVPlayerItemDidPlayToEndTime,
                                     object: player?.currentItem)
0 голосов
/ 24 июня 2018

Я не говорю, что это лучший ответ, и если кто-то еще может предложить лучшее решение, пожалуйста, напишите :) Насколько я понимаю, игрок не может различить количество наблюдателей.

(примечание, в настоящее время на моем телефоне, поэтому извините за псевдокод)

class PlayerViewController {
// other code and functions
    func removeObservers() {
        NSNotificationCenter.defaultCenter().removeObserver(self)
    }
}

В viewWillDisappear вызовите функцию удаления наблюдателей

Просто не забудьтеПовторно инициализируйте своих наблюдателей, когда они вам понадобятся, или когда у вас появится вид, или когда вы инициализируете следующее видео.

...