コード例 #1
0
ファイル: CMapParser.cs プロジェクト: DarkMoon4CN/CLT
        /**
         * This will parse the stream and create a cmap object.
         *
         * @param input The CMAP stream to parse.
         * @return The parsed stream as a java object.
         *
         * @throws IOException If there is an error parsing the stream.
         */
        public CMap Parse(Stream input)
        {
            PushbackStream cmapStream = new PushbackStream(input);
            CMap           result     = new CMap();
            Object         token      = null;

            while ((token = ParseNextToken(cmapStream)) != null)
            {
                if (token is Operator)
                {
                    Operator op = (Operator)token;
                    if (op.op.Equals(BEGIN_CODESPACE_RANGE))
                    {
                        while (true)
                        {
                            Object nx = ParseNextToken(cmapStream);
                            if (nx is Operator && ((Operator)nx).op.Equals("endcodespacerange"))
                            {
                                break;
                            }
                            byte[]         startRange = (byte[])nx;
                            byte[]         endRange   = (byte[])ParseNextToken(cmapStream);
                            CodespaceRange range      = new CodespaceRange();
                            range.SetStart(startRange);
                            range.SetEnd(endRange);
                            result.AddCodespaceRange(range);
                        }
                    }
                    else if (op.op.Equals(BEGIN_BASE_FONT_CHAR))
                    {
                        while (true)
                        {
                            Object nx = ParseNextToken(cmapStream);
                            if (nx is Operator && ((Operator)nx).op.Equals("endbfchar"))
                            {
                                break;
                            }
                            byte[] inputCode = (byte[])nx;
                            Object nextToken = ParseNextToken(cmapStream);
                            if (nextToken is byte[])
                            {
                                byte[] bytes = (byte[])nextToken;
                                String value = CreateStringFromBytes(bytes);
                                result.AddMapping(inputCode, value);
                            }
                            else if (nextToken is LiteralName)
                            {
                                result.AddMapping(inputCode, ((LiteralName)nextToken).name);
                            }
                            else
                            {
                                throw new IOException(MessageLocalization.GetComposedMessage("error.parsing.cmap.beginbfchar.expected.cosstring.or.cosname.and.not.1", nextToken));
                            }
                        }
                    }
                    else if (op.op.Equals(BEGIN_BASE_FONT_RANGE))
                    {
                        while (true)
                        {
                            Object nx = ParseNextToken(cmapStream);
                            if (nx is Operator && ((Operator)nx).op.Equals("endbfrange"))
                            {
                                break;
                            }
                            byte[]         startCode  = (byte[])nx;
                            byte[]         endCode    = (byte[])ParseNextToken(cmapStream);
                            Object         nextToken  = ParseNextToken(cmapStream);
                            IList <byte[]> array      = null;
                            byte[]         tokenBytes = null;
                            if (nextToken is IList <byte[]> )
                            {
                                array      = (IList <byte[]>)nextToken;
                                tokenBytes = array[0];
                            }
                            else
                            {
                                tokenBytes = (byte[])nextToken;
                            }

                            String value = null;

                            int  arrayIndex = 0;
                            bool done       = false;
                            while (!done)
                            {
                                if (Compare(startCode, endCode) >= 0)
                                {
                                    done = true;
                                }
                                value = CreateStringFromBytes(tokenBytes);
                                result.AddMapping(startCode, value);
                                Increment(startCode);

                                if (array == null)
                                {
                                    Increment(tokenBytes);
                                }
                                else
                                {
                                    arrayIndex++;
                                    if (arrayIndex < array.Count)
                                    {
                                        tokenBytes = array[arrayIndex];
                                    }
                                }
                            }
                        }
                    }
                }
            }
            return(result);
        }
