Presentation is loading. Please wait.

Presentation is loading. Please wait.

DirectX 简介. 名词解释(可以参考 DirectX 的词汇)  纹理映射( Texture mapping ):将一个图像映 射到一个几何物体的过程叫纹理映射。这个图像叫 纹理。 (demo)  缓冲区 (buffer) :位于显存中的一块区域,用于保 存光栅化后图像数据。  帧缓冲区.

Similar presentations


Presentation on theme: "DirectX 简介. 名词解释(可以参考 DirectX 的词汇)  纹理映射( Texture mapping ):将一个图像映 射到一个几何物体的过程叫纹理映射。这个图像叫 纹理。 (demo)  缓冲区 (buffer) :位于显存中的一块区域,用于保 存光栅化后图像数据。  帧缓冲区."— Presentation transcript:

1 DirectX 简介

2 名词解释(可以参考 DirectX 的词汇)  纹理映射( Texture mapping ):将一个图像映 射到一个几何物体的过程叫纹理映射。这个图像叫 纹理。 (demo)  缓冲区 (buffer) :位于显存中的一块区域,用于保 存光栅化后图像数据。  帧缓冲区 (frame buffer): 保存颜色的 buffer  深度缓冲区( depth buffer ) : 保存成像平面各点 处对应的深度。  Swap buffer( 交换缓冲 ) :显卡中的两块帧缓冲, 互相交换,用于显示动态的效果。 (demo)

3 主要授课内容  DirectX 简介  DXFramework 介绍  今后将以 DirectX 为主介绍!

4 DirectX 本质上是一个软件系统 ( 多媒体控制处理引 擎 ) ,它抽象了视频、音频、输入、网络、安装和其 他的功能,使得无论 PC 机器的配置如何,代码都可 以重用. DirectX 技术比 GDI/MCI(Media Control Interface) 要 快速、健壮。 充分利用硬件的加速功能,又隐藏硬件相关的设备 特性。 DirectX

5  DirectX 向后兼容  包含多个 dll 的允许库,可以和应用程序一起 发布  可以利用 VC 的 DX Wizzard 生成初始的程序 很多三维射击、动作、冒险、战略等游戏都基于 DirectX

6 基于 MCI 和 DirectX 的 Windows 游戏 Fast/primitive Win32 Application Fastslow/few options User Input slow GDI slow Lots of latency output Standard Win32 601/MCI Game Network Fast/robust very fast fast Input Sound output DirectX Win32 Game fast MCI Sound WinSock Network Fast Win32 Application DirectX

7 帝国时代 II 飞行模拟 2004

8 DirectX 结构 Win32 应用程序 DirectX SDK 硬件模拟层:基于软件的模拟 硬件抽象层 底层硬件

9 DirectX 构成 底层的 API ,面向游戏,图形,多媒体 直接与硬件打交道,只用于 Windows 操作系统 DX8.0 之前业余级, DX8.1 以后开始完善 DirectX Graphics : MS DirectDraw, MS Direct3D DirectX Graphics : MS DirectDraw, MS Direct3D MS DirectSound : 高层次音频应用 MS DirectSound : 高层次音频应用 MS DirectMusic: 音乐、音轨、动态多媒体授权 MS DirectMusic: 音乐、音轨、动态多媒体授权 MS DirectShow: 高层次多媒体流获取与播放 MS DirectShow: 高层次多媒体流获取与播放 MS DirectInput : 用户交互(包括力反馈) MS DirectInput : 用户交互(包括力反馈) MS DirectPlay : 多人联网游戏 MS DirectPlay : 多人联网游戏 Direct Setup: 设置 DirectX 元素之 API Direct Setup: 设置 DirectX 元素之 API Direct Media Objects: 数据流对象,包括 Video 与 Audio 的解码编码 Direct Media Objects: 数据流对象,包括 Video 与 Audio 的解码编码

10 DirectX Graphics :以 Direct3D 为主 ,也包含了 DirectDraw 的内容,特别 地,提供了一整套 D3DX 实用扩展库, 为向量、矩阵、旋转球的运算提供了良 好的支持。 DirectX 图形 水的 demo

11 Direct3D 与 OpenGL 图形硬件基本上相同,只是在 API 上,例如 ATI: RADEON, Nintendo GameCube NVIDIA: GeForce 系列, Microsoft Xbox 从功能上看,它们都包括 – 纹理映射 顶点和法向数组 透明度绘制 深度测试 90% 游戏以 DirectX 为平台开发

