LCOV - code coverage report
Current view: top level - usr/local/src/libreoffice/sdext/source/pdfimport/xpdfwrapper - pdfioutdev_gpl.cxx (source / functions) Hit Total Coverage
Test: libreoffice_filtered.info Lines: 238 404 58.9 %
Date: 2013-07-09 Functions: 38 53 71.7 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2             : /*
       3             :  * This file is part of the LibreOffice project.
       4             :  *
       5             :  * This Source Code Form is subject to the terms of the Mozilla Public
       6             :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       7             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       8             :  *
       9             :  * This file incorporates work covered by the following license notice:
      10             :  *
      11             :  *   Licensed to the Apache Software Foundation (ASF) under one or more
      12             :  *   contributor license agreements. See the NOTICE file distributed
      13             :  *   with this work for additional information regarding copyright
      14             :  *   ownership. The ASF licenses this file to you under the Apache
      15             :  *   License, Version 2.0 (the "License"); you may not use this file
      16             :  *   except in compliance with the License. You may obtain a copy of
      17             :  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
      18             :  */
      19             : 
      20             : #include "pdfioutdev_gpl.hxx"
      21             : #include "pnghelper.hxx"
      22             : 
      23             : #include <stdlib.h>
      24             : #include <stdio.h>
      25             : #include <assert.h>
      26             : #include <math.h>
      27             : #include <vector>
      28             : 
      29             : #include <boost/shared_array.hpp>
      30             : 
      31             : #if defined __SUNPRO_CC
      32             : #pragma disable_warn
      33             : #elif defined _MSC_VER
      34             : #pragma warning(push, 1)
      35             : #endif
      36             : 
      37             : // sigh, UTF8.h was removed in poppler-0.21.0 and put back in 0.21.1
      38             : // FIXME: we can't use #if POPPLER_CHECK_VERSION(0, 21, 0) && !POPPLER_CHECK_VERSION(0, 21, 1)
      39             : //        because the internal poppler does not provide poppler-version.h and the macro always returns 0
      40             : #if POPPLER_CHECK_VERSION(0, 21, 1)
      41             : #include "UTF8.h"
      42             : #elif POPPLER_CHECK_VERSION(0, 21, 0)
      43             : #include "UTF.h"
      44             : #else
      45             : #include "UTF8.h"
      46             : #endif
      47             : 
      48             : #if defined __SUNPRO_CC
      49             : #pragma enable_warn
      50             : #elif defined _MSC_VER
      51             : #pragma warning(pop)
      52             : #endif
      53             : 
      54             : #ifdef WNT
      55             : # define snprintf _snprintf
      56             : 
      57             : #if defined __GNUC__
      58             : #pragma GCC diagnostic warning "-Wformat"
      59             : #pragma GCC diagnostic warning "-Wformat-extra-args"
      60             : #endif
      61             : #endif
      62             : 
      63             : /* SYNC STREAMS
      64             :    ============
      65             : 
      66             :    We stream human-readble tokens to stdout, and binary data (fonts,
      67             :    bitmaps) to g_binary_out. Another process reads from those pipes, and
      68             :    there lies the rub: things can deadlock, if the two involved
      69             :    processes access the pipes in different order. At any point in
      70             :    time, both processes must access the same pipe. To ensure this,
      71             :    data must be flushed to the OS before writing to a different pipe,
      72             :    otherwise not-yet-written data will leave the reading process
      73             :    waiting on the wrong pipe.
      74             :  */
      75             : 
      76             : namespace pdfi
      77             : {
      78             : 
      79             : /// cut off very small numbers & clamp value to zero
      80        2991 : inline double normalize( double val )
      81             : {
      82        2991 :     return fabs(val) < 0.0000001 ? 0.0 : val;
      83             : }
      84             : 
      85             : namespace
      86             : {
      87             : 
      88             : /** Escapes line-ending characters (\n and \r) in input string.
      89             :   */
      90         348 : boost::shared_array<char> lcl_escapeLineFeeds(const char* const i_pStr)
      91             : {
      92         348 :     size_t nLength(strlen(i_pStr));
      93         348 :     char* pBuffer = new char[2*nLength+1];
      94             : 
      95         348 :     const char* pRead = i_pStr;
      96         348 :     char* pWrite = pBuffer;
      97        1584 :     while( nLength-- )
      98             :     {
      99         888 :         if( *pRead == '\r' )
     100             :         {
     101           0 :             *pWrite++ = '\\';
     102           0 :             *pWrite++ = 'r';
     103             :         }
     104         888 :         else if( *pRead == '\n' )
     105             :         {
     106           0 :             *pWrite++ = '\\';
     107           0 :             *pWrite++ = 'n';
     108             :         }
     109         888 :         else if( *pRead == '\\' )
     110             :         {
     111           0 :             *pWrite++ = '\\';
     112           0 :             *pWrite++ = '\\';
     113             :         }
     114             :         else
     115         888 :             *pWrite++ = *pRead;
     116         888 :         pRead++;
     117             :     }
     118         348 :     *pWrite++ = 0;
     119             : 
     120         348 :     return boost::shared_array<char>(pBuffer);
     121             : }
     122             : 
     123             : }
     124             : 
     125             : /// for the temp char buffer the header gets snprintfed in
     126             : #define WRITE_BUFFER_SIZE 1024
     127             : 
     128             : /// for the initial std::vector capacity when copying stream from xpdf
     129             : #define WRITE_BUFFER_INITIAL_CAPACITY (1024*100)
     130             : 
     131           3 : void initBuf(OutputBuffer& io_rBuffer)
     132             : {
     133           3 :     io_rBuffer.reserve(WRITE_BUFFER_INITIAL_CAPACITY);
     134           3 : }
     135             : 
     136           6 : void writeBinaryBuffer( const OutputBuffer& rBuffer )
     137             : {
     138             :     // ---sync point--- see SYNC STREAMS above
     139           6 :     fflush(stdout);
     140             : 
     141             :     // put buffer to stderr
     142           6 :     if( !rBuffer.empty() )
     143           6 :         if( fwrite(&rBuffer[0], sizeof(char),
     144           6 :                    rBuffer.size(), g_binary_out) != (size_t)rBuffer.size() )
     145           0 :             exit(1); // error
     146             : 
     147             :     // ---sync point--- see SYNC STREAMS above
     148           6 :     fflush(g_binary_out);
     149           6 : }
     150             : 
     151           3 : void writeJpeg_( OutputBuffer& o_rOutputBuf, Stream* str, bool bWithLinefeed )
     152             : {
     153             :     // dump JPEG file as-is
     154             : #if POPPLER_CHECK_VERSION(0, 17, 3)
     155           3 :     str = str->getBaseStream();
     156             : #else
     157             :     str = ((DCTStream *)str)->getRawStream();
     158             : #endif
     159           3 :     str->reset();
     160             : 
     161             :     int c;
     162           3 :     o_rOutputBuf.clear();
     163      132393 :     while((c=str->getChar()) != EOF)
     164      132387 :         o_rOutputBuf.push_back(static_cast<char>(c));
     165             : 
     166           3 :     printf( " JPEG %d", (int)o_rOutputBuf.size() );
     167           3 :     if( bWithLinefeed )
     168           3 :         printf("\n");
     169             : 
     170           3 :     str->close();
     171           3 : }
     172             : 
     173           0 : void writePbm_(OutputBuffer& o_rOutputBuf, Stream* str, int width, int height, bool bWithLinefeed, bool bInvert )
     174             : {
     175             :     // write as PBM (char by char, to avoid stdlib lineend messing)
     176           0 :     o_rOutputBuf.clear();
     177           0 :     o_rOutputBuf.resize(WRITE_BUFFER_SIZE);
     178           0 :     o_rOutputBuf[0] = 'P';
     179           0 :     o_rOutputBuf[1] = '4';
     180           0 :     o_rOutputBuf[2] = 0x0A;
     181           0 :     char *pAsCharPtr = reinterpret_cast<char *>(&o_rOutputBuf[3]);
     182           0 :     int nOutLen = snprintf(pAsCharPtr, WRITE_BUFFER_SIZE-10, "%d %d", width, height);
     183           0 :     if( nOutLen < 0 )
     184           0 :         nOutLen = WRITE_BUFFER_SIZE-10;
     185           0 :     o_rOutputBuf[3+nOutLen]  =0x0A;
     186           0 :     o_rOutputBuf[3+nOutLen+1]=0;
     187             : 
     188           0 :     const int header_size = 3+nOutLen+1;
     189           0 :     const int size = height * ((width + 7) / 8);
     190             : 
     191           0 :     printf( " PBM %d", size + header_size );
     192           0 :     if( bWithLinefeed )
     193           0 :         printf("\n");
     194             : 
     195             :     // trim buffer to exact header length
     196           0 :     o_rOutputBuf.resize(header_size);
     197             : 
     198             :     // initialize stream
     199           0 :     str->reset();
     200             : 
     201             :     // copy the raw stream
     202           0 :     if( bInvert )
     203             :     {
     204           0 :         for( int i=0; i<size; ++i)
     205           0 :             o_rOutputBuf.push_back(static_cast<char>(str->getChar() ^ 0xff));
     206             :     }
     207             :     else
     208             :     {
     209           0 :         for( int i=0; i<size; ++i)
     210           0 :             o_rOutputBuf.push_back(static_cast<char>(str->getChar()));
     211             :     }
     212             : 
     213           0 :     str->close();
     214           0 : }
     215             : 
     216           0 : void writePpm_( OutputBuffer&     o_rOutputBuf,
     217             :                 Stream*           str,
     218             :                 int               width,
     219             :                 int               height,
     220             :                 GfxImageColorMap* colorMap,
     221             :                 bool              bWithLinefeed )
     222             : {
     223             :     // write as PPM (char by char, to avoid stdlib lineend messing)
     224           0 :     o_rOutputBuf.clear();
     225           0 :     o_rOutputBuf.resize(WRITE_BUFFER_SIZE);
     226           0 :     o_rOutputBuf[0] = 'P';
     227           0 :     o_rOutputBuf[1] = '6';
     228           0 :     o_rOutputBuf[2] = '\n';
     229           0 :     char *pAsCharPtr = reinterpret_cast<char *>(&o_rOutputBuf[3]);
     230           0 :     int nOutLen = snprintf(pAsCharPtr, WRITE_BUFFER_SIZE-10, "%d %d", width, height);
     231           0 :     if( nOutLen < 0 )
     232           0 :         nOutLen = WRITE_BUFFER_SIZE-10;
     233           0 :     o_rOutputBuf[3+nOutLen]  ='\n';
     234           0 :     o_rOutputBuf[3+nOutLen+1]='2';
     235           0 :     o_rOutputBuf[3+nOutLen+2]='5';
     236           0 :     o_rOutputBuf[3+nOutLen+3]='5';
     237           0 :     o_rOutputBuf[3+nOutLen+4]='\n';
     238           0 :     o_rOutputBuf[3+nOutLen+5]=0;
     239             : 
     240           0 :     const int header_size = 3+nOutLen+5;
     241           0 :     const int size = width*height*3 + header_size;
     242             : 
     243           0 :     printf( " PPM %d", size );
     244           0 :     if( bWithLinefeed )
     245           0 :         printf("\n");
     246             : 
     247             :     // trim buffer to exact header size
     248           0 :     o_rOutputBuf.resize(header_size);
     249             : 
     250             :     // initialize stream
     251             :     Guchar *p;
     252             :     GfxRGB rgb;
     253             :     ImageStream* imgStr =
     254             :         new ImageStream(str,
     255             :                         width,
     256             :                         colorMap->getNumPixelComps(),
     257           0 :                         colorMap->getBits());
     258           0 :     imgStr->reset();
     259             : 
     260           0 :     for( int y=0; y<height; ++y)
     261             :     {
     262           0 :         p = imgStr->getLine();
     263           0 :         for( int x=0; x<width; ++x)
     264             :         {
     265           0 :             colorMap->getRGB(p, &rgb);
     266           0 :             o_rOutputBuf.push_back(colToByte(rgb.r));
     267           0 :             o_rOutputBuf.push_back(colToByte(rgb.g));
     268           0 :             o_rOutputBuf.push_back(colToByte(rgb.b));
     269             : 
     270           0 :             p +=colorMap->getNumPixelComps();
     271             :         }
     272             :     }
     273             : 
     274           0 :     delete imgStr;
     275             : 
     276           0 : }
     277             : 
     278             : // call this only for 1 bit image streams !
     279           0 : void writePng_( OutputBuffer&     o_rOutputBuf,
     280             :                 Stream*           str,
     281             :                 int               width,
     282             :                 int               height,
     283             :                 GfxRGB&           zeroColor,
     284             :                 GfxRGB&           oneColor,
     285             :                 bool              bIsMask,
     286             :                 bool              bWithLinefeed )
     287             : {
     288           0 :     o_rOutputBuf.clear();
     289             : 
     290             :     // get png image
     291           0 :     PngHelper::createPng( o_rOutputBuf, str, width, height, zeroColor, oneColor, bIsMask );
     292             : 
     293           0 :     printf( " PNG %d", (int)o_rOutputBuf.size() );
     294           0 :     if( bWithLinefeed )
     295           0 :         printf("\n");
     296           0 : }
     297             : 
     298           0 : void writePng_( OutputBuffer& o_rOutputBuf,
     299             :                 Stream* str,
     300             :                 int width, int height, GfxImageColorMap* colorMap,
     301             :                 Stream* maskStr,
     302             :                 int maskWidth, int maskHeight, GfxImageColorMap* maskColorMap,
     303             :                 bool bWithLinefeed )
     304             : {
     305           0 :     o_rOutputBuf.clear();
     306             : 
     307             :     // get png image
     308           0 :     PngHelper::createPng( o_rOutputBuf, str, width, height, colorMap, maskStr, maskWidth, maskHeight, maskColorMap );
     309             : 
     310           0 :     printf( " PNG %d", (int)o_rOutputBuf.size() );
     311           0 :     if( bWithLinefeed )
     312           0 :         printf("\n");
     313           0 : }
     314             : 
     315           0 : void writePng_( OutputBuffer& o_rOutputBuf,
     316             :                 Stream* str,
     317             :                 int width, int height, GfxImageColorMap* colorMap,
     318             :                 Stream* maskStr,
     319             :                 int maskWidth, int maskHeight, bool maskInvert,
     320             :                 bool bWithLinefeed )
     321             : {
     322           0 :     o_rOutputBuf.clear();
     323             : 
     324             :     // get png image
     325           0 :     PngHelper::createPng( o_rOutputBuf, str, width, height, colorMap, maskStr, maskWidth, maskHeight, maskInvert );
     326             : 
     327           0 :     printf( " PNG %d", (int)o_rOutputBuf.size() );
     328           0 :     if( bWithLinefeed )
     329           0 :         printf("\n");
     330           0 : }
     331             : 
     332             : // stolen from ImageOutputDev.cc
     333           0 : void writeMask_( OutputBuffer& o_rOutputBuf, Stream* str, int width, int height, bool bWithLinefeed, bool bInvert )
     334             : {
     335           0 :     if( str->getKind() == strDCT )
     336           0 :         writeJpeg_(o_rOutputBuf, str, bWithLinefeed);
     337             :     else
     338           0 :         writePbm_(o_rOutputBuf, str, width, height, bWithLinefeed, bInvert );
     339           0 : }
     340             : 
     341           3 : void writeImage_( OutputBuffer&     o_rOutputBuf,
     342             :                   Stream*           str,
     343             :                   int               width,
     344             :                   int               height,
     345             :                   GfxImageColorMap* colorMap,
     346             :                   bool              bWithLinefeed )
     347             : {
     348             :     // dump JPEG file
     349           9 :     if( str->getKind() == strDCT &&
     350           6 :         (colorMap->getNumPixelComps() == 1 ||
     351           3 :          colorMap->getNumPixelComps() == 3) )
     352             :     {
     353           3 :         writeJpeg_(o_rOutputBuf, str, bWithLinefeed);
     354             :     }
     355           0 :     else if (colorMap->getNumPixelComps() == 1 &&
     356           0 :              colorMap->getBits() == 1)
     357             :     {
     358             :         // this is a two color bitmap, write a png
     359             :         // provide default colors
     360           0 :         GfxRGB zeroColor = { 0, 0, 0 },
     361           0 :                 oneColor = { byteToCol( 0xff ), byteToCol( 0xff ), byteToCol( 0xff ) };
     362           0 :         if( colorMap->getColorSpace()->getMode() == csIndexed || colorMap->getColorSpace()->getMode() == csDeviceGray )
     363             :         {
     364           0 :             Guchar nIndex = 0;
     365           0 :             colorMap->getRGB( &nIndex, &zeroColor );
     366           0 :             nIndex = 1;
     367           0 :             colorMap->getRGB( &nIndex, &oneColor );
     368             :         }
     369           0 :         writePng_( o_rOutputBuf, str, width, height, zeroColor, oneColor, false, bWithLinefeed );
     370             :     }
     371             :     else
     372           0 :         writePpm_( o_rOutputBuf, str, width, height, colorMap, bWithLinefeed );
     373           3 : }
     374             : 
     375             : // forwarders
     376             : // ------------------------------------------------------------------
     377             : 
     378             : inline void writeImage( OutputBuffer&     o_rOutputBuf,
     379             :                         Stream*           str,
     380             :                         int               width,
     381             :                         int               height,
     382             :                         GfxImageColorMap* colorMap ) { writeImage_(o_rOutputBuf,str,width,height,colorMap,false); }
     383           3 : inline void writeImageLF( OutputBuffer&     o_rOutputBuf,
     384             :                           Stream*           str,
     385             :                           int               width,
     386             :                           int               height,
     387           3 :                           GfxImageColorMap* colorMap ) { writeImage_(o_rOutputBuf,str,width,height,colorMap,true); }
     388             : inline void writeMask( OutputBuffer&     o_rOutputBuf,
     389             :                        Stream*           str,
     390             :                        int               width,
     391             :                        int               height,
     392             :                        bool              bInvert ) { writeMask_(o_rOutputBuf,str,width,height,false,bInvert); }
     393           0 : inline void writeMaskLF( OutputBuffer&     o_rOutputBuf,
     394             :                          Stream*           str,
     395             :                          int               width,
     396             :                          int               height,
     397           0 :                          bool              bInvert ) { writeMask_(o_rOutputBuf,str,width,height,true,bInvert); }
     398             : 
     399             : // ------------------------------------------------------------------
     400             : 
     401             : 
     402           9 : int PDFOutDev::parseFont( long long nNewId, GfxFont* gfxFont, GfxState* state ) const
     403             : {
     404           9 :     FontAttributes aNewFont;
     405           9 :     int nSize = 0;
     406             : 
     407           9 :     GooString* pFamily = gfxFont->getName();
     408           9 :     if( pFamily )
     409             :     {
     410           9 :         aNewFont.familyName.clear();
     411           9 :         aNewFont.familyName.append( gfxFont->getName() );
     412             :     }
     413             :     else
     414             :     {
     415           0 :         aNewFont.familyName.clear();
     416           0 :         aNewFont.familyName.append( "Arial" );
     417             :     }
     418             : 
     419           9 :     aNewFont.isBold        = gfxFont->isBold();
     420           9 :     aNewFont.isItalic      = gfxFont->isItalic();
     421           9 :     aNewFont.size          = state->getTransformedFontSize();
     422           9 :     aNewFont.isUnderline   = false;
     423             : 
     424           9 :     if( gfxFont->getType() == fontTrueType || gfxFont->getType() == fontType1 )
     425             :     {
     426             :         // TODO(P3): Unfortunately, need to read stream twice, since
     427             :         // we must write byte count to stdout before
     428           9 :         char* pBuf = gfxFont->readEmbFontFile( m_pDoc->getXRef(), &nSize );
     429           9 :         if( pBuf )
     430             :         {
     431           9 :             aNewFont.isEmbedded = true;
     432           9 :             gfree(pBuf);
     433             :         }
     434             :     }
     435             : 
     436           9 :     m_aFontMap[ nNewId ] = aNewFont;
     437           9 :     return nSize;
     438             : }
     439             : 
     440           9 : void PDFOutDev::writeFontFile( GfxFont* gfxFont ) const
     441             : {
     442           9 :     if( gfxFont->getType() != fontTrueType && gfxFont->getType() != fontType1 )
     443           0 :         return;
     444             : 
     445           9 :     int nSize = 0;
     446           9 :     char* pBuf = gfxFont->readEmbFontFile( m_pDoc->getXRef(), &nSize );
     447           9 :     if( !pBuf )
     448           0 :         return;
     449             : 
     450             :     // ---sync point--- see SYNC STREAMS above
     451           9 :     fflush(stdout);
     452             : 
     453           9 :     if( fwrite(pBuf, sizeof(char), nSize, g_binary_out) != (size_t)nSize )
     454             :     {
     455           0 :         gfree(pBuf);
     456           0 :         exit(1); // error
     457             :     }
     458             :     // ---sync point--- see SYNC STREAMS above
     459           9 :     fflush(g_binary_out);
     460           9 :     gfree(pBuf);
     461             : }
     462             : 
     463          15 : void PDFOutDev::printPath( GfxPath* pPath ) const
     464             : {
     465          15 :     int nSubPaths = pPath ? pPath->getNumSubpaths() : 0;
     466          30 :     for( int i=0; i<nSubPaths; i++ )
     467             :     {
     468          15 :         GfxSubpath* pSub  = pPath->getSubpath( i );
     469          15 :         const int nPoints = pSub->getNumPoints();
     470             : 
     471          15 :         printf( " subpath %d", pSub->isClosed() );
     472             : 
     473          96 :         for( int n=0; n<nPoints; ++n )
     474             :         {
     475             :             printf( " %f %f %d",
     476             :                     normalize(pSub->getX(n)),
     477             :                     normalize(pSub->getY(n)),
     478          81 :                     pSub->getCurve(n) );
     479             :         }
     480             :     }
     481          15 : }
     482             : 
     483           3 : PDFOutDev::PDFOutDev( PDFDoc* pDoc ) :
     484             :     m_pDoc( pDoc ),
     485             :     m_aFontMap(),
     486           3 :     m_pUtf8Map( new UnicodeMap((char*)"UTF-8", gTrue, &mapUTF8) )
     487             : {
     488           3 : }
     489           0 : PDFOutDev::~PDFOutDev()
     490             : {
     491           0 :     delete m_pUtf8Map;
     492           0 : }
     493             : 
     494           3 : void PDFOutDev::startPage(int /*pageNum*/, GfxState* state)
     495             : {
     496             :     assert(state);
     497             :     printf("startPage %f %f\n",
     498             :            normalize(state->getPageWidth()),
     499           3 :            normalize(state->getPageHeight()));
     500           3 : }
     501             : 
     502           3 : void PDFOutDev::endPage()
     503             : {
     504           3 :     printf("endPage\n");
     505           3 : }
     506             : 
     507             : #if POPPLER_CHECK_VERSION(0, 19, 0)
     508           3 : void PDFOutDev::processLink(AnnotLink *link)
     509             : #elif POPPLER_CHECK_VERSION(0, 17, 0)
     510             : void PDFOutDev::processLink(AnnotLink *link, Catalog *)
     511             : #else
     512             : void PDFOutDev::processLink(Link* link, Catalog*)
     513             : #endif
     514             : {
     515             :     assert(link);
     516             : 
     517             :     double x1,x2,y1,y2;
     518           3 :     link->getRect( &x1, &y1, &x2, &y2 );
     519             : 
     520           3 :     LinkAction* pAction = link->getAction();
     521           3 :     if( pAction->getKind() == actionURI )
     522             :     {
     523           3 :         const char* pURI = static_cast<LinkURI*>(pAction)->getURI()->getCString();
     524             : 
     525           3 :         boost::shared_array<char> pEsc( lcl_escapeLineFeeds(pURI) );
     526             : 
     527             :         printf( "drawLink %f %f %f %f %s\n",
     528             :                 normalize(x1),
     529             :                 normalize(y1),
     530             :                 normalize(x2),
     531             :                 normalize(y2),
     532           3 :                 pEsc.get() );
     533             :     }
     534           3 : }
     535             : 
     536          48 : void PDFOutDev::saveState(GfxState*)
     537             : {
     538          48 :     printf( "saveState\n" );
     539          48 : }
     540             : 
     541          48 : void PDFOutDev::restoreState(GfxState*)
     542             : {
     543          48 :     printf( "restoreState\n" );
     544          48 : }
     545             : 
     546           3 : void PDFOutDev::setDefaultCTM(double *pMat)
     547             : {
     548             :     assert(pMat);
     549             : 
     550           3 :     OutputDev::setDefaultCTM(pMat);
     551             : 
     552             :     printf( "updateCtm %f %f %f %f %f %f\n",
     553             :             normalize(pMat[0]),
     554           3 :             normalize(pMat[2]),
     555           3 :             normalize(pMat[1]),
     556           3 :             normalize(pMat[3]),
     557           3 :             normalize(pMat[4]),
     558          15 :             normalize(pMat[5]) );
     559           3 : }
     560             : 
     561           3 : void PDFOutDev::updateCTM(GfxState* state,
     562             :                           double, double,
     563             :                           double, double,
     564             :                           double, double)
     565             : {
     566             :     assert(state);
     567             : 
     568           3 :     const double* const pMat = state->getCTM();
     569             :     assert(pMat);
     570             : 
     571             :     printf( "updateCtm %f %f %f %f %f %f\n",
     572             :             normalize(pMat[0]),
     573           3 :             normalize(pMat[2]),
     574           3 :             normalize(pMat[1]),
     575           3 :             normalize(pMat[3]),
     576           3 :             normalize(pMat[4]),
     577          15 :             normalize(pMat[5]) );
     578           3 : }
     579             : 
     580           6 : void PDFOutDev::updateLineDash(GfxState *state)
     581             : {
     582             :     assert(state);
     583             : 
     584             :     double* dashArray; int arrayLen; double startOffset;
     585           6 :     state->getLineDash(&dashArray, &arrayLen, &startOffset);
     586             : 
     587           6 :     printf( "updateLineDash" );
     588           6 :     if( arrayLen && dashArray )
     589             :     {
     590           3 :         printf( " %f %d", normalize(startOffset), arrayLen );
     591          15 :         for( int i=0; i<arrayLen; ++i )
     592          12 :             printf( " %f", normalize(*dashArray++) );
     593             :     }
     594           6 :     printf( "\n" );
     595           6 : }
     596             : 
     597           3 : void PDFOutDev::updateFlatness(GfxState *state)
     598             : {
     599             :     assert(state);
     600           3 :     printf( "updateFlatness %d\n", state->getFlatness() );
     601           3 : }
     602             : 
     603           9 : void PDFOutDev::updateLineJoin(GfxState *state)
     604             : {
     605             :     assert(state);
     606           9 :     printf( "updateLineJoin %d\n", state->getLineJoin() );
     607           9 : }
     608             : 
     609           9 : void PDFOutDev::updateLineCap(GfxState *state)
     610             : {
     611             :     assert(state);
     612           9 :     printf( "updateLineCap %d\n", state->getLineCap() );
     613           9 : }
     614             : 
     615           3 : void PDFOutDev::updateMiterLimit(GfxState *state)
     616             : {
     617             :     assert(state);
     618           3 :     printf( "updateMiterLimit %f\n", normalize(state->getMiterLimit()) );
     619           3 : }
     620             : 
     621          12 : void PDFOutDev::updateLineWidth(GfxState *state)
     622             : {
     623             :     assert(state);
     624          12 :     printf( "updateLineWidth %f\n", normalize(state->getLineWidth()) );
     625          12 : }
     626             : 
     627          42 : void PDFOutDev::updateFillColor(GfxState *state)
     628             : {
     629             :     assert(state);
     630             : 
     631             :     GfxRGB aRGB;
     632          42 :     state->getFillRGB( &aRGB );
     633             : 
     634             :     printf( "updateFillColor %f %f %f %f\n",
     635             :             normalize(colToDbl(aRGB.r)),
     636             :             normalize(colToDbl(aRGB.g)),
     637             :             normalize(colToDbl(aRGB.b)),
     638          42 :             normalize(state->getFillOpacity()) );
     639          42 : }
     640             : 
     641          12 : void PDFOutDev::updateStrokeColor(GfxState *state)
     642             : {
     643             :     assert(state);
     644             : 
     645             :     GfxRGB aRGB;
     646          12 :     state->getStrokeRGB( &aRGB );
     647             : 
     648             :     printf( "updateStrokeColor %f %f %f %f\n",
     649             :             normalize(colToDbl(aRGB.r)),
     650             :             normalize(colToDbl(aRGB.g)),
     651             :             normalize(colToDbl(aRGB.b)),
     652          12 :             normalize(state->getFillOpacity()) );
     653          12 : }
     654             : 
     655           3 : void PDFOutDev::updateFillOpacity(GfxState *state)
     656             : {
     657           3 :     updateFillColor(state);
     658           3 : }
     659             : 
     660           3 : void PDFOutDev::updateStrokeOpacity(GfxState *state)
     661             : {
     662           3 :     updateStrokeColor(state);
     663           3 : }
     664             : 
     665           3 : void PDFOutDev::updateBlendMode(GfxState*)
     666             : {
     667           3 : }
     668             : 
     669          36 : void PDFOutDev::updateFont(GfxState *state)
     670             : {
     671             :     assert(state);
     672             : 
     673          36 :     GfxFont *gfxFont = state->getFont();
     674          36 :     if( gfxFont )
     675             :     {
     676          33 :         FontAttributes aFont;
     677          33 :         int nEmbedSize=0;
     678             : 
     679          33 :         Ref* pID = gfxFont->getID();
     680             :         // TODO(Q3): Portability problem
     681          33 :         long long fontID = (long long)pID->gen << 32 | (long long)pID->num;
     682             :         boost::unordered_map< long long, FontAttributes >::const_iterator it =
     683          33 :             m_aFontMap.find( fontID );
     684          33 :         if( it == m_aFontMap.end() )
     685             :         {
     686           9 :             nEmbedSize = parseFont( fontID, gfxFont, state );
     687           9 :             it = m_aFontMap.find( fontID );
     688             :         }
     689             : 
     690          33 :         printf( "updateFont" );
     691          33 :         if( it != m_aFontMap.end() )
     692             :         {
     693             :             // conflating this with printf below crashes under Windoze
     694          33 :             printf( " %lld", fontID );
     695             : 
     696          33 :             aFont = it->second;
     697             : 
     698          33 :             boost::shared_array<char> pEsc( lcl_escapeLineFeeds(aFont.familyName.getCString()) );
     699             :             printf( " %d %d %d %d %f %d %s",
     700             :                     aFont.isEmbedded,
     701             :                     aFont.isBold,
     702             :                     aFont.isItalic,
     703             :                     aFont.isUnderline,
     704             :                     normalize(state->getTransformedFontSize()),
     705             :                     nEmbedSize,
     706          33 :                     pEsc.get() );
     707             :         }
     708          33 :         printf( "\n" );
     709             : 
     710          33 :         if( nEmbedSize )
     711           9 :             writeFontFile(gfxFont);
     712             :     }
     713          36 : }
     714             : 
     715           0 : void PDFOutDev::updateRender(GfxState *state)
     716             : {
     717             :     assert(state);
     718             : 
     719           0 :     printf( "setTextRenderMode %d\n", state->getRender() );
     720           0 : }
     721             : 
     722           6 : void PDFOutDev::stroke(GfxState *state)
     723             : {
     724             :     assert(state);
     725             : 
     726           6 :     printf( "strokePath" );
     727           6 :     printPath( state->getPath() );
     728           6 :     printf( "\n" );
     729           6 : }
     730             : 
     731           0 : void PDFOutDev::fill(GfxState *state)
     732             : {
     733             :     assert(state);
     734             : 
     735           0 :     printf( "fillPath" );
     736           0 :     printPath( state->getPath() );
     737           0 :     printf( "\n" );
     738           0 : }
     739             : 
     740           3 : void PDFOutDev::eoFill(GfxState *state)
     741             : {
     742             :     assert(state);
     743             : 
     744           3 :     printf( "eoFillPath" );
     745           3 :     printPath( state->getPath() );
     746           3 :     printf( "\n" );
     747           3 : }
     748             : 
     749           3 : void PDFOutDev::clip(GfxState *state)
     750             : {
     751             :     assert(state);
     752             : 
     753           3 :     printf( "clipPath" );
     754           3 :     printPath( state->getPath() );
     755           3 :     printf( "\n" );
     756           3 : }
     757             : 
     758           3 : void PDFOutDev::eoClip(GfxState *state)
     759             : {
     760             :     assert(state);
     761             : 
     762           3 :     printf( "eoClipPath" );
     763           3 :     printPath( state->getPath() );
     764           3 :     printf( "\n" );
     765           3 : }
     766             : 
     767             : /** Output one glyph
     768             : 
     769             : 
     770             :     @param dx
     771             :     horizontal skip for character (already scaled with font size) +
     772             :     inter-char space: cursor is shifted by this amount for next char
     773             : 
     774             :     @param dy
     775             :     vertical skip for character (zero for horizontal writing mode):
     776             :     cursor is shifted by this amount for next char
     777             : 
     778             :     @param originX
     779             :     local offset of character (zero for horizontal writing mode). not
     780             :     taken into account for output pos updates. Used for vertical writing.
     781             : 
     782             :     @param originY
     783             :     local offset of character (zero for horizontal writing mode). not
     784             :     taken into account for output pos updates. Used for vertical writing.
     785             :  */
     786         312 : void PDFOutDev::drawChar(GfxState *state, double x, double y,
     787             :                          double dx, double dy,
     788             :                          double originX, double originY,
     789             :                          CharCode, int /*nBytes*/, Unicode *u, int uLen)
     790             : {
     791             :     assert(state);
     792             : 
     793         312 :     if( u == NULL )
     794         312 :         return;
     795             : 
     796             :     // normalize coordinates: correct from baseline-relative to upper
     797             :     // left corner of glyphs
     798         312 :     double x2(0.0), y2(0.0);
     799             :     state->textTransformDelta( 0.0,
     800             :                                state->getFont()->getAscent(),
     801         312 :                                &x2, &y2 );
     802         312 :     const double fFontSize(state->getFontSize());
     803         312 :     x += x2*fFontSize;
     804         312 :     y += y2*fFontSize;
     805             : 
     806         312 :     const double aPositionX(x-originX);
     807         312 :     const double aPositionY(y-originY);
     808             :     // TODO(F2): use leading here, when set
     809         312 :     const double nWidth(dx != 0.0 ? dx : fFontSize);
     810         312 :     const double nHeight(dy != 0.0 ? dy : fFontSize);
     811             : 
     812         312 :     const double* pTextMat=state->getTextMat();
     813             :     printf( "drawChar %f %f %f %f %f %f %f %f ",
     814             :             normalize(aPositionX),
     815             :             normalize(aPositionY),
     816             :             normalize(aPositionX+nWidth),
     817             :             normalize(aPositionY-nHeight),
     818             :             normalize(pTextMat[0]),
     819         312 :             normalize(pTextMat[2]),
     820         312 :             normalize(pTextMat[1]),
     821         936 :             normalize(pTextMat[3]) );
     822             : 
     823             :     // silence spurious warning
     824             :     (void)&mapUCS2;
     825             : 
     826             :     char buf[9];
     827         624 :     for( int i=0; i<uLen; ++i )
     828             :     {
     829         312 :         buf[ m_pUtf8Map->mapUnicode(u[i], buf, sizeof(buf)-1) ] = 0;
     830         312 :         boost::shared_array<char> pEsc( lcl_escapeLineFeeds(buf) );
     831         312 :         printf( "%s", pEsc.get() );
     832         312 :     }
     833             : 
     834         312 :     printf( "\n" );
     835             : }
     836             : 
     837           0 : void PDFOutDev::drawString(GfxState*, GooString* /*s*/)
     838             : {
     839             :     // TODO(F3): NYI
     840           0 : }
     841             : 
     842          33 : void PDFOutDev::endTextObject(GfxState*)
     843             : {
     844          33 :     printf( "endTextObject\n" );
     845          33 : }
     846             : 
     847           0 : void PDFOutDev::drawImageMask(GfxState* pState, Object*, Stream* str,
     848             :                               int width, int height, GBool invert,
     849             : #if POPPLER_CHECK_VERSION(0, 12, 0)
     850             :                               GBool /*interpolate*/,
     851             : #endif
     852             :                               GBool /*inlineImg*/ )
     853             : {
     854           0 :     OutputBuffer aBuf; initBuf(aBuf);
     855             : 
     856           0 :     printf( "drawMask %d %d %d", width, height, invert );
     857             : 
     858           0 :     int bitsPerComponent = 1;
     859           0 :     StreamColorSpaceMode csMode = streamCSNone;
     860           0 :     str->getImageParams( &bitsPerComponent, &csMode );
     861           0 :     if( bitsPerComponent == 1 && (csMode == streamCSNone || csMode == streamCSDeviceGray) )
     862             :     {
     863           0 :         GfxRGB oneColor = { dblToCol( 1.0 ), dblToCol( 1.0 ), dblToCol( 1.0 ) };
     864           0 :         GfxRGB zeroColor = { dblToCol( 0.0 ), dblToCol( 0.0 ), dblToCol( 0.0 ) };
     865           0 :         pState->getFillColorSpace()->getRGB( pState->getFillColor(), &zeroColor );
     866           0 :         if( invert )
     867           0 :             writePng_( aBuf, str, width, height, oneColor, zeroColor, true, true );
     868             :         else
     869           0 :             writePng_( aBuf, str, width, height, zeroColor, oneColor, true, true );
     870             :     }
     871             :     else
     872           0 :         writeMaskLF(aBuf, str, width, height, invert != 0);
     873           0 :     writeBinaryBuffer(aBuf);
     874           0 : }
     875             : 
     876           3 : void PDFOutDev::drawImage(GfxState*, Object*, Stream* str,
     877             :                           int width, int height, GfxImageColorMap* colorMap,
     878             : #if POPPLER_CHECK_VERSION(0, 12, 0)
     879             :                           GBool /*interpolate*/,
     880             : #endif
     881             :                           int* maskColors, GBool /*inlineImg*/ )
     882             : {
     883           3 :     OutputBuffer aBuf; initBuf(aBuf);
     884           6 :     OutputBuffer aMaskBuf;
     885             : 
     886           3 :     printf( "drawImage %d %d", width, height );
     887             : 
     888           3 :     if( maskColors )
     889             :     {
     890             :         // write mask colors. nBytes must be even - first half is
     891             :         // lower bound values, second half upper bound values
     892           0 :         if( colorMap->getColorSpace()->getMode() == csIndexed )
     893             :         {
     894           0 :             aMaskBuf.push_back( (char)maskColors[0] );
     895           0 :             aMaskBuf.push_back( (char)maskColors[gfxColorMaxComps] );
     896             :         }
     897             :         else
     898             :         {
     899             :             GfxRGB aMinRGB;
     900           0 :             colorMap->getColorSpace()->getRGB(
     901             :                 (GfxColor*)maskColors,
     902           0 :                 &aMinRGB );
     903             : 
     904             :             GfxRGB aMaxRGB;
     905           0 :             colorMap->getColorSpace()->getRGB(
     906             :                 (GfxColor*)maskColors+gfxColorMaxComps,
     907           0 :                 &aMaxRGB );
     908             : 
     909           0 :             aMaskBuf.push_back( colToByte(aMinRGB.r) );
     910           0 :             aMaskBuf.push_back( colToByte(aMinRGB.g) );
     911           0 :             aMaskBuf.push_back( colToByte(aMinRGB.b) );
     912           0 :             aMaskBuf.push_back( colToByte(aMaxRGB.r) );
     913           0 :             aMaskBuf.push_back( colToByte(aMaxRGB.g) );
     914           0 :             aMaskBuf.push_back( colToByte(aMaxRGB.b) );
     915             :         }
     916             :     }
     917             : 
     918           3 :     printf( " %d", (int)aMaskBuf.size() );
     919           3 :     writeImageLF( aBuf, str, width, height, colorMap );
     920           3 :     writeBinaryBuffer(aBuf);
     921           6 :     writeBinaryBuffer(aMaskBuf);
     922           3 : }
     923             : 
     924           0 : void PDFOutDev::drawMaskedImage(GfxState*, Object*, Stream* str,
     925             :                                 int width, int height,
     926             :                                 GfxImageColorMap* colorMap,
     927             : #if POPPLER_CHECK_VERSION(0, 12, 0)
     928             :                                 GBool /*interpolate*/,
     929             : #endif
     930             :                                 Stream* maskStr,
     931             :                                 int maskWidth, int maskHeight,
     932             :                                 GBool maskInvert
     933             : #if POPPLER_CHECK_VERSION(0, 12, 0)
     934             :                                 , GBool /*maskInterpolate*/
     935             : #endif
     936             :                                )
     937             : {
     938           0 :     OutputBuffer aBuf;     initBuf(aBuf);
     939           0 :     printf( "drawImage %d %d 0", width, height );
     940           0 :     writePng_( aBuf, str, width, height, colorMap, maskStr, maskWidth, maskHeight, maskInvert, true );
     941           0 :     writeBinaryBuffer( aBuf );
     942           0 : }
     943             : 
     944           0 : void PDFOutDev::drawSoftMaskedImage(GfxState*, Object*, Stream* str,
     945             :                                     int width, int height,
     946             :                                     GfxImageColorMap* colorMap,
     947             : #if POPPLER_CHECK_VERSION(0, 12, 0)
     948             :                                     GBool /*interpolate*/,
     949             : #endif
     950             :                                     Stream* maskStr,
     951             :                                     int maskWidth, int maskHeight,
     952             :                                     GfxImageColorMap* maskColorMap
     953             : #if POPPLER_CHECK_VERSION(0, 12, 0)
     954             :                                     , GBool /*maskInterpolate*/
     955             : #endif
     956             :                                    )
     957             : {
     958           0 :     OutputBuffer aBuf;     initBuf(aBuf);
     959           0 :     printf( "drawImage %d %d 0", width, height );
     960           0 :     writePng_( aBuf, str, width, height, colorMap, maskStr, maskWidth, maskHeight, maskColorMap, true );
     961           0 :     writeBinaryBuffer( aBuf );
     962           0 : }
     963             : 
     964           3 : void PDFOutDev::setPageNum( int nNumPages )
     965             : {
     966             :     // TODO(F3): printf might format int locale-dependent!
     967           3 :     printf("setPageNum %d\n", nNumPages);
     968           3 : }
     969             : 
     970             : }
     971             : 
     972             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10