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_svx.hxx" 26 #include <svx/sdrpaintwindow.hxx> 27 #include <svx/sdr/overlay/overlaymanagerbuffered.hxx> 28 #include <svx/svdpntv.hxx> 29 #include <vcl/gdimtf.hxx> 30 #include <vcl/svapp.hxx> 31 32 //////////////////////////////////////////////////////////////////////////////////////////////////// 33 34 SdrPreRenderDevice::SdrPreRenderDevice(OutputDevice& rOriginal) 35 : mrOutputDevice(rOriginal) 36 { 37 } 38 39 SdrPreRenderDevice::~SdrPreRenderDevice() 40 { 41 } 42 43 void SdrPreRenderDevice::PreparePreRenderDevice() 44 { 45 // compare size of maPreRenderDevice with size of visible area 46 if(maPreRenderDevice.GetOutputSizePixel() != mrOutputDevice.GetOutputSizePixel()) 47 { 48 maPreRenderDevice.SetOutputSizePixel(mrOutputDevice.GetOutputSizePixel()); 49 } 50 51 // Also compare the MapModes for zoom/scroll changes 52 if(maPreRenderDevice.GetMapMode() != mrOutputDevice.GetMapMode()) 53 { 54 maPreRenderDevice.SetMapMode(mrOutputDevice.GetMapMode()); 55 } 56 57 // #i29186# 58 maPreRenderDevice.SetDrawMode(mrOutputDevice.GetDrawMode()); 59 maPreRenderDevice.SetSettings(mrOutputDevice.GetSettings()); 60 } 61 62 void SdrPreRenderDevice::OutputPreRenderDevice(const Region& rExpandedRegion) 63 { 64 // region to pixels 65 Region aRegionPixel(mrOutputDevice.LogicToPixel(rExpandedRegion)); 66 RegionHandle aRegionHandle(aRegionPixel.BeginEnumRects()); 67 Rectangle aRegionRectanglePixel; 68 69 // MapModes off 70 sal_Bool bMapModeWasEnabledDest(mrOutputDevice.IsMapModeEnabled()); 71 sal_Bool bMapModeWasEnabledSource(maPreRenderDevice.IsMapModeEnabled()); 72 mrOutputDevice.EnableMapMode(sal_False); 73 maPreRenderDevice.EnableMapMode(sal_False); 74 75 while(aRegionPixel.GetEnumRects(aRegionHandle, aRegionRectanglePixel)) 76 { 77 // for each rectangle, copy the area 78 const Point aTopLeft(aRegionRectanglePixel.TopLeft()); 79 const Size aSize(aRegionRectanglePixel.GetSize()); 80 81 mrOutputDevice.DrawOutDev( 82 aTopLeft, aSize, 83 aTopLeft, aSize, 84 maPreRenderDevice); 85 86 #ifdef DBG_UTIL 87 // #i74769# 88 static bool bDoPaintForVisualControlRegion(false); 89 if(bDoPaintForVisualControlRegion) 90 { 91 Color aColor((((((rand()&0x7f)|0x80)<<8L)|((rand()&0x7f)|0x80))<<8L)|((rand()&0x7f)|0x80)); 92 mrOutputDevice.SetLineColor(aColor); 93 mrOutputDevice.SetFillColor(); 94 mrOutputDevice.DrawRect(aRegionRectanglePixel); 95 } 96 #endif 97 } 98 99 aRegionPixel.EndEnumRects(aRegionHandle); 100 101 mrOutputDevice.EnableMapMode(bMapModeWasEnabledDest); 102 maPreRenderDevice.EnableMapMode(bMapModeWasEnabledSource); 103 } 104 105 //////////////////////////////////////////////////////////////////////////////////////////////////// 106 107 void SdrPaintWindow::impCreateOverlayManager() 108 { 109 // not yet one created? 110 if(!mpOverlayManager) 111 { 112 // is it a window? 113 if(OUTDEV_WINDOW == GetOutputDevice().GetOutDevType()) 114 { 115 // decide which OverlayManager to use 116 if(GetPaintView().IsBufferedOverlayAllowed() && mbUseBuffer) 117 { 118 // buffered OverlayManager, buffers it's background and refreshes from there 119 // for pure overlay changes (no system redraw). The 3rd parameter specifies 120 // if that refresh itself will use a 2nd vdev to avoid flickering. 121 // Also hand over the evtl. existing old OverlayManager; this means to take over 122 // the registered OverlayObjects from it 123 mpOverlayManager = new ::sdr::overlay::OverlayManagerBuffered(GetOutputDevice(), true); 124 } 125 else 126 { 127 // unbuffered OverlayManager, just invalidates places where changes 128 // take place 129 // Also hand over the evtl. existing old OverlayManager; this means to take over 130 // the registered OverlayObjects from it 131 mpOverlayManager = new ::sdr::overlay::OverlayManager(GetOutputDevice()); 132 } 133 134 OSL_ENSURE(mpOverlayManager, "SdrPaintWindow::SdrPaintWindow: Could not allocate an overlayManager (!)"); 135 136 // Request a repaint so that the buffered overlay manager fills 137 // its buffer properly. This is a workaround for missing buffer 138 // updates. 139 Window* pWindow = dynamic_cast<Window*>(&GetOutputDevice()); 140 if (pWindow != NULL) 141 pWindow->Invalidate(); 142 143 Color aColA(GetPaintView().getOptionsDrawinglayer().GetStripeColorA()); 144 Color aColB(GetPaintView().getOptionsDrawinglayer().GetStripeColorB()); 145 146 if(Application::GetSettings().GetStyleSettings().GetHighContrastMode()) 147 { 148 aColA = aColB = Application::GetSettings().GetStyleSettings().GetHighlightColor(); 149 aColB.Invert(); 150 } 151 152 mpOverlayManager->setStripeColorA(aColA); 153 mpOverlayManager->setStripeColorB(aColB); 154 mpOverlayManager->setStripeLengthPixel(GetPaintView().getOptionsDrawinglayer().GetStripeLength()); 155 } 156 } 157 } 158 159 SdrPaintWindow::SdrPaintWindow(SdrPaintView& rNewPaintView, OutputDevice& rOut) 160 : mrOutputDevice(rOut), 161 mrPaintView(rNewPaintView), 162 mpOverlayManager(0L), 163 mpPreRenderDevice(0L), 164 mbTemporaryTarget(false), // #i72889# 165 mbUseBuffer(true) 166 { 167 } 168 169 SdrPaintWindow::~SdrPaintWindow() 170 { 171 if(mpOverlayManager) 172 { 173 delete mpOverlayManager; 174 mpOverlayManager = 0L; 175 } 176 177 DestroyPreRenderDevice(); 178 } 179 180 ::sdr::overlay::OverlayManager* SdrPaintWindow::GetOverlayManager() const 181 { 182 if(!mpOverlayManager) 183 { 184 // Create buffered overlay manager by default. 185 const_cast< SdrPaintWindow* >(this)->impCreateOverlayManager(); 186 } 187 188 return mpOverlayManager; 189 } 190 191 Rectangle SdrPaintWindow::GetVisibleArea() const 192 { 193 Size aVisSizePixel(GetOutputDevice().GetOutputSizePixel()); 194 return Rectangle(GetOutputDevice().PixelToLogic(Rectangle(Point(0,0), aVisSizePixel))); 195 } 196 197 sal_Bool SdrPaintWindow::OutputToRecordingMetaFile() const 198 { 199 GDIMetaFile* pMetaFile = mrOutputDevice.GetConnectMetaFile(); 200 return (pMetaFile && pMetaFile->IsRecord() && !pMetaFile->IsPause()); 201 } 202 203 void SdrPaintWindow::PreparePreRenderDevice() 204 { 205 const sal_Bool bPrepareBufferedOutput( 206 mrPaintView.IsBufferedOutputAllowed() 207 && !OutputToPrinter() 208 && !OutputToVirtualDevice() 209 && !OutputToRecordingMetaFile()); 210 211 if(bPrepareBufferedOutput) 212 { 213 if(!mpPreRenderDevice) 214 { 215 mpPreRenderDevice = new SdrPreRenderDevice(mrOutputDevice); 216 } 217 } 218 else 219 { 220 DestroyPreRenderDevice(); 221 } 222 223 if(mpPreRenderDevice) 224 { 225 mpPreRenderDevice->PreparePreRenderDevice(); 226 } 227 } 228 229 void SdrPaintWindow::DestroyPreRenderDevice() 230 { 231 if(mpPreRenderDevice) 232 { 233 delete mpPreRenderDevice; 234 mpPreRenderDevice = 0L; 235 } 236 } 237 238 void SdrPaintWindow::OutputPreRenderDevice(const Region& rExpandedRegion) 239 { 240 if(mpPreRenderDevice) 241 { 242 mpPreRenderDevice->OutputPreRenderDevice(rExpandedRegion); 243 } 244 } 245 246 // #i73602# add flag if buffer shall be used 247 void SdrPaintWindow::DrawOverlay(const Region& rRegion) 248 { 249 // ## force creation of OverlayManager since the first repaint needs to 250 // save the background to get a controlled start into overlay mechanism 251 impCreateOverlayManager(); 252 253 if(mpOverlayManager && !OutputToPrinter()) 254 { 255 if(mpPreRenderDevice) 256 { 257 mpOverlayManager->completeRedraw(rRegion, &mpPreRenderDevice->GetPreRenderDevice()); 258 } 259 else 260 { 261 mpOverlayManager->completeRedraw(rRegion); 262 } 263 } 264 } 265 266 void SdrPaintWindow::HideOverlay(const Region& rRegion) 267 { 268 if(mpOverlayManager && !OutputToPrinter()) 269 { 270 if(!mpPreRenderDevice) 271 { 272 mpOverlayManager->restoreBackground(rRegion); 273 } 274 } 275 } 276 277 const Region& SdrPaintWindow::GetRedrawRegion() const 278 { 279 return maRedrawRegion; 280 } 281 282 void SdrPaintWindow::SetRedrawRegion(const Region& rNew) 283 { 284 maRedrawRegion = rNew; 285 } 286 287 //////////////////////////////////////////////////////////////////////////////////////////////////// 288 // eof 289