Avfoundation кадрирование видео вызывает неправильный кадр с черной областью вокруг видео - PullRequest
0 голосов
/ 29 октября 2018

Я использую библиотеку YPImagePicker для выбора и обрезки видео. Не каждое видео обрезается неправильно, но некоторые из них таковы. Библиотека использует AVFoundation для обрезки видео с определенным кадром и временем. В библиотеке есть следующий код для обрезки видео:

func fetchVideoUrlAndCrop(for videoAsset: PHAsset, cropRect: CGRect, callback: @escaping (URL) -> Void) {
    let videosOptions = PHVideoRequestOptions()
    videosOptions.isNetworkAccessAllowed = true
    imageManager?.requestAVAsset(forVideo: videoAsset, options: videosOptions) { asset, _, _ in
        do {
            guard let asset = asset else { print("⚠️ PHCachingImageManager >>> Don't have the asset"); return }

            let assetComposition = AVMutableComposition()
            let trackTimeRange = CMTimeRangeMake(kCMTimeZero, asset.duration)

            // 1. Inserting audio and video tracks in composition

            guard let videoTrack = asset.tracks(withMediaType: AVMediaType.video).first,
                let videoCompositionTrack = assetComposition
                    .addMutableTrack(withMediaType: .video,
                                     preferredTrackID: kCMPersistentTrackID_Invalid) else {
                                        print("⚠️ PHCachingImageManager >>> Problems with video track")
                                        return

            }
            guard let audioTrack = asset.tracks(withMediaType: AVMediaType.audio).first,
                let audioCompositionTrack = assetComposition
                    .addMutableTrack(withMediaType: AVMediaType.audio,
                                     preferredTrackID: kCMPersistentTrackID_Invalid) else {
                                        print("⚠️ PHCachingImageManager >>> Problems with audio track")
                                        return
            }

            try videoCompositionTrack.insertTimeRange(trackTimeRange, of: videoTrack, at: kCMTimeZero)
            try audioCompositionTrack.insertTimeRange(trackTimeRange, of: audioTrack, at: kCMTimeZero)

            // 2. Create the instructions

            let mainInstructions = AVMutableVideoCompositionInstruction()
            mainInstructions.timeRange = trackTimeRange

            // 3. Adding the layer instructions. Transforming

            let layerInstructions = AVMutableVideoCompositionLayerInstruction(assetTrack: videoCompositionTrack)
            layerInstructions.setTransform(videoTrack.getTransform(cropRect: cropRect), at: kCMTimeZero)
            layerInstructions.setOpacity(1.0, at: kCMTimeZero)
            mainInstructions.layerInstructions = [layerInstructions]

            // 4. Create the main composition and add the instructions

            let videoComposition = AVMutableVideoComposition()
            videoComposition.renderSize = cropRect.size
            videoComposition.instructions = [mainInstructions]
            videoComposition.frameDuration = CMTimeMake(1, 30)

            // 5. Configuring export session

            let exportSession = AVAssetExportSession(asset: assetComposition,
                                                     presetName: YPConfig.video.compression)
            exportSession?.outputFileType = YPConfig.video.fileType
            exportSession?.shouldOptimizeForNetworkUse = true
            exportSession?.videoComposition = videoComposition
            exportSession?.outputURL = URL(fileURLWithPath: NSTemporaryDirectory())
                .appendingUniquePathComponent(pathExtension: YPConfig.video.fileType.fileExtension)

            // 6. Exporting

            DispatchQueue.main.async {
            self.exportTimer = Timer.scheduledTimer(timeInterval: 0.1,
                                                    target: self,
                                                    selector: #selector(self.onTickExportTimer),
                                                    userInfo: exportSession,
                                                    repeats: true)
            }

            exportSession?.exportAsynchronously(completionHandler: {
                DispatchQueue.main.async {
                    if let url = exportSession?.outputURL, exportSession?.status == .completed {
                        callback(url)
                    } else {
                        let error = exportSession?.error
                        print("error exporting video \(String(describing: error))")
                    }
                }
            })
        } catch let error {
            print("⚠️ PHCachingImageManager >>> \(error)")
        }
    }
    }

У кого-нибудь есть идеи, почему он экспортирует видео с неправильным фреймом? Предложения приветствуются.

Заранее спасибо !!

Reference image

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...