コード例 #2
0
ファイル: DocumentFont.cs プロジェクト: karino2/wikipediaconv
 private void DoType1TT()
 {
     PdfObject enc = PdfReader.GetPdfObject(font.Get(PdfName.ENCODING));
     if (enc == null)
         FillEncoding(null);
     else {
         if (enc.IsName())
             FillEncoding((PdfName)enc);
         else if (enc.IsDictionary()) {
             PdfDictionary encDic = (PdfDictionary)enc;
             enc = PdfReader.GetPdfObject(encDic.Get(PdfName.BASEENCODING));
             if (enc == null)
                 FillEncoding(null);
             else
                 FillEncoding((PdfName)enc);
             PdfArray diffs = encDic.GetAsArray(PdfName.DIFFERENCES);
             if (diffs != null) {
                 CMap toUnicode = null;
                 diffmap = new IntHashtable();
                 int currentNumber = 0;
                 for (int k = 0; k < diffs.Size; ++k) {
                     PdfObject obj = diffs[k];
                     if (obj.IsNumber())
                         currentNumber = ((PdfNumber)obj).IntValue;
                     else {
                         int[] c = GlyphList.NameToUnicode(PdfName.DecodeName(((PdfName)obj).ToString()));
                         if (c != null && c.Length > 0) {
                             uni2byte[c[0]] = currentNumber;
                             diffmap[c[0]] = currentNumber;
                         }
                         else {
                             if (toUnicode == null) {
                                 toUnicode = ProcessToUnicode();
                                 if (toUnicode == null) {
                                     toUnicode = new CMap();
                                 }
                             }
                             string unicode = toUnicode.Lookup(new byte[]{(byte) currentNumber}, 0, 1);
                             if ((unicode != null) && (unicode.Length == 1)) {
                                 this.uni2byte[unicode[0]] = currentNumber;
                                 this.diffmap[unicode[0]] = currentNumber;
                             }
                         }
                         ++currentNumber;
                     }
                 }
             }
         }
     }
     PdfArray newWidths = font.GetAsArray(PdfName.WIDTHS);
     PdfNumber first = font.GetAsNumber(PdfName.FIRSTCHAR);
     PdfNumber last = font.GetAsNumber(PdfName.LASTCHAR);
     if (BuiltinFonts14.ContainsKey(fontName)) {
         BaseFont bf;
             bf = BaseFont.CreateFont(fontName, WINANSI, false);
         int[] e = uni2byte.ToOrderedKeys();
         for (int k = 0; k < e.Length; ++k) {
             int n = uni2byte[e[k]];
             widths[n] = bf.GetRawWidth(n, GlyphList.UnicodeToName(e[k]));
         }
         if (diffmap != null) { //widths for differences must override existing ones
             e = diffmap.ToOrderedKeys();
             for (int k = 0; k < e.Length; ++k) {
                 int n = diffmap[e[k]];
                 widths[n] = bf.GetRawWidth(n, GlyphList.UnicodeToName(e[k]));
             }
             diffmap = null;
         }
         Ascender = bf.GetFontDescriptor(ASCENT, 1000);
         CapHeight = bf.GetFontDescriptor(CAPHEIGHT, 1000);
         Descender = bf.GetFontDescriptor(DESCENT, 1000);
         ItalicAngle = bf.GetFontDescriptor(ITALICANGLE, 1000);
         llx = bf.GetFontDescriptor(BBOXLLX, 1000);
         lly = bf.GetFontDescriptor(BBOXLLY, 1000);
         urx = bf.GetFontDescriptor(BBOXURX, 1000);
         ury = bf.GetFontDescriptor(BBOXURY, 1000);
     }
     if (first != null && last != null && newWidths != null) {
         int f = first.IntValue;
         for (int k = 0; k < newWidths.Size; ++k) {
             widths[f + k] = newWidths.GetAsNumber(k).IntValue;
         }
     }
     FillFontDesc(font.GetAsDict(PdfName.FONTDESCRIPTOR));
 }
コード例 #3
0
        /**
         * Parses the ToUnicode entry, if present, and constructs a CMap for it
         * @since 2.1.7
         */
        private void ProcessToUnicode()
        {
            PdfObject toUni = PdfReader.GetPdfObjectRelease(fontDic.Get(PdfName.TOUNICODE));
            if (toUni is PRStream){

                try {
                    byte[] touni = PdfReader.GetStreamBytes((PRStream)toUni);

                    CMapParser cmapParser = new CMapParser();
                    toUnicodeCmap = cmapParser.Parse(new MemoryStream(touni));
                } catch {
                    // technically, we should log this or provide some sort of feedback... but sometimes the cmap will be junk, but it's still possible to get text, so we don't want to throw an exception
                    //throw new IllegalStateException("Unable to process ToUnicode map - " + e.GetMessage(), e);
                }
            }
        }
