// // MoreVM.swift // WOKA // // Created by MacBook Pro on 10/06/24. // import UIKit import AVFoundation enum PlayerStatus{ case play case loading case pause case resume case stopped } var currentTimePlayer = Int() var totalTime = Int() class MoreVM{ weak var vc : MoreVC! var blogData = [BlogDM.Blog]() var songData = [SongBlogDM.PaintDatum]() var player : AVPlayer? var playerObserver: NSKeyValueObservation? var playerStatus = PlayerStatus.loading var currentIndexPlayingSong : Int? func initView(){ getBLogs() setupAudioSession() getSong() setupCell() vc.songTableView.showsVerticalScrollIndicator = false vc.songTableView.showsHorizontalScrollIndicator = false vc.homeBtn.addTapGesture { PersistentStorage.shared.addOthersCount() self.vc.dismiss(animated: true) } } func setupAudioSession() { let session = AVAudioSession.sharedInstance() do { try session.setCategory(.playback, mode: .default) try session.setActive(true) } catch { print("Failed to set up audio session") } } func observePlayer() { playerObserver = self.player?.observe(\.timeControlStatus, options: [.new, .old], changeHandler: { [weak self] player, change in guard let self = self else { return } switch player.timeControlStatus { case .playing: print("Player is playing OOO") self.playerStatus = .play vc.songTableView.reloadRows(at: [IndexPath(row: currentIndexPlayingSong ?? 0, section: 0)], with: .none) case .paused: print("Player is paused OOO") // self.playerStatus = .pause if self.player?.currentTime() == self.player?.currentItem?.duration { print("Player finished playing") self.playerStatus = .stopped self.vc.songTableView.reloadRows(at: [IndexPath(row: currentIndexPlayingSong!, section: 0)], with: .none) currentIndexPlayingSong = nil } else { print("Player is paused") self.playerStatus = .pause } case .waitingToPlayAtSpecifiedRate: print("Player is waiting to play at specified rate OOO") self.playerStatus = .loading @unknown default: print("Unknown player status OOO") } }) } func setupCell(){ vc.blogsCollectionView.register(UINib(nibName: K.CellIdentifier.Home.blogsCell, bundle: nil), forCellWithReuseIdentifier: K.CellIdentifier.Home.blogsCell) vc.blogsCollectionView.delegate = vc.self vc.blogsCollectionView.dataSource = vc.self vc.songTableView.register(UINib(nibName: K.CellIdentifier.Home.songListCell, bundle: nil), forCellReuseIdentifier: K.CellIdentifier.Home.songListCell) vc.songTableView.delegate = vc.self vc.songTableView.dataSource = vc.self } // MARK: - Get BLogs Data func getBLogs(){ Utilities.startProgressHUD() NetworkManager.shareInstance.apiRequest(url: APIEndPoints.Home.blogs, method: .get) { [weak self](result : Result, NetworkManager.APIError>) in guard let self else{return} switch result{ case .success(let data): switch data.success{ case 0: /* Error */ Utilities.dismissProgressHUD() vc.toast(msg: data.message ?? "Unrecognised error" , time: 2) case 1: Utilities.dismissProgressHUD() guard let data = data.data?.blogs else{return} blogData = data vc.blogsCollectionView.reloadData() default: break } case .failure(let error): Utilities.dismissProgressHUD() vc.toast(msg: error.localizedDescription , time: 2) } } } func getSong(){ NetworkManager.shareInstance.apiRequest(url: APIEndPoints.Home.song_listing, method: .post) { [weak self](result : Result, NetworkManager.APIError>) in guard let self else{return} switch result{ case .success(let data): switch data.success{ case 0: /* Error */ Utilities.dismissProgressHUD() vc.toast(msg: data.message ?? "Unrecognised error" , time: 2) case 1: Utilities.dismissProgressHUD() guard let data = data.data?.paintData else{return} songData = data vc.songTableView.reloadData() break default: break } case .failure(let error): Utilities.dismissProgressHUD() vc.toast(msg: error.localizedDescription , time: 2) } } } } import UIKit extension UIView { private struct AssociatedKeys { static var loadingView = "loadingView" } private var loadingView: LoadingView? { get { return objc_getAssociatedObject(self, AssociatedKeys.loadingView) as? LoadingView } set { objc_setAssociatedObject(self, AssociatedKeys.loadingView, newValue, .OBJC_ASSOCIATION_RETAIN_NONATOMIC) } } func showLoading() { if loadingView == nil { let newLoadingView = LoadingView(frame: self.bounds) newLoadingView.translatesAutoresizingMaskIntoConstraints = false self.addSubview(newLoadingView) NSLayoutConstraint.activate([ newLoadingView.leadingAnchor.constraint(equalTo: self.leadingAnchor), newLoadingView.trailingAnchor.constraint(equalTo: self.trailingAnchor), newLoadingView.topAnchor.constraint(equalTo: self.topAnchor), newLoadingView.bottomAnchor.constraint(equalTo: self.bottomAnchor) ]) loadingView = newLoadingView } loadingView?.startLoading() } func hideLoading() { loadingView?.stopLoading() } } class LoadingView: UIView { private var activityIndicator: UIActivityIndicatorView! override init(frame: CGRect) { super.init(frame: frame) setupView() } required init?(coder: NSCoder) { super.init(coder: coder) setupView() } private func setupView() { self.backgroundColor = .clear activityIndicator = UIActivityIndicatorView(style: .medium) activityIndicator.translatesAutoresizingMaskIntoConstraints = false activityIndicator.color = .white self.addSubview(activityIndicator) NSLayoutConstraint.activate([ activityIndicator.centerXAnchor.constraint(equalTo: self.centerXAnchor), activityIndicator.centerYAnchor.constraint(equalTo: self.centerYAnchor), activityIndicator.heightAnchor.constraint(equalToConstant: self.frame.height - 10), activityIndicator.widthAnchor.constraint(equalToConstant: self.frame.width - 10) ]) } func startLoading() { activityIndicator.startAnimating() self.isHidden = false } func stopLoading() { activityIndicator.stopAnimating() self.isHidden = true } }