private void Init(TreeSkeleton skeleton) { if (skeleton.Leaves.Count == 0) { return; } Matrix[] transforms = new Matrix[skeleton.Branches.Count]; skeleton.CopyAbsoluteBranchTransformsTo(transforms); Vector3 center = Vector3.Zero; for (int i = 0; i < skeleton.Leaves.Count; i++) { center += transforms[skeleton.Leaves[i].ParentIndex].Translation; } center = center / (float)skeleton.Leaves.Count; LeafVertex[] vertices = new LeafVertex[skeleton.Leaves.Count * 4]; short[] indices = new short[skeleton.Leaves.Count * 6]; int vindex = 0; int iindex = 0; boundingSphere.Center = center; boundingSphere.Radius = 0.0f; foreach (TreeLeaf leaf in skeleton.Leaves) { // Get the position of the leaf Vector3 position = transforms[leaf.ParentIndex].Translation + transforms[leaf.ParentIndex].Up * skeleton.Branches[leaf.ParentIndex].Length; if (skeleton.LeafAxis != null) { position += skeleton.LeafAxis.Value * leaf.AxisOffset; } // Orientation Vector2 right = new Vector2((float)Math.Cos(leaf.Rotation), (float)Math.Sin(leaf.Rotation)); Vector2 up = new Vector2(-right.Y, right.X); // Scale vectors by size right = leaf.Size.X * right; up = leaf.Size.Y * up; // Choose a normal vector for lighting calculations float distanceFromCenter = Vector3.Distance(position, center); Vector3 normal = (position - center) / distanceFromCenter; // normalize the normal // 0---1 // Vertex positions: | \ | // 3---2 int vidx = vindex; vertices[vindex++] = new LeafVertex(position, new Vector2(0, 0), -right + up, leaf.Color, leaf.BoneIndex, normal); vertices[vindex++] = new LeafVertex(position, new Vector2(1, 0), right + up, leaf.Color, leaf.BoneIndex, normal); vertices[vindex++] = new LeafVertex(position, new Vector2(1, 1), right - up, leaf.Color, leaf.BoneIndex, normal); vertices[vindex++] = new LeafVertex(position, new Vector2(0, 1), -right - up, leaf.Color, leaf.BoneIndex, normal); // Add indices indices[iindex++] = (short)(vidx); indices[iindex++] = (short)(vidx + 1); indices[iindex++] = (short)(vidx + 2); indices[iindex++] = (short)(vidx); indices[iindex++] = (short)(vidx + 2); indices[iindex++] = (short)(vidx + 3); // Update the bounding sphere float size = leaf.Size.Length() / 2.0f; boundingSphere.Radius = Math.Max(boundingSphere.Radius, distanceFromCenter + size); } // Create the vertex declaration vdeclaration = new VertexDeclaration(LeafVertex.VertexElements); // Create the buffers vbuffer = new VertexBuffer(device, vdeclaration, vertices.Length, BufferUsage.WriteOnly); vbuffer.SetData <LeafVertex>(vertices); ibuffer = new IndexBuffer(device, IndexElementSize.SixteenBits, indices.Length, BufferUsage.WriteOnly); ibuffer.SetData <short>(indices); // Remember the number of leaves numleaves = skeleton.Leaves.Count; }
private void Init(TreeSkeleton skeleton) { if (skeleton.Leaves.Count == 0) return; var transforms = new Matrix[skeleton.Branches.Count]; skeleton.CopyAbsoluteBranchTransformsTo(transforms); Vector3 center = Vector3.Zero; for (int i = 0; i < skeleton.Leaves.Count; i++) { center += transforms[skeleton.Leaves[i].ParentIndex].Translation; } center = center/(float) skeleton.Leaves.Count; var vertices = new LeafVertex[skeleton.Leaves.Count*4]; var indices = new short[skeleton.Leaves.Count*6]; int vindex = 0; int iindex = 0; boundingSphere.Center = center; boundingSphere.Radius = 0.0f; foreach (TreeLeaf leaf in skeleton.Leaves) { // Get the position of the leaf Vector3 position = transforms[leaf.ParentIndex].Translation + transforms[leaf.ParentIndex].Up*skeleton.Branches[leaf.ParentIndex].Length; if (skeleton.LeafAxis != null) { position += skeleton.LeafAxis.Value*leaf.AxisOffset; } // Orientation var right = new Vector2((float) Math.Cos(leaf.Rotation), (float) Math.Sin(leaf.Rotation)); var up = new Vector2(-right.Y, right.X); // Scale vectors by size right = leaf.Size.X*right; up = leaf.Size.Y*up; // Choose a normal vector for lighting calculations float distanceFromCenter = Vector3.Distance(position, center); Vector3 normal = (position - center)/distanceFromCenter; // normalize the normal // 0---1 // Vertex positions: | \ | // 3---2 int vidx = vindex; vertices[vindex++] = new LeafVertex(position, new Vector2(0, 0), -right + up, leaf.Color, leaf.BoneIndex, normal); vertices[vindex++] = new LeafVertex(position, new Vector2(1, 0), right + up, leaf.Color, leaf.BoneIndex, normal); vertices[vindex++] = new LeafVertex(position, new Vector2(1, 1), right - up, leaf.Color, leaf.BoneIndex, normal); vertices[vindex++] = new LeafVertex(position, new Vector2(0, 1), -right - up, leaf.Color, leaf.BoneIndex, normal); // Add indices indices[iindex++] = (short) (vidx); indices[iindex++] = (short) (vidx + 1); indices[iindex++] = (short) (vidx + 2); indices[iindex++] = (short) (vidx); indices[iindex++] = (short) (vidx + 2); indices[iindex++] = (short) (vidx + 3); // Update the bounding sphere float size = leaf.Size.Length()/2.0f; boundingSphere.Radius = Math.Max(boundingSphere.Radius, distanceFromCenter + size); } // Create the buffers vbuffer = new VertexBuffer(device, vertices.Length*LeafVertex.SizeInBytes, BufferUsage.None); vbuffer.SetData<LeafVertex>(vertices); ibuffer = new IndexBuffer(device, indices.Length*sizeof (short), BufferUsage.None, IndexElementSize.SixteenBits); ibuffer.SetData<short>(indices); // Create the vertex declaration vdeclaration = new VertexDeclaration(device, LeafVertex.VertexElements); // Remember the number of leaves numleaves = skeleton.Leaves.Count; }