Show activity indicator and error while loading from url AVPlayer swiftui

Viewed 250

I was trying to load short videos from a URL and I found the best way is to use AVPlayer, I found the code below but it didn't show the activity indicator also if the user doesn't have an internet it won't play the video. Thanks in advance.

import SwiftUI
import AVKit

struct ContentView: View {
    
    @State var player = AVPlayer(url: URL(string: "http://commondatastorage.googleapis.com/gtv-videos-bucket/sample/ElephantsDream.mp4")!)
    @State var isplaying = false
    @State var showcontrols = false
    @State var value : Float = 0
    
    var body: some View {
        
        VStack{
            
            ZStack{
                
                VideoPlayer(player: $player)
                
                if self.showcontrols{
                    
                    Controls(player: self.$player, isplaying: self.$isplaying, pannel: self.$showcontrols,value: self.$value)
                }
                
            }
            .frame(height: UIScreen.main.bounds.height / 3.5)
            .onTapGesture {
                
                self.showcontrols = true
            }
            
            GeometryReader{_ in
                
                VStack{
                    
                    Text("Custom Video Player").foregroundColor(.white)
                }
            }
        }
        .background(Color.black.edgesIgnoringSafeArea(.all))
        .onAppear {
            
            self.player.play()
            self.isplaying = true
        }
    }
}

This is the main screen which is ContentView

struct Controls : View {
    
    @Binding var player : AVPlayer
    @Binding var isplaying : Bool
    @Binding var pannel : Bool
    @Binding var value : Float
    
    var body : some View{
        
        VStack{
            Spacer()
            HStack{
                Button(action: {
                    if self.isplaying{
                        
                        self.player.pause()
                        self.isplaying = false
                    }
                    else{
                        self.player.play()
                        self.isplaying = true
                    }
                    if self.player.currentItem?.duration.seconds == self.player.currentTime().seconds{
                        print("did it")
                        self.player.seek(to: CMTime.zero)
                        self.player.play()
                        self.isplaying = true
                    }
                }) {
                    
                    Image(systemName: self.isplaying ? "pause.fill" : "play.fill")
                        .font(.title)
                        .foregroundColor(.white)
                        .padding(20)
                }
                
            }
            
        }.padding()
        .onTapGesture {
            self.pannel = false
        }
    }
    
    func getSliderValue()->Float{
        
        return Float(self.player.currentTime().seconds / (self.player.currentItem?.duration.seconds)!)
    }
    
    func getSeconds()->Double{
        
        return Double(Double(self.value) * (self.player.currentItem?.duration.seconds)!)
    }
}

The button for control the video.

class Host : UIHostingController<ContentView>{
    
    override var preferredStatusBarStyle: UIStatusBarStyle{
        
        return .lightContent
    }
}
struct VideoPlayer : UIViewControllerRepresentable {
    
    @Binding var player : AVPlayer
    
    func makeUIViewController(context: UIViewControllerRepresentableContext<VideoPlayer>) -> AVPlayerViewController {
        
        let controller = AVPlayerViewController()
        controller.player = player
        controller.showsPlaybackControls = false
        controller.videoGravity = .resize
        return controller
    }
    
    func updateUIViewController(_ uiViewController: AVPlayerViewController, context: UIViewControllerRepresentableContext<VideoPlayer>) {
        
        
    }
}

0 Answers
Related