Beispiel #1
0
        public static int ParseOperand(FontParser parser, int b0)
        {
            if (b0 == 28)
            {
                return(parser.ReadInt16());
            }

            if (b0 == 29)
            {
                return(parser.ReadInt32());
            }

            if (b0 == 30)
            {
                // A floating point value which we really don't need - skipping!

                while (true)
                {
                    byte b  = parser.ReadByte();
                    int  n1 = b >> 4;
                    int  n2 = b & 15;

                    if (n1 == 15 || n2 == 15)
                    {
                        break;
                    }
                }

                return(0);
            }

            if (b0 >= 32 && b0 <= 246)
            {
                return(b0 - 139);
            }

            if (b0 >= 247 && b0 <= 250)
            {
                return((b0 - 247) * 256 + parser.ReadByte() + 108);
            }

            if (b0 >= 251 && b0 <= 254)
            {
                return(-(b0 - 251) * 256 - parser.ReadByte() - 108);
            }

            return(0);
        }
Beispiel #2
0
        private void Parse(int start, int codeLength)
        {
            // Seek there now:
            Parser.Position = start;

            // Where should the parser quit?
            int max = start + codeLength;

            float          c1x;
            float          c1y;
            float          c2x;
            float          c2y;
            int            subIndex;
            CffSubPosition subCode;

            // For each bytecode..
            while (Parser.Position < max)
            {
                // Grab the byte:
                byte v = Parser.ReadByte();

                switch (v)
                {
                case 1:                         // hstem
                    ParseStems();
                    break;

                case 3:                         // vstem
                    ParseStems();
                    break;

                case 4:                         // vmoveto

                    if (Stack.Length > 1 && !HasWidth)
                    {
                        Width    = Stack.Shift() + NominalWidthX;
                        HasWidth = true;
                    }

                    Y += Stack.Shift();

                    Glyph.ClosePath();

                    // Move:
                    Glyph.MoveTo(X * ScaleRatio, Y * ScaleRatio);

                    break;

                case 5:                         // rlineto

                    while (Stack.Length > 0)
                    {
                        X += Stack.Shift();
                        Y += Stack.Shift();

                        Glyph.LineTo(X * ScaleRatio, Y * ScaleRatio);
                    }

                    break;

                case 6:                         // hlineto

                    while (Stack.Length > 0)
                    {
                        X += Stack.Shift();
                        Glyph.LineTo(X * ScaleRatio, Y * ScaleRatio);

                        if (Stack.Empty)
                        {
                            break;
                        }

                        Y += Stack.Shift();
                        Glyph.LineTo(X * ScaleRatio, Y * ScaleRatio);
                    }

                    break;

                case 7:                         // vlineto

                    while (Stack.Length > 0)
                    {
                        Y += Stack.Shift();
                        Glyph.LineTo(X * ScaleRatio, Y * ScaleRatio);

                        if (Stack.Length == 0)
                        {
                            break;
                        }

                        X += Stack.Shift();
                        Glyph.LineTo(X * ScaleRatio, Y * ScaleRatio);
                    }

                    break;

                case 8:                         // rrcurveto

                    while (Stack.Length > 0)
                    {
                        c1x = X + Stack.Shift();
                        c1y = Y + Stack.Shift();
                        c2x = c1x + Stack.Shift();
                        c2y = c1y + Stack.Shift();
                        X   = c2x + Stack.Shift();
                        Y   = c2y + Stack.Shift();
                        Glyph.CurveTo(c1x * ScaleRatio, c1y * ScaleRatio, c2x * ScaleRatio, c2y * ScaleRatio, X * ScaleRatio, Y * ScaleRatio);
                    }

                    break;

                case 10:                         // callsubr

                    subIndex = (int)Stack.Pop() + SubrsBias;
                    subCode  = Subrs[subIndex];

                    if (subCode != null)
                    {
                        // Cache the position:
                        subIndex = Parser.Position;

                        // Parse:
                        Parse(subCode.Position, subCode.Length);

                        // Re-apply:
                        Parser.Position = subIndex;
                    }

                    break;

                case 11:                         // return
                    return;

                case 12:                         // escape
                    v = Parser.ReadByte();
                    break;

                case 14:                         // endchar

                    if (Stack.Length > 0 && !HasWidth)
                    {
                        Width    = Stack.Shift() + NominalWidthX;
                        HasWidth = true;
                    }

                    // Close the glyph:
                    Glyph.ClosePath();

                    break;

                case 18:                         // hstemhm
                    ParseStems();
                    break;

                case 19:                         // hintmask
                case 20:                         // cntrmask
                    ParseStems();
                    Parser.Position += (NStems + 7) >> 3;
                    break;

                case 21:                         // rmoveto

                    if (Stack.Length > 2 && !HasWidth)
                    {
                        Width    = Stack.Shift() + NominalWidthX;
                        HasWidth = true;
                    }

                    X += Stack.Shift();
                    Y += Stack.Shift();

                    Glyph.ClosePath();

                    // Move now:
                    Glyph.MoveTo(X * ScaleRatio, Y * ScaleRatio);

                    break;

                case 22:                         // hmoveto

                    if (Stack.Length > 1 && !HasWidth)
                    {
                        Width    = Stack.Shift() + NominalWidthX;
                        HasWidth = true;
                    }

                    X += Stack.Shift();

                    Glyph.ClosePath();

                    // Move now:
                    Glyph.MoveTo(X * ScaleRatio, Y * ScaleRatio);

                    break;

                case 23:                         // vstemhm
                    ParseStems();
                    break;

                case 24:                         // rcurveline

                    while (Stack.Length > 2)
                    {
                        c1x = X + Stack.Shift();
                        c1y = Y + Stack.Shift();
                        c2x = c1x + Stack.Shift();
                        c2y = c1y + Stack.Shift();
                        X   = c2x + Stack.Shift();
                        Y   = c2y + Stack.Shift();

                        Glyph.CurveTo(c1x * ScaleRatio, c1y * ScaleRatio, c2x * ScaleRatio, c2y * ScaleRatio, X * ScaleRatio, Y * ScaleRatio);
                    }

                    X += Stack.Shift();
                    Y += Stack.Shift();
                    Glyph.LineTo(X * ScaleRatio, Y * ScaleRatio);

                    break;

                case 25:                         // rlinecurve

                    while (Stack.Length > 6)
                    {
                        X += Stack.Shift();
                        Y += Stack.Shift();
                        Glyph.LineTo(X * ScaleRatio, Y * ScaleRatio);
                    }

                    c1x = X + Stack.Shift();
                    c1y = Y + Stack.Shift();
                    c2x = c1x + Stack.Shift();
                    c2y = c1y + Stack.Shift();
                    X   = c2x + Stack.Shift();
                    Y   = c2y + Stack.Shift();
                    Glyph.CurveTo(c1x * ScaleRatio, c1y * ScaleRatio, c2x * ScaleRatio, c2y * ScaleRatio, X * ScaleRatio, Y * ScaleRatio);

                    break;

                case 26:                         // vvcurveto

                    if (Stack.IsOdd)
                    {
                        X += Stack.Shift();
                    }

                    while (Stack.Length > 0)
                    {
                        c1x = X;
                        c1y = Y + Stack.Shift();
                        c2x = c1x + Stack.Shift();
                        c2y = c1y + Stack.Shift();
                        X   = c2x;
                        Y   = c2y + Stack.Shift();

                        Glyph.CurveTo(c1x * ScaleRatio, c1y * ScaleRatio, c2x * ScaleRatio, c2y * ScaleRatio, X * ScaleRatio, Y * ScaleRatio);
                    }

                    break;

                case 27:                         // hhcurveto

                    if (Stack.IsOdd)
                    {
                        Y += Stack.Shift();
                    }

                    while (Stack.Length > 0)
                    {
                        c1x = X + Stack.Shift();
                        c1y = Y;
                        c2x = c1x + Stack.Shift();
                        c2y = c1y + Stack.Shift();
                        X   = c2x + Stack.Shift();
                        Y   = c2y;

                        Glyph.CurveTo(c1x * ScaleRatio, c1y * ScaleRatio, c2x * ScaleRatio, c2y * ScaleRatio, X * ScaleRatio, Y * ScaleRatio);
                    }

                    break;

                case 28:                         // shortint

                    Stack.Push(Parser.ReadInt16());

                    break;

                case 29:                         // callgsubr

                    subIndex = (int)Stack.Pop() + GsubrsBias;
                    subCode  = GSubrs[subIndex];

                    if (subCode != null)
                    {
                        // Cache the position:
                        subIndex = Parser.Position;

                        // Parse:
                        Parse(subCode.Position, subCode.Length);

                        // Re-apply:
                        Parser.Position = subIndex;
                    }

                    break;

                case 30:                         // vhcurveto

                    while (Stack.Length > 0)
                    {
                        c1x = X;
                        c1y = Y + Stack.Shift();
                        c2x = c1x + Stack.Shift();
                        c2y = c1y + Stack.Shift();
                        X   = c2x + Stack.Shift();
                        Y   = c2y + (Stack.Length == 1?Stack.Shift():0);
                        Glyph.CurveTo(c1x * ScaleRatio, c1y * ScaleRatio, c2x * ScaleRatio, c2y * ScaleRatio, X * ScaleRatio, Y * ScaleRatio);

                        if (Stack.Empty)
                        {
                            break;
                        }

                        c1x = X + Stack.Shift();
                        c1y = Y;
                        c2x = c1x + Stack.Shift();
                        c2y = c1y + Stack.Shift();
                        Y   = c2y + Stack.Shift();
                        X   = c2x + (Stack.Length == 1?Stack.Shift():0);
                        Glyph.CurveTo(c1x * ScaleRatio, c1y * ScaleRatio, c2x * ScaleRatio, c2y * ScaleRatio, X * ScaleRatio, Y * ScaleRatio);
                    }

                    break;

                case 31:                         // hvcurveto

                    while (Stack.Length > 0)
                    {
                        c1x = X + Stack.Shift();
                        c1y = Y;
                        c2x = c1x + Stack.Shift();
                        c2y = c1y + Stack.Shift();
                        Y   = c2y + Stack.Shift();
                        X   = c2x + (Stack.Length == 1 ? Stack.Shift() : 0);
                        Glyph.CurveTo(c1x * ScaleRatio, c1y * ScaleRatio, c2x * ScaleRatio, c2y * ScaleRatio, X * ScaleRatio, Y * ScaleRatio);

                        if (Stack.Empty)
                        {
                            break;
                        }

                        c1x = X;
                        c1y = Y + Stack.Shift();
                        c2x = c1x + Stack.Shift();
                        c2y = c1y + Stack.Shift();
                        X   = c2x + Stack.Shift();
                        Y   = c2y + (Stack.Length == 1?Stack.Shift():0);

                        Glyph.CurveTo(c1x * ScaleRatio, c1y * ScaleRatio, c2x * ScaleRatio, c2y * ScaleRatio, X * ScaleRatio, Y * ScaleRatio);
                    }

                    break;

                default:

                    if (v < 32)
                    {
                        // Faulty operator.
                        return;
                    }
                    else if (v < 247)
                    {
                        Stack.Push(v - 139);
                    }
                    else if (v < 251)
                    {
                        Stack.Push((v - 247) * 256 + Parser.ReadByte() + 108);
                    }
                    else if (v < 255)
                    {
                        Stack.Push(-(v - 251) * 256 - Parser.ReadByte() - 108);
                    }
                    else
                    {
                        Stack.Push((float)Parser.ReadInt32() / 65536f);
                    }

                    break;
                }
            }
        }
		public static int ParseOperand(FontParser parser,int b0){
			
			if(b0==28){
				return parser.ReadInt16();
			}
			
			if(b0==29){
				return parser.ReadInt32();
			}
			
			if(b0==30){
				// A floating point value which we really don't need - skipping!
				
				while(true){
					byte b=parser.ReadByte();
					int n1 = b >> 4;
					int n2 = b & 15;

					if (n1 ==15 || n2==15) {
						break;
					}
					
				}
				
				return 0;
			}
			
			if (b0 >= 32 && b0 <= 246) {
				return b0 - 139;
			}
			
			if (b0 >= 247 && b0 <= 250) {
				return (b0 - 247) * 256 + parser.ReadByte() + 108;
			}
			
			if (b0 >= 251 && b0 <= 254) {
				return -(b0 - 251) * 256 - parser.ReadByte() - 108;
			}
			
			return 0;
		}