簡體   English   中英

iOS GLKit:使用相機輸出設置GLKBaseEffect紋理

[英]iOS GLKit: set GLKBaseEffect texture with camera output

我已經建立了一個AVCapture會話,並在委托方法中,使用以下代碼嘗試通過輸出設置GLKBaseEffect紋理,但是我得到的只是黑色。 我應該怎么做才能使其正常工作?

- (void)captureOutput:(AVCaptureOutput *)captureOutput didOutputSampleBuffer (CMSampleBufferRef)sampleBuffer fromConnection:(AVCaptureConnection *)connection {

CVPixelBufferRef pixelBuffer = (CVPixelBufferRef)CMSampleBufferGetImageBuffer(sampleBuffer);

effect.texture2d0.name = CVOpenGLESTextureGetName(pixelBuffer);
}

TLDR:我認為您不能將相機輸出與GLKBaseEffect -來自相機的數據為雙平面YUV格式,因此您需要一個自定義片段着色器以在渲染時將其轉換為RGB,而GLKBaseEffect不會執行自定義着色器。

看起來這里有些API混亂,因此,如果您需要更多背景知識,請繼續閱讀...

盡管CVOpenGLESTexture類型是從CVPixelBuffer派生的, CVPixelBuffer CMSampleBufferGetImageBuffer返回的圖像緩沖區並不是自動的OpenGL ES紋理。 每次使用CVOpenGLESTextureCache從相機獲取一幀時,都需要從圖像緩沖區創建紋理。

蘋果的GLCameraRipple示例代碼說明了如何執行此操作。 快速概覽:

  1. 設置GL上下文后, setupAVCapture方法將調用CVOpenGLESTextureCacheCreate來創建綁定到該上下文的紋理緩存。
  2. captureOutput:didOutputSampleBuffer:fromConnection: ,他們使用CMSampleBufferGetImageBuffer從樣本緩沖區中獲取圖像緩沖區,然后使用紋理緩存的CVOpenGLESTextureCacheCreateTextureFromImage函數從中創建兩個OpenGL ES紋理。 您需要兩個紋理,因為圖像緩沖區在兩個位平面中具有YUV顏色數據。
  3. 每個紋理在使用glBindTexture創建后就必須進行渲染。 一般情況下,你可以更換glBindTexture與呼叫設置GLKBaseEffecttexture2d0.name ,它告訴給prepareToDraw ,但GLKBaseEffect無法呈現YUV。
  4. 使用着色器程序繪制兩個綁定的紋理,該着色器程序的片段着色器首先通過組合來自Y和UV紋理的分量來生成YUV向量,然后進行簡單的矩陣乘法以根據HDTV色彩空間規范將其轉換為RGB像素顏色。 。

因為您需要用於YUV到RGB轉換的自定義片段着色器,所以GLKBaseEffect無法為您提供幫助。 但是,如GLCameraRipple示例所示,您需要編寫的自定義着色器並不是那么可怕。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM