コード例 #1
0
        /// <summary>
        /// Deserializes file data from a stream.
        /// </summary>
        protected override void Read(BinaryReaderEx br)
        {
            br.BigEndian = false;
            Version      = br.ReadEnum32 <CCMVer>();
            if (Version == CCMVer.DemonsSouls)
            {
                br.BigEndian = true;
            }

            int fileSize = br.ReadInt32();

            FullWidth = br.ReadInt16();
            TexWidth  = br.ReadInt16();
            TexHeight = br.ReadInt16();

            short codeGroupCount, texRegionCount, glyphCount;

            if (Version == CCMVer.DemonsSouls || Version == CCMVer.DarkSouls1)
            {
                Unk0E          = br.ReadInt16();
                codeGroupCount = br.ReadInt16();
                texRegionCount = -1;
                glyphCount     = br.ReadInt16();
            }
            else
            {
                Unk0E          = 0;
                codeGroupCount = -1;
                texRegionCount = br.ReadInt16();
                glyphCount     = br.ReadInt16();
                br.AssertInt16(0);
            }

            br.AssertInt32(0x20);
            int glyphOffset = br.ReadInt32();

            Unk1C    = br.ReadByte();
            Unk1D    = br.ReadByte();
            TexCount = br.ReadByte();
            br.AssertByte(0);

            Glyphs = new Dictionary <int, Glyph>(glyphCount);
            if (Version == CCMVer.DemonsSouls || Version == CCMVer.DarkSouls1)
            {
                var codeGroups = new List <CodeGroup>(codeGroupCount);
                for (int i = 0; i < codeGroupCount; i++)
                {
                    codeGroups.Add(new CodeGroup(br));
                }

                var glyphs = new List <Glyph>(glyphCount);
                for (int i = 0; i < glyphCount; i++)
                {
                    Vector2 uv1      = br.ReadVector2();
                    Vector2 uv2      = br.ReadVector2();
                    short   preSpace = br.ReadInt16();
                    short   width    = br.ReadInt16();
                    short   advance  = br.ReadInt16();
                    short   texIndex = br.ReadInt16();

                    glyphs.Add(new Glyph(uv1, uv2, preSpace, width, advance, texIndex));
                }

                foreach (CodeGroup group in codeGroups)
                {
                    int codeCount = group.EndCode - group.StartCode + 1;
                    for (int i = 0; i < codeCount; i++)
                    {
                        Glyphs[group.StartCode + i] = glyphs[group.GlyphIndex + i];
                    }
                }
            }
            else if (Version == CCMVer.DarkSouls2)
            {
                var texRegions = new Dictionary <int, TexRegion>(texRegionCount);
                for (int i = 0; i < texRegionCount; i++)
                {
                    texRegions[(int)br.Position] = new TexRegion(br);
                }

                for (int i = 0; i < glyphCount; i++)
                {
                    int   code            = br.ReadInt32();
                    int   texRegionOffset = br.ReadInt32();
                    short texIndex        = br.ReadInt16();
                    short preSpace        = br.ReadInt16();
                    short width           = br.ReadInt16();
                    short advance         = br.ReadInt16();
                    br.AssertInt32(0);
                    br.AssertInt32(0);

                    TexRegion texRegion = texRegions[texRegionOffset];
                    Vector2   uv1       = new Vector2(texRegion.X1 / (float)TexWidth, texRegion.Y1 / (float)TexHeight);
                    Vector2   uv2       = new Vector2(texRegion.X2 / (float)TexWidth, texRegion.Y2 / (float)TexHeight);
                    Glyphs[code] = new Glyph(uv1, uv2, preSpace, width, advance, texIndex);
                }
            }
        }
