示例#1
0
 private static int MeasureTabScriptRun(ScriptRun* scriptRun, Style paragraphStyle, int x, bool invalidate)
 {
     int advanceWidth = scriptRun->ABC.abcB;
     if (advanceWidth < 0 || invalidate)
     {
         int nextX = paragraphStyle.TabStopRuler.AdvanceToNextTabStop(x);
         advanceWidth = scriptRun->ABC.abcB = nextX - x;
     }
     return advanceWidth;
 }
示例#2
0
 private static int MeasureObjectScriptRun(ScriptRun* scriptRun)
 {
     return scriptRun->ABC.TotalWidth;
 }
示例#3
0
        private static int MeasureTextScriptRun(ScriptParagraph* scriptParagraph, ScriptRun* scriptRun,
            int truncatedLeadingCharsCount, int truncatedTrailingCharsCount,
            out int glyphIndexInParagraph, out int glyphCount)
        {
            if (truncatedLeadingCharsCount != 0 || truncatedTrailingCharsCount != 0)
            {
                ushort* logicalClusters = scriptRun->CharLogicalClusters(scriptParagraph);
                int startGlyphIndexInRun, endGlyphIndexInRun;
                if (scriptRun->ScriptAnalysis.fRTL)
                {
                    startGlyphIndexInRun = truncatedTrailingCharsCount != 0
                        ? logicalClusters[scriptRun->CharCount - truncatedTrailingCharsCount] + 1
                        : 0;
                    endGlyphIndexInRun = truncatedLeadingCharsCount != 0
                        ? logicalClusters[truncatedLeadingCharsCount] + 1
                        : scriptRun->GlyphCount;
                }
                else
                {
                    startGlyphIndexInRun = truncatedLeadingCharsCount != 0
                        ? logicalClusters[truncatedLeadingCharsCount]
                        : 0;
                    endGlyphIndexInRun = truncatedTrailingCharsCount != 0
                        ? logicalClusters[scriptRun->CharCount - truncatedTrailingCharsCount]
                        : scriptRun->GlyphCount;
                }

                glyphIndexInParagraph = scriptRun->GlyphIndexInParagraph + startGlyphIndexInRun;
                glyphCount = endGlyphIndexInRun - startGlyphIndexInRun;

                int* glyphAdvanceWidths = scriptParagraph->GlyphAdvanceWidths + glyphIndexInParagraph;
                int measuredWidth = 0;
                for (int j = 0; j < glyphCount; j++)
                    measuredWidth += glyphAdvanceWidths[j];
                return measuredWidth;
            }

            glyphIndexInParagraph = scriptRun->GlyphIndexInParagraph;
            glyphCount = scriptRun->GlyphCount;
            return scriptRun->ABC.TotalWidth;
        }
示例#4
0
        private static void ScriptShapeAndPlace(IntPtr hdc, ref IntPtr scriptCache, ScriptParagraph* scriptParagraph, ScriptRun* scriptRun, char* paragraphChars)
        {
            int charIndexInParagraph = scriptRun->CharIndexInParagraph;
            char* chars = paragraphChars + charIndexInParagraph;
            int charCount = scriptRun->CharCount;
            int glyphIndexInParagraph = scriptParagraph->GlyphCount;
            ushort* charLogicalClusters = scriptParagraph->CharLogicalClusters + charIndexInParagraph;

            SCRIPT_ANALYSIS* scriptAnalysis = &scriptRun->ScriptAnalysis;
            int glyphCapacity = charCount * 3 / 2 + 16; // * 1.5 + 16 per Uniscribe recommendations for ScriptShape.
            int glyphCount;
            ushort* glyphs;
            SCRIPT_VISATTR* glyphVisualAttributes;
            int result;
            for (; ; )
            {
                scriptParagraph->EnsureGlyphCapacityAndPreserveContents(glyphIndexInParagraph + glyphCapacity);

                glyphs = scriptParagraph->Glyphs + glyphIndexInParagraph;
                glyphVisualAttributes = scriptParagraph->GlyphVisualAttributes + glyphIndexInParagraph;
                result = NativeMethods.ScriptShape(hdc, ref scriptCache, chars, charCount, glyphCapacity,
                    scriptAnalysis, glyphs, charLogicalClusters, glyphVisualAttributes,
                    out glyphCount);

                if (result == NativeConstants.S_OK)
                    break;

                if (result == NativeConstants.USP_E_SCRIPT_NOT_IN_FONT)
                {
                    SCRIPT_ANALYSIS modifiedScriptAnalysis = *scriptAnalysis;
                    modifiedScriptAnalysis.eScript = NativeConstants.SCRIPT_UNDEFINED;
                    result = NativeMethods.ScriptShape(hdc, ref scriptCache, chars, charCount, glyphCapacity,
                        &modifiedScriptAnalysis, glyphs, charLogicalClusters, glyphVisualAttributes,
                        out glyphCount);
                    if (result == NativeConstants.S_OK)
                        break;
                }

                if (result != NativeConstants.E_OUTOFMEMORY)
                    Marshal.ThrowExceptionForHR(result);

                glyphCapacity *= 2;
            }

            int* glyphAdvanceWidths = scriptParagraph->GlyphAdvanceWidths + glyphIndexInParagraph;
            GOFFSET* glyphOffsets = scriptParagraph->GlyphOffsets + glyphIndexInParagraph;
            result = NativeMethods.ScriptPlace(hdc, ref scriptCache, glyphs, glyphCount,
                glyphVisualAttributes, scriptAnalysis, glyphAdvanceWidths, glyphOffsets, out scriptRun->ABC);
            if (result != NativeConstants.S_OK)
                Marshal.ThrowExceptionForHR(result);

            scriptRun->GlyphIndexInParagraph = glyphIndexInParagraph;
            scriptRun->GlyphCount = glyphCount;
            scriptParagraph->GlyphCount += glyphCount;
        }
示例#5
0
        private int* GetTempVisualToLogicalMap(ScriptRun* scriptRuns, int count)
        {
            tempEmbeddingLevelBuffer.EnsureCapacity(count);
            byte* embeddingLevels = (byte*)tempEmbeddingLevelBuffer.GetPointer();
            for (int i = 0; i < count; i++)
                embeddingLevels[i] = (byte)scriptRuns[i].ScriptAnalysis.s.uBidiLevel;

            tempVisualToLogicalMapBuffer.EnsureCapacity(count);
            int* visualToLogicalMap = (int*)tempVisualToLogicalMapBuffer.GetPointer();

            int result = NativeMethods.ScriptLayout(count, embeddingLevels, visualToLogicalMap, null);
            if (result != NativeConstants.S_OK)
                Marshal.ThrowExceptionForHR(result);

            return visualToLogicalMap;
        }
示例#6
0
        public void InitializeTruncatedCopy(ScriptRun* scriptRun, int truncatedLeadingCharsCount, int truncatedTrailingCharsCount)
        {
            this.run = scriptRun->run;
            if (this.run.RunKind == RunKind.Text)
                this.run.CharCount = scriptRun->CharCount - truncatedLeadingCharsCount - truncatedTrailingCharsCount;

            ScriptAnalysis = scriptRun->ScriptAnalysis;
            CharIndexInParagraph = scriptRun->CharIndexInParagraph + truncatedLeadingCharsCount;
        }