コード例 #1
0
        public static List <Dictionary <string, dynamic> > parseVertexBuffers(ExpandoObject staticTgxBin, dynamic staticRenderMesh)
        {
            dynamic tgxBin     = staticTgxBin;
            dynamic renderMesh = staticRenderMesh;

            if (renderMesh.GetProperty("stage_part_vertex_stream_layout_definitions").GetArrayLength() > 1)
            {
                ConsoleEx.Warn("Multiple Stage Part Vertex Layout Definitions", renderMesh.GetProperty("stage_part_vertex_stream_layout_definitions"));
            }
            dynamic stagePartVertexStreamLayoutDefinition = renderMesh.GetProperty("stage_part_vertex_stream_layout_definitions")[0];
            dynamic formats = stagePartVertexStreamLayoutDefinition.GetProperty("formats");

            List <Dictionary <string, dynamic> > vertexBuffer = new List <Dictionary <string, dynamic> >();

            for (var vertexBufferIndex = 0; vertexBufferIndex < renderMesh.GetProperty("vertex_buffers").GetArrayLength(); vertexBufferIndex++)
            {
                dynamic vertexBufferInfo = renderMesh.GetProperty("vertex_buffers")[vertexBufferIndex];
                byte[]  vertexBufferData = tgxBin.files[vertexBufferInfo.GetProperty("file_name").GetString()].data;
                dynamic format           = formats[vertexBufferIndex];

                var vertexIndex = 0;
                for (var v = 0; v < vertexBufferInfo.GetProperty("byte_size").GetInt32(); v += vertexBufferInfo.GetProperty("stride_byte_size").GetInt32())
                {
                    var vertexOffset = v;
                    if (vertexBuffer.Count <= vertexIndex)
                    {
                        vertexBuffer.Add(new Dictionary <string, dynamic>());                                                     //vertexBuffer[vertexIndex] = new JObject();
                    }
                    for (var e = 0; e < format.GetProperty("elements").GetArrayLength(); e++)
                    {
                        dynamic        element  = format.GetProperty("elements")[e];
                        List <dynamic> values   = new List <dynamic>();
                        List <byte>    rawBytes = new List <byte>();

                        string   elementType = element.GetProperty("type").GetString().Replace("_vertex_format_attribute_", "");
                        string[] types       = new string[] { "ubyte", "byte", "ushort", "short", "uint", "int", "float" };
                        foreach (var typeIndex in types)
                        {
                            string type = typeIndex;
                            if (elementType.IndexOf(type) == 0)
                            {
                                var     count = Convert.ToInt32(elementType.Replace(type, ""));
                                var     j     = 0;
                                dynamic value;
                                switch (type)
                                {
                                case "ubyte":
                                    for (j = 0; j < count; j++)
                                    {
                                        value = vertexBufferData[vertexOffset];
                                        if (element.GetProperty("normalized").GetBoolean())
                                        {
                                            value = TGXMUtils.unormalize(value, 8);
                                        }
                                        values.Add(value);
                                        rawBytes.Add(vertexBufferData[vertexOffset]);
                                        vertexOffset++;
                                    }
                                    break;

                                case "byte":
                                    for (j = 0; j < count; j++)
                                    {
                                        value = TGXMUtils.Sbyte(vertexBufferData, vertexOffset);
                                        if (element.GetProperty("normalized").GetBoolean())
                                        {
                                            value = TGXMUtils.normalize(value, 8);
                                        }
                                        values.Add(value);
                                        rawBytes.Add(vertexBufferData[vertexOffset]);
                                        vertexOffset++;
                                    }
                                    break;

                                case "ushort":
                                    for (j = 0; j < count; j++)
                                    {
                                        value = BitConverter.ToUInt16(vertexBufferData, vertexOffset);
                                        if (element.GetProperty("normalized").GetBoolean)
                                        {
                                            value = TGXMUtils.unormalize(value, 16);
                                        }
                                        values.Add(value);
                                        rawBytes.Add(vertexBufferData[vertexOffset]);
                                        rawBytes.Add(vertexBufferData[vertexOffset + 1]);
                                        vertexOffset += 2;
                                    }
                                    break;

                                case "short":
                                    for (j = 0; j < count; j++)
                                    {
                                        value = BitConverter.ToInt16(vertexBufferData, vertexOffset);
                                        if (element.GetProperty("normalized").GetBoolean())
                                        {
                                            value = TGXMUtils.normalize(value, 16);
                                        }
                                        values.Add(value);
                                        rawBytes.Add(vertexBufferData[vertexOffset]);
                                        rawBytes.Add(vertexBufferData[vertexOffset + 1]);
                                        vertexOffset += 2;
                                    }
                                    break;

                                case "uint":
                                    for (j = 0; j < count; j++)
                                    {
                                        value = BitConverter.ToUInt32(vertexBufferData, vertexOffset);
                                        if (element.GetProperty("normalized").GetBoolean())
                                        {
                                            value = TGXMUtils.unormalize(value, 32);
                                        }
                                        values.Add(value);
                                        rawBytes.Add(vertexBufferData[vertexOffset]);
                                        rawBytes.Add(vertexBufferData[vertexOffset + 1]);
                                        rawBytes.Add(vertexBufferData[vertexOffset + 2]);
                                        rawBytes.Add(vertexBufferData[vertexOffset + 3]);
                                        vertexOffset += 4;
                                    }
                                    break;

                                case "int":
                                    for (j = 0; j < count; j++)
                                    {
                                        value = BitConverter.ToInt32(vertexBufferData, vertexOffset);
                                        if (element.GetProperty("normalized").GetBoolean())
                                        {
                                            value = TGXMUtils.normalize(value, 32);
                                        }
                                        values.Add(value);
                                        rawBytes.Add(vertexBufferData[vertexOffset]);
                                        rawBytes.Add(vertexBufferData[vertexOffset + 1]);
                                        rawBytes.Add(vertexBufferData[vertexOffset + 2]);
                                        rawBytes.Add(vertexBufferData[vertexOffset + 3]);
                                        vertexOffset += 4;
                                    }
                                    break;

                                case "float":
                                    for (j = 0; j < count; j++)
                                    {
                                        value = BitConverter.ToSingle(vertexBufferData, vertexOffset);
                                        values.Add(value);
                                        rawBytes.Add(vertexBufferData[vertexOffset]);
                                        rawBytes.Add(vertexBufferData[vertexOffset + 1]);
                                        rawBytes.Add(vertexBufferData[vertexOffset + 2]);
                                        rawBytes.Add(vertexBufferData[vertexOffset + 3]);
                                        vertexOffset += 4;
                                    }
                                    break;
                                }
                                break;
                            }
                        }

                        string semantic = element.GetProperty("semantic").GetString().Replace("_tfx_vb_semantic_", "");
                        switch (semantic)
                        {
                        case "position":
                        case "normal":
                        case "tangent":
                        case "blendweight":                                 // Bone weights 0-1
                        case "blendindices":                                // Bone indices, 255=none, index starts at 1?
                        case "color":
                            break;

                        case "texcoord":
                            semantic = "uv";
                            break;

                        default:
                            Console.WriteLine($"Unknown Vertex Semantic : {semantic} : {element.semantic_index}");
                            break;
                        }
                        int semantic_index = (int)element.GetProperty("semantic_index").GetInt32();
                        if (semantic_index != 0)
                        {
                            semantic_index--;
                        }
                        vertexBuffer[vertexIndex].Add(semantic + semantic_index, values.ToArray());
                        vertexBuffer[vertexIndex].Add(semantic + semantic_index + "_raw", rawBytes.ToArray());
                    }
                    vertexIndex++;
                }
            }
            return(vertexBuffer);
        }
