⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 meshloader.cs

📁 功能:基于windows mobile 的地图查看器。使用vs2005开发
💻 CS
📖 第 1 页 / 共 3 页
字号:
            try
            {
                // Managed Direct3D mobile uses different Fvf defines than
                // managed Direct3D for the desktop
                // when this code is linked against the desktop version
                // this will convert the Fvf to match MD3DM constants
                // when this code is linked against MD3DM this section will
                // not have changed anything.

                // determine the necessary Fvf
                sourceVertexFormat = mesh.VertexFormat;
                int textureCount;
                sourceFormat = VertexFormats.Position;
                flexibleVertexFormat = 0;
    
                if ((sourceVertexFormat & VertexFormats.Normal) != 0)
                {
                    flexibleVertexFormat |= md3dmFvfNormal;
                    sourceFormat |= VertexFormats.Normal;
                }
    
                if ((sourceVertexFormat & VertexFormats.Diffuse) != 0)
                {
                    flexibleVertexFormat |= md3dmFvfDiffuse;
                    sourceFormat |= VertexFormats.Diffuse;
                }
    
                if ((sourceVertexFormat & VertexFormats.Specular) != 0)
                {
                    flexibleVertexFormat |= md3dmFvfDiffuse;
                    sourceFormat |= VertexFormats.Specular;
                }
    
                // determine number of textures
                textureCount = (int)(sourceVertexFormat & 
                    VertexFormats.TextureCountMask) >> 
                    (int)VertexFormats.TextureCountShift;
    
                //limit to 4 textures
                if (textureCount > 4)
                    textureCount = 4;
    
                // continue setting up necessary fvf
                sourceFormat |= (VertexFormats)(textureCount << 
                    (int)VertexFormats.TextureCountShift);
                flexibleVertexFormat |= 
                    (textureCount << md3dmFvfTextureCountShift);
    
                if (sourceFormat != sourceVertexFormat)
                {
                    mesh = mesh.Clone(mesh.Options.Value, sourceFormat, 
                        mesh.Device);
                    tempMesh = (IDisposable)mesh;
                }

                attributeRanges = mesh.GetAttributeTable();
            
                if (attributeRanges == null)
                {
                    throw new MeshSerializationException(
                        "No Attribute table present");
                }
    
                // determine number of vertices and create buffer
                numberVertices = mesh.NumberVertices;
                vertices = new byte[numberVertices * 
                    VertexInformation.GetFormatSize(sourceFormat)];

                // copy vertices to buffer
                mesh.VertexBuffer.Lock(0, vertices.Length, 
                    LockFlags.None).Read(vertices, 0, vertices.Length);
                mesh.VertexBuffer.Unlock();

                // determine number of indices
                numberIndices = mesh.NumberFaces * 3;
            
                // create index data buffer
                indices = new byte[numberIndices * 
                    (mesh.Options.Use32Bit ? 4 : 2)];

                // fill index data into buffer
                mesh.IndexBuffer.Lock(0, indices.Length, 
                    LockFlags.None).Read(indices, 0, indices.Length);
                mesh.IndexBuffer.Unlock();

                // write the data out to file
                MeshLoader.SaveMeshData(stream, flexibleVertexFormat, 
                    numberVertices, vertices,
                    numberIndices, indices, attributeRanges, materials,
                    textures);
            }
            finally
            {
                if (tempMesh != null)
                {
                    tempMesh.Dispose();
                }
            }
        }

        /// <summary>
        /// Serializes mesh data to a custom format
        /// </summary>
        /// <param name="stream">The stream to which to serialize</param>
        /// <param name="flexibleVertexFormat">The Fvf of the vertex data
        /// </param>
        /// <param name="numberVertices">The number of vertices in the vertex
        /// data</param>
        /// <param name="vertices">The buffer of vertex data</param>
        /// <param name="numberIndices">The number of indices in the index
        /// data</param>
        /// <param name="indices">The buffer of index data</param>
        /// <param name="attributeRanges">The attribute ranges to
        /// serialize</param>
        /// <param name="materials">The materials for the mesh subparts
        /// </param>
        /// <param name="textures">The texture filenames for the mesh
        /// subparts</param>
        /// 
        public static void SaveMeshData(Stream stream, 
            int flexibleVertexFormat, int numberVertices,
            byte [] vertices, int numberIndices, 
            byte [] indices, AttributeRange [] attributeRanges, 
            Material [] materials, string [] textures)
        {

            if(numberIndices <= 0)
                throw new ArgumentException("NumberIndices <= 0");
            if(numberVertices <= 0)
                throw new ArgumentException("NumberVertices <= 0");

            // calculate the size of the vertex buffer
            int bytesVertices = vertices.Length;

            // verify 16 or 32 bit indices
            int bytesPerIndex = indices.Length / numberIndices;
            if ((bytesPerIndex != 2) && (bytesPerIndex != 4))
                throw new MeshSerializationException(
                    "Indices are neither 16 nor 32 bit");

            int is16BitIndices = (bytesPerIndex == 2) ? 1 : 0;

            // verify the same number of materials as texture names
            if (materials.Length != textures.Length)
                throw new MeshSerializationException(
                    "The number of textures must" +
                    " match the number of materials");

            // determine the number of materials and attribue ranges
            int numberMaterials = materials.Length;
            int numberAttrRanges = attributeRanges.Length;

            // determine the offsets
            int offsetVertex = sizeofHeader;
            int offsetIndices = offsetVertex + vertices.Length;
            int offsetAttrRange = offsetIndices + indices.Length;
            int offsetMaterial = offsetAttrRange + numberAttrRanges * 
                sizeofAttributeRange;

            // go to the beginning of the stream
            stream.Seek(0, SeekOrigin.Begin);

            // write the header
            stream.Write(BitConverter.GetBytes(magicNumber), 0, 4);
            stream.Write(BitConverter.GetBytes(versionNumber), 0, 4);
            stream.Write(BitConverter.GetBytes(flexibleVertexFormat), 0, 4);
            stream.Write(BitConverter.GetBytes(numberVertices), 0, 4);
            stream.Write(BitConverter.GetBytes(numberIndices), 0, 4);
            stream.Write(BitConverter.GetBytes(is16BitIndices), 0, 4);
            stream.Write(BitConverter.GetBytes(numberMaterials), 0, 4);
            stream.Write(BitConverter.GetBytes(numberAttrRanges), 0, 4);
            stream.Write(BitConverter.GetBytes(offsetVertex), 0, 4);
            stream.Write(BitConverter.GetBytes(offsetIndices), 0, 4);
            stream.Write(BitConverter.GetBytes(offsetAttrRange), 0, 4);
            stream.Write(BitConverter.GetBytes(offsetMaterial), 0, 4);
        
            // write a 0 length for BytesMaterials right now
            // the correct value will be filled in once it is known
            stream.Write(BitConverter.GetBytes(0), 0, 4); 

            // write the vertex and index information
            stream.Write(vertices, 0, vertices.Length);
            stream.Write(indices, 0, indices.Length);

            // write the attribute range information
            foreach (AttributeRange attr in attributeRanges)
            {
                stream.Write(BitConverter.GetBytes(attr.AttributeId), 0, 4);
                stream.Write(BitConverter.GetBytes(attr.FaceStart), 0, 4);
                stream.Write(BitConverter.GetBytes(attr.FaceCount), 0, 4);
                stream.Write(BitConverter.GetBytes(attr.VertexStart), 0, 4);
                stream.Write(BitConverter.GetBytes(attr.VertexCount), 0, 4);
            }

            // write the material information
            for (int i = 0; i < materials.Length; i++)
            {
                stream.Write(BitConverter.GetBytes(
                    materials[i].DiffuseColor.Red  ), 0, 4); 
                stream.Write(BitConverter.GetBytes(
                    materials[i].DiffuseColor.Green), 0, 4); 
                stream.Write(BitConverter.GetBytes(
                    materials[i].DiffuseColor.Blue ), 0, 4); 
                stream.Write(BitConverter.GetBytes(
                    materials[i].DiffuseColor.Alpha), 0, 4); 
                stream.Write(BitConverter.GetBytes(
                    materials[i].AmbientColor.Red  ), 0, 4);                  
                stream.Write(BitConverter.GetBytes(
                    materials[i].AmbientColor.Green), 0, 4); 
                stream.Write(BitConverter.GetBytes(
                    materials[i].AmbientColor.Blue ), 0, 4); 
                stream.Write(BitConverter.GetBytes(
                    materials[i].AmbientColor.Alpha), 0, 4); 
                stream.Write(BitConverter.GetBytes(
                    materials[i].SpecularColor.Red  ), 0, 4); 
                stream.Write(BitConverter.GetBytes(
                    materials[i].SpecularColor.Green), 0, 4);
                stream.Write(BitConverter.GetBytes(
                    materials[i].SpecularColor.Blue ), 0, 4);
                stream.Write(BitConverter.GetBytes(
                    materials[i].SpecularColor.Alpha), 0, 4);
                stream.Write(BitConverter.GetBytes(
                    materials[i].SpecularSharpness), 0, 4);

                if (textures[i] != null)
                {
                    byte [] rgb = Encoding.Unicode.GetBytes(textures[i]);
                    stream.Write(BitConverter.GetBytes(rgb.Length), 0, 4);
                    stream.Write(rgb, 0, rgb.Length);
                }
                else
                    stream.Write(BitConverter.GetBytes((int)0), 0, 4);
            }

            // go back to fill in the length of the materials section
            long currentPosition = stream.Position;
            int bytesMaterials = (int)(stream.Position - offsetMaterial);
            stream.Seek((int)48, SeekOrigin.Begin);
            stream.Write(BitConverter.GetBytes(0), 0, 4);
            stream.Seek(currentPosition, SeekOrigin.Begin);
        }
    }
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -