xref: /aoo41x/main/sw/source/core/view/viewpg.cxx (revision cdf0e10c)
1 /*************************************************************************
2  *
3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4  *
5  * Copyright 2000, 2010 Oracle and/or its affiliates.
6  *
7  * OpenOffice.org - a multi-platform office productivity suite
8  *
9  * This file is part of OpenOffice.org.
10  *
11  * OpenOffice.org is free software: you can redistribute it and/or modify
12  * it under the terms of the GNU Lesser General Public License version 3
13  * only, as published by the Free Software Foundation.
14  *
15  * OpenOffice.org is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  * GNU Lesser General Public License version 3 for more details
19  * (a copy is included in the LICENSE file that accompanied this code).
20  *
21  * You should have received a copy of the GNU Lesser General Public License
22  * version 3 along with OpenOffice.org.  If not, see
23  * <http://www.openoffice.org/license.html>
24  * for a copy of the LGPLv3 License.
25  *
26  ************************************************************************/
27 
28 // MARKER(update_precomp.py): autogen include statement, do not remove
29 #include "precompiled_sw.hxx"
30 
31 #include <com/sun/star/uno/Sequence.hxx>
32 
33 #include <hintids.hxx>
34 #include <vcl/window.hxx>
35 #include <vcl/oldprintadaptor.hxx>
36 #include <sfx2/printer.hxx>
37 #include <sfx2/progress.hxx>
38 #include <pvprtdat.hxx>
39 #include <viewsh.hxx>
40 #include <pagefrm.hxx>
41 #include <rootfrm.hxx>
42 #include <viewimp.hxx>
43 #include <viewopt.hxx>
44 #include <printdata.hxx>
45 #include <fldbas.hxx>
46 #include <ptqueue.hxx>
47 #include <swregion.hxx>
48 #include <hints.hxx>
49 #include <fntcache.hxx>
50 
51 #include <statstr.hrc>	// Text fuer SfxProgress
52 #include <comcore.hrc>
53 
54 #include <IDocumentFieldsAccess.hxx>
55 #include <IDocumentDeviceAccess.hxx>
56 
57 
58 using namespace ::com::sun::star;
59 
60 
61 // OD 12.12.2002 #103492#
62 SwPagePreviewLayout* ViewShell::PagePreviewLayout()
63 {
64     return Imp()->PagePreviewLayout();
65 }
66 
67 void ViewShell::ShowPreViewSelection( sal_uInt16 nSelPage )
68 {
69     Imp()->InvalidateAccessiblePreViewSelection( nSelPage );
70 }
71 
72 /** adjust view options for page preview
73 
74     OD 09.01.2003 #i6467#
75 */
76 void ViewShell::AdjustOptionsForPagePreview(SwPrintData const& rPrintOptions)
77 {
78     if ( !IsPreView() )
79     {
80         ASSERT( false, "view shell doesn't belongs to a page preview - no adjustment of its view options");
81         return;
82     }
83 
84     PrepareForPrint( rPrintOptions );
85 
86     return;
87 }
88 
89 // print brochure
90 // OD 05.05.2003 #i14016# - consider empty pages on calculation of the scaling
91 // for a page to be printed.
92 void ViewShell::PrintProspect(
93     OutputDevice *pOutDev,
94     const SwPrintData &rPrintData,
95     sal_Int32 nRenderer // the index in the vector of prospect pages to be printed
96     )
97 {
98     const sal_Int32 nMaxRenderer = rPrintData.GetRenderData().GetPagePairsForProspectPrinting().size() - 1;
99 #if OSL_DEBUG_LEVEL > 1
100     DBG_ASSERT( 0 <= nRenderer && nRenderer <= nMaxRenderer, "nRenderer out of bounds");
101 #endif
102     Printer *pPrinter = dynamic_cast< Printer * >(pOutDev);
103     if (!pPrinter || nMaxRenderer < 0 || nRenderer < 0 || nRenderer > nMaxRenderer)
104 		return;
105 
106     // save settings of OutputDevice (should be done always since the
107     // output device is now provided by a call from outside the Writer)
108     pPrinter->Push();
109 
110     std::pair< sal_Int32, sal_Int32 > rPagesToPrint =
111             rPrintData.GetRenderData().GetPagePairsForProspectPrinting()[ nRenderer ];
112 // const sal_uInt16 nPageMax = static_cast< sal_uInt16 >(rPagesToPrint.first > rPagesToPrint.second ?
113 //            rPagesToPrint.first : rPagesToPrint.second);
114 #if OSL_DEBUG_LEVEL > 1
115     DBG_ASSERT( rPagesToPrint.first  == -1 || rPrintData.GetRenderData().GetValidPagesSet().count( rPagesToPrint.first ) == 1, "first Page not valid" );
116     DBG_ASSERT( rPagesToPrint.second == -1 || rPrintData.GetRenderData().GetValidPagesSet().count( rPagesToPrint.second ) == 1, "second Page not valid" );
117 #endif
118 
119 	// eine neue Shell fuer den Printer erzeugen
120     ViewShell aShell( *this, 0, pPrinter );
121 
122     SET_CURR_SHELL( &aShell );
123 
124     aShell.PrepareForPrint( rPrintData );
125 
126     //!! applying view options and formatting the dcoument should now only be done in getRendererCount!
127 
128     MapMode aMapMode( MAP_TWIP );
129     Size aPrtSize( pPrinter->PixelToLogic( pPrinter->GetPaperSizePixel(), aMapMode ) );
130 
131     SwTwips nMaxRowSz, nMaxColSz;
132 
133     const SwPageFrm *pStPage    = 0;
134     const SwPageFrm *pNxtPage   = 0;
135     const SwRenderData::ValidStartFramesMap_t &rFrms = rPrintData.GetRenderData().GetValidStartFrames();
136     if (rPagesToPrint.first > 0)
137     {
138         SwRenderData::ValidStartFramesMap_t::const_iterator aIt( rFrms.find( rPagesToPrint.first ) );
139         DBG_ASSERT( aIt != rFrms.end(), "failed to find start frame" );
140         pStPage = aIt->second;
141     }
142     if (rPagesToPrint.second > 0)
143     {
144         SwRenderData::ValidStartFramesMap_t::const_iterator aIt( rFrms.find( rPagesToPrint.second ) );
145         DBG_ASSERT( aIt != rFrms.end(), "failed to find start frame" );
146         pNxtPage = aIt->second;
147     }
148 
149     // OD 05.05.2003 #i14016# - consider empty pages on calculation
150     // of page size, used for calculation of scaling.
151     Size aSttPageSize;
152     if ( pStPage )
153     {
154         if ( pStPage->IsEmptyPage() )
155         {
156             if ( pStPage->GetPhyPageNum() % 2 == 0 )
157                 aSttPageSize = pStPage->GetPrev()->Frm().SSize();
158             else
159                 aSttPageSize = pStPage->GetNext()->Frm().SSize();
160         }
161         else
162         {
163             aSttPageSize = pStPage->Frm().SSize();
164         }
165     }
166     Size aNxtPageSize;
167     if ( pNxtPage )
168     {
169         if ( pNxtPage->IsEmptyPage() )
170         {
171             if ( pNxtPage->GetPhyPageNum() % 2 == 0 )
172                 aNxtPageSize = pNxtPage->GetPrev()->Frm().SSize();
173             else
174                 aNxtPageSize = pNxtPage->GetNext()->Frm().SSize();
175         }
176         else
177         {
178             aNxtPageSize = pNxtPage->Frm().SSize();
179         }
180     }
181 
182     if( !pStPage )
183     {
184         nMaxColSz = 2 * aNxtPageSize.Width();
185         nMaxRowSz = aNxtPageSize.Height();
186     }
187     else if( !pNxtPage )
188     {
189         nMaxColSz = 2 * aSttPageSize.Width();
190         nMaxRowSz = aSttPageSize.Height();
191     }
192     else
193     {
194         nMaxColSz = aNxtPageSize.Width() + aSttPageSize.Width();
195         nMaxRowSz = Max( aNxtPageSize.Height(), aSttPageSize.Height() );
196     }
197 
198     // den MapMode einstellen
199     aMapMode.SetOrigin( Point() );
200     {
201         Fraction aScX( aPrtSize.Width(), nMaxColSz );
202         Fraction aScY( aPrtSize.Height(), nMaxRowSz );
203         if( aScX < aScY )
204             aScY = aScX;
205 
206         {
207             // fuer Drawing, damit diese ihre Objecte vernuenftig Painten
208             // koennen, auf "glatte" Prozentwerte setzen
209             aScY *= Fraction( 1000, 1 );
210             long nTmp = (long)aScY;
211             if( 1 < nTmp )
212                 --nTmp;
213             else
214                 nTmp = 1;
215             aScY = Fraction( nTmp, 1000 );
216         }
217 
218         aMapMode.SetScaleY( aScY );
219         aMapMode.SetScaleX( aScY );
220     }
221 
222     Size aTmpPrtSize( pPrinter->PixelToLogic( pPrinter->GetPaperSizePixel(), aMapMode ) );
223 
224     // calculate start point for equal border on all sides
225     Point aSttPt( (aTmpPrtSize.Width() - nMaxColSz) / 2,
226                   (aTmpPrtSize.Height() - nMaxRowSz) / 2 );
227     for( int nC = 0; nC < 2; ++nC )
228     {
229         if( pStPage )
230         {
231             aShell.Imp()->SetFirstVisPageInvalid();
232             aShell.aVisArea = pStPage->Frm();
233 
234             Point aPos( aSttPt );
235             aPos -= aShell.aVisArea.Pos();
236 //            aPos -= aPrtOff;
237             aMapMode.SetOrigin( aPos );
238             pPrinter->SetMapMode( aMapMode );
239             pStPage->GetUpper()->Paint( pStPage->Frm() );
240         }
241 
242         pStPage = pNxtPage;
243         aSttPt.X() += aTmpPrtSize.Width() / 2;
244     }
245 
246     SwPaintQueue::Repaint();
247 
248     //!! applying/modifying view options and formatting the dcoument should now only be done in getRendererCount!
249 
250     pFntCache->Flush();
251 
252     // restore settings of OutputDevice (should be done always now since the
253     // output device is now provided by a call from outside the Writer)
254     pPrinter->Pop();
255 }
256 
257 
258