1 /************************************************************************* 2 * 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * Copyright 2000, 2010 Oracle and/or its affiliates. 6 * 7 * OpenOffice.org - a multi-platform office productivity suite 8 * 9 * This file is part of OpenOffice.org. 10 * 11 * OpenOffice.org is free software: you can redistribute it and/or modify 12 * it under the terms of the GNU Lesser General Public License version 3 13 * only, as published by the Free Software Foundation. 14 * 15 * OpenOffice.org is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 * GNU Lesser General Public License version 3 for more details 19 * (a copy is included in the LICENSE file that accompanied this code). 20 * 21 * You should have received a copy of the GNU Lesser General Public License 22 * version 3 along with OpenOffice.org. If not, see 23 * <http://www.openoffice.org/license.html> 24 * for a copy of the LGPLv3 License. 25 * 26 ************************************************************************/ 27 28 // MARKER(update_precomp.py): autogen include statement, do not remove 29 #include "precompiled_vcl.hxx" 30 31 #include <stdlib.h> 32 #include <unistd.h> 33 #include <fcntl.h> 34 #include <sys/mman.h> 35 #include <sys/stat.h> 36 #include <sys/types.h> 37 38 #include "basegfx/vector/b2ivector.hxx" 39 #include "basegfx/point/b2ipoint.hxx" 40 41 #include "basebmp/color.hxx" 42 43 #include "vcl/jobdata.hxx" 44 #include "vcl/printerinfomanager.hxx" 45 #include "vcl/bmpacc.hxx" 46 #include "vcl/svapp.hxx" 47 #include "vcl/sysdata.hxx" 48 49 #include "salprn.hxx" 50 #include "salbmp.hxx" 51 #include "glyphcache.hxx" 52 #include "impfont.hxx" 53 #include "outfont.hxx" 54 #include "fontsubset.hxx" 55 #include "printergfx.hxx" 56 #include "svppspgraphics.hxx" 57 #include "svpbmp.hxx" 58 #include "region.h" 59 60 using namespace psp; 61 using namespace rtl; 62 using namespace basebmp; 63 using namespace basegfx; 64 65 // ----- Implementation of PrinterBmp by means of SalBitmap/BitmapBuffer --------------- 66 67 class SalPrinterBmp : public psp::PrinterBmp 68 { 69 private: 70 SalPrinterBmp (); 71 72 BitmapDeviceSharedPtr m_aBitmap; 73 public: 74 75 SalPrinterBmp (const BitmapDeviceSharedPtr& rDevice); 76 virtual ~SalPrinterBmp (); 77 virtual sal_uInt32 GetPaletteColor (sal_uInt32 nIdx) const; 78 virtual sal_uInt32 GetPaletteEntryCount () const; 79 virtual sal_uInt32 GetPixelRGB (sal_uInt32 nRow, sal_uInt32 nColumn) const; 80 virtual sal_uInt8 GetPixelGray (sal_uInt32 nRow, sal_uInt32 nColumn) const; 81 virtual sal_uInt8 GetPixelIdx (sal_uInt32 nRow, sal_uInt32 nColumn) const; 82 virtual sal_uInt32 GetWidth () const; 83 virtual sal_uInt32 GetHeight() const; 84 virtual sal_uInt32 GetDepth () const; 85 86 static sal_uInt32 getRGBFromColor( const basebmp::Color& rCol ) 87 { 88 return ((rCol.getBlue()) & 0x000000ff) 89 | ((rCol.getGreen() << 8) & 0x0000ff00) 90 | ((rCol.getRed() << 16) & 0x00ff0000); 91 } 92 }; 93 94 SalPrinterBmp::SalPrinterBmp(const BitmapDeviceSharedPtr& rDevice) : 95 m_aBitmap( rDevice ) 96 { 97 } 98 99 SalPrinterBmp::~SalPrinterBmp () 100 { 101 } 102 103 sal_uInt32 104 SalPrinterBmp::GetWidth () const 105 { 106 return m_aBitmap.get() ? m_aBitmap->getSize().getX() : 0; 107 } 108 109 sal_uInt32 110 SalPrinterBmp::GetHeight () const 111 { 112 return m_aBitmap.get() ? m_aBitmap->getSize().getY() : 0; 113 } 114 115 sal_uInt32 116 SalPrinterBmp::GetDepth () const 117 { 118 return m_aBitmap.get() ? 119 SvpElement::getBitCountFromScanlineFormat( m_aBitmap->getScanlineFormat() ) 120 : 0; 121 } 122 123 124 sal_uInt32 125 SalPrinterBmp::GetPaletteEntryCount () const 126 { 127 return m_aBitmap.get() ? m_aBitmap->getPaletteEntryCount() : 0; 128 } 129 130 sal_uInt32 131 SalPrinterBmp::GetPaletteColor (sal_uInt32 nIdx) const 132 { 133 sal_uInt32 nCol = 0; 134 if( m_aBitmap.get() && nIdx < static_cast<sal_uInt32>(m_aBitmap->getPaletteEntryCount()) ) 135 { 136 const basebmp::Color& rColor = (*m_aBitmap->getPalette().get())[ nIdx ]; 137 nCol = getRGBFromColor( rColor ); 138 } 139 return nCol; 140 } 141 142 sal_uInt32 143 SalPrinterBmp::GetPixelRGB (sal_uInt32 nRow, sal_uInt32 nColumn) const 144 { 145 sal_uInt32 nCol = 0; 146 if( m_aBitmap.get() ) 147 nCol = getRGBFromColor( m_aBitmap->getPixel( B2IPoint( nColumn, nRow ) ) ); 148 return nCol; 149 } 150 151 sal_uInt8 152 SalPrinterBmp::GetPixelGray (sal_uInt32 nRow, sal_uInt32 nColumn) const 153 { 154 sal_uInt8 nGray = 0; 155 if( m_aBitmap.get() ) 156 { 157 // TODO: don't use tools color 158 basebmp::Color aCol = m_aBitmap->getPixel( B2IPoint( nColumn, nRow ) ); 159 ::Color aColor( aCol.getRed(), aCol.getGreen(), aCol.getBlue() ); 160 nGray = aColor.GetLuminance(); 161 } 162 return nGray; 163 } 164 165 sal_uInt8 166 SalPrinterBmp::GetPixelIdx (sal_uInt32 nRow, sal_uInt32 nColumn) const 167 { 168 sal_uInt8 nIdx = 0; 169 if( m_aBitmap.get() ) 170 nIdx = static_cast<sal_uInt8>(m_aBitmap->getPixelData( B2IPoint( nColumn, nRow ) )); 171 return nIdx; 172 } 173 174 /******************************************************* 175 * PspGraphics * 176 *******************************************************/ 177 178 bool PspGraphics::drawAlphaBitmap( const SalTwoRect&, const SalBitmap& /*rSourceBitmap*/, const SalBitmap& /*rAlphaBitmap*/ ) 179 { 180 return false; 181 } 182 183 bool PspGraphics::drawAlphaRect( long /*nX*/, long /*nY*/, long /*nWidth*/, long /*nHeight*/, sal_uInt8 /*nTransparency*/ ) 184 { 185 return false; 186 } 187 188 bool PspGraphics::supportsOperation( OutDevSupportType ) const 189 { 190 return false; 191 } 192 193 PspGraphics::~PspGraphics() 194 { 195 ReleaseFonts(); 196 } 197 198 void PspGraphics::GetResolution( sal_Int32 &rDPIX, sal_Int32 &rDPIY ) 199 { 200 if (m_pJobData != NULL) 201 { 202 int x = m_pJobData->m_aContext.getRenderResolution(); 203 204 rDPIX = x; 205 rDPIY = x; 206 } 207 } 208 209 sal_uInt16 PspGraphics::GetBitCount() 210 { 211 return m_pPrinterGfx->GetBitCount(); 212 } 213 214 long PspGraphics::GetGraphicsWidth() const 215 { 216 return 0; 217 } 218 219 void PspGraphics::ResetClipRegion() 220 { 221 m_pPrinterGfx->ResetClipRegion(); 222 } 223 224 bool PspGraphics::setClipRegion( const Region& i_rClip ) 225 { 226 // TODO: support polygonal clipregions here 227 m_pPrinterGfx->BeginSetClipRegion( i_rClip.GetRectCount() ); 228 229 ImplRegionInfo aInfo; 230 long nX, nY, nW, nH; 231 bool bRegionRect = i_rClip.ImplGetFirstRect(aInfo, nX, nY, nW, nH ); 232 while( bRegionRect ) 233 { 234 if ( nW && nH ) 235 { 236 m_pPrinterGfx->UnionClipRegion( nX, nY, nW, nH ); 237 } 238 bRegionRect = i_rClip.ImplGetNextRect( aInfo, nX, nY, nW, nH ); 239 } 240 m_pPrinterGfx->EndSetClipRegion(); 241 return true; 242 } 243 244 void PspGraphics::SetLineColor() 245 { 246 m_pPrinterGfx->SetLineColor (); 247 } 248 249 void PspGraphics::SetLineColor( SalColor nSalColor ) 250 { 251 psp::PrinterColor aColor (SALCOLOR_RED (nSalColor), 252 SALCOLOR_GREEN (nSalColor), 253 SALCOLOR_BLUE (nSalColor)); 254 m_pPrinterGfx->SetLineColor (aColor); 255 } 256 257 void PspGraphics::SetFillColor() 258 { 259 m_pPrinterGfx->SetFillColor (); 260 } 261 262 void PspGraphics::SetFillColor( SalColor nSalColor ) 263 { 264 psp::PrinterColor aColor (SALCOLOR_RED (nSalColor), 265 SALCOLOR_GREEN (nSalColor), 266 SALCOLOR_BLUE (nSalColor)); 267 m_pPrinterGfx->SetFillColor (aColor); 268 } 269 270 void PspGraphics::SetROPLineColor( SalROPColor ) 271 { 272 DBG_ASSERT( 0, "Error: PrinterGfx::SetROPLineColor() not implemented" ); 273 } 274 275 void PspGraphics::SetROPFillColor( SalROPColor ) 276 { 277 DBG_ASSERT( 0, "Error: PrinterGfx::SetROPFillColor() not implemented" ); 278 } 279 280 void PspGraphics::SetXORMode( bool bSet, bool ) 281 { 282 (void)bSet; 283 DBG_ASSERT( !bSet, "Error: PrinterGfx::SetXORMode() not implemented" ); 284 } 285 286 void PspGraphics::drawPixel( long nX, long nY ) 287 { 288 m_pPrinterGfx->DrawPixel (Point(nX, nY)); 289 } 290 291 void PspGraphics::drawPixel( long nX, long nY, SalColor nSalColor ) 292 { 293 psp::PrinterColor aColor (SALCOLOR_RED (nSalColor), 294 SALCOLOR_GREEN (nSalColor), 295 SALCOLOR_BLUE (nSalColor)); 296 m_pPrinterGfx->DrawPixel (Point(nX, nY), aColor); 297 } 298 299 void PspGraphics::drawLine( long nX1, long nY1, long nX2, long nY2 ) 300 { 301 m_pPrinterGfx->DrawLine (Point(nX1, nY1), Point(nX2, nY2)); 302 } 303 304 void PspGraphics::drawRect( long nX, long nY, long nDX, long nDY ) 305 { 306 m_pPrinterGfx->DrawRect (Rectangle(Point(nX, nY), Size(nDX, nDY))); 307 } 308 309 void PspGraphics::drawPolyLine( sal_uLong nPoints, const SalPoint *pPtAry ) 310 { 311 m_pPrinterGfx->DrawPolyLine (nPoints, (Point*)pPtAry); 312 } 313 314 void PspGraphics::drawPolygon( sal_uLong nPoints, const SalPoint* pPtAry ) 315 { 316 // Point must be equal to SalPoint! see vcl/inc/salgtype.hxx 317 m_pPrinterGfx->DrawPolygon (nPoints, (Point*)pPtAry); 318 } 319 320 void PspGraphics::drawPolyPolygon( sal_uInt32 nPoly, 321 const sal_uInt32 *pPoints, 322 PCONSTSALPOINT *pPtAry ) 323 { 324 m_pPrinterGfx->DrawPolyPolygon (nPoly, pPoints, (const Point**)pPtAry); 325 } 326 327 bool PspGraphics::drawPolyLine( const ::basegfx::B2DPolygon&, double /*fTransparency*/, const ::basegfx::B2DVector& /*rLineWidths*/, basegfx::B2DLineJoin /*eJoin*/ ) 328 { 329 // TODO: implement and advertise OutDevSupport_B2DDraw support 330 return false; 331 } 332 333 sal_Bool PspGraphics::drawPolyLineBezier( sal_uLong nPoints, const SalPoint* pPtAry, const sal_uInt8* pFlgAry ) 334 { 335 m_pPrinterGfx->DrawPolyLineBezier (nPoints, (Point*)pPtAry, pFlgAry); 336 return sal_True; 337 } 338 339 sal_Bool PspGraphics::drawPolygonBezier( sal_uLong nPoints, const SalPoint* pPtAry, const sal_uInt8* pFlgAry ) 340 { 341 m_pPrinterGfx->DrawPolygonBezier (nPoints, (Point*)pPtAry, pFlgAry); 342 return sal_True; 343 } 344 345 sal_Bool PspGraphics::drawPolyPolygonBezier( sal_uInt32 nPoly, 346 const sal_uInt32* pPoints, 347 const SalPoint* const* pPtAry, 348 const sal_uInt8* const* pFlgAry ) 349 { 350 // Point must be equal to SalPoint! see vcl/inc/salgtype.hxx 351 m_pPrinterGfx->DrawPolyPolygonBezier (nPoly, pPoints, (Point**)pPtAry, (sal_uInt8**)pFlgAry); 352 return sal_True; 353 } 354 355 bool PspGraphics::drawPolyPolygon( const basegfx::B2DPolyPolygon&, double /*fTransparency*/ ) 356 { 357 // TODO: implement and advertise OutDevSupport_B2DDraw support 358 return false; 359 } 360 361 void PspGraphics::invert( sal_uLong /*nPoints*/, 362 const SalPoint* /*pPtAry*/, 363 SalInvert /*nFlags*/ ) 364 { 365 DBG_ASSERT( 0, "Error: PrinterGfx::Invert() not implemented" ); 366 } 367 sal_Bool PspGraphics::drawEPS( long nX, long nY, long nWidth, long nHeight, void* pPtr, sal_uLong nSize ) 368 { 369 return m_pPrinterGfx->DrawEPS( Rectangle( Point( nX, nY ), Size( nWidth, nHeight ) ), pPtr, nSize ); 370 } 371 372 void PspGraphics::copyBits( const SalTwoRect* /*pPosAry*/, 373 SalGraphics* /*pSSrcGraphics*/ ) 374 { 375 DBG_ERROR( "Error: PrinterGfx::CopyBits() not implemented" ); 376 } 377 378 void PspGraphics::copyArea ( long /*nDestX*/, long /*nDestY*/, 379 long /*nSrcX*/, long /*nSrcY*/, 380 long /*nSrcWidth*/, long /*nSrcHeight*/, 381 sal_uInt16 /*nFlags*/ ) 382 { 383 DBG_ERROR( "Error: PrinterGfx::CopyArea() not implemented" ); 384 } 385 386 void PspGraphics::drawBitmap( const SalTwoRect* pPosAry, const SalBitmap& rSalBitmap ) 387 { 388 Rectangle aSrc (Point(pPosAry->mnSrcX, pPosAry->mnSrcY), 389 Size(pPosAry->mnSrcWidth, pPosAry->mnSrcHeight)); 390 Rectangle aDst (Point(pPosAry->mnDestX, pPosAry->mnDestY), 391 Size(pPosAry->mnDestWidth, pPosAry->mnDestHeight)); 392 393 const SvpSalBitmap* pBmp = dynamic_cast<const SvpSalBitmap*>(&rSalBitmap); 394 if( pBmp ) 395 { 396 SalPrinterBmp aBmp(pBmp->getBitmap()); 397 m_pPrinterGfx->DrawBitmap(aDst, aSrc, aBmp); 398 } 399 } 400 401 void PspGraphics::drawBitmap( const SalTwoRect* /*pPosAry*/, 402 const SalBitmap& /*rSalBitmap*/, 403 const SalBitmap& /*rTransBitmap*/ ) 404 { 405 DBG_ERROR("Error: no PrinterGfx::DrawBitmap() for transparent bitmap"); 406 } 407 408 void PspGraphics::drawBitmap( const SalTwoRect* /*pPosAry*/, 409 const SalBitmap& /*rSalBitmap*/, 410 SalColor /*nTransparentColor*/ ) 411 { 412 DBG_ERROR("Error: no PrinterGfx::DrawBitmap() for transparent color"); 413 } 414 415 void PspGraphics::drawMask( const SalTwoRect* /*pPosAry*/, 416 const SalBitmap& /*rSalBitmap*/, 417 SalColor /*nMaskColor*/ ) 418 { 419 DBG_ERROR("Error: PrinterGfx::DrawMask() not implemented"); 420 } 421 422 SalBitmap* PspGraphics::getBitmap( long /*nX*/, long /*nY*/, long /*nDX*/, long /*nDY*/ ) 423 { 424 DBG_WARNING ("Warning: PrinterGfx::GetBitmap() not implemented"); 425 return NULL; 426 } 427 428 SalColor PspGraphics::getPixel( long /*nX*/, long /*nY*/ ) 429 { 430 DBG_ERROR ("Warning: PrinterGfx::GetPixel() not implemented"); 431 return 0; 432 } 433 434 void PspGraphics::invert( 435 long /*nX*/, 436 long /*nY*/, 437 long /*nDX*/, 438 long /*nDY*/, 439 SalInvert /*nFlags*/ ) 440 { 441 DBG_ERROR ("Warning: PrinterGfx::Invert() not implemented"); 442 } 443 444 //========================================================================== 445 446 class ImplPspFontData : public ImplFontData 447 { 448 private: 449 enum { PSPFD_MAGIC = 0xb5bf01f0 }; 450 sal_IntPtr mnFontId; 451 452 public: 453 ImplPspFontData( const psp::FastPrintFontInfo& ); 454 virtual sal_IntPtr GetFontId() const { return mnFontId; } 455 virtual ImplFontData* Clone() const { return new ImplPspFontData( *this ); } 456 virtual ImplFontEntry* CreateFontInstance( ImplFontSelectData& ) const; 457 static bool CheckFontData( const ImplFontData& r ) { return r.CheckMagic( PSPFD_MAGIC ); } 458 }; 459 460 //-------------------------------------------------------------------------- 461 462 ImplPspFontData::ImplPspFontData( const psp::FastPrintFontInfo& rInfo ) 463 : ImplFontData( PspGraphics::Info2DevFontAttributes(rInfo), PSPFD_MAGIC ), 464 mnFontId( rInfo.m_nID ) 465 {} 466 467 //-------------------------------------------------------------------------- 468 469 ImplFontEntry* ImplPspFontData::CreateFontInstance( ImplFontSelectData& rFSD ) const 470 { 471 ImplServerFontEntry* pEntry = new ImplServerFontEntry( rFSD ); 472 return pEntry; 473 } 474 475 //========================================================================== 476 477 class PspFontLayout : public GenericSalLayout 478 { 479 public: 480 PspFontLayout( ::psp::PrinterGfx& ); 481 virtual bool LayoutText( ImplLayoutArgs& ); 482 virtual void InitFont() const; 483 virtual void DrawText( SalGraphics& ) const; 484 private: 485 ::psp::PrinterGfx& mrPrinterGfx; 486 sal_IntPtr mnFontID; 487 int mnFontHeight; 488 int mnFontWidth; 489 bool mbVertical; 490 bool mbArtItalic; 491 bool mbArtBold; 492 }; 493 494 //-------------------------------------------------------------------------- 495 496 PspFontLayout::PspFontLayout( ::psp::PrinterGfx& rGfx ) 497 : mrPrinterGfx( rGfx ) 498 { 499 mnFontID = mrPrinterGfx.GetFontID(); 500 mnFontHeight = mrPrinterGfx.GetFontHeight(); 501 mnFontWidth = mrPrinterGfx.GetFontWidth(); 502 mbVertical = mrPrinterGfx.GetFontVertical(); 503 mbArtItalic = mrPrinterGfx.GetArtificialItalic(); 504 mbArtBold = mrPrinterGfx.GetArtificialBold(); 505 } 506 507 //-------------------------------------------------------------------------- 508 509 bool PspFontLayout::LayoutText( ImplLayoutArgs& rArgs ) 510 { 511 mbVertical = ((rArgs.mnFlags & SAL_LAYOUT_VERTICAL) != 0); 512 513 long nUnitsPerPixel = 1; 514 int nOldGlyphId = -1; 515 long nGlyphWidth = 0; 516 int nCharPos = -1; 517 Point aNewPos( 0, 0 ); 518 GlyphItem aPrevItem; 519 rtl_TextEncoding aFontEnc = mrPrinterGfx.GetFontMgr().getFontEncoding( mnFontID ); 520 for(;;) 521 { 522 bool bRightToLeft; 523 if( !rArgs.GetNextPos( &nCharPos, &bRightToLeft ) ) 524 break; 525 526 sal_UCS4 cChar = rArgs.mpStr[ nCharPos ]; 527 if( bRightToLeft ) 528 cChar = GetMirroredChar( cChar ); 529 // symbol font aliasing: 0x0020-0x00ff -> 0xf020 -> 0xf0ff 530 if( aFontEnc == RTL_TEXTENCODING_SYMBOL ) 531 if( cChar < 256 ) 532 cChar += 0xf000; 533 int nGlyphIndex = cChar; // printer glyphs = unicode 534 535 // update fallback_runs if needed 536 psp::CharacterMetric aMetric; 537 mrPrinterGfx.GetFontMgr().getMetrics( mnFontID, cChar, cChar, &aMetric, mbVertical ); 538 if( aMetric.width == -1 && aMetric.height == -1 ) 539 rArgs.NeedFallback( nCharPos, bRightToLeft ); 540 541 // apply pair kerning to prev glyph if requested 542 if( SAL_LAYOUT_KERNING_PAIRS & rArgs.mnFlags ) 543 { 544 if( nOldGlyphId > 0 ) 545 { 546 const std::list< KernPair >& rKernPairs = mrPrinterGfx.getKernPairs(mbVertical); 547 for( std::list< KernPair >::const_iterator it = rKernPairs.begin(); 548 it != rKernPairs.end(); ++it ) 549 { 550 if( it->first == nOldGlyphId && it->second == nGlyphIndex ) 551 { 552 int nTextScale = mrPrinterGfx.GetFontWidth(); 553 if( ! nTextScale ) 554 nTextScale = mrPrinterGfx.GetFontHeight(); 555 int nKern = (mbVertical ? it->kern_y : it->kern_x) * nTextScale; 556 nGlyphWidth += nKern; 557 aPrevItem.mnNewWidth = nGlyphWidth; 558 break; 559 } 560 } 561 } 562 } 563 564 // finish previous glyph 565 if( nOldGlyphId >= 0 ) 566 AppendGlyph( aPrevItem ); 567 nOldGlyphId = nGlyphIndex; 568 aNewPos.X() += nGlyphWidth; 569 570 // prepare GlyphItem for appending it in next round 571 nUnitsPerPixel = mrPrinterGfx.GetCharWidth( cChar, cChar, &nGlyphWidth ); 572 int nGlyphFlags = bRightToLeft ? GlyphItem::IS_RTL_GLYPH : 0; 573 nGlyphIndex |= GF_ISCHAR; 574 aPrevItem = GlyphItem( nCharPos, nGlyphIndex, aNewPos, nGlyphFlags, nGlyphWidth ); 575 } 576 577 // append last glyph item if any 578 if( nOldGlyphId >= 0 ) 579 AppendGlyph( aPrevItem ); 580 581 SetOrientation( mrPrinterGfx.GetFontAngle() ); 582 SetUnitsPerPixel( nUnitsPerPixel ); 583 return (nOldGlyphId >= 0); 584 } 585 586 class PspServerFontLayout : public ServerFontLayout 587 { 588 public: 589 PspServerFontLayout( psp::PrinterGfx&, ServerFont& rFont, const ImplLayoutArgs& rArgs ); 590 591 virtual void InitFont() const; 592 const sal_Unicode* getTextPtr() const { return maText.getStr() - mnMinCharPos; } 593 int getMinCharPos() const { return mnMinCharPos; } 594 int getMaxCharPos() const { return mnMinCharPos+maText.getLength()-1; } 595 private: 596 ::psp::PrinterGfx& mrPrinterGfx; 597 sal_IntPtr mnFontID; 598 int mnFontHeight; 599 int mnFontWidth; 600 bool mbVertical; 601 bool mbArtItalic; 602 bool mbArtBold; 603 rtl::OUString maText; 604 int mnMinCharPos; 605 }; 606 607 PspServerFontLayout::PspServerFontLayout( ::psp::PrinterGfx& rGfx, ServerFont& rFont, const ImplLayoutArgs& rArgs ) 608 : ServerFontLayout( rFont ), 609 mrPrinterGfx( rGfx ) 610 { 611 mnFontID = mrPrinterGfx.GetFontID(); 612 mnFontHeight = mrPrinterGfx.GetFontHeight(); 613 mnFontWidth = mrPrinterGfx.GetFontWidth(); 614 mbVertical = mrPrinterGfx.GetFontVertical(); 615 mbArtItalic = mrPrinterGfx.GetArtificialItalic(); 616 mbArtBold = mrPrinterGfx.GetArtificialBold(); 617 maText = OUString( rArgs.mpStr + rArgs.mnMinCharPos, rArgs.mnEndCharPos - rArgs.mnMinCharPos+1 ); 618 mnMinCharPos = rArgs.mnMinCharPos; 619 } 620 621 void PspServerFontLayout::InitFont() const 622 { 623 mrPrinterGfx.SetFont( mnFontID, mnFontHeight, mnFontWidth, 624 mnOrientation, mbVertical, mbArtItalic, mbArtBold ); 625 } 626 627 //-------------------------------------------------------------------------- 628 629 static void DrawPrinterLayout( const SalLayout& rLayout, ::psp::PrinterGfx& rGfx, bool bIsPspServerFontLayout ) 630 { 631 const int nMaxGlyphs = 200; 632 sal_GlyphId aGlyphAry[ nMaxGlyphs ]; 633 sal_Int32 aWidthAry[ nMaxGlyphs ]; 634 sal_Int32 aIdxAry [ nMaxGlyphs ]; 635 sal_Ucs aUnicodes[ nMaxGlyphs ]; 636 int aCharPosAry [ nMaxGlyphs ]; 637 638 Point aPos; 639 long nUnitsPerPixel = rLayout.GetUnitsPerPixel(); 640 const sal_Unicode* pText = bIsPspServerFontLayout ? static_cast<const PspServerFontLayout&>(rLayout).getTextPtr() : NULL; 641 int nMinCharPos = bIsPspServerFontLayout ? static_cast<const PspServerFontLayout&>(rLayout).getMinCharPos() : 0; 642 int nMaxCharPos = bIsPspServerFontLayout ? static_cast<const PspServerFontLayout&>(rLayout).getMaxCharPos() : 0; 643 for( int nStart = 0;; ) 644 { 645 int nGlyphCount = rLayout.GetNextGlyphs( nMaxGlyphs, aGlyphAry, aPos, nStart, aWidthAry, bIsPspServerFontLayout ? aCharPosAry : NULL ); 646 if( !nGlyphCount ) 647 break; 648 649 sal_Int32 nXOffset = 0; 650 for( int i = 0; i < nGlyphCount; ++i ) 651 { 652 nXOffset += aWidthAry[ i ]; 653 aIdxAry[ i ] = nXOffset / nUnitsPerPixel; 654 sal_Int32 nGlyphIdx = aGlyphAry[i] & (GF_IDXMASK | GF_ROTMASK); 655 if( bIsPspServerFontLayout ) 656 aUnicodes[i] = (aCharPosAry[i] >= nMinCharPos && aCharPosAry[i] <= nMaxCharPos) ? pText[ aCharPosAry[i] ] : 0; 657 else 658 aUnicodes[i] = (aGlyphAry[i] & GF_ISCHAR) ? nGlyphIdx : 0; 659 aGlyphAry[i] = nGlyphIdx; 660 } 661 662 rGfx.DrawGlyphs( aPos, (sal_uInt32 *)aGlyphAry, aUnicodes, nGlyphCount, aIdxAry ); 663 } 664 } 665 666 //-------------------------------------------------------------------------- 667 668 void PspFontLayout::InitFont() const 669 { 670 mrPrinterGfx.SetFont( mnFontID, mnFontHeight, mnFontWidth, 671 mnOrientation, mbVertical, mbArtItalic, mbArtBold ); 672 } 673 674 //-------------------------------------------------------------------------- 675 676 void PspFontLayout::DrawText( SalGraphics& ) const 677 { 678 DrawPrinterLayout( *this, mrPrinterGfx, false ); 679 } 680 681 void PspGraphics::DrawServerFontLayout( const ServerFontLayout& rLayout ) 682 { 683 // print complex text 684 DrawPrinterLayout( rLayout, *m_pPrinterGfx, true ); 685 } 686 687 const ImplFontCharMap* PspGraphics::GetImplFontCharMap() const 688 { 689 if( !m_pServerFont[0] ) 690 return NULL; 691 692 const ImplFontCharMap* pIFCMap = m_pServerFont[0]->GetImplFontCharMap(); 693 return pIFCMap; 694 } 695 696 sal_uInt16 PspGraphics::SetFont( ImplFontSelectData *pEntry, int nFallbackLevel ) 697 { 698 // release all fonts that are to be overridden 699 for( int i = nFallbackLevel; i < MAX_FALLBACK; ++i ) 700 { 701 if( m_pServerFont[i] != NULL ) 702 { 703 // old server side font is no longer referenced 704 GlyphCache::GetInstance().UncacheFont( *m_pServerFont[i] ); 705 m_pServerFont[i] = NULL; 706 } 707 } 708 709 // return early if there is no new font 710 if( !pEntry ) 711 return 0; 712 713 sal_IntPtr nID = pEntry->mpFontData ? pEntry->mpFontData->GetFontId() : 0; 714 715 // determine which font attributes need to be emulated 716 bool bArtItalic = false; 717 bool bArtBold = false; 718 if( pEntry->meItalic == ITALIC_OBLIQUE || pEntry->meItalic == ITALIC_NORMAL ) 719 { 720 psp::italic::type eItalic = m_pPrinterGfx->GetFontMgr().getFontItalic( nID ); 721 if( eItalic != psp::italic::Italic && eItalic != psp::italic::Oblique ) 722 bArtItalic = true; 723 } 724 int nWeight = (int)pEntry->meWeight; 725 int nRealWeight = (int)m_pPrinterGfx->GetFontMgr().getFontWeight( nID ); 726 if( nRealWeight <= (int)psp::weight::Medium && nWeight > (int)WEIGHT_MEDIUM ) 727 { 728 bArtBold = true; 729 } 730 731 // also set the serverside font for layouting 732 m_bFontVertical = pEntry->mbVertical; 733 if( pEntry->mpFontData ) 734 { 735 // requesting a font provided by builtin rasterizer 736 ServerFont* pServerFont = GlyphCache::GetInstance().CacheFont( *pEntry ); 737 if( pServerFont != NULL ) 738 { 739 if( pServerFont->TestFont() ) 740 m_pServerFont[ nFallbackLevel ] = pServerFont; 741 else 742 GlyphCache::GetInstance().UncacheFont( *pServerFont ); 743 } 744 } 745 746 // set the printer font 747 return m_pPrinterGfx->SetFont( nID, 748 pEntry->mnHeight, 749 pEntry->mnWidth, 750 pEntry->mnOrientation, 751 pEntry->mbVertical, 752 bArtItalic, 753 bArtBold 754 ); 755 } 756 757 void PspGraphics::SetTextColor( SalColor nSalColor ) 758 { 759 psp::PrinterColor aColor (SALCOLOR_RED (nSalColor), 760 SALCOLOR_GREEN (nSalColor), 761 SALCOLOR_BLUE (nSalColor)); 762 m_pPrinterGfx->SetTextColor (aColor); 763 } 764 765 bool PspGraphics::AddTempDevFont( ImplDevFontList*, const String&, const String& ) 766 { 767 return false; 768 } 769 770 void PspGraphics::GetDevFontList( ImplDevFontList *pList ) 771 { 772 ::std::list< psp::fontID > aList; 773 psp::PrintFontManager& rMgr = psp::PrintFontManager::get(); 774 rMgr.getFontList( aList, m_pJobData->m_pParser, m_pInfoPrinter->m_bCompatMetrics ); 775 776 ::std::list< psp::fontID >::iterator it; 777 psp::FastPrintFontInfo aInfo; 778 for (it = aList.begin(); it != aList.end(); ++it) 779 if (rMgr.getFontFastInfo (*it, aInfo)) 780 AnnounceFonts( pList, aInfo ); 781 } 782 783 void PspGraphics::GetDevFontSubstList( OutputDevice* pOutDev ) 784 { 785 const psp::PrinterInfo& rInfo = psp::PrinterInfoManager::get().getPrinterInfo( m_pJobData->m_aPrinterName ); 786 if( rInfo.m_bPerformFontSubstitution ) 787 { 788 for( std::hash_map< rtl::OUString, rtl::OUString, rtl::OUStringHash >::const_iterator it = rInfo.m_aFontSubstitutes.begin(); it != rInfo.m_aFontSubstitutes.end(); ++it ) 789 AddDevFontSubstitute( pOutDev, it->first, it->second, FONT_SUBSTITUTE_ALWAYS ); 790 } 791 } 792 793 void PspGraphics::GetFontMetric( ImplFontMetricData *pMetric, int ) 794 { 795 const psp::PrintFontManager& rMgr = psp::PrintFontManager::get(); 796 psp::PrintFontInfo aInfo; 797 798 if (rMgr.getFontInfo (m_pPrinterGfx->GetFontID(), aInfo)) 799 { 800 ImplDevFontAttributes aDFA = Info2DevFontAttributes( aInfo ); 801 static_cast<ImplFontAttributes&>(*pMetric) = aDFA; 802 pMetric->mbDevice = aDFA.mbDevice; 803 pMetric->mbScalableFont = true; 804 805 pMetric->mnOrientation = m_pPrinterGfx->GetFontAngle(); 806 pMetric->mnSlant = 0; 807 808 sal_Int32 nTextHeight = m_pPrinterGfx->GetFontHeight(); 809 sal_Int32 nTextWidth = m_pPrinterGfx->GetFontWidth(); 810 if( ! nTextWidth ) 811 nTextWidth = nTextHeight; 812 813 pMetric->mnWidth = nTextWidth; 814 pMetric->mnAscent = ( aInfo.m_nAscend * nTextHeight + 500 ) / 1000; 815 pMetric->mnDescent = ( aInfo.m_nDescend * nTextHeight + 500 ) / 1000; 816 pMetric->mnIntLeading = ( aInfo.m_nLeading * nTextHeight + 500 ) / 1000; 817 pMetric->mnExtLeading = 0; 818 } 819 } 820 821 sal_uLong PspGraphics::GetKernPairs( sal_uLong nPairs, ImplKernPairData *pKernPairs ) 822 { 823 const ::std::list< ::psp::KernPair >& rPairs( m_pPrinterGfx->getKernPairs() ); 824 sal_uLong nHavePairs = rPairs.size(); 825 if( pKernPairs && nPairs ) 826 { 827 ::std::list< ::psp::KernPair >::const_iterator it; 828 unsigned int i; 829 int nTextScale = m_pPrinterGfx->GetFontWidth(); 830 if( ! nTextScale ) 831 nTextScale = m_pPrinterGfx->GetFontHeight(); 832 for( i = 0, it = rPairs.begin(); i < nPairs && i < nHavePairs; i++, ++it ) 833 { 834 pKernPairs[i].mnChar1 = it->first; 835 pKernPairs[i].mnChar2 = it->second; 836 pKernPairs[i].mnKern = it->kern_x * nTextScale / 1000; 837 } 838 839 } 840 return nHavePairs; 841 } 842 843 sal_Bool PspGraphics::GetGlyphBoundRect( long nGlyphIndex, Rectangle& rRect ) 844 { 845 int nLevel = nGlyphIndex >> GF_FONTSHIFT; 846 if( nLevel >= MAX_FALLBACK ) 847 return sal_False; 848 849 ServerFont* pSF = m_pServerFont[ nLevel ]; 850 if( !pSF ) 851 return sal_False; 852 853 nGlyphIndex &= ~GF_FONTMASK; 854 const GlyphMetric& rGM = pSF->GetGlyphMetric( nGlyphIndex ); 855 rRect = Rectangle( rGM.GetOffset(), rGM.GetSize() ); 856 return sal_True; 857 } 858 859 sal_Bool PspGraphics::GetGlyphOutline( long nGlyphIndex, 860 ::basegfx::B2DPolyPolygon& rB2DPolyPoly ) 861 { 862 int nLevel = nGlyphIndex >> GF_FONTSHIFT; 863 if( nLevel >= MAX_FALLBACK ) 864 return sal_False; 865 866 ServerFont* pSF = m_pServerFont[ nLevel ]; 867 if( !pSF ) 868 return sal_False; 869 870 nGlyphIndex &= ~GF_FONTMASK; 871 if( pSF->GetGlyphOutline( nGlyphIndex, rB2DPolyPoly ) ) 872 return sal_True; 873 874 return sal_False; 875 } 876 877 SalLayout* PspGraphics::GetTextLayout( ImplLayoutArgs& rArgs, int nFallbackLevel ) 878 { 879 // workaround for printers not handling glyph indexing for non-TT fonts 880 int nFontId = m_pPrinterGfx->GetFontID(); 881 if( psp::fonttype::TrueType != psp::PrintFontManager::get().getFontType( nFontId ) ) 882 rArgs.mnFlags |= SAL_LAYOUT_DISABLE_GLYPH_PROCESSING; 883 else if( nFallbackLevel > 0 ) 884 rArgs.mnFlags &= ~SAL_LAYOUT_DISABLE_GLYPH_PROCESSING; 885 886 GenericSalLayout* pLayout = NULL; 887 888 if( m_pServerFont[ nFallbackLevel ] 889 && !(rArgs.mnFlags & SAL_LAYOUT_DISABLE_GLYPH_PROCESSING) ) 890 pLayout = new PspServerFontLayout( *m_pPrinterGfx, *m_pServerFont[nFallbackLevel], rArgs ); 891 else 892 pLayout = new PspFontLayout( *m_pPrinterGfx ); 893 894 return pLayout; 895 } 896 897 //-------------------------------------------------------------------------- 898 899 sal_Bool PspGraphics::CreateFontSubset( 900 const rtl::OUString& rToFile, 901 const ImplFontData* pFont, 902 sal_Int32* pGlyphIDs, 903 sal_uInt8* pEncoding, 904 sal_Int32* pWidths, 905 int nGlyphCount, 906 FontSubsetInfo& rInfo 907 ) 908 { 909 // in this context the pFont->GetFontId() is a valid PSP 910 // font since they are the only ones left after the PDF 911 // export has filtered its list of subsettable fonts (for 912 // which this method was created). The correct way would 913 // be to have the GlyphCache search for the ImplFontData pFont 914 psp::fontID aFont = pFont->GetFontId(); 915 916 psp::PrintFontManager& rMgr = psp::PrintFontManager::get(); 917 bool bSuccess = rMgr.createFontSubset( rInfo, 918 aFont, 919 rToFile, 920 pGlyphIDs, 921 pEncoding, 922 pWidths, 923 nGlyphCount ); 924 return bSuccess; 925 } 926 927 //-------------------------------------------------------------------------- 928 929 const void* PspGraphics::GetEmbedFontData( const ImplFontData* pFont, const sal_Ucs* pUnicodes, sal_Int32* pWidths, FontSubsetInfo& rInfo, long* pDataLen ) 930 { 931 // in this context the pFont->GetFontId() is a valid PSP 932 // font since they are the only ones left after the PDF 933 // export has filtered its list of subsettable fonts (for 934 // which this method was created). The correct way would 935 // be to have the GlyphCache search for the ImplFontData pFont 936 psp::fontID aFont = pFont->GetFontId(); 937 return PspGraphics::DoGetEmbedFontData( aFont, pUnicodes, pWidths, rInfo, pDataLen ); 938 } 939 940 //-------------------------------------------------------------------------- 941 942 void PspGraphics::FreeEmbedFontData( const void* pData, long nLen ) 943 { 944 PspGraphics::DoFreeEmbedFontData( pData, nLen ); 945 } 946 947 //-------------------------------------------------------------------------- 948 949 const Ucs2SIntMap* PspGraphics::GetFontEncodingVector( const ImplFontData* pFont, const Ucs2OStrMap** pNonEncoded ) 950 { 951 // in this context the pFont->GetFontId() is a valid PSP 952 // font since they are the only ones left after the PDF 953 // export has filtered its list of subsettable fonts (for 954 // which this method was created). The correct way would 955 // be to have the GlyphCache search for the ImplFontData pFont 956 psp::fontID aFont = pFont->GetFontId(); 957 return PspGraphics::DoGetFontEncodingVector( aFont, pNonEncoded ); 958 } 959 960 //-------------------------------------------------------------------------- 961 962 void PspGraphics::GetGlyphWidths( const ImplFontData* pFont, 963 bool bVertical, 964 Int32Vector& rWidths, 965 Ucs2UIntMap& rUnicodeEnc ) 966 { 967 // in this context the pFont->GetFontId() is a valid PSP 968 // font since they are the only ones left after the PDF 969 // export has filtered its list of subsettable fonts (for 970 // which this method was created). The correct way would 971 // be to have the GlyphCache search for the ImplFontData pFont 972 psp::fontID aFont = pFont->GetFontId(); 973 PspGraphics::DoGetGlyphWidths( aFont, bVertical, rWidths, rUnicodeEnc ); 974 } 975 976 // static helpers of PspGraphics 977 978 const void* PspGraphics::DoGetEmbedFontData( fontID aFont, const sal_Ucs* pUnicodes, sal_Int32* pWidths, FontSubsetInfo& rInfo, long* pDataLen ) 979 { 980 psp::PrintFontManager& rMgr = psp::PrintFontManager::get(); 981 982 psp::PrintFontInfo aFontInfo; 983 if( ! rMgr.getFontInfo( aFont, aFontInfo ) ) 984 return NULL; 985 986 // fill in font info 987 rInfo.m_nAscent = aFontInfo.m_nAscend; 988 rInfo.m_nDescent = aFontInfo.m_nDescend; 989 rInfo.m_aPSName = rMgr.getPSName( aFont ); 990 991 int xMin, yMin, xMax, yMax; 992 rMgr.getFontBoundingBox( aFont, xMin, yMin, xMax, yMax ); 993 994 psp::CharacterMetric aMetrics[256]; 995 sal_Ucs aUnicodes[256]; 996 if( aFontInfo.m_aEncoding == RTL_TEXTENCODING_SYMBOL && aFontInfo.m_eType == psp::fonttype::Type1 ) 997 { 998 for( int i = 0; i < 256; i++ ) 999 aUnicodes[i] = pUnicodes[i] < 0x0100 ? pUnicodes[i] + 0xf000 : pUnicodes[i]; 1000 pUnicodes = aUnicodes; 1001 } 1002 if( ! rMgr.getMetrics( aFont, pUnicodes, 256, aMetrics ) ) 1003 return NULL; 1004 1005 OString aSysPath = rMgr.getFontFileSysPath( aFont ); 1006 struct stat aStat; 1007 if( stat( aSysPath.getStr(), &aStat ) ) 1008 return NULL; 1009 int fd = open( aSysPath.getStr(), O_RDONLY ); 1010 if( fd < 0 ) 1011 return NULL; 1012 void* pFile = mmap( NULL, aStat.st_size, PROT_READ, MAP_SHARED, fd, 0 ); 1013 close( fd ); 1014 if( pFile == MAP_FAILED ) 1015 return NULL; 1016 1017 *pDataLen = aStat.st_size; 1018 1019 rInfo.m_aFontBBox = Rectangle( Point( xMin, yMin ), Size( xMax-xMin, yMax-yMin ) ); 1020 rInfo.m_nCapHeight = yMax; // Well ... 1021 1022 for( int i = 0; i < 256; i++ ) 1023 pWidths[i] = (aMetrics[i].width > 0 ? aMetrics[i].width : 0); 1024 1025 switch( aFontInfo.m_eType ) 1026 { 1027 case psp::fonttype::TrueType: 1028 rInfo.m_nFontType = FontSubsetInfo::SFNT_TTF; 1029 break; 1030 case psp::fonttype::Type1: { 1031 const bool bPFA = ((*(unsigned char*)pFile) < 0x80); 1032 rInfo.m_nFontType = bPFA ? FontSubsetInfo::TYPE1_PFA : FontSubsetInfo::TYPE1_PFB; 1033 } 1034 break; 1035 default: 1036 return NULL; 1037 } 1038 1039 return pFile; 1040 } 1041 1042 void PspGraphics::DoFreeEmbedFontData( const void* pData, long nLen ) 1043 { 1044 if( pData ) 1045 munmap( (char*)pData, nLen ); 1046 } 1047 1048 const Ucs2SIntMap* PspGraphics::DoGetFontEncodingVector( fontID aFont, const Ucs2OStrMap** pNonEncoded ) 1049 { 1050 psp::PrintFontManager& rMgr = psp::PrintFontManager::get(); 1051 1052 psp::PrintFontInfo aFontInfo; 1053 if( ! rMgr.getFontInfo( aFont, aFontInfo ) ) 1054 { 1055 if( pNonEncoded ) 1056 *pNonEncoded = NULL; 1057 return NULL; 1058 } 1059 1060 return rMgr.getEncodingMap( aFont, pNonEncoded ); 1061 } 1062 1063 void PspGraphics::DoGetGlyphWidths( psp::fontID aFont, 1064 bool bVertical, 1065 Int32Vector& rWidths, 1066 Ucs2UIntMap& rUnicodeEnc ) 1067 { 1068 psp::PrintFontManager& rMgr = psp::PrintFontManager::get(); 1069 rMgr.getGlyphWidths( aFont, bVertical, rWidths, rUnicodeEnc ); 1070 } 1071 1072 // ---------------------------------------------------------------------------- 1073 1074 FontWidth PspGraphics::ToFontWidth (psp::width::type eWidth) 1075 { 1076 switch (eWidth) 1077 { 1078 case psp::width::UltraCondensed: return WIDTH_ULTRA_CONDENSED; 1079 case psp::width::ExtraCondensed: return WIDTH_EXTRA_CONDENSED; 1080 case psp::width::Condensed: return WIDTH_CONDENSED; 1081 case psp::width::SemiCondensed: return WIDTH_SEMI_CONDENSED; 1082 case psp::width::Normal: return WIDTH_NORMAL; 1083 case psp::width::SemiExpanded: return WIDTH_SEMI_EXPANDED; 1084 case psp::width::Expanded: return WIDTH_EXPANDED; 1085 case psp::width::ExtraExpanded: return WIDTH_EXTRA_EXPANDED; 1086 case psp::width::UltraExpanded: return WIDTH_ULTRA_EXPANDED; 1087 default: break; 1088 } 1089 return WIDTH_DONTKNOW; 1090 } 1091 1092 FontWeight PspGraphics::ToFontWeight (psp::weight::type eWeight) 1093 { 1094 switch (eWeight) 1095 { 1096 case psp::weight::Thin: return WEIGHT_THIN; 1097 case psp::weight::UltraLight: return WEIGHT_ULTRALIGHT; 1098 case psp::weight::Light: return WEIGHT_LIGHT; 1099 case psp::weight::SemiLight: return WEIGHT_SEMILIGHT; 1100 case psp::weight::Normal: return WEIGHT_NORMAL; 1101 case psp::weight::Medium: return WEIGHT_MEDIUM; 1102 case psp::weight::SemiBold: return WEIGHT_SEMIBOLD; 1103 case psp::weight::Bold: return WEIGHT_BOLD; 1104 case psp::weight::UltraBold: return WEIGHT_ULTRABOLD; 1105 case psp::weight::Black: return WEIGHT_BLACK; 1106 default: break; 1107 } 1108 return WEIGHT_DONTKNOW; 1109 } 1110 1111 FontPitch PspGraphics::ToFontPitch (psp::pitch::type ePitch) 1112 { 1113 switch (ePitch) 1114 { 1115 case psp::pitch::Fixed: return PITCH_FIXED; 1116 case psp::pitch::Variable: return PITCH_VARIABLE; 1117 default: break; 1118 } 1119 return PITCH_DONTKNOW; 1120 } 1121 1122 FontItalic PspGraphics::ToFontItalic (psp::italic::type eItalic) 1123 { 1124 switch (eItalic) 1125 { 1126 case psp::italic::Upright: return ITALIC_NONE; 1127 case psp::italic::Oblique: return ITALIC_OBLIQUE; 1128 case psp::italic::Italic: return ITALIC_NORMAL; 1129 default: break; 1130 } 1131 return ITALIC_DONTKNOW; 1132 } 1133 1134 FontFamily PspGraphics::ToFontFamily (psp::family::type eFamily) 1135 { 1136 switch (eFamily) 1137 { 1138 case psp::family::Decorative: return FAMILY_DECORATIVE; 1139 case psp::family::Modern: return FAMILY_MODERN; 1140 case psp::family::Roman: return FAMILY_ROMAN; 1141 case psp::family::Script: return FAMILY_SCRIPT; 1142 case psp::family::Swiss: return FAMILY_SWISS; 1143 case psp::family::System: return FAMILY_SYSTEM; 1144 default: break; 1145 } 1146 return FAMILY_DONTKNOW; 1147 } 1148 1149 ImplDevFontAttributes PspGraphics::Info2DevFontAttributes( const psp::FastPrintFontInfo& rInfo ) 1150 { 1151 ImplDevFontAttributes aDFA; 1152 aDFA.maName = rInfo.m_aFamilyName; 1153 aDFA.maStyleName = rInfo.m_aStyleName; 1154 aDFA.meFamily = ToFontFamily (rInfo.m_eFamilyStyle); 1155 aDFA.meWeight = ToFontWeight (rInfo.m_eWeight); 1156 aDFA.meItalic = ToFontItalic (rInfo.m_eItalic); 1157 aDFA.meWidthType = ToFontWidth (rInfo.m_eWidth); 1158 aDFA.mePitch = ToFontPitch (rInfo.m_ePitch); 1159 aDFA.mbSymbolFlag = (rInfo.m_aEncoding == RTL_TEXTENCODING_SYMBOL); 1160 1161 switch( rInfo.m_eType ) 1162 { 1163 case psp::fonttype::Builtin: 1164 aDFA.mnQuality = 1024; 1165 aDFA.mbDevice = true; 1166 aDFA.mbSubsettable = false; 1167 aDFA.mbEmbeddable = false; 1168 break; 1169 case psp::fonttype::TrueType: 1170 aDFA.mnQuality = 512; 1171 aDFA.mbDevice = false; 1172 aDFA.mbSubsettable = true; 1173 aDFA.mbEmbeddable = false; 1174 break; 1175 case psp::fonttype::Type1: 1176 aDFA.mnQuality = 0; 1177 aDFA.mbDevice = false; 1178 aDFA.mbSubsettable = false; 1179 aDFA.mbEmbeddable = true; 1180 break; 1181 default: 1182 aDFA.mnQuality = 0; 1183 aDFA.mbDevice = false; 1184 aDFA.mbSubsettable = false; 1185 aDFA.mbEmbeddable = false; 1186 break; 1187 } 1188 1189 aDFA.mbOrientation = true; 1190 1191 // add font family name aliases 1192 ::std::list< OUString >::const_iterator it = rInfo.m_aAliases.begin(); 1193 bool bHasMapNames = false; 1194 for(; it != rInfo.m_aAliases.end(); ++it ) 1195 { 1196 if( bHasMapNames ) 1197 aDFA.maMapNames.Append( ';' ); 1198 aDFA.maMapNames.Append( (*it).getStr() ); 1199 bHasMapNames = true; 1200 } 1201 1202 #if OSL_DEBUG_LEVEL > 2 1203 if( bHasMapNames ) 1204 { 1205 ByteString aOrigName( aDFA.maName, osl_getThreadTextEncoding() ); 1206 ByteString aAliasNames( aDFA.maMapNames, osl_getThreadTextEncoding() ); 1207 fprintf( stderr, "using alias names \"%s\" for font family \"%s\"\n", 1208 aAliasNames.GetBuffer(), aOrigName.GetBuffer() ); 1209 } 1210 #endif 1211 1212 return aDFA; 1213 } 1214 1215 // ----------------------------------------------------------------------- 1216 1217 void PspGraphics::AnnounceFonts( ImplDevFontList* pFontList, const psp::FastPrintFontInfo& aInfo ) 1218 { 1219 int nQuality = 0; 1220 1221 if( aInfo.m_eType == psp::fonttype::TrueType ) 1222 { 1223 // asian type 1 fonts are not known 1224 psp::PrintFontManager& rMgr = psp::PrintFontManager::get(); 1225 ByteString aFileName( rMgr.getFontFileSysPath( aInfo.m_nID ) ); 1226 int nPos = aFileName.SearchBackward( '_' ); 1227 if( nPos == STRING_NOTFOUND || aFileName.GetChar( nPos+1 ) == '.' ) 1228 nQuality += 5; 1229 else 1230 { 1231 static const char* pLangBoost = NULL; 1232 static bool bOnce = true; 1233 if( bOnce ) 1234 { 1235 bOnce = false; 1236 const LanguageType aLang = Application::GetSettings().GetUILanguage(); 1237 switch( aLang ) 1238 { 1239 case LANGUAGE_JAPANESE: 1240 pLangBoost = "jan"; 1241 break; 1242 case LANGUAGE_CHINESE: 1243 case LANGUAGE_CHINESE_SIMPLIFIED: 1244 case LANGUAGE_CHINESE_SINGAPORE: 1245 pLangBoost = "zhs"; 1246 break; 1247 case LANGUAGE_CHINESE_TRADITIONAL: 1248 case LANGUAGE_CHINESE_HONGKONG: 1249 case LANGUAGE_CHINESE_MACAU: 1250 pLangBoost = "zht"; 1251 break; 1252 case LANGUAGE_KOREAN: 1253 case LANGUAGE_KOREAN_JOHAB: 1254 pLangBoost = "kor"; 1255 break; 1256 } 1257 } 1258 1259 if( pLangBoost ) 1260 if( aFileName.Copy( nPos+1, 3 ).EqualsIgnoreCaseAscii( pLangBoost ) ) 1261 nQuality += 10; 1262 } 1263 } 1264 1265 ImplPspFontData* pFD = new ImplPspFontData( aInfo ); 1266 pFD->mnQuality += nQuality; 1267 pFontList->Add( pFD ); 1268 } 1269 1270 bool PspGraphics::filterText( const String& rOrig, String& rNewText, xub_StrLen nIndex, xub_StrLen& rLen, xub_StrLen& rCutStart, xub_StrLen& rCutStop ) 1271 { 1272 if( ! m_pPhoneNr ) 1273 return false; 1274 1275 rCutStop = rCutStart = STRING_NOTFOUND; 1276 1277 #define FAX_PHONE_TOKEN "@@#" 1278 #define FAX_PHONE_TOKEN_LENGTH 3 1279 #define FAX_END_TOKEN "@@" 1280 #define FAX_END_TOKEN_LENGTH 2 1281 1282 bool bRet = false; 1283 bool bStarted = false; 1284 bool bStopped = false; 1285 sal_uInt16 nPos; 1286 sal_uInt16 nStart = 0; 1287 sal_uInt16 nStop = rLen; 1288 String aPhone = rOrig.Copy( nIndex, rLen ); 1289 1290 if( ! m_bPhoneCollectionActive ) 1291 { 1292 if( ( nPos = aPhone.SearchAscii( FAX_PHONE_TOKEN ) ) != STRING_NOTFOUND ) 1293 { 1294 nStart = nPos; 1295 m_bPhoneCollectionActive = true; 1296 m_aPhoneCollection.Erase(); 1297 bRet = true; 1298 bStarted = true; 1299 } 1300 } 1301 if( m_bPhoneCollectionActive ) 1302 { 1303 bRet = true; 1304 nPos = bStarted ? nStart + FAX_PHONE_TOKEN_LENGTH : 0; 1305 if( ( nPos = aPhone.SearchAscii( FAX_END_TOKEN, nPos ) ) != STRING_NOTFOUND ) 1306 { 1307 m_bPhoneCollectionActive = false; 1308 nStop = nPos + FAX_END_TOKEN_LENGTH; 1309 bStopped = true; 1310 } 1311 int nTokenStart = nStart + (bStarted ? FAX_PHONE_TOKEN_LENGTH : 0); 1312 int nTokenStop = nStop - (bStopped ? FAX_END_TOKEN_LENGTH : 0); 1313 m_aPhoneCollection += aPhone.Copy( nTokenStart, nTokenStop - nTokenStart ); 1314 if( ! m_bPhoneCollectionActive ) 1315 { 1316 m_pPhoneNr->AppendAscii( "<Fax#>" ); 1317 m_pPhoneNr->Append( m_aPhoneCollection ); 1318 m_pPhoneNr->AppendAscii( "</Fax#>" ); 1319 m_aPhoneCollection.Erase(); 1320 } 1321 } 1322 if( m_aPhoneCollection.Len() > 1024 ) 1323 { 1324 m_bPhoneCollectionActive = false; 1325 m_aPhoneCollection.Erase(); 1326 bRet = false; 1327 } 1328 1329 if( bRet && m_bSwallowFaxNo ) 1330 { 1331 rLen -= nStop - nStart; 1332 rCutStart = nStart+nIndex; 1333 rCutStop = nStop+nIndex; 1334 if( rCutStart ) 1335 rNewText = rOrig.Copy( 0, rCutStart ); 1336 rNewText += rOrig.Copy( rCutStop ); 1337 } 1338 1339 return bRet && m_bSwallowFaxNo; 1340 } 1341 1342 SystemFontData PspGraphics::GetSysFontData( int nFallbacklevel ) const 1343 { 1344 SystemFontData aSysFontData; 1345 1346 if (nFallbacklevel >= MAX_FALLBACK) nFallbacklevel = MAX_FALLBACK - 1; 1347 if (nFallbacklevel < 0 ) nFallbacklevel = 0; 1348 1349 aSysFontData.nSize = sizeof( SystemFontData ); 1350 aSysFontData.nFontId = 0; 1351 aSysFontData.nFontFlags = 0; 1352 aSysFontData.bFakeBold = false; 1353 aSysFontData.bFakeItalic = false; 1354 aSysFontData.bAntialias = true; 1355 return aSysFontData; 1356 } 1357 1358 SystemGraphicsData PspGraphics::GetGraphicsData() const 1359 { 1360 SystemGraphicsData aRes; 1361 aRes.nSize = sizeof(aRes); 1362 aRes.hDrawable = 0; 1363 aRes.pRenderFormat = 0; 1364 return aRes; 1365 } 1366 1367