//
//  PQStuckPointMaterialDetailController.swift
//  PQSpeed
//
//  Created by SanW on 2021/4/27.
//  Copyright © 2021 BytesFlow. All rights reserved.
//

import Kingfisher
import KingfisherWebP
import UIKit

class PQStuckPointMaterialDetailController: PQBaseViewController {
    var materialData: PQEditVisionTrackMaterialsModel?
    // 点击的回调
    var materialDetailClickHandle: ((_ isMaterialSelected: Bool?, _ materialData: PQEditVisionTrackMaterialsModel?) -> Void)?
    var isMaterialSelected: Bool?
    var margin: CGFloat = 35 // 左右间距
    // 最大的宽度
    var maxWidth: CGFloat = cScreenWidth
    // 最大的高度
    var maxHeight: CGFloat = cScreenHeigth - cDevice_iPhoneNavBarAndStatusBarHei - cDevice_iPhoneStatusBarHei
    // 预览区域宽度
    var preViewWidth: CGFloat = cScreenWidth
    // 预览区域高度
    var preViewHeight: CGFloat = cScreenHeigth - cDevice_iPhoneNavBarAndStatusBarHei - cDevice_iPhoneStatusBarHei
    lazy var preImageView: UIImageView = {
        let preImageView = UIImageView(frame: CGRect(x: (maxWidth - preViewWidth) / 2, y: cDevice_iPhoneNavBarAndStatusBarHei + (maxHeight - preViewHeight) / 2, width: preViewWidth, height: preViewHeight))
        preImageView.center.x = view.center.x
        preImageView.backgroundColor = PQBFConfig.shared.styleBackGroundColor
        preImageView.contentMode = .scaleAspectFit
        preImageView.isUserInteractionEnabled = true
        preImageView.clipsToBounds = true
        // preImageView.image = UIImage.init(named: "cut_place")
        return preImageView
    }()

