merge the formfield patch from ooo-build
[ooovba.git] / vcl / unx / source / gdi / pspgraphics.cxx
bloba6a2e4920eee2df271abeff0ef42f155016f4eb9
1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * This file is part of OpenOffice.org.
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.
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).
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.
26 ************************************************************************/
28 // MARKER(update_precomp.py): autogen include statement, do not remove
29 #include "precompiled_vcl.hxx"
31 #include "pspgraphics.h"
32 #include "vcl/jobdata.hxx"
33 #include "vcl/printergfx.hxx"
34 #include "vcl/printerinfomanager.hxx"
35 #include "vcl/bmpacc.hxx"
36 #include "vcl/salbmp.hxx"
37 #include "vcl/glyphcache.hxx"
38 #include "vcl/impfont.hxx"
39 #include "vcl/outfont.hxx"
40 #include "vcl/fontsubset.hxx"
41 #include "vcl/svapp.hxx"
42 #include "vcl/salprn.hxx"
43 #include "vcl/sysdata.hxx"
45 #include <stdlib.h>
46 #include <unistd.h>
47 #include <fcntl.h>
48 #include <sys/mman.h>
49 #include <sys/stat.h>
50 #include <sys/types.h>
52 #ifdef ENABLE_GRAPHITE
53 #include <vcl/graphite_layout.hxx>
54 #include <vcl/graphite_serverfont.hxx>
55 #endif
57 using namespace psp;
58 using namespace rtl;
60 // ----- Implementation of PrinterBmp by means of SalBitmap/BitmapBuffer ---------------
62 class SalPrinterBmp : public psp::PrinterBmp
64 private:
65 BitmapBuffer* mpBmpBuffer;
67 FncGetPixel mpFncGetPixel;
68 Scanline mpScanAccess;
69 sal_PtrDiff mnScanOffset;
71 sal_uInt32 ColorOf (BitmapColor& rColor) const;
72 sal_uInt8 GrayOf (BitmapColor& rColor) const;
74 SalPrinterBmp ();
76 public:
78 SalPrinterBmp (BitmapBuffer* pBitmap);
79 virtual ~SalPrinterBmp ();
80 virtual sal_uInt32 GetPaletteColor (sal_uInt32 nIdx) const;
81 virtual sal_uInt32 GetPaletteEntryCount () const;
82 virtual sal_uInt32 GetPixelRGB (sal_uInt32 nRow, sal_uInt32 nColumn) const;
83 virtual sal_uInt8 GetPixelGray (sal_uInt32 nRow, sal_uInt32 nColumn) const;
84 virtual sal_uInt8 GetPixelIdx (sal_uInt32 nRow, sal_uInt32 nColumn) const;
85 virtual sal_uInt32 GetWidth () const;
86 virtual sal_uInt32 GetHeight() const;
87 virtual sal_uInt32 GetDepth () const;
90 SalPrinterBmp::SalPrinterBmp (BitmapBuffer* pBuffer) :
91 mpBmpBuffer (pBuffer)
93 DBG_ASSERT (mpBmpBuffer, "SalPrinterBmp::SalPrinterBmp () can't acquire Bitmap");
95 // calibrate scanline buffer
96 if( BMP_SCANLINE_ADJUSTMENT( mpBmpBuffer->mnFormat ) == BMP_FORMAT_TOP_DOWN )
98 mpScanAccess = mpBmpBuffer->mpBits;
99 mnScanOffset = mpBmpBuffer->mnScanlineSize;
101 else
103 mpScanAccess = mpBmpBuffer->mpBits
104 + (mpBmpBuffer->mnHeight - 1) * mpBmpBuffer->mnScanlineSize;
105 mnScanOffset = - mpBmpBuffer->mnScanlineSize;
108 // request read access to the pixels
109 switch( BMP_SCANLINE_FORMAT( mpBmpBuffer->mnFormat ) )
111 case BMP_FORMAT_1BIT_MSB_PAL:
112 mpFncGetPixel = BitmapReadAccess::GetPixelFor_1BIT_MSB_PAL; break;
113 case BMP_FORMAT_1BIT_LSB_PAL:
114 mpFncGetPixel = BitmapReadAccess::GetPixelFor_1BIT_LSB_PAL; break;
115 case BMP_FORMAT_4BIT_MSN_PAL:
116 mpFncGetPixel = BitmapReadAccess::GetPixelFor_4BIT_MSN_PAL; break;
117 case BMP_FORMAT_4BIT_LSN_PAL:
118 mpFncGetPixel = BitmapReadAccess::GetPixelFor_4BIT_LSN_PAL; break;
119 case BMP_FORMAT_8BIT_PAL:
120 mpFncGetPixel = BitmapReadAccess::GetPixelFor_8BIT_PAL; break;
121 case BMP_FORMAT_8BIT_TC_MASK:
122 mpFncGetPixel = BitmapReadAccess::GetPixelFor_8BIT_TC_MASK; break;
123 case BMP_FORMAT_16BIT_TC_MSB_MASK:
124 mpFncGetPixel = BitmapReadAccess::GetPixelFor_16BIT_TC_MSB_MASK; break;
125 case BMP_FORMAT_16BIT_TC_LSB_MASK:
126 mpFncGetPixel = BitmapReadAccess::GetPixelFor_16BIT_TC_LSB_MASK; break;
127 case BMP_FORMAT_24BIT_TC_BGR:
128 mpFncGetPixel = BitmapReadAccess::GetPixelFor_24BIT_TC_BGR; break;
129 case BMP_FORMAT_24BIT_TC_RGB:
130 mpFncGetPixel = BitmapReadAccess::GetPixelFor_24BIT_TC_RGB; break;
131 case BMP_FORMAT_24BIT_TC_MASK:
132 mpFncGetPixel = BitmapReadAccess::GetPixelFor_24BIT_TC_MASK; break;
133 case BMP_FORMAT_32BIT_TC_ABGR:
134 mpFncGetPixel = BitmapReadAccess::GetPixelFor_32BIT_TC_ABGR; break;
135 case BMP_FORMAT_32BIT_TC_ARGB:
136 mpFncGetPixel = BitmapReadAccess::GetPixelFor_32BIT_TC_ARGB; break;
137 case BMP_FORMAT_32BIT_TC_BGRA:
138 mpFncGetPixel = BitmapReadAccess::GetPixelFor_32BIT_TC_BGRA; break;
139 case BMP_FORMAT_32BIT_TC_RGBA:
140 mpFncGetPixel = BitmapReadAccess::GetPixelFor_32BIT_TC_RGBA; break;
141 case BMP_FORMAT_32BIT_TC_MASK:
142 mpFncGetPixel = BitmapReadAccess::GetPixelFor_32BIT_TC_MASK; break;
144 default:
145 DBG_ERROR("Error: SalPrinterBmp::SalPrinterBmp() unknown bitmap format");
146 break;
150 SalPrinterBmp::~SalPrinterBmp ()
154 sal_uInt32
155 SalPrinterBmp::GetWidth () const
157 return mpBmpBuffer->mnWidth;
160 sal_uInt32
161 SalPrinterBmp::GetHeight () const
163 return mpBmpBuffer->mnHeight;
166 sal_uInt32
167 SalPrinterBmp::GetDepth () const
169 sal_uInt32 nDepth;
171 switch (mpBmpBuffer->mnBitCount)
173 case 1:
174 nDepth = 1;
175 break;
177 case 4:
178 case 8:
179 nDepth = 8;
180 break;
182 case 16:
183 case 24:
184 case 32:
185 nDepth = 24;
186 break;
188 default:
189 nDepth = 1;
190 DBG_ERROR ("Error: unsupported bitmap depth in SalPrinterBmp::GetDepth()");
191 break;
194 return nDepth;
197 sal_uInt32
198 SalPrinterBmp::ColorOf (BitmapColor& rColor) const
200 if (rColor.IsIndex())
201 return ColorOf (mpBmpBuffer->maPalette[rColor.GetIndex()]);
202 else
203 return ((rColor.GetBlue()) & 0x000000ff)
204 | ((rColor.GetGreen() << 8) & 0x0000ff00)
205 | ((rColor.GetRed() << 16) & 0x00ff0000);
208 sal_uInt8
209 SalPrinterBmp::GrayOf (BitmapColor& rColor) const
211 if (rColor.IsIndex())
212 return GrayOf (mpBmpBuffer->maPalette[rColor.GetIndex()]);
213 else
214 return ( rColor.GetBlue() * 28UL
215 + rColor.GetGreen() * 151UL
216 + rColor.GetRed() * 77UL ) >> 8;
219 sal_uInt32
220 SalPrinterBmp::GetPaletteEntryCount () const
222 return mpBmpBuffer->maPalette.GetEntryCount ();
225 sal_uInt32
226 SalPrinterBmp::GetPaletteColor (sal_uInt32 nIdx) const
228 return ColorOf (mpBmpBuffer->maPalette[nIdx]);
231 sal_uInt32
232 SalPrinterBmp::GetPixelRGB (sal_uInt32 nRow, sal_uInt32 nColumn) const
234 Scanline pScan = mpScanAccess + nRow * mnScanOffset;
235 BitmapColor aColor = mpFncGetPixel (pScan, nColumn, mpBmpBuffer->maColorMask);
237 return ColorOf (aColor);
240 sal_uInt8
241 SalPrinterBmp::GetPixelGray (sal_uInt32 nRow, sal_uInt32 nColumn) const
243 Scanline pScan = mpScanAccess + nRow * mnScanOffset;
244 BitmapColor aColor = mpFncGetPixel (pScan, nColumn, mpBmpBuffer->maColorMask);
246 return GrayOf (aColor);
249 sal_uInt8
250 SalPrinterBmp::GetPixelIdx (sal_uInt32 nRow, sal_uInt32 nColumn) const
252 Scanline pScan = mpScanAccess + nRow * mnScanOffset;
253 BitmapColor aColor = mpFncGetPixel (pScan, nColumn, mpBmpBuffer->maColorMask);
255 if (aColor.IsIndex())
256 return aColor.GetIndex();
257 else
258 return 0;
261 /*******************************************************
262 * PspGraphics *
263 *******************************************************/
265 PspGraphics::~PspGraphics()
267 ReleaseFonts();
270 void PspGraphics::GetResolution( sal_Int32 &rDPIX, sal_Int32 &rDPIY )
272 if (m_pJobData != NULL)
274 int x = m_pJobData->m_aContext.getRenderResolution();
276 rDPIX = x;
277 rDPIY = x;
281 USHORT PspGraphics::GetBitCount()
283 return m_pPrinterGfx->GetBitCount();
286 long PspGraphics::GetGraphicsWidth() const
288 return 0;
291 void PspGraphics::ResetClipRegion()
293 m_pPrinterGfx->ResetClipRegion ();
296 void PspGraphics::BeginSetClipRegion( ULONG n )
298 m_pPrinterGfx->BeginSetClipRegion(n);
301 BOOL PspGraphics::unionClipRegion( long nX, long nY, long nDX, long nDY )
303 return (BOOL)m_pPrinterGfx->UnionClipRegion (nX, nY, nDX, nDY);
306 bool PspGraphics::unionClipRegion( const ::basegfx::B2DPolyPolygon& )
308 // TODO: implement and advertise OutDevSupport_B2DClip support
309 return false;
312 void PspGraphics::EndSetClipRegion()
314 m_pPrinterGfx->EndSetClipRegion ();
317 void PspGraphics::SetLineColor()
319 m_pPrinterGfx->SetLineColor ();
322 void PspGraphics::SetLineColor( SalColor nSalColor )
324 psp::PrinterColor aColor (SALCOLOR_RED (nSalColor),
325 SALCOLOR_GREEN (nSalColor),
326 SALCOLOR_BLUE (nSalColor));
327 m_pPrinterGfx->SetLineColor (aColor);
330 void PspGraphics::SetFillColor()
332 m_pPrinterGfx->SetFillColor ();
335 void PspGraphics::SetFillColor( SalColor nSalColor )
337 psp::PrinterColor aColor (SALCOLOR_RED (nSalColor),
338 SALCOLOR_GREEN (nSalColor),
339 SALCOLOR_BLUE (nSalColor));
340 m_pPrinterGfx->SetFillColor (aColor);
343 void PspGraphics::SetROPLineColor( SalROPColor )
345 DBG_ASSERT( 0, "Error: PrinterGfx::SetROPLineColor() not implemented" );
348 void PspGraphics::SetROPFillColor( SalROPColor )
350 DBG_ASSERT( 0, "Error: PrinterGfx::SetROPFillColor() not implemented" );
353 void PspGraphics::SetXORMode( bool bSet, bool )
355 (void)bSet;
356 DBG_ASSERT( !bSet, "Error: PrinterGfx::SetXORMode() not implemented" );
359 void PspGraphics::drawPixel( long nX, long nY )
361 m_pPrinterGfx->DrawPixel (Point(nX, nY));
364 void PspGraphics::drawPixel( long nX, long nY, SalColor nSalColor )
366 psp::PrinterColor aColor (SALCOLOR_RED (nSalColor),
367 SALCOLOR_GREEN (nSalColor),
368 SALCOLOR_BLUE (nSalColor));
369 m_pPrinterGfx->DrawPixel (Point(nX, nY), aColor);
372 void PspGraphics::drawLine( long nX1, long nY1, long nX2, long nY2 )
374 m_pPrinterGfx->DrawLine (Point(nX1, nY1), Point(nX2, nY2));
377 void PspGraphics::drawRect( long nX, long nY, long nDX, long nDY )
379 m_pPrinterGfx->DrawRect (Rectangle(Point(nX, nY), Size(nDX, nDY)));
382 void PspGraphics::drawPolyLine( ULONG nPoints, const SalPoint *pPtAry )
384 m_pPrinterGfx->DrawPolyLine (nPoints, (Point*)pPtAry);
387 void PspGraphics::drawPolygon( ULONG nPoints, const SalPoint* pPtAry )
389 // Point must be equal to SalPoint! see vcl/inc/salgtype.hxx
390 m_pPrinterGfx->DrawPolygon (nPoints, (Point*)pPtAry);
393 void PspGraphics::drawPolyPolygon( sal_uInt32 nPoly,
394 const sal_uInt32 *pPoints,
395 PCONSTSALPOINT *pPtAry )
397 m_pPrinterGfx->DrawPolyPolygon (nPoly, pPoints, (const Point**)pPtAry);
400 bool PspGraphics::drawPolyPolygon( const ::basegfx::B2DPolyPolygon&, double /*fTransparency*/ )
402 // TODO: implement and advertise OutDevSupport_B2DDraw support
403 return false;
406 bool PspGraphics::drawPolyLine( const basegfx::B2DPolygon&, const basegfx::B2DVector& /*rLineWidths*/, basegfx::B2DLineJoin /*eJoin*/)
408 // TODO: a PS printer can draw B2DPolyLines almost directly
409 return false;
412 sal_Bool PspGraphics::drawPolyLineBezier( ULONG nPoints, const SalPoint* pPtAry, const BYTE* pFlgAry )
414 m_pPrinterGfx->DrawPolyLineBezier (nPoints, (Point*)pPtAry, pFlgAry);
415 return sal_True;
418 sal_Bool PspGraphics::drawPolygonBezier( ULONG nPoints, const SalPoint* pPtAry, const BYTE* pFlgAry )
420 m_pPrinterGfx->DrawPolygonBezier (nPoints, (Point*)pPtAry, pFlgAry);
421 return sal_True;
424 sal_Bool PspGraphics::drawPolyPolygonBezier( sal_uInt32 nPoly,
425 const sal_uInt32* pPoints,
426 const SalPoint* const* pPtAry,
427 const BYTE* const* pFlgAry )
429 // Point must be equal to SalPoint! see vcl/inc/salgtype.hxx
430 m_pPrinterGfx->DrawPolyPolygonBezier (nPoly, pPoints, (Point**)pPtAry, (BYTE**)pFlgAry);
431 return sal_True;
434 void PspGraphics::invert( ULONG,
435 const SalPoint*,
436 SalInvert )
438 DBG_ASSERT( 0, "Error: PrinterGfx::Invert() not implemented" );
440 BOOL PspGraphics::drawEPS( long nX, long nY, long nWidth, long nHeight, void* pPtr, ULONG nSize )
442 return m_pPrinterGfx->DrawEPS( Rectangle( Point( nX, nY ), Size( nWidth, nHeight ) ), pPtr, nSize );
445 void PspGraphics::copyBits( const SalTwoRect*,
446 SalGraphics* )
448 DBG_ERROR( "Error: PrinterGfx::CopyBits() not implemented" );
451 void PspGraphics::copyArea ( long,long,long,long,long,long,USHORT )
453 DBG_ERROR( "Error: PrinterGfx::CopyArea() not implemented" );
456 void PspGraphics::drawBitmap( const SalTwoRect* pPosAry, const SalBitmap& rSalBitmap )
458 Rectangle aSrc (Point(pPosAry->mnSrcX, pPosAry->mnSrcY),
459 Size(pPosAry->mnSrcWidth, pPosAry->mnSrcHeight));
460 Rectangle aDst (Point(pPosAry->mnDestX, pPosAry->mnDestY),
461 Size(pPosAry->mnDestWidth, pPosAry->mnDestHeight));
463 BitmapBuffer* pBuffer= const_cast<SalBitmap&>(rSalBitmap).AcquireBuffer(sal_True);
465 SalPrinterBmp aBmp (pBuffer);
466 m_pPrinterGfx->DrawBitmap (aDst, aSrc, aBmp);
468 const_cast<SalBitmap&>(rSalBitmap).ReleaseBuffer (pBuffer, sal_True);
471 void PspGraphics::drawBitmap( const SalTwoRect*,
472 const SalBitmap&,
473 const SalBitmap& )
475 DBG_ERROR("Error: no PrinterGfx::DrawBitmap() for transparent bitmap");
478 void PspGraphics::drawBitmap( const SalTwoRect*,
479 const SalBitmap&,
480 SalColor )
482 DBG_ERROR("Error: no PrinterGfx::DrawBitmap() for transparent color");
485 void PspGraphics::drawMask( const SalTwoRect*,
486 const SalBitmap &,
487 SalColor )
489 DBG_ERROR("Error: PrinterGfx::DrawMask() not implemented");
492 SalBitmap* PspGraphics::getBitmap( long, long, long, long )
494 DBG_WARNING ("Warning: PrinterGfx::GetBitmap() not implemented");
495 return NULL;
498 SalColor PspGraphics::getPixel( long, long )
500 DBG_ERROR ("Warning: PrinterGfx::GetPixel() not implemented");
501 return 0;
504 void PspGraphics::invert(long,long,long,long,SalInvert)
506 DBG_ERROR ("Warning: PrinterGfx::Invert() not implemented");
509 //==========================================================================
511 class ImplPspFontData : public ImplFontData
513 private:
514 enum { PSPFD_MAGIC = 0xb5bf01f0 };
515 sal_IntPtr mnFontId;
517 public:
518 ImplPspFontData( const psp::FastPrintFontInfo& );
519 virtual sal_IntPtr GetFontId() const { return mnFontId; }
520 virtual ImplFontData* Clone() const { return new ImplPspFontData( *this ); }
521 virtual ImplFontEntry* CreateFontInstance( ImplFontSelectData& ) const;
522 static bool CheckFontData( const ImplFontData& r ) { return r.CheckMagic( PSPFD_MAGIC ); }
525 //--------------------------------------------------------------------------
527 ImplPspFontData::ImplPspFontData( const psp::FastPrintFontInfo& rInfo )
528 : ImplFontData( PspGraphics::Info2DevFontAttributes(rInfo), PSPFD_MAGIC ),
529 mnFontId( rInfo.m_nID )
532 //--------------------------------------------------------------------------
534 ImplFontEntry* ImplPspFontData::CreateFontInstance( ImplFontSelectData& rFSD ) const
536 ImplServerFontEntry* pEntry = new ImplServerFontEntry( rFSD );
537 return pEntry;
540 //==========================================================================
542 class PspFontLayout : public GenericSalLayout
544 public:
545 PspFontLayout( ::psp::PrinterGfx& );
546 virtual bool LayoutText( ImplLayoutArgs& );
547 virtual void InitFont() const;
548 virtual void DrawText( SalGraphics& ) const;
549 private:
550 ::psp::PrinterGfx& mrPrinterGfx;
551 sal_IntPtr mnFontID;
552 int mnFontHeight;
553 int mnFontWidth;
554 bool mbVertical;
555 bool mbArtItalic;
556 bool mbArtBold;
559 //--------------------------------------------------------------------------
561 PspFontLayout::PspFontLayout( ::psp::PrinterGfx& rGfx )
562 : mrPrinterGfx( rGfx )
564 mnFontID = mrPrinterGfx.GetFontID();
565 mnFontHeight = mrPrinterGfx.GetFontHeight();
566 mnFontWidth = mrPrinterGfx.GetFontWidth();
567 mbVertical = mrPrinterGfx.GetFontVertical();
568 mbArtItalic = mrPrinterGfx.GetArtificialItalic();
569 mbArtBold = mrPrinterGfx.GetArtificialBold();
572 //--------------------------------------------------------------------------
574 bool PspFontLayout::LayoutText( ImplLayoutArgs& rArgs )
576 mbVertical = ((rArgs.mnFlags & SAL_LAYOUT_VERTICAL) != 0);
578 long nUnitsPerPixel = 1;
579 int nOldGlyphId = -1;
580 long nGlyphWidth = 0;
581 int nCharPos = -1;
582 Point aNewPos( 0, 0 );
583 GlyphItem aPrevItem;
584 rtl_TextEncoding aFontEnc = mrPrinterGfx.GetFontMgr().getFontEncoding( mnFontID );
585 for(;;)
587 bool bRightToLeft;
588 if( !rArgs.GetNextPos( &nCharPos, &bRightToLeft ) )
589 break;
591 sal_Unicode cChar = rArgs.mpStr[ nCharPos ];
592 if( bRightToLeft )
593 cChar = GetMirroredChar( cChar );
594 // symbol font aliasing: 0x0020-0x00ff -> 0xf020 -> 0xf0ff
595 if( aFontEnc == RTL_TEXTENCODING_SYMBOL )
596 if( cChar < 256 )
597 cChar += 0xf000;
598 int nGlyphIndex = cChar; // printer glyphs = unicode
600 // update fallback_runs if needed
601 psp::CharacterMetric aMetric;
602 mrPrinterGfx.GetFontMgr().getMetrics( mnFontID, cChar, cChar, &aMetric, mbVertical );
603 if( aMetric.width == -1 && aMetric.height == -1 )
604 rArgs.NeedFallback( nCharPos, bRightToLeft );
606 // apply pair kerning to prev glyph if requested
607 if( SAL_LAYOUT_KERNING_PAIRS & rArgs.mnFlags )
609 if( nOldGlyphId > 0 )
611 const std::list< KernPair >& rKernPairs = mrPrinterGfx.getKernPairs(mbVertical);
612 for( std::list< KernPair >::const_iterator it = rKernPairs.begin();
613 it != rKernPairs.end(); ++it )
615 if( it->first == nOldGlyphId && it->second == nGlyphIndex )
617 int nTextScale = mrPrinterGfx.GetFontWidth();
618 if( ! nTextScale )
619 nTextScale = mrPrinterGfx.GetFontHeight();
620 int nKern = (mbVertical ? it->kern_y : it->kern_x) * nTextScale;
621 nGlyphWidth += nKern;
622 aPrevItem.mnNewWidth = nGlyphWidth;
623 break;
629 // finish previous glyph
630 if( nOldGlyphId >= 0 )
631 AppendGlyph( aPrevItem );
632 nOldGlyphId = nGlyphIndex;
633 aNewPos.X() += nGlyphWidth;
635 // prepare GlyphItem for appending it in next round
636 nUnitsPerPixel = mrPrinterGfx.GetCharWidth( cChar, cChar, &nGlyphWidth );
637 int nGlyphFlags = bRightToLeft ? GlyphItem::IS_RTL_GLYPH : 0;
638 nGlyphIndex |= GF_ISCHAR;
639 aPrevItem = GlyphItem( nCharPos, nGlyphIndex, aNewPos, nGlyphFlags, nGlyphWidth );
642 // append last glyph item if any
643 if( nOldGlyphId >= 0 )
644 AppendGlyph( aPrevItem );
646 SetOrientation( mrPrinterGfx.GetFontAngle() );
647 SetUnitsPerPixel( nUnitsPerPixel );
648 return (nOldGlyphId >= 0);
651 class PspServerFontLayout : public ServerFontLayout
653 public:
654 PspServerFontLayout( psp::PrinterGfx&, ServerFont& rFont, const ImplLayoutArgs& rArgs );
656 virtual void InitFont() const;
657 const sal_Unicode* getTextPtr() const { return maText.getStr() - mnMinCharPos; }
658 int getMinCharPos() const { return mnMinCharPos; }
659 int getMaxCharPos() const { return mnMinCharPos+maText.getLength()-1; }
660 private:
661 ::psp::PrinterGfx& mrPrinterGfx;
662 sal_IntPtr mnFontID;
663 int mnFontHeight;
664 int mnFontWidth;
665 bool mbVertical;
666 bool mbArtItalic;
667 bool mbArtBold;
668 rtl::OUString maText;
669 int mnMinCharPos;
672 PspServerFontLayout::PspServerFontLayout( ::psp::PrinterGfx& rGfx, ServerFont& rFont, const ImplLayoutArgs& rArgs )
673 : ServerFontLayout( rFont ),
674 mrPrinterGfx( rGfx )
676 mnFontID = mrPrinterGfx.GetFontID();
677 mnFontHeight = mrPrinterGfx.GetFontHeight();
678 mnFontWidth = mrPrinterGfx.GetFontWidth();
679 mbVertical = mrPrinterGfx.GetFontVertical();
680 mbArtItalic = mrPrinterGfx.GetArtificialItalic();
681 mbArtBold = mrPrinterGfx.GetArtificialBold();
682 maText = OUString( rArgs.mpStr + rArgs.mnMinCharPos, rArgs.mnEndCharPos - rArgs.mnMinCharPos+1 );
683 mnMinCharPos = rArgs.mnMinCharPos;
686 void PspServerFontLayout::InitFont() const
688 mrPrinterGfx.SetFont( mnFontID, mnFontHeight, mnFontWidth,
689 mnOrientation, mbVertical, mbArtItalic, mbArtBold );
692 //--------------------------------------------------------------------------
694 static void DrawPrinterLayout( const SalLayout& rLayout, ::psp::PrinterGfx& rGfx, bool bIsPspServerFontLayout )
696 const int nMaxGlyphs = 200;
697 sal_GlyphId aGlyphAry[ nMaxGlyphs ];
698 sal_Int32 aWidthAry[ nMaxGlyphs ];
699 sal_Int32 aIdxAry [ nMaxGlyphs ];
700 sal_Unicode aUnicodes[ nMaxGlyphs ];
701 int aCharPosAry [ nMaxGlyphs ];
703 Point aPos;
704 long nUnitsPerPixel = rLayout.GetUnitsPerPixel();
705 const sal_Unicode* pText = NULL;
706 int nMinCharPos = 0;
707 int nMaxCharPos = 0;
708 if (bIsPspServerFontLayout)
710 const PspServerFontLayout * pPspLayout = dynamic_cast<const PspServerFontLayout*>(&rLayout);
711 #ifdef ENABLE_GRAPHITE
712 const GraphiteServerFontLayout * pGrLayout = dynamic_cast<const GraphiteServerFontLayout*>(&rLayout);
713 #endif
714 if (pPspLayout)
716 pText = pPspLayout->getTextPtr();
717 nMinCharPos = pPspLayout->getMinCharPos();
718 nMaxCharPos = pPspLayout->getMaxCharPos();
720 #ifdef ENABLE_GRAPHITE
721 else if (pGrLayout)
723 pText = pGrLayout->getTextPtr();
724 nMinCharPos = pGrLayout->getMinCharPos();
725 nMaxCharPos = pGrLayout->getMaxCharPos();
727 #endif
729 for( int nStart = 0;; )
731 int nGlyphCount = rLayout.GetNextGlyphs( nMaxGlyphs, aGlyphAry, aPos, nStart, aWidthAry, bIsPspServerFontLayout ? aCharPosAry : NULL );
732 if( !nGlyphCount )
733 break;
735 sal_Int32 nXOffset = 0;
736 for( int i = 0; i < nGlyphCount; ++i )
738 nXOffset += aWidthAry[ i ];
739 aIdxAry[ i ] = nXOffset / nUnitsPerPixel;
740 sal_Int32 nGlyphIdx = aGlyphAry[i] & (GF_IDXMASK | GF_ROTMASK);
741 if( bIsPspServerFontLayout )
742 aUnicodes[i] = (aCharPosAry[i] >= nMinCharPos && aCharPosAry[i] <= nMaxCharPos) ? pText[ aCharPosAry[i] ] : 0;
743 else
744 aUnicodes[i] = (aGlyphAry[i] & GF_ISCHAR) ? nGlyphIdx : 0;
745 aGlyphAry[i] = nGlyphIdx;
748 rGfx.DrawGlyphs( aPos, (sal_uInt32 *)aGlyphAry, aUnicodes, nGlyphCount, aIdxAry );
752 //--------------------------------------------------------------------------
754 void PspFontLayout::InitFont() const
756 mrPrinterGfx.SetFont( mnFontID, mnFontHeight, mnFontWidth,
757 mnOrientation, mbVertical, mbArtItalic, mbArtBold );
760 //--------------------------------------------------------------------------
762 void PspFontLayout::DrawText( SalGraphics& ) const
764 DrawPrinterLayout( *this, mrPrinterGfx, false );
767 void PspGraphics::DrawServerFontLayout( const ServerFontLayout& rLayout )
769 // print complex text
770 DrawPrinterLayout( rLayout, *m_pPrinterGfx, true );
773 ImplFontCharMap* PspGraphics::GetImplFontCharMap() const
775 // TODO: get ImplFontCharMap directly from fonts
776 if( !m_pServerFont[0] )
777 return NULL;
779 CmapResult aCmapResult;
780 if( !m_pServerFont[0]->GetFontCodeRanges( aCmapResult ) )
781 return NULL;
782 return new ImplFontCharMap( aCmapResult );
785 USHORT PspGraphics::SetFont( ImplFontSelectData *pEntry, int nFallbackLevel )
787 // release all fonts that are to be overridden
788 for( int i = nFallbackLevel; i < MAX_FALLBACK; ++i )
790 if( m_pServerFont[i] != NULL )
792 // old server side font is no longer referenced
793 GlyphCache::GetInstance().UncacheFont( *m_pServerFont[i] );
794 m_pServerFont[i] = NULL;
798 // return early if there is no new font
799 if( !pEntry )
800 return 0;
802 sal_IntPtr nID = pEntry->mpFontData ? pEntry->mpFontData->GetFontId() : 0;
804 // determine which font attributes need to be emulated
805 bool bArtItalic = false;
806 bool bArtBold = false;
807 if( pEntry->meItalic == ITALIC_OBLIQUE || pEntry->meItalic == ITALIC_NORMAL )
809 psp::italic::type eItalic = m_pPrinterGfx->GetFontMgr().getFontItalic( nID );
810 if( eItalic != psp::italic::Italic && eItalic != psp::italic::Oblique )
811 bArtItalic = true;
813 int nWeight = (int)pEntry->meWeight;
814 int nRealWeight = (int)m_pPrinterGfx->GetFontMgr().getFontWeight( nID );
815 if( nRealWeight <= (int)psp::weight::Medium && nWeight > (int)WEIGHT_MEDIUM )
817 bArtBold = true;
820 // also set the serverside font for layouting
821 m_bFontVertical = pEntry->mbVertical;
822 if( pEntry->mpFontData )
824 // requesting a font provided by builtin rasterizer
825 ServerFont* pServerFont = GlyphCache::GetInstance().CacheFont( *pEntry );
826 if( pServerFont != NULL )
828 if( pServerFont->TestFont() )
829 m_pServerFont[ nFallbackLevel ] = pServerFont;
830 else
831 GlyphCache::GetInstance().UncacheFont( *pServerFont );
835 // set the printer font
836 return m_pPrinterGfx->SetFont( nID,
837 pEntry->mnHeight,
838 pEntry->mnWidth,
839 pEntry->mnOrientation,
840 pEntry->mbVertical,
841 bArtItalic,
842 bArtBold
846 void PspGraphics::SetTextColor( SalColor nSalColor )
848 psp::PrinterColor aColor (SALCOLOR_RED (nSalColor),
849 SALCOLOR_GREEN (nSalColor),
850 SALCOLOR_BLUE (nSalColor));
851 m_pPrinterGfx->SetTextColor (aColor);
854 bool PspGraphics::AddTempDevFont( ImplDevFontList*, const String&,const String& )
856 return false;
859 void RegisterFontSubstitutors( ImplDevFontList* );
861 void PspGraphics::GetDevFontList( ImplDevFontList *pList )
863 ::std::list< psp::fontID > aList;
864 psp::PrintFontManager& rMgr = psp::PrintFontManager::get();
865 rMgr.getFontList( aList, m_pJobData->m_pParser, m_pInfoPrinter->m_bCompatMetrics );
867 ::std::list< psp::fontID >::iterator it;
868 psp::FastPrintFontInfo aInfo;
869 for (it = aList.begin(); it != aList.end(); ++it)
870 if (rMgr.getFontFastInfo (*it, aInfo))
871 AnnounceFonts( pList, aInfo );
873 // register platform specific font substitutions if available
874 if( rMgr.hasFontconfig() )
875 RegisterFontSubstitutors( pList );
878 void PspGraphics::GetDevFontSubstList( OutputDevice* pOutDev )
880 const psp::PrinterInfo& rInfo = psp::PrinterInfoManager::get().getPrinterInfo( m_pJobData->m_aPrinterName );
881 if( rInfo.m_bPerformFontSubstitution )
883 for( std::hash_map< rtl::OUString, rtl::OUString, rtl::OUStringHash >::const_iterator it = rInfo.m_aFontSubstitutes.begin(); it != rInfo.m_aFontSubstitutes.end(); ++it )
884 pOutDev->ImplAddDevFontSubstitute( it->first, it->second, FONT_SUBSTITUTE_ALWAYS );
888 void PspGraphics::GetFontMetric( ImplFontMetricData *pMetric )
890 const psp::PrintFontManager& rMgr = psp::PrintFontManager::get();
891 psp::PrintFontInfo aInfo;
893 if (rMgr.getFontInfo (m_pPrinterGfx->GetFontID(), aInfo))
895 ImplDevFontAttributes aDFA = Info2DevFontAttributes( aInfo );
896 static_cast<ImplFontAttributes&>(*pMetric) = aDFA;
897 pMetric->mbDevice = aDFA.mbDevice;
898 pMetric->mbScalableFont = true;
900 pMetric->mnOrientation = m_pPrinterGfx->GetFontAngle();
901 pMetric->mnSlant = 0;
903 sal_Int32 nTextHeight = m_pPrinterGfx->GetFontHeight();
904 sal_Int32 nTextWidth = m_pPrinterGfx->GetFontWidth();
905 if( ! nTextWidth )
906 nTextWidth = nTextHeight;
908 pMetric->mnWidth = nTextWidth;
909 pMetric->mnAscent = ( aInfo.m_nAscend * nTextHeight + 500 ) / 1000;
910 pMetric->mnDescent = ( aInfo.m_nDescend * nTextHeight + 500 ) / 1000;
911 pMetric->mnIntLeading = ( aInfo.m_nLeading * nTextHeight + 500 ) / 1000;
912 pMetric->mnExtLeading = 0;
916 ULONG PspGraphics::GetKernPairs( ULONG nPairs, ImplKernPairData *pKernPairs )
918 const ::std::list< ::psp::KernPair >& rPairs( m_pPrinterGfx->getKernPairs() );
919 ULONG nHavePairs = rPairs.size();
920 if( pKernPairs && nPairs )
922 ::std::list< ::psp::KernPair >::const_iterator it;
923 unsigned int i;
924 int nTextScale = m_pPrinterGfx->GetFontWidth();
925 if( ! nTextScale )
926 nTextScale = m_pPrinterGfx->GetFontHeight();
927 for( i = 0, it = rPairs.begin(); i < nPairs && i < nHavePairs; i++, ++it )
929 pKernPairs[i].mnChar1 = it->first;
930 pKernPairs[i].mnChar2 = it->second;
931 pKernPairs[i].mnKern = it->kern_x * nTextScale / 1000;
935 return nHavePairs;
938 BOOL PspGraphics::GetGlyphBoundRect( long nGlyphIndex, Rectangle& rRect )
940 int nLevel = nGlyphIndex >> GF_FONTSHIFT;
941 if( nLevel >= MAX_FALLBACK )
942 return FALSE;
944 ServerFont* pSF = m_pServerFont[ nLevel ];
945 if( !pSF )
946 return FALSE;
948 nGlyphIndex &= ~GF_FONTMASK;
949 const GlyphMetric& rGM = pSF->GetGlyphMetric( nGlyphIndex );
950 rRect = Rectangle( rGM.GetOffset(), rGM.GetSize() );
951 return TRUE;
954 BOOL PspGraphics::GetGlyphOutline( long nGlyphIndex,
955 ::basegfx::B2DPolyPolygon& rB2DPolyPoly )
957 int nLevel = nGlyphIndex >> GF_FONTSHIFT;
958 if( nLevel >= MAX_FALLBACK )
959 return FALSE;
961 ServerFont* pSF = m_pServerFont[ nLevel ];
962 if( !pSF )
963 return FALSE;
965 nGlyphIndex &= ~GF_FONTMASK;
966 if( pSF->GetGlyphOutline( nGlyphIndex, rB2DPolyPoly ) )
967 return TRUE;
969 return FALSE;
972 SalLayout* PspGraphics::GetTextLayout( ImplLayoutArgs& rArgs, int nFallbackLevel )
974 // workaround for printers not handling glyph indexing for non-TT fonts
975 int nFontId = m_pPrinterGfx->GetFontID();
976 if( psp::fonttype::TrueType != psp::PrintFontManager::get().getFontType( nFontId ) )
977 rArgs.mnFlags |= SAL_LAYOUT_DISABLE_GLYPH_PROCESSING;
978 else if( nFallbackLevel > 0 )
979 rArgs.mnFlags &= ~SAL_LAYOUT_DISABLE_GLYPH_PROCESSING;
981 GenericSalLayout* pLayout = NULL;
983 if( m_pServerFont[ nFallbackLevel ]
984 && !(rArgs.mnFlags & SAL_LAYOUT_DISABLE_GLYPH_PROCESSING) )
986 #ifdef ENABLE_GRAPHITE
987 // Is this a Graphite font?
988 if (GraphiteFontAdaptor::IsGraphiteEnabledFont(*m_pServerFont[nFallbackLevel]))
990 sal_Int32 xdpi, ydpi;
991 GetResolution(xdpi, ydpi);
992 GraphiteFontAdaptor * pGrfont = new GraphiteFontAdaptor( *m_pServerFont[nFallbackLevel], xdpi, ydpi);
993 if (!pGrfont) return NULL;
994 pLayout = new GraphiteServerFontLayout(pGrfont);
996 else
997 #endif
998 pLayout = new PspServerFontLayout( *m_pPrinterGfx, *m_pServerFont[nFallbackLevel], rArgs );
1000 else
1001 pLayout = new PspFontLayout( *m_pPrinterGfx );
1003 return pLayout;
1006 //--------------------------------------------------------------------------
1008 BOOL PspGraphics::CreateFontSubset(
1009 const rtl::OUString& rToFile,
1010 const ImplFontData* pFont,
1011 sal_Int32* pGlyphIDs,
1012 sal_uInt8* pEncoding,
1013 sal_Int32* pWidths,
1014 int nGlyphCount,
1015 FontSubsetInfo& rInfo
1018 // in this context the pFont->GetFontId() is a valid PSP
1019 // font since they are the only ones left after the PDF
1020 // export has filtered its list of subsettable fonts (for
1021 // which this method was created). The correct way would
1022 // be to have the GlyphCache search for the ImplFontData pFont
1023 psp::fontID aFont = pFont->GetFontId();
1025 psp::PrintFontManager& rMgr = psp::PrintFontManager::get();
1026 bool bSuccess = rMgr.createFontSubset( rInfo,
1027 aFont,
1028 rToFile,
1029 pGlyphIDs,
1030 pEncoding,
1031 pWidths,
1032 nGlyphCount );
1033 return bSuccess;
1036 //--------------------------------------------------------------------------
1038 const void* PspGraphics::GetEmbedFontData( const ImplFontData* pFont, const sal_Ucs* pUnicodes, sal_Int32* pWidths, FontSubsetInfo& rInfo, long* pDataLen )
1040 // in this context the pFont->GetFontId() is a valid PSP
1041 // font since they are the only ones left after the PDF
1042 // export has filtered its list of subsettable fonts (for
1043 // which this method was created). The correct way would
1044 // be to have the GlyphCache search for the ImplFontData pFont
1045 psp::fontID aFont = pFont->GetFontId();
1046 return PspGraphics::DoGetEmbedFontData( aFont, pUnicodes, pWidths, rInfo, pDataLen );
1049 //--------------------------------------------------------------------------
1051 void PspGraphics::FreeEmbedFontData( const void* pData, long nLen )
1053 PspGraphics::DoFreeEmbedFontData( pData, nLen );
1056 //--------------------------------------------------------------------------
1058 const Ucs2SIntMap* PspGraphics::GetFontEncodingVector( const ImplFontData* pFont, const Ucs2OStrMap** pNonEncoded )
1060 // in this context the pFont->GetFontId() is a valid PSP
1061 // font since they are the only ones left after the PDF
1062 // export has filtered its list of subsettable fonts (for
1063 // which this method was created). The correct way would
1064 // be to have the GlyphCache search for the ImplFontData pFont
1065 psp::fontID aFont = pFont->GetFontId();
1066 return PspGraphics::DoGetFontEncodingVector( aFont, pNonEncoded );
1069 //--------------------------------------------------------------------------
1071 void PspGraphics::GetGlyphWidths( const ImplFontData* pFont,
1072 bool bVertical,
1073 Int32Vector& rWidths,
1074 Ucs2UIntMap& rUnicodeEnc )
1076 // in this context the pFont->GetFontId() is a valid PSP
1077 // font since they are the only ones left after the PDF
1078 // export has filtered its list of subsettable fonts (for
1079 // which this method was created). The correct way would
1080 // be to have the GlyphCache search for the ImplFontData pFont
1081 psp::fontID aFont = pFont->GetFontId();
1082 PspGraphics::DoGetGlyphWidths( aFont, bVertical, rWidths, rUnicodeEnc );
1086 // static helpers of PspGraphics
1088 const void* PspGraphics::DoGetEmbedFontData( fontID aFont, const sal_Ucs* pUnicodes, sal_Int32* pWidths, FontSubsetInfo& rInfo, long* pDataLen )
1090 psp::PrintFontManager& rMgr = psp::PrintFontManager::get();
1092 psp::PrintFontInfo aFontInfo;
1093 if( ! rMgr.getFontInfo( aFont, aFontInfo ) )
1094 return NULL;
1096 // fill in font info
1097 switch( aFontInfo.m_eType )
1099 case psp::fonttype::TrueType: rInfo.m_nFontType = FontSubsetInfo::SFNT_TTF; break;
1100 case psp::fonttype::Type1: rInfo.m_nFontType = FontSubsetInfo::ANY_TYPE1; break;
1101 default:
1102 return NULL;
1104 rInfo.m_nAscent = aFontInfo.m_nAscend;
1105 rInfo.m_nDescent = aFontInfo.m_nDescend;
1106 rInfo.m_aPSName = rMgr.getPSName( aFont );
1108 int xMin, yMin, xMax, yMax;
1109 rMgr.getFontBoundingBox( aFont, xMin, yMin, xMax, yMax );
1111 psp::CharacterMetric aMetrics[256];
1112 sal_Ucs aUnicodes[256];
1113 if( aFontInfo.m_aEncoding == RTL_TEXTENCODING_SYMBOL && aFontInfo.m_eType == psp::fonttype::Type1 )
1115 for( int i = 0; i < 256; i++ )
1116 aUnicodes[i] = pUnicodes[i] < 0x0100 ? pUnicodes[i] + 0xf000 : pUnicodes[i];
1117 pUnicodes = aUnicodes;
1119 if( ! rMgr.getMetrics( aFont, pUnicodes, 256, aMetrics ) )
1120 return NULL;
1122 OString aSysPath = rMgr.getFontFileSysPath( aFont );
1123 struct stat aStat;
1124 if( stat( aSysPath.getStr(), &aStat ) )
1125 return NULL;
1126 int fd = open( aSysPath.getStr(), O_RDONLY );
1127 if( fd < 0 )
1128 return NULL;
1129 void* pFile = mmap( NULL, aStat.st_size, PROT_READ, MAP_SHARED, fd, 0 );
1130 close( fd );
1131 if( pFile == MAP_FAILED )
1132 return NULL;
1134 *pDataLen = aStat.st_size;
1136 rInfo.m_aFontBBox = Rectangle( Point( xMin, yMin ), Size( xMax-xMin, yMax-yMin ) );
1137 rInfo.m_nCapHeight = yMax; // Well ...
1139 for( int i = 0; i < 256; i++ )
1141 pWidths[i] = (aMetrics[i].width > 0 ? aMetrics[i].width : 0);
1143 return pFile;
1146 void PspGraphics::DoFreeEmbedFontData( const void* pData, long nLen )
1148 if( pData )
1149 munmap( (char*)pData, nLen );
1152 const Ucs2SIntMap* PspGraphics::DoGetFontEncodingVector( fontID aFont, const Ucs2OStrMap** pNonEncoded )
1154 psp::PrintFontManager& rMgr = psp::PrintFontManager::get();
1156 psp::PrintFontInfo aFontInfo;
1157 if( ! rMgr.getFontInfo( aFont, aFontInfo ) )
1159 if( pNonEncoded )
1160 *pNonEncoded = NULL;
1161 return NULL;
1164 return rMgr.getEncodingMap( aFont, pNonEncoded );
1167 void PspGraphics::DoGetGlyphWidths( psp::fontID aFont,
1168 bool bVertical,
1169 Int32Vector& rWidths,
1170 Ucs2UIntMap& rUnicodeEnc )
1172 psp::PrintFontManager& rMgr = psp::PrintFontManager::get();
1173 rMgr.getGlyphWidths( aFont, bVertical, rWidths, rUnicodeEnc );
1175 // ----------------------------------------------------------------------------
1177 FontWidth PspGraphics::ToFontWidth (psp::width::type eWidth)
1179 switch (eWidth)
1181 case psp::width::UltraCondensed: return WIDTH_ULTRA_CONDENSED;
1182 case psp::width::ExtraCondensed: return WIDTH_EXTRA_CONDENSED;
1183 case psp::width::Condensed: return WIDTH_CONDENSED;
1184 case psp::width::SemiCondensed: return WIDTH_SEMI_CONDENSED;
1185 case psp::width::Normal: return WIDTH_NORMAL;
1186 case psp::width::SemiExpanded: return WIDTH_SEMI_EXPANDED;
1187 case psp::width::Expanded: return WIDTH_EXPANDED;
1188 case psp::width::ExtraExpanded: return WIDTH_EXTRA_EXPANDED;
1189 case psp::width::UltraExpanded: return WIDTH_ULTRA_EXPANDED;
1190 case psp::width::Unknown: return WIDTH_DONTKNOW;
1191 default:
1192 DBG_ERROR( "unknown width mapping" );
1193 break;
1195 return WIDTH_DONTKNOW;
1198 FontWeight PspGraphics::ToFontWeight (psp::weight::type eWeight)
1200 switch (eWeight)
1202 case psp::weight::Thin: return WEIGHT_THIN;
1203 case psp::weight::UltraLight: return WEIGHT_ULTRALIGHT;
1204 case psp::weight::Light: return WEIGHT_LIGHT;
1205 case psp::weight::SemiLight: return WEIGHT_SEMILIGHT;
1206 case psp::weight::Normal: return WEIGHT_NORMAL;
1207 case psp::weight::Medium: return WEIGHT_MEDIUM;
1208 case psp::weight::SemiBold: return WEIGHT_SEMIBOLD;
1209 case psp::weight::Bold: return WEIGHT_BOLD;
1210 case psp::weight::UltraBold: return WEIGHT_ULTRABOLD;
1211 case psp::weight::Black: return WEIGHT_BLACK;
1212 case psp::weight::Unknown: return WEIGHT_DONTKNOW;
1213 default:
1214 DBG_ERROR( "unknown weight mapping" );
1215 break;
1217 return WEIGHT_DONTKNOW;
1220 FontPitch PspGraphics::ToFontPitch (psp::pitch::type ePitch)
1222 switch (ePitch)
1224 case psp::pitch::Fixed: return PITCH_FIXED;
1225 case psp::pitch::Variable: return PITCH_VARIABLE;
1226 case psp::pitch::Unknown: return PITCH_DONTKNOW;
1227 default:
1228 DBG_ERROR( "unknown pitch mapping" );
1229 break;
1231 return PITCH_DONTKNOW;
1234 FontItalic PspGraphics::ToFontItalic (psp::italic::type eItalic)
1236 switch (eItalic)
1238 case psp::italic::Upright: return ITALIC_NONE;
1239 case psp::italic::Oblique: return ITALIC_OBLIQUE;
1240 case psp::italic::Italic: return ITALIC_NORMAL;
1241 case psp::italic::Unknown: return ITALIC_DONTKNOW;
1242 default:
1243 DBG_ERROR( "unknown italic mapping" );
1244 break;
1246 return ITALIC_DONTKNOW;
1249 FontFamily PspGraphics::ToFontFamily (psp::family::type eFamily)
1251 switch (eFamily)
1253 case psp::family::Decorative: return FAMILY_DECORATIVE;
1254 case psp::family::Modern: return FAMILY_MODERN;
1255 case psp::family::Roman: return FAMILY_ROMAN;
1256 case psp::family::Script: return FAMILY_SCRIPT;
1257 case psp::family::Swiss: return FAMILY_SWISS;
1258 case psp::family::System: return FAMILY_SYSTEM;
1259 case psp::family::Unknown: return FAMILY_DONTKNOW;
1260 default:
1261 DBG_ERROR( "unknown family mapping" );
1262 break;
1264 return FAMILY_DONTKNOW;
1267 ImplDevFontAttributes PspGraphics::Info2DevFontAttributes( const psp::FastPrintFontInfo& rInfo )
1269 ImplDevFontAttributes aDFA;
1270 aDFA.maName = rInfo.m_aFamilyName;
1271 aDFA.maStyleName = rInfo.m_aStyleName;
1272 aDFA.meFamily = ToFontFamily (rInfo.m_eFamilyStyle);
1273 aDFA.meWeight = ToFontWeight (rInfo.m_eWeight);
1274 aDFA.meItalic = ToFontItalic (rInfo.m_eItalic);
1275 aDFA.meWidthType = ToFontWidth (rInfo.m_eWidth);
1276 aDFA.mePitch = ToFontPitch (rInfo.m_ePitch);
1277 aDFA.mbSymbolFlag = (rInfo.m_aEncoding == RTL_TEXTENCODING_SYMBOL);
1278 aDFA.mbSubsettable = rInfo.m_bSubsettable;
1279 aDFA.mbEmbeddable = rInfo.m_bEmbeddable;
1281 switch (rInfo.m_eEmbeddedbitmap)
1283 default:
1284 aDFA.meEmbeddedBitmap = EMBEDDEDBITMAP_DONTKNOW;
1285 break;
1286 case psp::fcstatus::istrue:
1287 aDFA.meEmbeddedBitmap = EMBEDDEDBITMAP_TRUE;
1288 break;
1289 case psp::fcstatus::isfalse:
1290 aDFA.meEmbeddedBitmap = EMBEDDEDBITMAP_FALSE;
1291 break;
1294 switch (rInfo.m_eAntialias)
1296 default:
1297 aDFA.meAntiAlias = ANTIALIAS_DONTKNOW;
1298 break;
1299 case psp::fcstatus::istrue:
1300 aDFA.meAntiAlias = ANTIALIAS_TRUE;
1301 break;
1302 case psp::fcstatus::isfalse:
1303 aDFA.meAntiAlias = ANTIALIAS_FALSE;
1304 break;
1307 switch( rInfo.m_eType )
1309 case psp::fonttype::Builtin:
1310 aDFA.mnQuality = 1024;
1311 aDFA.mbDevice = true;
1312 break;
1313 case psp::fonttype::TrueType:
1314 aDFA.mnQuality = 512;
1315 aDFA.mbDevice = false;
1316 break;
1317 case psp::fonttype::Type1:
1318 aDFA.mnQuality = 0;
1319 aDFA.mbDevice = false;
1320 break;
1321 default:
1322 aDFA.mnQuality = 0;
1323 aDFA.mbDevice = false;
1324 break;
1327 aDFA.mbOrientation = true;
1329 // add font family name aliases
1330 ::std::list< OUString >::const_iterator it = rInfo.m_aAliases.begin();
1331 bool bHasMapNames = false;
1332 for(; it != rInfo.m_aAliases.end(); ++it )
1334 if( bHasMapNames )
1335 aDFA.maMapNames.Append( ';' );
1336 aDFA.maMapNames.Append( (*it).getStr() );
1337 bHasMapNames = true;
1340 #if OSL_DEBUG_LEVEL > 2
1341 if( bHasMapNames )
1343 ByteString aOrigName( aDFA.maName, osl_getThreadTextEncoding() );
1344 ByteString aAliasNames( aDFA.maMapNames, osl_getThreadTextEncoding() );
1345 fprintf( stderr, "using alias names \"%s\" for font family \"%s\"\n",
1346 aAliasNames.GetBuffer(), aOrigName.GetBuffer() );
1348 #endif
1350 return aDFA;
1353 // -----------------------------------------------------------------------
1355 void PspGraphics::AnnounceFonts( ImplDevFontList* pFontList, const psp::FastPrintFontInfo& aInfo )
1357 int nQuality = 0;
1359 if( aInfo.m_eType == psp::fonttype::TrueType )
1361 // asian type 1 fonts are not known
1362 psp::PrintFontManager& rMgr = psp::PrintFontManager::get();
1363 ByteString aFileName( rMgr.getFontFileSysPath( aInfo.m_nID ) );
1364 int nPos = aFileName.SearchBackward( '_' );
1365 if( nPos == STRING_NOTFOUND || aFileName.GetChar( nPos+1 ) == '.' )
1366 nQuality += 5;
1367 else
1369 static const char* pLangBoost = NULL;
1370 static bool bOnce = true;
1371 if( bOnce )
1373 bOnce = false;
1374 const LanguageType aLang = Application::GetSettings().GetUILanguage();
1375 switch( aLang )
1377 case LANGUAGE_JAPANESE:
1378 pLangBoost = "jan";
1379 break;
1380 case LANGUAGE_CHINESE:
1381 case LANGUAGE_CHINESE_SIMPLIFIED:
1382 case LANGUAGE_CHINESE_SINGAPORE:
1383 pLangBoost = "zhs";
1384 break;
1385 case LANGUAGE_CHINESE_TRADITIONAL:
1386 case LANGUAGE_CHINESE_HONGKONG:
1387 case LANGUAGE_CHINESE_MACAU:
1388 pLangBoost = "zht";
1389 break;
1390 case LANGUAGE_KOREAN:
1391 case LANGUAGE_KOREAN_JOHAB:
1392 pLangBoost = "kor";
1393 break;
1397 if( pLangBoost )
1398 if( aFileName.Copy( nPos+1, 3 ).EqualsIgnoreCaseAscii( pLangBoost ) )
1399 nQuality += 10;
1403 ImplPspFontData* pFD = new ImplPspFontData( aInfo );
1404 pFD->mnQuality += nQuality;
1405 pFontList->Add( pFD );
1408 bool PspGraphics::filterText( const String& rOrig, String& rNewText, xub_StrLen nIndex, xub_StrLen& rLen, xub_StrLen& rCutStart, xub_StrLen& rCutStop )
1410 if( ! m_pPhoneNr )
1411 return false;
1413 rCutStop = rCutStart = STRING_NOTFOUND;
1415 #define FAX_PHONE_TOKEN "@@#"
1416 #define FAX_PHONE_TOKEN_LENGTH 3
1417 #define FAX_END_TOKEN "@@"
1418 #define FAX_END_TOKEN_LENGTH 2
1420 bool bRet = false;
1421 bool bStarted = false;
1422 bool bStopped = false;
1423 USHORT nPos;
1424 USHORT nStart = 0;
1425 USHORT nStop = rLen;
1426 String aPhone = rOrig.Copy( nIndex, rLen );
1428 if( ! m_bPhoneCollectionActive )
1430 if( ( nPos = aPhone.SearchAscii( FAX_PHONE_TOKEN ) ) != STRING_NOTFOUND )
1432 nStart = nPos;
1433 m_bPhoneCollectionActive = true;
1434 m_aPhoneCollection.Erase();
1435 bRet = true;
1436 bStarted = true;
1439 if( m_bPhoneCollectionActive )
1441 bRet = true;
1442 nPos = bStarted ? nStart + FAX_PHONE_TOKEN_LENGTH : 0;
1443 if( ( nPos = aPhone.SearchAscii( FAX_END_TOKEN, nPos ) ) != STRING_NOTFOUND )
1445 m_bPhoneCollectionActive = false;
1446 nStop = nPos + FAX_END_TOKEN_LENGTH;
1447 bStopped = true;
1449 int nTokenStart = nStart + (bStarted ? FAX_PHONE_TOKEN_LENGTH : 0);
1450 int nTokenStop = nStop - (bStopped ? FAX_END_TOKEN_LENGTH : 0);
1451 m_aPhoneCollection += aPhone.Copy( nTokenStart, nTokenStop - nTokenStart );
1452 if( ! m_bPhoneCollectionActive )
1454 m_pPhoneNr->AppendAscii( "<Fax#>" );
1455 m_pPhoneNr->Append( m_aPhoneCollection );
1456 m_pPhoneNr->AppendAscii( "</Fax#>" );
1457 m_aPhoneCollection.Erase();
1460 if( m_aPhoneCollection.Len() > 1024 )
1462 m_bPhoneCollectionActive = false;
1463 m_aPhoneCollection.Erase();
1464 bRet = false;
1467 if( bRet && m_bSwallowFaxNo )
1469 rLen -= nStop - nStart;
1470 rCutStart = nStart+nIndex;
1471 rCutStop = nStop+nIndex;
1472 if( rCutStart )
1473 rNewText = rOrig.Copy( 0, rCutStart );
1474 rNewText += rOrig.Copy( rCutStop );
1477 return bRet && m_bSwallowFaxNo;
1480 bool PspGraphics::drawAlphaBitmap( const SalTwoRect&,
1481 const SalBitmap&,
1482 const SalBitmap& )
1484 return false;
1487 bool PspGraphics::drawAlphaRect( long, long, long, long, sal_uInt8 )
1489 return false;
1492 SystemGraphicsData PspGraphics::GetGraphicsData() const
1494 SystemGraphicsData aRes;
1495 aRes.nSize = sizeof(aRes);
1496 aRes.hDrawable = 0;
1497 aRes.pRenderFormat = 0;
1498 return aRes;
1501 SystemFontData PspGraphics::GetSysFontData( int nFallbacklevel ) const
1503 SystemFontData aSysFontData;
1505 if (nFallbacklevel >= MAX_FALLBACK) nFallbacklevel = MAX_FALLBACK - 1;
1506 if (nFallbacklevel < 0 ) nFallbacklevel = 0;
1508 aSysFontData.nSize = sizeof( SystemFontData );
1509 aSysFontData.nFontId = 0;
1510 aSysFontData.nFontFlags = 0;
1511 aSysFontData.bFakeBold = false;
1512 aSysFontData.bFakeItalic = false;
1513 aSysFontData.bAntialias = true;
1514 return aSysFontData;
1517 bool PspGraphics::supportsOperation( OutDevSupportType ) const
1519 return false;