コード例 #2
0
        /// <summary>
        /// Serializes file data to a stream.
        /// </summary>
        protected override void Write(BinaryWriterEx bw)
        {
            bw.BigEndian = false;
            bw.WriteUInt32((uint)Version);
            bw.BigEndian = Version == CCMVer.DemonsSouls;

            bw.ReserveInt32("FileSize");
            bw.WriteInt16(FullWidth);
            bw.WriteInt16(TexWidth);
            bw.WriteInt16(TexHeight);

            if (Version == CCMVer.DemonsSouls || Version == CCMVer.DarkSouls1)
            {
                bw.WriteInt16(Unk0E);
                bw.ReserveInt16("CodeGroupCount");
                bw.WriteInt16((short)Glyphs.Count);
            }
            else if (Version == CCMVer.DarkSouls2)
            {
                bw.ReserveInt16("TexRegionCount");
                bw.WriteInt16((short)Glyphs.Count);
                bw.WriteInt16(0);
            }

            bw.WriteInt32(0x20);
            bw.ReserveInt32("GlyphOffset");
            bw.WriteByte(Unk1C);
            bw.WriteByte(Unk1D);
            bw.WriteByte(TexCount);
            bw.WriteByte(0);

            var codes = new List <int>(Glyphs.Keys);

            codes.Sort();
            if (Version == CCMVer.DemonsSouls || Version == CCMVer.DarkSouls1)
            {
                var codeGroups = new List <CodeGroup>();
                for (int i = 0; i < Glyphs.Count;)
                {
                    int startCode  = codes[i];
                    int glyphIndex = i;
                    for (i++; i < Glyphs.Count && codes[i] == codes[i - 1] + 1; i++)
                    {
                        ;
                    }
                    int endCode = codes[i - 1];
                    codeGroups.Add(new CodeGroup(startCode, endCode, glyphIndex));
                }

                bw.FillInt16("CodeGroupCount", (short)codeGroups.Count);
                foreach (CodeGroup group in codeGroups)
                {
                    group.Write(bw);
                }

                bw.FillInt32("GlyphOffset", (int)bw.Position);
                foreach (int code in codes)
                {
                    Glyph glyph = Glyphs[code];
                    bw.WriteVector2(glyph.UV1);
                    bw.WriteVector2(glyph.UV2);
                    bw.WriteInt16(glyph.PreSpace);
                    bw.WriteInt16(glyph.Width);
                    bw.WriteInt16(glyph.Advance);
                    bw.WriteInt16(glyph.TexIndex);
                }
            }
            else if (Version == CCMVer.DarkSouls2)
            {
                var texRegionsByCode = new Dictionary <int, TexRegion>(Glyphs.Count);
                var texRegions       = new HashSet <TexRegion>();
                foreach (int code in codes)
                {
                    Glyph glyph  = Glyphs[code];
                    short x1     = (short)Math.Round(glyph.UV1.X * TexWidth);
                    short y1     = (short)Math.Round(glyph.UV1.Y * TexHeight);
                    short x2     = (short)Math.Round(glyph.UV2.X * TexWidth);
                    short y2     = (short)Math.Round(glyph.UV2.Y * TexHeight);
                    var   region = new TexRegion(x1, y1, x2, y2);
                    texRegionsByCode[code] = region;
                    texRegions.Add(region);
                }

                bw.FillInt16("TexRegionCount", (short)texRegions.Count);
                var texRegionOffsets = new Dictionary <TexRegion, int>(texRegions.Count);
                foreach (TexRegion region in texRegions)
                {
                    texRegionOffsets[region] = (int)bw.Position;
                    region.Write(bw);
                }

                bw.FillInt32("GlyphOffset", (int)bw.Position);
                foreach (int code in codes)
                {
                    Glyph glyph = Glyphs[code];
                    bw.WriteInt32(code);
                    bw.WriteInt32(texRegionOffsets[texRegionsByCode[code]]);
                    bw.WriteInt16(glyph.TexIndex);
                    bw.WriteInt16(glyph.PreSpace);
                    bw.WriteInt16(glyph.Width);
                    bw.WriteInt16(glyph.Advance);
                    bw.WriteInt32(0);
                    bw.WriteInt32(0);
                }
            }

            bw.FillInt32("FileSize", (int)bw.Position);
        }