diff options
author | Philipp Lohmann <pl@openoffice.org> | 2002-07-15 11:04:39 +0000 |
---|---|---|
committer | Philipp Lohmann <pl@openoffice.org> | 2002-07-15 11:04:39 +0000 |
commit | 69e16c1ac6c3eef346e776de5225992a0a40adcb (patch) | |
tree | 0bfb57002aa19d1a6cf06c3b7d8b71f5fd834bd4 /vcl/source/gdi | |
parent | c773fdcf2262b6af5980a8000c9ad8ded01c8820 (diff) |
#100608# helper for pdf export
Diffstat (limited to 'vcl/source/gdi')
-rw-r--r-- | vcl/source/gdi/outdev.cxx | 11 | ||||
-rw-r--r-- | vcl/source/gdi/outdev3.cxx | 28 | ||||
-rw-r--r-- | vcl/source/gdi/pdfwriter_impl.cxx | 278 | ||||
-rw-r--r-- | vcl/source/gdi/pdfwriter_impl.hxx | 83 | ||||
-rw-r--r-- | vcl/source/gdi/print.cxx | 10 |
5 files changed, 237 insertions, 173 deletions
diff --git a/vcl/source/gdi/outdev.cxx b/vcl/source/gdi/outdev.cxx index 6c71d2b1852f..8ffbc191bbf9 100644 --- a/vcl/source/gdi/outdev.cxx +++ b/vcl/source/gdi/outdev.cxx @@ -2,9 +2,9 @@ * * $RCSfile: outdev.cxx,v $ * - * $Revision: 1.9 $ + * $Revision: 1.10 $ * - * last change: $Author: cp $ $Date: 2002-07-11 11:42:38 $ + * last change: $Author: pl $ $Date: 2002-07-15 12:01:01 $ * * The Contents of this file are made available subject to the terms of * either of the following licenses @@ -415,6 +415,7 @@ OutputDevice::OutputDevice() : mpObjStack = NULL; mpOutDevData = NULL; mp3DContext = NULL; + mpPDFWriter = NULL; mnOutOffX = 0; mnOutOffY = 0; mnOutWidth = 0; @@ -508,6 +509,12 @@ OutputDevice::~OutputDevice() delete mpGetDevFontList; if ( mpGetDevSizeList ) delete mpGetDevSizeList; + + if( mpFontList && mpFontList != ImplGetSVData()->maGDIData.mpScreenFontList ) + { + mpFontList->Clear(); + delete mpFontList; + } } // ----------------------------------------------------------------------- diff --git a/vcl/source/gdi/outdev3.cxx b/vcl/source/gdi/outdev3.cxx index 771c75ee8ccd..3723a8e74a0a 100644 --- a/vcl/source/gdi/outdev3.cxx +++ b/vcl/source/gdi/outdev3.cxx @@ -2,9 +2,9 @@ * * $RCSfile: outdev3.cxx,v $ * - * $Revision: 1.100 $ + * $Revision: 1.101 $ * - * last change: $Author: ssa $ $Date: 2002-07-01 08:21:16 $ + * last change: $Author: pl $ $Date: 2002-07-15 12:01:02 $ * * The Contents of this file are made available subject to the terms of * either of the following licenses @@ -156,6 +156,9 @@ #endif #include <unohelp.hxx> +#ifndef _VCL_PDFWRITER_IMPL_HXX +#include <pdfwriter_impl.hxx> +#endif #ifndef _COM_SUN_STAR_BEANS_PROPERTYVALUES_HDL_ #include <com/sun/star/beans/PropertyValues.hdl> @@ -280,9 +283,12 @@ void OutputDevice::ImplUpdateFontData( BOOL bNewFontLists ) } } - if ( GetOutDevType() == OUTDEV_PRINTER ) + if ( GetOutDevType() == OUTDEV_PRINTER || mpPDFWriter ) { - mpFontCache->Clear(); + ImplSVData* pSVData = ImplGetSVData(); + + if( mpFontCache && mpFontCache != pSVData->maGDIData.mpScreenFontCache ) + mpFontCache->Clear(); if ( bNewFontLists ) { @@ -293,8 +299,17 @@ void OutputDevice::ImplUpdateFontData( BOOL bNewFontLists ) if ( ImplGetServerGraphics() ) #endif { - mpFontList->Clear(); - mpGraphics->GetDevFontList( mpFontList ); + if( mpFontList && mpFontList != pSVData->maGDIData.mpScreenFontList ) + mpFontList->Clear(); + + if( mpPDFWriter ) + { + if( mpFontList ) + delete mpFontList; + mpFontList = mpPDFWriter->filterDevFontList( pSVData->maGDIData.mpScreenFontList ); + } + else + mpGraphics->GetDevFontList( mpFontList ); } } } @@ -2405,7 +2420,6 @@ ImplFontEntry* ImplFontCache::Get( ImplDevFontList* pFontList, // initialize font selection data ImplFontSelectData* pFontSelData = &(pEntry->maFontSelData); pFontSelData->mpFontData = pFontData; - pFontSelData->mpSysSelData = NULL; pFontSelData->maName = rName; pFontSelData->maStyleName = rStyleName; pFontSelData->mnWidth = nWidth; diff --git a/vcl/source/gdi/pdfwriter_impl.cxx b/vcl/source/gdi/pdfwriter_impl.cxx index db1740a48236..42643a7885d2 100644 --- a/vcl/source/gdi/pdfwriter_impl.cxx +++ b/vcl/source/gdi/pdfwriter_impl.cxx @@ -2,9 +2,9 @@ * * $RCSfile: pdfwriter_impl.cxx,v $ * - * $Revision: 1.2 $ + * $Revision: 1.3 $ * - * last change: $Author: kz $ $Date: 2002-07-10 14:21:56 $ + * last change: $Author: pl $ $Date: 2002-07-15 12:02:20 $ * * The Contents of this file are made available subject to the terms of * either of the following licenses @@ -66,6 +66,8 @@ #include <bmpacc.hxx> #include <bitmapex.hxx> #include <image.hxx> +#include <outdev.h> +#include <sallayout.hxx> #include "implncvt.hxx" @@ -474,10 +476,35 @@ OutputDevice* PDFWriterImpl::getReferenceDevice() VirtualDevice* pVDev = new VirtualDevice( 0 ); m_pReferenceDevice = pVDev; pVDev->SetOutputSizePixel( Size( 640, 480 ) ); + m_pReferenceDevice->mpPDFWriter = this; } return m_pReferenceDevice; } +ImplDevFontList* PDFWriterImpl::filterDevFontList( ImplDevFontList* pFontList ) +{ + DBG_ASSERT( m_aPages.begin() == m_aPages.end(), "Fonts changing during PDF generation, document will be invalid" ); + + ImplDevFontList* pFiltered = new ImplDevFontList(); + + ImplDevFontListData* pData = pFontList->First(); + while( pData ) + { + ImplFontData* pEntry = pData->mpFirst; + while( pEntry ) + { + if( pEntry->mbSubsettable || pEntry->mbEmbeddable ) + { + ImplFontData* pNewData = new ImplFontData(); + *pNewData = *pEntry; + pFiltered->Add( pNewData ); + } + pData = pFontList->Next(); + } + } + return pFiltered; +} + sal_Int32 PDFWriterImpl::newPage( sal_Int32 nPageWidth, sal_Int32 nPageHeight, PDFWriter::Orientation eOrientation ) { endPage(); @@ -779,93 +806,10 @@ bool PDFWriterImpl::emitHatches() return true; } -sal_Int32 PDFWriterImpl::emitFont( const Font& rFont ) +sal_Int32 PDFWriterImpl::emitFonts() { - sal_Int32 nFont = 0; - // catch the 14 special fonts - if( rFont.GetName().EqualsIgnoreCaseAscii( "Times" ) - || rFont.GetName().EqualsIgnoreCaseAscii( "Helvetica" ) - || rFont.GetName().EqualsIgnoreCaseAscii( "Courier" ) - || rFont.GetName().EqualsIgnoreCaseAscii( "Symbol" ) - || rFont.GetName().EqualsIgnoreCaseAscii( "ZapfDingbats" ) - ) - { - // emit a simple font - nFont = createObject(); - if( updateObject( nFont ) ) - { - OStringBuffer aLine( 256 ); - aLine.append( nFont ); - aLine.append( " 0 obj\r\n << /Type /Font\r\n /Subtype /Type1\r\n /BaseFont " ); - if( rFont.GetName().EqualsIgnoreCaseAscii( "Times" ) ) - { - if( rFont.GetItalic() == ITALIC_NONE || rFont.GetItalic() == ITALIC_DONTKNOW ) - { - if( rFont.GetWeight() == WEIGHT_DONTKNOW || rFont.GetWeight() < WEIGHT_SEMIBOLD ) - aLine.append( "/Times-Roman" ); - else - aLine.append( "/Times-Bold" ); - } - else - { - if( rFont.GetWeight() == WEIGHT_DONTKNOW || rFont.GetWeight() < WEIGHT_SEMIBOLD ) - aLine.append( "/Times-Italic" ); - else - aLine.append( "/Times-BoldItalic" ); - } - } - else if( rFont.GetName().EqualsIgnoreCaseAscii( "Helvetica" ) ) - { - if( rFont.GetItalic() == ITALIC_NONE || rFont.GetItalic() == ITALIC_DONTKNOW ) - { - if( rFont.GetWeight() == WEIGHT_DONTKNOW || rFont.GetWeight() < WEIGHT_SEMIBOLD ) - aLine.append( "/Helvetica" ); - else - aLine.append( "/Helvetica-Bold" ); - } - else - { - if( rFont.GetWeight() == WEIGHT_DONTKNOW || rFont.GetWeight() < WEIGHT_SEMIBOLD ) - aLine.append( "/Helvetica-Oblique" ); - else - aLine.append( "/Helvetica-BoldOblique" ); - } - } - else if( rFont.GetName().EqualsIgnoreCaseAscii( "Courier" ) ) - { - if( rFont.GetItalic() == ITALIC_NONE || rFont.GetItalic() == ITALIC_DONTKNOW ) - { - if( rFont.GetWeight() == WEIGHT_DONTKNOW || rFont.GetWeight() < WEIGHT_SEMIBOLD ) - aLine.append( "/Courier" ); - else - aLine.append( "/Courier" ); - } - else - { - if( rFont.GetWeight() == WEIGHT_DONTKNOW || rFont.GetWeight() < WEIGHT_SEMIBOLD ) - aLine.append( "/Courier-Oblique" ); - else - aLine.append( "/Courier-BoldOblique" ); - } - } - else if( rFont.GetName().EqualsIgnoreCaseAscii( "ZapfDingbats" ) ) - aLine.append( "/ZapfDingbats" ); - else - aLine.append( "/Symbol" ); - aLine.append( "\r\n >>\r\nendobj\r\n\r\n" ); - CHECK_RETURN( writeBuffer( aLine.getStr(), aLine.getLength() ) ); - } - } - // much TODO here - // preliminary: map everything else to Helvetica - else - { - Font aFont( rFont ); - aFont.SetName( String( RTL_CONSTASCII_USTRINGPARAM( "Helvetica" ) ) ); - nFont = emitFont( aFont ); - } - - return nFont; + // TODO + return 0; } sal_Int32 PDFWriterImpl::emitResources() @@ -929,27 +873,8 @@ sal_Int32 PDFWriterImpl::emitResources() } // emit font dict - sal_Int32 nFontDict = createObject(); - aLine.setLength( 0 ); - aLine.append( nFontDict ); - aLine.append( " 0 obj\r\n << " ); - for( std::map< Font, sal_Int32 >::const_iterator it = m_aFonts.begin(); - it != m_aFonts.end(); ++it ) - { - sal_Int32 nFont = emitFont( it->first ); - DBG_ASSERT( nFont, "could not emit font" ); - if( nFont ) - { - aLine.append( "/F" ); - aLine.append( it->second ); - aLine.append( ' ' ); - aLine.append( nFont ); - aLine.append( " 0 R\r\n " ); - } - } - aLine.append( ">>\r\nendobj\r\n\r\n" ); - CHECK_RETURN( updateObject( nFontDict ) ); - CHECK_RETURN( writeBuffer( aLine.getStr(), aLine.getLength() ) ); + sal_Int32 nFontDict = 0; + CHECK_RETURN( (nFontDict = emitFonts()) ); // emit xobject dict sal_Int32 nXObjectDict = 0; @@ -1137,35 +1062,125 @@ bool PDFWriterImpl::emit() return true; } -void PDFWriterImpl::drawText( const Point& rPos, const String& rText ) +void PDFWriterImpl::registerGlyphs( int nGlyphs, long* pGlyphs, sal_Unicode* pUnicodes, sal_uInt8* pMappedGlyphs, sal_Int32* pMappedFontObjects ) { - MARK( "drawText" ); + ImplFontData* pCurrentFont = m_pReferenceDevice->mpFontEntry->maFontSelData.mpFontData; + if( pCurrentFont->mbSubsettable ) + { + FontSubset& rSubset = m_aSubsets[ pCurrentFont ]; + for( int i = 0; i < nGlyphs; i++ ) + { + // search for glyphID + FontMapping::iterator it = rSubset.m_aMapping.find( pGlyphs[i] ); + if( it != rSubset.m_aMapping.end() ) + { + pMappedFontObjects[i] = it->second.m_nFontID; + pMappedGlyphs[i] = it->second.m_nSubsetGlyphID; + } + else + { + // create new subset if necessary + if( rSubset.m_aSubsets.begin() == rSubset.m_aSubsets.end() || + rSubset.m_aSubsets.back().m_aMapping.size() > 253 ) + { + rSubset.m_aSubsets.push_back( FontEmit( m_nNextFID++ ) ); + } - // just for testing purposes - ByteString aText( rText, RTL_TEXTENCODING_MS_1252 ); + // copy font id + pMappedFontObjects[i] = rSubset.m_aSubsets.back().m_nFontID; + // create new glyph in subset + sal_uInt8 nNewId = rSubset.m_aSubsets.back().m_aMapping.size()+1; + pMappedGlyphs[i] = nNewId; + + // add new glyph to emitted font subset + GlyphEmit& rNewGlyphEmit = rSubset.m_aSubsets.back().m_aMapping[ pGlyphs[i] ]; + rNewGlyphEmit.m_nSubsetGlyphID = nNewId; + rNewGlyphEmit.m_aUnicode = (pUnicodes ? pUnicodes[i] : 0); + + // add new glyph to font mapping + Glyph& rNewGlyph = rSubset.m_aMapping[ pGlyphs[i] ]; + rNewGlyph.m_nFontID = pMappedFontObjects[i]; + rNewGlyph.m_nSubsetGlyphID = nNewId; + } + } + } + else + { + // TODO: downloadable font + } +} - updateGraphicsState(); +void PDFWriterImpl::drawLayout( const SalLayout& rSalLayout ) +{ + // TODO: the needed methods must be moved to the base class + // then rename the input paramter and scratch the next line + const GenericSalLayout& rLayout = reinterpret_cast<const GenericSalLayout&>(rSalLayout); - DBG_ASSERT( m_aCurrentPDFState.m_aFont.GetName().Len(), "invalid font set" ); + OStringBuffer aLine( 512 ); + // begin text object + aLine.append( "BT\r\n" ); + + const int nMaxGlyphs = 100; + + long pGlyphs[nMaxGlyphs]; + sal_Int32 pXOffsets[nMaxGlyphs]; + sal_uInt8 pMappedGlyphs[nMaxGlyphs]; + sal_Int32 pMappedFontObjects[nMaxGlyphs]; + int nGlyphs; + int nIndex = 0; + Point aPos; + while( nGlyphs = rLayout.GetNextGlyphs( nMaxGlyphs, pGlyphs, aPos, nIndex, pXOffsets ) ) + { + registerGlyphs( nGlyphs, pGlyphs, NULL, pMappedGlyphs, pMappedFontObjects ); + int nLast = 0; + while( nLast < nGlyphs ) + { + int nNext = nLast+1; + while( nNext < nGlyphs && pMappedFontObjects[ nNext ] == pMappedFontObjects[nLast] ) + nNext++; + aLine.append( "/F" ); + aLine.append( pMappedFontObjects[nLast] ); + aLine.append( ' ' ); + m_aPages.back().appendMappedLength( m_aCurrentPDFState.m_aFont.GetHeight(), aLine, true ); + aLine.append( " Tf [ <" ); + for( int i = nLast; i < nNext; i++ ) + { + appendHex( (sal_Int8)pMappedGlyphs[i], aLine ); + if( (i % 70) == 0 ) + aLine.append( "\r\n" ); + } + aLine.append( "> ] Tj\r\n" ); - OStringBuffer aLine; - aLine.append( "BT\r\n /F" ); - aLine.append( m_aFonts[ m_aCurrentPDFState.m_aFont ] ); - aLine.append( ' ' ); - m_aPages.back().appendMappedLength( m_aCurrentPDFState.m_aFont.GetHeight(), aLine, true ); - aLine.append( " Tf\r\n " ); - m_aPages.back().appendPoint( rPos, aLine ); - aLine.append( " Td\r\n <" ); - for( int i = 0; i < aText.Len(); i++ ) - { - sal_Int8 aChar = aText.GetChar( i ); - appendHex( aChar, aLine ); + nLast = nNext; + } } - aLine.append( "> Tj\r\nET\r\n" ); + + // end textobject + aLine.append( "ET\r\n" ); writeBuffer( aLine.getStr(), aLine.getLength() ); } +void PDFWriterImpl::drawText( const Point& rPos, const String& rText ) +{ + MARK( "drawText" ); + + updateGraphicsState(); + + // get a sal layout + getReferenceDevice(); + // set font on reference device + m_pReferenceDevice->SetFont( m_aCurrentPDFState.m_aFont ); + m_pReferenceDevice->SetLayoutMode( m_aCurrentPDFState.m_nLayoutMode ); + // get the layout from the OuputDevice's SalGraphics + // this also enforces font substitution and sets the font on SalGraphics + SalLayout* pLayout = m_pReferenceDevice->ImplLayout( rText, 0, rText.Len(), rPos ); + pLayout->Reference(); + + drawLayout( *pLayout ); + pLayout->Release(); +} + void PDFWriterImpl::drawLine( const Point& rStart, const Point& rStop ) { MARK( "drawLine" ); @@ -2303,13 +2318,6 @@ void PDFWriterImpl::updateGraphicsState() aLine.append( "\r\n" ); } - if( m_aCurrentPDFState.m_aFont != rNewState.m_aFont && rNewState.m_aFont.GetName().Len() - ) - { - if( m_aFonts.find( rNewState.m_aFont ) == m_aFonts.end() ) - m_aFonts[ rNewState.m_aFont ] = m_nNextFID++; - } - if( m_eVersion >= PDFWriter::PDF_1_4 && m_aCurrentPDFState.m_nTransparentPercent != rNewState.m_nTransparentPercent ) { // TODO: switch extended graphicsstate diff --git a/vcl/source/gdi/pdfwriter_impl.hxx b/vcl/source/gdi/pdfwriter_impl.hxx index 53826811b31e..9f108ddd8294 100644 --- a/vcl/source/gdi/pdfwriter_impl.hxx +++ b/vcl/source/gdi/pdfwriter_impl.hxx @@ -2,9 +2,9 @@ * * $RCSfile: pdfwriter_impl.hxx,v $ * - * $Revision: 1.1 $ + * $Revision: 1.2 $ * - * last change: $Author: pl $ $Date: 2002-07-08 14:18:57 $ + * last change: $Author: pl $ $Date: 2002-07-15 12:02:21 $ * * The Contents of this file are made available subject to the terms of * either of the following licenses @@ -98,13 +98,17 @@ #include <list> namespace rtl { class OStringBuffer; } +class SalLayout; +struct ImplFontData; namespace vcl { class PDFWriterImpl { -private: +public: + // definition of structs + struct PDFPage { PDFWriterImpl* m_pWriter; @@ -171,6 +175,36 @@ private: Rectangle m_aRectangle; }; + // font subsets + struct GlyphEmit + { + sal_uInt8 m_nSubsetGlyphID; + sal_Unicode m_aUnicode; + }; + typedef std::map< long, GlyphEmit > FontEmitMapping; + struct FontEmit + { + sal_Int32 m_nFontID; + FontEmitMapping m_aMapping; + + FontEmit( sal_Int32 nID ) : m_nFontID( nID ) {} + }; + typedef std::list< FontEmit > FontEmitList; + struct Glyph + { + sal_Int32 m_nFontID; + sal_uInt8 m_nSubsetGlyphID; + }; + typedef std::map< long, Glyph > FontMapping; + + struct FontSubset + { + FontEmitList m_aSubsets; + FontMapping m_aMapping; + }; + typedef std::map< ImplFontData*, FontSubset > FontSubsetData; + +private: OutputDevice* m_pReferenceDevice; MapMode m_aMapMode; // PDFWriterImpl scaled units @@ -188,6 +222,9 @@ private: std::list< HatchEmit > m_aHatches; /* contains bitmap tiling patterns */ std::list< BitmapPatternEmit > m_aTilings; + /* contains all font subsets in use */ + FontSubsetData m_aSubsets; + sal_Int32 m_nNextFID; sal_Int32 m_nInheritedPageWidth; // in inch/72 sal_Int32 m_nInheritedPageHeight; // in inch/72 @@ -201,26 +238,6 @@ private: oslFileHandle m_aFile; bool m_bOpen; - struct ltfont - { - bool operator()(const Font& rLeft, const Font& rRight) - { - StringCompare eComp = rLeft.GetName().CompareTo( rRight.GetName() ); - if( eComp != COMPARE_EQUAL ) - return eComp == COMPARE_LESS; - if( rLeft.GetItalic() != rRight.GetItalic() ) - return rLeft.GetItalic() < rRight.GetItalic(); - if( rLeft.GetWeight() != rRight.GetWeight() ) - return rLeft.GetWeight() < rRight.GetWeight(); - return rLeft.GetWidth() < rRight.GetWidth(); - } - }; - - // fonts used in whole file, maps to font id - std::map< Font, sal_Int32, ltfont > m_aFonts; - sal_Int32 m_nNextFID; - - // graphics state struct GraphicsState { @@ -239,6 +256,7 @@ private: m_aLineColor( COL_TRANSPARENT ), m_aFillColor( COL_TRANSPARENT ), m_aTextLineColor( COL_BLACK ), + m_nLayoutMode( 0 ), m_nTransparentPercent( 0 ) {} GraphicsState( const GraphicsState& rState ) : m_aFont( rState.m_aFont ), @@ -272,6 +290,12 @@ private: std::list< GraphicsState > m_aGraphicsStack; GraphicsState m_aCurrentPDFState; + /* creates fonts and subsets that will be emitted later */ + void registerGlyphs( int nGlyphs, long* pGlyphs, sal_Unicode* pUnicodes, sal_uInt8* pMappedGlyphs, sal_Int32* pMappedFontObjects ); + + /* emits a text object according to the passed layout */ + void drawLayout( const SalLayout& rLayout ); + /* writes differences between graphics stack and current real PDF * state to the file */ @@ -296,10 +320,10 @@ private: bool emitGradients(); /* writes all hatch patterns */ bool emitHatches(); - /* writes a font dictionary; - * returns object id (or 0 on error) + /* writes a the font dictionary and emits all font objects + * returns object id of font directory (or 0 on error) */ - sal_Int32 emitFont( const Font& rFont ); + sal_Int32 emitFonts(); /* writes the Resource dictionary; * returns dict object id (or 0 on error) */ @@ -323,6 +347,13 @@ public: PDFWriterImpl( const rtl::OUString& rTargetFile, PDFWriter::PDFVersion eVersion = PDFWriter::PDF_1_4 ); ~PDFWriterImpl(); + /* for OutputDevice so the reference device can have a list + * that contains only suitable fonts (subsettable or builtin) + * produces a new font list + */ + ImplDevFontList* filterDevFontList( ImplDevFontList* pFontList ); + + /* for documentation of public fucntions please see pdfwriter.hxx */ OutputDevice* getReferenceDevice(); diff --git a/vcl/source/gdi/print.cxx b/vcl/source/gdi/print.cxx index 0d36c0f74f8f..e7d7badbacf8 100644 --- a/vcl/source/gdi/print.cxx +++ b/vcl/source/gdi/print.cxx @@ -2,9 +2,9 @@ * * $RCSfile: print.cxx,v $ * - * $Revision: 1.35 $ + * $Revision: 1.36 $ * - * last change: $Author: pl $ $Date: 2002-07-04 16:31:03 $ + * last change: $Author: pl $ $Date: 2002-07-15 12:02:22 $ * * The Contents of this file are made available subject to the terms of * either of the following licenses @@ -912,8 +912,8 @@ Printer::~Printer() delete mpGetDevSizeList; mpGetDevSizeList = NULL; } - delete mpFontList; delete mpFontCache; + // font list deleted by OutputDevice dtor } // Printer aus der Liste eintragen @@ -1145,7 +1145,11 @@ BOOL Printer::SetPrinterProps( const Printer* pPrinter ) delete mpGetDevSizeList; mpGetDevSizeList = NULL; } + // clean up font list + mpFontList->Clear(); delete mpFontList; + mpFontList = NULL; + delete mpFontCache; mbInitFont = TRUE; mbNewFont = TRUE; |