swift – 媒体类型的样本缓冲区必须与接收者的媒体类型(“soun”)匹配

swift – 媒体类型的样本缓冲区必须与接收者的媒体类型(“soun”)匹配,第1张

概述基于这个答案 https://stackoverflow.com/a/16035330/1615183我在Swift中创建了以下用于压缩视频的代码: var videoWriter:AVAssetWriter!var videoWriterInput:AVAssetWriterInput!var processingQueue:dispatch_queue_t = dispatch_queu 基于这个答案 https://stackoverflow.com/a/16035330/1615183我在Swift中创建了以下用于压缩视频的代码:

var vIDeoWriter:AVAssetWriter!var vIDeoWriterinput:AVAssetWriterinput!var processingQueue:dispatch_queue_t  = dispatch_queue_create("processingQueue1",nil)var processingQueue2:dispatch_queue_t = dispatch_queue_create("processingQueue2",nil)var audioWriterinput:AVAssetWriterinput!func encode(){    NSfileManager.defaultManager().removeItemAtURL(self.outputfile,error: nil)    let vIDeoCleanAperturesettings = [AVVIDeoCleanApertureHeightKey: 720,AVVIDeoCleanApertureWIDthKey: 1280,AVVIDeoCleanApertureHorizontalOffsetKey: 2,AVVIDeoCleanApertureVerticalOffsetKey: 2    ]    let codecSettings  = [AVVIDeoAverageBitRateKey: 1024000,AVVIDeoCleanApertureKey: vIDeoCleanAperturesettings    ]    let vIDeoSettings = [AVVIDeoCodecKey: AVVIDeoCodecKey,AVVIDeoCompressionPropertIEsKey: codecSettings,AVVIDeoHeightKey: 720,AVVIDeoWIDthKey: 1280]    //setup vIDeo writer    var error:NSError?    let asset = AVURLAsset(URL: self.inputfile,options: nil)    let vIDeoTrack:AVAssetTrack = asset.tracksWithMediaType(AVMediaTypeVIDeo)[0] as AVAssetTrack    let vIDeoSize:CGSize = vIDeoTrack.naturalSize    vIDeoWriterinput = AVAssetWriterinput(mediaType: AVMediaTypeVIDeo,outputSettings: vIDeoSettings)    vIDeoWriterinput.expectsMediaDataInRealTime = false    vIDeoWriterinput.transform = vIDeoTrack.preferredtransform    vIDeoWriter = AVAssetWriter(URL: self.outputfile,fileType: AVfileTypeQuickTimeMovIE,error: &error)    if vIDeoWriter.canAddinput(vIDeoWriterinput) {        vIDeoWriter.addinput(vIDeoWriterinput)    }else{        println("cant add vIDeo writer input")        return    }    //setup vIDeo reader    let vIDeoReaderSettings = [ kCVPixelBufferPixelFormatTypeKey as String : kCVPixelFormatType_420YpCbCr8BiPlanarVIDeoRange]    let vIDeoReaderOutput:AVAssetReaderTrackOutput = AVAssetReaderTrackOutput(track: vIDeoTrack,outputSettings: vIDeoReaderSettings) // should it be vIDeoReaderSettings?    let vIDeoReader:AVAssetReader = AVAssetReader(asset: asset,error: &error)    if vIDeoReader.canAddOutput(vIDeoReaderOutput) {        vIDeoReader.addOutput(vIDeoReaderOutput)    }    //setup audio writer    audioWriterinput = AVAssetWriterinput(mediaType: AVMediaTypeAudio,outputSettings: nil)    audioWriterinput.expectsMediaDataInRealTime = false    if vIDeoWriter.canAddinput(audioWriterinput){        vIDeoWriter.addinput(audioWriterinput)    }    //setup audio reader    let audioTrack:AVAssetTrack = asset.tracksWithMediaType(AVMediaTypeVIDeo)[0] as AVAssetTrack    let audioReaderOutput:AVAssetReaderOutput = AVAssetReaderTrackOutput(track: audioTrack,outputSettings: nil)    let audioReader:AVAssetReader = AVAssetReader(asset: asset,error: &error)    if audioReader.canAddOutput(audioReaderOutput) {        audioReader.addOutput(audioReaderOutput)    }else {        println("cant add audio reader")        return    }    vIDeoWriter.startWriting()    vIDeoReader.startReading()    vIDeoWriter.startSessionAtSourceTime(kCMTimeZero)    vIDeoWriterinput.requestMediaDataWhenReadyOnQueue(processingQueue) {        while self.vIDeoWriterinput.readyForMoreMediaData {            println("First loop")            var sampleBuffer = vIDeoReaderOutput.copyNextSampleBuffer()            if vIDeoReader.status == .Reading && sampleBuffer != nil {                println("Appending")                self.vIDeoWriterinput.appendSampleBuffer(sampleBuffer)            }else {                self.vIDeoWriterinput.markAsFinished()                if vIDeoReader.status == .Completed {                    audioReader.startReading()                    self.vIDeoWriter.startSessionAtSourceTime(kCMTimeZero)                    self.audioWriterinput.requestMediaDataWhenReadyOnQueue(self.processingQueue2) {                        while self.audioWriterinput.readyForMoreMediaData {                            println("Second loop")                            var sampleBuffer2:CMSampleBufferRef? = audioReaderOutput.copyNextSampleBuffer()                            if audioReader.status == .Reading && sampleBuffer2 != nil {                                self.audioWriterinput.appendSampleBuffer(sampleBuffer2)                            }else {                                self.audioWriterinput.markAsFinished()                                println("Audio finish")                                self.vIDeoWriter.finishWritingWithCompletionHandler { println("Done") }                            }                        }                    }                }                else {                    println("VIDeo Reader not completed")                }                println("Finished")                break            }// else vIDoSampleBuffer        }    } }

但是,如果我删除音频部分,我只得到一个空文件.如果我在第二次循环运行时第一次按原样运行它没有问题,但在第二次迭代时它崩溃并出现以下错误:

*** Terminating app due to uncaught exception 'NSinvalidargumentexception',reason: '*** -[AVAssetWriterinput appendSampleBuffer:] Media type of sample buffer must match receiver's media type ("soun")'

有没有人有同样的问题?

解决方法 将AVMediaTypeVIDeo更改为音频:

let audioTrack:AVAssetTrack = asset.tracksWithMediaType(AVMediaTypeVIDeo)[0] as AVAssetTrack

应该

let audioTrack:AVAssetTrack = asset.tracksWithMediaType(AVMediaTypeAudio)[0] as AVAssetTrack
总结

以上是内存溢出为你收集整理的swift – 媒体类型的样本缓冲区必须与接收者的媒体类型(“soun”)匹配全部内容,希望文章能够帮你解决swift – 媒体类型的样本缓冲区必须与接收者的媒体类型(“soun”)匹配所遇到的程序开发问题。

如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。

欢迎分享,转载请注明来源:内存溢出

原文地址: https://outofmemory.cn/web/1014355.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-05-22
下一篇 2022-05-22

发表评论

登录后才能评论

评论列表(0条)

保存