コード例 #2
0
        public static dynamic loadTGXBin(byte[] data)
        {
            Console.WriteLine("Loading model data...");

            Console.Write("Reading TGXM header... ");
            string magic          = TGXMUtils.String(data, 0x0, 0x4);    // TGXM
            int    version        = (int)BitConverter.ToUInt32(data, 0x4);
            int    fileOffset     = (int)BitConverter.ToUInt32(data, 0x8);
            int    fileCount      = (int)BitConverter.ToUInt32(data, 0xC);
            string fileIdentifier = TGXMUtils.String(data, 0x10, 0x100);

            if (magic != "TGXM")
            {
                Console.WriteLine("Invalid TGX File, skipping");
                return(null);
            }
            Console.WriteLine("Done.");

            Dictionary <string, dynamic> files = new Dictionary <string, dynamic>();
            //dynamic fileLookup = new JArray();
            dynamic renderMetadata = new Object();

            for (var f = 0; f < fileCount; f++)
            //Parallel.For(0, fileCount, f =>
            {
                int    headerOffset = fileOffset + (0x110 * f);
                string name         = TGXMUtils.String(data, headerOffset, 0x100);
                int    offset       = (int)BitConverter.ToUInt32(data, headerOffset + 0x100);
                int    type         = (int)BitConverter.ToUInt32(data, headerOffset + 0x104);
                int    size         = (int)BitConverter.ToUInt32(data, headerOffset + 0x108);
                Console.WriteLine("Loading file \"" + name + ".\" File size: " + size + " bytes.");
                byte[] fileData = new byte[size];
                if (!File.Exists(Path.Combine("Tilemaps", $"{name}.dds")))
                {
                    Array.ConstrainedCopy(data, offset, fileData, 0, size);
                }
                else
                {
                    fileData = File.ReadAllBytes(Path.Combine("Tilemaps", $"{name}.dds"));
                }

                dynamic file = new ExpandoObject();
                file.name   = name;
                file.offset = offset;
                file.type   = type;
                file.size   = size;

                if (name.IndexOf(".js") != -1)
                {                 // render_metadata.js
                    renderMetadata = JsonSerializer.Deserialize <RenderMetadata>(TGXMUtils.String(fileData, 0, 0));
                    files.Add("render_metadata_js", fileData);
                    file.data = renderMetadata;
                }
                else
                {
                    file.data = fileData;
                }

                files.Add(name, file);
                //fileLookup.Add(name);
                Console.WriteLine("File \"" + name + "\" loaded.");
            }            //);

            dynamic tgxBin = new ExpandoObject();

            tgxBin.fileIdentifier = fileIdentifier;
            tgxBin.files          = files;
            //tgxBin.lookup = fileLookup;
            tgxBin.metadata = renderMetadata;

            Console.WriteLine("Done loading model data.");
            return(tgxBin);
        }