多媒体技术13DirectX编程入门_第1页
多媒体技术13DirectX编程入门_第2页
多媒体技术13DirectX编程入门_第3页
多媒体技术13DirectX编程入门_第4页
多媒体技术13DirectX编程入门_第5页
已阅读5页,还剩84页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

编号:时间:2021年x月x日书山有路勤为径,学海无涯苦作舟页码:第页第13章DirectX编程入门DirectX是微软公司为编写游戏和其他高性能多媒体应用程序而开发的一组高级的Windows低层API,它包含了对图(图形、视频和三维动画)、声音(声效与音乐)、输入设备和网络游戏等的支持。本章先概述DirectX的基本内容,然后介绍DirectX的主要组件Direct3D和DirectSound的基本编程方法,并给出若干具体编程实例。13.1DirectX概述本节简单介绍DurectX的发展历史、版本和功能的演化、结构和模块划分。DurectX是Windows的一种多媒体API,它在保持设备无关性的同时,可以让应用程序直接控制多媒体设备,从而能充分利用硬件的功能,因此可获得最高的性能。DurectX自从推出以来,就始终处在快速发展的过程之中。它已经经历了多个版本,其模块和功能也一直在不断地增加和完善。DirectX是一种基于COM的系统,主要由硬件抽象层HAL和硬件模拟层HEL所构成。DurectX被分成若干个组件模块,涵盖了多媒体应用的方方面面。而且这些组件的数目、名称和功能,也是随着其版本的演化而有所增减、改变和加强。13.1.1历史微软公司于1990年5月推出的Windows3.0大获成功,它是一种与设备无关的具有图形用户界面(GUI)的操作系统。后来又于1992年3月推出Windows3.1,提供了对多媒体的支持。不过Windows的与设备无关的设计思想,虽然使得Windows向程序员提供了一个独立于硬件的软件开发优秀平台,但它不让应用程序直接操作显卡和声卡等多媒体硬件,这样就降低了多媒体应用程序(特别是计算机游戏)的运行效率,例如限制了动画的帧率、不提供混音功能等。所以当时的Windows并不是一个可以开发和运行高效多媒体程序(如3D游戏)的理想环境,逼迫PC游戏开发商只好绕开Windows而仍旧开发DOS下的游戏。为了改变这种难堪的局面,促使游戏界放弃DOS而使用Windows,微软需要在设备无关性与高性能之间取得某种平衡,决定为Windows添加一种高性能的动画机制(以及后来的输入与音响等),因此于1995年推出了GameSDK,后来改名为DirectX。其中的Direct指可以直接访问多媒体硬件;X指它的不同组成部分,如Direct3D、DirectSound、DirectInput和DirectPlay等。13.1.2版本与功能因为DirectX必须支持多媒体设备的最新技术和功能,而多媒体硬件(尤其是显卡[的3D性能])和技术始终处在高速发展过程中,所以DirectX的技术和版本也同样在不断地发展和演变,其中发展最快的是3D接口部分。下面列出DirectX的主要版本的发布时间、引入的新模块和特性:1.0——1995年9月30日:DirectDraw、DirectSound、DirectInput、DirectPlay、DirectSetup;2.0——1996年6月5日:引入Direct3D(次版本有2.0a);3.0——1996年9月15日:支持MMX、为DirectSound补充DirectSound3DAPI(次版本有3.0a);4.0——无此版本号;5.0——1997年7月16日:有许多改进,如受力反馈控制器、多显示器支持、新的游戏控制面板、用户界面的全面改进等(次版本有5.1和5.2);6.0——1998年8月7日:添加新的3D特性(如添加DXUT框架)、支持AMD公司的3DNow!技术、性能较5.0有提高。在1999年2月3日推出的6.1版中,添加了DirectMusic模块;7.0——1999年9月22日:改进3D图形和声音、性能更快,为Direct3DAPI引入硬件传送、光照和纹理压缩、以及硬件加速,引入D3DX工具库。使用Creative公司的EAX技术改进3D声音的算法(次版本有7.0a和7.1);8.0——2000年9月30日:将DirectDraw与Direct3D完全集成在一起、其中Direct3D的性能有了本质上的飞跃(引入顶点/像素shader[着色引擎/光照模型]、支持硬件点精灵和三维体纹理),将DirectMusic与DirectSound更紧密地集成在一起构成DirectXAudio,更新了DirectInput与DirectPlay,添加了DirectShow、抛弃了其余的DirectXMedia模块。2001年11月11日推出的8.1版,被集成在WindowsXP中销售,该版本添加了从DirectShow分离出的DMO(DirectXMediaObjects媒体对象)组件模块。它还支持许多新的图形特性,如像素着色引擎的1.2~1.4版、动态/高分辨率纹理、新3D扩展方法等(次版本有8.0a、8.1、8.1a和8.1b);9.0——2002年12月24日:添加许多新特性到DirectXGraphics和DirectShow中,例如将DirectDraw的功能并入到Direct3D之中,支持顶点和像素着色引擎的新版本2.0和3.0,引入裁剪测试、位移贴图和多元纹理,支持128位浮点着色精度和根据显示器自动调整γ值等。也添加若干新特性到DirectInput、DirectPlay、DirectSound和DirectMusic中。(次版本有9.0a、9.0b和9.0c)。DirectX的最后一个以数字和字母命名的版本是2004年8月9日推出的9.0c,后来又于2004年10月、2005年的2/4/6/8/10月分别推出了它的多个升级版。从2005年12月推出的DirectX开始,其版本的命名发生了变化:主版本号改为DX,次版本改为发布的年月。一般是每两个月推出一个新版本,因此也叫做DirectX9.0c的双月更新(bimonthlyupdates)。当前最新版本为2006年10月11日推出的DXOctober2006。它们都包含了(于2002年推出的专为.NET框架设计的)托管(Managed)DirectX,将原来DirectX多个分离的COM模块集成到了一个容易使用的单一CLR文件之中。10——?:DirectX不会有第10版了,因为微软公司已将DirectX的功能集成进其新一代操作系统WindowsVista中,而不再将其作为一个额外的模块了。但是会有Direct3D10,已于2006年12月13日随Direct3DSDK的December2006版一起发布,并被嵌入到WindowsVista中。另外,作为学生和业余爱好者的DirectX替代产品,微软公司于2004年3月24日宣布了用于托管运行环境下计算机游戏的设计、开发和管理的框架和工具集XNA,并于2006年12月11日推出了XNAFrameworkRedistributable和XNAGameStudioExpress的1.0版,可用于Windows和Xbox360游戏的开发。WindowsAPI应用程序WindowsAPI子系统(GDI、MMAPI、MCI、...)Windows驱动程序接口DirectXWindowsAPI应用程序WindowsAPI子系统(GDI、MMAPI、MCI、...)Windows驱动程序接口DirectXHELHALPC硬件子系统DirectX图13-1DirectX子系统DirectX是一种基于COM(ComponentObjectModel,组件对象模型)的系统,它既不属于驱动程序层,也不属于应用层。DirectX的主要设计目标是在提供某种设备独立性的同时获取高速度,为此微软公司为DirectX设计了如图13-1所示的体系结构。其中:图13-1DirectX子系统HAL=HardwareAbstractLayer(硬件抽象层)——负责检测本机的硬件功能,并以一种独立于设备的方式提供这些功能;HEL=HardwareEmulationLayer(硬件模拟层)——负责提供DirectX功能中本机硬件不支持部分的模拟实现。但是从8.0版起,DirectX就不再提供硬件模拟层HEL了,需要开发商、第三方或自己来编写一个PSD(PluggableSoftwareDevice可插式软件设备)连到DirectX提供的HEL接口上,称之为参考设备。但是现在很少有这样的PSD可用,因此新版本的DirectX是严重依赖于硬件的。13.1.4组成DirectX由多个(COM组件)模块组成,而且随着版本的演化,这些模块也在不断地增减、合并和改变。最新的DirectX组件的模块构成如图13-2所示,括号中的数字为该模块被首次引进(或移出)的版本号。下面是DirectX的主要组成模块的简单介绍:DirectXGraphics(图形)——包括DirectDraw和Direct3D:DirectDraw(绘制)——二维图形绘制(高速位图传送/视频与2D动画)。从9.0版起,DirectDraw已被集成到了Direct3D之中。Direct3D(三维)——三维图形绘制。分成保留(retained)和立即(immediate)两种模式(mode):保留模式是一种高层API,建立在立即模式之上,使用起来方便容易,但是效率不高,适合于初学者;立即模式则是一种底层API,使用复杂,但是其效率比保留模式高得多。大多数DirectX应用程序,特别是计算机游戏,都是采用立即模式进行开发。自从6.0版以来,保留模式API的发展停滞不前,而立即模式API的发展却日新月异。不论是保留模式还是立即模式,Direct3D都是建立在DirectDraw之上的。从9.0版起,Direct3D包含了DirectDraw,它像OpenGL一样也具有二维图形绘制的功能。Direct3D的下一个版本为Durect3D10,为WindowsVista的一个有机组成部分。D3DX(Direct3D扩展)——为Direct3D服务的实用工具库,执行公共的数学计算和一些复杂的任务,包含若干简化3D模型使用的类,如粒子系统(particlesystem)。D3DX由动态链接库(DLL)提供。DXUT(编程框架)——建立在Direct3DAPI之上的样例框架,也叫通用文件框架,可以帮助程序员减少在繁琐的平凡工作(如创建窗口、创建设备、处理Windows消息和设备事件等)上所花的时间。DirectXDirectXDirectXGraphics(8.0)DirectDraw(1.0)Direct3D(2.0)DirectXAudio(8.0)DirectSound(1.0)DirectMusic(6.1)DirectSound3D(3.0)DirectInput(1.0)DirectPlay(1.0)DirectSetup(1.0)DirectXMedia(5.0)DirectShow(5.0)DirectAnimation(5.0)DirectX视频加速(5.0)Direct3D保留模式(5.0)DirectXTransform(5.0)并入(9.0)移入平台SDK(9.0c2005.4)建议用WinSocket和WinFirewallAPI代替(9.0c)并入(8.0)移入WindowsMediaSDK(8.0)XInput(9.0c2005.10)XboxLive(Vista)MediaFoundation(Vista)XACT(9.0c2006.2)XNA(Xbox/Vista)DirectXMediaObjects(8.1)分出(8.1)并入(6.0)Direct3D立即模式(2.0)D3DX(7.0)/DXUT(6.0)图13-2DirectX的组成模块DirectXAudio(音频)——包括DirectSound和DirectMusic:DirectSound(声音)——主要针对波形音频,底层接口。可用于开发播放和捕捉波形音频的高性能立体与三维(DirectSound3D)音频应用程序。在下一代DirectX中,DirectSound的功能将由XACT(MicrosoftCross-PlatformAudioCreationTool微软跨平台音频生成工具)来代替。DirectMusic(音乐)——主要针对MIDI音乐,高层接口。为基于波形、MIDI声音或DirectMusic生成器所创造的动态内容之音乐和非音乐声道提供一个完整的解决方案。XACT(游戏音频)——XACT(MicrosoftCross-PlatformAudioCreationTool,微软跨平台音频生成工具),是一种多人合作的音频设计工具和相关API,用于游戏的动态音频开发。DirectInput(输入)——提供对各种输入设备的支持,包括对受力反馈(force-feedback)技术的全面支持。在下一代DirectX中,DirectInput将被XInput代替。DirectPlay(游戏)——提供对多人网络游戏的支持。在最新的DirectX版本中,微软公司反对(deprecate)使用DirectPlay,而建议改用WindowsSockets和WindowsFirewallAPI来代替。在下一代DirectX中,DirectPlay可能会被XboxLive代替。DirectSetup(安装)——提供DirectX组件的一次性调用安装的一个简单API(自动安装DirectX驱动程序)。DirectShow(展示)——提供多媒体(音视频)流的高质量捕捉和重放。在8.0版之前,DirectShow是DirectXMedia的一个组成模块。到8.0版时,因为DirectXSDK抛弃了DirectXMedia,所以才将DirectShow集成到了DirectX之中。在DirectX9.0c的2005年4月升级版中,DirectShow又被移出DirectX,放入微软公司的平台SDK之中。DirectXMediaObjects(媒体对象DMO)——基于COM的多媒体和数据流组件,支持音视频的编解码器和特效。是在DirectX的8.1版时,从DirectShow分出的,其功能类似于DirectShow的过滤器。DirectXMedia(媒体)——是一个用于流媒体应用的外部API集合。在DirectX6.0之前,DirectXMediaSDK和DirectXSDK是两个分离的SDK。在6.0版时DirectXMediaSDK被集成到DirectXSDK之中。DirectXMedia的运行模块,被集成到Windows和IE之中。到了8.0版时,DirectXMedia又被DirectXSDK抛弃(其核心模块DirectShow被集成到了DirectX之中),其功能被随Windows2000Server推出的WindowsMediaSDK所代替。DirectXTransform(变换)——用于产生二、三维图形的各种效果,如α混色和表面弯曲等。DirectAnimation(动画)——集成多种媒体类型来创建复杂动画,并可用作网页内容。DirectXVideoAcceleration(视频加速DXVA)——利用硬件加速二维视频的解码操作。Direct3DRetainedMode(保留模式)——Direct3D的保留模式是一种高层API,建立在Direct3D立即模式之上,使用起来方便容易,但是效率不高,适合于初学者。DirectShow(展示)——支持音视频流的高质量采集和重放。13.1.5编程准备为了用VC编写DirectX应用程序,必须先下载并安装DirectXSDK,并进行必要的头/库文件路径和链接库的设置。下面以WindowsXP中文版环境下的VisualC++2005中文版和DirectX9.0cAugust2006SDK为例,介绍进行具体的DirectX编程之前,所需做的必要准备工作。下载并安装DirectXSDK可以从微软公司的官方网站(/windows/directx/)下载最新的DirectXSDK,如dxsdk_dec2006.exe(448MB)。安装完成后,会在安装目录(缺省为“C:\ProgramFiles\MicrosoftDirectXSDK((December2006)”)中生成DeveloperRuntime、Documentation、Include、Lib、Redist、Samples和Utilities等多个子目录。安装时还会为Windows操作系统生成名为“MicrosoftDirectXSDK((December2006)”的程序组,包含多个子程序组和程序。安装程序会将DirectXSDK的帮助文档,也安装到VisualStudio2005的帮助系统内,位于其“目录/DirectXSDK((December2006)”目录之中,包含“DirectXSDK((December2006)C++”和“DirectXSDK((December2006)Managed”两个帮助子目录。设置包含和库路径在VisualStudio2005中文版的IDE中,选“工具/选项”菜单项,打开“选项”对话框(参见图13-5)。图13-5VisualStudio2005的“选项”对话框再选该对话框左边的“项目和解决方案/VC++目录”路径,在右边的“显示以下内容的目录”栏的下拉式列表框中,选“包含文件”项。按该栏下面的“新行”钮,则在其下方的显示栏中会出现新行,再按新行右端的带省略号的浏览钮,在弹出的“选择目录”对话框中,选择DirectXSDK的Include目录所在的路径“C:\ProgramFiles\MicrosoftDirectXSDK(August2006)\Include”,然后按“打开”关闭“选择目录”对话框。结果参见图13-6。图13-6设置DirectX的“包含文件”的路径可类似选择“库文件”项,添加库文件路径“C:\ProgramFiles\MicrosoftDirectXSDK(August2006)\Lib\x86”,结果参见图13-7。最后,按“确定”钮,关闭“选项”对话框。图13-7设置DirectX的“库文件”的路径注意,对DirectX的包含路径和库路径的设置,对所有项目都有效。设置链接库先创建一个DirectX应用程序的MFC单文档项目(如DxTest),再在VS05的IDE中,选“项目/属性”,打开“DxTest属性页”对话框。在左上角的“配置”栏中,选中“所有配置”项;再选左边的路径“配置属性/链接器/输入”,在右边的“附加依赖项”栏中,添加d3d9.libd3dx9.libd3dxof.libdsound.libdxguid.libwinmm.lib等链接库(在多个库文件之间,用空格分隔)。具体添加哪些DirectX库,与具体应用程序所使用的DirectX模块有关,你也可以查看DirectX的库目录。最后,按“应用”钮和“确定”钮,关闭属性页对话框。参见图13-8。图13-8设置DirectX的链接库注意,对DirectX链接库的设置,只对VC05中当前打开的单个项目有效。在安装了DirectXSDK,并设置好文件路径和链接库后,就可以开始编写具体的DirectX应用程序了。DirectX的组件众多、功能强大、编程复杂,完整的介绍需要几本大部头的专著才行,本书只准备简单介绍DirectX的最主要模块——Direct3D和DirectSound编程的最基本内容。13.2Direct3D编程简介Direct3D(直接三维)是DirectX的核心模块,新版本的Direct3D中还包含原来DirectDraw模块的2D功能。因此,现在的Direct3D是DirectXGraphics的唯一模块,具有DirectX(二、三维)图形的全部功能。13.2.1流水线与设备Direct3D用图形流水线(graphicspipeline)来处理和渲染场景(renderscene),而Direct3D设备(device)是执行变换(transformation)和光照(lighting)等操作的渲染部件。Direct3D图形流水线可通过Direct3D图形流水线来充分利用硬件性能,以提供高效处理和绘制Direct3D场景到显示器的能力。图13-9为流水线(pipeline,管线/管道/流程)的组成模块框图。顶点数据顶点数据图元数据镶嵌顶点处理几何处理像素处理像素绘制纹理采样器纹理表面图13-9Direct3D图形流水线Direct3D设备图13-10Direct3D设备架构变换模块光照模块光栅化器Direct3D设备架构Direct3D设备(device)是Direct3D的渲染部件,它封装和存储渲染状态。另外,它还执行变换和光照等操作,并且光栅化图像到表面(如屏幕)。在结构上,Direct3D设备包含变换模块(transformationmodule)、光照模块(lightingmodule)和光栅化器(rasteriz图13-10Direct3D设备架构变换模块光照模块光栅化器Direct3D设备架构当前,Direct3D有两种主要的设备类型:HAL设备(haldevice)——具有硬件加速的光栅化(rasterization),可同时使用硬件和软件的顶点处理进行着色(shading)。参考设备(referencedevice)——由软件驱动程序提供,现在主要用于性能测试。创建Direct3D对象创建Direct3D设备对象创建Direct3D对象创建Direct3D设备对象设置渲染状态定义顶点格式创建顶点缓冲区锁定顶点缓冲区解锁顶点缓冲区开始场景结束场景构造几何对象设置材质和光照或纹理设置设备的流源和顶点格式绘制图元展现场景进行世界、观察和投影矩阵变换清除对象清除显示表面13.2.2基本编程过程Direct3D的基本编程过程如图13-11所示。下面各小节依次介绍Direct3D编程的基本步骤和方法。13.2.3创建和初始化对象为了使用Direct3D,你必须首先创建一个应用窗口,然后再创建和初始化Direct3D对象。利用这些对象所实现的COM接口来操作它们,以创建绘制场景所需的其它对象。如果进行MFC编程,则可以省略创建窗口这一步,而直接使用视图类所代表的客户区窗口。图13-11Direct3D编程的基本过程下面介绍的是初始化Direct3D的内容,包括创建Direct3D对象、创建Direct3D图13-11Direct3D编程的基本过程创建Direct3D对象可使用全局函数Direct3DCreate9来创建Direct3D接口对象:IDirect3D9*Direct3DCreate9(//成功返回指向IDirect3D9接口的指针,失败返回NULLUINTSDKVersion//必须为D3D_SDK_VERSION);例如:IDirect3D9*g_pD3D=Direct3DCreate9(D3D_SDK_VERSION);创建Direct3D设备可使用IDirect3D9接口的CreateDevice方法来创建设备(尾参数的返回值):HRESULTCreateDevice(//成功返回D3D_OK(=0)UINTAdapter,//显卡(displayadapter)序号,D3DADAPTER_DEFAULT为主显卡D3DDEVTYPEDeviceType,//设备的枚举类型,一般取为D3DDEVTYPE_HALHWNDhFocusWindow,//焦点窗口句柄,可取为this->m_hWndDWORDBehaviorFlags,//控制设备的创建行为之选项组合,可以采用硬件或软件//的顶点处理,如D3DCREATE_SOFTWARE_VERTEXPROCESSINGD3DPRESENT_PARAMETERS*pPresentationParameters,//指向展现参数结构//D3DPRESENT_PARAMETERS的指针IDirect3DDevice9**ppReturnedDeviceInterface//代表被创建设备的//IDirect3DDevice9返回接口的指针地址);其中,展现参数结构D3DPRESENT_PARAMETERS的定义为:typedefstructD3DPRESENT_PARAMETERS{//展现参数结构UINTBackBufferWidth,BackBufferHeight;//后台缓冲区的宽高(以像素为单位),//对窗口模式可取为0,对全屏模式则必须与当前显卡枚举模式的一致D3DFORMATBackBufferFormat;//后台缓冲区的格式,可取为//D3DFMT_UNKNOWN(=0)UINTBackBufferCount;//后台缓冲区计数,可取为0~3,取0时等价于1D3DMULTISAMPLE_TYPEMultiSampleType;//多样本类型,一般取为 //D3DMULTISAMPLE_NONE(=0)DWORDMultiSampleQuality;//多样本质量水平,一般取0D3DSWAPEFFECTSwapEffect;//交换效果,可取为 //D3DSWAPEFFECT_DISCARD(=1)、D3DSWAPEFFECT_FLIP(=2) //和D3DSWAPEFFECT_COPY(=3)等枚举值HWNDhDeviceWindow;//设备窗口的句柄,对窗口模式可取为NULL(=0)BOOLWindowed;//应用程序在窗口/全屏中运行时取TRUE/FALSEBOOLEnableAutoDepthStencil;//允许自动深度模板,为TRUE则由Direct3D//来管理应用程序的深度缓冲区D3DFORMATAutoDepthStencilFormat;//自动深度模板格式,可取//D3DFMT_D16、D3DFMT_D24S8和D3DFMT_D32等枚举值DWORDFlags;//表现标志D3DPRESENTFLAG常数之一,可取为0UINTFullScreen_RefreshRateInHz;//全屏时的屏幕刷新率,对窗口模式必须为0UINTPresentationInterval;//前后台缓冲区交换的最大速率,可取为//D3DPRESENT_INTERVAL_DEFAULT(=0)}D3DPRESENT_PARAMETERS;例如://设置创建D3D设备用的表现结构D3DPRESENT_PARAMETERSd3dpp;//定义表现结构变量ZeroMemory(&d3dpp,sizeof(d3dpp));//内存清零d3dpp.Windowed=TRUE;//窗口模式d3dpp.SwapEffect=D3DSWAPEFFECT_DISCARD;//放弃交换效果d3dpp.BackBufferFormat=D3DFMT_UNKNOWN;//未知格式d3dpp.EnableAutoDepthStencil=TRUE;//允许自动深度模板d3dpp.AutoDepthStencilFormat=D3DFMT_D16;//16位深度缓冲LPDIRECT3DDEVICE9g_pd3dDevice;//定义D3D设备接口的指针//创建D3D设备对象(获取D3D设备接口的指针)g_pD3D->CreateDevice(D3DADAPTER_DEFAULT,D3DDEVTYPE_HAL, this->m_hWnd,D3DCREATE_SOFTWARE_VERTEXPROCESSING, &d3dpp,&g_pd3dDevice);设置设备的渲染状态利用IDirect3D9接口的CreateDevice方法所返回的设备接口IDirect3DDevice9的指针,可以调用该接口的设置渲染(render着色)状态方法SetRenderState,来初始化设备:HRESULTSetRenderState(//成功返回D3D_OK(=0)D3DRENDERSTATETYPEState,//设备状态DWORDValue//设置值);其中,设备状态State,可取D3DRENDERSTATETYPE枚举的任意值,如D3DRS_ZENABLE(允许Z缓冲)、D3DRS_FILLMODE(填充模式)、D3DRS_SHADEMODE(阴影模式)、D3DRS_ALPHATESTENABLE(允许α测试)、D3DRS_CULLMODE(剔除模式)、D3DRS_FOGENABLE(允许雾化)、D3DRS_LIGHTING(光照)、D3DRS_DITHERENABLE(允许抖动)、……。例如:g_pd3dDevice->SetRenderState(D3DRS_CULLMODE,D3DCULL_NONE);//关闭背面剔除g_pd3dDevice->SetRenderState(D3DRS_ZENABLE,TRUE);//允许Z缓冲g_pd3dDevice->SetRenderState(D3DRS_LIGHTING,FALSE);//关闭光照13.2.4创建场景三维场景是由若干物体(几何对象)构成的,复杂的几何对象由多个简单的图元(点、线、三角形和多边形等)所组成,而图元(primitive)又是顶点(vertex)的集合。图13-123D图元表面的三角网格3D图元一般是一个多面体,通常用其表面的三角网格来表示,参见图13-12。所以最基本的图元是三角形和顶点。图13-123D图元表面的三角网格创建场景中的几何对象,等价于建立表示该几何体的顶点集合。因此,必须先定义自己的顶点结构并创建顶点缓冲区,然后在锁定顶点缓冲区后,再通过给顶点缓冲区中的各顶点结构赋值来构造几何对象,最后解锁顶点缓冲区。定义顶点结构Direct3D使用一种FVF(FlexibleVertexFormat可变顶点格式)结构来定义顶点,以满足用户的不同需要。在FVF结构CUSTOMVERTEX中,可以包含描述顶点的位置、RHW(reciprocalhomogeneousw倒数齐次w,表示已变换顶点位置的齐次坐标w分量)、法向、大小和(漫射、镜面反射)颜色等字段,具体内容由用户根据需要自己来确定,但是各字段之间的相对顺序不能改变。其中,顶点的位置和法向等字段,一般为三维点向量,可以用Direct3D的扩展三维向量结构D3DXVECTOR3来表示:typedefstructD3DXVECTOR3{FLOATx;FLOATy;FLOATz;}D3DXVECTOR3;其中的FLOAT为float的typedef类型,定义在windef.h头文件中。而颜色一般采用DWORD的typedef定义类型D3DCOLOR。例如: structCUSTOMVERTEX{//含位置、法向量和颜色的自定义顶点结构 D3DXVECTOR3position;//未变换顶点的3D位置 D3DXVECTOR3normal;//顶点的表面法向量 D3DCOLORcolor;//颜色 };或:structCUSTOMVERTEX{//含位置、颜色和纹理坐标的自定义顶点结构D3DXVECTOR3position;//未变换顶点的3D位置D3DCOLORcolor;//颜色FLOATtu,tv;//纹理坐标};或:structCUSTOMVERTEX{//含位置齐次坐标和颜色的自定义顶点结构 FLOATx,y,z,rhw;//已变换顶点的3D位置 DWORDcolor;//颜色 };用户在定义了自己的顶点结构类型后,还需要定义一个对应的(宏)常量,来描述该结构的字段内容。该(宏)常量由若干表示顶点格式的标志位符号常量(参见表13-1)的位或组合而成。表13-1顶点数据格式标志符号常量值数据类型描述D3DFVF_XYZ0x002float,float,float未转换的顶点坐标D3DFVF_XYZRHW0x004float,float,float,float已转换的顶点坐标D3DFVF_XYZB1~50x006/8/a/c/e1-3个float含权重i的顶点坐标D3DFVF_XYZW0x4002float,float,float,float已转换和裁剪的顶点坐标D3DFVF_NORMAL0x010float,float,float顶点的法线D3DFVF_PSIZE0x020float点大小D3DFVF_DIFFUSE0x040DWORD(ARGB)漫射颜色D3DFVF_SPECULAR0x080DWORD(ARGB)镜面反射颜色D3DFVF_TEX0~80x0~8001-4个floati重纹理映射例如:#defineD3DFVF_CUSTOMVERTEX(D3DFVF_XYZ|D3DFVF_NORMAL|D3DFVF_DIFFUSE)或:#defineD3DFVF_CUSTOMVERTEX(D3DFVF_XYZ|D3DFVF_DIFFUSE|D3DFVF_TEX1)或:constDWORDFVF=(D3DFVF_XYZRHW|D3DFVF_DIFFUSE);创建顶点缓冲区在定义了顶点结构后,就可以创建顶点缓冲区了,这可以由IDirect3DDevice9接口的CreateVertexBuffer方法来完成:HRESULTCreateVertexBuffer(//成功返回D3D_OK(=0)UINTLength,//缓冲区的字节大小,一般为n*sizeof(CUSTOMVERTEX)DWORDUsage,//缓冲区用法的附加属性标志,一般为0DWORDFVF,//顶点结构格式常量D3DPOOLPool,//缓冲区所在的内存池类型(D3DPOOL枚举值)IDirect3DVertexBuffer9**ppVertexBuffer,//返回被创建的顶点缓冲区指针HANDLE*pSharedHandle//保留,设为NULL);其中,内存池类型D3DPOOL枚举的定义为:typedefenumD3DPOOL{//内存池类型枚举D3DPOOL_DEFAULT=0,//AGP存储器或显存D3DPOOL_MANAGED=1,//AGP存储器或显存,且在系统内存中还有一份拷贝D3DPOOL_SYSTEMMEM=2,//系统内存D3DPOOL_SCRATCH=3,//系统内存中的临时池D3DPOOL_FORCE_DWORD=0x7fffffff//未使用(强制该枚举被编译成32位)}D3DPOOL;例如:g_pd3dDevice->CreateVertexBuffer(100*sizeof(CUSTOMVERTEX),0,D3DFVF_CUSTOMVERTEX,D3DPOOL_DEFAULT,&g_pVB,NULL);或: g_pd3dDevice->CreateVertexBuffer(3*sizeof(CUSTOMVERTEX),0,FVF,D3DPOOL_MANAGED,&g_pVB,NULL);构造点集创建三维场景中的几何对象,需要计算和构造描述该几何对象的点集。具体做法是:先定义一个顶点指针(用于操作顶点数组);再调用Lock方法来获取顶点缓冲区的首地址(赋值给顶点指针),并锁定该区域仅供当前操作使用;然后利用该顶点指针,将计算的顶点结构值填入顶点缓冲区,从而构造出几何对象;最后调用Unlock方法解锁顶点缓冲区。IDirect3DVertexBuffer9接口的Lock和Unlock方法的定义为:HRESULTLock(//成功返回D3D_OK(=0)UINTOffsetToLock,//锁定的偏移地址UINTSizeToLock,//锁定的字节数VOID**ppbData,//返回被锁定的缓冲区头的指针DWORDFlags//锁定方式标志,可为0或下列符号常量的组合: //D3DLOCK_DISCARD、D3DLOCK_NO_DIRTY_UPDATE、//D3DLOCK_NOSYSLOCK、D3DLOCK_READONLY、//D3DLOCK_NOOVERWRITE);HRESULTUnlock();//成功返回D3D_OK(=0)例如:CUSTOMVERTEX*pVertices;g_pVB->Lock(0,0,(void**)&pVertices,0);……//给顶点缓冲区中的各顶点结构赋值(构造几何对象的点集)g_pVB->Unlock();13.2.5矩阵变换描述单个物体(3D几何对象)一般采用的是本地相对坐标。因此,在渲染之前,需要将它们都转换为描述场景的统一世界空间(worldspace)坐标,这对应于世界矩阵变换。为了将三维场景显示在二维屏幕上,还需要选择一个观察点(眼睛/摄像机)和观察角度(方向/坐标)(对应于观察坐标矩阵变换),并将3D场景投影到一个2D平面(屏幕)上(对应于投影矩阵变换),还要将超出屏幕的部分去掉(裁剪),也可以将场景投射到屏幕的某个矩形区域中(视口缩放)。参见图13-13。世界世界变换观察变换投影变换裁剪与视口缩放顶点光栅器变换引擎图13-13Direct3D的变换引擎下面依次对这些变换加以介绍,这需要首先介绍Direct3D中的矩阵定义和变换方法。矩阵与变换在Direct3D中,定义了矩阵(matrix)结构D3DXMATRIX:typedefstructD3DXMATRIX{//矩阵结构struct{//注意,C/C++的变量名可以下划线开头(但不能以数字开头)FLOAT_11;FLOAT_12;FLOAT_13;FLOAT_14;FLOAT_21;FLOAT_22;FLOAT_23;FLOAT_24;FLOAT_31;FLOAT_32;FLOAT_33;FLOAT_34;FLOAT_41;FLOAT_42;FLOAT_43;FLOAT_44;};}D3DXMATRIX;对应于4*4的浮点矩阵:在Direct3D中,还定义了一个对IntelP4CPU运算进行了优化的16字节对齐的矩阵结构(从D3DXMATRIX派生的C++结构对象):typedefstruct_D3DXMATRIXA16:publicD3DXMATRIX{//16字节对齐矩阵结构_D3DXMATRIXA16();_D3DXMATRIXA16(CONSTFLOAT*f);_D3DXMATRIXA16(CONSTD3DMATRIX&m);_D3DXMATRIXA16(FLOAT_11,FLOAT_12,FLOAT_13,FLOAT_14,FLOAT_21,FLOAT_22,FLOAT_23,FLOAT_24,FLOAT_31,FLOAT_32,FLOAT_33,FLOAT_34,FLOAT_41,FLOAT_42,FLOAT_43,FLOAT_44);void*operatornew(size_ts);void*operatornew[](size_ts);voidoperatordelete(void*p);voidoperatordelete[](void*p);struct_D3DXMATRIXA16&operator=(CONSTD3DXMATRIX&rhs);}_D3DXMATRIXA16;typedefD3DX_ALIGN16_D3DXMATRIXA16D3DXMATRIXA16;Direct3D还提供了若干全局矩阵函数,如:D3DXMATRIX*D3DXMatrixIdentity(D3DXMATRIX*pOut);//创建单位矩阵FLOATD3DXMatrixDeterminant(CONSTD3DXMATRIX*pM);//返回矩阵的行列式值D3DXMATRIX*D3DXMatrixInverse(//计算逆矩阵D3DXMATRIX*pOut,//结果矩阵FLOAT*pDeterminant,//行列式值,可置为NULLCONSTD3DXMATRIX*pM//原矩阵);D3DXMATRIX*D3DXMatrixMultiply(//两矩阵相乘D3DXMATRIX*pOut,//结果矩阵CONSTD3DXMATRIX*pM1,//矩阵1CONSTD3DXMATRIX*pM2//矩阵2);矩阵变换(transform)的实施,可采用IDirect3DDevice9接口提供的SetTransform方法:HRESULTSetTransform(//成功返回D3D_OK(=0)D3DTRANSFORMSTATETYPEState,//变换类型状态值CONSTD3DMATRIX*pMatrix//变换矩阵);其中State的取值可为D3DTRANSFORMSTATETYPE枚举类型或D3DTS_WORLDMATRIX宏的值。如:D3DTS_VIEW(=2,观察变换)、D3DTS_PROJECTION(=3,投影变换)、D3DTS_TEXTURE0~7(=16~23,纹理变换)、D3DTS_WORLD(=256,世界变换)等。例如:D3DXMATRIXA16matWorld;//定义矩阵结构对象D3DXMatrixIdentity(&matWorld);//变成单位矩阵……//对matWorld进行其他矩阵变换g_pd3dDevice->SetTransform(D3DTS_WORLD,&matWorld);//实施变换世界变换图13-14世界变换一般用每个物体各自的本地坐标来描述所对应的3D几何对象,而用统一的世界坐标来描述整个场景(参见图13-14),渲染之前需要将顶点从本地坐标系转换到世界坐标系。称这种从本地坐标到世界坐标的转换为世界变换(worldtransform),世界变换包含平移(translation)、旋转(rotation)和缩放(scaling)等三种具体变换类型,它们都可用对应的矩阵变换来表示。图13-14世界变换下面是Direct3D提供的若干世界矩阵变换的全局函数:D3DXMATRIX*D3DXMatrixTranslation(//平移变换D3DXMATRIX*pOut,//原/结果矩阵FLOATx,//x偏移量FLOATy,//y偏移量FLOATz//z偏移量);D3DXMATRIX*D3DXMatrixRotationX[Y/Z](//(绕x[y/z]轴的)旋转变换D3DXMATRIX*pOut,//原/结果矩阵FLOATAngle//旋转角度(弧度单位));D3DXMATRIX*D3DXMatrixScaling(//缩放变换D3DXMATRIX*pOut,//原/结果矩阵FLOATsx,//x方向的比例因子FLOATsy,//y方向的比例因子FLOATsz//z方向的比例因子);可以通过这些函数,获得所需要的各种变换矩阵。最后,还须使用D3DTS_WORLD状态值,来调用IDirect3DDevice9接口的SetTransform方法,以实施最终矩阵所对应的世界变换。例如:D3DXMatrixTranslation(&matWorld,m_xPos,m_yPos,m_zPos);//平移D3DXMatrixRotationX(&matWorld,m_fPitch);//绕x轴旋转g_pd3dDevice->SetTransform(D3DTS_WORLD,&matWorld);//实施世界变换观察变换观察变换(viewtransform),可在世界坐标系(xw,yw,zw)中设置和改变观察者的位置和方向,将世界空间中的顶点转换到摄影空间(cameraspace)(xe,ye,ze),参见图13-15。图13-15观察变换在Direct3D中,观察矩阵由全局助手函数D3DXMatrixLookAtLH(Left-Handed,左手系)和D3DXMatrixLookAtRH(Right-Handed,右手系)来创建:图13-15观察变换D3DXMATRIX*D3DXMatrixLookAtLH(//创建左手系观察矩阵(右手系:LH→RH)D3DXMATRIX*pOut,//结果矩阵CONSTD3DXVECTOR3*pEye,//眼睛位置点CONSTD3DXVECTOR3*pAt,//观察目标点(方向),通常取为原点(0,0,0)CONSTD3DXVECTOR3*pUp//观察上方点,通常取为y轴正向(0,1,0));可以通过这两个函数之一(一般采用左手系的观察矩阵函数),来获得所需要的观察变换矩阵。最后,也是需要使用D3DTS_VIEW状态值,来调用IDirect3DDevice9接口的SetTransform方法,以实施矩阵所对应的观察变换。例如:D3DXMATRIXmatView;//定义观察矩阵结构D3DXVECTOR3eye(2,3,3);//设眼睛位置为(2,3,3)D3DXVECTOR3at(0,0,0);//设目标点为原点D3DXVECTOR3up(0,1,0);//设y轴正向为上方D3DXMatrixLookAtLH(&matView,&eye,&at,&up);//获取观察变换矩阵g_pd3dDevice->SetTransform(D3DTS_VIEW,&matView);//实施观察变换投影变换投影变换(projectiontransform)将观察平截头体(frustum,切割物体的两个平面之间的立体部分)转换为一个立方体形状(cuboidshape)。靠近观察点的物体,投影后会显得大一些。参见图13-16。图13-16投影变换与观察平截头体 图13-17观察平截头体的确定观察平截头体由fov(fieldofview,视场/视野)角度和前后剪切面(frontandbackclippingplanes)的(用z坐标指定的)距离来决定,参见图13-17。图13-18投影变换将观察平截头体转换为一个立方体投影矩阵是典型的缩放和透视投影(scaleandperspectiveprojection)变换,它将观察平截头体转换为一个立方体,其原点也从右上角移到了中心。参见图13-18。图13-18投影变换将观察平截头体转换为一个立方体Direct3D提供了下列6个全局函数来创建投影矩阵:创建左手系透视投影矩阵——D3DXMatrixPerspectiveLH;创建右手系透视投影矩阵——D3DXMatrixPerspectiveRH;创建基于视野的左手系透视投影矩阵——D3DXMatrixPerspectiveFovLH;创建基于视野的右手系透视投影矩阵——D3DXMatrixPerspectiveFovRH;创建定制的左手系透视投影矩阵——D3DXMatrixPerspectiveOffCenterLH。创建定制的右手系透视投影矩阵——D3DXMatrixPerspectiveOffCenterRH。其中最常用的是创建基于视野的左手系透视投影矩阵函数:D3DXMATRIX*D3DXMatrixPerspectiveFovLH(//返回结果矩阵D3DXMATRIX*pOut,//结果矩阵FLOATfovY,//视角(弧度值)FLOATAspect,//水平视角与垂直视角的比例FLOATzn,//近观察平面(前剪切面)的Z值(距离)FLOATzf//远观察平面(后剪切面)的Z值(距离));其返回矩阵为:其中:yScale=tan(2/fovY)、xScale=yScale/Aspect与世界变换和观察变换一样,在获得了投影变换矩阵后,也需要使用D3DTS_PROJECTION状态值,来调用IDirect3DDevice9接口的SetTransform方法,以实施该矩阵所对应的投影变换。例如:D3DXMATRIXA16matProj;//定义矩阵结构//设置基于视野的左手系透视投影矩阵(45度视角、水平与垂直视角的比例为1、//Z值从1~100)D3DXMatrixPerspectiveFovLH(&matProj,D3DX_PI/4,1.0f,1.0f,100.0f);g_pd3dDevice->SetTransform(D3DTS_PROJECTION,&matProj);//实施投影变换剪切和窗口缩放视口(viewport)是一个(三维场景被投影到其中的)二维矩形。当视口小于Direct3D的显示表面(如屏幕)时,就需要进行裁剪(clipping)。参见图13-19。在Direct3D中,定义了视口结构:typedefstructD3DVIEWPORT9{//视口结构DWORDX;//视口矩形左上角的x坐标DWORDY;//视口矩形左上角的y坐标DWORDWidth;//视口矩形的宽度DWORDHeight;//视口矩形的高度图13-19显示表面与视口(结构)floatMinZ;//最小深度缓冲值图13-19显示表面与视口(结构)floatMaxZ;//最大深度缓冲值}D3DVIEWPORT9;可以用IDirect3DDevice9接口的SetViewport和GetViewport方法来设置和获取视口:HRESULTSetViewport(CONSTD3DVIEWPORT9*pViewport);//设置视口HRESULTGetViewport(D3DVIEWPORT9*pViewport);//获取视口例如:D3DVIEWPORT9vp(0,0,800,600,0,1);g_pd3dDevice->SetViewport(&vp);13.2.6光照、材质与纹理几何对象只有形状和大小,而真实的物体还有材质、纹理、重量、刚度、弹性等等其他物理特性,我们这里只讨论影响其外观的材质和纹理。当然,任何物体,如果没有光线照射,你是什么也看不见的。所以,场景的最后观看效果,还取决于灯光的设置。下面简单介绍Direct3D中的光照安排、材质设置和纹理使用等的基本内容。光照光照(light灯光)用于照亮三维场景中的物体。Direct3D提供了两种灯光模式:环境光和直接光。环境光(ambientlight)是一种散射的光,没有固定的方向,也不会产生阴影,可以照亮场景的任何地方。例如阴天。图13-20直接光的种类聚光外角φ内角θ光照区方向光点光图13-20直接光的种类聚光外角φ内角θ光照区方向光点光在Direct3D中定义了光结构D3DLIGHT9:typedefstructD3DLIGHT9{光结构D3DLIGHTTYPEType;//光类型D3DCOLORVALUEDiffuse;//光发出的漫射色D3DCOLORVALUESpecular;//光发出的反射色D3DCOLORVALUEAmbient;//光发出的环境色D3DVECTORPosition;//光源位置点,方向光时被忽略D3DVECTORDirection;//光的方向(非0矢量),点光时被忽略floatRange;//范围:光照距离的最大值,必须≤最大浮点值的平方根,方向光时被忽略floatFalloff;//下降:聚光时的内角到外角的光线衰减值(0.0~1.0),一般取为1.0floatAttenuation0;//衰减0:光线强度和距离关系的计算权值0,取值0.0~∞floatAttenuation1;//Direct3D中光强衰减倍数A的计算公式(D为到光源的距离):floatAttenuation2;//floatTheta;//θ:聚光的内角大小floatPhi;//φ:聚光的外角大小}D3DLIGHT9;其中:光类型枚举D3DLIGHTTYPE定义为:typedefenumD3DLIGHTTYPE{//光类型枚举D3DLIGHT_POINT=1,//点光D3DLIGHT_SPOT=2,//聚光D3DLIGHT_DIRECTIONAL=3,//方向光D3DLIGHT_FORCE_DWORD=0x7fffffff,//强制此枚举类型的值为双字}D3DLIGHTTYPE;浮点颜色值结构D3DCOLORVALUE的定义为:(其中各字段的取值范围为0.0~1.0)typedefstructD3DCOLORVALUE{floatr;floatg;floatb;floata;}D3DCOLORVALUE;其中,a为表示透明度的α值。矢量结构D3DVECTOR的定义为:typedefstructD3DVECTOR{floatx,y,z;}D3DVECTOR;在定义并初始化了光结构后,可以利用IDirect3DDevice9接口的SetLight方法,来设置场景的各个灯光:HRESULTSetLight(//成功返回D3D_OKDWORDIndex,//灯光的索引值(下同)CONSTD3DLight9*pLight//灯光的结构);可以对一个场景设置多个灯光,它们用各自的索引值来标识。对同一索引值的再次灯光设置,将会覆盖掉原来已有的设置。还可以利用IDirect3DDevice9接口的GetLight方法,来保存场景的灯光设置:HRESULTGetLight(DWORDIndex,D3DLight9*pLight);注意,Direct3D允许打开和关闭所设置的各个灯光,这可由IDirect3DDevice9接口的LightEnable方法来完成:HRESULTLightEnable(//成功返回D3D_OKDWORDLightIndex,//灯光的索引值BOOLbEnable//TRUE:开,FALSE:关);还可以利用IDirect3DDevice9接口的GetLightEnable方法,来获取场景中的灯光开关情况:HRESULTGetLightEnable(DWORDIndex,BOOL*pEnable/*返回值*/);例如:D3DLight9d3dLight;//定义灯光结构变量ZeroMemory(&D3dLight,sizeof(d3dLight));//初始化为0//设置白色电光d3dLight.Type=D3DLIGHT_POINT;d3dLight.Diffuse.r=1.0f; d3dLight.Diffuse.g=1.0f; d3dLight.Diffuse.b=1.0f;d3dLight.Ambient.r=1.0f; d3dLight.Ambient.g=1.0f; d3dLight.Ambient.b=1.0f;d3dLight.Specular.r=1.0f; d3dLight.Specular.g=1.0f; d3dLight.Specular.b=1.0f;//设置光源位置d3dLight.Position.x=0.0f; d3dLight.Position.y=1000.0f; d3dLight.Position.z=-100.0f;d3dLight.Attenuation0=1.0f;//无衰减d3dLight.Range=1000.0f;//最大距离if(g_pd3dDevice->SetLight(0,&d3dLight)==D3D_OK)//设置灯光g_pd3dDevice->LightEnable(0,TRUE);//打开灯光材质材质(material)是构成物体的材料和质地(如金属、木头、布料、镜子等),它决定了物体表面队光线的反应:如何反射光线,包括如何进行镜面反射和漫反射;在高光部分如何反射光线;是否自己发出光线没有设置材质的物体,不能反射任何光线。因此,即使场景中有光源,物体仍然显示出一片黑暗,你什么也不会看到。所以,只有给场景的物体指定了材质,才会在显示出正确的光照效果来。在Direct3D中,并没有给出一个与自然物体(如木材、钢铁、布料等)对应的材质表,而是定义了一个可以设置物体反光特性的材质结构D3DMATERIAL9:typedefstructD3DMATERIAL9{//材质结构D3DCOLORVALUEDiffuse;//漫反射光线的颜色D3DCOLORVALUEAmbient;//环境反射光线的颜色D3DCOLORVALUESpecular;//(高光部分)镜面反射光线的颜色D3DCOLORVALUEEmissive;//发射光线的颜色(光源)floatPower;//镜面反射光线的强度}D3DMATERIAL9;可以利用IDirect3DDevice9接口的SetMaterial方法来为Direct3D设备设置材质:HRESULTSetMaterial(CONSTD3DMATERIAL9*pMaterial);//成功返回D3D_OK该材质设置对后面所渲染的所有物体都有效。如果希望对不同的物体设置不同的材质,就必须在渲染每个物体前,重新设置Direct3D设备为对应的材质。你还可以利用IDirect3DDevice9接口的GetMaterial方法来获取Direct3D设备的当前材质设置:HRESULTGetMaterial(D3DMATERIAL9*pMaterial/*返回材质设置*/);例如:D3DMATERIAL9mat;//定义材质结构变量//设置漫反射颜色值RGBAmat.Diffuse.r=0.5f; mat.Diffuse.g=0.0f; mat.Diffuse.b=0.5f; mat.Diffuse.a=1.0f;//设置环境反射颜色值RGBAmat.Ambient.r=0.5f; mat.Ambient.g=0.0f; mat.Ambient.b=0.5f; mat.Ambient.a=1.0f;//设置镜面反射颜色值和强度mat.Specular.r=1.0f; mat.Specular.g=1.0f; mat.Specular.b=1.0f; mat.Specular.a=1.0f;mat.Power=50.0f;//设置发射颜色值RGBAmat.Emissive.r=0.0f; mat.Emissive.g=0.0f; mat.Emissive.b=0.0f; mat.Emissive.a=0.0f;g_pd3dDev->SetMaterial(&mat);//设置设备材质纹理纹理(texture)是物体的表面图形特征(花纹),它比单一的表面颜色更逼近真实。在Direct3D中,纹理实际上被定义为覆盖在物体表面的矩形平面图像。为了将纹理覆盖在物体表面上,需要确定纹理在物体表面上的位置,称之为纹理坐标。在Direct3D中,定义了一个统一的纹理坐标系,其纹理坐标的取值范围为规范为0.0~1.0。纹理中单个的颜色值,称为纹理元素(texel=textureelement)。参见图13-21。为了在物体表面上使用纹理,在定义顶点格式时,必须考虑纹理坐标(x,y)。例如:structCUSTOMVERTEX{//顶点结构D3DXVECTOR3position;//位置D3DCOLORcolor;//颜色FLOATtu,tv;//纹理坐标图13-21纹理坐标与映射}图13-21纹理坐标与映射对应的宏常量定义也改为:#defineD3DFVF_CUSTOMVERTEX(D3DFVF_XYZ|D3DFVF_DIFFUSE|D3DFVF_TEX1)在Direct3D中,定义了多种纹理接口,其中最主要的是IDirect3DTexture9。在Direct3D中,创建纹理的最简单的方法是,调用全局函数D3DXCreateTextureFromFile:HRESULTD3DXCreateTextureFromFile(//成功返回D3D_OKLPDIRECT3DDEVICE9pDevice,//设备指针LPCTSTRpSrcFile,//图像文件路径串LPDIRECT3DTEXTURE9*ppTexture//返回的纹理接口指针);来从一个图像文件来产生纹理,它所支持的图像文件格式有:BMP、DDS、DIB、HDR、JPG、PFM、PNG、PPM和TGA,但是不支持GIF格式。然后,我们可使用IDirect3DDevice9接口的SetTexture方法,来设置Direct3D设备的当前纹理状态:(似材质设置,对后面渲染的物体有效)HRESULTSetTexture(//成功返回D3D_OKDWORDSampler,//采样器编号,用于可编程渲染的参考纹理和纹理层次编号IDirect3DBaseTexture9*pTexture//纹理接口指针(NULL=清除纹理));例如:LPDIRECT3DTEXTURE9g_pTexture=NULL;if(D3DXCreateTextureFromFile(g_pd3dDevice,"picture.bmp

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论