What's new in AVKit
Audio & Video 进阶 12m

AVKit 的新功能

What's new in AVKit

2021年6月10日

在 Apple 官方观看视频

一句话判断

如果你在做视频播放 App,iOS 15 给 AVPlayerViewController 加的那堆播放器定制能力,让你终于不用重写整个播放器 UI 了。

这场 Session 讲了什么

AVKit 是苹果封装的视频播放 UI 框架,AVPlayerViewController 是它的核心组件。在 iOS 15 之前,如果你想自定义播放器的外观(比如改变控制按钮、添加自定义操作),几乎只能从头写一个——AVPlayerViewController 的定制能力极其有限。iOS 15 填补了这个空白。

Session 介绍的主要更新包括:自定义播放控制按钮(customActions)、控制播放器界面的显示/隐藏时机、以及新的播放速度控制 API。AVPlayerViewController 新增了 customActions 属性,你可以在播放控制栏中插入自定义按钮(比如「画中画」「投屏」「下一集」),这些按钮会自动适配系统的播放器布局。播放速度控制也不再需要自己写 UI——系统提供了 0.5x 到 2x 的预设速度选项。

另外,Session 讲了 tvOS 上 AVKit 的更新:新的 AVInterstitialTimeRange API 可以标记视频中的插播广告时间段,播放器会在这些时间段显示特定的 UI。还有 AVPlayerViewController 对 HDR 内容的改进——播放器会自动检测显示能力并调整色调映射。

值得深挖的点

AVPlayerViewController.CustomAction 的设计模式。 自定义按钮通过 AVPlayerViewController.CustomAction 结构体定义,你需要提供图标(UIImage 或 SF Symbol 名称)和点击回调。关键设计决策是:你的自定义按钮应该出现在Leading 还是 Trailing 位置——Leading 放主要操作(如「下一集」),Trailing 放辅助操作(如「画质设置」)。系统会根据设备类型(iPhone vs iPad vs Apple TV)自动调整按钮的大小和间距,你不需要为不同设备做适配。但要注意,自定义按钮数量不宜过多——控制栏空间有限,超过 3-4 个自定义按钮会让界面拥挤。

AVPlayerViewController 的外部分辨率控制。 iOS 15 新增了 appliesMediaSelectionCriteriaAutomatically 的细粒度控制,以及 currentItem.videoComposition 对 HDR 内容的支持。对于流媒体 App,你可以通过 preferredForwardBufferDuration 控制预缓冲量,通过 preferredPeakBitRate 限制最高码率来节省带宽。这些属性以前是 AVPlayerItem 级别的,现在 AVPlayerViewController 提供了更方便的设置入口。

代码片段

import AVKit

// 创建带有自定义控制按钮的播放器
let playerVC = AVPlayerViewController()
playerVC.player = AVPlayer(url: videoURL)

// 添加自定义按钮到播放控制栏
let nextEpisodeAction = AVPlayerViewController.CustomAction(
    image: UIImage(systemName: "forward.end.fill")!,
    accessibilityLabel: "下一集"
) { [weak self] in
    self?.playNextEpisode()
}

let subtitleAction = AVPlayerViewController.CustomAction(
    image: UIImage(systemName: "captions.bubble")!,
    accessibilityLabel: "字幕设置"
) { [weak self] in
    self?.showSubtitleOptions()
}

playerVC.customActions = [nextEpisodeAction, subtitleAction]
// 控制播放速度
func setupPlaybackSpeedControl() {
    // 设置默认播放速度
    playerVC.player?.rate = 1.0

    // AVPlayerViewController 在 iOS 15 中内置了速度选择 UI
    // 用户可以在控制栏中直接选择 0.5x, 1.0x, 1.5x, 2.0x
    // 通过 requiresFullSubtitlesDisplay 控制字幕显示策略
}
// 标记广告插播时间段(tvOS)
func setupInterstitialAds() {
    guard let currentItem = playerVC.player?.currentItem else { return }

    // 标记 30 秒到 60 秒为广告时段
    let adRange = AVInterstitialTimeRange(
        timeRange: CMTimeRange(
            start: CMTime(seconds: 30, preferredTimescale: 600),
            duration: CMTime(seconds: 30, preferredTimescale: 600)
        )
    )

    // 播放器会在广告时段显示特殊 UI
    currentItem.interstitialTimeRanges = [adRange]
}

最佳实践

  • 自定义按钮的图标使用 SF Symbols 以确保视觉一致性,如果 SF Symbols 里没有合适的图标,用 24x24pt 的模板图片
  • 在 iPhone 上,播放控制栏空间非常有限,自定义按钮不要超过 2 个;在 iPad 和 Apple TV 上可以放 3-4 个
  • 测试时用不同长宽比的视频内容(16:9、4:3、21:9),确认播放器布局在不同视频尺寸下不会出问题
  • 如果你的 App 支持 AirPlay,确保自定义按钮在 AirPlay 播放时仍然可用

还有什么值得关注

  • iOS 15 的 AVPlayerViewController 自动支持 Spatial Audio,如果你播放的内容包含空间音频轨道
  • tvOS 上播放器对 HDR 的处理更加智能,会根据电视的能力自动选择合适的色调映射模式
  • AVPlayerItempreferredPeakBitRate 可以用来实现「省流模式」,在蜂窝网络下自动降低码率
WWDC 2021