示例#1
0
        // Methods
        public override void Load(Stream fileStream,
                                  Dictionary <string, SetObjectType> objectTemplates)
        {
            // Header
            var reader = new BINAReader(fileStream);

            Header = reader.ReadHeader();

            reader.JumpAhead(0x2C); // Skip "test" string
            uint objectLength = reader.ReadUInt32();
            uint objectOffset = reader.ReadUInt32();
            uint groupLength  = reader.ReadUInt32();
            uint groupOffset  = reader.ReadUInt32();

            Console.WriteLine($"Object Count: {objectLength}");
            Console.WriteLine($"Object Table Offset Location: {objectOffset}");
            Console.WriteLine($"Group Count: {groupLength}");
            Console.WriteLine($"Group Table Offset Location: {groupOffset}");

            //Groups
            reader.JumpTo(groupOffset, false);
            for (uint i = 0; i < groupLength; ++i)
            {
                //What we know so far:
                //First 4 bytes is a name for the group (usually GroupHelperXX?)
                //Second 4 bytes are the type? (according to LibS06), might be a second name (stuff like next_set/GroupHelperXX)?
                //Third 4 bytes is the amount of objects in this group.
                //Last 4 bytes is a list of the object IDs in this group.

                uint nameOffset        = reader.ReadUInt32(); //Name
                uint typeOffset        = reader.ReadUInt32(); //Type?
                uint groupObjectCount  = reader.ReadUInt32(); //Count
                uint groupObjectOffset = reader.ReadUInt32(); //Address of Objects

                string groupName = string.Empty;
                string groupType = string.Empty;

                long pos = reader.BaseStream.Position;

                reader.JumpTo(nameOffset, false);
                groupName = reader.ReadNullTerminatedString();
                groupNames.Add(groupName);

                reader.JumpTo(typeOffset, false);
                groupType = reader.ReadNullTerminatedString();
                groupTypes.Add(groupType);

                reader.JumpTo(groupObjectOffset, false);
                for (int c = 0; c < groupObjectCount; c++)
                {
                    reader.JumpAhead(4);
                    uint objID = reader.ReadUInt32();
                    objGroupData.Add($"{groupName}|{groupType}|{objID}");
                    groupIDs.Add(objID);
                }

                reader.JumpTo(pos, true);
            }

            // Data
            reader.JumpTo(objectOffset, false);
            for (uint i = 0; i < objectLength; ++i)
            {
                Objects.Add(ReadObject(i));
            }

            // TODO: Read Footer

            // Sub-Methods
            SetObject ReadObject(uint id)
            {
                // Object Entry
                var  obj        = new SetObject();
                uint nameOffset = reader.ReadUInt32();
                uint typeOffset = reader.ReadUInt32();

                reader.JumpAhead(16);

                obj.Transform.Position = reader.ReadVector3();
                reader.JumpAhead(4);
                obj.Transform.Rotation = new Quaternion(reader.ReadVector4());

                uint paramCount  = reader.ReadUInt32();
                uint paramOffset = reader.ReadUInt32();

                // Object Parameters
                long pos = reader.BaseStream.Position;

                for (uint i = 0; i < paramCount; ++i)
                {
                    reader.JumpTo(paramOffset + i * 0x14, false);
                    obj.Parameters.Add(ReadParam());
                }

                // Object Name
                reader.JumpTo(nameOffset, false);
                obj.CustomData.Add("Name", new SetObjectParam(
                                       typeof(string), reader.ReadNullTerminatedString()));

                // Object Type
                reader.JumpTo(typeOffset, false);
                obj.ObjectType = reader.ReadNullTerminatedString();
                obj.ObjectID   = id;

                //Object Group
                if (!groupIDs.Contains(id))
                {
                    obj.CustomData.Add("GroupName", new SetObjectParam(
                                           typeof(string), ""));
                    obj.CustomData.Add("GroupType", new SetObjectParam(
                                           typeof(string), ""));
                }
                else
                {
                    string[] groupData = objGroupData[groupIDs.IndexOf(id)].Split('|');
                    obj.CustomData.Add("GroupName", new SetObjectParam(
                                           typeof(string), groupData[0]));
                    obj.CustomData.Add("GroupType", new SetObjectParam(
                                           typeof(string), groupData[1]));
                }

                reader.JumpTo(pos, true);
                return(obj);
            }

            SetObjectParam ReadParam()
            {
                var  param = new SetObjectParam();
                uint type  = reader.ReadUInt32();

                switch (type)
                {
                case 0:
                    param.DataType = typeof(bool);
                    param.Data     = (reader.ReadUInt32() == 1);
                    break;

                case 1:
                    param.DataType = typeof(int);
                    param.Data     = reader.ReadInt32();
                    break;

                case 2:
                    param.DataType = typeof(float);
                    param.Data     = reader.ReadSingle();
                    break;

                case 3:
                    uint offset = reader.ReadUInt32();
                    uint amount = reader.ReadUInt32();

                    if (amount != 1)
                    {
                        Console.WriteLine($"WARNING: Amount != 1. ({amount})");
                    }

                    long pos = reader.BaseStream.Position;
                    reader.JumpTo(offset, false);

                    param.DataType = typeof(string);
                    param.Data     = reader.ReadNullTerminatedString();
                    reader.JumpTo(pos, true);
                    break;

                case 4:
                    param.DataType = typeof(Vector3);
                    param.Data     = reader.ReadVector3();
                    break;

                case 6:
                    param.DataType = typeof(uint);
                    param.Data     = reader.ReadUInt32();
                    break;

                default:
                    Console.WriteLine($"WARNING: Unknown object param type {type}!");
                    return(null);
                }

                return(param);
            }
        }
