DynamicModelWriter.cs 5.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134
  1. #region License
  2. // Copyright 2016 Kastellanos Nikolaos
  3. //
  4. // Licensed under the Apache License, Version 2.0 (the "License");
  5. // you may not use this file except in compliance with the License.
  6. // You may obtain a copy of the License at
  7. //
  8. // http://www.apache.org/licenses/LICENSE-2.0
  9. //
  10. // Unless required by applicable law or agreed to in writing, software
  11. // distributed under the License is distributed on an "AS IS" BASIS,
  12. // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13. // See the License for the specific language governing permissions and
  14. // limitations under the License.
  15. #endregion
  16. using System;
  17. using System.Collections.Generic;
  18. using Microsoft.Xna.Framework;
  19. using Microsoft.Xna.Framework.Content.Pipeline;
  20. using Microsoft.Xna.Framework.Content.Pipeline.Processors;
  21. using Microsoft.Xna.Framework.Content.Pipeline.Serialization.Compiler;
  22. using nkast.Aether.Content.Pipeline.Graphics;
  23. namespace nkast.Aether.Content.Pipeline.Serialization
  24. {
  25. [ContentTypeWriter]
  26. class DynamicModelWriter : ContentTypeWriter<DynamicModelContent>
  27. {
  28. /// <summary>
  29. /// Write a Model xnb, compatible with the XNB Container Format.
  30. /// </summary>
  31. protected override void Write(ContentWriter output, DynamicModelContent model)
  32. {
  33. WriteBones(output, model.Bones);
  34. WriteMeshes(output, model, model.Meshes);
  35. WriteBoneReference(output, model.Bones.Count, model.Source.Root);
  36. output.WriteObject(model.Source.Tag);
  37. return;
  38. }
  39. private void WriteBones(ContentWriter output, ModelBoneContentCollection bones)
  40. {
  41. int bonesCount = bones.Count;
  42. output.Write((UInt32)bonesCount);
  43. foreach (ModelBoneContent bone in bones)
  44. {
  45. output.WriteObject(bone.Name);
  46. output.Write(bone.Transform);
  47. }
  48. foreach (ModelBoneContent bone in bones)
  49. {
  50. WriteBoneReference(output, bonesCount, bone.Parent);
  51. output.Write((uint)bone.Children.Count);
  52. foreach (ModelBoneContent child in bone.Children)
  53. WriteBoneReference(output, bonesCount, child);
  54. }
  55. return;
  56. }
  57. // The BoneReference type varies in size depending on the number of bones in the model.
  58. // If bone count is less than 255 this value is serialized as a Byte, otherwise it is UInt32.
  59. // If the reference value is zero the bone is null, otherwise (bone reference - 1) is an index into the model bone list.
  60. private void WriteBoneReference(ContentWriter output, int bonesCount, ModelBoneContent bone)
  61. {
  62. if (bone == null)
  63. output.Write((byte)0);
  64. else if (bonesCount < 255)
  65. output.Write((byte)(bone.Index + 1));
  66. else
  67. output.Write((UInt32)(bone.Index + 1));
  68. }
  69. private void WriteMeshes(ContentWriter output, DynamicModelContent model, List<DynamicModelMeshContent> meshes)
  70. {
  71. output.Write((UInt32)meshes.Count);
  72. int bonesCount = model.Bones.Count;
  73. foreach (DynamicModelMeshContent mesh in meshes)
  74. {
  75. output.WriteObject(mesh.Name);
  76. WriteBoneReference(output, bonesCount, mesh.ParentBone);
  77. WriteBoundingSphere(output, mesh.BoundingSphere);
  78. output.WriteObject(mesh.Tag);
  79. WriteParts(output, model, mesh.MeshParts);
  80. }
  81. return;
  82. }
  83. private void WriteBoundingSphere(ContentWriter output, BoundingSphere value)
  84. {
  85. output.Write(value.Center);
  86. output.Write(value.Radius);
  87. }
  88. private void WriteParts(ContentWriter output, DynamicModelContent model, List<DynamicModelMeshPartContent> parts)
  89. {
  90. output.Write((UInt32)parts.Count);
  91. foreach (DynamicModelMeshPartContent part in parts)
  92. {
  93. output.Write((UInt32)part.VertexOffset);
  94. output.Write((UInt32)part.NumVertices);
  95. output.Write((UInt32)part.StartIndex);
  96. output.Write((UInt32)part.PrimitiveCount);
  97. output.WriteObject(part.Tag);
  98. output.WriteSharedResource(part.VertexBuffer);
  99. output.WriteSharedResource(part.IndexBuffer);
  100. output.WriteSharedResource(part.Material);
  101. }
  102. return;
  103. }
  104. public override string GetRuntimeType(TargetPlatform targetPlatform)
  105. {
  106. return "Microsoft.Xna.Framework.Graphics.Model";
  107. }
  108. public override string GetRuntimeReader(TargetPlatform targetPlatform)
  109. {
  110. return "Microsoft.Xna.Framework.Content.ModelReader, Microsoft.Xna.Framework.Graphics, Version=4.0.0.0, Culture=neutral, PublicKeyToken=842cf8be1de50553";
  111. }
  112. }
  113. }