コード例 #4
0
        /**
         * This will parse the stream and create a cmap object.
         *
         * @param input The CMAP stream to parse.
         * @return The parsed stream as a java object.
         *
         * @throws IOException If there is an error parsing the stream.
         */
        public CMap Parse( Stream input )
        {
            PushbackStream cmapStream = new PushbackStream( input );
            CMap result = new CMap();
            Object previousToken = null;
            Object token = null;
            while ( (token = ParseNextToken( cmapStream )) != null )
            {
                if ( token is Operator )
                {
                    Operator op = (Operator)token;
                    if ( op.op.Equals( BEGIN_CODESPACE_RANGE ) )
                    {
                        IConvertible cosCount = (IConvertible)previousToken;
                        for ( int j=0; j<cosCount.ToInt32(CultureInfo.InvariantCulture); j++ )
                        {
                            byte[] startRange = (byte[])ParseNextToken( cmapStream );
                            byte[] endRange = (byte[])ParseNextToken( cmapStream );
                            CodespaceRange range = new CodespaceRange();
                            range.SetStart( startRange );
                            range.SetEnd( endRange );
                            result.AddCodespaceRange( range );
                        }
                    }
                    else if ( op.op.Equals( BEGIN_BASE_FONT_CHAR ) )
                    {
                        IConvertible cosCount = (IConvertible)previousToken;
                        for ( int j=0; j<cosCount.ToInt32(CultureInfo.InvariantCulture); j++ )
                        {
                            byte[] inputCode = (byte[])ParseNextToken( cmapStream );
                            Object nextToken = ParseNextToken( cmapStream );
                            if ( nextToken is byte[] )
                            {
                                byte[] bytes = (byte[])nextToken;
                                String value = CreateStringFromBytes( bytes );
                                result.AddMapping( inputCode, value );
                            }
                            else if ( nextToken is LiteralName )
                            {
                                result.AddMapping( inputCode, ((LiteralName)nextToken).name );
                            }
                            else
                            {
                                throw new IOException(MessageLocalization.GetComposedMessage("error.parsing.cmap.beginbfchar.expected.cosstring.or.cosname.and.not.1", nextToken));
                            }
                        }
                    }
                   else if ( op.op.Equals( BEGIN_BASE_FONT_RANGE ) )
                    {
                        IConvertible cosCount = (IConvertible)previousToken;

                        for ( int j=0; j<cosCount.ToInt32(CultureInfo.InvariantCulture); j++ )
                        {
                            byte[] startCode = (byte[])ParseNextToken( cmapStream );
                            byte[] endCode = (byte[])ParseNextToken( cmapStream );
                            Object nextToken = ParseNextToken( cmapStream );
                            IList<byte[]> array = null;
                            byte[] tokenBytes = null;
                            if ( nextToken is IList<byte[]> )
                            {
                                array = (IList<byte[]>)nextToken;
                                tokenBytes = array[0];
                            }
                            else
                            {
                                tokenBytes = (byte[])nextToken;
                            }

                            String value = null;

                            int arrayIndex = 0;
                            bool done = false;
                            while ( !done )
                            {
                                if ( Compare( startCode, endCode ) >= 0 )
                                {
                                    done = true;
                                }
                                value = CreateStringFromBytes( tokenBytes );
                                result.AddMapping( startCode, value );
                                Increment( startCode );

                                if ( array == null )
                                {
                                    Increment( tokenBytes );
                                }
                                else
                                {
                                    arrayIndex++;
                                    if ( arrayIndex < array.Count )
                                    {
                                        tokenBytes = array[arrayIndex];
                                    }
                                }
                            }
                        }
                    }
                }
                previousToken = token;
            }
            return result;
        }