2014-09-27 48 views
1

我在OpenGL編程方面很新穎。我的目標是設置面向對象的圖形編程,我可以自豪地說我已經取得了一些進展。現在我有不同的問題。C++,OpenGL - 渲染大量的茶壺

可以說我們有工作程序什麼可以使一個,兩個或許多旋轉茶壺。我通過在我的課堂內使用列表來做到這一點。繪圖功能的原始代碼是在這裏:

void Draw(void) 
{ 
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); 
glMatrixMode(GL_MODELVIEW); 
glPushMatrix(); 

for(list<teapot>::iterator it=teapots.begin();it!=teapots.end();it++){ 
glTranslatef(it->pos.x,it->pos.y,it->pos.z); 
glRotatef(angle,it->ang.x,it->ang.y,it->ang.z); 
glutSolidTeapot(it->size); 
glRotatef(angle,-it->ang.x,-it->ang.y,-it->ang.z); 
glTranslatef(-it->pos.x,-it->pos.y,-it->pos.z); 
} 
glPopMatrix(); 
glutSwapBuffers(); 
} 

一切都很好,但是當我畫大量的茶壺 - 兩行說,128 - 我的FPS數下降。我不知道,如果這只是硬件限制,或者我做錯了什麼?也許glPushMatrix()和glPopMatrix()應該更頻繁地發生?或更少?

+0

GLUT使用即時模式渲染,這對於性能來說很糟糕。改用VBOs,或者至少首先將茶壺呈現在顯示列表中。 – 2014-09-27 13:59:43

回答

11

你使用OpenGL的一個古老的,過時的部分(稱爲「直接模式」),其中所有的圖形數據從CPU發送到GPU每一幀:內glutSolidTeapot()是代碼,不會後跟類似glBegin(GL_TRIANGLES)大量glVertex3f(...),最後glEnd()。棄用的原因是因爲它是一個瓶頸。 GPU是高度並行的,並且能夠同時處理許多三角形,但是如果您的程序一次只發送一個頂點,則它們不能這樣做,其中的glVertex3f

你應該瞭解現代的OpenGL API,在其中您可以通過創建一個「緩衝區對象」和你的頂點數據加載到它開始 - 基本上傳你的形狀到GPU的內存一次,先期 - 然後您可以發出大量調用,告訴GPU使用該緩衝區對象中的頂點繪製三角形,而不必每次都發送所有頂點。

(不幸的是,這意味着你將無法使用glutSolidTeapot(),因爲它引用了即時模式,並不知道如何爲緩衝區對象生成頂點數據,但我相信你可以找到一個茶壺模型在網上某處。)

Open.gl是一個體面的教程,我知道現代風格的OpenGL,但我敢肯定也有其他人。

+1

+1,因爲我喜歡茶壺。部分原因是你寫的是正確的。 – 2014-09-27 14:12:26

+0

謝謝你!現在我明白生成一個茶壺不是很好開始...;) – 2014-09-27 16:33:15

+1

好吧,把茶壺作爲測試沒有錯。只需將其放入VBO中,而不是使用'glutSolidTeapot'在即時模式下繪製它。 – Wyzard 2014-09-27 16:37:33

1

由於您正在使用舊的棄用API,因此在每次繪製調用時,您一次又一次地將所有數據從CPU提交到GPU,您還希望在渲染相同幾何體時保持下降幀率因此實際上,在使用可編程管道時保持這種幾何體渲染方法也不會讓您獲益。您將在+ - 40-60個物體(取決於您的GPU)之後開始注意到FPS已經下降。您真正需要的是稱爲批處理drawing.the批處理繪圖可能有不同的技術,所有的女巫暗示你使用現代的OpenGL,因爲我們在這裏談論的數據緩衝區(您上傳到GPU的情況下的頂點陣列)。您可以將所有的幾何體推入單個頂點緩衝區或使用instanced rendering命令。在您的情況下,如果您所有人都在多次繪製相同的網格,則s第二種技術是完美的解決方案。還有更復雜的技術,如indirect multiple draw命令,它們允許您通過一次繪製調用確實繪製非常大量的不同幾何圖形。但對於初學者來說,這些技術相當先進。總而言之,底線是您必須移動到現代的OpenGL,並開始使用幾何配料,如果你想保持你的應用程序FPS高,同時繪製大量的網格。