Ejemplo n.º 1
0
        public void Save(string path)
        {
            using (var fs = new FileStream(path, FileMode.Create))
                using (var br = new BinaryStream(fs))
                {
                    br.WriteString(Magic, StringCoding.Raw);
                    br.WriteInt32(2);
                    br.Position += 4; // Write File Size Later
                    br.WriteInt32(Playlists.Count);

                    int totalTracks = GetTotalTrackCount();
                    br.WriteInt32(totalTracks);

                    br.Position = 0x14;

                    // Step 1: Skip all way to the string table location so we can have proper string offsets

                    // - Move to the Playlist Tree for now
                    br.Position += 0x08 * Playlists.Count;

                    int trackOffsetMap = (int)br.Position;

                    // - Go to the end of the Playlist Tree
                    br.Position += totalTracks * 0x18;

                    // Step 2: We reached the string table location, write the string tables
                    OptimizedStringTable trackStringTable = SerializeTrackStringTable();
                    trackStringTable.SaveStream(br);

                    // Step 3: Populate the trees that reference the string tables
                    int lastTrackDataPos = trackOffsetMap;

                    for (int i = 0; i < Playlists.Count; i++)
                    {
                        for (int j = 0; j < Playlists[i].Tracks.Count; j++)
                        {
                            br.Position = lastTrackDataPos + (j * 0x18);

                            var track = Playlists[i].Tracks[j];
                            br.WriteInt32(trackStringTable.GetStringOffset(track.Label));
                            br.WriteInt32(trackStringTable.GetStringOffset(track.FileName));
                            br.WriteInt32(trackStringTable.GetStringOffset(track.TrackName));
                            br.WriteInt32(trackStringTable.GetStringOffset(track.Artist));
                            br.WriteInt32(trackStringTable.GetStringOffset(track.Genre));
                            if (Type == PlaylistType.SEQ)
                            {
                                br.WriteInt32(j);
                            }
                        }

                        br.Position = 0x14 + (0x08 * i);
                        br.WriteInt32(lastTrackDataPos);
                        br.WriteInt32(Playlists[i].Tracks.Count);

                        lastTrackDataPos += 0x18 * Playlists[i].Tracks.Count;
                    }
                }
        }
Ejemplo n.º 2
0
        public OptimizedStringTable GetPrefixStringTable()
        {
            var opt = new OptimizedStringTable();

            opt.Alignment = 0x04;
            foreach (var prefix in Prefixes)
            {
                opt.AddString(prefix.Name);
            }
            return(opt);
        }
Ejemplo n.º 3
0
        public OptimizedStringTable SerializePlaylistStringTable()
        {
            var playlistStrTable = new OptimizedStringTable();

            foreach (var playlist in Playlists)
            {
                playlistStrTable.AddString(playlist.Name);
            }

            return(playlistStrTable);
        }
Ejemplo n.º 4
0
        public OptimizedStringTable GetStringTable()
        {
            var table = new OptimizedStringTable();

            table.Alignment = 0x04;

            foreach (var name in Entries)
            {
                table.AddString(name.FullName);
            }

            return(table);
        }
Ejemplo n.º 5
0
        public OptimizedStringTable SerializeTrackStringTable()
        {
            var trackStrTable = new OptimizedStringTable();

            foreach (var track in Tracks)
            {
                trackStrTable.AddString(track.Label);
                trackStrTable.AddString(track.FileName);
                trackStrTable.AddString(track.TrackName);
                trackStrTable.AddString(track.Artist);
                trackStrTable.AddString(track.Genre);
            }

            return(trackStrTable);
        }
Ejemplo n.º 6
0
        private OptimizedStringTable GetStringDbTable(IEnumerable <string> strings)
        {
            var optimizedStringTable = new OptimizedStringTable();

            optimizedStringTable.StringCoding      = StringCoding.Int16CharCount;
            optimizedStringTable.NullTerminated    = true;
            optimizedStringTable.Alignment         = 0x02;
            optimizedStringTable.IsRelativeOffsets = true;

            foreach (var str in strings)
            {
                optimizedStringTable.AddString(str);
            }

            return(optimizedStringTable);
        }
Ejemplo n.º 7
0
        private OptimizedStringTable GetLabelTable(List <SpecDBRowData> rows)
        {
            var optimizedStringTable = new OptimizedStringTable();

            optimizedStringTable.StringCoding      = StringCoding.Int16CharCount;
            optimizedStringTable.NullTerminated    = true;
            optimizedStringTable.Alignment         = 0x02;
            optimizedStringTable.IsRelativeOffsets = true;

            foreach (var row in rows)
            {
                optimizedStringTable.AddString(row.Label);
            }

            return(optimizedStringTable);
        }
