书法字典:https://www.shufadict.com

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也可以顺利被创建。

posted on   翰墨小生  阅读(3909)  评论(0编辑  收藏  举报

编辑推荐:
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
阅读排行:
· 周边上新:园子的第一款马克杯温暖上架
· Open-Sora 2.0 重磅开源!
· .NET周刊【3月第1期 2025-03-02】
· 分享 3 个 .NET 开源的文件压缩处理库,助力快速实现文件压缩解压功能!
· [AI/GPT/综述] AI Agent的设计模式综述
历史上的今天:
2011-09-15 也谈走台阶问题

导航

< 2012年9月 >
26 27 28 29 30 31 1
2 3 4 5 6 7 8
9 10 11 12 13 14 15
16 17 18 19 20 21 22
23 24 25 26 27 28 29
30 1 2 3 4 5 6
书法字典:https://www.shufadict.com
点击右上角即可分享
微信分享提示