SwiftUI AVPlayer - 如何暂停和恢复播放?
SwiftUI AVPlayer - How to pause and resume playing?
所以我制作了一个名为“VideoElement”的视图,它会在加载父视图时在后台播放视频。它运作良好。但是,我不知道如何实施 pause/resume 系统。我想更改一个变量(var“暂停”),它会在 true 时暂停视频并在 false 时恢复播放。它有点管用。具体来说,当“暂停”为真时,视频暂停。但是,当它变为 false 时,视频不会继续播放。
也许它可能与“updateUIViewController”有关?另外,我不知道为什么“暂停”必须是绑定变量而不是状态变量(@State 不起作用)。任何帮助将不胜感激。谢谢!
import SwiftUI
import AVKit
struct VideoElement: View {
var fileName: String
@Binding var paused: Bool //this controls playback
var body: some View {
let player = AVPlayer(url: URL(fileURLWithPath: Bundle.main.path(forAuxiliaryExecutable: fileName)!))
AVPlayerControllerRepresented(player: player)
.onAppear {
player.play()
}
.onChange(of: paused, perform: { paused in
if paused {
player.pause()
}
else {
player.play() //should play the video, does not
print("resume") //this runs, so above should've run also
}
})
}
}
}
struct AVPlayerControllerRepresented : UIViewControllerRepresentable {
var player : AVPlayer
func makeUIViewController(context: Context) -> AVPlayerViewController {
let controller = AVPlayerViewController()
controller.player = player
controller.showsPlaybackControls = false
return controller
}
func updateUIViewController(_ uiViewController: AVPlayerViewController, context: Context) {
}
}
我不建议在 body
中创建 AVPlayer
-- 这将保证任何时候重新呈现视图时,都会重新创建播放器。相反,将其存储在可以重新渲染的地方。为此,我选择了 ObservableObject
。
class PlayerManager : ObservableObject {
let player = AVPlayer(url: URL(string: "https://media.w3.org/2010/05/sintel/trailer.mp4")!)
@Published private var playing = false
func play() {
player.play()
playing = true
}
func playPause() {
if playing {
player.pause()
} else {
player.play()
}
playing.toggle()
}
}
struct ContentView: View {
@StateObject var playerManager = PlayerManager()
var body: some View {
VStack {
AVPlayerControllerRepresented(player: playerManager.player)
.onAppear {
playerManager.play()
}
Button("Play/Pause") {
playerManager.playPause()
}
}
}
}
struct AVPlayerControllerRepresented : UIViewControllerRepresentable {
var player : AVPlayer
func makeUIViewController(context: Context) -> AVPlayerViewController {
let controller = AVPlayerViewController()
controller.player = player
controller.showsPlaybackControls = false
return controller
}
func updateUIViewController(_ uiViewController: AVPlayerViewController, context: Context) {
}
}
所以我制作了一个名为“VideoElement”的视图,它会在加载父视图时在后台播放视频。它运作良好。但是,我不知道如何实施 pause/resume 系统。我想更改一个变量(var“暂停”),它会在 true 时暂停视频并在 false 时恢复播放。它有点管用。具体来说,当“暂停”为真时,视频暂停。但是,当它变为 false 时,视频不会继续播放。
也许它可能与“updateUIViewController”有关?另外,我不知道为什么“暂停”必须是绑定变量而不是状态变量(@State 不起作用)。任何帮助将不胜感激。谢谢!
import SwiftUI
import AVKit
struct VideoElement: View {
var fileName: String
@Binding var paused: Bool //this controls playback
var body: some View {
let player = AVPlayer(url: URL(fileURLWithPath: Bundle.main.path(forAuxiliaryExecutable: fileName)!))
AVPlayerControllerRepresented(player: player)
.onAppear {
player.play()
}
.onChange(of: paused, perform: { paused in
if paused {
player.pause()
}
else {
player.play() //should play the video, does not
print("resume") //this runs, so above should've run also
}
})
}
}
}
struct AVPlayerControllerRepresented : UIViewControllerRepresentable {
var player : AVPlayer
func makeUIViewController(context: Context) -> AVPlayerViewController {
let controller = AVPlayerViewController()
controller.player = player
controller.showsPlaybackControls = false
return controller
}
func updateUIViewController(_ uiViewController: AVPlayerViewController, context: Context) {
}
}
我不建议在 body
中创建 AVPlayer
-- 这将保证任何时候重新呈现视图时,都会重新创建播放器。相反,将其存储在可以重新渲染的地方。为此,我选择了 ObservableObject
。
class PlayerManager : ObservableObject {
let player = AVPlayer(url: URL(string: "https://media.w3.org/2010/05/sintel/trailer.mp4")!)
@Published private var playing = false
func play() {
player.play()
playing = true
}
func playPause() {
if playing {
player.pause()
} else {
player.play()
}
playing.toggle()
}
}
struct ContentView: View {
@StateObject var playerManager = PlayerManager()
var body: some View {
VStack {
AVPlayerControllerRepresented(player: playerManager.player)
.onAppear {
playerManager.play()
}
Button("Play/Pause") {
playerManager.playPause()
}
}
}
}
struct AVPlayerControllerRepresented : UIViewControllerRepresentable {
var player : AVPlayer
func makeUIViewController(context: Context) -> AVPlayerViewController {
let controller = AVPlayerViewController()
controller.player = player
controller.showsPlaybackControls = false
return controller
}
func updateUIViewController(_ uiViewController: AVPlayerViewController, context: Context) {
}
}