2017-04-10 50 views
1

我有這款相機的應用程序。爲什麼一個方法可以很好地工作,但如果我把它放在dispatch_async裏面會崩潰?

我把圖像從相機,並處理與過濾器,並在裏面captureOutput:didOutputSampleBuffer:fromConnection:某些時候,我把最後的圖像,並利用這一點,寫入文件:奇妙

CFRetain(sampleBuffer); 
    [myself writeToVideoImage:resultadoFinal 
      withSampleBuffer:sampleBuffer]; 
    CFRelease(sampleBuffer); 

作品,但如果我把這個隊列內,像這樣:

CFRetain(sampleBuffer);   
    dispatch_async(_writeToVideoQueue, ^{ 
     [myself writeToVideoImage:resultadoFinal 
       withSampleBuffer:sampleBuffer]; 
     CFRelease(sampleBuffer); 
    }); 

崩潰就行

[_assetWriter startSessionAtSourceTime:presentationTime]; 

of

- (void)writeToVideoImage:(CIImage *)resultadoFinal 
     withSampleBuffer:(CMSampleBufferRef)sampleBuffer 
{ 

    CFRetain(sampleBuffer); 
    CMTime presentationTime = CMSampleBufferGetPresentationTimeStamp(sampleBuffer); 

    CGRect extent = [resultadoFinal extent]; 

    if (!_readyToWriteVideo) { 
    _readyToWriteVideo = [self setupAssetWriterVideoInputWithSize:extent.size]; 
    return; 
    } 
    else if (_videoWritingStarted) { 
    _videoWritingStarted = NO; 
    // ***** CRASHES HERE ************ 
    [_assetWriter startSessionAtSourceTime:presentationTime]; 
    } 


    CVPixelBufferRef renderedOutputPixelBuffer = NULL; 

    OSStatus err = CVPixelBufferPoolCreatePixelBuffer(NULL, 
                _pixelBufferAdaptor.pixelBufferPool, 
                &renderedOutputPixelBuffer); 
    if (err) return; 

    [_ciContext render:resultadoFinal 
    toCVPixelBuffer:renderedOutputPixelBuffer 
       bounds:extent 
      colorSpace:_sDeviceRgbColorSpace]; 

    [self writeToFile:renderedOutputPixelBuffer 
     comSampleTime:presentationTime 
       size:extent.size]; 
    CFRelease(renderedOutputPixelBuffer); 
    CFRelease(sampleBuffer); 
} 

我不知道發生了什麼。

它似乎是一些釋放。我第一次懷疑sampleBuffer正在釋放,但我保留它的功能內外,以防萬一。我也嘗試在調用方法之前在塊內創建resultadoFinal的副本,但沒有成功。

Xcode中顯示錯誤

[AVAssetWriter startSessionAtSourceTime:]不能調用方法時的狀態是0

大約有上做題。我嘗試了所有建議,但都沒有成功。

任何想法?

+1

聽起來好像你在分派寫入之後,但在執行之前對資產編寫者做了某些事情(我知道這是模糊的)。暴力方法可能是觀察「狀態」(KVO)並查看是否有東西將其改變爲被拒絕的值。 –

+1

我對AVAssetWriter瞭解不多,但是錯誤「狀態爲0時無法調用方法」聽起來像某些東西沒有正確初始化 - 請記住,當您在不同線程上運行dispatch_async時,可能需要某些東西在該線程上初始化?只是一個想法 –

+0

@JeffLoughlin - 簡直太棒了!我使用了3個隊列,一個以超高優先級在屏幕上顯示視頻,另一個以高優先級將幀寫入磁盤,另一個以中等優先級來執行其他操作。這種做法是最近發生的,錯誤的是'AVAssetWriter'初始化發生在另一個隊列上,而不是正在編寫視頻的隊列。現在它像絲一樣工作。謝謝!請將此評論作爲答案,以便我可以接受。 – SpaceDog

回答

1

錯誤「狀態爲0時無法調用方法」聽起來像某些東西沒有正確初始化 - 請記住,當您在不同線程上運行dispatch_async時,所以您需要在該線程上初始化AVAssetWriter。

+0

只是燦爛的!我使用了3個隊列,一個以超高優先級在屏幕上顯示視頻,另一個以高優先級將幀寫入磁盤,另一個以中等優先級來執行其他操作。這種方法是最近的錯誤,AVAssetWriter初始化發生在另一個隊列上,而不是正在編寫視頻的隊列。現在它像絲一樣工作。謝謝! – SpaceDog

+0

我不知道「輝煌」是如何描述我的答案......就像我上面所說,我對AVAssetWriter瞭解不多,所以這只是一個猜測 - 但我一直在圍繞這個iOS足夠長的時間來識別一些常見問題以及遇到它們時出現的錯誤類型(它們並不總是清楚說明實際問題是什麼......)。很高興我能幫上忙。 –

相關問題