AVAsset 的 NaturalSize 与视频文件不同

NaturalSize of AVAsset is different than video file

我在检查视频方向时遇到了很大的问题。有一个代码可以检查视频文件是否处于纵向模式:

private func checkIfVideoIsPortrait(videoURL: NSURL) -> Bool {

    let videoAsset = AVAsset.init(URL: videoURL)
    let videoTrack = videoAsset.tracksWithMediaType(AVMediaTypeVideo)[0]
    let size = videoTrack.naturalSize
    let txf = videoTrack.preferredTransform

    let realSize = CGSizeApplyAffineTransform(size, txf)

    print(videoTrack)
    print(txf)
    print(size)
    print(realSize)

    if (size.width == txf.tx && size.height == txf.ty) {
        return false
    } else if (txf.tx == 0 && txf.ty == 0) {
        return false
    } else if (txf.tx == 0 && txf.ty == size.width) {
        return true
    } else {
        return true
    }
}

我有两个视频文件:1080x1920 和 360x640。关键是代码 return 文件的不同尺寸,我无法识别视频方向。

有一个日志:

< AVAssetTrack: 0x157dee9a0, trackID = 2, mediaType = vide >

CGAffineTransform(a: 1.0, b: 0.0, c: 0.0, d: 1.0, tx: 0.0, ty: 0.0)

(320.0, 568.0)

(320.0, 568.0)

< AVAssetTrack: 0x1593643c0, trackID = 2, mediaType = vide >

CGAffineTransform(a: 0.0, b: 1.0, c: -1.0, d: 0.0, tx: 720.0, ty: 0.0)

(1280.0, 720.0)

(-720.0, 1280.0)

如何正确查看视频的尺寸?我很乐意提供帮助。

经过多天的尝试和思考如何获得视频的真实自然大小,我改变了我的策略。

现在我正在使用从视频创建的缩略图来检查胶片的尺寸。

问题出在 AVAssetExportSession 中。它会破坏 preferredTransform 并使用横向值。原因可能隐藏在 AVAssetExportPreset640x480.

Swift2.0中有解决代码:

func checkIfVideoIsPortrait(videoURL: NSURL) -> Bool {

    let videoAsset = AVAsset.init(URL: videoURL)

    let generator = AVAssetImageGenerator.init(asset: videoAsset)
    let imageRef: CGImageRef!

    do {
        try imageRef = generator.copyCGImageAtTime(kCMTimeZero, actualTime: nil)

        let thumbinal = UIImage.init(CGImage: imageRef)

        if thumbinal.size.width < thumbinal.size.height {
            return true
        } else if thumbinal.size.width > thumbinal.size.height{
            return false
        }

    } catch let error as NSError {
        print("Failed to check video portrait")
        print(error.localizedDescription)
    }
    return false
}