VideoView.swift 2.7 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091
  1. //
  2. // VideoView.swift
  3. // LoopKitUI
  4. //
  5. // Created by Rick Pasetto on 4/13/21.
  6. // Copyright © 2021 Tidepool Project. All rights reserved.
  7. //
  8. import SwiftUI
  9. import AVKit
  10. /// Opens a Swift `VideoPlayer` on the given URL in a new page
  11. public struct VideoView: View {
  12. @Environment(\.dismissAction) var dismiss
  13. let url: URL?
  14. let autoPlay: Bool
  15. private class PlayerHolder {
  16. private let prevCategory: AVAudioSession.Category?
  17. private var player: AVPlayer?
  18. init(overrideMuteSwitch: Bool) {
  19. if overrideMuteSwitch {
  20. prevCategory = AVAudioSession.sharedInstance().category
  21. } else {
  22. prevCategory = nil
  23. }
  24. }
  25. func destroy() {
  26. if let prevCategory = prevCategory {
  27. try? AVAudioSession.sharedInstance().setCategory(prevCategory)
  28. }
  29. }
  30. func player(for url: URL, autoPlay: Bool) -> AVPlayer {
  31. if let player = player {
  32. return player
  33. } else {
  34. let player = AVPlayer(url: url)
  35. if autoPlay, player.timeControlStatus == .paused {
  36. player.play()
  37. } else if !autoPlay, player.timeControlStatus == .playing {
  38. player.pause()
  39. }
  40. if prevCategory != nil {
  41. // Overrides mute switch (Silent mode) on the phone
  42. try? AVAudioSession.sharedInstance().setCategory(AVAudioSession.Category.playback)
  43. }
  44. self.player = player
  45. return player
  46. }
  47. }
  48. }
  49. private let playerHolder: PlayerHolder
  50. public init(url: URL?, autoPlay: Bool, overrideMuteSwitch: Bool = false) {
  51. self.url = url
  52. self.autoPlay = autoPlay
  53. self.playerHolder = PlayerHolder(overrideMuteSwitch: overrideMuteSwitch)
  54. }
  55. public var body: some View {
  56. HStack {
  57. Spacer()
  58. Button(LocalizedString("Done", comment: "Video player done button label"), action: dismiss)
  59. }
  60. .padding()
  61. if let url = url {
  62. VideoPlayer(player: playerHolder.player(for: url, autoPlay: autoPlay))
  63. .onDisappear {
  64. playerHolder.destroy()
  65. }
  66. } else {
  67. Spacer()
  68. Image(systemName: "questionmark.video")
  69. .resizable()
  70. .scaledToFit()
  71. .frame(width: 100, height: 100, alignment: .center)
  72. Spacer()
  73. }
  74. }
  75. }
  76. struct VideoView_Previews: PreviewProvider {
  77. static var previews: some View {
  78. VideoView(url: nil, autoPlay: true, overrideMuteSwitch: true)
  79. }
  80. }