protected void InitModelDebugPhysic(GraphicNode graphic_node) { var physic = graphic_node.Entity.Get <PhysicComponent>(); var min = physic.BoundingBox.Min; var max = physic.BoundingBox.Max; var x0 = (float)min.X; var y0 = (float)min.Y; var z0 = (float)min.Z; var x1 = (float)max.X; var y1 = (float)max.Y; var z1 = (float)max.Z; var verticies = new VertexP3[] { new VertexP3(x0, y0, z0), new VertexP3(x0, y1, z0), new VertexP3(x0, y0, z1), new VertexP3(x0, y1, z1), new VertexP3(x1, y0, z0), new VertexP3(x1, y1, z0), new VertexP3(x1, y0, z1), new VertexP3(x1, y1, z1), new VertexP3(x0, y0, z0), new VertexP3(x1, y0, z0), new VertexP3(x0, y1, z0), new VertexP3(x1, y1, z0), new VertexP3(x0, y0, z1), new VertexP3(x1, y0, z1), new VertexP3(x0, y1, z1), new VertexP3(x1, y1, z1), new VertexP3(x0, y0, z0), new VertexP3(x0, y0, z1), new VertexP3(x1, y0, z0), new VertexP3(x1, y0, z1), new VertexP3(x0, y1, z0), new VertexP3(x0, y1, z1), new VertexP3(x1, y1, z0), new VertexP3(x1, y1, z1) }; graphic_node.ModelDebugPhysic = new Model(); graphic_node.ModelDebugPhysic.Mesh(new Mesh <VertexP3, uint>(verticies)); graphic_node.ModelDebugPhysic.Mode = PrimitiveType.Lines; graphic_node.ModelDebugPhysic.Program = ResourceManager.Programs["primitive_colored"]; }
public Form1() { InitializeComponent(); m_Device = new Device(); m_Device.Init(panelOutput1.Handle, false, false); m_Shader_RenderMesh = new Shader(m_Device, new ShaderFile(new System.IO.FileInfo("./Shaders/RenderMesh.hlsl")), VERTEX_FORMAT.P3, "VS", null, "PS", null); { List <VertexP3> Vertices = new List <VertexP3>(); List <uint> Indices = new List <uint>(); const int SUBDIVS_THETA = 80; const int SUBDIVS_PHI = 160; for (int Y = 0; Y <= SUBDIVS_THETA; Y++) { double Theta = Y * Math.PI / SUBDIVS_THETA; float CosTheta = (float)Math.Cos(Theta); float SinTheta = (float)Math.Sin(Theta); for (int X = 0; X <= SUBDIVS_PHI; X++) { double Phi = X * 2.0 * Math.PI / SUBDIVS_PHI; float CosPhi = (float)Math.Cos(Phi); float SinPhi = (float)Math.Sin(Phi); float3 N = new float3(SinTheta * SinPhi, CosTheta, SinTheta * CosPhi); Vertices.Add(new VertexP3() { P = N }); } } for (int Y = 0; Y < SUBDIVS_THETA; Y++) { int CurrentLineOffset = Y * (SUBDIVS_PHI + 1); int NextLineOffset = (Y + 1) * (SUBDIVS_PHI + 1); for (int X = 0; X <= SUBDIVS_PHI; X++) { Indices.Add((uint)(CurrentLineOffset + X)); Indices.Add((uint)(NextLineOffset + X)); } if (Y < SUBDIVS_THETA - 1) { Indices.Add((uint)(NextLineOffset - 1)); // Degenerate triangle to end the line Indices.Add((uint)NextLineOffset); // Degenerate triangle to start the next line } } m_Prim_Sphere = new Primitive(m_Device, Vertices.Count, VertexP3.FromArray(Vertices.ToArray()), Indices.ToArray(), Primitive.TOPOLOGY.TRIANGLE_STRIP, VERTEX_FORMAT.P3); } // Setup camera m_CB_Camera = new ConstantBuffer <CB_Camera>(m_Device, 0); m_CB_Mesh = new ConstantBuffer <CB_Mesh>(m_Device, 1); m_Camera.CreatePerspectiveCamera(60.0f * (float)Math.PI / 180.0f, (float)panelOutput1.Width / panelOutput1.Height, 0.01f, 40.0f); m_Camera.CameraTransformChanged += new EventHandler(Camera_CameraTransformChanged); m_CameraManipulator.Attach(panelOutput1, m_Camera); m_CameraManipulator.InitializeCamera(4.0f * float3.UnitZ, float3.Zero, float3.UnitY); // Build SH { const int SUBDIVS_THETA = 80; const int SUBDIVS_PHI = 160; const double f0 = 0.28209479177387814347403972578039; // 0.5 / sqrt(PI); const double f1 = 0.48860251190291992158638462283835; // 0.5 * sqrt(3/PI); const double f2 = 1.09254843059207907054338570580270; // 0.5 * sqrt(15/PI); const double f3 = 0.31539156525252000603089369029571; // 0.25 * sqrt(5.PI); double[] SH = new double[9]; double[] DirectionSH = new double[9]; double[] PreciseDirectionSH = new double[9]; double[] SumDirectionSH = new double[9]; double[] SumPreciseDirectionSH = new double[9]; for (int Y = 0; Y < SUBDIVS_THETA; Y++) { for (int X = 0; X < SUBDIVS_PHI; X++) { double Theta = 2.0 * Math.Acos(Math.Sqrt(1.0 - (Y + WMath.SimpleRNG.GetUniform()) / SUBDIVS_THETA)); double Phi = 2.0 * Math.PI * (X + WMath.SimpleRNG.GetUniform()) / SUBDIVS_PHI; float CosTheta = (float)Math.Cos(Theta); float SinTheta = (float)Math.Sin(Theta); float CosPhi = (float)Math.Cos(Phi); float SinPhi = (float)Math.Sin(Phi); float3 Direction = new float3(SinTheta * CosPhi, SinTheta * SinPhi, CosTheta); // Z up DirectionSH[0] = f0; // l=0 m=0 DirectionSH[1] = f1 * Direction.y; // l=1 m=-1 DirectionSH[2] = f1 * Direction.z; // l=1 m=0 DirectionSH[3] = f1 * Direction.x; // l=1 m=1 DirectionSH[4] = f2 * Direction.x * Direction.y; // l=2 m=-2 DirectionSH[5] = f2 * Direction.y * Direction.z; // l=2 m=-1 DirectionSH[6] = f3 * (3.0 * Direction.z * Direction.z - 1.0); // l=2 m=0 DirectionSH[7] = f2 * Direction.x * Direction.z; // l=2 m=1 DirectionSH[8] = f2 * 0.5 * (Direction.x * Direction.x - Direction.y * Direction.y); // l=2 m=2 for (int i = 0; i < 9; i++) { int l = (int)Math.Floor(Math.Sqrt(i)); int m = i - l * (l + 1); PreciseDirectionSH[i] = SphericalHarmonics.SHFunctions.ComputeSH(l, m, Theta, Phi); SumDirectionSH[i] += DirectionSH[i]; SumPreciseDirectionSH[i] += PreciseDirectionSH[i]; // bool rha = false; // if ( Math.Abs( DirectionSH[i] - PreciseDirectionSH[i] ) > 1e-3 ) { // //throw new Exception( "BRA!" ); // rha = true; // } } // Encode function // double Function = 0.1 + 0.45 * (1.0 - Math.Cos( 2.0 * Theta ) * Math.Cos( 1.0 * Phi )); double Function = 0.5 * (1.0 + Direction.x); for (int i = 0; i < 9; i++) { SH[i] += Function * DirectionSH[i]; } } } // Normalize and store double Normalizer = 4.0 * Math.PI / (SUBDIVS_THETA * SUBDIVS_PHI); for (int i = 0; i < 9; i++) { SH[i] *= Normalizer; SumDirectionSH[i] *= Normalizer; SumPreciseDirectionSH[i] *= Normalizer; } // SphericalHarmonics.SHFunctions.EncodeIntoSH( SH, SUBDIVS_THETA, SUBDIVS_PHI, 1, 3, ( double _Theta, double _Phi ) => { // // double Function = 0.1 + 0.45 * (1.0 - Math.Cos( 2.0 * _Theta ) * Math.Cos( 1.0 * _Phi )); // double Function = Math.Cos( _Phi ); // return Function; // } ); m_CB_Mesh.m.m_SH0.x = (float)SH[0]; m_CB_Mesh.m.m_SH0.y = (float)SH[1]; m_CB_Mesh.m.m_SH0.z = (float)SH[2]; m_CB_Mesh.m.m_SH0.w = (float)SH[3]; m_CB_Mesh.m.m_SH1.x = (float)SH[4]; m_CB_Mesh.m.m_SH1.y = (float)SH[5]; m_CB_Mesh.m.m_SH1.z = (float)SH[6]; m_CB_Mesh.m.m_SH1.w = (float)SH[7]; m_CB_Mesh.m.m_SH2 = (float)SH[8]; } Application.Idle += new EventHandler(Application_Idle); }
public TestForm() { InitializeComponent(); ComputeConeDirections(); try { m_device.Init(panelOutput.Handle, false, true); m_shader_voxelizeScene = new ComputeShader(m_device, new System.IO.FileInfo("./Shaders/VoxelizeScene.hlsl"), "CS", null); m_shader_buildVoxelMips = new ComputeShader(m_device, new System.IO.FileInfo("./Shaders/VoxelizeScene.hlsl"), "CS_Mip", null); m_shader_buildSingleVoxelMips = new ComputeShader(m_device, new System.IO.FileInfo("./Shaders/VoxelizeScene.hlsl"), "CS_SingleMip", null); m_shader_accumulateVoxelLighting = new ComputeShader(m_device, new System.IO.FileInfo("./Shaders/VoxelizeScene.hlsl"), "CS_Accumulate", null); m_shader_computeIndirectLighting = new ComputeShader(m_device, new System.IO.FileInfo("./Shaders/ComputeIndirectLighting.hlsl"), "CS", null); m_shader_renderGBuffer = new Shader(m_device, new System.IO.FileInfo("./Shaders/RenderGBuffer.hlsl"), VERTEX_FORMAT.Pt4, "VS", null, "PS", null); m_shader_renderScene = new Shader(m_device, new System.IO.FileInfo("./Shaders/RenderScene.hlsl"), VERTEX_FORMAT.Pt4, "VS", null, "PS", null); m_shader_renderVoxels = new Shader(m_device, new System.IO.FileInfo("./Shaders/RenderVoxels.hlsl"), VERTEX_FORMAT.P3, "VS", null, "PS", null); m_shader_postProcess = new Shader(m_device, new System.IO.FileInfo("./Shaders/PostProcess.hlsl"), VERTEX_FORMAT.Pt4, "VS", null, "PS", null); m_tex_GBuffer = new Texture2D(m_device, (uint)panelOutput.Width, (uint)panelOutput.Height, 4, 1, PIXEL_FORMAT.RGBA32F, COMPONENT_FORMAT.UNORM, false, false, null); m_tex_sceneRadiance = new Texture2D(m_device, (uint)panelOutput.Width, (uint)panelOutput.Height, 1, 1, PIXEL_FORMAT.RGBA32F, COMPONENT_FORMAT.UNORM, false, false, null); using (ImageFile blueNoise = new ImageFile(new System.IO.FileInfo("BlueNoise64x64.png"))) { m_Tex_BlueNoise = new Texture2D(m_device, new ImagesMatrix(new ImageFile[, ] { { blueNoise } }), COMPONENT_FORMAT.UNORM); } m_CB_computeIndirect = new ConstantBuffer <CB_ComputeIndirectLighting>(m_device, 10); m_CB_global = new ConstantBuffer <CB_Global>(m_device, 0); m_CB_camera = new ConstantBuffer <CB_Camera>(m_device, 1); m_CB_renderScene = new ConstantBuffer <CB_RenderScene>(m_device, 10); m_CB_renderVoxels = new ConstantBuffer <CB_RenderVoxels>(m_device, 10); m_CB_filtering = new ConstantBuffer <CB_Filtering>(m_device, 10); m_CB_postProcess = new ConstantBuffer <CB_PostProcess>(m_device, 10); // Build the cube primitive used to render voxels { VertexP3[] vertices = new VertexP3[] { new VertexP3() { P = new float3(-1, -1, -1) }, new VertexP3() { P = new float3(1, -1, -1) }, new VertexP3() { P = new float3(1, 1, -1) }, new VertexP3() { P = new float3(-1, 1, -1) }, new VertexP3() { P = new float3(-1, -1, +1) }, new VertexP3() { P = new float3(1, -1, +1) }, new VertexP3() { P = new float3(1, 1, +1) }, new VertexP3() { P = new float3(-1, 1, +1) }, }; uint[] indices = new uint[] { 3, 0, 4, 3, 4, 7, 6, 5, 1, 6, 1, 2, 3, 7, 6, 3, 6, 2, 4, 0, 1, 4, 1, 5, 2, 1, 0, 2, 0, 3, 7, 4, 5, 7, 5, 6, }; m_prim_Cube = new Primitive(m_device, (uint)vertices.Length, VertexP3.FromArray(vertices), indices, Primitive.TOPOLOGY.TRIANGLE_LIST, VERTEX_FORMAT.P3); } // Voxelize the scene & compute indirect lighting Voxelize(); ComputeIndirectLighting((uint)integerTrackbarControlBouncesCount.Value); } catch (Exception _e) { MessageBox.Show(this, "An exception occurred while creating DX structures:\r\n" + _e.Message, "Error"); } // Initialize camera m_camera.CreatePerspectiveCamera(CAMERA_FOV, (float)panelOutput.Width / panelOutput.Height, 0.1f, 100.0f); m_camera.CameraTransformChanged += m_camera_CameraTransformChanged; m_cameraManipulator.Attach(panelOutput, m_camera); // m_cameraManipulator.InitializeCamera( new float3( 0, 1.5f, 4.0f ), new float3( 0, 1.5f, 0.0f ), float3.UnitY ); m_cameraManipulator.InitializeCamera(new float3(0.0f, 2.73f, -6.0f), new float3(0.0f, 2.73f, 0.0f), float3.UnitY); m_startTime = DateTime.Now; Application.Idle += Application_Idle; }
protected override void OnLoad(EventArgs e) { base.OnLoad(e); m_Device.Init(viewportPanel.Handle, false, true); m_Device.Clear(m_Device.DefaultTarget, new RendererManaged.float4(Color.SkyBlue, 1)); Reg(m_CS = new ComputeShader(m_Device, new ShaderFile(new System.IO.FileInfo(@"Shaders/Test/TestCompute.hlsl")), "CS", null)); Reg(m_PS = new Shader(m_Device, new ShaderFile(new System.IO.FileInfo(@"Shaders/DisplayDistanceField.hlsl")), VERTEX_FORMAT.Pt4, "VS", null, "PS", null)); Reg(m_CB_Camera = new ConstantBuffer <CB_Camera>(m_Device, 0)); Reg(m_CB_Render = new ConstantBuffer <CB_Render>(m_Device, 8)); Build3DNoise(); ////////////////////////////////////////////////////////////////////////// // Photon Shooter Reg(m_CS_PhotonShooter = new ComputeShader(m_Device, new ShaderFile(new System.IO.FileInfo(@"Shaders/CanonicalCubeRenderer/PhotonShooter.hlsl")), "CS", null)); Reg(m_CB_PhotonShooterInput = new ConstantBuffer <CB_PhotonShooterInput>(m_Device, 8)); Reg(m_SB_PhotonOut = new StructuredBuffer <SB_PhotonOut>(m_Device, PHOTONS_COUNT, true)); BuildPhaseQuantileBuffer(new System.IO.FileInfo(@"Mie65536x2.float")); BuildRandomBuffer(); ////////////////////////////////////////////////////////////////////////// // Photons Splatter Reg(m_PS_PhotonSplatter = new Shader(m_Device, new ShaderFile(new System.IO.FileInfo(@"Shaders/CanonicalCubeRenderer/SplatPhoton.hlsl")), VERTEX_FORMAT.P3, "VS", "GS", "PS", null)); Reg(m_PS_PhotonSplatter_Intensity = new Shader(m_Device, new ShaderFile(new System.IO.FileInfo(@"Shaders/CanonicalCubeRenderer/SplatPhoton.hlsl")), VERTEX_FORMAT.P3, "VS", "GS", "PS_Intensity", null)); Reg(m_CB_SplatPhoton = new ConstantBuffer <CB_SplatPhoton>(m_Device, 8)); Reg(m_Tex_Photons = new Texture2D(m_Device, 512, 512, -6 * 4, 1, PIXEL_FORMAT.RGBA16_FLOAT, false, true, null)); // Build a single point that will be instanced as many times as there are photons { ByteBuffer Point = new ByteBuffer(3 * System.Runtime.InteropServices.Marshal.SizeOf(typeof(float3))); Reg(m_Prim_Point = new Primitive(m_Device, 1, Point, null, Primitive.TOPOLOGY.POINT_LIST, VERTEX_FORMAT.P3)); } ////////////////////////////////////////////////////////////////////////// // Photons Smoother Reg(m_PS_PhotonsSmooth = new Shader(m_Device, new ShaderFile(new System.IO.FileInfo(@"Shaders/CanonicalCubeRenderer/SmoothPhotons.hlsl")), VERTEX_FORMAT.P3, "VS", null, "PS", null)); Reg(m_PS_PhotonsUnsharpMask = new Shader(m_Device, new ShaderFile(new System.IO.FileInfo(@"Shaders/CanonicalCubeRenderer/SmoothPhotons.hlsl")), VERTEX_FORMAT.P3, "VS", null, "PS_HiFreq", null)); Reg(m_CB_SmoothPhotons = new ConstantBuffer <CB_SmoothPhotons>(m_Device, 8)); Reg(m_Tex_PhotonsSmooth = new Texture2D(m_Device, 512, 512, 6 * 4, 1, PIXEL_FORMAT.RGBA16_FLOAT, false, true, null)); Reg(m_Tex_PhotonsHiFreq = new Texture2D(m_Device, 512, 512, 6 * 4, 1, PIXEL_FORMAT.RGBA16_FLOAT, false, true, null)); ////////////////////////////////////////////////////////////////////////// // Photons Renderer Reg(m_PS_RenderCube = new Shader(m_Device, new ShaderFile(new System.IO.FileInfo(@"Shaders/CanonicalCubeRenderer/DisplayPhotonCube.hlsl")), VERTEX_FORMAT.P3N3, "VS", null, "PS", null)); BuildCube(); Reg(m_PS_RenderWorldCube = new Shader(m_Device, new ShaderFile(new System.IO.FileInfo(@"Shaders/DisplayWorldCube.hlsl")), VERTEX_FORMAT.P3N3, "VS", null, "PS", null)); ////////////////////////////////////////////////////////////////////////// // Photon Vectors Renderer Reg(m_PS_RenderPhotonVectors = new Shader(m_Device, new ShaderFile(new System.IO.FileInfo(@"Shaders/CanonicalCubeRenderer/DisplayPhotonVector.hlsl")), VERTEX_FORMAT.P3, "VS", null, "PS", null)); Reg(m_CB_RenderPhotonVector = new ConstantBuffer <CB_RenderPhotonVector>(m_Device, 8)); { ByteBuffer Line = VertexP3.FromArray(new VertexP3[] { new VertexP3() { P = new float3(0, 0, 0) }, new VertexP3() { P = new float3(1, 0, 0) } }); Reg(m_Prim_Line = new Primitive(m_Device, 2, Line, null, Primitive.TOPOLOGY.LINE_LIST, VERTEX_FORMAT.P3)); } // Create the camera manipulator m_CB_Camera.m.Camera2World = float4x4.Identity; UpdateCameraProjection(60.0f * (float)Math.PI / 180.0f, (float)viewportPanel.Width / viewportPanel.Height, 0.1f, 100.0f); m_Manipulator.Attach(viewportPanel); m_Manipulator.CameraTransformChanged += new CameraManipulator.UpdateCameraTransformEventHandler(Manipulator_CameraTransformChanged); m_Manipulator.InitializeCamera(new float3(0.0f, 0.0f, 4.0f), new float3(0, 0, 0), new float3(0, 1, 0)); }
void BuildPrimCylinder() { const int COUNT = 20; // Build 2 circles at Y=0 and Y=1 VertexP3[] Vertices = new VertexP3[2*COUNT]; for ( uint Y=0; Y < 2; Y++ ) { for ( uint X=0; X < COUNT; X++ ) { float phi = 2.0f * (float) Math.PI * X / COUNT; Vertices[COUNT*Y+X].P.Set( (float) Math.Cos( phi ), Y, (float) Math.Sin( phi ) ); } } // Link the 2 circles with quads List<uint> Indices = new List<uint>(); for ( uint X=0; X < COUNT; X++ ) { uint NX = (X+1) % COUNT; Indices.Add( X ); Indices.Add( COUNT+X ); Indices.Add( COUNT+NX ); Indices.Add( X ); Indices.Add( COUNT+NX ); Indices.Add( NX ); } // Cap the circles for ( uint X=1; X < COUNT-1; X++ ) { Indices.Add( 0 ); Indices.Add( X ); Indices.Add( X+1 ); Indices.Add( COUNT+0 ); Indices.Add( COUNT+X+1 ); // Indices reversed for bottom triangles, although we render in CULL_NONE so we don't really care... Indices.Add( COUNT+X ); } m_Prim_Cylinder = new Primitive( m_Device, 2*COUNT, VertexP3.FromArray( Vertices ), Indices.ToArray(), Primitive.TOPOLOGY.TRIANGLE_LIST, VERTEX_FORMAT.P3 ); }
void BuildPrimLobe() { const int RESOLUTION_THETA = 4 * LOBES_COUNT_THETA; const int RESOLUTION_PHI = 2 * RESOLUTION_THETA; #if true // FULL SPHERE VertexP3[] Vertices = new VertexP3[RESOLUTION_PHI*2*RESOLUTION_THETA]; for ( uint Y=0; Y < 2*RESOLUTION_THETA; Y++ ) { // float theta = 2.0f * (float) Math.Asin( Math.Sqrt( (float) Y / (2*RESOLUTION_THETA-1) ) ); float theta = (float) Math.PI * (float) Y / (2*RESOLUTION_THETA-1); for ( uint X=0; X < RESOLUTION_PHI; X++ ) { float phi = 2.0f * (float) Math.PI * X / RESOLUTION_PHI; Vertices[RESOLUTION_PHI*Y+X].P.Set( (float) (Math.Sin( theta ) * Math.Cos( phi )), (float) Math.Cos( theta ), -(float) (Math.Sin( theta ) * Math.Sin( phi )) ); // Phi=0 => +X, Phi=PI/2 => -Z in our Y-up frame } } List<uint> Indices = new List<uint>(); for ( uint Y=0; Y < 2*RESOLUTION_THETA-1; Y++ ) { uint IndexStart0 = RESOLUTION_PHI*Y; // Start index of top band uint IndexStart1 = RESOLUTION_PHI*(Y+1); // Start index of bottom band for ( uint X=0; X < RESOLUTION_PHI; X++ ) { Indices.Add( IndexStart0++ ); Indices.Add( IndexStart1++ ); } Indices.Add( IndexStart0-RESOLUTION_PHI ); // Loop Indices.Add( IndexStart1-RESOLUTION_PHI ); if ( Y != 2*RESOLUTION_THETA-1 ) { Indices.Add( IndexStart1-1 ); // Double current band's last index (first degenerate triangle => finish current band) Indices.Add( IndexStart0 ); // Double next band's first index (second degenerate triangle => start new band) } } m_Prim_Lobe = new Primitive( m_Device, RESOLUTION_PHI*2*RESOLUTION_THETA, VertexP3.FromArray( Vertices ), Indices.ToArray(), Primitive.TOPOLOGY.TRIANGLE_STRIP, VERTEX_FORMAT.P3 ); #else // HEMISPHERE VertexP3[] Vertices = new VertexP3[RESOLUTION_PHI*RESOLUTION_THETA]; for ( uint Y=0; Y < RESOLUTION_THETA; Y++ ) { // float theta = 2.0f * (float) Math.Asin( Math.Sqrt( 0.5 * Y / (RESOLUTION_THETA-1) ) ); float theta = 0.5f * (float) Math.PI * Y / (RESOLUTION_THETA-1); for ( uint X=0; X < RESOLUTION_PHI; X++ ) { float phi = 2.0f * (float) Math.PI * X / RESOLUTION_PHI; Vertices[RESOLUTION_PHI*Y+X].P.Set( (float) (Math.Sin( theta ) * Math.Cos( phi )), (float) Math.Cos( theta ), -(float) (Math.Sin( theta ) * Math.Sin( phi )) ); // Phi=0 => +X, Phi=PI/2 => -Z in our Y-up frame } } List<uint> Indices = new List<uint>(); for ( uint Y=0; Y < RESOLUTION_THETA-1; Y++ ) { uint IndexStart0 = RESOLUTION_PHI*Y; // Start index of top band uint IndexStart1 = RESOLUTION_PHI*(Y+1); // Start index of bottom band for ( uint X=0; X < RESOLUTION_PHI; X++ ) { Indices.Add( IndexStart0++ ); Indices.Add( IndexStart1++ ); } Indices.Add( IndexStart0-RESOLUTION_PHI ); // Loop Indices.Add( IndexStart1-RESOLUTION_PHI ); if ( Y != RESOLUTION_THETA-1 ) { Indices.Add( IndexStart1-1 ); // Double current band's last index (first degenerate triangle => finish current band) Indices.Add( IndexStart0 ); // Double next band's first index (second degenerate triangle => start new band) } } m_Prim_Lobe = new Primitive( m_Device, RESOLUTION_PHI*RESOLUTION_THETA, VertexP3.FromArray( Vertices ), Indices.ToArray(), Primitive.TOPOLOGY.TRIANGLE_STRIP, VERTEX_FORMAT.P3 ); #endif }
void BuildPrimHeightfield() { VertexP3[] Vertices = new VertexP3[HEIGHTFIELD_SIZE*HEIGHTFIELD_SIZE]; for ( uint Y=0; Y < HEIGHTFIELD_SIZE; Y++ ) { float y = -1.0f + 2.0f * Y / (HEIGHTFIELD_SIZE-1); for ( uint X=0; X < HEIGHTFIELD_SIZE; X++ ) { float x = -1.0f + 2.0f * X / (HEIGHTFIELD_SIZE-1); Vertices[HEIGHTFIELD_SIZE*Y+X].P.Set( x, y, 0.0f ); } } List< uint > Indices = new List< uint >(); for ( uint Y=0; Y < HEIGHTFIELD_SIZE-1; Y++ ) { uint IndexStart0 = HEIGHTFIELD_SIZE*Y; // Start index of top band uint IndexStart1 = HEIGHTFIELD_SIZE*(Y+1); // Start index of bottom band for ( uint X=0; X < HEIGHTFIELD_SIZE; X++ ) { Indices.Add( IndexStart0++ ); Indices.Add( IndexStart1++ ); } if ( Y != HEIGHTFIELD_SIZE-1 ) { Indices.Add( IndexStart1-1 ); // Double current band's last index (first degenerate triangle => finish current band) Indices.Add( IndexStart0 ); // Double next band's first index (second degenerate triangle => start new band) } } m_Prim_Heightfield = new Primitive( m_Device, HEIGHTFIELD_SIZE*HEIGHTFIELD_SIZE, VertexP3.FromArray( Vertices ), Indices.ToArray(), Primitive.TOPOLOGY.TRIANGLE_STRIP, VERTEX_FORMAT.P3 ); }