UICollectionViewCell 中的 AVPlayer 播放声音但不显示视频
AVPlayer in UICollectionViewCell plays sound but doesn't show video
我有一个 UICollectionViewController,它带有水平滚动的全屏单元格。每个单元格中都有另一个垂直滚动的 collectionView。 collectionView 的 header 单元有一个从 URL 中拉取视频的 AVPlayer。目前只播放音频,不播放视频。
下面的 AVPlayer 设置和观察器与我在 UICollectionViewCell 之外的应用程序中多次使用的相同代码没有问题。播放器帧大小已检查,音频按预期播放和循环,因此观察者似乎正确触发。
相关代码:
var post: Post! {
didSet {
videoURL = URL(string: post.videoURL)
setupVideoObservers()
}
}
var videoURL: URL! {
didSet {
videoPlayer = AVPlayer(url: videoURL!)
}
}
@objc dynamic var videoPlayer: AVPlayer!
var videoPlayerLayer: AVPlayerLayer!
let videoContainerView = UIView()
override init(frame: CGRect) {
super.init(frame: frame)
setupCell()
}
func setupCell() {
addSubview(videoContainerView)
videoContainerView.anchor(top: topAnchor,
right: rightAnchor,
bottom: bottomAnchor,
left: leftAnchor)
videoPlayerLayer = AVPlayerLayer(player: videoPlayer)
videoPlayerLayer.frame = frame
videoPlayerLayer.videoGravity = .resizeAspectFill
videoContainerView.layer.addSublayer(videoPlayerLayer)
}
func setupVideoObservers() {
addObserver(self, forKeyPath: "videoPlayer.currentItem.status", options: .new, context: nil)
NotificationCenter.default.addObserver(self, selector: #selector(playerReachedEndOfVideo(notification:)), name: .AVPlayerItemDidPlayToEndTime, object: videoPlayer.currentItem)
NotificationCenter.default.addObserver(self, selector: #selector(appWillEnterForegroundNotification), name: .UIApplicationWillEnterForeground, object: videoPlayer.currentItem)
}
override func observeValue(forKeyPath keyPath: String?, of object: Any?, change: [NSKeyValueChangeKey: Any]?, context: UnsafeMutableRawPointer?) {
if keyPath == "videoPlayer.currentItem.status" {
videoPlayer.play()
}
}
@objc func playerReachedEndOfVideo(notification: NSNotification) {
let seekTime = CMTime(seconds: 0, preferredTimescale: 1000)
videoPlayer.seek(to: seekTime, toleranceBefore: kCMTimeZero, toleranceAfter: kCMTimeZero)
videoPlayer.play()
}
@objc func appWillEnterForegroundNotification() {
videoPlayer.play()
}
我遇到的所有其他针对 AVPlayer 音频无视频问题的 SO 解决方案均未应用。如果有人有任何见解,将不胜感激。
提前致谢。
我有一个非常相似的问题。填充内容后,尝试将 AVPlayerLayer
的框架设置为所需大小的 CGRect()
。此外,您可能希望为 didSet
.
进行 Dispatch.Queue
异步调用
我有一个 UICollectionViewController,它带有水平滚动的全屏单元格。每个单元格中都有另一个垂直滚动的 collectionView。 collectionView 的 header 单元有一个从 URL 中拉取视频的 AVPlayer。目前只播放音频,不播放视频。
下面的 AVPlayer 设置和观察器与我在 UICollectionViewCell 之外的应用程序中多次使用的相同代码没有问题。播放器帧大小已检查,音频按预期播放和循环,因此观察者似乎正确触发。
相关代码:
var post: Post! {
didSet {
videoURL = URL(string: post.videoURL)
setupVideoObservers()
}
}
var videoURL: URL! {
didSet {
videoPlayer = AVPlayer(url: videoURL!)
}
}
@objc dynamic var videoPlayer: AVPlayer!
var videoPlayerLayer: AVPlayerLayer!
let videoContainerView = UIView()
override init(frame: CGRect) {
super.init(frame: frame)
setupCell()
}
func setupCell() {
addSubview(videoContainerView)
videoContainerView.anchor(top: topAnchor,
right: rightAnchor,
bottom: bottomAnchor,
left: leftAnchor)
videoPlayerLayer = AVPlayerLayer(player: videoPlayer)
videoPlayerLayer.frame = frame
videoPlayerLayer.videoGravity = .resizeAspectFill
videoContainerView.layer.addSublayer(videoPlayerLayer)
}
func setupVideoObservers() {
addObserver(self, forKeyPath: "videoPlayer.currentItem.status", options: .new, context: nil)
NotificationCenter.default.addObserver(self, selector: #selector(playerReachedEndOfVideo(notification:)), name: .AVPlayerItemDidPlayToEndTime, object: videoPlayer.currentItem)
NotificationCenter.default.addObserver(self, selector: #selector(appWillEnterForegroundNotification), name: .UIApplicationWillEnterForeground, object: videoPlayer.currentItem)
}
override func observeValue(forKeyPath keyPath: String?, of object: Any?, change: [NSKeyValueChangeKey: Any]?, context: UnsafeMutableRawPointer?) {
if keyPath == "videoPlayer.currentItem.status" {
videoPlayer.play()
}
}
@objc func playerReachedEndOfVideo(notification: NSNotification) {
let seekTime = CMTime(seconds: 0, preferredTimescale: 1000)
videoPlayer.seek(to: seekTime, toleranceBefore: kCMTimeZero, toleranceAfter: kCMTimeZero)
videoPlayer.play()
}
@objc func appWillEnterForegroundNotification() {
videoPlayer.play()
}
我遇到的所有其他针对 AVPlayer 音频无视频问题的 SO 解决方案均未应用。如果有人有任何见解,将不胜感激。
提前致谢。
我有一个非常相似的问题。填充内容后,尝试将 AVPlayerLayer
的框架设置为所需大小的 CGRect()
。此外,您可能希望为 didSet
.
Dispatch.Queue
异步调用