Draw Call就是CPU調(diào)用圖形編程接口,比如DirectX或OpenGL,來(lái)命令GPU進(jìn)行渲染的操作。
例如,DirectX中的DrawIndexedPrimitive命令,OpenGL中的glDrawElement命令。
1.CPU和GPU并行工作的原理
為了CPU和GPU可以并行工作,就需要一個(gè)命令緩沖區(qū)(Command Buffer)
命令緩沖區(qū)包含了一個(gè)命令隊(duì)列,由CPU向其中添加命令,而由GPU從中讀取命令。添加和讀取的過(guò)程是相互獨(dú)立的,因此命令緩沖區(qū)可以使CPU和GPU相互獨(dú)立工作。當(dāng)CPU需要渲染一些對(duì)象時(shí),它可以向命令緩沖區(qū)添加命令,而GPU完成了上一次的渲染任務(wù)后,它就可以從命令隊(duì)列里取出一個(gè)命令并執(zhí)行它。
命令緩沖區(qū)中的命令有很多種類(lèi),而Draw Call是其中的一種,其它命令還有改變渲染狀態(tài)等命令(改變使用的Shader,使用不同的紋理等)。
2.為什么 Draw Call多了會(huì)影響幀率?
在每次調(diào)用Draw Call之前,CPU需要向GPU發(fā)送很多內(nèi)容,包括數(shù)據(jù),狀態(tài),命令等。在這一階段,CPU需要完成很多工作,例如檢查渲染狀態(tài)等。而一旦CPU完成了這些準(zhǔn)備工作,GPU就可以開(kāi)始本次的渲染。GPU的渲染能力是很強(qiáng)的,渲染300個(gè)和3000個(gè)三角網(wǎng)格通常沒(méi)有什么區(qū)別,因此渲染速度往往快于CPU提交命令的速度。如果Draw Call的數(shù)量太多,CPU就會(huì)把大量時(shí)間花費(fèi)在提交Draw Call命令上,造成CPU的過(guò)載。
*因此造成Draw Call性能問(wèn)題的元兇是CPU。
3.如何減少DrawCall?
提交大量很小的Draw Call會(huì)造成CPU的性能瓶頸,即CPU把時(shí)間都花費(fèi)在準(zhǔn)備Draw Call的工作上了。那么,一個(gè)很顯然的優(yōu)化想法就是把很多小的Draw Call合并成一個(gè)大的Draw Call,這就是批處理的思想。
需要注意的是,由于我們需要在CPU的內(nèi)存中合并網(wǎng)格,而合并的過(guò)程是需要消耗時(shí)間的。因此,批處理更適合靜態(tài)的物體,例如不會(huì)移動(dòng)的大地,石頭等,對(duì)于這些靜態(tài)物體我們只需合并一次即可。當(dāng)然,我們也可以對(duì)動(dòng)態(tài)物體進(jìn)行批處理。但是,由于這些物體是不斷運(yùn)動(dòng)的,因此每一幀都需要重新進(jìn)行合并然后再發(fā)送給GPU,這對(duì)空間和時(shí)間都會(huì)造成一定的影響。
作者:SwordMaster003
鏈接:http://www.itdecent.cn/p/061b84e4f863
來(lái)源:簡(jiǎn)書(shū)
簡(jiǎn)書(shū)著作權(quán)歸作者所有,任何形式的轉(zhuǎn)載都請(qǐng)聯(lián)系作者獲得授權(quán)并注明出處。