Exemple #1
0
            public static LigatureAttachTable ReadFrom(BinaryReader reader, ushort classCount)
            {
                LigatureAttachTable table = new LigatureAttachTable();
                ushort componentCount     = reader.ReadUInt16();

                ComponentRecord[] componentRecs = new ComponentRecord[componentCount];
                table.records = componentRecs;
                for (int i = 0; i < componentCount; ++i)
                {
                    componentRecs[i] = new ComponentRecord(
                        Utils.ReadInt16Array(reader, classCount));
                }
                return(table);
            }
Exemple #2
0
            public void ReadFrom(BinaryReader reader, ushort classCount)
            {
                long   startPos      = reader.BaseStream.Position;
                ushort ligatureCount = reader.ReadUInt16();

                short[] offsets = Utils.ReadInt16Array(reader, ligatureCount);

                ligatures = new LigatureAttachTable[ligatureCount];

                for (int i = 0; i < ligatureCount; ++i)
                {
                    //each ligature table
                    reader.BaseStream.Seek(startPos + offsets[i], SeekOrigin.Begin);
                    ligatures[i] = LigatureAttachTable.ReadFrom(reader, classCount);
                }
            }
Exemple #3
0
 public static LigatureAttachTable ReadFrom(BinaryReader reader, ushort classCount)
 {
     LigatureAttachTable table = new LigatureAttachTable();
     ushort componentCount = reader.ReadUInt16();
     ComponentRecord[] componentRecs = new ComponentRecord[componentCount];
     table.records = componentRecs;
     for (int i = 0; i < componentCount; ++i)
     {
         componentRecs[i] = new ComponentRecord(
             Utils.ReadInt16Array(reader, classCount));
     }
     return table;
 }
Exemple #4
0
            public override bool TryUpdatePosition(
                FontMetrics fontMetrics,
                GPosTable table,
                GlyphPositioningCollection collection,
                Tag feature,
                ushort index,
                int count)
            {
                // Mark-to-Ligature Attachment Positioning.
                // Implements: https://docs.microsoft.com/en-us/typography/opentype/spec/gpos#lookup-type-5-mark-to-ligature-attachment-positioning-subtable
                ushort glyphId = collection[index][0];

                if (glyphId == 0)
                {
                    return(false);
                }

                int markIndex = this.markCoverage.CoverageIndexOf(glyphId);

                if (markIndex < 0)
                {
                    return(false);
                }

                // Search backward for a base glyph.
                int baseGlyphIndex = index;

                while (--baseGlyphIndex >= 0)
                {
                    GlyphShapingData data = collection.GetGlyphShapingData(baseGlyphIndex);
                    if (!AdvancedTypographicUtils.IsMarkGlyph(fontMetrics, data.GlyphIds[0], data))
                    {
                        break;
                    }
                }

                if (baseGlyphIndex < 0)
                {
                    return(false);
                }

                ushort baseGlyphId   = collection[baseGlyphIndex][0];
                int    ligatureIndex = this.ligatureCoverage.CoverageIndexOf(baseGlyphId);

                if (ligatureIndex < 0)
                {
                    return(false);
                }

                // We must now check whether the ligature ID of the current mark glyph
                // is identical to the ligature ID of the found ligature.
                // If yes, we can directly use the component index. If not, we attach the mark
                // glyph to the last component of the ligature.
                LigatureAttachTable ligatureAttach = this.ligatureArrayTable.LigatureAttachTables[ligatureIndex];
                GlyphShapingData    markGlyph      = collection.GetGlyphShapingData(index);
                GlyphShapingData    ligGlyph       = collection.GetGlyphShapingData(baseGlyphIndex);
                int compIndex = ligGlyph.LigatureId > 0 && ligGlyph.LigatureId == markGlyph.LigatureId && markGlyph.LigatureComponent > 0
                    ? Math.Min(markGlyph.LigatureComponent, ligGlyph.CodePointCount) - 1
                    : ligGlyph.CodePointCount - 1;

                MarkRecord  markRecord = this.markArrayTable.MarkRecords[markIndex];
                AnchorTable baseAnchor = ligatureAttach.ComponentRecords[compIndex].LigatureAnchorTables[markRecord.MarkClass];

                AdvancedTypographicUtils.ApplyAnchor(collection, index, baseAnchor, markRecord, baseGlyphIndex);

                return(true);
            }