1 /************************************************************** 2 * 3 * Licensed to the Apache Software Foundation (ASF) under one 4 * or more contributor license agreements. See the NOTICE file 5 * distributed with this work for additional information 6 * regarding copyright ownership. The ASF licenses this file 7 * to you under the Apache License, Version 2.0 (the 8 * "License"); you may not use this file except in compliance 9 * with the License. You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, 14 * software distributed under the License is distributed on an 15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 16 * KIND, either express or implied. See the License for the 17 * specific language governing permissions and limitations 18 * under the License. 19 * 20 *************************************************************/ 21 22 23 24 // MARKER(update_precomp.py): autogen include statement, do not remove 25 #include "precompiled_sw.hxx" 26 27 28 #include <vcl/window.hxx> 29 30 #include "hintids.hxx" 31 #include "viewsh.hxx" 32 #include "virtoutp.hxx" 33 #include "viewopt.hxx" 34 #include "rootfrm.hxx" 35 // OD 12.11.2002 #96272# - include declaration for <SetMappingForVirtDev> 36 #include "setmapvirtdev.hxx" 37 38 #ifdef DBG_UTIL 39 40 /************************************************************************* 41 * class DbgRect 42 *************************************************************************/ 43 44 class DbgRect 45 { 46 OutputDevice *pOut; 47 public: 48 DbgRect( OutputDevice *pOut, const Rectangle &rRect, 49 const ColorData eColor = COL_LIGHTBLUE ); 50 }; 51 52 inline DbgRect::DbgRect( OutputDevice *pOutDev, const Rectangle &rRect, 53 const ColorData eColor ) 54 :pOut( pOutDev ) 55 { 56 if( pOut ) 57 { 58 pOut->Push( PUSH_FILLCOLOR|PUSH_LINECOLOR ); 59 pOut->SetLineColor( eColor ); 60 pOut->SetFillColor(); 61 pOut->DrawRect( rRect ); 62 pOut->Pop(); 63 } 64 } 65 66 #endif 67 68 /* class SwLayVout verwaltet das virtuelle Outputdevice 69 * Es gibt von dieser Klasse einen statischen Member am RootFrm, 70 * dieser wird in _FrmInit angelegt und in _FrmFinit zerstoert. 71 * */ 72 73 sal_Bool SwRootFrm::FlushVout() 74 { 75 if( SwRootFrm::pVout->IsFlushable() ) 76 { 77 SwRootFrm::pVout->_Flush(); 78 return sal_True; 79 } 80 return sal_False; 81 } 82 83 sal_Bool SwRootFrm::HasSameRect( const SwRect& rRect ) 84 { 85 if( SwRootFrm::pVout->IsFlushable() ) 86 return ( rRect == SwRootFrm::pVout->GetOrgRect() ); 87 return sal_False; 88 } 89 90 /** method to set mapping/pixel offset for virtual output device 91 92 OD 12.11.2002 #96272# - method implements two solutions for the mapping of 93 the virtual output device: 94 The old solution set the origin of the mapping mode, which will be used in 95 the virtual output device. This causes several paint errors, because of the 96 different roundings in the virtual output device and the original output device. 97 The new solution avoids the rounding differences between virtual and original 98 output device by setting a pixel offset at the virtual output device. 99 A define controls, which solution is used, in order to switch in escalation 100 back to old solution. 101 102 @author OD 103 104 @param _pOrgOutDev 105 input parameter - constant instance of the original output device, for which 106 the virtual output device is created. 107 108 @param _pVirDev 109 input/output parameter - instance of the virtual output device. 110 111 @param _pMapMode 112 input/output parameter - instance of the mapping mode, which will be set 113 at the virtual output device. 114 115 @param _rNewOrigin 116 input parameter - constant instance of the origin, which will be used in 117 the virtual output device 118 */ 119 // define to control, if old or new solution for setting the mapping for 120 // an virtual output device is used. 121 void SetMappingForVirtDev( const Point& _rNewOrigin, 122 MapMode* , 123 const OutputDevice* _pOrgOutDev, 124 VirtualDevice* _pVirDev ) 125 { 126 // new solution: set pixel offset at virtual output device 127 Point aPixelOffset = _pOrgOutDev->LogicToPixel( _rNewOrigin ); 128 _pVirDev->SetPixelOffset( Size( -aPixelOffset.X(), -aPixelOffset.Y() ) ); 129 } 130 131 132 /************************************************************************* 133 * SwVOut::DoesFit() 134 *************************************************************************/ 135 136 // rSize muss in Pixel-Koordinaten vorliegen! 137 sal_Bool SwLayVout::DoesFit( const Size &rNew ) 138 { 139 if( rNew.Height() > VIRTUALHEIGHT ) 140 return sal_False; 141 if( rNew.Width() <= 0 || rNew.Height() <= 0 ) 142 return sal_False; 143 if( rNew.Width() <= aSize.Width() ) 144 return sal_True; 145 if( !pVirDev ) 146 { 147 pVirDev = new VirtualDevice(); 148 pVirDev->SetLineColor(); 149 if( pOut ) 150 { 151 if( pVirDev->GetFillColor() != pOut->GetFillColor() ) 152 pVirDev->SetFillColor( pOut->GetFillColor() ); 153 } 154 } 155 156 if( rNew.Width() > aSize.Width() ) 157 { 158 aSize.Width() = rNew.Width(); 159 if( !pVirDev->SetOutputSizePixel( aSize ) ) 160 { 161 delete pVirDev; 162 pVirDev = NULL; 163 aSize.Width() = 0; 164 return sal_False; 165 } 166 } 167 return sal_True; 168 } 169 170 /************************************************************************* 171 * SwLayVout::Enter 172 *************************************************************************/ 173 /// OD 27.09.2002 #103636# - change 2nd parameter <rRect> - no longer <const> 174 /// in order to return value of class member variable <aRect>, if virtual 175 /// output is used. 176 /// <aRect> contains the rectangle that represents the area the virtual 177 /// output device is used for and that is flushed at the end. 178 void SwLayVout::Enter( ViewShell *pShell, SwRect &rRect, sal_Bool bOn ) 179 { 180 Flush(); 181 182 #ifdef DBG_UTIL 183 if( pShell->GetViewOptions()->IsTest3() ) 184 { 185 ++nCount; 186 return; 187 } 188 #endif 189 190 bOn = bOn && !nCount && rRect.HasArea() && pShell->GetWin(); 191 ++nCount; 192 if( bOn ) 193 { 194 pSh = pShell; 195 pOut = NULL; 196 OutputDevice *pO = pSh->GetOut(); 197 // Auf dem Drucker oder einem virt. Outputdevice wird nicht getrickst... 198 if( OUTDEV_WINDOW != pO->GetOutDevType() ) 199 return; 200 201 pOut = pO; 202 Size aPixSz( pOut->PixelToLogic( Size( 1,1 )) ); 203 SwRect aTmp( rRect ); 204 aTmp.SSize().Width() += aPixSz.Width()/2 + 1; 205 aTmp.SSize().Height()+= aPixSz.Height()/2 + 1; 206 Rectangle aTmpRect( pO->LogicToPixel( aTmp.SVRect() ) ); 207 208 ASSERT( !pSh->GetWin()->IsReallyVisible() || 209 aTmpRect.GetWidth() <= pSh->GetWin()->GetOutputSizePixel().Width() + 2, 210 "Paintwidth bigger than visarea?" ); 211 // Passt das Rechteck in unseren Buffer ? 212 if( !DoesFit( aTmpRect.GetSize() ) ) 213 { 214 pOut = NULL; 215 return; 216 } 217 218 aRect = SwRect( pO->PixelToLogic( aTmpRect ) ); 219 220 SetOutDev( pSh, pVirDev ); 221 222 if( pVirDev->GetFillColor() != pOut->GetFillColor() ) 223 pVirDev->SetFillColor( pOut->GetFillColor() ); 224 225 MapMode aMapMode( pOut->GetMapMode() ); 226 // OD 12.11.2002 #96272# - use method to set mapping 227 //aMapMode.SetOrigin( Point(0,0) - aRect.Pos() ); 228 ::SetMappingForVirtDev( aRect.Pos(), &aMapMode, pOut, pVirDev ); 229 230 if( aMapMode != pVirDev->GetMapMode() ) 231 pVirDev->SetMapMode( aMapMode ); 232 233 /// OD 27.09.2002 #103636# - set value of parameter <rRect> 234 rRect = aRect; 235 } 236 } 237 238 /************************************************************************* 239 * SwLayVout::Flush() 240 *************************************************************************/ 241 242 void SwLayVout::_Flush() 243 { 244 ASSERT( pVirDev, "SwLayVout::DrawOut: nothing left Toulouse" ); 245 Rectangle aTmp( aRect.SVRect() ); 246 pOut->DrawOutDev( aRect.Pos(), aRect.SSize(), 247 aRect.Pos(), aRect.SSize(), *pVirDev ); 248 SetOutDev( pSh, pOut ); 249 pOut = NULL; 250 } 251 252 253