예제 #1
0
        private static Wad.DirectoryEntry GetOrCreateDirectory(WadFile wad, string path)
        {
            var parts = path.Split(Path.DirectorySeparatorChar);

            Wad.DirectoryEntry root;

            root = wad.Directories.SingleOrDefault(d => d.Name == parts[0]);
            if (root == null)
            {
                root = new Wad.DirectoryEntry(null)
                {
                    Name = parts[0],
                };
                wad.Directories.Add(root);
            }

            Wad.DirectoryEntry current = root;
            foreach (string part in parts.Skip(1))
            {
                var child = current.Directories.SingleOrDefault(
                    d => d.Name == part);

                if (child == null)
                {
                    child = new Wad.DirectoryEntry(current)
                    {
                        Name = part,
                    };
                    current.Directories.Add(child);
                }

                current = child;
            }

            return(current);
        }
예제 #2
0
 public MyFileEntry(Wad.DirectoryEntry directory)
     : base(directory)
 {
 }
예제 #3
0
        private void Deserialize(Stream input, Endian endian)
        {
            var version = input.ReadValueU16(endian);

            if (IsValidVersion(version) == false)
            {
                throw new FormatException("invalid or unsupported wad version");
            }
            this.Version = version;

            if (version == 0x101 || version >= 0x200)
            {
                this.Flags = input.ReadValueEnum <Wad.ArchiveFlags>(endian);
            }
            else
            {
                this.Flags = Wad.ArchiveFlags.None;
            }

            if (version >= 0x202)
            {
                var headerXmlLength = input.ReadValueU32(endian);
                this.HeaderXml = input.ReadBytes(headerXmlLength);
            }

            var stringTableSize = input.ReadValueU32(endian);

            using (var stringTableData = new MemoryStream())
            {
                if (version >= 0x200)
                {
                    stringTableData.WriteFromStream(input, stringTableSize);
                    stringTableData.Position = 0;
                }

                this.DataTypes.Clear();
                if ((this.Flags & Wad.ArchiveFlags.HasDataTypes) == Wad.ArchiveFlags.HasDataTypes)
                {
                    uint count = input.ReadValueU32(endian);
                    for (uint i = 0; i < count; i++)
                    {
                        var item = new Wad.DataType();
                        item.Index    = input.ReadValueU32(endian);
                        item.Unknown2 = input.ReadValueU32(endian);
                        this.DataTypes.Add(item);
                    }
                }

                var totalFileCount      = input.ReadValueU32(endian);
                var totalDirectoryCount = input.ReadValueU32(endian);

                this.DataOffsets.Clear();
                if (version >= 0x200)
                {
                    uint count = input.ReadValueU32(endian);
                    for (uint i = 0; i < count; i++)
                    {
                        this.DataOffsets.Add(input.ReadValueU32(endian));
                    }
                }
                else
                {
                    // don't know how to handle this situation
                    throw new InvalidOperationException();
                }

                if (version == 0x100)
                {
                    stringTableData.WriteFromStream(input, stringTableSize);
                    stringTableData.Position = 0;
                }

                var stringTableReader = new StringTableReader(stringTableData);

                using (var fileTableData = input.ReadToMemoryStream((totalDirectoryCount + totalFileCount) * 16))
                {
                    while (fileTableData.Position < fileTableData.Length)
                    {
                        var dir = new Wad.DirectoryEntry(null);
                        dir.Deserialize(fileTableData, endian, stringTableReader);
                        this.Directories.Add(dir);
                    }

                    if (this.TotalFileCount != totalFileCount ||
                        this.TotalDirectoryCount != totalDirectoryCount)
                    {
                        throw new InvalidOperationException();
                    }

                    if (fileTableData.Position != fileTableData.Length)
                    {
                        throw new InvalidOperationException();
                    }
                }
            }
        }