12 D3D 与 OpenGL (续) OpenGL: 跨平台 D3D: Windows ,与设备打交道 OpenGL: 仅图形 D3D: 包含游戏所需要的其他 API OpenGL: 1.5 规范 (2.0?) D3D:9.0 (8.0 以前非常业余) OpenGL: 支持立体显示 D3D: 不支持 OpenGL: Cg of Nvidia D3D: RenderMonkey of Ati OpenGL + DX = Fahrenheit 失败! OpenGL ES Direct3Dm

13 DirectInput :提供了对应用程序所有的输 入设备的支持,包括键盘、鼠标、手柄、操 纵杆和方向盘等。利用 DirectInput 还能控 制力反馈设备,模拟使用者的真实感觉,如 打开窗门、被武器击中等,一系列输入设备 的接口,包括力反馈装置。 DirectInput DXFramework demo

14 DirectDraw – 最古老最基本的绘制方法,类 似于 GDI ,主要是位图绘制引擎和视频显示。 所有的三维图形绘制最终都要体现在 DirectDraw 中。 自 DirectX8.1 以后,被集成到 Direct3D 中。 DirectDraw DXFramework demo

15 DirectSound 提供了对高质量声音效果的支持 ,利用 DirectSound API, 可以添加具有真实感 的三维声音效果。主要功能有装入、播放所 有声音( Wave, MIDI 格式等) DirectSound DXFramework demo

16 DirectMusic 提供了对基于 Wave 、 MIDI 和 DirectMusic Producer 制作的音乐的完整解决 办法,能够处理兼容于 DirectMusic 的各种音 乐数据。 DirectMusic 仙剑奇侠传游戏 demo

17 DirectPlay 提供玩家进行多人游戏中信息通讯 、玩家互动交流的平台环境。可以创建、查 询和连接网络游戏的服务端和客户端。一旦 建立了网络游戏的连接, DirectPlay 能够实现 网络直接的数据通讯。 DirectPlay VC 游戏 demo

18 DirectSetup – 准 DirectX 元素。提供了 DirectX 的自动安装功能。对于没有安装 DirectX 或者 安装了较早的 DirectX 版本的系统, DirectSetup 可帮助开发人员对系统进行最新版 本的 DirectX 的自动安装。 DirectSetup

19 DirectX Media Objects – 简称 DMO 是 DirectX 基于 COM 的数据流组件,它提供 了对数据流对象的写入和使用操作,包括 视频和音频的编码、解码和效果。 DMO

20 DirectShow DirectShow 提供了对多媒体数据流的高质 量捕做和回放的支持,它支持多种多媒体 格式,包括 ASF 、 MPEG 、 AVI 、 MP3 和 WAV 等。

21 COM 接口  Component Object Model (组件对象 模型)对象是对一组特定功能的抽象几何, 应用程序不能直接访问 COM 对象,而是必 须通过 COM 对象的接口( Interface )的指 针执行 COM 对象的功能。  COM 对象接口定义了可供应用程序调用的 一组函数(方法, method )。 COM 对象 接口指针在使用上类似于 C++ 类的指针。

22 COM 接口  COM 对象做为 DLL 文件与应用程序同时发布  COM 对象是动态被装入的  在创建 COM 接口的时候,从 IUknown (COM 基类 ) 继承  每个继承类包含三个方法 QueryInterface( ) – 请求接口的指针 AddRef( ) – 增加一个引用数 Release( ) – 减少 COM 对象的引用数

23 一个简单 COM 对象例子:包括 三个接口 IGRAPHICS, ISOUND 和 IINPUT. IUnknown Addref() Release() QueryInterface() Interface 1 Func1() Func2() IGRAPHICS Interface 2 Func1() Func2() ISOUND Interface 3 Func1() Func2() IINPUT Win32 app uses COM object Input Output

24 HAL and HEL  HAL : Hardware Abstraction Level 软件的最底层,提供设备无关性 由制造商的驱动组成 DirectX 给出需要的 COM 接口  HEL: hardware Emulation Level 在 HAL 之上 允许模拟没有的硬件(就时是说,尽管没有三维 显卡,也可以用 HEL 方式运行程序) 速度慢

25 简单的 Direct3D 程序 (Demo1)  创建一个 Windows 窗口  初始化 Direct3D 程序  处理消息循环  物体图形显示  结束 Direct3D 程序

