Direct2D中資源的創建順序


資源類型

Direct2D中有兩種類型的資源,設備無關資源和設備相關資源,設備無關的資源可以一次創建,永久使用(在程序生存期內),且通常創建於系統內存中,設備相關的資源和設備有相同的生命周期,一旦設備丟失,則資源也需重建。這類資源一般在顯存中創建。

設備無關的資源包括

  • ID2D1DrawingStateBlock
  • ID2D1Factory
  • ID2D1Geometry及繼承自它的接口
  • ID2D1GeometrySink和ID2D1SimplifiedGeometrySink
  • ID2D1StrokeStyle

設備相關的資源包括

  • ID2D1Brush及繼承自它的接口
  • ID2D1Layer
  • ID2D1RenderTarget及繼承自它的接口

創建順序

通常來說,先創建設備無關的資源,再創建設備相關的資源,因為ID2D1Factory是設備無關的資源,也是所有其他D2D資源的創建者。包括ID2D1RenderTarget。

一個案例

先看下面的代碼,這段代碼創建窗口,然后調用函數CreateDeviceIndependentResources創建設備無關的資源,其中包括ID2D1Factory。

HWND hwnd = CreateWindowEx(NULL,  
    L"DirectWrite Hello, World",    // window class name
    L"Draw Text",                    // window caption
    WS_OVERLAPPEDWINDOW,             // window style
    CW_USEDEFAULT,                    // initial x position
    CW_USEDEFAULT,                    // initial y position
    600,                            // initial x size
    600,                            // initial y size
    NULL,                            // parent window handle
    NULL,                            // window menu handle
    hInstance,                        // program instance handle
    NULL) ;                            // creation parameters

ShowWindow (hwnd, iCmdShow) ;
UpdateWindow (hwnd) ;

CreateDeviceIndependentResources(hwnd);

下面這段代碼響應WM_PAINT消息,調用Render函數來繪制字體。

switch (message)    
{
case   WM_PAINT:
    Render(hwnd);
    ValidateRect(hwnd, NULL) ;
    return 0 ;

Render函數中調用CreateDeviceDependentResources,該函數創建設備相關的資源,包括ID2D1RenderTarget。

VOID Render(HWND hwnd)
{
    // Create device dependent resources
    CreateDeviceDependentResources(hwnd);

    g_pRT->BeginDraw();
    g_pRT->SetTransform(D2D1::IdentityMatrix());
    g_pRT->Clear(D2D1::ColorF(D2D1::ColorF::White));

    DrawText(hwnd);

    g_pRT->EndDraw();
}

這段代碼是有問題的,因為CreateDeviceDependentResources在CreateDeviceIndependentResources之前被調用了,這是因為在調用函數UpdateWindow時,系統就發出了WM_PAINT消息,從而激發Render函數被調用,繼而CreateDeviceDependentResources函數被調用。但是這時CreateDeviceIndependentResources還未被調用,所以導致ID2D1Factory還不存在的時候,ID2D1RenderTarget就要創建,這肯定是錯誤的,因為后者是由前者創建的。

修復

將CreateDeviceIndependentResources放到函數UpdateWindow之前調用。這樣,在UpdateWindw函數發出WM_PAINT消息時,ID2D1Factory已經創建好了,所以ID2D1RenderTarget也可以順利被創建。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM