[Libreoffice-commits] core.git: vcl/source
Khaled Hosny
khaledhosny at eglug.org
Tue Nov 29 22:51:33 UTC 2016
vcl/source/gdi/pdfwriter_impl.cxx | 560 --------------------------------------
vcl/source/gdi/pdfwriter_impl.hxx | 3
2 files changed, 563 deletions(-)
New commits:
commit 70ecf1919e3e3b9509ff55b2265b3d98d2a5f1aa
Author: Khaled Hosny <khaledhosny at eglug.org>
Date: Tue Nov 29 11:51:23 2016 +0200
Dead code
m_aEmbeddedFonts is always empty now.
Change-Id: Ia0cdfbabff29722d51b92ed47e04ef40d71f65be
Reviewed-on: https://gerrit.libreoffice.org/31373
Reviewed-by: Khaled Hosny <khaledhosny at eglug.org>
Tested-by: Khaled Hosny <khaledhosny at eglug.org>
diff --git a/vcl/source/gdi/pdfwriter_impl.cxx b/vcl/source/gdi/pdfwriter_impl.cxx
index 12fe24d..30daf70 100644
--- a/vcl/source/gdi/pdfwriter_impl.cxx
+++ b/vcl/source/gdi/pdfwriter_impl.cxx
@@ -3046,555 +3046,6 @@ static bool getPfbSegmentLengths( const unsigned char* pFontBytes, int nByteLen,
return true;
}
-struct FontException : public std::exception
-{
-};
-
-// TODO: always subset instead of embedding the full font => this method becomes obsolete then
-std::map< sal_Int32, sal_Int32 > PDFWriterImpl::emitEmbeddedFont( const PhysicalFontFace* pFont, EmbedFont& rEmbed )
-{
- std::map< sal_Int32, sal_Int32 > aRet;
-
- sal_Int32 nStreamObject = 0;
- sal_Int32 nFontDescriptor = 0;
-
- SalGraphics *pGraphics = m_pReferenceDevice->GetGraphics();
-
- assert(pGraphics);
-
- // prepare font encoding
- sal_Int32 nToUnicodeStream = 0;
- sal_uInt8 nEncoding[256];
- sal_Ucs nEncodedCodes[256];
- std::vector<sal_Ucs> aUnicodes;
- aUnicodes.reserve( 256 );
- sal_Int32 pUnicodesPerGlyph[256];
- sal_Int32 pEncToUnicodeIndex[256];
-
- FontSubsetInfo aInfo;
- sal_Int32 pWidths[256];
- const unsigned char* pFontData = nullptr;
- long nFontLen = 0;
- sal_Int32 nLength1, nLength2;
- try
- {
- if( (pFontData = static_cast<const unsigned char*>(pGraphics->GetEmbedFontData(pFont, nEncodedCodes, pWidths, 256, aInfo, &nFontLen))) != nullptr )
- {
- if( (aInfo.m_nFontType & FontSubsetInfo::ANY_TYPE1) == 0 )
- throw FontException();
- // see whether it is pfb or pfa; if it is a pfb, fill ranges
- // of 6 bytes that are not part of the font program
- std::list< int > aSections;
- std::list< int >::const_iterator it;
- int nIndex = 0;
- while( (nIndex < nFontLen-1) && pFontData[nIndex] == 0x80 )
- {
- aSections.push_back( nIndex );
- if( pFontData[nIndex+1] == 0x03 )
- break;
- sal_Int32 nBytes =
- ((sal_Int32)pFontData[nIndex+2]) |
- ((sal_Int32)pFontData[nIndex+3]) << 8 |
- ((sal_Int32)pFontData[nIndex+4]) << 16 |
- ((sal_Int32)pFontData[nIndex+5]) << 24;
- nIndex += nBytes+6;
- }
-
- // search for eexec
- // TODO: use getPfbSegmentLengths() if possible to skip the search thingies below
- nIndex = 0;
- int nEndAsciiIndex;
- int nBeginBinaryIndex;
- int nEndBinaryIndex;
- do
- {
- while( nIndex < nFontLen-4 &&
- ( pFontData[nIndex] != 'e' ||
- pFontData[nIndex+1] != 'e' ||
- pFontData[nIndex+2] != 'x' ||
- pFontData[nIndex+3] != 'e' ||
- pFontData[nIndex+4] != 'c'
- )
- )
- {
- ++nIndex;
- }
- // check whether we are in a excluded section
- for( it = aSections.begin(); it != aSections.end() && (nIndex < *it || nIndex > ((*it) + 5) ); ++it )
- ;
- } while( it != aSections.end() && nIndex < nFontLen-4 );
- // this should end the ascii part
- if( nIndex > nFontLen-5 )
- throw FontException();
-
- nEndAsciiIndex = nIndex+4;
- // now count backwards until we can account for 512 '0'
- // which is the endmarker of the (hopefully) binary data
- // do not count the pfb header sections
- int nFound = 0;
- nIndex = nFontLen-1;
- while( nIndex > 0 && nFound < 512 )
- {
- for( it = aSections.begin(); it != aSections.end() && (nIndex < *it || nIndex > ((*it) + 5) ); ++it )
- ;
- if( it == aSections.end() )
- {
- // inside the 512 '0' block there may only be whitespace
- // according to T1 spec; probably it would be to simple
- // if all fonts complied
- if( pFontData[nIndex] == '0' )
- nFound++;
- else if( nFound > 0 &&
- pFontData[nIndex] != '\r' &&
- pFontData[nIndex] != '\t' &&
- pFontData[nIndex] != '\n' &&
- pFontData[nIndex] != ' ' )
- break;
- }
- nIndex--;
- }
-
- if( nIndex < 1 || nIndex <= nEndAsciiIndex )
- throw FontException();
-
- // nLength3 is the rest of the file - excluding any section headers
- // nIndex now points before the first of the 512 '0' characters marking the
- // fixed content portion
- sal_Int32 nLength3 = nFontLen - nIndex - 1;
- for( it = aSections.begin(); it != aSections.end(); ++it )
- {
- // special case: nIndex inside a section marker
- if( nIndex >= (*it) && (*it)+6 > nIndex )
- nLength3 -= (*it)+6 - nIndex;
- else if( *it >= nIndex )
- {
- if( *it < nFontLen - 6 )
- nLength3 -= 6;
- else // the last section 0x8003 is only 2 bytes after all
- nLength3 -= (nFontLen - *it);
- }
- }
-
- // there may be whitespace to ignore before the 512 '0'
- while( pFontData[nIndex] == '\r' || pFontData[nIndex] == '\n' )
- {
- nIndex--;
- for( it = aSections.begin(); it != aSections.end() && (nIndex < *it || nIndex > ((*it) + 5) ); ++it )
- ;
- if( it != aSections.end() )
- {
- nIndex = (*it)-1;
- break; // this is surely a binary boundary, in ascii case it wouldn't matter
- }
- }
- nEndBinaryIndex = nIndex;
-
- // search for beginning of binary section
- nBeginBinaryIndex = nEndAsciiIndex;
- do
- {
- nBeginBinaryIndex++;
- for( it = aSections.begin(); it != aSections.end() && (nBeginBinaryIndex < *it || nBeginBinaryIndex > ((*it) + 5) ); ++it )
- ;
- } while( nBeginBinaryIndex < nEndBinaryIndex &&
- ( pFontData[nBeginBinaryIndex] == '\r' ||
- pFontData[nBeginBinaryIndex] == '\n' ||
- it != aSections.end() ) );
-
- // it seems to be vital to copy the exact whitespace between binary data
- // and eexec, else a invalid font results. so make nEndAsciiIndex
- // always immediate in front of nBeginBinaryIndex
- nEndAsciiIndex = nBeginBinaryIndex-1;
- for( it = aSections.begin(); it != aSections.end() && (nEndAsciiIndex < *it || nEndAsciiIndex > ((*it)+5)); ++it )
- ;
- if( it != aSections.end() )
- nEndAsciiIndex = (*it)-1;
-
- nLength1 = nEndAsciiIndex+1; // including the last character
- for( it = aSections.begin(); it != aSections.end() && *it < nEndAsciiIndex; ++it )
- nLength1 -= 6; // decrease by pfb section size
-
- // if the first four bytes are all ascii hex characters, then binary data
- // has to be converted to real binary data
- for( nIndex = 0; nIndex < 4 &&
- ( ( pFontData[ nBeginBinaryIndex+nIndex ] >= '0' && pFontData[ nBeginBinaryIndex+nIndex ] <= '9' ) ||
- ( pFontData[ nBeginBinaryIndex+nIndex ] >= 'a' && pFontData[ nBeginBinaryIndex+nIndex ] <= 'f' ) ||
- ( pFontData[ nBeginBinaryIndex+nIndex ] >= 'A' && pFontData[ nBeginBinaryIndex+nIndex ] <= 'F' )
- ); ++nIndex )
- ;
- bool bConvertHexData = true;
- if( nIndex < 4 )
- {
- bConvertHexData = false;
- nLength2 = nEndBinaryIndex - nBeginBinaryIndex + 1; // include the last byte
- for( it = aSections.begin(); it != aSections.end(); ++it )
- if( *it > nBeginBinaryIndex && *it < nEndBinaryIndex )
- nLength2 -= 6;
- }
- else
- {
- // count the hex ascii characters to get nLength2
- nLength2 = 0;
- int nNextSectionIndex = 0;
- for( it = aSections.begin(); it != aSections.end() && *it < nBeginBinaryIndex; ++it )
- ;
- if( it != aSections.end() )
- nNextSectionIndex = *it;
- for( nIndex = nBeginBinaryIndex; nIndex <= nEndBinaryIndex; nIndex++ )
- {
- if( nIndex == nNextSectionIndex )
- {
- nIndex += 6;
- ++it;
- nNextSectionIndex = (it == aSections.end() ? 0 : *it );
- }
- if( ( pFontData[ nIndex ] >= '0' && pFontData[ nIndex ] <= '9' ) ||
- ( pFontData[ nIndex ] >= 'a' && pFontData[ nIndex ] <= 'f' ) ||
- ( pFontData[ nIndex ] >= 'A' && pFontData[ nIndex ] <= 'F' ) )
- nLength2++;
- }
- SAL_WARN_IF( (nLength2 & 1), "vcl", "uneven number of hex chars in binary pfa section" );
- nLength2 /= 2;
- }
-
- // now we can actually write the font stream !
- #if OSL_DEBUG_LEVEL > 1
- emitComment( " PDFWriterImpl::emitEmbeddedFont" );
- #endif
- OStringBuffer aLine( 512 );
- nStreamObject = createObject();
- if( !updateObject(nStreamObject))
- throw FontException();
- sal_Int32 nStreamLengthObject = createObject();
- aLine.append( nStreamObject );
- aLine.append( " 0 obj\n"
- "<</Length " );
- aLine.append( nStreamLengthObject );
- if (!g_bDebugDisableCompression)
- aLine.append( " 0 R"
- "/Filter/FlateDecode"
- "/Length1 " );
- else
- aLine.append( " 0 R"
- "/Length1 " );
- aLine.append( nLength1 );
- aLine.append( " /Length2 " );
- aLine.append( nLength2 );
- aLine.append( " /Length3 ");
- aLine.append( nLength3 );
- aLine.append( ">>\n"
- "stream\n" );
- if( !writeBuffer( aLine.getStr(), aLine.getLength() ) )
- throw FontException();
-
- sal_uInt64 nBeginStreamPos = 0;
- m_aFile.getPos(nBeginStreamPos);
-
- beginCompression();
- checkAndEnableStreamEncryption( nStreamObject );
-
- // write ascii section
- if( aSections.begin() == aSections.end() )
- {
- if( ! writeBuffer( pFontData, nEndAsciiIndex+1 ) )
- throw FontException();
- }
- else
- {
- // first section always starts at 0
- it = aSections.begin();
- nIndex = (*it)+6;
- ++it;
- while( *it < nEndAsciiIndex )
- {
- if( ! writeBuffer( pFontData+nIndex, (*it)-nIndex ) )
- throw FontException();
- nIndex = (*it)+6;
- ++it;
- }
- // write partial last section
- if( ! writeBuffer( pFontData+nIndex, nEndAsciiIndex-nIndex+1 ) )
- throw FontException();
- }
-
- // write binary section
- if( ! bConvertHexData )
- {
- if( aSections.begin() == aSections.end() )
- {
- if( ! writeBuffer( pFontData+nBeginBinaryIndex, nFontLen-nBeginBinaryIndex ) )
- throw FontException();
- }
- else
- {
- for( it = aSections.begin(); *it < nBeginBinaryIndex; ++it )
- ;
- // write first partial section
- if( ! writeBuffer( pFontData+nBeginBinaryIndex, (*it) - nBeginBinaryIndex ) )
- throw FontException();
- // write following sections
- while( it != aSections.end() )
- {
- nIndex = (*it)+6;
- ++it;
- if( nIndex < nFontLen ) // last section marker is usually the EOF which has only 2 bytes
- {
- sal_Int32 nSectionLen = (it == aSections.end()) ? nFontLen - nIndex : (*it) - nIndex;
- if( ! writeBuffer( pFontData+nIndex, nSectionLen ) )
- throw FontException();
- }
- }
- }
- }
- else
- {
- std::unique_ptr<unsigned char[]> xWriteBuffer(new unsigned char[nLength2]);
- memset(xWriteBuffer.get(), 0, nLength2);
- int nWriteIndex = 0;
-
- int nNextSectionIndex = 0;
- for( it = aSections.begin(); it != aSections.end() && *it < nBeginBinaryIndex; ++it )
- ;
- if( it != aSections.end() )
- nNextSectionIndex = *it;
- for( nIndex = nBeginBinaryIndex; nIndex <= nEndBinaryIndex; nIndex++ )
- {
- if( nIndex == nNextSectionIndex )
- {
- nIndex += 6;
- ++it;
- nNextSectionIndex = (it == aSections.end() ? nFontLen : *it );
- }
- unsigned char cNibble = 0x80;
- if( pFontData[ nIndex ] >= '0' && pFontData[ nIndex ] <= '9' )
- cNibble = pFontData[nIndex] - '0';
- else if( pFontData[ nIndex ] >= 'a' && pFontData[ nIndex ] <= 'f' )
- cNibble = pFontData[nIndex] - 'a' + 10;
- else if( pFontData[ nIndex ] >= 'A' && pFontData[ nIndex ] <= 'F' )
- cNibble = pFontData[nIndex] - 'A' + 10;
- if( cNibble != 0x80 )
- {
- if( !(nWriteIndex & 1 ) )
- cNibble <<= 4;
- xWriteBuffer.get()[ nWriteIndex/2 ] |= cNibble;
- nWriteIndex++;
- }
- }
- if (!writeBuffer(xWriteBuffer.get(), nLength2))
- throw FontException();
- if( aSections.empty() )
- {
- if( ! writeBuffer( pFontData+nIndex, nFontLen-nIndex ) )
- throw FontException();
- }
- else
- {
- // write rest of this section
- if( nIndex < nNextSectionIndex )
- {
- if( ! writeBuffer( pFontData+nIndex, nNextSectionIndex - nIndex ) )
- throw FontException();
- }
- // write following sections
- while( it != aSections.end() )
- {
- nIndex = (*it)+6;
- ++it;
- if( nIndex < nFontLen ) // last section marker is usually the EOF which has only 2 bytes
- {
- sal_Int32 nSectionLen = (it == aSections.end()) ? nFontLen - nIndex : (*it) - nIndex;
- if( ! writeBuffer( pFontData+nIndex, nSectionLen ) )
- throw FontException();
- }
- }
- }
- }
- endCompression();
- disableStreamEncryption();
-
- sal_uInt64 nEndStreamPos = 0;
- m_aFile.getPos(nEndStreamPos);
-
- // and finally close the stream
- aLine.setLength( 0 );
- aLine.append( "\nendstream\nendobj\n\n" );
- if( ! writeBuffer( aLine.getStr(), aLine.getLength() ) )
- throw FontException();
-
- // write stream length object
- aLine.setLength( 0 );
- if( ! updateObject( nStreamLengthObject ) )
- throw FontException();
- aLine.append( nStreamLengthObject );
- aLine.append( " 0 obj\n" );
- aLine.append( (sal_Int64)(nEndStreamPos-nBeginStreamPos ) );
- aLine.append( "\nendobj\n\n" );
- if( ! writeBuffer( aLine.getStr(), aLine.getLength() ) )
- throw FontException();
- }
- else
- {
- OStringBuffer aErrorComment( 256 );
- aErrorComment.append( "GetEmbedFontData failed for font \"" );
- aErrorComment.append( OUStringToOString( pFont->GetFamilyName(), RTL_TEXTENCODING_UTF8 ) );
- aErrorComment.append( '\"' );
- if( pFont->GetItalic() == ITALIC_NORMAL )
- aErrorComment.append( " italic" );
- else if( pFont->GetItalic() == ITALIC_OBLIQUE )
- aErrorComment.append( " oblique" );
- aErrorComment.append( " weight=" );
- aErrorComment.append( sal_Int32(pFont->GetWeight()) );
- emitComment( aErrorComment.getStr() );
- }
-
- if( nStreamObject )
- {
- // write font descriptor
- nFontDescriptor = emitFontDescriptor( pFont, aInfo, 0, nStreamObject );
- }
-
- if( nFontDescriptor )
- {
- // write font object
- sal_Int32 nObject = createObject();
- if( ! updateObject( nObject ) )
- throw FontException();
-
- OStringBuffer aLine( 1024 );
- aLine.append( nObject );
- aLine.append( " 0 obj\n"
- "<</Type/Font/Subtype/Type1/BaseFont/" );
- appendName( aInfo.m_aPSName, aLine );
- aLine.append( "\n" );
- if (!pFont->IsSymbolFont())
- aLine.append( "/Encoding/WinAnsiEncoding\n" );
- if( nToUnicodeStream )
- {
- aLine.append( "/ToUnicode " );
- aLine.append( nToUnicodeStream );
- aLine.append( " 0 R\n" );
- }
- aLine.append( "/FirstChar 0 /LastChar 255\n"
- "/Widths[" );
- for( int i = 0; i < 256; i++ )
- {
- aLine.append( pWidths[i] );
- aLine.append( ((i&15) == 15) ? "\n" : " " );
- }
- aLine.append( "]\n"
- "/FontDescriptor " );
- aLine.append( nFontDescriptor );
- aLine.append( " 0 R>>\n"
- "endobj\n\n" );
- if( ! writeBuffer( aLine.getStr(), aLine.getLength() ) )
- throw FontException();
-
- aRet[ rEmbed.m_nNormalFontID ] = nObject;
-
- // write additional encodings
- for( std::list< EmbedEncoding >::iterator enc_it = rEmbed.m_aExtendedEncodings.begin(); enc_it != rEmbed.m_aExtendedEncodings.end(); ++enc_it )
- {
- sal_Int32 aEncWidths[ 256 ];
- // emit encoding dict
- sal_Int32 nEncObject = createObject();
- if( ! updateObject( nEncObject ) )
- throw FontException();
-
- OutputDevice* pRef = getReferenceDevice();
- pRef->Push( PushFlags::FONT | PushFlags::MAPMODE );
- pRef->SetMapMode( MapMode( MapUnit::MapPixel ) );
- Font aFont( pFont->GetFamilyName(), pFont->GetStyleName(), Size( 0, 1000 ) );
- aFont.SetWeight( pFont->GetWeight() );
- aFont.SetItalic( pFont->GetItalic() );
- aFont.SetPitch( pFont->GetPitch() );
- pRef->SetFont( aFont );
- pRef->ImplNewFont();
-
- aLine.setLength( 0 );
- aLine.append( nEncObject );
- aLine.append( " 0 obj\n"
- "<</Type/Encoding/Differences[ 0\n" );
- int nEncoded = 0;
- aUnicodes.clear();
- for( std::vector< EmbedCode >::iterator str_it = enc_it->m_aEncVector.begin(); str_it != enc_it->m_aEncVector.end(); ++str_it )
- {
- OUString aStr( str_it->m_aUnicode );
- aEncWidths[nEncoded] = pRef->GetTextWidth( aStr );
- nEncodedCodes[nEncoded] = str_it->m_aUnicode;
- nEncoding[nEncoded] = sal::static_int_cast<sal_uInt8>(nEncoded);
- pEncToUnicodeIndex[nEncoded] = static_cast<sal_Int32>(aUnicodes.size());
- aUnicodes.push_back( nEncodedCodes[nEncoded] );
- pUnicodesPerGlyph[nEncoded] = 1;
-
- aLine.append( " /" );
- aLine.append( str_it->m_aName );
- if( !((++nEncoded) & 15) )
- aLine.append( "\n" );
- }
- aLine.append( "]>>\n"
- "endobj\n\n" );
-
- pRef->Pop();
-
- if( ! writeBuffer( aLine.getStr(), aLine.getLength() ) )
- throw FontException();
-
- nToUnicodeStream = createToUnicodeCMap( nEncoding, &aUnicodes[0], pUnicodesPerGlyph, pEncToUnicodeIndex, nEncoded );
-
- nObject = createObject();
- if( ! updateObject( nObject ) )
- throw FontException();
-
- aLine.setLength( 0 );
- aLine.append( nObject );
- aLine.append( " 0 obj\n"
- "<</Type/Font/Subtype/Type1/BaseFont/" );
- appendName( aInfo.m_aPSName, aLine );
- aLine.append( "\n" );
- aLine.append( "/Encoding " );
- aLine.append( nEncObject );
- aLine.append( " 0 R\n" );
- if( nToUnicodeStream )
- {
- aLine.append( "/ToUnicode " );
- aLine.append( nToUnicodeStream );
- aLine.append( " 0 R\n" );
- }
- aLine.append( "/FirstChar 0\n"
- "/LastChar " );
- aLine.append( (sal_Int32)(nEncoded-1) );
- aLine.append( "\n"
- "/Widths[" );
- for( int i = 0; i < nEncoded; i++ )
- {
- aLine.append( aEncWidths[i] );
- aLine.append( ((i&15) == 15) ? "\n" : " " );
- }
- aLine.append( " ]\n"
- "/FontDescriptor " );
- aLine.append( nFontDescriptor );
- aLine.append( " 0 R>>\n"
- "endobj\n\n" );
- if( ! writeBuffer( aLine.getStr(), aLine.getLength() ) )
- throw FontException();
-
- aRet[ enc_it->m_nFontID ] = nObject;
- }
- }
- }
- catch( FontException& )
- {
- // these do nothing in case there was no compression or encryption ongoing
- endCompression();
- disableStreamEncryption();
- }
-
- if( pFontData )
- pGraphics->FreeEmbedFontData( pFontData, nFontLen );
-
- return aRet;
-}
-
static void appendSubsetName( int nSubsetID, const OUString& rPSName, OStringBuffer& rBuffer )
{
if( nSubsetID )
@@ -4045,17 +3496,6 @@ bool PDFWriterImpl::emitFonts()
}
osl_removeFile( aTmpName.pData );
- // emit embedded fonts
- for( FontEmbedData::iterator eit = m_aEmbeddedFonts.begin(); eit != m_aEmbeddedFonts.end(); ++eit )
- {
- std::map< sal_Int32, sal_Int32 > aObjects = emitEmbeddedFont( eit->first, eit->second );
- for( std::map< sal_Int32, sal_Int32 >::iterator fit = aObjects.begin(); fit != aObjects.end(); ++fit )
- {
- if ( !fit->second ) return false;
- aFontIDToObject[ fit->first ] = fit->second;
- }
- }
-
// emit system fonts
for( FontEmbedData::iterator sit = m_aSystemFonts.begin(); sit != m_aSystemFonts.end(); ++sit )
{
diff --git a/vcl/source/gdi/pdfwriter_impl.hxx b/vcl/source/gdi/pdfwriter_impl.hxx
index 16f1fbd..8cad2f9 100644
--- a/vcl/source/gdi/pdfwriter_impl.hxx
+++ b/vcl/source/gdi/pdfwriter_impl.hxx
@@ -627,7 +627,6 @@ private:
std::list< TransparencyEmit > m_aTransparentObjects;
/* contains all font subsets in use */
FontSubsetData m_aSubsets;
- FontEmbedData m_aEmbeddedFonts;
FontEmbedData m_aSystemFonts;
sal_Int32 m_nNextFID;
PDFFontCache m_aFontCache;
@@ -806,8 +805,6 @@ i12626
bool emitGradients();
/* writes a builtin font object and returns its objectid (or 0 in case of failure ) */
sal_Int32 emitBuiltinFont( const PdfBuiltinFontFace*, sal_Int32 nObject );
- /* writes a type1 embedded font object and returns its mapping from font ids to object ids (or 0 in case of failure ) */
- std::map< sal_Int32, sal_Int32 > emitEmbeddedFont( const PhysicalFontFace*, EmbedFont& );
/* writes a type1 system font object and returns its mapping from font ids to object ids (or 0 in case of failure ) */
std::map< sal_Int32, sal_Int32 > emitSystemFont( const PhysicalFontFace*, EmbedFont& );
/* writes a font descriptor and returns its object id (or 0) */
More information about the Libreoffice-commits
mailing list