    lazy var choseTitleBtn: UIButton = {
        let choseTitleBtn = UIButton(type: .custom)
        choseTitleBtn.frame = CGRect(x: cScreenWidth - cDefaultMargin * 6, y: 0, width: cDefaultMargin * 5, height: cDefaultMargin * 3)
        choseTitleBtn.setTitleColor(UIColor.white, for: .normal)
        choseTitleBtn.titleLabel?.font = UIFont.systemFont(ofSize: 17, weight: .medium)
        choseTitleBtn.setTitle("取消", for: .selected)
        choseTitleBtn.setTitle("选择", for: .normal)
        choseTitleBtn.tag = 2
        choseTitleBtn.addTarget(self, action: #selector(btnClick(sender:)), for: .touchUpInside)
        return choseTitleBtn
    }()

    lazy var choseBtn: UIButton = {
        let choseBtn = UIButton(type: .custom)
        choseBtn.frame = CGRect(x: choseTitleBtn.frame.minX - cDefaultMargin * 3, y: 0, width: cDefaultMargin * 3, height: cDefaultMargin * 3)
        choseBtn.setBackgroundImage(UIImage().BF_Image(named: "videomk_chose_nomal"), for: .normal)
        choseBtn.setTitleColor(UIColor.white, for: .normal)
        choseBtn.titleLabel?.font = UIFont.systemFont(ofSize: 12)
        choseBtn.tag = 1
        choseBtn.addCorner(corner: 15)
        choseBtn.addTarget(self, action: #selector(btnClick(sender:)), for: .touchUpInside)
        return choseBtn
    }()

    lazy var changeModeBtn: UIButton = {
        let changeModeBtn = UIButton(type: .custom)
        changeModeBtn.setImage(UIImage().BF_Image(named: "videomk_changeMode"), for: .normal)
        changeModeBtn.frame = CGRect(x: 15, y: preImageView.frame.height - cDefaultMargin * 4 - 15, width: cDefaultMargin * 4, height: cDefaultMargin * 4)
        changeModeBtn.tag = 3
        changeModeBtn.addTarget(self, action: #selector(btnClick(sender:)), for: .touchUpInside)
        return changeModeBtn
    }()

    lazy var gifRemindLab: UILabel = {
        let gifRemindLab = UILabel(frame: CGRect(x: (preImageView.frame.width - cDefaultMargin * 4) / 2, y: preImageView.frame.height - cDefaultMargin * 3 - 15, width: cDefaultMargin * 4, height: cDefaultMargin * 3))
        gifRemindLab.textAlignment = .center
        gifRemindLab.font = UIFont.systemFont(ofSize: 18)
        gifRemindLab.textColor = UIColor.white
        gifRemindLab.text = "GIF"
        return gifRemindLab
    }()

    lazy var playBtn: UIButton = {
        let playBtn = UIButton(type: .custom)
        playBtn.frame = CGRect(x: (preImageView.frame.width - cDefaultMargin * 5) / 2, y: (preImageView.frame.height - cDefaultMargin * 5) / 2, width: cDefaultMargin * 5, height: cDefaultMargin * 5)
        playBtn.setImage(UIImage().BF_Image(named: "icon_video_play"), for: .normal)
        playBtn.isUserInteractionEnabled = false
        playBtn.isHidden = true
        // playBtn.addTarget(self, action: #selector(btnClick(sender:)), for: .touchUpInside)
        return playBtn
    }()

    lazy var avPlayer: AVPlayer = {
        let avPlayer = AVPlayer()
        NotificationCenter.default.addObserver(forName: .AVPlayerItemDidPlayToEndTime, object: avPlayer.currentItem, queue: .main) { [weak self] notify in
            BFLog(message: "AVPlayerItemDidPlayToEndTime = \(notify)")
            avPlayer.seek(to: CMTime(value: CMTimeValue((self?.materialData?.model_in ?? 0) * playerTimescale), timescale: CMTimeScale(playerTimescale)))
            self?.playBtn.isHidden = false
        }
        NotificationCenter.default.addObserver(forName: .AVPlayerItemNewErrorLogEntry, object: avPlayer.currentItem, queue: .main) { notify in
            BFLog(message: "AVPlayerItemNewErrorLogEntry = \(notify)")
        }
        NotificationCenter.default.addObserver(forName: .AVPlayerItemFailedToPlayToEndTime, object: avPlayer.currentItem, queue: .main) { notify in
            BFLog(message: "AVPlayerItemFailedToPlayToEndTime = \(notify)")
        }
        NotificationCenter.default.addObserver(forName: .AVPlayerItemPlaybackStalled, object: avPlayer.currentItem, queue: .main) { notify in
            BFLog(message: "AVPlayerItemPlaybackStalled = \(notify)")
        }
        avPlayer.addPeriodicTimeObserver(forInterval: CMTime(value: 1, timescale: CMTimeScale(playerTimescale)), queue: .main) { [weak self] cmTime in
            // let progress = CMTimeGetSeconds(avPlayer.currentItem?.currentTime() ?? CMTime.zero) / CMTimeGetSeconds(avPlayer.currentItem?.duration ?? CMTime.zero)
            let delta = CMTimeGetSeconds(cmTime)
            let start = CGFloat(delta - (self?.materialData?.model_in ?? 0.0))
            var endTime: Float64 = self?.materialData?.out ?? 0
            if endTime <= 0 {
                endTime = self?.materialData?.duration ?? 0
            }
            let total = CGFloat(endTime - (self?.materialData?.model_in ?? 0.0))
            let progress = start / total
            if progress >= 1 {
                self?.playBtn.isHidden = false
            }
            BFLog(message: "progress = \(progress)")
        }
        return avPlayer
    }()

    lazy var playerLayer: AVPlayerLayer = {
        let playerLayer = AVPlayerLayer(player: avPlayer)
        playerLayer.frame = CGRect(origin: CGPoint.zero, size: preImageView.frame.size)
        return playerLayer
    }()

    override func viewDidLoad() {
        super.viewDidLoad()
        leftButton(image: "icon_detail_back", tintColor: PQBFConfig.shared.styleTitleColor)
        navHeadImageView?.backgroundColor = UIColor.clear
        let width = CGFloat(materialData?.width ?? Float(preViewWidth))
        let height = CGFloat(materialData?.height ?? Float(preViewHeight))
        if width >= height {
            preViewWidth = maxWidth
            preViewHeight = preViewWidth * height / width
        } else {
            preViewHeight = maxHeight
            preViewWidth = preViewHeight * width / height
        }
        lineView?.removeFromSuperview()
        view.addSubview(preImageView)
//        preImageView.addSubview(changeModeBtn)
        if materialData?.type == StickerType.GIF.rawValue {
            preImageView.addSubview(gifRemindLab)
            setImageToPreImageView()
        } else if materialData?.type == StickerType.IMAGE.rawValue {
            setImageToPreImageView()
        } else if materialData?.type == StickerType.VIDEO.rawValue {
            preImageView.addSubview(playBtn)
            preImageView.layer.insertSublayer(playerLayer, at: 0)
            let ges = UITapGestureRecognizer(target: self, action: #selector(playPreVideo))
            preImageView.addGestureRecognizer(ges)
            // 设置播放内容
            setPlayerItem()
        }
//        updateSelectedState()
        isMaterialSelected = materialData?.isSelected
    }

    deinit {
        if materialData?.type == StickerType.VIDEO.rawValue {
            avPlayer.replaceCurrentItem(with: nil)
            PQNotification.removeObserver(self)
        }
    }

    /// 设置图片
    /// - Returns: <#description#>
    func setImageToPreImageView() {
        if materialData?.asset != nil {
            if materialData?.originalData == nil {
                PQPHAssetVideoParaseUtil.requestAssetOringinImage(asset: (materialData?.asset)!) { [weak self] _, data, image, _ in
                    if image == nil {
                        BFLog(message: "图片数据为空！！！！！")
                    }
                    // 1,图片，gif的原文件数据,和视频的封面
                    var newImage: UIImage?
                    if image != nil {
                        newImage = UIImage.nx_fixOrientation(image, isFront: false).nx_scaleWithMaxLength(maxLength: 1920)
                    }
                    self?.materialData?.coverImageUI = newImage
                    self?.materialData?.originalData = data
//                    if isGIF {
//                        self?.materialData?.type = StickerType.GIF.rawValue
//                        if self?.gifRemindLab.superview == nil {
//                            self?.preImageView.addSubview(self!.gifRemindLab)
//                        }
//                        self?.preImageView.displayGIF(data: data)
//                    } else {
                    self?.preImageView.image = newImage
//                    }
                }
            } else {
                setNomarlImageToPreImageView()
            }
        } else {
            setNomarlImageToPreImageView()
        }
    }

    func setNomarlImageToPreImageView() {
        if materialData?.type == StickerType.VIDEO.rawValue {
            return
        }
        if materialData?.type == StickerType.GIF.rawValue && materialData?.originalData != nil {
            preImageView.displayGIF(data: materialData?.originalData)
        } else if preImageView.image != nil {
            preImageView.image = preImageView.image
        } else if preImageView.image == nil && materialData?.coverImageUI != nil {
            if materialData?.type == StickerType.GIF.rawValue {
                preImageView.displayGIF(data: kf_imageCacheData(originUrl: materialData?.netResCoverImageURL ?? ""))
            } else {
                preImageView.image = materialData?.coverImageUI
            }
        } else if materialData?.coverImageUI != nil {
            preImageView.image = materialData?.coverImageUI
        } else if materialData?.locationPath.count ?? 0 > 0 {
            if materialData?.type == StickerType.GIF.rawValue {
                let fileData: Data = try! Data(contentsOf: URL(fileURLWithPath: documensDirectory + (materialData?.locationPath)!))
                materialData?.originalData = fileData
                preImageView.displayGIF(data: materialData?.originalData)
            } else {
                var coverImage = UIImage(contentsOfFile: documensDirectory + (materialData?.locationPath)!)
                if coverImage == nil {
                    // 有可能是 WEBP
                    let fileData: Data = try! Data(contentsOf: URL(fileURLWithPath: documensDirectory + (materialData?.locationPath)!))
                    if fileData.count != 0, fileData.isWebPFormat {
                        coverImage = WebPProcessor.default.process(item: ImageProcessItem.data(fileData), options: KingfisherParsedOptionsInfo([.onlyLoadFirstFrame, .scaleFactor(1)]))
                    }
                }
                preImageView.image = coverImage
                materialData?.coverImageUI = coverImage
            }

        } else if (materialData?.netResCoverImageURL != nil && ((materialData?.netResCoverImageURL?.count ?? 0) > 0)) || (materialData?.materialUrl != nil && ((materialData?.materialUrl.count ?? 0) > 0)) {
            var url = materialData?.materialUrl
            if url == nil || (url?.count ?? 0) <= 0 {
                url = materialData?.netResCoverImageURL
            }
            ImageDownloader.default.downloadImage(with: URL(string: url ?? "")!, options: nil) { [weak self] result in
                switch result {
                case let .success(imageLoading):
                    self?.materialData?.originalData = imageLoading.originalData
                    self?.materialData?.coverImageUI = imageLoading.image
                    if self?.materialData?.type == StickerType.GIF.rawValue {
                        self?.preImageView.displayGIF(data: imageLoading.originalData)
                    } else {
                        self?.preImageView.image = imageLoading.image
                    }
                    let imageOrientation = UIImage.nx_fixOrientation(imageLoading.image, isFront: false).nx_scaleWithMaxLength(maxLength: 1024)
                    // 下载器的原地址
                    let diskCachePath = ImageCache.default.cachePath(forKey: url!)
                    let imageCacheName = url!.md5
                    let imageCachePath = downloadImagesDirectory + imageCacheName
                    if !directoryIsExists(dicPath: downloadImagesDirectory) {
                        BFLog(message: "文件夹不存在 \(downloadImagesDirectory)")
                        createDirectory(path: downloadImagesDirectory)
                    }
                    if self?.materialData?.type != StickerType.GIF.rawValue {
                        try! imageOrientation.pngData()?.write(to: URL(fileURLWithPath: imageCachePath))
                    } else {
                        try! imageLoading.originalData.write(to: URL(fileURLWithPath: imageCachePath))
                    }
                    if !FileManager.default.fileExists(atPath: imageCachePath) {
                        try! FileManager.default.copyItem(atPath: diskCachePath, toPath: downloadImagesDirectory + imageCacheName)
                    }
                    if self?.materialData?.type != StickerType.VIDEO.rawValue {
                        self?.materialData?.locationPath = imageCachePath.replacingOccurrences(of: documensDirectory, with: "")
                    }
                case let .failure(error):
                    BFLog(message: "下载图片失败:\(error.localizedDescription)")
                }
            }
        }
    }

    /// 预览视频
    @objc func playPreVideo() {
        playBtn.isHidden = !playBtn.isHidden
        if avPlayer.currentItem == nil {
            setPlayerItem()
        }
        if playBtn.isHidden {
            if playerLayer.superlayer == nil {
                preImageView.layer.insertSublayer(playerLayer, at: 0)
            }
            avPlayer.play()
        } else {
            avPlayer.pause()
        }
    }

    /// 设置播放item
    /// - Returns: <#description#>
    func setPlayerItem() {
        if materialData?.locationPath.count ?? 0 > 0 {
            if materialData?.locationPath.contains("mobile/Media/DCIM") ?? false {
                addPlayItem(playerItem: AVPlayerItem(url: URL(fileURLWithPath: materialData!.locationPath)))
            } else {
                addPlayItem(playerItem: AVPlayerItem(url: URL(fileURLWithPath: documensDirectory + materialData!.locationPath)))
            }
        } else if materialData?.locationPath.count == 0 && materialData?.asset != nil {
            PQLoadingHUB.shared.showHUB()
            PQPHAssetVideoParaseUtil.parasToAVPlayerItem(phAsset: (materialData?.asset)!) { [weak self] playerItem, _, _ in
                PQLoadingHUB.shared.dismissHUB()
//                self?.materialData?.locationPath = (playerItem?.asset as? AVURLAsset)?.url.absoluteString.replacingOccurrences(of: "file:///", with: "") ?? ""
                self?.addPlayItem(playerItem: playerItem)
            }
        } else if isValidURL(url: materialData?.netResUrl) {
            addPlayItem(playerItem: AVPlayerItem(url: URL(string: materialData?.netResUrl ?? "")!))
        }
    }

    /// 添加播放
    /// - Parameter playerItem: <#playerItem description#>
    func addPlayItem(playerItem: AVPlayerItem?) {
        avPlayer.replaceCurrentItem(with: playerItem)
        avPlayer.play()
        let startTime = materialData?.model_in ?? 0
        var endTime = materialData?.out ?? 0
        if endTime <= 0 {
            endTime = Float64(materialData?.duration ?? 0.0)
        }
        avPlayer.seek(to: CMTime(value: CMTimeValue(startTime * playerTimescale), timescale: CMTimeScale(playerTimescale)))
        avPlayer.currentItem?.forwardPlaybackEndTime = CMTime(value: CMTimeValue(endTime * playerTimescale), timescale: CMTimeScale(playerTimescale))
    }

    /// 按钮点击事件
    /// - Parameter sender: <#sender description#>
    @objc func btnClick(sender: UIButton) {
        switch sender.tag {
        case 1, 2:
            let ratio = (materialData?.width ?? 0) / (materialData?.height ?? 1)
            if ratio < 0.4 || ratio > 4.2 {
                cShowHUB(superView: nil, msg: "暂不支持该比例的素材")
                return
            }
            materialData?.isSelected = !(materialData?.isSelected ?? false)
//            updateSelectedState()
        default:
            break
        }
    }

    /// 更新选中状态
    func updateSelectedState() {
        if materialData?.isSelected ?? false {
            choseBtn.setBackgroundImage(nil, for: .normal)
            choseBtn.backgroundColor = UIColor.hexColor(hexadecimal: "#EE0051")
            if materialData?.selectedIndex == 0 {
                choseBtn.setTitle("1", for: .normal)
            } else {
                choseBtn.setTitle("\(materialData?.selectedIndex ?? 1)", for: .normal)
            }
            choseTitleBtn.isSelected = true
        } else {
            choseBtn.setBackgroundImage(UIImage().BF_Image(named: "videomk_chose_nomal"), for: .normal)
            choseBtn.backgroundColor = UIColor.clear
            choseBtn.setTitle(nil, for: .normal)
            choseTitleBtn.isSelected = false
        }

        if materialData?.originalData == nil {
            materialData?.originalData = kf_imageCacheData(originUrl: materialData?.netResCoverImageURL ?? "")
            if materialData?.originalData != nil {
                if materialData?.type == StickerType.GIF.rawValue && materialData?.originalData != nil && (materialData?.duration ?? 0.0) <= 0 {
                    PQPHAssetVideoParaseUtil.parasGIFImage(data: (materialData?.originalData)!) { [weak self] _, _, duration in
                        self?.materialData?.duration = duration ?? 0.0
                    }
                }
            }
        }
    }

    override func backBtnClick() {
        if materialDetailClickHandle != nil {
            materialDetailClickHandle!(isMaterialSelected, materialData)
        }
        super.backBtnClick()
    }
}