Ejemplo n.º 8
0
        public void Save(string path)
        {
            using (var fs = new FileStream(path, FileMode.Create))
                using (var bs = new BinaryStream(fs, ByteConverter.Big))
                {
                    bs.WriteString(MAGIC, StringCoding.Raw);
                    bs.Position += 4;
                    bs.Position += 4; // Skip prefixes offset for now
                    bs.WriteInt32(NameTrees.Count);

                    bs.Position += NameTrees.Count * sizeof(uint);
                    bs.AlignWithValue(0x10, 0x5E);

                    long lastPos = bs.Position;
                    for (int i = 0; i < NameTrees.Count; i++)
                    {
                        var currentTree = NameTrees[i];
                        bs.Position = lastPos;
                        int baseTreePos = (int)bs.Position;
                        // For now skip everything and go to the string tables
                        bs.Position += 0x10;
                        bs.Position += 0x10 * currentTree.Entries.Count;

                        OptimizedStringTable opt = NameTrees[i].GetStringTable();
                        opt.SaveStream(bs);
                        bs.AlignWithValue(0x10, 0x5E);

                        lastPos = bs.Position;

                        // Write where the tree is located
                        bs.Position = 0x10 + (i * sizeof(uint));
                        bs.WriteInt32(baseTreePos);

                        // Write its data
                        bs.Position = baseTreePos;
                        bs.WriteInt32(100);
                        bs.WriteInt32(currentTree.Entries.Count);
                        bs.AlignWithValue(0x10, 0x5E);
                        for (int j = 0; j < currentTree.Entries.Count; j++)
                        {
                            var entry = currentTree.Entries[j];
                            bs.WriteUInt32(entry.SpecDBID);
                            bs.WriteUInt32(entry.AlphabeticalID);
                            bs.WriteInt32(opt.GetStringOffset(entry.FullName));
                            bs.WriteBytes(new byte[] { 0xFF, 0xFF, 0xFF, 0xFF });
                        }
                    }

                    // Write the prefix tree
                    bs.Position = lastPos;
                    bs.WriteInt32(Prefixes.Count); // 4 byte header

                    // Skip entries
                    bs.Position += Prefixes.Count * sizeof(uint);
                    OptimizedStringTable prefixST = GetPrefixStringTable();
                    prefixST.SaveStream(bs);
                    bs.Align(0x10, true);

                    // String table
                    bs.Position = lastPos + 4;
                    foreach (var prefix in Prefixes)
                    {
                        bs.WriteInt32(prefixST.GetStringOffset(prefix.Name));
                    }

                    // Write prefix tree offset
                    bs.Position = 0x08;
                    bs.WriteInt32((int)lastPos);
                }
        }
Ejemplo n.º 9
0
        public void Save(string path)
        {
            using (var fs = new FileStream(path, FileMode.Create))
                using (var br = new BinaryStream(fs))
                {
                    br.WriteString(BGML.MAGIC, StringCoding.Raw);
                    br.Position += 4;
                    br.Position += 4; // Write File Size Later
                    br.Position += 4;
                    br.WriteInt32(Tracks.Count);
                    br.WriteInt32(0x30); // We know its always at 0x30.. so just write anyway
                    br.WriteInt32(Playlists.Count);
                    br.Position += 4;    // Offset write later

                    br.Position = 0x30;

                    // Step 1: Skip all way to the string table location so we can have proper string offsets

                    // - Move to the Playlist Tree for now
                    br.Position += 0x30 * Tracks.Count;

                    // - Go to the end of the Playlist Tree
                    br.Position += Playlists.Count * sizeof(uint);

                    // - Playlist Tree is aligned
                    br.Align(0x10, true);


                    int[] playlistDataOffsets = new int[Playlists.Count]; // Will be used later on to write the tree
                    // - Write Playlist Data along the way
                    for (int i = 0; i < Playlists.Count; i++)
                    {
                        playlistDataOffsets[i] = (int)br.Position;
                        br.Position           += 0x10; // We're skipping the first int which is the string offset
                        br.WriteInt32(Playlists[i].TrackIndexes.Count);
                        foreach (var index in Playlists[i].TrackIndexes)
                        {
                            br.WriteInt32(index);
                        }
                        br.Align(0x10, true);
                    }

                    // Step 2: We reached the string table location, write the string tables
                    OptimizedStringTable trackStringTable = SerializeTrackStringTable();
                    trackStringTable.SaveStream(br);

                    OptimizedStringTable playlistStringTable = SerializePlaylistStringTable();
                    playlistStringTable.SaveStream(br);

                    // Step 3: Populate the trees that reference the string tables
                    for (int i = 0; i < Tracks.Count; i++)
                    {
                        br.Position = 0x30 + (i * 0x30);
                        br.WriteInt32(trackStringTable.GetStringOffset(Tracks[i].Label));
                        br.WriteInt32((int)Tracks[i].Format);
                        br.WriteInt32(trackStringTable.GetStringOffset(Tracks[i].FileName));
                        br.Position += 8;
                        br.WriteInt32(trackStringTable.GetStringOffset(Tracks[i].TrackName));
                        br.WriteInt32(trackStringTable.GetStringOffset(Tracks[i].Artist));
                        br.WriteInt32(trackStringTable.GetStringOffset(Tracks[i].Genre));
                        br.Position += 0x10;
                    }

                    // Write the playlist data pointers
                    int playlistTreeOffset = (int)br.Position;
                    for (int i = 0; i < playlistDataOffsets.Length; i++)
                    {
                        br.WriteInt32(playlistDataOffsets[i]);
                    }
                    br.Align(0x10, true);

                    // Write Playlist Label offsets
                    for (int i = 0; i < Playlists.Count; i++)
                    {
                        br.Position = playlistDataOffsets[i]; // Using shortcut by using the precalculated offsets from earlier
                        br.WriteInt32(playlistStringTable.GetStringOffset(Playlists[i].Name));
                    }

                    // Finish up the header
                    br.Position = 0x08;
                    br.WriteInt32((int)br.Length); // File Size
                    br.Position = 0x1C;
                    br.WriteInt32(playlistTreeOffset);
                }
        }