Direct2D 另一种与D3D创建类似的方法
在进行D2D学习的时候,发现了这样一篇文档,
Direct2D Quickstart for Windows 8
只有这么一小段介绍,
Direct2D is a native-code, immediate-mode API for creating 2D graphics. This topic illustrates how to use Direct2D to draw to a Windows::UI::Core::CoreWindow.
与先前使用CreateHwndRenderTarget直接创建渲染目标的方法不同,它使用的D3D中的交换链技术,也就是先创建Device,再从Device中创建context,有了context后,再在context中创建渲染对象,并将后缓存区绑定到渲染对象上。最终调用context来绘制图形。并使用交换链的技术present来显示图像。
目前不知道这个与之前d2d的绘图方法的主要区别,我猜测是性能方面可能是交换链技术更高,毕竟涉及到D3D。
以下的创建的详细步骤,
步骤1:包括Direct2D标头
除了应用程序所需的头之外,还包括d2d1.h和d2d1_1.h头。
步骤2:创建一个ID2D1Factory1
任何Direct2D示例所做的第一件事就是创建一个ID2D1Factory1。
DX::ThrowIfFailed(
D2D1CreateFactory(
D2D1_FACTORY_TYPE_SINGLE_THREADED,
__uuidof(ID2D1Factory1),
&options,
&m_d2dFactory
)
);
所述ID2D1Factory1接口是使用的Direct2D的起点; 使用ID2D1Factory1创建Direct2D资源。
创建工厂时,可以指定它是多线程还是单线程。(有关多线程工厂的更多信息,请参见ID2D1Factory参考页上的说明。)本示例创建一个单线程工厂。
通常,您的应用程序应创建一次工厂,并在应用程序的生命周期内保留它。
步骤3:创建一个ID2D1Device和一个ID2D1DeviceContext
创建工厂后,使用它创建Direct2D设备,然后使用该设备创建Direct2D设备上下文。为了创建这些Direct2D对象,您必须具有Direct3D 11设备,DXGI设备和DXGI交换链。有关创建必要先决条件的信息,请参见设备和设备上下文。
// Obtain the underlying DXGI device of the Direct3D11.1 device.
DX::ThrowIfFailed(
m_d3dDevice.As(&dxgiDevice)
); // Obtain the Direct2D device for 2-D rendering.
DX::ThrowIfFailed(
m_d2dFactory->CreateDevice(dxgiDevice.Get(), &m_d2dDevice)
); // And get its corresponding device context object.
DX::ThrowIfFailed(
m_d2dDevice->CreateDeviceContext(
D2D1_DEVICE_CONTEXT_OPTIONS_NONE,
&m_d2dContext
)
);
设备上下文是可以执行绘图操作并创建与设备相关的绘图资源(如画笔)的设备。您还可以使用设备上下文将ID2D1Bitmap链接到DXGI曲面以用作渲染目标。设备上下文可以呈现给不同类型的目标。
此处的代码声明了位图的属性,该位图链接到渲染到CoreWindow的DXGI交换链。该ID2D1DeviceContext :: CreateBitmapFromDxgiSurface方法从表面DXGI得到了Direct2D的表面。这使得渲染到目标ID2D1Bitmap的所有内容都渲染到交换链的表面。
有了Direct2D曲面后,请使用ID2D1DeviceContext :: SetTarget方法将其设置为活动渲染目标。
// Now we set up the Direct2D render target bitmap linked to the swapchain.
// Whenever we render to this bitmap, it will be directly rendered to the
// swapchain associated with the window.
D2D1_BITMAP_PROPERTIES1 bitmapProperties =
BitmapProperties1(
D2D1_BITMAP_OPTIONS_TARGET | D2D1_BITMAP_OPTIONS_CANNOT_DRAW,
PixelFormat(DXGI_FORMAT_B8G8R8A8_UNORM, D2D1_ALPHA_MODE_PREMULTIPLIED),
m_dpi,
m_dpi
); // Direct2D needs the dxgi version of the backbuffer surface pointer.
ComPtr<IDXGISurface> dxgiBackBuffer;
DX::ThrowIfFailed(
m_swapChain->GetBuffer(0, IID_PPV_ARGS(&dxgiBackBuffer))
); // Get a D2D surface from the DXGI back buffer to use as the D2D render target.
DX::ThrowIfFailed(
m_d2dContext->CreateBitmapFromDxgiSurface(
dxgiBackBuffer.Get(),
&bitmapProperties,
&m_d2dTargetBitmap
)
); // So now we can set the Direct2D render target.
m_d2dContext->SetTarget(m_d2dTargetBitmap.Get());
第4步:创建画笔
就像工厂一样,设备上下文可以创建图形资源。在此示例中,设备上下文创建画笔。
ComPtr<ID2D1SolidColorBrush> pBlackBrush;
DX::ThrowIfFailed(
m_d2dContext->CreateSolidColorBrush(
D2D1::ColorF(D2D1::ColorF::Black),
&pBlackBrush
)
);
画笔是绘制区域的对象,例如形状的笔触或几何图形的填充。在此示例中,笔刷用预定义的纯色黑色绘制区域。
Direct2D还提供其他类型的笔刷:用于绘制线性和径向渐变的渐变笔刷,用于使用位图和图案进行绘制的位图画笔,以及从Windows 8开始使用的用于绘制渲染图像的图像笔刷。
一些绘图API提供了用于绘制轮廓的笔和用于填充形状的画笔。Direct2D有所不同:它不提供笔对象,但使用笔刷绘制轮廓和填充形状。绘制轮廓时,请使用ID2D1StrokeStyle接口,或者在Windows 8中从ID2D1StrokeStyle1接口开始,使用画笔来控制路径描边操作。
画笔只能与创建画笔的渲染目标以及同一资源域中的其他渲染目标一起使用。通常,您应该只创建一次画笔,并在创建它们的渲染目标的整个生命周期内保留它们。ID2D1SolidColorBrush是唯一的异常;由于创建起来相对便宜,因此每次绘制框架时都可以创建一个ID2D1SolidColorBrush,而不会明显降低性能。您也可以使用一个ID2D1SolidColorBrush,并且每次使用时只需更改其颜色或不透明度。
步骤5:绘制矩形
接下来,使用设备上下文绘制矩形
m_d2dContext->BeginDraw(); m_d2dContext->DrawRectangle(
D2D1::RectF(
rc.left + 100.0f,
rc.top + 100.0f,
rc.right - 100.0f,
rc.bottom - 100.0f),
pBlackBrush); DX::ThrowIfFailed(
m_d2dContext->EndDraw()
); DX::ThrowIfFailed(
m_swapChain->Present1(1, 0, ¶meters);
);
该DrawRectangle的方法有两个参数:要绘制的矩形,并使用画笔绘制矩形的轮廓。(可选)您还可以指定笔划宽度,虚线图案,线连接和端盖选项。
您必须在发出任何绘图命令之前调用BeginDraw方法,并且在完成发出绘图命令之后必须调用EndDraw方法。该EndDraw方法返回HRESULT指示绘图命令是否成功。如果失败,则ThrowIfFailed帮助器函数将引发异常。
所述IDXGISwapChain ::Present方法是交换缓冲面与上屏幕表面,以显示结果。
Direct2D 另一种与D3D创建类似的方法的更多相关文章
- GoF的23种设计模式之创建型模式的特点和分类
创建型模式的主要关注点是“怎样创建对象?”,它的主要特点是“将对象的创建与使用分离”.这样可以降低系统的耦合度,使用者不需要关注对象的创建细节,对象的创建由相关的工厂来完成.就像我们去商场购买商品时, ...
- C#两种创建快捷方式的方法
C#两种创建快捷方式的方法http://www.cnblogs.com/linmilove/archive/2009/06/10/1500989.html
- 【Java 线程的深入研究1】Java 提供了三种创建线程的方法
Java 提供了三种创建线程的方法: 通过实现 Runnable 接口: 通过继承 Thread 类本身: 通过 Callable 和 Future 创建线程. 1.通过实现 Runnable 接口来 ...
- Linux下几种另类创建文件之方法
以前我们用编辑器例如vi来新建文件,下面介绍几种另类生成文件的方法,多用在备份和测试上. 创建文件的方法: 1.echo 命令 #echo "set bell" >& ...
- Expression Blend 的点滴(4)--创建类似iPhone屏幕锁控件(下)
原文:Expression Blend 的点滴(4)--创建类似iPhone屏幕锁控件(下) 接着上篇... 接下去,将一步步演示如果创建当点击checkBox后,其中的按钮由左边滑动到右边,表示处于 ...
- Expression Blend 的点滴(4)--创建类似iPhone屏幕锁控件(上)
原文:Expression Blend 的点滴(4)--创建类似iPhone屏幕锁控件(上) 本篇文章,最终效果图: 当然,不只是一个UI而已,如果只是一张图片,那专业的设计师能做出更出色的效果.在 ...
- Java四种读取和创建XML文档的例子教程
四种方法解析XML文档:Dom.SAX.JDOM.dom4j 1.了解XML XML,即可扩展标记语言(Extensible Markup Language),标准通用标记语言的子集 ...
- Spring 中如何自动创建代理(spring中的三种自动代理创建器)
Spring 提供了自动代理机制,可以让容器自动生成代理,从而把开发人员从繁琐的配置中解脱出来 . 具体是使用 BeanPostProcessor 来实现这项功能. 这三种自动代理创建器 为:Bean ...
- 创建用户的方法 3种mysql创建方法
mysql创建用户的方法分成三种:INSERT USER表的方法.CREATE USER的方法.GRANT的方法. 一.账号名称的构成方式 账号的组成方式:用户名+主机(所以可以出现重复的用户 ...
- 创建多线程程序的第一种方式_创建Thread类的子类
创建多线程程序的第一种方式:创建Thread类的子类java.lang.Thread类:是描述线程的类,我们想要实现多线程程序,就必须继承Thread类 实现步骤: 1.创建一个Thread类的子类 ...
随机推荐
- [转帖]麒麟v10上部署TiDBv5.1.2生产环境的最佳实践
https://tidb.net/book/tidb-monthly/2022/2022-07/usercase/tidb-v5-1-2 前言 笔者最近在一个银行项目中做 PoC 测试,由于客户选择 ...
- [转帖]没 K8s 用不了 Chaos Mesh?试试 Chaosd
https://cn.pingcap.com/blog/cannot-use-chaosmesh-without-k8s-then-try-chaosd Chaosd 是什么? 相信大家对 Chaos ...
- [转帖]基于Fuse的用户态文件系统性能优化几点建议
https://zhuanlan.zhihu.com/p/68085075 目前很多文件系统基于Fuse( http://fuse.sourceforge.net/ )开发,在较为深入钻研Fuse实现 ...
- [转帖]Jmeter之界面语言设置
https://developer.aliyun.com/article/1173114#:~:text=%E6%B0%B8%E4%B9%85%E6%80%A7%E8%AE%BE%E7%BD%AE%E ...
- 使用buildx在x86机器上面编译arm64架构的Docker镜像
buildx 多架构编译 安装docker 下载docker 下载buildx 安装架构支持 docker run --privileged --rm tonistiigi/binfmt --inst ...
- [转帖]springcloud nacos配置
配置文件中的nacos配置,discovery和config配置项 版本: <spring.boot.version>2.3.2.RELEASE</spring.boot.versi ...
- js 删除数组中的某一个内容
<script type="text/javascript"> let list=["为","啊发大水","阿斯蒂芬& ...
- 在Linux Ubuntu系统中部署C++环境与Visual Studio Code软件
本文介绍在Linux Ubuntu操作系统下,配置Visual Studio Code软件与C++代码开发环境的方法. 在文章VMware虚拟机部署Linux Ubuntu系统的方法中,我们介 ...
- 【小实验】golang中的字节对齐
作者:张富春(ahfuzhang),转载时请注明作者和引用链接,谢谢! cnblogs博客 zhihu Github 公众号:一本正经的瞎扯 使用golang来调用SIMD指令,发现程序崩溃了: __ ...
- [2] 以逆向的角度来看流程控制语句——switch
[2] 以逆向的角度来看流程控制语句--switch 1. switch分支数小于4 汇编标识: 00401021 mov [ebp-4], ecx 00401024 cmp dword ptr [e ...