OpenGL基礎34 幀緩衝(中)之附件

2021-10-08 03:17:12 字數 2305 閱讀 7070

在之前的章節,所有的物體都是中規中矩的顯示的,只考慮了光照對物體的影響,那假設想要顯示特殊的效果該怎麼操作呢?例如馬賽克風、將所有的物體都顯示為黑白色,就像上世紀80年代的灰白電視一樣,又或者說將整個場景渲染到一張泛黃的紙上以體現出年代感……

當然是修改著色器,事實上,很多地方都是這麼做的,不過有些情況下,場景中的物體和對應的著色器都不少,若是想要整個場景(視口)體現出某個效果,就需要借助別的方法了

接上文:opengl基礎33:幀緩衝之離屏渲染

接下來,就是想辦法往幀緩衝裡新增附件,乙個附件就是乙個記憶體位址,這個記憶體位址裡面包含乙個為幀緩衝準備的緩衝,它可以是個影象,當建立乙個附件的時候我們有兩種方式可以採用:紋理或渲染緩衝(renderbuffer)物件

先建立乙個幀緩衝的紋理:

gluint getattachmenttexture()

這裡和之前的定義紋理有三點不同:

紋理的大小為螢幕的大小(測試是800 x 600)

不需要傳遞data引數,只分配記憶體而不去填充,紋理填充會在渲染到幀緩衝的時候去做

不再關心環繞方式或者mipmap

建立完紋理後,緊接著就是把它附加到幀緩衝上:

glframebuffertexture2d(gl_framebuffer, gl_color_attachment0, gl_texture_2d, texturecolorbuffer, 0);
glframebuffertexture2d 函式引數:

擴充套件:如果想要附加深度緩衝和模板緩衝,就需要在生成紋理時是用 gl_depth24_stencil8 的紋理格式和內部型別,這樣的紋理每32位數值就包含了24位的深度資訊和8位的模板資訊,不過這裡暫時不需要考慮,大致用法如下:

glteximage2d(gl_texture_2d, 0, gl_depth24_stencil8, width, height, 0, gl_depth_stencil, gl_unsigned_int_24_8, null);

glframebuffertexture2d(gl_framebuffer, gl_depth_stencil_attachment, gl_texture_2d, texture, 0);

紋理是乙個幀緩衝的可行附件型別,除此之外,opengl還有渲染緩衝物件(renderbuffer objects),渲染快取是為離線渲染而新引進的,它容許將乙個場景直接渲染到乙個渲染快取物件中,而不是渲染到紋理物件中

rbo並不能單獨使用,必須配合fbo,與opengl緩衝區對應,rbo可以存放顏色、深度、模板資料

和紋理影象一樣,渲染緩衝物件也是乙個緩衝,它可以是一堆位元組、整數、畫素或者其他東西。渲染緩衝物件的一大優點是,它以opengl原生渲染格式儲存它的資料,因此在離屏渲染到幀緩衝的時候,這些資料時已經被優化過的了,這樣的話,寫入或把它們的資料簡單地到其他緩衝的時候非常快,之前提到的函式glfwswapbuffers交換緩衝區,同樣以渲染緩衝物件實現

glgenrenderbuffers(1, &rbo);

glbindrenderbuffer(gl_renderbuffer, rbo);

glrenderbufferstorage(gl_renderbuffer, gl_depth24_stencil8, width, height);

glbindrenderbuffer(gl_renderbuffer, 0);

glframebufferrenderbuffer(gl_framebuffer, gl_depth_stencil_attachment, gl_renderbuffer, rbo);

由於渲染緩衝物件通常是只寫的,它們經常作為深度和模板附件來使用,因為大多數時候並不需要從深度和模板緩衝中讀取資料

到現在幀緩衝就做好了:繫結了顏色緩衝,也有了深度和模板緩衝、如果遺漏了某個緩衝,那麼對應的測試就不會工作,因為當前繫結的幀緩衝裡沒有對應的緩衝

好了,現在回到上篇的目的:

定義乙個幀緩衝並且啟用,然後走之前正常的渲染邏輯,這個時候,本應該在螢幕中展示的圖象就被渲染到了自己定義的幀緩衝中,接下來,我們再想辦法將幀緩衝中的資料轉變為紋理,並且對這張紋理在預設幀緩衝中進行渲染顯示

在此,目的就變成了:繫結為上面自己定義的幀緩衝,像往常那樣渲染場景,之後繫結回預設幀緩衝,簡單的繪製乙個全屏四邊形,用自己的幀緩衝的顏色緩衝作為他的紋

OpenGL基礎33 幀緩衝(上)之離屏渲染

在之前的章節,所有的物體都是中規中矩的顯示的,只考慮了光照對物體的影響,那假設想要顯示特殊的效果該怎麼操作呢?例如馬賽克風 將所有的物體都顯示為黑白色,就像上世紀80年代的灰白電視一樣,又或者說將整個場景渲染到一張泛黃的紙上以體現出年代感 當然是修改著色器,事實上,很多地方都是這麼做的,不過有些情況...

高階OpenGL渲染管線之幀緩衝(三)

幀緩衝包括之前學的 用於寫入顏色值的顏色緩衝 用於寫入深度資訊的深度緩衝和允許我們根據一些條件對齊特定片段的模板緩衝。他們都儲存在記憶體中,我們也可以定義自己的幀緩衝。在繫結到gl framebuffer目標之後,所有的讀取和寫入幀緩衝的操作將會影響當前繫結的幀緩衝。我們也可以使用gl read f...

OpenGL建立乙個幀緩衝

1.定義幀緩衝變數名 unsigned int gbuffer 2.建立幀緩衝 glgenframebuffers 1,gbuffer 3.將幀緩衝繫結到gl framebuffer glbindframebuffer gl framebuffer,gbuffer 4.將gposition紋理變數儲...