Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*
3 : * This file is part of the LibreOffice project.
4 : *
5 : * This Source Code Form is subject to the terms of the Mozilla Public
6 : * License, v. 2.0. If a copy of the MPL was not distributed with this
7 : * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 : *
9 : * This file incorporates work covered by the following license notice:
10 : *
11 : * Licensed to the Apache Software Foundation (ASF) under one or more
12 : * contributor license agreements. See the NOTICE file distributed
13 : * with this work for additional information regarding copyright
14 : * ownership. The ASF licenses this file to you under the Apache
15 : * License, Version 2.0 (the "License"); you may not use this file
16 : * except in compliance with the License. You may obtain a copy of
17 : * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 : */
19 :
20 : #include <list>
21 :
22 : #include <tools/debug.hxx>
23 : #include <tools/resary.hxx>
24 : #include <tools/stream.hxx>
25 : #include <tools/vcompat.hxx>
26 : #include <tools/helpers.hxx>
27 :
28 : #include <vcl/unohelp.hxx>
29 : #include <vcl/svapp.hxx>
30 : #include <vcl/wrkwin.hxx>
31 : #include <vcl/virdev.hxx>
32 : #include <vcl/window.hxx>
33 : #include <vcl/gdimtf.hxx>
34 : #include <vcl/metaact.hxx>
35 : #include <vcl/print.hxx>
36 :
37 : #include <salinst.hxx>
38 : #include <salvd.hxx>
39 : #include <salgdi.hxx>
40 : #include <salptype.hxx>
41 : #include <salprn.hxx>
42 : #include <svdata.hxx>
43 : #include <svids.hrc>
44 : #include <jobset.h>
45 : #include <outdev.h>
46 : #include "PhysicalFontCollection.hxx"
47 : #include <print.h>
48 :
49 : #include <comphelper/processfactory.hxx>
50 :
51 : #include "com/sun/star/beans/XPropertySet.hpp"
52 : #include "com/sun/star/configuration/theDefaultProvider.hpp"
53 : #include "com/sun/star/container/XNameAccess.hpp"
54 : #include "com/sun/star/lang/XMultiServiceFactory.hpp"
55 :
56 : using namespace com::sun::star::uno;
57 : using namespace com::sun::star::lang;
58 : using namespace com::sun::star::beans;
59 : using namespace com::sun::star::container;
60 : using namespace com::sun::star::configuration;
61 :
62 : int nImplSysDialog = 0;
63 :
64 : namespace
65 : {
66 0 : static Paper ImplGetPaperFormat( long nWidth100thMM, long nHeight100thMM )
67 : {
68 0 : PaperInfo aInfo(nWidth100thMM, nHeight100thMM);
69 0 : aInfo.doSloppyFit();
70 0 : return aInfo.getPaper();
71 : }
72 :
73 0 : static const PaperInfo& ImplGetEmptyPaper()
74 : {
75 0 : static PaperInfo aInfo(PAPER_USER);
76 0 : return aInfo;
77 : }
78 : }
79 :
80 780 : void ImplUpdateJobSetupPaper( JobSetup& rJobSetup )
81 : {
82 780 : const ImplJobSetup* pConstData = rJobSetup.ImplGetConstData();
83 :
84 780 : if ( !pConstData->mnPaperWidth || !pConstData->mnPaperHeight )
85 : {
86 780 : if ( pConstData->mePaperFormat != PAPER_USER )
87 : {
88 780 : ImplJobSetup* pData = rJobSetup.ImplGetData();
89 780 : PaperInfo aInfo(pConstData->mePaperFormat);
90 780 : pData->mnPaperWidth = aInfo.getWidth();
91 780 : pData->mnPaperHeight = aInfo.getHeight();
92 780 : }
93 : }
94 0 : else if ( pConstData->mePaperFormat == PAPER_USER )
95 : {
96 0 : Paper ePaper = ImplGetPaperFormat( pConstData->mnPaperWidth, pConstData->mnPaperHeight );
97 0 : if ( ePaper != PAPER_USER )
98 0 : rJobSetup.ImplGetData()->mePaperFormat = ePaper;
99 : }
100 780 : }
101 :
102 : // PrinterOptions
103 680 : PrinterOptions::PrinterOptions() :
104 : mbReduceTransparency( false ),
105 : meReducedTransparencyMode( PRINTER_TRANSPARENCY_AUTO ),
106 : mbReduceGradients( false ),
107 : meReducedGradientsMode( PRINTER_GRADIENT_STRIPES ),
108 : mnReducedGradientStepCount( 64 ),
109 : mbReduceBitmaps( false ),
110 : meReducedBitmapMode( PRINTER_BITMAP_NORMAL ),
111 : mnReducedBitmapResolution( 200 ),
112 : mbReducedBitmapsIncludeTransparency( true ),
113 : mbConvertToGreyscales( false ),
114 680 : mbPDFAsStandardPrintJobFormat( false )
115 : {
116 680 : }
117 :
118 677 : PrinterOptions::~PrinterOptions()
119 : {
120 677 : }
121 :
122 : #define PROPERTYNAME_REDUCETRANSPARENCY OUString("ReduceTransparency")
123 : #define PROPERTYNAME_REDUCEDTRANSPARENCYMODE OUString("ReducedTransparencyMode")
124 : #define PROPERTYNAME_REDUCEGRADIENTS OUString("ReduceGradients")
125 : #define PROPERTYNAME_REDUCEDGRADIENTMODE OUString("ReducedGradientMode")
126 : #define PROPERTYNAME_REDUCEDGRADIENTSTEPCOUNT OUString("ReducedGradientStepCount")
127 : #define PROPERTYNAME_REDUCEBITMAPS OUString("ReduceBitmaps")
128 : #define PROPERTYNAME_REDUCEDBITMAPMODE OUString("ReducedBitmapMode")
129 : #define PROPERTYNAME_REDUCEDBITMAPRESOLUTION OUString("ReducedBitmapResolution")
130 : #define PROPERTYNAME_REDUCEDBITMAPINCLUDESTRANSPARENCY OUString("ReducedBitmapIncludesTransparency")
131 : #define PROPERTYNAME_CONVERTTOGREYSCALES OUString("ConvertToGreyscales")
132 : #define PROPERTYNAME_PDFASSTANDARDPRINTJOBFORMAT OUString("PDFAsStandardPrintJobFormat")
133 :
134 0 : bool PrinterOptions::ReadFromConfig( bool i_bFile )
135 : {
136 0 : bool bSuccess = false;
137 : // save old state in case something goes wrong
138 0 : PrinterOptions aOldValues( *this );
139 :
140 : // get the configuration service
141 0 : Reference< XMultiServiceFactory > xConfigProvider;
142 0 : Reference< XNameAccess > xConfigAccess;
143 : try
144 : {
145 : // get service provider
146 0 : Reference< XComponentContext > xContext( comphelper::getProcessComponentContext() );
147 : // create configuration hierachical access name
148 : try
149 : {
150 0 : xConfigProvider = theDefaultProvider::get( xContext );
151 :
152 0 : Sequence< Any > aArgs(1);
153 0 : PropertyValue aVal;
154 0 : aVal.Name = "nodepath";
155 0 : if( i_bFile )
156 0 : aVal.Value <<= OUString( "/org.openoffice.Office.Common/Print/Option/File" );
157 : else
158 0 : aVal.Value <<= OUString( "/org.openoffice.Office.Common/Print/Option/Printer" );
159 0 : aArgs.getArray()[0] <<= aVal;
160 0 : xConfigAccess = Reference< XNameAccess >(
161 0 : xConfigProvider->createInstanceWithArguments(
162 0 : OUString( "com.sun.star.configuration.ConfigurationAccess" ), aArgs ),
163 0 : UNO_QUERY );
164 0 : if( xConfigAccess.is() )
165 : {
166 0 : Reference< XPropertySet > xSet( xConfigAccess, UNO_QUERY );
167 0 : if( xSet.is() )
168 : {
169 0 : sal_Int32 nValue = 0;
170 0 : bool bValue = false;
171 0 : if( xSet->getPropertyValue(PROPERTYNAME_REDUCETRANSPARENCY) >>= bValue )
172 0 : SetReduceTransparency( bValue );
173 0 : if( xSet->getPropertyValue(PROPERTYNAME_REDUCEDTRANSPARENCYMODE) >>= nValue )
174 0 : SetReducedTransparencyMode( (PrinterTransparencyMode)nValue );
175 0 : if( xSet->getPropertyValue(PROPERTYNAME_REDUCEGRADIENTS) >>= bValue )
176 0 : SetReduceGradients( bValue );
177 0 : if( xSet->getPropertyValue(PROPERTYNAME_REDUCEDGRADIENTMODE) >>= nValue )
178 0 : SetReducedGradientMode( (PrinterGradientMode)nValue );
179 0 : if( xSet->getPropertyValue(PROPERTYNAME_REDUCEDGRADIENTSTEPCOUNT) >>= nValue )
180 0 : SetReducedGradientStepCount( (sal_uInt16)nValue );
181 0 : if( xSet->getPropertyValue(PROPERTYNAME_REDUCEBITMAPS) >>= bValue )
182 0 : SetReduceBitmaps( bValue );
183 0 : if( xSet->getPropertyValue(PROPERTYNAME_REDUCEDBITMAPMODE) >>= nValue )
184 0 : SetReducedBitmapMode( (PrinterBitmapMode)nValue );
185 0 : if( xSet->getPropertyValue(PROPERTYNAME_REDUCEDBITMAPRESOLUTION) >>= nValue )
186 0 : SetReducedBitmapResolution( (sal_uInt16)nValue );
187 0 : if( xSet->getPropertyValue(PROPERTYNAME_REDUCEDBITMAPINCLUDESTRANSPARENCY) >>= bValue )
188 0 : SetReducedBitmapIncludesTransparency( bValue );
189 0 : if( xSet->getPropertyValue(PROPERTYNAME_CONVERTTOGREYSCALES) >>= bValue )
190 0 : SetConvertToGreyscales( bValue );
191 0 : if( xSet->getPropertyValue(PROPERTYNAME_PDFASSTANDARDPRINTJOBFORMAT) >>= bValue )
192 0 : SetPDFAsStandardPrintJobFormat( bValue );
193 :
194 0 : bSuccess = true;
195 0 : }
196 0 : }
197 : }
198 0 : catch( const Exception& )
199 : {
200 0 : }
201 : }
202 0 : catch( const WrappedTargetException& )
203 : {
204 : }
205 :
206 0 : if( ! bSuccess )
207 0 : *this = aOldValues;
208 0 : return bSuccess;
209 : }
210 :
211 0 : bool Printer::DrawTransformBitmapExDirect(
212 : const basegfx::B2DHomMatrix& /*aFullTransform*/,
213 : const BitmapEx& /*rBitmapEx*/)
214 : {
215 : // printers can't draw bitmaps directly
216 0 : return false;
217 : }
218 :
219 0 : bool Printer::TransformAndReduceBitmapExToTargetRange(
220 : const basegfx::B2DHomMatrix& /*aFullTransform*/,
221 : basegfx::B2DRange& /*aVisibleRange*/,
222 : double& /*fMaximumArea*/)
223 : {
224 : // deliberately do nothing - you can't reduce the
225 : // target range for a printer at all
226 0 : return true;
227 : }
228 :
229 0 : void Printer::DrawDeviceBitmap( const Point& rDestPt, const Size& rDestSize,
230 : const Point& rSrcPtPixel, const Size& rSrcSizePixel,
231 : BitmapEx& rBmpEx )
232 : {
233 0 : if( rBmpEx.IsAlpha() )
234 : {
235 : // #107169# For true alpha bitmaps, no longer masking the
236 : // bitmap, but perform a full alpha blend against a white
237 : // background here.
238 0 : Bitmap aBmp( rBmpEx.GetBitmap() );
239 0 : aBmp.Blend( rBmpEx.GetAlpha(), Color( COL_WHITE) );
240 0 : DrawBitmap( rDestPt, rDestSize, rSrcPtPixel, rSrcSizePixel, aBmp );
241 : }
242 : else
243 : {
244 0 : Bitmap aBmp( rBmpEx.GetBitmap() ), aMask( rBmpEx.GetMask() );
245 0 : aBmp.Replace( aMask, Color( COL_WHITE ) );
246 0 : ImplPrintTransparent( aBmp, aMask, rDestPt, rDestSize, rSrcPtPixel, rSrcSizePixel );
247 : }
248 0 : }
249 :
250 0 : void Printer::EmulateDrawTransparent ( const tools::PolyPolygon& rPolyPoly,
251 : sal_uInt16 nTransparencePercent )
252 : {
253 : // #110958# Disable alpha VDev, we perform the necessary
254 0 : VirtualDevice* pOldAlphaVDev = mpAlphaVDev;
255 :
256 : // operation explicitly further below.
257 0 : if( mpAlphaVDev )
258 0 : mpAlphaVDev = NULL;
259 :
260 0 : GDIMetaFile* pOldMetaFile = mpMetaFile;
261 0 : mpMetaFile = NULL;
262 :
263 0 : mpMetaFile = pOldMetaFile;
264 :
265 : // #110958# Restore disabled alpha VDev
266 0 : mpAlphaVDev = pOldAlphaVDev;
267 :
268 0 : Rectangle aPolyRect( LogicToPixel( rPolyPoly ).GetBoundRect() );
269 0 : const Size aDPISize( LogicToPixel( Size( 1, 1 ), MAP_INCH ) );
270 0 : const long nBaseExtent = std::max( FRound( aDPISize.Width() / 300. ), 1L );
271 : long nMove;
272 : const sal_uInt16 nTrans = ( nTransparencePercent < 13 ) ? 0 :
273 : ( nTransparencePercent < 38 ) ? 25 :
274 : ( nTransparencePercent < 63 ) ? 50 :
275 0 : ( nTransparencePercent < 88 ) ? 75 : 100;
276 :
277 0 : switch( nTrans )
278 : {
279 0 : case( 25 ): nMove = nBaseExtent * 3; break;
280 0 : case( 50 ): nMove = nBaseExtent * 4; break;
281 0 : case( 75 ): nMove = nBaseExtent * 6; break;
282 :
283 : // #i112959# very transparent (88 < nTransparencePercent <= 99)
284 0 : case( 100 ): nMove = nBaseExtent * 8; break;
285 :
286 : // #i112959# not transparent (nTransparencePercent < 13)
287 0 : default: nMove = 0; break;
288 : }
289 :
290 0 : Push( PushFlags::CLIPREGION | PushFlags::LINECOLOR );
291 0 : IntersectClipRegion(vcl::Region(rPolyPoly));
292 0 : SetLineColor( GetFillColor() );
293 0 : const bool bOldMap = mbMap;
294 0 : EnableMapMode( false );
295 :
296 0 : if(nMove)
297 : {
298 0 : Rectangle aRect( aPolyRect.TopLeft(), Size( aPolyRect.GetWidth(), nBaseExtent ) );
299 0 : while( aRect.Top() <= aPolyRect.Bottom() )
300 : {
301 0 : DrawRect( aRect );
302 0 : aRect.Move( 0, nMove );
303 : }
304 :
305 0 : aRect = Rectangle( aPolyRect.TopLeft(), Size( nBaseExtent, aPolyRect.GetHeight() ) );
306 0 : while( aRect.Left() <= aPolyRect.Right() )
307 : {
308 0 : DrawRect( aRect );
309 0 : aRect.Move( nMove, 0 );
310 : }
311 : }
312 : else
313 : {
314 : // #i112959# if not transparent, draw full rectangle in clip region
315 0 : DrawRect( aPolyRect );
316 : }
317 :
318 0 : EnableMapMode( bOldMap );
319 0 : Pop();
320 :
321 0 : mpMetaFile = pOldMetaFile;
322 :
323 : // #110958# Restore disabled alpha VDev
324 0 : mpAlphaVDev = pOldAlphaVDev;
325 0 : }
326 :
327 0 : void Printer::DrawOutDev( const Point& /*rDestPt*/, const Size& /*rDestSize*/,
328 : const Point& /*rSrcPt*/, const Size& /*rSrcSize*/ )
329 : {
330 : DBG_ASSERT( false, "Don't use OutputDevice::DrawOutDev(...) with printer devices!" );
331 0 : }
332 :
333 0 : void Printer::DrawOutDev( const Point& /*rDestPt*/, const Size& /*rDestSize*/,
334 : const Point& /*rSrcPt*/, const Size& /*rSrcSize*/,
335 : const OutputDevice& /*rOutDev*/ )
336 : {
337 : DBG_ASSERT( false, "Don't use OutputDevice::DrawOutDev(...) with printer devices!" );
338 0 : }
339 :
340 0 : void Printer::CopyArea( const Point& /*rDestPt*/,
341 : const Point& /*rSrcPt*/, const Size& /*rSrcSize*/,
342 : sal_uInt16 /*nFlags*/ )
343 : {
344 : DBG_ASSERT( false, "Don't use OutputDevice::CopyArea(...) with printer devices!" );
345 0 : }
346 :
347 0 : void Printer::SetPrinterOptions( const PrinterOptions& i_rOptions )
348 : {
349 0 : *mpPrinterOptions = i_rOptions;
350 0 : }
351 :
352 0 : bool Printer::HasMirroredGraphics() const
353 : {
354 : // due to a "hotfix" for AOO bug i55719, this needs to return false
355 0 : return false;
356 : }
357 :
358 : // QueueInfo
359 0 : QueueInfo::QueueInfo()
360 : {
361 0 : mnStatus = 0;
362 0 : mnJobs = 0;
363 0 : }
364 :
365 0 : QueueInfo::QueueInfo( const QueueInfo& rInfo ) :
366 : maPrinterName( rInfo.maPrinterName ),
367 : maDriver( rInfo.maDriver ),
368 : maLocation( rInfo.maLocation ),
369 : maComment( rInfo.maComment ),
370 : mnStatus( rInfo.mnStatus ),
371 0 : mnJobs( rInfo.mnJobs )
372 : {
373 0 : }
374 :
375 0 : QueueInfo::~QueueInfo()
376 : {
377 0 : }
378 :
379 0 : bool QueueInfo::operator==( const QueueInfo& rInfo ) const
380 : {
381 : return
382 0 : maPrinterName == rInfo.maPrinterName &&
383 0 : maDriver == rInfo.maDriver &&
384 0 : maLocation == rInfo.maLocation &&
385 0 : maComment == rInfo.maComment &&
386 0 : mnStatus == rInfo.mnStatus &&
387 0 : mnJobs == rInfo.mnJobs;
388 : }
389 :
390 0 : SvStream& WriteQueueInfo( SvStream& rOStream, const QueueInfo& rInfo )
391 : {
392 0 : VersionCompat aCompat( rOStream, STREAM_WRITE, 1 );
393 :
394 0 : write_uInt16_lenPrefixed_uInt8s_FromOUString(rOStream, rInfo.maPrinterName, RTL_TEXTENCODING_UTF8);
395 0 : write_uInt16_lenPrefixed_uInt8s_FromOUString(rOStream, rInfo.maDriver, RTL_TEXTENCODING_UTF8);
396 0 : write_uInt16_lenPrefixed_uInt8s_FromOUString(rOStream, rInfo.maLocation, RTL_TEXTENCODING_UTF8);
397 0 : write_uInt16_lenPrefixed_uInt8s_FromOUString(rOStream, rInfo.maComment, RTL_TEXTENCODING_UTF8);
398 0 : rOStream.WriteUInt32( rInfo.mnStatus );
399 0 : rOStream.WriteUInt32( rInfo.mnJobs );
400 :
401 0 : return rOStream;
402 : }
403 :
404 0 : SvStream& ReadQueueInfo( SvStream& rIStream, QueueInfo& rInfo )
405 : {
406 0 : VersionCompat aCompat( rIStream, STREAM_READ );
407 :
408 0 : rInfo.maPrinterName = read_uInt16_lenPrefixed_uInt8s_ToOUString(rIStream, RTL_TEXTENCODING_UTF8);
409 0 : rInfo.maDriver = read_uInt16_lenPrefixed_uInt8s_ToOUString(rIStream, RTL_TEXTENCODING_UTF8);
410 0 : rInfo.maLocation = read_uInt16_lenPrefixed_uInt8s_ToOUString(rIStream, RTL_TEXTENCODING_UTF8);
411 0 : rInfo.maComment = read_uInt16_lenPrefixed_uInt8s_ToOUString(rIStream, RTL_TEXTENCODING_UTF8);
412 0 : rIStream.ReadUInt32( rInfo.mnStatus );
413 0 : rIStream.ReadUInt32( rInfo.mnJobs );
414 :
415 0 : return rIStream;
416 : }
417 :
418 74 : SalPrinterQueueInfo::SalPrinterQueueInfo()
419 : {
420 74 : mnStatus = 0;
421 74 : mnJobs = QUEUE_JOBS_DONTKNOW;
422 74 : mpSysData = NULL;
423 74 : }
424 :
425 72 : SalPrinterQueueInfo::~SalPrinterQueueInfo()
426 : {
427 72 : }
428 :
429 144 : ImplPrnQueueList::~ImplPrnQueueList()
430 : {
431 72 : ImplSVData* pSVData = ImplGetSVData();
432 144 : for( unsigned int i = 0; i < m_aQueueInfos.size(); i++ )
433 : {
434 72 : delete m_aQueueInfos[i].mpQueueInfo;
435 72 : pSVData->mpDefInst->DeletePrinterQueueInfo( m_aQueueInfos[i].mpSalQueueInfo );
436 : }
437 72 : }
438 :
439 74 : void ImplPrnQueueList::Add( SalPrinterQueueInfo* pData )
440 : {
441 : boost::unordered_map< OUString, sal_Int32, OUStringHash >::iterator it =
442 74 : m_aNameToIndex.find( pData->maPrinterName );
443 74 : if( it == m_aNameToIndex.end() )
444 : {
445 74 : m_aNameToIndex[ pData->maPrinterName ] = m_aQueueInfos.size();
446 74 : m_aQueueInfos.push_back( ImplPrnQueueData() );
447 74 : m_aQueueInfos.back().mpQueueInfo = NULL;
448 74 : m_aQueueInfos.back().mpSalQueueInfo = pData;
449 74 : m_aPrinterList.push_back( pData->maPrinterName );
450 : }
451 : else // this should not happen, but ...
452 : {
453 0 : ImplPrnQueueData& rData = m_aQueueInfos[ it->second ];
454 0 : delete rData.mpQueueInfo;
455 0 : rData.mpQueueInfo = NULL;
456 0 : ImplGetSVData()->mpDefInst->DeletePrinterQueueInfo( rData.mpSalQueueInfo );
457 0 : rData.mpSalQueueInfo = pData;
458 : }
459 74 : }
460 :
461 794 : ImplPrnQueueData* ImplPrnQueueList::Get( const OUString& rPrinter )
462 : {
463 794 : ImplPrnQueueData* pData = NULL;
464 : boost::unordered_map<OUString,sal_Int32,OUStringHash>::iterator it =
465 794 : m_aNameToIndex.find( rPrinter );
466 794 : if( it != m_aNameToIndex.end() )
467 680 : pData = &m_aQueueInfos[it->second];
468 794 : return pData;
469 : }
470 :
471 74 : static void ImplInitPrnQueueList()
472 : {
473 74 : ImplSVData* pSVData = ImplGetSVData();
474 :
475 74 : pSVData->maGDIData.mpPrinterQueueList = new ImplPrnQueueList;
476 :
477 74 : static const char* pEnv = getenv( "SAL_DISABLE_PRINTERLIST" );
478 74 : if( !pEnv || !*pEnv )
479 74 : pSVData->mpDefInst->GetPrinterQueueInfo( pSVData->maGDIData.mpPrinterQueueList );
480 74 : }
481 :
482 367 : void ImplDeletePrnQueueList()
483 : {
484 367 : ImplSVData* pSVData = ImplGetSVData();
485 367 : ImplPrnQueueList* pPrnList = pSVData->maGDIData.mpPrinterQueueList;
486 :
487 367 : if ( pPrnList )
488 : {
489 72 : delete pPrnList;
490 72 : pSVData->maGDIData.mpPrinterQueueList = NULL;
491 : }
492 367 : }
493 :
494 0 : const std::vector<OUString>& Printer::GetPrinterQueues()
495 : {
496 0 : ImplSVData* pSVData = ImplGetSVData();
497 0 : if ( !pSVData->maGDIData.mpPrinterQueueList )
498 0 : ImplInitPrnQueueList();
499 0 : return pSVData->maGDIData.mpPrinterQueueList->m_aPrinterList;
500 : }
501 :
502 0 : const QueueInfo* Printer::GetQueueInfo( const OUString& rPrinterName, bool bStatusUpdate )
503 : {
504 0 : ImplSVData* pSVData = ImplGetSVData();
505 :
506 0 : if ( !pSVData->maGDIData.mpPrinterQueueList )
507 0 : ImplInitPrnQueueList();
508 :
509 0 : if ( !pSVData->maGDIData.mpPrinterQueueList )
510 0 : return NULL;
511 :
512 0 : ImplPrnQueueData* pInfo = pSVData->maGDIData.mpPrinterQueueList->Get( rPrinterName );
513 0 : if( pInfo )
514 : {
515 0 : if( !pInfo->mpQueueInfo || bStatusUpdate )
516 0 : pSVData->mpDefInst->GetPrinterQueueState( pInfo->mpSalQueueInfo );
517 :
518 0 : if ( !pInfo->mpQueueInfo )
519 0 : pInfo->mpQueueInfo = new QueueInfo;
520 :
521 0 : pInfo->mpQueueInfo->maPrinterName = pInfo->mpSalQueueInfo->maPrinterName;
522 0 : pInfo->mpQueueInfo->maDriver = pInfo->mpSalQueueInfo->maDriver;
523 0 : pInfo->mpQueueInfo->maLocation = pInfo->mpSalQueueInfo->maLocation;
524 0 : pInfo->mpQueueInfo->maComment = pInfo->mpSalQueueInfo->maComment;
525 0 : pInfo->mpQueueInfo->mnStatus = pInfo->mpSalQueueInfo->mnStatus;
526 0 : pInfo->mpQueueInfo->mnJobs = pInfo->mpSalQueueInfo->mnJobs;
527 0 : return pInfo->mpQueueInfo;
528 : }
529 0 : return NULL;
530 : }
531 :
532 2052 : OUString Printer::GetDefaultPrinterName()
533 : {
534 2052 : static const char* pEnv = getenv( "SAL_DISABLE_DEFAULTPRINTER" );
535 2052 : if( !pEnv || !*pEnv )
536 : {
537 2052 : ImplSVData* pSVData = ImplGetSVData();
538 :
539 2052 : return pSVData->mpDefInst->GetDefaultPrinter();
540 : }
541 0 : return OUString();
542 : }
543 :
544 680 : void Printer::ImplInitData()
545 : {
546 680 : mbDevOutput = false;
547 680 : meOutDevType = OUTDEV_PRINTER;
548 680 : mbDefPrinter = false;
549 680 : mnError = 0;
550 680 : mnCurPage = 0;
551 680 : mnCurPrintPage = 0;
552 680 : mnPageQueueSize = 0;
553 680 : mnCopyCount = 1;
554 680 : mbCollateCopy = false;
555 680 : mbPrinting = false;
556 680 : mbJobActive = false;
557 680 : mbPrintFile = false;
558 680 : mbInPrintPage = false;
559 680 : mbNewJobSetup = false;
560 680 : mpInfoPrinter = NULL;
561 680 : mpPrinter = NULL;
562 680 : mpDisplayDev = NULL;
563 680 : mbIsQueuePrinter = false;
564 680 : mpPrinterOptions = new PrinterOptions;
565 :
566 : // Add printer to the list
567 680 : ImplSVData* pSVData = ImplGetSVData();
568 680 : mpNext = pSVData->maGDIData.mpFirstPrinter;
569 680 : mpPrev = NULL;
570 680 : if ( mpNext )
571 244 : mpNext->mpPrev = this;
572 : else
573 436 : pSVData->maGDIData.mpLastPrinter = this;
574 680 : pSVData->maGDIData.mpFirstPrinter = this;
575 680 : }
576 :
577 1760 : bool Printer::AcquireGraphics() const
578 : {
579 : DBG_TESTSOLARMUTEX();
580 :
581 1760 : if ( mpGraphics )
582 980 : return true;
583 :
584 780 : mbInitLineColor = true;
585 780 : mbInitFillColor = true;
586 780 : mbInitFont = true;
587 780 : mbInitTextColor = true;
588 780 : mbInitClipRegion = true;
589 :
590 780 : ImplSVData* pSVData = ImplGetSVData();
591 :
592 780 : if ( mpJobGraphics )
593 0 : mpGraphics = mpJobGraphics;
594 780 : else if ( mpDisplayDev )
595 : {
596 0 : const VirtualDevice* pVirDev = mpDisplayDev;
597 0 : mpGraphics = pVirDev->mpVirDev->AcquireGraphics();
598 : // if needed retry after releasing least recently used virtual device graphics
599 0 : while ( !mpGraphics )
600 : {
601 0 : if ( !pSVData->maGDIData.mpLastVirGraphics )
602 0 : break;
603 0 : pSVData->maGDIData.mpLastVirGraphics->ReleaseGraphics();
604 0 : mpGraphics = pVirDev->mpVirDev->AcquireGraphics();
605 : }
606 : // update global LRU list of virtual device graphics
607 0 : if ( mpGraphics )
608 : {
609 0 : mpNextGraphics = pSVData->maGDIData.mpFirstVirGraphics;
610 0 : pSVData->maGDIData.mpFirstVirGraphics = const_cast<Printer*>(this);
611 0 : if ( mpNextGraphics )
612 0 : mpNextGraphics->mpPrevGraphics = const_cast<Printer*>(this);
613 0 : if ( !pSVData->maGDIData.mpLastVirGraphics )
614 0 : pSVData->maGDIData.mpLastVirGraphics = const_cast<Printer*>(this);
615 : }
616 : }
617 : else
618 : {
619 780 : mpGraphics = mpInfoPrinter->AcquireGraphics();
620 : // if needed retry after releasing least recently used printer graphics
621 1560 : while ( !mpGraphics )
622 : {
623 0 : if ( !pSVData->maGDIData.mpLastPrnGraphics )
624 0 : break;
625 0 : pSVData->maGDIData.mpLastPrnGraphics->ReleaseGraphics();
626 0 : mpGraphics = mpInfoPrinter->AcquireGraphics();
627 : }
628 : // update global LRU list of printer graphics
629 780 : if ( mpGraphics )
630 : {
631 780 : mpNextGraphics = pSVData->maGDIData.mpFirstPrnGraphics;
632 780 : pSVData->maGDIData.mpFirstPrnGraphics = const_cast<Printer*>(this);
633 780 : if ( mpNextGraphics )
634 274 : mpNextGraphics->mpPrevGraphics = const_cast<Printer*>(this);
635 780 : if ( !pSVData->maGDIData.mpLastPrnGraphics )
636 506 : pSVData->maGDIData.mpLastPrnGraphics = const_cast<Printer*>(this);
637 : }
638 : }
639 :
640 780 : if ( mpGraphics )
641 : {
642 780 : mpGraphics->SetXORMode( (ROP_INVERT == meRasterOp) || (ROP_XOR == meRasterOp), ROP_INVERT == meRasterOp );
643 780 : mpGraphics->setAntiAliasB2DDraw(mnAntialiasing & ANTIALIASING_ENABLE_B2DDRAW);
644 : }
645 :
646 780 : return mpGraphics ? true : false;
647 : }
648 :
649 777 : void Printer::ImplReleaseFonts()
650 : {
651 : #ifdef UNX
652 : // HACK to fix an urgent P1 printing issue fast
653 : // WinSalPrinter does not respect GetGraphics/ReleaseGraphics conventions
654 : // so Printer::mpGraphics often points to a dead WinSalGraphics
655 : // TODO: fix WinSalPrinter's GetGraphics/ReleaseGraphics handling
656 777 : mpGraphics->ReleaseFonts();
657 : #endif
658 777 : mbNewFont = true;
659 777 : mbInitFont = true;
660 :
661 777 : if ( mpFontEntry )
662 : {
663 367 : mpFontCache->Release( mpFontEntry );
664 367 : mpFontEntry = NULL;
665 : }
666 :
667 777 : if ( mpGetDevFontList )
668 : {
669 90 : delete mpGetDevFontList;
670 90 : mpGetDevFontList = NULL;
671 : }
672 :
673 777 : if ( mpGetDevSizeList )
674 : {
675 0 : delete mpGetDevSizeList;
676 0 : mpGetDevSizeList = NULL;
677 : }
678 777 : }
679 :
680 777 : void Printer::ReleaseGraphics( bool bRelease )
681 : {
682 : DBG_TESTSOLARMUTEX();
683 :
684 777 : if ( !mpGraphics )
685 777 : return;
686 :
687 : // release the fonts of the physically released graphics device
688 777 : if( bRelease )
689 777 : ImplReleaseFonts();
690 :
691 777 : ImplSVData* pSVData = ImplGetSVData();
692 :
693 777 : Printer* pPrinter = (Printer*)this;
694 :
695 777 : if ( !pPrinter->mpJobGraphics )
696 : {
697 777 : if ( pPrinter->mpDisplayDev )
698 : {
699 0 : VirtualDevice* pVirDev = pPrinter->mpDisplayDev;
700 0 : if ( bRelease )
701 0 : pVirDev->mpVirDev->ReleaseGraphics( mpGraphics );
702 : // remove from global LRU list of virtual device graphics
703 0 : if ( mpPrevGraphics )
704 0 : mpPrevGraphics->mpNextGraphics = mpNextGraphics;
705 : else
706 0 : pSVData->maGDIData.mpFirstVirGraphics = mpNextGraphics;
707 0 : if ( mpNextGraphics )
708 0 : mpNextGraphics->mpPrevGraphics = mpPrevGraphics;
709 : else
710 0 : pSVData->maGDIData.mpLastVirGraphics = mpPrevGraphics;
711 : }
712 : else
713 : {
714 777 : if ( bRelease )
715 777 : pPrinter->mpInfoPrinter->ReleaseGraphics( mpGraphics );
716 : // remove from global LRU list of printer graphics
717 777 : if ( mpPrevGraphics )
718 26 : mpPrevGraphics->mpNextGraphics = mpNextGraphics;
719 : else
720 751 : pSVData->maGDIData.mpFirstPrnGraphics = mpNextGraphics;
721 777 : if ( mpNextGraphics )
722 254 : mpNextGraphics->mpPrevGraphics = mpPrevGraphics;
723 : else
724 523 : pSVData->maGDIData.mpLastPrnGraphics = mpPrevGraphics;
725 : }
726 : }
727 :
728 777 : mpGraphics = NULL;
729 777 : mpPrevGraphics = NULL;
730 777 : mpNextGraphics = NULL;
731 : }
732 :
733 680 : void Printer::ImplInit( SalPrinterQueueInfo* pInfo )
734 : {
735 680 : ImplSVData* pSVData = ImplGetSVData();
736 : // #i74084# update info for this specific SalPrinterQueueInfo
737 680 : pSVData->mpDefInst->GetPrinterQueueState( pInfo );
738 :
739 : // Test whether the driver actually matches the JobSetup
740 680 : ImplJobSetup* pJobSetup = maJobSetup.ImplGetData();
741 :
742 680 : if ( pJobSetup->mpDriverData )
743 : {
744 0 : if ( (pJobSetup->maPrinterName != pInfo->maPrinterName) ||
745 0 : (pJobSetup->maDriver != pInfo->maDriver) )
746 : {
747 0 : rtl_freeMemory( pJobSetup->mpDriverData );
748 0 : pJobSetup->mpDriverData = NULL;
749 0 : pJobSetup->mnDriverDataLen = 0;
750 : }
751 : }
752 :
753 : // Remember printer name
754 680 : maPrinterName = pInfo->maPrinterName;
755 680 : maDriver = pInfo->maDriver;
756 :
757 : // Add printer name to JobSetup
758 680 : pJobSetup->maPrinterName = maPrinterName;
759 680 : pJobSetup->maDriver = maDriver;
760 :
761 680 : mpInfoPrinter = pSVData->mpDefInst->CreateInfoPrinter( pInfo, pJobSetup );
762 680 : mpPrinter = NULL;
763 680 : mpJobGraphics = NULL;
764 680 : ImplUpdateJobSetupPaper( maJobSetup );
765 :
766 680 : if ( !mpInfoPrinter )
767 : {
768 0 : ImplInitDisplay( NULL );
769 0 : return;
770 : }
771 :
772 : // we need a graphics
773 680 : if ( !AcquireGraphics() )
774 : {
775 0 : ImplInitDisplay( NULL );
776 0 : return;
777 : }
778 :
779 : // Init data
780 680 : ImplUpdatePageData();
781 680 : mpFontCollection = new PhysicalFontCollection();
782 680 : mpFontCache = new ImplFontCache();
783 680 : mpGraphics->GetDevFontList( mpFontCollection );
784 : }
785 :
786 0 : void Printer::ImplInitDisplay( const vcl::Window* pWindow )
787 : {
788 0 : ImplSVData* pSVData = ImplGetSVData();
789 :
790 0 : mpInfoPrinter = NULL;
791 0 : mpPrinter = NULL;
792 0 : mpJobGraphics = NULL;
793 :
794 0 : if ( pWindow )
795 0 : mpDisplayDev = new VirtualDevice( *pWindow );
796 : else
797 0 : mpDisplayDev = new VirtualDevice();
798 0 : mpFontCollection = pSVData->maGDIData.mpScreenFontList;
799 0 : mpFontCache = pSVData->maGDIData.mpScreenFontCache;
800 0 : mnDPIX = mpDisplayDev->mnDPIX;
801 0 : mnDPIY = mpDisplayDev->mnDPIY;
802 0 : }
803 :
804 0 : void Printer::DrawDeviceMask( const Bitmap& rMask, const Color& rMaskColor,
805 : const Point& rDestPt, const Size& rDestSize,
806 : const Point& rSrcPtPixel, const Size& rSrcSizePixel )
807 : {
808 0 : Point aPt;
809 0 : Point aDestPt( LogicToPixel( rDestPt ) );
810 0 : Size aDestSz( LogicToPixel( rDestSize ) );
811 0 : Rectangle aSrcRect( rSrcPtPixel, rSrcSizePixel );
812 :
813 0 : aSrcRect.Justify();
814 :
815 0 : if( !rMask.IsEmpty() && aSrcRect.GetWidth() && aSrcRect.GetHeight() && aDestSz.Width() && aDestSz.Height() )
816 : {
817 0 : Bitmap aMask( rMask );
818 0 : sal_uLong nMirrFlags = 0UL;
819 :
820 0 : if( aMask.GetBitCount() > 1 )
821 0 : aMask.Convert( BMP_CONVERSION_1BIT_THRESHOLD );
822 :
823 : // mirrored horizontically
824 0 : if( aDestSz.Width() < 0L )
825 : {
826 0 : aDestSz.Width() = -aDestSz.Width();
827 0 : aDestPt.X() -= ( aDestSz.Width() - 1L );
828 0 : nMirrFlags |= BMP_MIRROR_HORZ;
829 : }
830 :
831 : // mirrored vertically
832 0 : if( aDestSz.Height() < 0L )
833 : {
834 0 : aDestSz.Height() = -aDestSz.Height();
835 0 : aDestPt.Y() -= ( aDestSz.Height() - 1L );
836 0 : nMirrFlags |= BMP_MIRROR_VERT;
837 : }
838 :
839 : // source cropped?
840 0 : if( aSrcRect != Rectangle( aPt, aMask.GetSizePixel() ) )
841 0 : aMask.Crop( aSrcRect );
842 :
843 : // destination mirrored
844 0 : if( nMirrFlags )
845 0 : aMask.Mirror( nMirrFlags );
846 :
847 : // do painting
848 0 : const long nSrcWidth = aSrcRect.GetWidth(), nSrcHeight = aSrcRect.GetHeight();
849 : long nX, nY; //, nWorkX, nWorkY, nWorkWidth, nWorkHeight;
850 0 : long* pMapX = new long[ nSrcWidth + 1 ];
851 0 : long* pMapY = new long[ nSrcHeight + 1 ];
852 0 : GDIMetaFile* pOldMetaFile = mpMetaFile;
853 0 : const bool bOldMap = mbMap;
854 :
855 0 : mpMetaFile = NULL;
856 0 : mbMap = false;
857 0 : Push( PushFlags::FILLCOLOR | PushFlags::LINECOLOR );
858 0 : SetLineColor( rMaskColor );
859 0 : SetFillColor( rMaskColor );
860 0 : InitLineColor();
861 0 : InitFillColor();
862 :
863 : // create forward mapping tables
864 0 : for( nX = 0L; nX <= nSrcWidth; nX++ )
865 0 : pMapX[ nX ] = aDestPt.X() + FRound( (double) aDestSz.Width() * nX / nSrcWidth );
866 :
867 0 : for( nY = 0L; nY <= nSrcHeight; nY++ )
868 0 : pMapY[ nY ] = aDestPt.Y() + FRound( (double) aDestSz.Height() * nY / nSrcHeight );
869 :
870 : // walk through all rectangles of mask
871 0 : const vcl::Region aWorkRgn(aMask.CreateRegion(COL_BLACK, Rectangle(Point(), aMask.GetSizePixel())));
872 0 : RectangleVector aRectangles;
873 0 : aWorkRgn.GetRegionRectangles(aRectangles);
874 :
875 0 : for(RectangleVector::const_iterator aRectIter(aRectangles.begin()); aRectIter != aRectangles.end(); ++aRectIter)
876 : {
877 0 : const Point aMapPt(pMapX[aRectIter->Left()], pMapY[aRectIter->Top()]);
878 : const Size aMapSz(
879 0 : pMapX[aRectIter->Right() + 1] - aMapPt.X(), // pMapX[L + W] -> L + ((R - L) + 1) -> R + 1
880 0 : pMapY[aRectIter->Bottom() + 1] - aMapPt.Y()); // same for Y
881 :
882 0 : DrawRect(Rectangle(aMapPt, aMapSz));
883 : }
884 :
885 0 : Pop();
886 0 : delete[] pMapX;
887 0 : delete[] pMapY;
888 0 : mbMap = bOldMap;
889 0 : mpMetaFile = pOldMetaFile;
890 : }
891 0 : }
892 :
893 680 : SalPrinterQueueInfo* Printer::ImplGetQueueInfo( const OUString& rPrinterName,
894 : const OUString* pDriver )
895 : {
896 680 : ImplSVData* pSVData = ImplGetSVData();
897 680 : if ( !pSVData->maGDIData.mpPrinterQueueList )
898 74 : ImplInitPrnQueueList();
899 :
900 680 : ImplPrnQueueList* pPrnList = pSVData->maGDIData.mpPrinterQueueList;
901 680 : if ( pPrnList && pPrnList->m_aQueueInfos.size() )
902 : {
903 : // first search for the printer name directly
904 680 : ImplPrnQueueData* pInfo = pPrnList->Get( rPrinterName );
905 680 : if( pInfo )
906 566 : return pInfo->mpSalQueueInfo;
907 :
908 : // then search case insensitive
909 228 : for( unsigned int i = 0; i < pPrnList->m_aQueueInfos.size(); i++ )
910 : {
911 114 : if( pPrnList->m_aQueueInfos[i].mpSalQueueInfo->maPrinterName.equalsIgnoreAsciiCase( rPrinterName ) )
912 0 : return pPrnList->m_aQueueInfos[i].mpSalQueueInfo;
913 : }
914 :
915 : // then search for driver name
916 114 : if ( pDriver )
917 : {
918 0 : for( unsigned int i = 0; i < pPrnList->m_aQueueInfos.size(); i++ )
919 : {
920 0 : if( pPrnList->m_aQueueInfos[i].mpSalQueueInfo->maDriver == *pDriver )
921 0 : return pPrnList->m_aQueueInfos[i].mpSalQueueInfo;
922 : }
923 : }
924 :
925 : // then the default printer
926 114 : pInfo = pPrnList->Get( GetDefaultPrinterName() );
927 114 : if( pInfo )
928 114 : return pInfo->mpSalQueueInfo;
929 :
930 : // last chance: the first available printer
931 0 : return pPrnList->m_aQueueInfos[0].mpSalQueueInfo;
932 : }
933 :
934 0 : return NULL;
935 : }
936 :
937 780 : void Printer::ImplUpdatePageData()
938 : {
939 : // we need a graphics
940 780 : if ( !AcquireGraphics() )
941 780 : return;
942 :
943 780 : mpGraphics->GetResolution( mnDPIX, mnDPIY );
944 780 : mpInfoPrinter->GetPageInfo( maJobSetup.ImplGetConstData(),
945 : mnOutWidth, mnOutHeight,
946 780 : maPageOffset.X(), maPageOffset.Y(),
947 2340 : maPaperSize.Width(), maPaperSize.Height() );
948 : }
949 :
950 100 : void Printer::ImplUpdateFontList()
951 : {
952 100 : ImplUpdateFontData( true );
953 100 : }
954 :
955 0 : long Printer::GetGradientStepCount( long nMinRect )
956 : {
957 : // use display-equivalent step size calculation
958 0 : long nInc = (nMinRect < 800) ? 10 : 20;
959 :
960 0 : return nInc;
961 : }
962 :
963 466 : Printer::Printer()
964 : {
965 466 : ImplInitData();
966 466 : SalPrinterQueueInfo* pInfo = ImplGetQueueInfo( GetDefaultPrinterName(), NULL );
967 466 : if ( pInfo )
968 : {
969 466 : ImplInit( pInfo );
970 466 : if ( !IsDisplayPrinter() )
971 466 : mbDefPrinter = true;
972 : }
973 : else
974 0 : ImplInitDisplay( NULL );
975 466 : }
976 :
977 0 : Printer::Printer( const JobSetup& rJobSetup ) :
978 0 : maJobSetup( rJobSetup )
979 : {
980 0 : ImplInitData();
981 : SalPrinterQueueInfo* pInfo = ImplGetQueueInfo( rJobSetup.mpData->maPrinterName,
982 0 : &rJobSetup.mpData->maDriver );
983 0 : if ( pInfo )
984 : {
985 0 : ImplInit( pInfo );
986 0 : SetJobSetup( rJobSetup );
987 : }
988 : else
989 : {
990 0 : ImplInitDisplay( NULL );
991 0 : maJobSetup = JobSetup();
992 : }
993 0 : }
994 :
995 0 : Printer::Printer( const QueueInfo& rQueueInfo )
996 : {
997 0 : ImplInitData();
998 0 : SalPrinterQueueInfo* pInfo = ImplGetQueueInfo( rQueueInfo.GetPrinterName(),
999 0 : &rQueueInfo.GetDriver() );
1000 0 : if ( pInfo )
1001 0 : ImplInit( pInfo );
1002 : else
1003 0 : ImplInitDisplay( NULL );
1004 0 : }
1005 :
1006 214 : Printer::Printer( const OUString& rPrinterName )
1007 : {
1008 214 : ImplInitData();
1009 214 : SalPrinterQueueInfo* pInfo = ImplGetQueueInfo( rPrinterName, NULL );
1010 214 : if ( pInfo )
1011 214 : ImplInit( pInfo );
1012 : else
1013 0 : ImplInitDisplay( NULL );
1014 214 : }
1015 :
1016 1354 : Printer::~Printer()
1017 : {
1018 : DBG_ASSERT( !IsPrinting(), "Printer::~Printer() - Job is printing" );
1019 : DBG_ASSERT( !IsJobActive(), "Printer::~Printer() - Job is active" );
1020 :
1021 677 : delete mpPrinterOptions;
1022 :
1023 677 : ReleaseGraphics();
1024 677 : if ( mpInfoPrinter )
1025 677 : ImplGetSVData()->mpDefInst->DestroyInfoPrinter( mpInfoPrinter );
1026 677 : if ( mpDisplayDev )
1027 0 : delete mpDisplayDev;
1028 : else
1029 : {
1030 : // OutputDevice Dtor is tryig the same thing; that why we need to set
1031 : // the FontEntry to NULL here
1032 : // TODO: consolidate duplicate cleanup by Printer and OutputDevice
1033 677 : if ( mpFontEntry )
1034 : {
1035 0 : mpFontCache->Release( mpFontEntry );
1036 0 : mpFontEntry = NULL;
1037 : }
1038 677 : if ( mpGetDevFontList )
1039 : {
1040 0 : delete mpGetDevFontList;
1041 0 : mpGetDevFontList = NULL;
1042 : }
1043 677 : if ( mpGetDevSizeList )
1044 : {
1045 0 : delete mpGetDevSizeList;
1046 0 : mpGetDevSizeList = NULL;
1047 : }
1048 677 : delete mpFontCache;
1049 677 : mpFontCache = NULL;
1050 : // font list deleted by OutputDevice dtor
1051 : }
1052 :
1053 : // Add printer from the list
1054 677 : ImplSVData* pSVData = ImplGetSVData();
1055 677 : if ( mpPrev )
1056 26 : mpPrev->mpNext = mpNext;
1057 : else
1058 651 : pSVData->maGDIData.mpFirstPrinter = mpNext;
1059 677 : if ( mpNext )
1060 224 : mpNext->mpPrev = mpPrev;
1061 : else
1062 453 : pSVData->maGDIData.mpLastPrinter = mpPrev;
1063 677 : }
1064 :
1065 0 : sal_uLong Printer::GetCapabilities( sal_uInt16 nType ) const
1066 : {
1067 0 : if ( IsDisplayPrinter() )
1068 0 : return 0;
1069 :
1070 0 : if( mpInfoPrinter )
1071 0 : return mpInfoPrinter->GetCapabilities( maJobSetup.ImplGetConstData(), nType );
1072 : else
1073 0 : return 0;
1074 : }
1075 :
1076 0 : bool Printer::HasSupport( PrinterSupport eFeature ) const
1077 : {
1078 0 : switch ( eFeature )
1079 : {
1080 : case SUPPORT_SET_ORIENTATION:
1081 0 : return GetCapabilities( PRINTER_CAPABILITIES_SETORIENTATION ) != 0;
1082 : case SUPPORT_SET_PAPERBIN:
1083 0 : return GetCapabilities( PRINTER_CAPABILITIES_SETPAPERBIN ) != 0;
1084 : case SUPPORT_SET_PAPERSIZE:
1085 0 : return GetCapabilities( PRINTER_CAPABILITIES_SETPAPERSIZE ) != 0;
1086 : case SUPPORT_SET_PAPER:
1087 0 : return GetCapabilities( PRINTER_CAPABILITIES_SETPAPER ) != 0;
1088 : case SUPPORT_COPY:
1089 0 : return (GetCapabilities( PRINTER_CAPABILITIES_COPIES ) != 0);
1090 : case SUPPORT_COLLATECOPY:
1091 0 : return (GetCapabilities( PRINTER_CAPABILITIES_COLLATECOPIES ) != 0);
1092 : case SUPPORT_SETUPDIALOG:
1093 0 : return GetCapabilities( PRINTER_CAPABILITIES_SUPPORTDIALOG ) != 0;
1094 : case SUPPORT_FAX:
1095 0 : return GetCapabilities( PRINTER_CAPABILITIES_FAX ) != 0;
1096 : case SUPPORT_PDF:
1097 0 : return GetCapabilities( PRINTER_CAPABILITIES_PDF ) != 0;
1098 : }
1099 :
1100 0 : return true;
1101 : }
1102 :
1103 100 : bool Printer::SetJobSetup( const JobSetup& rSetup )
1104 : {
1105 100 : if ( IsDisplayPrinter() || mbInPrintPage )
1106 0 : return false;
1107 :
1108 100 : JobSetup aJobSetup = rSetup;
1109 :
1110 100 : ReleaseGraphics();
1111 100 : if ( mpInfoPrinter->SetPrinterData( aJobSetup.ImplGetData() ) )
1112 : {
1113 100 : ImplUpdateJobSetupPaper( aJobSetup );
1114 100 : mbNewJobSetup = true;
1115 100 : maJobSetup = aJobSetup;
1116 100 : ImplUpdatePageData();
1117 100 : ImplUpdateFontList();
1118 100 : return true;
1119 : }
1120 :
1121 0 : return false;
1122 : }
1123 :
1124 0 : bool Printer::Setup( vcl::Window* pWindow )
1125 : {
1126 0 : if ( IsDisplayPrinter() )
1127 0 : return false;
1128 :
1129 0 : if ( IsJobActive() || IsPrinting() )
1130 0 : return false;
1131 :
1132 0 : JobSetup aJobSetup = maJobSetup;
1133 : SalFrame* pFrame;
1134 0 : if ( !pWindow )
1135 0 : pWindow = ImplGetDefaultWindow();
1136 0 : if( !pWindow )
1137 0 : return false;
1138 :
1139 0 : pFrame = pWindow->ImplGetFrame();
1140 0 : ReleaseGraphics();
1141 0 : ImplSVData* pSVData = ImplGetSVData();
1142 0 : pSVData->maAppData.mnModalMode++;
1143 0 : nImplSysDialog++;
1144 0 : bool bSetup = mpInfoPrinter->Setup( pFrame, aJobSetup.ImplGetData() );
1145 0 : pSVData->maAppData.mnModalMode--;
1146 0 : nImplSysDialog--;
1147 0 : if ( bSetup )
1148 : {
1149 0 : ImplUpdateJobSetupPaper( aJobSetup );
1150 0 : mbNewJobSetup = true;
1151 0 : maJobSetup = aJobSetup;
1152 0 : ImplUpdatePageData();
1153 0 : ImplUpdateFontList();
1154 0 : return true;
1155 : }
1156 0 : return false;
1157 : }
1158 :
1159 0 : bool Printer::SetPrinterProps( const Printer* pPrinter )
1160 : {
1161 0 : if ( IsJobActive() || IsPrinting() )
1162 0 : return false;
1163 :
1164 0 : ImplSVData* pSVData = ImplGetSVData();
1165 :
1166 0 : mbDefPrinter = pPrinter->mbDefPrinter;
1167 0 : maPrintFile = pPrinter->maPrintFile;
1168 0 : mbPrintFile = pPrinter->mbPrintFile;
1169 0 : mnCopyCount = pPrinter->mnCopyCount;
1170 0 : mbCollateCopy = pPrinter->mbCollateCopy;
1171 0 : mnPageQueueSize = pPrinter->mnPageQueueSize;
1172 0 : *mpPrinterOptions = *pPrinter->mpPrinterOptions;
1173 :
1174 0 : if ( pPrinter->IsDisplayPrinter() )
1175 : {
1176 : // Destroy old printer
1177 0 : if ( !IsDisplayPrinter() )
1178 : {
1179 0 : ReleaseGraphics();
1180 0 : pSVData->mpDefInst->DestroyInfoPrinter( mpInfoPrinter );
1181 0 : if ( mpFontEntry )
1182 : {
1183 0 : mpFontCache->Release( mpFontEntry );
1184 0 : mpFontEntry = NULL;
1185 : }
1186 0 : if ( mpGetDevFontList )
1187 : {
1188 0 : delete mpGetDevFontList;
1189 0 : mpGetDevFontList = NULL;
1190 : }
1191 0 : if ( mpGetDevSizeList )
1192 : {
1193 0 : delete mpGetDevSizeList;
1194 0 : mpGetDevSizeList = NULL;
1195 : }
1196 : // clean up font list
1197 0 : delete mpFontCache;
1198 0 : delete mpFontCollection;
1199 0 : mpFontCache = NULL;
1200 0 : mpFontCollection = NULL;
1201 :
1202 0 : mbInitFont = true;
1203 0 : mbNewFont = true;
1204 0 : mpInfoPrinter = NULL;
1205 : }
1206 :
1207 : // Construct new printer
1208 0 : ImplInitDisplay( NULL );
1209 0 : return true;
1210 : }
1211 :
1212 : // Destroy old printer?
1213 0 : if ( GetName() != pPrinter->GetName() )
1214 : {
1215 0 : ReleaseGraphics();
1216 0 : if ( mpDisplayDev )
1217 : {
1218 0 : delete mpDisplayDev;
1219 0 : mpDisplayDev = NULL;
1220 : }
1221 : else
1222 : {
1223 0 : pSVData->mpDefInst->DestroyInfoPrinter( mpInfoPrinter );
1224 :
1225 0 : if ( mpFontEntry )
1226 : {
1227 0 : mpFontCache->Release( mpFontEntry );
1228 0 : mpFontEntry = NULL;
1229 : }
1230 0 : if ( mpGetDevFontList )
1231 : {
1232 0 : delete mpGetDevFontList;
1233 0 : mpGetDevFontList = NULL;
1234 : }
1235 0 : if ( mpGetDevSizeList )
1236 : {
1237 0 : delete mpGetDevSizeList;
1238 0 : mpGetDevSizeList = NULL;
1239 : }
1240 0 : delete mpFontCache;
1241 0 : delete mpFontCollection;
1242 0 : mpFontCache = NULL;
1243 0 : mpFontCollection = NULL;
1244 0 : mbInitFont = true;
1245 0 : mbNewFont = true;
1246 0 : mpInfoPrinter = NULL;
1247 : }
1248 :
1249 : // Construct new printer
1250 0 : OUString aDriver = pPrinter->GetDriverName();
1251 0 : SalPrinterQueueInfo* pInfo = ImplGetQueueInfo( pPrinter->GetName(), &aDriver );
1252 0 : if ( pInfo )
1253 : {
1254 0 : ImplInit( pInfo );
1255 0 : SetJobSetup( pPrinter->GetJobSetup() );
1256 : }
1257 : else
1258 0 : ImplInitDisplay( NULL );
1259 : }
1260 : else
1261 0 : SetJobSetup( pPrinter->GetJobSetup() );
1262 :
1263 0 : return false;
1264 : }
1265 :
1266 0 : bool Printer::SetOrientation( Orientation eOrientation )
1267 : {
1268 0 : if ( mbInPrintPage )
1269 0 : return false;
1270 :
1271 0 : if ( maJobSetup.ImplGetConstData()->meOrientation != eOrientation )
1272 : {
1273 0 : JobSetup aJobSetup = maJobSetup;
1274 0 : ImplJobSetup* pSetupData = aJobSetup.ImplGetData();
1275 0 : pSetupData->meOrientation = eOrientation;
1276 :
1277 0 : if ( IsDisplayPrinter() )
1278 : {
1279 0 : mbNewJobSetup = true;
1280 0 : maJobSetup = aJobSetup;
1281 0 : return true;
1282 : }
1283 :
1284 0 : ReleaseGraphics();
1285 0 : if ( mpInfoPrinter->SetData( SAL_JOBSET_ORIENTATION, pSetupData ) )
1286 : {
1287 0 : ImplUpdateJobSetupPaper( aJobSetup );
1288 0 : mbNewJobSetup = true;
1289 0 : maJobSetup = aJobSetup;
1290 0 : ImplUpdatePageData();
1291 0 : ImplUpdateFontList();
1292 0 : return true;
1293 : }
1294 : else
1295 0 : return false;
1296 : }
1297 :
1298 0 : return true;
1299 : }
1300 :
1301 338 : Orientation Printer::GetOrientation() const
1302 : {
1303 338 : return maJobSetup.ImplGetConstData()->meOrientation;
1304 : }
1305 :
1306 0 : bool Printer::SetPaperBin( sal_uInt16 nPaperBin )
1307 : {
1308 0 : if ( mbInPrintPage )
1309 0 : return false;
1310 :
1311 0 : if ( (maJobSetup.ImplGetConstData()->mnPaperBin != nPaperBin) &&
1312 0 : (nPaperBin < GetPaperBinCount()) )
1313 : {
1314 0 : JobSetup aJobSetup = maJobSetup;
1315 0 : ImplJobSetup* pSetupData = aJobSetup.ImplGetData();
1316 0 : pSetupData->mnPaperBin = nPaperBin;
1317 :
1318 0 : if ( IsDisplayPrinter() )
1319 : {
1320 0 : mbNewJobSetup = true;
1321 0 : maJobSetup = aJobSetup;
1322 0 : return true;
1323 : }
1324 :
1325 0 : ReleaseGraphics();
1326 0 : if ( mpInfoPrinter->SetData( SAL_JOBSET_PAPERBIN, pSetupData ) )
1327 : {
1328 0 : ImplUpdateJobSetupPaper( aJobSetup );
1329 0 : mbNewJobSetup = true;
1330 0 : maJobSetup = aJobSetup;
1331 0 : ImplUpdatePageData();
1332 0 : ImplUpdateFontList();
1333 0 : return true;
1334 : }
1335 : else
1336 0 : return false;
1337 : }
1338 :
1339 0 : return true;
1340 : }
1341 :
1342 0 : sal_uInt16 Printer::GetPaperBin() const
1343 : {
1344 0 : return maJobSetup.ImplGetConstData()->mnPaperBin;
1345 : }
1346 :
1347 : // Map user paper format to a available printer paper formats
1348 0 : void Printer::ImplFindPaperFormatForUserSize( JobSetup& aJobSetup, bool bMatchNearest )
1349 : {
1350 0 : ImplJobSetup* pSetupData = aJobSetup.ImplGetData();
1351 :
1352 0 : int nLandscapeAngle = GetLandscapeAngle();
1353 0 : int nPaperCount = GetPaperInfoCount();
1354 0 : bool bFound = false;
1355 :
1356 0 : PaperInfo aInfo(pSetupData->mnPaperWidth, pSetupData->mnPaperHeight);
1357 :
1358 : // Compare all paper formats and get the appropriate one
1359 0 : for ( int i = 0; i < nPaperCount; i++ )
1360 : {
1361 0 : const PaperInfo& rPaperInfo = GetPaperInfo( i );
1362 :
1363 0 : if ( aInfo.sloppyEqual(rPaperInfo) )
1364 : {
1365 : pSetupData->mePaperFormat = ImplGetPaperFormat( rPaperInfo.getWidth(),
1366 0 : rPaperInfo.getHeight() );
1367 0 : pSetupData->meOrientation = ORIENTATION_PORTRAIT;
1368 0 : bFound = true;
1369 0 : break;
1370 : }
1371 : }
1372 :
1373 : // If the printer supports landscape orientation, check paper sizes again
1374 : // with landscape orientation. This is necessary as a printer driver provides
1375 : // all paper sizes with portrait orientation only!!
1376 0 : if ( pSetupData->mePaperFormat == PAPER_USER &&
1377 0 : nLandscapeAngle != 0 &&
1378 0 : HasSupport( SUPPORT_SET_ORIENTATION ))
1379 : {
1380 0 : const long nRotatedWidth = pSetupData->mnPaperHeight;
1381 0 : const long nRotatedHeight = pSetupData->mnPaperWidth;
1382 0 : PaperInfo aRotatedInfo(nRotatedWidth, nRotatedHeight);
1383 :
1384 0 : for ( int i = 0; i < nPaperCount; i++ )
1385 : {
1386 0 : const PaperInfo& rPaperInfo = GetPaperInfo( i );
1387 :
1388 0 : if ( aRotatedInfo.sloppyEqual( rPaperInfo ) )
1389 : {
1390 : pSetupData->mePaperFormat = ImplGetPaperFormat( rPaperInfo.getWidth(),
1391 0 : rPaperInfo.getHeight() );
1392 0 : pSetupData->meOrientation = ORIENTATION_LANDSCAPE;
1393 0 : bFound = true;
1394 0 : break;
1395 : }
1396 : }
1397 : }
1398 :
1399 0 : if( ! bFound && bMatchNearest )
1400 : {
1401 0 : sal_Int64 nBestMatch = SAL_MAX_INT64;
1402 0 : int nBestIndex = 0;
1403 0 : Orientation eBestOrientation = ORIENTATION_PORTRAIT;
1404 0 : for( int i = 0; i < nPaperCount; i++ )
1405 : {
1406 0 : const PaperInfo& rPaperInfo = GetPaperInfo( i );
1407 :
1408 : // check portrait match
1409 0 : sal_Int64 nDX = pSetupData->mnPaperWidth - rPaperInfo.getWidth();
1410 0 : sal_Int64 nDY = pSetupData->mnPaperHeight - rPaperInfo.getHeight();
1411 0 : sal_Int64 nMatch = nDX*nDX + nDY*nDY;
1412 0 : if( nMatch < nBestMatch )
1413 : {
1414 0 : nBestMatch = nMatch;
1415 0 : nBestIndex = i;
1416 0 : eBestOrientation = ORIENTATION_PORTRAIT;
1417 : }
1418 :
1419 : // check landscape match
1420 0 : nDX = pSetupData->mnPaperWidth - rPaperInfo.getHeight();
1421 0 : nDY = pSetupData->mnPaperHeight - rPaperInfo.getWidth();
1422 0 : nMatch = nDX*nDX + nDY*nDY;
1423 0 : if( nMatch < nBestMatch )
1424 : {
1425 0 : nBestMatch = nMatch;
1426 0 : nBestIndex = i;
1427 0 : eBestOrientation = ORIENTATION_LANDSCAPE;
1428 : }
1429 : }
1430 0 : const PaperInfo& rBestInfo = GetPaperInfo( nBestIndex );
1431 : pSetupData->mePaperFormat = ImplGetPaperFormat( rBestInfo.getWidth(),
1432 0 : rBestInfo.getHeight() );
1433 0 : pSetupData->meOrientation = eBestOrientation;
1434 : }
1435 0 : }
1436 :
1437 0 : bool Printer::SetPaper( Paper ePaper )
1438 : {
1439 0 : if ( mbInPrintPage )
1440 0 : return false;
1441 :
1442 0 : if ( maJobSetup.ImplGetConstData()->mePaperFormat != ePaper )
1443 : {
1444 0 : JobSetup aJobSetup = maJobSetup;
1445 0 : ImplJobSetup* pSetupData = aJobSetup.ImplGetData();
1446 0 : pSetupData->mePaperFormat = ePaper;
1447 0 : if ( ePaper != PAPER_USER )
1448 : {
1449 0 : PaperInfo aInfo(ePaper);
1450 0 : pSetupData->mnPaperWidth = aInfo.getWidth();
1451 0 : pSetupData->mnPaperHeight = aInfo.getHeight();
1452 : }
1453 :
1454 0 : if ( IsDisplayPrinter() )
1455 : {
1456 0 : mbNewJobSetup = true;
1457 0 : maJobSetup = aJobSetup;
1458 0 : return true;
1459 : }
1460 :
1461 0 : ReleaseGraphics();
1462 0 : if ( ePaper == PAPER_USER )
1463 0 : ImplFindPaperFormatForUserSize( aJobSetup, false );
1464 0 : if ( mpInfoPrinter->SetData( SAL_JOBSET_PAPERSIZE|SAL_JOBSET_ORIENTATION, pSetupData ) )
1465 : {
1466 0 : ImplUpdateJobSetupPaper( aJobSetup );
1467 0 : mbNewJobSetup = true;
1468 0 : maJobSetup = aJobSetup;
1469 0 : ImplUpdatePageData();
1470 0 : ImplUpdateFontList();
1471 0 : return true;
1472 : }
1473 : else
1474 0 : return false;
1475 : }
1476 :
1477 0 : return true;
1478 : }
1479 :
1480 0 : bool Printer::SetPaperSizeUser( const Size& rSize )
1481 : {
1482 0 : return SetPaperSizeUser( rSize, false );
1483 : }
1484 :
1485 0 : bool Printer::SetPaperSizeUser( const Size& rSize, bool bMatchNearest )
1486 : {
1487 0 : if ( mbInPrintPage )
1488 0 : return false;
1489 :
1490 0 : const Size aPixSize = LogicToPixel( rSize );
1491 0 : const Size aPageSize = PixelToLogic( aPixSize, MAP_100TH_MM );
1492 0 : bool bNeedToChange(maJobSetup.ImplGetConstData()->mnPaperWidth != aPageSize.Width() ||
1493 0 : maJobSetup.ImplGetConstData()->mnPaperHeight != aPageSize.Height());
1494 :
1495 0 : if(!bNeedToChange)
1496 : {
1497 : // #i122984# only need to change when Paper is different from PAPER_USER and
1498 : // the mapped Paper which will created below in the call to ImplFindPaperFormatForUserSize
1499 : // and will replace maJobSetup.ImplGetConstData()->mePaperFormat. This leads to
1500 : // unnecessary JobSetups, e.g. when printing a multi-page fax, but also with
1501 : // normal print
1502 0 : const Paper aPaper = ImplGetPaperFormat(aPageSize.Width(), aPageSize.Height());
1503 :
1504 0 : bNeedToChange = maJobSetup.ImplGetConstData()->mePaperFormat != PAPER_USER &&
1505 0 : maJobSetup.ImplGetConstData()->mePaperFormat != aPaper;
1506 : }
1507 :
1508 0 : if(bNeedToChange)
1509 : {
1510 0 : JobSetup aJobSetup = maJobSetup;
1511 0 : ImplJobSetup* pSetupData = aJobSetup.ImplGetData();
1512 0 : pSetupData->mePaperFormat = PAPER_USER;
1513 0 : pSetupData->mnPaperWidth = aPageSize.Width();
1514 0 : pSetupData->mnPaperHeight = aPageSize.Height();
1515 :
1516 0 : if ( IsDisplayPrinter() )
1517 : {
1518 0 : mbNewJobSetup = true;
1519 0 : maJobSetup = aJobSetup;
1520 0 : return true;
1521 : }
1522 :
1523 0 : ReleaseGraphics();
1524 0 : ImplFindPaperFormatForUserSize( aJobSetup, bMatchNearest );
1525 :
1526 : // Changing the paper size can also change the orientation!
1527 0 : if ( mpInfoPrinter->SetData( SAL_JOBSET_PAPERSIZE|SAL_JOBSET_ORIENTATION, pSetupData ) )
1528 : {
1529 0 : ImplUpdateJobSetupPaper( aJobSetup );
1530 0 : mbNewJobSetup = true;
1531 0 : maJobSetup = aJobSetup;
1532 0 : ImplUpdatePageData();
1533 0 : ImplUpdateFontList();
1534 0 : return true;
1535 : }
1536 : else
1537 0 : return false;
1538 : }
1539 :
1540 0 : return true;
1541 : }
1542 :
1543 0 : int Printer::GetPaperInfoCount() const
1544 : {
1545 0 : if( ! mpInfoPrinter )
1546 0 : return 0;
1547 0 : if( ! mpInfoPrinter->m_bPapersInit )
1548 0 : mpInfoPrinter->InitPaperFormats( maJobSetup.ImplGetConstData() );
1549 0 : return mpInfoPrinter->m_aPaperFormats.size();
1550 : }
1551 :
1552 0 : OUString Printer::GetPaperName( Paper ePaper )
1553 : {
1554 0 : ImplSVData* pSVData = ImplGetSVData();
1555 0 : if( ! pSVData->mpPaperNames )
1556 : {
1557 0 : pSVData->mpPaperNames = new boost::unordered_map< int, OUString >();
1558 0 : if( ImplGetResMgr() )
1559 : {
1560 0 : ResStringArray aPaperStrings( VclResId( RID_STR_PAPERNAMES ) );
1561 : static const int PaperIndex[] =
1562 : {
1563 : PAPER_A0, PAPER_A1, PAPER_A2, PAPER_A3, PAPER_A4, PAPER_A5,
1564 : PAPER_B4_ISO, PAPER_B5_ISO, PAPER_LETTER, PAPER_LEGAL, PAPER_TABLOID,
1565 : PAPER_USER, PAPER_B6_ISO, PAPER_ENV_C4, PAPER_ENV_C5, PAPER_ENV_C6, PAPER_ENV_C65,
1566 : PAPER_ENV_DL, PAPER_SLIDE_DIA, PAPER_C, PAPER_D, PAPER_E,
1567 : PAPER_EXECUTIVE, PAPER_FANFOLD_LEGAL_DE, PAPER_ENV_MONARCH, PAPER_ENV_PERSONAL,
1568 : PAPER_ENV_9, PAPER_ENV_10, PAPER_ENV_11, PAPER_ENV_12, PAPER_KAI16,
1569 : PAPER_KAI32, PAPER_KAI32BIG, PAPER_B4_JIS, PAPER_B5_JIS, PAPER_B6_JIS,
1570 : PAPER_POSTCARD_JP
1571 : };
1572 : OSL_ENSURE( sal_uInt32(SAL_N_ELEMENTS(PaperIndex)) == aPaperStrings.Count(), "localized paper name count wrong" );
1573 0 : for( int i = 0; i < int(SAL_N_ELEMENTS(PaperIndex)); i++ )
1574 0 : (*pSVData->mpPaperNames)[PaperIndex[i]] = aPaperStrings.GetString(i);
1575 : }
1576 : }
1577 :
1578 0 : boost::unordered_map<int,OUString>::const_iterator it = pSVData->mpPaperNames->find( (int)ePaper );
1579 0 : return (it != pSVData->mpPaperNames->end()) ? it->second : OUString();
1580 : }
1581 :
1582 0 : OUString Printer::GetPaperName( bool i_bPaperUser ) const
1583 : {
1584 0 : Size aPageSize = PixelToLogic( GetPaperSizePixel(), MAP_100TH_MM );
1585 0 : Paper ePaper = ImplGetPaperFormat( aPageSize.Width(), aPageSize.Height() );
1586 0 : if( ePaper == PAPER_USER )
1587 0 : ePaper = ImplGetPaperFormat( aPageSize.Height(), aPageSize.Width() );
1588 0 : return (ePaper != PAPER_USER || i_bPaperUser ) ? GetPaperName( ePaper ) : OUString();
1589 : }
1590 :
1591 0 : const PaperInfo& Printer::GetPaperInfo( int nPaper ) const
1592 : {
1593 0 : if( ! mpInfoPrinter )
1594 0 : return ImplGetEmptyPaper();
1595 0 : if( ! mpInfoPrinter->m_bPapersInit )
1596 0 : mpInfoPrinter->InitPaperFormats( maJobSetup.ImplGetConstData() );
1597 0 : if( mpInfoPrinter->m_aPaperFormats.empty() || nPaper < 0 || nPaper >= int(mpInfoPrinter->m_aPaperFormats.size()) )
1598 0 : return ImplGetEmptyPaper();
1599 0 : return mpInfoPrinter->m_aPaperFormats[nPaper];
1600 : }
1601 :
1602 0 : bool Printer::SetDuplexMode( DuplexMode eDuplex )
1603 : {
1604 0 : if ( mbInPrintPage )
1605 0 : return false;
1606 :
1607 0 : if ( maJobSetup.ImplGetConstData()->meDuplexMode != eDuplex )
1608 : {
1609 0 : JobSetup aJobSetup = maJobSetup;
1610 0 : ImplJobSetup* pSetupData = aJobSetup.ImplGetData();
1611 0 : pSetupData->meDuplexMode = eDuplex;
1612 :
1613 0 : if ( IsDisplayPrinter() )
1614 : {
1615 0 : mbNewJobSetup = true;
1616 0 : maJobSetup = aJobSetup;
1617 0 : return true;
1618 : }
1619 :
1620 0 : ReleaseGraphics();
1621 0 : if ( mpInfoPrinter->SetData( SAL_JOBSET_DUPLEXMODE, pSetupData ) )
1622 : {
1623 0 : ImplUpdateJobSetupPaper( aJobSetup );
1624 0 : mbNewJobSetup = true;
1625 0 : maJobSetup = aJobSetup;
1626 0 : ImplUpdatePageData();
1627 0 : ImplUpdateFontList();
1628 0 : return true;
1629 : }
1630 : else
1631 0 : return false;
1632 : }
1633 :
1634 0 : return true;
1635 : }
1636 :
1637 0 : int Printer::GetLandscapeAngle() const
1638 : {
1639 0 : return mpInfoPrinter ? mpInfoPrinter->GetLandscapeAngle( maJobSetup.ImplGetConstData() ) : 900;
1640 : }
1641 :
1642 178 : Paper Printer::GetPaper() const
1643 : {
1644 178 : return maJobSetup.ImplGetConstData()->mePaperFormat;
1645 : }
1646 :
1647 0 : sal_uInt16 Printer::GetPaperBinCount() const
1648 : {
1649 0 : if ( IsDisplayPrinter() )
1650 0 : return 0;
1651 :
1652 0 : return (sal_uInt16)mpInfoPrinter->GetPaperBinCount( maJobSetup.ImplGetConstData() );
1653 : }
1654 :
1655 0 : OUString Printer::GetPaperBinName( sal_uInt16 nPaperBin ) const
1656 : {
1657 0 : if ( IsDisplayPrinter() )
1658 0 : return OUString();
1659 :
1660 0 : if ( nPaperBin < GetPaperBinCount() )
1661 0 : return mpInfoPrinter->GetPaperBinName( maJobSetup.ImplGetConstData(), nPaperBin );
1662 : else
1663 0 : return OUString();
1664 : }
1665 :
1666 0 : bool Printer::SetCopyCount( sal_uInt16 nCopy, bool bCollate )
1667 : {
1668 0 : mnCopyCount = nCopy;
1669 0 : mbCollateCopy = bCollate;
1670 0 : return true;
1671 : }
1672 :
1673 0 : void Printer::Error()
1674 : {
1675 0 : maErrorHdl.Call( this );
1676 0 : }
1677 :
1678 0 : sal_uLong Printer::ImplSalPrinterErrorCodeToVCL( sal_uLong nError )
1679 : {
1680 : sal_uLong nVCLError;
1681 0 : switch ( nError )
1682 : {
1683 : case 0:
1684 0 : nVCLError = PRINTER_OK;
1685 0 : break;
1686 : case SAL_PRINTER_ERROR_ABORT:
1687 0 : nVCLError = PRINTER_ABORT;
1688 0 : break;
1689 : default:
1690 0 : nVCLError = PRINTER_GENERALERROR;
1691 0 : break;
1692 : }
1693 :
1694 0 : return nVCLError;
1695 : }
1696 :
1697 0 : bool Printer::EndJob()
1698 : {
1699 0 : bool bRet = false;
1700 0 : if ( !IsJobActive() )
1701 0 : return bRet;
1702 :
1703 : DBG_ASSERT( !mbInPrintPage, "Printer::EndJob() - StartPage() without EndPage() called" );
1704 :
1705 0 : mbJobActive = false;
1706 :
1707 0 : if ( mpPrinter )
1708 : {
1709 0 : ReleaseGraphics();
1710 :
1711 0 : mnCurPage = 0;
1712 :
1713 0 : mbPrinting = false;
1714 0 : mnCurPrintPage = 0;
1715 0 : maJobName = OUString();
1716 :
1717 0 : mbDevOutput = false;
1718 0 : bRet = mpPrinter->EndJob();
1719 : // FIXME: Do not destroy the printer asynchronously as Win95
1720 : // can't handle destroying a printer object and printing
1721 : // at the same time
1722 0 : ImplGetSVData()->mpDefInst->DestroyPrinter( mpPrinter );
1723 0 : mpPrinter = NULL;
1724 : }
1725 :
1726 0 : return bRet;
1727 : }
1728 :
1729 0 : void Printer::ImplStartPage()
1730 : {
1731 0 : if ( !IsJobActive() )
1732 0 : return;
1733 :
1734 0 : if ( mpPrinter )
1735 : {
1736 0 : SalGraphics* pGraphics = mpPrinter->StartPage( maJobSetup.ImplGetConstData(), mbNewJobSetup );
1737 0 : if ( pGraphics )
1738 : {
1739 0 : ReleaseGraphics();
1740 0 : mpJobGraphics = pGraphics;
1741 : }
1742 0 : mbDevOutput = true;
1743 :
1744 : // PrintJob not aborted ???
1745 0 : if ( IsJobActive() )
1746 : {
1747 0 : mbInPrintPage = true;
1748 0 : mnCurPage++;
1749 0 : mnCurPrintPage++;
1750 : }
1751 : }
1752 : }
1753 :
1754 0 : void Printer::ImplEndPage()
1755 : {
1756 0 : if ( !IsJobActive() )
1757 0 : return;
1758 :
1759 0 : mbInPrintPage = false;
1760 :
1761 0 : if ( mpPrinter )
1762 : {
1763 0 : mpPrinter->EndPage();
1764 0 : ReleaseGraphics();
1765 0 : mbDevOutput = false;
1766 :
1767 0 : mpJobGraphics = NULL;
1768 0 : mbNewJobSetup = false;
1769 : }
1770 : }
1771 :
1772 0 : void Printer::updatePrinters()
1773 : {
1774 0 : ImplSVData* pSVData = ImplGetSVData();
1775 0 : ImplPrnQueueList* pPrnList = pSVData->maGDIData.mpPrinterQueueList;
1776 :
1777 0 : if ( pPrnList )
1778 : {
1779 0 : ImplPrnQueueList* pNewList = new ImplPrnQueueList;
1780 0 : pSVData->mpDefInst->GetPrinterQueueInfo( pNewList );
1781 :
1782 0 : bool bChanged = pPrnList->m_aQueueInfos.size() != pNewList->m_aQueueInfos.size();
1783 0 : for( unsigned int i = 0; ! bChanged && i < pPrnList->m_aQueueInfos.size(); i++ )
1784 : {
1785 0 : ImplPrnQueueData& rInfo = pPrnList->m_aQueueInfos[i];
1786 0 : ImplPrnQueueData& rNewInfo = pNewList->m_aQueueInfos[i];
1787 0 : if( ! rInfo.mpSalQueueInfo || ! rNewInfo.mpSalQueueInfo || // sanity check
1788 0 : rInfo.mpSalQueueInfo->maPrinterName != rNewInfo.mpSalQueueInfo->maPrinterName )
1789 : {
1790 0 : bChanged = true;
1791 : }
1792 : }
1793 0 : if( bChanged )
1794 : {
1795 0 : ImplDeletePrnQueueList();
1796 0 : pSVData->maGDIData.mpPrinterQueueList = pNewList;
1797 :
1798 0 : Application* pApp = GetpApp();
1799 0 : if( pApp )
1800 : {
1801 0 : DataChangedEvent aDCEvt( DATACHANGED_PRINTER );
1802 0 : pApp->DataChanged( aDCEvt );
1803 0 : Application::NotifyAllWindows( aDCEvt );
1804 : }
1805 : }
1806 : else
1807 0 : delete pNewList;
1808 : }
1809 0 : }
1810 :
1811 0 : bool Printer::UsePolyPolygonForComplexGradient()
1812 : {
1813 0 : return true;
1814 : }
1815 :
1816 1088 : void Printer::InitFont() const
1817 : {
1818 : DBG_TESTSOLARMUTEX();
1819 :
1820 1088 : if (!mpFontEntry)
1821 1088 : return;
1822 :
1823 1088 : if ( mbInitFont )
1824 : {
1825 : // select font in the device layers
1826 1088 : mpFontEntry->mnSetFontFlags = mpGraphics->SetFont( &(mpFontEntry->maFontSelData), 0 );
1827 1088 : mbInitFont = false;
1828 : }
1829 : }
1830 :
1831 485 : void Printer::SetFontOrientation( ImplFontEntry* const pFontEntry ) const
1832 : {
1833 485 : pFontEntry->mnOrientation = pFontEntry->maMetric.mnOrientation;
1834 485 : }
1835 :
1836 0 : void Printer::DrawImage( const Point&, const Image&, sal_uInt16 )
1837 : {
1838 : SAL_WARN ("vcl.gdi", "DrawImage(): Images can't be drawn on any Printer instance");
1839 : assert(false);
1840 0 : }
1841 :
1842 0 : void Printer::DrawImage( const Point&, const Size&, const Image&, sal_uInt16 )
1843 : {
1844 : SAL_WARN ("vcl.gdi", "DrawImage(): Images can't be drawn on any Printer instance");
1845 : assert(false);
1846 0 : }
1847 :
1848 :
1849 0 : Bitmap Printer::GetBitmap( const Point& rSrcPt, const Size& rSize ) const
1850 : {
1851 : SAL_WARN("vcl.gdi", "GetBitmap(): This should never be called on by a Printer instance");
1852 :
1853 0 : return OutputDevice::GetBitmap( rSrcPt, rSize );
1854 1233 : }
1855 :
1856 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|