示例#2
0
        // Methods
        public override void Load(Stream fileStream,
                                  Dictionary <string, SetObjectType> objectTemplates)
        {
            // Header
            var reader = new BINAReader(fileStream);

            Header = reader.ReadHeader();

            reader.JumpAhead(0x2C); // Skip "test" string
            uint objectLength = reader.ReadUInt32();
            uint objectOffset = reader.ReadUInt32();
            uint groupLength  = reader.ReadUInt32();
            uint groupOffset  = reader.ReadUInt32();

            // Data
            reader.JumpTo(objectOffset, false);
            for (uint i = 0; i < objectLength; ++i)
            {
                Objects.Add(ReadObject());
            }

            // TODO: Read Groups
            // TODO: Read Footer

            // Sub-Methods
            SetObject ReadObject()
            {
                // Object Entry
                var  obj        = new SetObject();
                uint nameOffset = reader.ReadUInt32();
                uint typeOffset = reader.ReadUInt32();

                reader.JumpAhead(16);

                obj.Transform.Position = reader.ReadVector3();
                reader.JumpAhead(4);
                obj.Transform.Rotation = new Quaternion(reader.ReadVector4());

                uint paramCount  = reader.ReadUInt32();
                uint paramOffset = reader.ReadUInt32();

                // Object Parameters
                long pos = reader.BaseStream.Position;

                for (uint i = 0; i < paramCount; ++i)
                {
                    reader.JumpTo(paramOffset + i * 0x14, false);
                    obj.Parameters.Add(ReadParam());
                }

                // TODO: Read Object Name

                // Object Type
                reader.JumpTo(typeOffset, false);
                obj.ObjectType = reader.ReadNullTerminatedString();

                reader.JumpTo(pos, true);
                return(obj);
            }

            SetObjectParam ReadParam()
            {
                var  param = new SetObjectParam();
                uint type  = reader.ReadUInt32();

                switch (type)
                {
                case 0:
                    param.DataType = typeof(bool);
                    param.Data     = (reader.ReadUInt32() == 1);
                    break;

                case 1:
                    param.DataType = typeof(int);
                    param.Data     = reader.ReadInt32();
                    break;

                case 2:
                    param.DataType = typeof(float);
                    param.Data     = reader.ReadSingle();
                    break;

                case 3:
                    uint offset = reader.ReadUInt32();
                    uint amount = reader.ReadUInt32();

                    if (amount != 1)
                    {
                        Console.WriteLine($"WARNING: Amount != 1. ({amount})");
                    }

                    long pos = reader.BaseStream.Position;
                    reader.JumpTo(offset, false);

                    param.DataType = typeof(string);
                    param.Data     = reader.ReadNullTerminatedString();
                    reader.JumpTo(pos, true);
                    break;

                case 4:
                    param.DataType = typeof(Vector3);
                    param.Data     = reader.ReadVector3();
                    break;

                case 6:
                    param.DataType = typeof(uint);
                    param.Data     = reader.ReadUInt32();
                    break;

                default:
                    Console.WriteLine($"WARNING: Unknown object param type {type}!");
                    return(null);
                }

                return(param);
            }
        }