2009-04-15 179 views
0

我有3位圖點。什麼是在另一幅圖像上繪製圖像的最快方式?

Bitmap* totalCanvas = new Bitmap(400, 300, PixelFormat32bppARGB); // final canvas 
Bitmap* bottomLayer = new Bitmap(400, 300,PixelFormat32bppARGB); // background 
Bitmap* topLayer = new Bitmap(XXX); // always changed. 

我會在bottomLayer上繪製複雜的背景。我不想一次又一次地在totalCanvas上重繪複雜背景,所以我將它存儲在bottomLayer中。

TopLayer頻繁更改。 我想繪製bottomLayer到totalCanvas。哪種方法最快?

Graphics canvas(totalCanvas); 
canvas.DrawImage(bottomLayer, 0, 0); step1 
canvas.DrawImage(topLayer ,XXXXX); step2 

我希望step1儘可能快。任何人都可以給我一些樣品嗎? 非常感謝!

感謝unwind的回答。我寫了下面的代碼:

Graphics canvas(totalCanvas); 
for (int i = 0; i < 100; ++i) 
{ 
canvas.DrawImage(bottomLayer, 0,0); 
} 

這部分需要968ms ......實在是太慢了......

+0

是bottoLayer尺寸總是一樣的totalCanvas尺寸? 如果是這樣,爲什麼創建兩個位圖? – user88637 2009-04-15 07:28:13

+0

謝謝,我在問題中添加了原因。 – user25749 2009-04-15 08:15:15

回答

1

幾乎所有的GDI +操作應該由驅動程序實現對GPU儘可能地運行。這應該意味着一個簡單的2D位圖複製操作將「足夠快」,即使是相當大的「足夠」值。

我的建議很明顯:不要花時間尋找「最快」的方式來做這件事。您已經非常清楚地闡述了這個問題,所以只要按照您在問題中概述的方式嘗試清楚地實施它即可。那麼你當然可以繼續進行基準測試並決定繼續尋找。

一個簡單的例子:

甲32 BPP 400x300的位圖的大小約爲469 KB。根據this handy table,2002年的Nvidia GeForce 4 MX的理論內存帶寬爲2.6 GB/s。假設複製是以純粹的「覆蓋」模式完成的,即不混合現有表面(這聽起來是正確的,因爲您的副本基本上是將幀「清除」到副本的源數據的方式),並且開銷係數爲4爲了安全起見,我們得到:

(2.6 * 2^30 /(4 * 469 * 2^10))= 1453

這意味着你的副本應在1453愉快地運行FPS,這是我假定「足夠好」。

0

如果可能(並且它看起來像來自您的代碼),使用DrawImageUnscaled將比DrawImage快得多。或者如果你一遍又一遍地使用相同的圖像,創建一個TextureBrush並使用它。

GDI +的問題是,大多數情況下,它是不加速的。爲了獲得快速的繪圖速度,你真的需要GDI和BitBlt,這是一個嚴重的痛苦,但是與GDI +一起使用,特別是當你在託管代碼中(很難判斷你是否使用託管C++或直C++)。

有關在.net中快速顯示圖形的更多信息,請參閱此post

相關問題