 |
文件下载(vb.net)
在picking演示中,
我们先在MeshNode.Teapot方法中初始化两个材料。当渲染茶壶网格,每个子物体会分别渲染出来,子物体0是没有选到的面,子物体1是选到的面.
首先 unprojected
函数通过鼠标坐标取得对应的3D向量RayPos,(深度从0到Z的值).为了得到射线方向,我们用深度Z创建另一个远距离的向量,然后我们用远距离向量减近距离向量就得到了方向向量raydir.
RayPos和RayDir利用 Mesh.Intersect
方法返回相交的信息.再用FaceIndex来改变漫反射材料attribute id从原来的0到1,这样这个表面就赋予了另一材料.Pick 操作在 MeshNode 类中完成.
|
'MeshNode类
Public Class
MeshNode Implements INode Private Mesh As Mesh Private Materials(1) As
Material
'MeshNode 类中创建Pick函数 Sub Pick(ByVal x As Single, ByVal y
As Single) Implements INode.Pick Dim vNear As Vector3 Dim vFar As
Vector3 Dim RayDir As Vector3 Dim Closest As IntersectInformation vNear
= New Vector3(x, y, 0)
'将鼠标的平面坐标反投影到3D空间中,这还需要指定一个Z深度(即vNear.z,它不是结果中的z,与投影矩阵远近裁剪面有关) vNear.Unproject(Device.Viewport,
Device.Transform.Projection, Device.Transform.View, Device.Transform.World) vFar = New Vector3(x, y,
1) vFar.Unproject(Device.Viewport, Device.Transform.Projection,
Device.Transform.View, Device.Transform.World)
'计算射线方向 vFar.Subtract(vNear) If
Mesh.Intersect(vNear, vFar, Closest) Then Dim AttributeBuffer() As Integer AttributeBuffer =
Mesh.LockAttributeBuffer(LockFlags.None)
'修改漫反射材料ID AttributeBuffer(Closest.FaceIndex) =
1 Mesh.UnlockAttributeBuffer(AttributeBuffer) End If End Sub
'分别渲染两子物体 Sub Render() Implements INode.Render Dim i
As Integer For i = 0 To 1 Device.Material = Materials(i) Mesh.DrawSubset(i) Next End Sub
Public Shared
Function Teapot() As MeshNode Dim MeshNode As New MeshNode()
'用DirectX自带的函数创建一茶壶 MeshNode.Mesh =
Microsoft.DirectX.Direct3D.Mesh.Teapot(Device)
'创建0号材质 MeshNode.Materials(0)
= New Material()
With
MeshNode.Materials(0) .Ambient = Color.White .Diffuse =
Color.White .Emissive = Color.White End With
'创建1号材质 MeshNode.Materials(1) = New Material() With
MeshNode.Materials(1) .Ambient = Color.Red .Diffuse =
Color.Red .Emissive = Color.Red End With Return MeshNode End
Function End Class
...
完 |