26 创建一个 Windows 窗口  全屏幕或窗口模式  WinMain :赋值窗口类 WNDCLASS 并注册  // Register the window class  WNDCLASSEX wc = { sizeof(WNDCLASSEX), CS_CLASSDC, MsgProc, 0L, 0L, GetModuleHandle(NULL), NULL, NULL, NULL, NULL,"D3D Tutorial", NULL };   RegisterClassEx( &wc );

27 创建一个 Windows 窗口(续)  WinMain :创建窗口  HWND hWnd = CreateWindow(  “ D3D Tutorial ”, // 已经注册的窗口类名称  “ D3D Tutorial 01: CreateDevice ”, // 窗口名称 WS_OVERLAPPEDWINDOW, // 窗口分割  100, // 窗口位置的 x 坐标  100, // 窗口位置的 y 坐标  300, // 窗口宽度  300,// 窗口高度  GetDesktopWindow(), // 父窗口句柄  NULL, // 窗口菜单句柄  wc.hInstance, // 应用程序实例句柄  NULL // 应用程序数据区指针  );

28 创建 D3D 对象  InitD3D 函数:创建 Direct3D 对象,赋予 g_pD3D.  g_pD3D = Direct3DCreate9( D3D_SDK_VERSION )  创建 Direct3D 设备对象并得到接口: g_pD3D->CreateDevice( D3DADAPTER_DEFAULT, // 显卡序号 D3DDEVTYPE_HAL, // 硬件抽象层 hWnd, // 所属窗口句柄 D3DCREATE_SOFTWARE_VERTEXPROCESSING, // 软件顶点处理 &d3dpp, // D3DPRESENT_PARAMETERS - Direct3D 设备相关信息的变量地 址 &g_pd3dDevice //Direct3D 设备接口指针的地址 )  我们打交道最多的是 Direct3D Deviec, 它定义了所有绘图组件。 Direct3D 对象更 象是 DirectX 显示信息的说明。

29 创建 D3D 对象(续) 参数: D3DDEVTYPE_HAL :高速的渲染过程,通过硬件渲染。 D3DDEVTYPE_REF(Reference rasterizer Device): 参考光栅设备 D3DDEVTYPE_SW: 外观的 Direct3D 设备,用以支持第 3 方的软件 参数: D3DCREATE_SOFTWARE_VERTEXPROCESSING :软件处理 D3DCREATE_HARDWARE_VERTEXPROCESSING :硬件处理

30 创建 D3D 对象(续)  D3DPRESENT_PARAMETERS d3dpp;  ZeroMemory( &d3dpp, sizeof(d3dpp) );  d3dpp.Windowed = TRUE;// 全屏还是窗口?  d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;// 后台缓冲复制到前 台缓冲后,清除后台缓冲内容  // D3DSWAPEFFECT_FLIP 后台缓冲复制到前台缓冲 后,保留后台内容不变 d3dpp.BackBufferFormat = D3DFMT_UNKNOWN;

31 处理消息循环  MSG msg;  while( GetMessage( &msg, NULL, 0, 0 ) )  {  TranslateMessage( &msg );  DispatchMessage( &msg );  }

32 处理消息循环(续)  LRESULT WINAPI MsgProc( HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam )  {  switch( msg )  {  case WM_DESTROY:  Cleanup();  PostQuitMessage( 0 );  return 0;  case WM_PAINT:  Render();  ValidateRect( hWnd, NULL );  return 0;  }  return DefWindowProc( hWnd, msg, wParam, lParam );  }

33 绘制场景  if( NULL == g_pd3dDevice )  return;  // Clear the backbuffer to a blue color, 重新绘制时必须  g_pd3dDevice->Clear( 0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB(0,0,255), 1.0f, 0 );  // Begin the scene  if( SUCCEEDED( g_pd3dDevice->BeginScene() ) )  {  // Rendering of scene objects can happen here   // End the scene  g_pd3dDevice->EndScene();  }  // Present the backbuffer contents to the display  g_pd3dDevice->Present( NULL, NULL, NULL, NULL );

34 清除函数  关闭窗口时,窗口过程函数接收到 WM_DESTROY 消息,调用 Cleanup() 函数 释放 Direct3D 资源, UnregisterClass() 注 销 wndclass 类。

35 简单的 Direct3D 顶点绘制( Demo2 )  创建一个 Windows 窗口  初始化 Direct3D 程序  初始化图形数据  处理消息循环  物体图形显示  结束 Direct3D 程序

36 简单的绘制程序  在 D3D 中,最基本的绘制单元是三角形(顶点组成)  所有模型都可表示为三角形模型 QSPLAT 例子

37 Direct3D 基本图形表示  顶点集合: D3DPT_POINTLIST  线段集合: D3DPT_LINELIST  线段 strip : D3DPT_LINESTRIPLIST  三角形集合: D3DPT_TRIANGLELIST  三角形 Strip : D3DPT_TRIANGLESTRIP  三角形 Fan : D3DPT_TRIANGLEFAN

38 Direct3D 基本图形表示 ( 续 )  TriangleStrip: 仅需保存 v1,v2,v3,v4  (v1,v2,v3), (v2,v4,v3),  (v3,v4,v5),  TriangleFAN: 仅需保存 v1,v2,v3,v4  (v1,v2,v3), (v1,v3,v4),  (v1,v4,v5),

39 Direct3D 基本图形表示 ( 续 )  Indexed TriangleList: 最常用  顶点列表 : 保存在 Index Buffer ,可以共享  (x1,y1,z1),  (x2,y2,z2),  (x3,y3,z3),  …..  三角形列表:保存在 Vertex Buffer  (v1, v2, v5)  (v2, v5, v3)  (v3, v4, v5)  ….. v1 v2 v3 v4 v5

40 Direct3D 基本图形表示 ( 续 )  Unindexed TriangleList: 效率最低  顶点列表 : 保存在 Vertex Buffer  T1 = (V1, V2,V5)  T2 = (V2 ’, V5 ’,V3)  T3 = (V3 ’, V5 ’’,V4)  顶点数等于三角形数乘以 3  一共需要 9 个顶点 v1 v2 v3 v4 v5 T1 T2 T3 V2 ’ V3 ’ V5 ’’ V5 ’

41 Direct3D 中的顶点数据的设置  顶点: Vertex  确定顶点描述符和顶点结构  创建顶点 Buffer  填充顶点 Buffer  顶点数据来源:从文件中读取。

42 简单的绘制程序(续)  InitVB(): 设置顶点数据  D3DFVF_CUSTOMVERTEX :顶点描述符  D3DFVF_XYZW: 位置  D3DFVF_XYZRHW: 变换后的位置信息  D3DFVF_NORMAL: 法向  D3DFVF_DIFFUSE: 漫射光分量  D3DFVF_TEX*: 纹理坐标  ….  FVF: Flexible Vertex Format

43 简单的绘制程序(续)  定义好的顶点结构  struct CUSTOMVERTEX  {  FLOAT x, y, z, rhw; // The transformed position for the vertex  DWORD color; // The vertex color  };  // Our custom FVF, which describes our custom vertex structure  #define D3DFVF_CUSTOMVERTEX (D3DFVF_XYZRHW|D3DFVF_DIFFUSE)

44 简单的绘制程序(续)  预先设定好的顶点数据 :  CUSTOMVERTEX vertices[] =  {  { 150.0f, 50.0f, 0.5f, 1.0f, 0xffff0000, }, // x, y, z, rhw, color  { 250.0f, 250.0f, 0.5f, 1.0f, 0xff00ff00, },  { 50.0f, 250.0f, 0.5f, 1.0f, 0xff00ffff, },  };

45 简单的绘制程序(续)  创建顶点 Buffer:  LPDIRECT3DVERTEXBUFFER9 g_pVB ;  if( FAILED( g_pd3dDevice->CreateVertexBuffer( 3*sizeof(CUSTOMVERTEX), // 顶点尺寸  0, //D3DUSAGE ,缺省为 0  D3DFVF_CUSTOMVERTEX, // 顶点描述符 D3DPOOL_DEFAULT, //D3DPOOL : 定义内存管理方式 &g_pVB, // Vertex Buffer 对象 NULL // 设为空 ) ) )  {  return E_FAIL;  }

46 简单的绘制程序(续)  填充顶点 buffer  VOID* pVertices;//buffer 指针  if( FAILED( g_pVB->Lock( 0, sizeof(vertices), (void**)&pVertices, 0 ) ) ) // 先 Lock 这个 VB  return E_FAIL;  memcpy( pVertices, vertices, sizeof(vertices) ); // 然后对 VB 赋值  g_pVB->Unlock();//UnLock

47 简单的绘制程序(续)  预先设定好的顶点数据 :  CUSTOMVERTEX vertices[] =  {  { 150.0f, 50.0f, 0.5f, 1.0f, 0xffff0000, }, // x, y, z, rhw, color  { 250.0f, 250.0f, 0.5f, 1.0f, 0xff00ff00, },  { 50.0f, 250.0f, 0.5f, 1.0f, 0xff00ffff, },  };

48 简单的绘制程序(续)  内存管理方式主要有:  D3DPOOL_DEFAULT: 缺省方式,系统自动管理 数据,将数据放在最合适的地方,包括显存、主存、 AGP内存。  D3DPOOL_MANAGED:设备自动地将数据放到显 存中,并且在内存中备份。当设备释放时,不需要 重新重新创建。  D3DPOOL_SYSTEMMEM:数据放在系统主存中。 速度最慢。  D3DPOOL_SCRATCH :也是放在系统主存中, 可以被创建、拷贝和Lock。

49 简单的绘制程序(续)  绘制顶点数据  g_pd3dDevice->Clear( 0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB(0,0,255), 1.0f, 0 );  // Begin the scene  if( SUCCEEDED( g_pd3dDevice->BeginScene() ) ) {  // 设置顶点流  g_pd3dDevice->SetStreamSource( 0, g_pVB, 0, sizeof(CUSTOMVERTEX) );  g_pd3dDevice->SetFVF( D3DFVF_CUSTOMVERTEX ); // 设置顶点格式  // 绘制无 index 的三角形列表  g_pd3dDevice->DrawPrimitive( D3DPT_TRIANGLELIST, 0, 1 );  // End the scene  g_pd3dDevice->EndScene();  }  // Present the backbuffer contents to the display  g_pd3dDevice->Present( NULL, NULL, NULL, NULL );

50 简单的 Direct3D 顶点变换( Demo3 )  创建一个 Windows 窗口  初始化 Direct3D 程序  初始化图形数据  处理消息循环  物体图形显示:顶点位置改变  结束 Direct3D 程序

51 设置顶点格式  struct CUSTOMVERTEX  {  FLOAT x, y, z;  // 变换前的顶点位置  DWORD color; // 顶点颜色  };  !!!与前例不同  // Our custom FVF, which describes our custom vertex structure  #define D3DFVF_CUSTOMVERTEX (D3DFVF_XYZ|D3DFVF_DIFFUSE)

52 创建顶点数据  CUSTOMVERTEX g_Vertices[] =  {  { -1.0f,-1.0f, 0.0f, 0xffff0000, },  { 1.0f,-1.0f, 0.0f, 0xff0000ff, },  { 0.0f, 1.0f, 0.0f, 0xffffffff, },  };  三个不同颜色的顶点

53 创建顶点 Buffer  // Create the vertex buffer.  if( FAILED( g_pd3dDevice->CreateVertexBuffer( 3*sizeof(CUSTOMVERTEX),  0, D3DFVF_CUSTOMVERTEX,  D3DPOOL_DEFAULT, &g_pVB, NULL ) ) )  {  return E_FAIL;  }  // Fill the vertex buffer.  VOID* pVertices;  if( FAILED( g_pVB->Lock( 0, sizeof(g_Vertices), (void**)&pVertices, 0 ) ) )  return E_FAIL;  memcpy( pVertices, g_Vertices, sizeof(g_Vertices) );  g_pVB->Unlock();

54 绘制三角形  g_pd3dDevice->Clear( 0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB(0,0,0), 1.0f, 0 ); // 仅清除颜色缓冲  // Begin the scene  if( SUCCEEDED( g_pd3dDevice->BeginScene() ) ) {  // Setup the world, view, and projection matrices  SetupMatrices(); // 设置世界、相机和投影矩阵  // Render the vertex buffer contents  g_pd3dDevice->SetStreamSource( 0, g_pVB, 0, sizeof(CUSTOMVERTEX) );  g_pd3dDevice->SetFVF( D3DFVF_CUSTOMVERTEX );  g_pd3dDevice->DrawPrimitive( D3DPT_TRIANGLESTRIP, 0, 1 );  // End the scene  g_pd3dDevice->EndScene();  }  // Present the backbuffer contents to the display  g_pd3dDevice->Present( NULL, NULL, NULL, NULL );

55 矩阵变换( Transformation )  变换决定了物体最后在成像平面的位置  变换是通过 4x4 齐次坐标矩阵完成的  齐次坐标: Homogenous Coordinates  矩阵: Matrix (Matrices 是其复数 )  在游戏动画中,由于人物、场景在不停地运 动,矩阵必须每帧更新。因此, SetMatrices 函数放在 Render() 或者 FrameMove 函数中。

56 设置世界变换 (SetMatrices())  D3DXMATRIXA16 matWorld; //D3DX 库类  // 设置在 1 秒之内旋转 2PI 角度   UINT iTime = timeGetTime() % 1000; // 获取时间  // 计算角度  FLOAT fAngle = iTime * (2.0f * D3DX_PI) / 1000.0f;  // 设置世界坐标矩阵  D3DXMatrixRotationY( &matWorld, fAngle );  g_pd3dDevice->SetTransform( D3DTS_WORLD, &matWorld );

57 设置相机变换( SetMatrices() )  // 视点位置  D3DXVECTOR3 vEyePt( 0.0f, 3.0f,-5.0f );  // 看的位置  D3DXVECTOR3 vLookatPt( 0.0f, 0.0f, 0.0f );  //Up 方向  D3DXVECTOR3 vUpVec( 0.0f, 1.0f, 0.0f );  D3DXMATRIXA16 matView;  //D3DX 函数库自动生成相机矩阵  D3DXMatrixLookAtLH( &matView, &vEyePt, &vLookatPt, &vUpVec );  // 设置到系统中 g_pd3dDevice->SetTransform( D3DTS_VIEW, &matView );

58 设置投影变换( SetMatrices() )  D3DXMATRIXA16 matProj;  // 设置视玉角、方正率、近平面和远平面  D3DXMatrixPerspectiveFovLH( &matProj, D3DX_PI/4, 1.0f, 1.0f, 100.0f );  g_pd3dDevice->SetTransform( D3DTS_PROJECTION, &matProj );

59 简单的 Direct3D 光照例程( Demo4 )  创建一个 Windows 窗口  初始化 Direct3D 程序  初始化图形数据  处理消息循环  物体图形显示:打开光源  结束 Direct3D 程序

60 设置顶点格式  struct CUSTOMVERTEX  {  D3DXVECTOR3 position; // 顶点位置 D3DXVECTOR3 normal; // 顶点所在处的 法向  };  D3DXVECTOR3/4: 向量类库  #define D3DFVF_CUSTOMVERTEX (D3DFVF_XYZ|D3DFVF_NORMAL)

61 设置绘制状态  InitD3D()  d3dpp.AutoDepthStencilFormat = D3DFMT_D16; // 设置深度 buffer 为 16 位  // 关闭背面剔除  g_pd3dDevice->SetRenderState( D3DRS_CULLMODE, D3DCULL_NONE );  // 打开 zbuffer 消隐  g_pd3dDevice->SetRenderState( D3DRS_ZENABLE, TRUE );

62 设置顶点数据  CUSTOMVERTEX* pVertices;  if( FAILED( g_pVB->Lock( 0, 0, (void**)&pVertices, 0 ) ) )  return E_FAIL;  for( DWORD i=0; i<50; i++ )  {  FLOAT theta = (2*D3DX_PI*i)/(50-1);  pVertices[2*i+0].position = D3DXVECTOR3( sinf(theta),-1.0f, cosf(theta) );  pVertices[2*i+0].normal = D3DXVECTOR3( sinf(theta), 0.0f, cosf(theta) );  pVertices[2*i+1].position = D3DXVECTOR3( sinf(theta), 1.0f, cosf(theta) );  pVertices[2*i+1].normal = D3DXVECTOR3( sinf(theta), 0.0f, cosf(theta) );  }  g_pVB->Unlock();  // 程序生成一个圆柱的数据

63 绘制场景  // Clear the backbuffer and the zbuffer  g_pd3dDevice->Clear( 0, NULL, D3DCLEAR_TARGET|D3DCLEAR_ZBUFFER, D3DCOLOR_XRGB(0,0,255), 1.0f, 0 ); // 除了清颜色缓冲外,还清深度缓冲  if( SUCCEEDED( g_pd3dDevice->BeginScene() ) ) {  // 设置光源和材质  SetupLights();  // 设置变换矩阵  SetupMatrices();  // 绘制顶点 g_pd3dDevice->SetStreamSource( 0, g_pVB, 0, sizeof(CUSTOMVERTEX) );  g_pd3dDevice->SetFVF( D3DFVF_CUSTOMVERTEX );  g_pd3dDevice->DrawPrimitive( D3DPT_TRIANGLESTRIP, 0, 2*50-2 );  g_pd3dDevice->EndScene();  }  // 相当于 Swapbuffer  g_pd3dDevice->Present( NULL, NULL, NULL, NULL );

64 设置物体材质  SetLights():  D3DMATERIAL9 mtrl; // 材质接口  ZeroMemory( &mtrl, sizeof(D3DMATERIAL9) );  mtrl.Diffuse.r = mtrl.Ambient.r = 1.0f;  mtrl.Diffuse.g = mtrl.Ambient.g = 1.0f;  mtrl.Diffuse.b = mtrl.Ambient.b = 0.0f;  mtrl.Diffuse.a = mtrl.Ambient.a = 1.0f;  g_pd3dDevice->SetMaterial( &mtrl );

65 设置光源  D3DXVECTOR3 vecDir;  D3DLIGHT9 light;  ZeroMemory( &light, sizeof(D3DLIGHT9) );  light.Type = D3DLIGHT_DIRECTIONAL; // 方向光  light.Diffuse.r = 1.0f;// 光源的颜色  light.Diffuse.g = 1.0f;  light.Diffuse.b = 1.0f;  vecDir = D3DXVECTOR3(cosf(timeGetTime()/350.0f),  1.0f, sinf(timeGetTime()/350.0f) );  D3DXVec3Normalize( (D3DXVECTOR3*)&light.Direction, &vecDir ); // 光源的方向  light.Range = 1000.0f; // 光源的范围  g_pd3dDevice->SetLight( 0, &light );

66 设置光照有关的绘制状态  g_pd3dDevice->LightEnable( 0, TRUE ); // 打开第一个光源  g_pd3dDevice->SetRenderState( D3DRS_LIGHTING, TRUE ); // 打开光照  g_pd3dDevice->SetRenderState( D3DRS_AMBIENT, 0x00202020 );  // 设置泛光

67 简单的纹理映射例程( Demo5 )  创建一个 Windows 窗口  初始化 Direct3D 程序  初始化图形数据(包括设置纹理)  处理消息循环  物体图形显示:打开光源,打开纹理映射  结束 Direct3D 程序

68 设置顶点格式  struct CUSTOMVERTEX  {  D3DXVECTOR3 position; // 位置  D3DCOLOR color; // 颜色  // 没有法向,因为不做光照!  FLOAT tu, tv; // 纹理坐标  };  #define D3DFVF_CUSTOMVERTEX (D3DFVF_XYZ|D3DFVF_DIFFUSE|D3DFVF_ TEX1)

69 设置绘制状态  Init3D():  // 关闭背面剔除  g_pd3dDevice->SetRenderState( D3DRS_CULLMODE, D3DCULL_NONE );  // 关闭光照  g_pd3dDevice->SetRenderState( D3DRS_LIGHTING, FALSE );  // 打开深度测试  g_pd3dDevice->SetRenderState( D3DRS_ZENABLE, TRUE );

70 设置顶点纹理坐标  for( DWORD i=0; i<50; i++ )  {  FLOAT theta = (2*D3DX_PI*i)/(50-1);  pVertices[2*i+0].position = D3DXVECTOR3( sinf(theta),-1.0f, cosf(theta) );  pVertices[2*i+0].color = 0xffffffff; pVertices[2*i+0].tu = ((FLOAT)i)/(50-1); // 纹理坐标  pVertices[2*i+0].tv = 1.0f; // 纹理坐标  pVertices[2*i+1].position = D3DXVECTOR3( sinf(theta), 1.0f, cosf(theta) );  pVertices[2*i+1].color = 0xff808080; pVertices[2*i+1].tu = ((FLOAT)i)/(50-1); // 纹理坐标  pVertices[2*i+1].tv = 0.0f; // 纹理坐标  }

71 绘制场景  Render 函数:  清屏: g_pd3dDevice->Clear( 0, NULL, D3DCLEAR_TARGET|D3DCLEAR_ZBUFFER, D3DCOLOR_XRGB(0,0,255), 1.0f, 0 );  设置矩阵: SetMatrices  设置纹理参数  设置纹理矩阵  绘制场景

72 绘制场景(续)  // 设置纹理  g_pd3dDevice->SetTexture( 0, g_pTexture );  // 设置纹理和颜色的混合模式  g_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLOROP, D3DTOP_MODULATE );  // 设置第一个纹理映射函数的参数为纹理  g_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLORARG1, D3DTA_TEXTURE );  // 设置第二个纹理映射函数的参数为漫射光  g_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLORARG2, D3DTA_DIFFUSE );  // 关闭透明度融合功能  g_pd3dDevice->SetTextureStageState( 0, D3DTSS_ALPHAOP, D3DTOP_DISABLE );

73 绘制场景(续)  D3DXMATRIXA16 mat;  mat._11 = 0.25f; mat._12 = 0.00f; mat._13 = 0.00f; mat._14 = 0.00f;  mat._21 = 0.00f; mat._22 =-0.25f; mat._23 = 0.00f; mat._24 = 0.00f;  mat._31 = 0.00f; mat._32 = 0.00f; mat._33 = 1.00f; mat._34 = 0.00f;  mat._41 = 0.50f; mat._42 = 0.50f; mat._43 = 0.00f; mat._44 = 1.00f;  g_pd3dDevice->SetTransform( D3DTS_TEXTURE0, &mat );  g_pd3dDevice->SetTextureStageState( 0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT2 );  g_pd3dDevice->SetTextureStageState( 0, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_CAMERASPACEPOSITION );

74 装入纹理  // D3DX 可从图像文件中直接装入  if( FAILED( D3DXCreateTextureFromFile( g_pd3dDevice, "banana.bmp", &g_pTexture ) ) )  {  // 继续找!  if( FAILED( D3DXCreateTextureFromFile( g_pd3dDevice, "..\\banana.bmp", &g_pTexture ) ) )  {  MessageBox(NULL, "Could not find banana.bmp", "Textures.exe", MB_OK);  return E_FAIL;  }  非常容易哦

75 简单的 X 模型绘制例程( Demo6 )  创建一个 Windows 窗口  初始化 Direct3D 程序  初始化图形数据(装入网格数据)  处理消息循环  物体图形显示:绘制网格  结束 Direct3D 程序  Mesh: 网格,即一系列三角形的集合

76 网格结构  LPD3DXMESH g_pMesh = NULL; // 保存在系统内存中的 D3DX 网格结构  D3DMATERIAL9* g_pMeshMaterials = NULL; // 网格的材质  LPDIRECT3DTEXTURE9* g_pMeshTextures = NULL; // 网格的纹理  DWORD g_dwNumMaterials = 0L;  // 网格的材质数目

77 读入网格( InitGeometry() ) LPD3DXBUFFER pD3DXMtrlBuffer; // 接口 -> 用于保存顶点信息等数据的 buffer  if( FAILED( D3DXLoadMeshFromX( "Tiger.x", D3DXMESH_SYSTEMMEM, g_pd3dDevice, NULL, &pD3DXMtrlBuffer, NULL, &g_dwNumMaterials,  &g_pMesh ) ) ) {  // 继续寻找  if( FAILED( D3DXLoadMeshFromX( "..\\Tiger.x", D3DXMESH_SYSTEMMEM,  g_pd3dDevice, NULL,  &pD3DXMtrlBuffer, NULL, &g_dwNumMaterials,  &g_pMesh ) ) )  {  MessageBox(NULL, "Could not find tiger.x", "Meshes.exe", MB_OK);  return E_FAIL;  }

78 设置材质和纹理( InitGeometry() )  D3DXMATERIAL* d3dxMaterials = (D3DXMATERIAL*)pD3DXMtrlBuffer- >GetBufferPointer(); // 获得材质指针  g_pMeshMaterials = new D3DMATERIAL9[g_dwNumMaterials];  g_pMeshTextures = new LPDIRECT3DTEXTURE9[g_dwNumMaterials]; // 每个材质一 个纹理  for( DWORD i=0; i<g_dwNumMaterials; i++ )  {  从 pD3DXMtrlBuffer 获得纹理和材质数据  }

79 绘制网格 (Render())  ….  一般每个网格被分为多个子集 (Subset )  for( DWORD i=0; i<g_dwNumMaterials; i++ ) { // 设置材质  g_pd3dDevice->SetMaterial( &g_pMeshMaterials[i] );  // 设置纹理  g_pd3dDevice->SetTexture( 0, g_pMeshTextures[i] );   // 绘制网格的某子部分  g_pMesh->DrawSubset( i );  }  …

80 课后作业  安装 DirectX 9.0  复习 DirectX 的 tutorials  下载并熟悉 DXFramework  阅读新课本相关内容  下周交作业!(向量代数) 


Download ppt "DirectX 简介. 名词解释(可以参考 DirectX 的词汇)  纹理映射( Texture mapping ):将一个图像映 射到一个几何物体的过程叫纹理映射。这个图像叫 纹理。 (demo)  缓冲区 (buffer) :位于显存中的一块区域,用于保 存光栅化后图像数据。  帧缓冲区."

Similar presentations


Ads by Google