LibreOffice Module vcl (master)  1
map.cxx
Go to the documentation of this file.
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 <sal/config.h>
21 
22 #include <tools/bigint.hxx>
23 #include <tools/debug.hxx>
24 #include <vcl/cursor.hxx>
25 #include <vcl/gdimtf.hxx>
26 #include <vcl/lineinfo.hxx>
27 #include <vcl/metaact.hxx>
28 #include <vcl/virdev.hxx>
29 #include <vcl/wrkwin.hxx>
30 #include <sal/log.hxx>
31 #include <osl/diagnose.h>
32 
33 #include <ImplOutDevData.hxx>
34 #include <svdata.hxx>
35 #include <window.h>
36 
38 #include <tools/UnitConversion.hxx>
39 
40 /*
41 Reduces accuracy until it is a fraction (should become
42 ctor fraction once); we could also do this with BigInts
43 */
44 
46 {
47  if( nD1 == 0 || nD2 == 0 ) //under these bad circumstances the following while loop will be endless
48  {
49  SAL_WARN("vcl.gdi", "Invalid parameter for ImplMakeFraction");
50  return Fraction( 1, 1 );
51  }
52 
53  tools::Long i = 1;
54 
55  if ( nN1 < 0 ) { i = -i; nN1 = -nN1; }
56  if ( nN2 < 0 ) { i = -i; nN2 = -nN2; }
57  if ( nD1 < 0 ) { i = -i; nD1 = -nD1; }
58  if ( nD2 < 0 ) { i = -i; nD2 = -nD2; }
59  // all positive; i sign
60 
61  Fraction aF = Fraction( i*nN1, nD1 ) * Fraction( nN2, nD2 );
62 
63  while ( !aF.IsValid() ) {
64  if ( nN1 > nN2 )
65  nN1 = (nN1 + 1) / 2;
66  else
67  nN2 = (nN2 + 1) / 2;
68  if ( nD1 > nD2 )
69  nD1 = (nD1 + 1) / 2;
70  else
71  nD2 = (nD2 + 1) / 2;
72 
73  aF = Fraction( i*nN1, nD1 ) * Fraction( nN2, nD2 );
74  }
75 
76  aF.ReduceInaccurate(32);
77  return aF;
78 }
79 
80 static auto setMapRes(ImplMapRes& rMapRes, const o3tl::Length eUnit)
81 {
82  const auto [nNum, nDen] = o3tl::getConversionMulDiv(eUnit, o3tl::Length::in);
83  rMapRes.mnMapScNumX = rMapRes.mnMapScNumY = nNum;
84  rMapRes.mnMapScDenomX = rMapRes.mnMapScDenomY = nDen;
85 };
86 
87 static void ImplCalcMapResolution( const MapMode& rMapMode,
88  tools::Long nDPIX, tools::Long nDPIY, ImplMapRes& rMapRes )
89 {
90  switch ( rMapMode.GetMapUnit() )
91  {
92  case MapUnit::MapRelative:
93  break;
94  case MapUnit::Map100thMM:
96  break;
97  case MapUnit::Map10thMM:
98  setMapRes(rMapRes, o3tl::Length::mm10);
99  break;
100  case MapUnit::MapMM:
101  setMapRes(rMapRes, o3tl::Length::mm);
102  break;
103  case MapUnit::MapCM:
104  setMapRes(rMapRes, o3tl::Length::cm);
105  break;
106  case MapUnit::Map1000thInch:
108  break;
109  case MapUnit::Map100thInch:
110  setMapRes(rMapRes, o3tl::Length::in100);
111  break;
112  case MapUnit::Map10thInch:
113  setMapRes(rMapRes, o3tl::Length::in10);
114  break;
115  case MapUnit::MapInch:
116  setMapRes(rMapRes, o3tl::Length::in);
117  break;
118  case MapUnit::MapPoint:
119  setMapRes(rMapRes, o3tl::Length::pt);
120  break;
121  case MapUnit::MapTwip:
122  setMapRes(rMapRes, o3tl::Length::twip);
123  break;
124  case MapUnit::MapPixel:
125  rMapRes.mnMapScNumX = 1;
126  rMapRes.mnMapScDenomX = nDPIX;
127  rMapRes.mnMapScNumY = 1;
128  rMapRes.mnMapScDenomY = nDPIY;
129  break;
130  case MapUnit::MapSysFont:
131  case MapUnit::MapAppFont:
132  {
133  ImplSVData* pSVData = ImplGetSVData();
134  if ( !pSVData->maGDIData.mnAppFontX )
135  {
136  if (pSVData->maFrameData.mpFirstFrame)
138  else
139  {
140  ScopedVclPtrInstance<WorkWindow> pWin( nullptr, 0 );
142  }
143  }
144  rMapRes.mnMapScNumX = pSVData->maGDIData.mnAppFontX;
145  rMapRes.mnMapScDenomX = nDPIX * 40;
146  rMapRes.mnMapScNumY = pSVData->maGDIData.mnAppFontY;
147  rMapRes.mnMapScDenomY = nDPIY * 80;
148  }
149  break;
150  default:
151  OSL_FAIL( "unhandled MapUnit" );
152  break;
153  }
154 
155  const Fraction& aScaleX = rMapMode.GetScaleX();
156  const Fraction& aScaleY = rMapMode.GetScaleY();
157 
158  // set offset according to MapMode
159  Point aOrigin = rMapMode.GetOrigin();
160  if ( rMapMode.GetMapUnit() != MapUnit::MapRelative )
161  {
162  rMapRes.mnMapOfsX = aOrigin.X();
163  rMapRes.mnMapOfsY = aOrigin.Y();
164  }
165  else
166  {
167  auto nXNumerator = aScaleX.GetNumerator();
168  auto nYNumerator = aScaleY.GetNumerator();
169  assert(nXNumerator != 0 && nYNumerator != 0);
170 
171  BigInt aX( rMapRes.mnMapOfsX );
172  aX *= BigInt( aScaleX.GetDenominator() );
173  if ( rMapRes.mnMapOfsX >= 0 )
174  {
175  if (nXNumerator >= 0)
176  aX += BigInt(nXNumerator / 2);
177  else
178  aX -= BigInt((nXNumerator + 1) / 2);
179  }
180  else
181  {
182  if (nXNumerator >= 0 )
183  aX -= BigInt((nXNumerator - 1) / 2);
184  else
185  aX += BigInt(nXNumerator / 2);
186  }
187  aX /= BigInt(nXNumerator);
188  rMapRes.mnMapOfsX = static_cast<tools::Long>(aX) + aOrigin.X();
189  BigInt aY( rMapRes.mnMapOfsY );
190  aY *= BigInt( aScaleY.GetDenominator() );
191  if( rMapRes.mnMapOfsY >= 0 )
192  {
193  if (nYNumerator >= 0)
194  aY += BigInt(nYNumerator / 2);
195  else
196  aY -= BigInt((nYNumerator + 1) / 2);
197  }
198  else
199  {
200  if (nYNumerator >= 0)
201  aY -= BigInt((nYNumerator - 1) / 2);
202  else
203  aY += BigInt(nYNumerator / 2);
204  }
205  aY /= BigInt(nYNumerator);
206  rMapRes.mnMapOfsY = static_cast<tools::Long>(aY) + aOrigin.Y();
207  }
208 
209  // calculate scaling factor according to MapMode
210  // aTemp? = rMapRes.mnMapSc? * aScale?
211  Fraction aTempX = ImplMakeFraction( rMapRes.mnMapScNumX,
212  aScaleX.GetNumerator(),
213  rMapRes.mnMapScDenomX,
214  aScaleX.GetDenominator() );
215  Fraction aTempY = ImplMakeFraction( rMapRes.mnMapScNumY,
216  aScaleY.GetNumerator(),
217  rMapRes.mnMapScDenomY,
218  aScaleY.GetDenominator() );
219  rMapRes.mnMapScNumX = aTempX.GetNumerator();
220  rMapRes.mnMapScDenomX = aTempX.GetDenominator();
221  rMapRes.mnMapScNumY = aTempY.GetNumerator();
222  rMapRes.mnMapScDenomY = aTempY.GetDenominator();
223 }
224 
225 // #i75163#
227 {
228  if(!mpOutDevData)
229  return;
230 
231  if(mpOutDevData->mpViewTransform)
232  {
233  delete mpOutDevData->mpViewTransform;
234  mpOutDevData->mpViewTransform = nullptr;
235  }
236 
237  if(mpOutDevData->mpInverseViewTransform)
238  {
239  delete mpOutDevData->mpInverseViewTransform;
240  mpOutDevData->mpInverseViewTransform = nullptr;
241  }
242 }
243 
245  tools::Long nMapDenom)
246 {
247  assert(nDPI > 0);
248  assert(nMapDenom != 0);
249  if constexpr (sizeof(tools::Long) >= 8)
250  {
251  assert(nMapNum >= 0);
252  //detect overflows
253  assert(nMapNum == 0
254  || std::abs(n) < std::numeric_limits<tools::Long>::max() / nMapNum / nDPI);
255  }
256  sal_Int64 n64 = n;
257  n64 *= nMapNum;
258  n64 *= nDPI;
259  if (nMapDenom == 1)
260  n = static_cast<tools::Long>(n64);
261  else
262  {
263  n64 = 2 * n64 / nMapDenom;
264  if (n64 < 0)
265  --n64;
266  else
267  ++n64;
268  n = static_cast<tools::Long>(n64 / 2);
269  }
270  return n;
271 }
272 
273 static double ImplLogicToPixel(double n, tools::Long nDPI, tools::Long nMapNum,
274  tools::Long nMapDenom)
275 {
276  assert(nDPI > 0);
277  assert(nMapDenom != 0);
278  return n * nMapNum * nDPI / nMapDenom;
279 }
280 
282  tools::Long nMapDenom)
283 {
284  assert(nDPI > 0);
285  if (nMapNum == 0)
286  return 0;
287  sal_Int64 nDenom = nDPI;
288  nDenom *= nMapNum;
289 
290  sal_Int64 n64 = n;
291  n64 *= nMapDenom;
292  if (nDenom == 1)
293  n = static_cast<tools::Long>(n64);
294  else
295  {
296  n64 = 2 * n64 / nDenom;
297  if (n64 < 0)
298  --n64;
299  else
300  ++n64;
301  n = static_cast<tools::Long>(n64 / 2);
302  }
303  return n;
304 }
305 
307 {
308  if ( !mbMap )
309  return nX+mnOutOffX;
310 
313 }
314 
316 {
317  if ( !mbMap )
318  return nY+mnOutOffY;
319 
322 }
323 
325 {
326  if ( !mbMap )
327  return nWidth;
328 
330 }
331 
333 {
334  if ( !mbMap )
335  return nHeight;
336 
338 }
339 
340 float OutputDevice::ImplFloatLogicHeightToDevicePixel( float fLogicHeight) const
341 {
342  if( !mbMap)
343  return fLogicHeight;
344  float fPixelHeight = (fLogicHeight * mnDPIY * maMapRes.mnMapScNumY) / maMapRes.mnMapScDenomY;
345  return fPixelHeight;
346 }
347 
349 {
350  if ( !mbMap )
351  return nWidth;
352 
354 }
355 
357 {
358  if ( !mbMap )
359  return nHeight;
360 
362 }
363 
364 Point OutputDevice::ImplLogicToDevicePixel( const Point& rLogicPt ) const
365 {
366  if ( !mbMap )
367  return Point( rLogicPt.X()+mnOutOffX, rLogicPt.Y()+mnOutOffY );
368 
369  return Point( ImplLogicToPixel( rLogicPt.X() + maMapRes.mnMapOfsX, mnDPIX,
371  ImplLogicToPixel( rLogicPt.Y() + maMapRes.mnMapOfsY, mnDPIY,
373 }
374 
376 {
377  if ( !mbMap )
378  return rLogicSize;
379 
380  return Size( ImplLogicToPixel( rLogicSize.Width(), mnDPIX,
382  ImplLogicToPixel( rLogicSize.Height(), mnDPIY,
384 }
385 
387 {
388  // tdf#141761 IsEmpty() removed
389  // Even if rLogicRect.IsEmpty(), transform of the Position contained
390  // in the Rectangle is necessary. Due to Rectangle::Right() returning
391  // Left() when IsEmpty(), the code *could* stay unchanged (same for Bottom),
392  // but:
393  // The Rectangle constructor used with the four tools::Long values does not
394  // check for IsEmpty(), so to keep that state correct there are two possibilities:
395  // (1) Add a test to the Rectangle constructor in question
396  // (2) Do it handish here
397  // I have tried (1) first, but test Test::test_rectangle() claims that for
398  // tools::Rectangle aRect(1, 1, 1, 1);
399  // tools::Long(1) == aRect.GetWidth()
400  // tools::Long(0) == aRect.getWidth()
401  // (remember: this means Left == Right == 1 -> GetWidth => 1, getWidth == 0)
402  // so indeed the 1's have to go uncommented/unchecked into the data body
403  // of rectangle. Switching to (2) *is* needed, doing so
404  tools::Rectangle aRetval;
405 
406  if ( !mbMap )
407  {
408  aRetval = tools::Rectangle(
409  rLogicRect.Left()+mnOutOffX,
410  rLogicRect.Top()+mnOutOffY,
411  rLogicRect.IsWidthEmpty() ? 0 : rLogicRect.Right()+mnOutOffX,
412  rLogicRect.IsHeightEmpty() ? 0 : rLogicRect.Bottom()+mnOutOffY );
413  }
414  else
415  {
416  aRetval = tools::Rectangle(
421  }
422 
423  if(rLogicRect.IsWidthEmpty())
424  aRetval.SetWidthEmpty();
425 
426  if(rLogicRect.IsHeightEmpty())
427  aRetval.SetHeightEmpty();
428 
429  return aRetval;
430 }
431 
433 {
434  if ( !mbMap && !mnOutOffX && !mnOutOffY )
435  return rLogicPoly;
436 
437  sal_uInt16 i;
438  sal_uInt16 nPoints = rLogicPoly.GetSize();
439  tools::Polygon aPoly( rLogicPoly );
440 
441  // get pointer to Point-array (copy data)
442  const Point* pPointAry = aPoly.GetConstPointAry();
443 
444  if ( mbMap )
445  {
446  for ( i = 0; i < nPoints; i++ )
447  {
448  const Point& rPt = pPointAry[i];
453  aPoly[i] = aPt;
454  }
455  }
456  else
457  {
458  for ( i = 0; i < nPoints; i++ )
459  {
460  Point aPt = pPointAry[i];
461  aPt.AdjustX(mnOutOffX );
462  aPt.AdjustY(mnOutOffY );
463  aPoly[i] = aPt;
464  }
465  }
466 
467  return aPoly;
468 }
469 
471 {
472  if (!mbMap && !mnOutOffX && !mnOutOffY)
473  return rLogicPoly;
474 
475  sal_uInt32 nPoints = rLogicPoly.count();
476  basegfx::B2DPolygon aPoly(rLogicPoly);
477 
478  if (mbMap)
479  {
480  for (sal_uInt32 i = 0; i < nPoints; ++i)
481  {
482  const basegfx::B2DPoint& rPt = aPoly.getB2DPoint(i);
487  aPoly.setB2DPoint(i, aPt);
488  }
489  }
490  else
491  {
492  for (sal_uInt32 i = 0; i < nPoints; ++i)
493  {
494  const basegfx::B2DPoint& rPt = aPoly.getB2DPoint(i);
495  basegfx::B2DPoint aPt(rPt.getX() + mnOutOffX, rPt.getY() + mnOutOffY);
496  aPoly.setB2DPoint(i, aPt);
497  }
498  }
499 
500  return aPoly;
501 }
502 
504 {
505  if ( !mbMap && !mnOutOffX && !mnOutOffY )
506  return rLogicPolyPoly;
507 
508  tools::PolyPolygon aPolyPoly( rLogicPolyPoly );
509  sal_uInt16 nPoly = aPolyPoly.Count();
510  for( sal_uInt16 i = 0; i < nPoly; i++ )
511  {
512  tools::Polygon& rPoly = aPolyPoly[i];
513  rPoly = ImplLogicToDevicePixel( rPoly );
514  }
515  return aPolyPoly;
516 }
517 
519 {
520  LineInfo aInfo( rLineInfo );
521 
522  if( aInfo.GetStyle() == LineStyle::Dash )
523  {
524  if( aInfo.GetDotCount() && aInfo.GetDotLen() )
525  aInfo.SetDotLen( std::max( ImplLogicWidthToDevicePixel( aInfo.GetDotLen() ), tools::Long(1) ) );
526  else
527  aInfo.SetDotCount( 0 );
528 
529  if( aInfo.GetDashCount() && aInfo.GetDashLen() )
530  aInfo.SetDashLen( std::max( ImplLogicWidthToDevicePixel( aInfo.GetDashLen() ), tools::Long(1) ) );
531  else
532  aInfo.SetDashCount( 0 );
533 
534  aInfo.SetDistance( ImplLogicWidthToDevicePixel( aInfo.GetDistance() ) );
535 
536  if( ( !aInfo.GetDashCount() && !aInfo.GetDotCount() ) || !aInfo.GetDistance() )
537  aInfo.SetStyle( LineStyle::Solid );
538  }
539 
540  aInfo.SetWidth( ImplLogicWidthToDevicePixel( aInfo.GetWidth() ) );
541 
542  return aInfo;
543 }
544 
546 {
547  // tdf#141761 see comments above, IsEmpty() removed
548  tools::Rectangle aRetval;
549 
550  if ( !mbMap )
551  {
552  aRetval = tools::Rectangle(
553  rPixelRect.Left()-mnOutOffX,
554  rPixelRect.Top()-mnOutOffY,
555  rPixelRect.IsWidthEmpty() ? 0 : rPixelRect.Right()-mnOutOffX,
556  rPixelRect.IsHeightEmpty() ? 0 : rPixelRect.Bottom()-mnOutOffY );
557  }
558  else
559  {
560  aRetval = tools::Rectangle(
565  }
566 
567  if(rPixelRect.IsWidthEmpty())
568  aRetval.SetWidthEmpty();
569 
570  if(rPixelRect.IsHeightEmpty())
571  aRetval.SetHeightEmpty();
572 
573  return aRetval;
574 }
575 
577 {
578  if ( !mnOutOffX && !mnOutOffY )
579  return rRegion;
580 
581  vcl::Region aRegion( rRegion );
583  return aRegion;
584 }
585 
586 void OutputDevice::EnableMapMode( bool bEnable )
587 {
588  mbMap = bEnable;
589 
590  if( mpAlphaVDev )
591  mpAlphaVDev->EnableMapMode( bEnable );
592 }
593 
595 {
596 
597  if ( mpMetaFile )
599 
600  if ( mbMap || !maMapMode.IsDefault() )
601  {
602  mbMap = false;
603  maMapMode = MapMode();
604 
605  // create new objects (clip region are not re-scaled)
606  mbNewFont = true;
607  mbInitFont = true;
609 
610  // #106426# Adapt logical offset when changing mapmode
611  mnOutOffLogicX = mnOutOffOrigX; // no mapping -> equal offsets
613 
614  // #i75163#
616  }
617 
618  if( mpAlphaVDev )
620 }
621 
622 void OutputDevice::SetMapMode( const MapMode& rNewMapMode )
623 {
624 
625  bool bRelMap = (rNewMapMode.GetMapUnit() == MapUnit::MapRelative);
626 
627  if ( mpMetaFile )
628  {
629  mpMetaFile->AddAction( new MetaMapModeAction( rNewMapMode ) );
630  }
631 
632  // do nothing if MapMode was not changed
633  if ( maMapMode == rNewMapMode )
634  return;
635 
636  if( mpAlphaVDev )
637  mpAlphaVDev->SetMapMode( rNewMapMode );
638 
639  // if default MapMode calculate nothing
640  bool bOldMap = mbMap;
641  mbMap = !rNewMapMode.IsDefault();
642  if ( mbMap )
643  {
644  // if only the origin is converted, do not scale new
645  if ( (rNewMapMode.GetMapUnit() == maMapMode.GetMapUnit()) &&
646  (rNewMapMode.GetScaleX() == maMapMode.GetScaleX()) &&
647  (rNewMapMode.GetScaleY() == maMapMode.GetScaleY()) &&
648  (bOldMap == mbMap) )
649  {
650  // set offset
651  Point aOrigin = rNewMapMode.GetOrigin();
652  maMapRes.mnMapOfsX = aOrigin.X();
653  maMapRes.mnMapOfsY = aOrigin.Y();
654  maMapMode = rNewMapMode;
655 
656  // #i75163#
658 
659  return;
660  }
661  if ( !bOldMap && bRelMap )
662  {
663  maMapRes.mnMapScNumX = 1;
664  maMapRes.mnMapScNumY = 1;
667  maMapRes.mnMapOfsX = 0;
668  maMapRes.mnMapOfsY = 0;
669  }
670 
671  // calculate new MapMode-resolution
673  }
674 
675  // set new MapMode
676  if ( bRelMap )
677  {
679  // aScale? = maMapMode.GetScale?() * rNewMapMode.GetScale?()
681  rNewMapMode.GetScaleX().GetNumerator(),
683  rNewMapMode.GetScaleX().GetDenominator() );
685  rNewMapMode.GetScaleY().GetNumerator(),
687  rNewMapMode.GetScaleY().GetDenominator() );
688  maMapMode.SetOrigin( aOrigin );
689  maMapMode.SetScaleX( aScaleX );
690  maMapMode.SetScaleY( aScaleY );
691  }
692  else
693  maMapMode = rNewMapMode;
694 
695  // create new objects (clip region are not re-scaled)
696  mbNewFont = true;
697  mbInitFont = true;
699 
700  // #106426# Adapt logical offset when changing mapmode
705 
706  // #i75163#
708 }
709 
710 void OutputDevice::SetMetafileMapMode(const MapMode& rNewMapMode, bool bIsRecord)
711 {
712  if (bIsRecord)
713  SetRelativeMapMode(rNewMapMode);
714  else
715  SetMapMode(rNewMapMode);
716 }
717 
719 
720 void OutputDevice::SetRelativeMapMode( const MapMode& rNewMapMode )
721 {
722  // do nothing if MapMode did not change
723  if ( maMapMode == rNewMapMode )
724  return;
725 
726  MapUnit eOld = maMapMode.GetMapUnit();
727  MapUnit eNew = rNewMapMode.GetMapUnit();
728 
729  // a?F = rNewMapMode.GetScale?() / maMapMode.GetScale?()
730  Fraction aXF = ImplMakeFraction( rNewMapMode.GetScaleX().GetNumerator(),
732  rNewMapMode.GetScaleX().GetDenominator(),
734  Fraction aYF = ImplMakeFraction( rNewMapMode.GetScaleY().GetNumerator(),
736  rNewMapMode.GetScaleY().GetDenominator(),
738 
739  Point aPt( LogicToLogic( Point(), nullptr, &rNewMapMode ) );
740  if ( eNew != eOld )
741  {
742  if ( eOld > MapUnit::MapPixel )
743  {
744  SAL_WARN( "vcl.gdi", "Not implemented MapUnit" );
745  }
746  else if ( eNew > MapUnit::MapPixel )
747  {
748  SAL_WARN( "vcl.gdi", "Not implemented MapUnit" );
749  }
750  else
751  {
752  const auto eFrom = MapToO3tlLength(eOld, o3tl::Length::in);
753  const auto eTo = MapToO3tlLength(eNew, o3tl::Length::in);
754  const auto& [mul, div] = o3tl::getConversionMulDiv(eFrom, eTo);
755  Fraction aF(div, mul);
756 
757  // a?F = a?F * aF
758  aXF = ImplMakeFraction( aXF.GetNumerator(), aF.GetNumerator(),
759  aXF.GetDenominator(), aF.GetDenominator() );
760  aYF = ImplMakeFraction( aYF.GetNumerator(), aF.GetNumerator(),
761  aYF.GetDenominator(), aF.GetDenominator() );
762  if ( eOld == MapUnit::MapPixel )
763  {
764  aXF *= Fraction( mnDPIX, 1 );
765  aYF *= Fraction( mnDPIY, 1 );
766  }
767  else if ( eNew == MapUnit::MapPixel )
768  {
769  aXF *= Fraction( 1, mnDPIX );
770  aYF *= Fraction( 1, mnDPIY );
771  }
772  }
773  }
774 
775  MapMode aNewMapMode( MapUnit::MapRelative, Point( -aPt.X(), -aPt.Y() ), aXF, aYF );
776  SetMapMode( aNewMapMode );
777 
778  if ( eNew != eOld )
779  maMapMode = rNewMapMode;
780 
781  // #106426# Adapt logical offset when changing MapMode
786 
787  if( mpAlphaVDev )
788  mpAlphaVDev->SetRelativeMapMode( rNewMapMode );
789 }
790 
791 // #i75163#
793 {
794  if(mbMap && mpOutDevData)
795  {
796  if(!mpOutDevData->mpViewTransform)
797  {
798  mpOutDevData->mpViewTransform = new basegfx::B2DHomMatrix;
799 
800  const double fScaleFactorX(static_cast<double>(mnDPIX) * static_cast<double>(maMapRes.mnMapScNumX) / static_cast<double>(maMapRes.mnMapScDenomX));
801  const double fScaleFactorY(static_cast<double>(mnDPIY) * static_cast<double>(maMapRes.mnMapScNumY) / static_cast<double>(maMapRes.mnMapScDenomY));
802  const double fZeroPointX((static_cast<double>(maMapRes.mnMapOfsX) * fScaleFactorX) + static_cast<double>(mnOutOffOrigX));
803  const double fZeroPointY((static_cast<double>(maMapRes.mnMapOfsY) * fScaleFactorY) + static_cast<double>(mnOutOffOrigY));
804 
805  mpOutDevData->mpViewTransform->set(0, 0, fScaleFactorX);
806  mpOutDevData->mpViewTransform->set(1, 1, fScaleFactorY);
807  mpOutDevData->mpViewTransform->set(0, 2, fZeroPointX);
808  mpOutDevData->mpViewTransform->set(1, 2, fZeroPointY);
809  }
810 
811  return *mpOutDevData->mpViewTransform;
812  }
813  else
814  {
815  return basegfx::B2DHomMatrix();
816  }
817 }
818 
819 // #i75163#
821 {
822  if(mbMap && mpOutDevData)
823  {
824  if(!mpOutDevData->mpInverseViewTransform)
825  {
827  mpOutDevData->mpInverseViewTransform = new basegfx::B2DHomMatrix(*mpOutDevData->mpViewTransform);
828  mpOutDevData->mpInverseViewTransform->invert();
829  }
830 
831  return *mpOutDevData->mpInverseViewTransform;
832  }
833  else
834  {
835  return basegfx::B2DHomMatrix();
836  }
837 }
838 
839 // #i75163#
841 {
842  // #i82615#
843  ImplMapRes aMapRes;
844  ImplCalcMapResolution(rMapMode, mnDPIX, mnDPIY, aMapRes);
845 
846  basegfx::B2DHomMatrix aTransform;
847 
848  const double fScaleFactorX(static_cast<double>(mnDPIX) * static_cast<double>(aMapRes.mnMapScNumX) / static_cast<double>(aMapRes.mnMapScDenomX));
849  const double fScaleFactorY(static_cast<double>(mnDPIY) * static_cast<double>(aMapRes.mnMapScNumY) / static_cast<double>(aMapRes.mnMapScDenomY));
850  const double fZeroPointX((static_cast<double>(aMapRes.mnMapOfsX) * fScaleFactorX) + static_cast<double>(mnOutOffOrigX));
851  const double fZeroPointY((static_cast<double>(aMapRes.mnMapOfsY) * fScaleFactorY) + static_cast<double>(mnOutOffOrigY));
852 
853  aTransform.set(0, 0, fScaleFactorX);
854  aTransform.set(1, 1, fScaleFactorY);
855  aTransform.set(0, 2, fZeroPointX);
856  aTransform.set(1, 2, fZeroPointY);
857 
858  return aTransform;
859 }
860 
861 // #i75163#
863 {
864  basegfx::B2DHomMatrix aMatrix( GetViewTransformation( rMapMode ) );
865  aMatrix.invert();
866  return aMatrix;
867 }
868 
870 {
871  basegfx::B2DHomMatrix aTransformation = GetViewTransformation();
872  // TODO: is it worth to cache the transformed result?
873  if( mnOutOffX || mnOutOffY )
874  aTransformation.translate( mnOutOffX, mnOutOffY );
875  return aTransformation;
876 }
877 
878 Point OutputDevice::LogicToPixel( const Point& rLogicPt ) const
879 {
880 
881  if ( !mbMap )
882  return rLogicPt;
883 
884  return Point( ImplLogicToPixel( rLogicPt.X() + maMapRes.mnMapOfsX, mnDPIX,
886  ImplLogicToPixel( rLogicPt.Y() + maMapRes.mnMapOfsY, mnDPIY,
888 }
889 
890 Size OutputDevice::LogicToPixel( const Size& rLogicSize ) const
891 {
892 
893  if ( !mbMap )
894  return rLogicSize;
895 
896  return Size( ImplLogicToPixel( rLogicSize.Width(), mnDPIX,
898  ImplLogicToPixel( rLogicSize.Height(), mnDPIY,
900 }
901 
903 {
904  // tdf#141761 see comments above, IsEmpty() removed
905  if ( !mbMap )
906  return rLogicRect;
907 
908  tools::Rectangle aRetval(
913 
914  if(rLogicRect.IsWidthEmpty())
915  aRetval.SetWidthEmpty();
916 
917  if(rLogicRect.IsHeightEmpty())
918  aRetval.SetHeightEmpty();
919 
920  return aRetval;
921 }
922 
924 {
925 
926  if ( !mbMap )
927  return rLogicPoly;
928 
929  sal_uInt16 i;
930  sal_uInt16 nPoints = rLogicPoly.GetSize();
931  tools::Polygon aPoly( rLogicPoly );
932 
933  // get pointer to Point-array (copy data)
934  const Point* pPointAry = aPoly.GetConstPointAry();
935 
936  for ( i = 0; i < nPoints; i++ )
937  {
938  const Point* pPt = &(pPointAry[i]);
939  Point aPt;
940  aPt.setX( ImplLogicToPixel( pPt->X() + maMapRes.mnMapOfsX, mnDPIX,
942  aPt.setY( ImplLogicToPixel( pPt->Y() + maMapRes.mnMapOfsY, mnDPIY,
944  aPoly[i] = aPt;
945  }
946 
947  return aPoly;
948 }
949 
951 {
952 
953  if ( !mbMap )
954  return rLogicPolyPoly;
955 
956  tools::PolyPolygon aPolyPoly( rLogicPolyPoly );
957  sal_uInt16 nPoly = aPolyPoly.Count();
958  for( sal_uInt16 i = 0; i < nPoly; i++ )
959  {
960  tools::Polygon& rPoly = aPolyPoly[i];
961  rPoly = LogicToPixel( rPoly );
962  }
963  return aPolyPoly;
964 }
965 
967 {
968  basegfx::B2DPolyPolygon aTransformedPoly = rLogicPolyPoly;
969  const basegfx::B2DHomMatrix& rTransformationMatrix = GetViewTransformation();
970  aTransformedPoly.transform( rTransformationMatrix );
971  return aTransformedPoly;
972 }
973 
975 {
976 
977  if(!mbMap || rLogicRegion.IsNull() || rLogicRegion.IsEmpty())
978  {
979  return rLogicRegion;
980  }
981 
982  vcl::Region aRegion;
983 
984  if(rLogicRegion.getB2DPolyPolygon())
985  {
986  aRegion = vcl::Region(LogicToPixel(*rLogicRegion.getB2DPolyPolygon()));
987  }
988  else if(rLogicRegion.getPolyPolygon())
989  {
990  aRegion = vcl::Region(LogicToPixel(*rLogicRegion.getPolyPolygon()));
991  }
992  else if(rLogicRegion.getRegionBand())
993  {
994  RectangleVector aRectangles;
995  rLogicRegion.GetRegionRectangles(aRectangles);
996  const RectangleVector& rRectangles(aRectangles); // needed to make the '!=' work
997 
998  // make reverse run to fill new region bottom-up, this will speed it up due to the used data structuring
999  for(RectangleVector::const_reverse_iterator aRectIter(rRectangles.rbegin()); aRectIter != rRectangles.rend(); ++aRectIter)
1000  {
1001  aRegion.Union(LogicToPixel(*aRectIter));
1002  }
1003  }
1004 
1005  return aRegion;
1006 }
1007 
1008 Point OutputDevice::LogicToPixel( const Point& rLogicPt,
1009  const MapMode& rMapMode ) const
1010 {
1011 
1012  if ( rMapMode.IsDefault() )
1013  return rLogicPt;
1014 
1015  // convert MapMode resolution and convert
1016  ImplMapRes aMapRes;
1017  ImplCalcMapResolution(rMapMode, mnDPIX, mnDPIY, aMapRes);
1018 
1019  return Point( ImplLogicToPixel( rLogicPt.X() + aMapRes.mnMapOfsX, mnDPIX,
1020  aMapRes.mnMapScNumX, aMapRes.mnMapScDenomX )+mnOutOffOrigX,
1021  ImplLogicToPixel( rLogicPt.Y() + aMapRes.mnMapOfsY, mnDPIY,
1022  aMapRes.mnMapScNumY, aMapRes.mnMapScDenomY )+mnOutOffOrigY );
1023 }
1024 
1026  const MapMode& rMapMode ) const
1027 {
1028 
1029  if ( rMapMode.IsDefault() )
1030  return rLogicSize;
1031 
1032  // convert MapMode resolution and convert
1033  ImplMapRes aMapRes;
1034  ImplCalcMapResolution(rMapMode, mnDPIX, mnDPIY, aMapRes);
1035 
1036  return Size( ImplLogicToPixel( rLogicSize.Width(), mnDPIX,
1037  aMapRes.mnMapScNumX, aMapRes.mnMapScDenomX ),
1038  ImplLogicToPixel( rLogicSize.Height(), mnDPIY,
1039  aMapRes.mnMapScNumY, aMapRes.mnMapScDenomY ) );
1040 }
1041 
1043  const MapMode& rMapMode ) const
1044 {
1045  // tdf#141761 see comments above, IsEmpty() removed
1046  if ( rMapMode.IsDefault() )
1047  return rLogicRect;
1048 
1049  // convert MapMode resolution and convert
1050  ImplMapRes aMapRes;
1051  ImplCalcMapResolution(rMapMode, mnDPIX, mnDPIY, aMapRes);
1052 
1053  tools::Rectangle aRetval(
1054  ImplLogicToPixel( rLogicRect.Left() + aMapRes.mnMapOfsX, mnDPIX, aMapRes.mnMapScNumX, aMapRes.mnMapScDenomX )+mnOutOffOrigX,
1055  ImplLogicToPixel( rLogicRect.Top() + aMapRes.mnMapOfsY, mnDPIY, aMapRes.mnMapScNumY, aMapRes.mnMapScDenomY )+mnOutOffOrigY,
1056  rLogicRect.IsWidthEmpty() ? 0 : ImplLogicToPixel( rLogicRect.Right() + aMapRes.mnMapOfsX, mnDPIX, aMapRes.mnMapScNumX, aMapRes.mnMapScDenomX )+mnOutOffOrigX,
1057  rLogicRect.IsHeightEmpty() ? 0 : ImplLogicToPixel( rLogicRect.Bottom() + aMapRes.mnMapOfsY, mnDPIY, aMapRes.mnMapScNumY, aMapRes.mnMapScDenomY )+mnOutOffOrigY );
1058 
1059  if(rLogicRect.IsWidthEmpty())
1060  aRetval.SetWidthEmpty();
1061 
1062  if(rLogicRect.IsHeightEmpty())
1063  aRetval.SetHeightEmpty();
1064 
1065  return aRetval;
1066 }
1067 
1069  const MapMode& rMapMode ) const
1070 {
1071 
1072  if ( rMapMode.IsDefault() )
1073  return rLogicPoly;
1074 
1075  // convert MapMode resolution and convert
1076  ImplMapRes aMapRes;
1077  ImplCalcMapResolution(rMapMode, mnDPIX, mnDPIY, aMapRes);
1078 
1079  sal_uInt16 i;
1080  sal_uInt16 nPoints = rLogicPoly.GetSize();
1081  tools::Polygon aPoly( rLogicPoly );
1082 
1083  // get pointer to Point-array (copy data)
1084  const Point* pPointAry = aPoly.GetConstPointAry();
1085 
1086  for ( i = 0; i < nPoints; i++ )
1087  {
1088  const Point* pPt = &(pPointAry[i]);
1089  Point aPt;
1090  aPt.setX( ImplLogicToPixel( pPt->X() + aMapRes.mnMapOfsX, mnDPIX,
1091  aMapRes.mnMapScNumX, aMapRes.mnMapScDenomX )+mnOutOffOrigX );
1092  aPt.setY( ImplLogicToPixel( pPt->Y() + aMapRes.mnMapOfsY, mnDPIY,
1093  aMapRes.mnMapScNumY, aMapRes.mnMapScDenomY )+mnOutOffOrigY );
1094  aPoly[i] = aPt;
1095  }
1096 
1097  return aPoly;
1098 }
1099 
1101  const MapMode& rMapMode ) const
1102 {
1103  basegfx::B2DPolyPolygon aTransformedPoly = rLogicPolyPoly;
1104  const basegfx::B2DHomMatrix& rTransformationMatrix = GetViewTransformation( rMapMode );
1105  aTransformedPoly.transform( rTransformationMatrix );
1106  return aTransformedPoly;
1107 }
1108 
1109 Point OutputDevice::PixelToLogic( const Point& rDevicePt ) const
1110 {
1111 
1112  if ( !mbMap )
1113  return rDevicePt;
1114 
1115  return Point( ImplPixelToLogic( rDevicePt.X(), mnDPIX,
1117  ImplPixelToLogic( rDevicePt.Y(), mnDPIY,
1119 }
1120 
1121 Size OutputDevice::PixelToLogic( const Size& rDeviceSize ) const
1122 {
1123 
1124  if ( !mbMap )
1125  return rDeviceSize;
1126 
1127  return Size( ImplPixelToLogic( rDeviceSize.Width(), mnDPIX,
1129  ImplPixelToLogic( rDeviceSize.Height(), mnDPIY,
1131 }
1132 
1134 {
1135  // tdf#141761 see comments above, IsEmpty() removed
1136  if ( !mbMap )
1137  return rDeviceRect;
1138 
1139  tools::Rectangle aRetval(
1144 
1145  if(rDeviceRect.IsWidthEmpty())
1146  aRetval.SetWidthEmpty();
1147 
1148  if(rDeviceRect.IsHeightEmpty())
1149  aRetval.SetHeightEmpty();
1150 
1151  return aRetval;
1152 }
1153 
1155 {
1156 
1157  if ( !mbMap )
1158  return rDevicePoly;
1159 
1160  sal_uInt16 i;
1161  sal_uInt16 nPoints = rDevicePoly.GetSize();
1162  tools::Polygon aPoly( rDevicePoly );
1163 
1164  // get pointer to Point-array (copy data)
1165  const Point* pPointAry = aPoly.GetConstPointAry();
1166 
1167  for ( i = 0; i < nPoints; i++ )
1168  {
1169  const Point* pPt = &(pPointAry[i]);
1170  Point aPt;
1171  aPt.setX( ImplPixelToLogic( pPt->X(), mnDPIX,
1173  aPt.setY( ImplPixelToLogic( pPt->Y(), mnDPIY,
1175  aPoly[i] = aPt;
1176  }
1177 
1178  return aPoly;
1179 }
1180 
1182 {
1183 
1184  if ( !mbMap )
1185  return rDevicePolyPoly;
1186 
1187  tools::PolyPolygon aPolyPoly( rDevicePolyPoly );
1188  sal_uInt16 nPoly = aPolyPoly.Count();
1189  for( sal_uInt16 i = 0; i < nPoly; i++ )
1190  {
1191  tools::Polygon& rPoly = aPolyPoly[i];
1192  rPoly = PixelToLogic( rPoly );
1193  }
1194  return aPolyPoly;
1195 }
1196 
1198 {
1199  basegfx::B2DPolyPolygon aTransformedPoly = rPixelPolyPoly;
1200  const basegfx::B2DHomMatrix& rTransformationMatrix = GetInverseViewTransformation();
1201  aTransformedPoly.transform( rTransformationMatrix );
1202  return aTransformedPoly;
1203 }
1204 
1206 {
1207 
1208  if(!mbMap || rDeviceRegion.IsNull() || rDeviceRegion.IsEmpty())
1209  {
1210  return rDeviceRegion;
1211  }
1212 
1213  vcl::Region aRegion;
1214 
1215  if(rDeviceRegion.getB2DPolyPolygon())
1216  {
1217  aRegion = vcl::Region(PixelToLogic(*rDeviceRegion.getB2DPolyPolygon()));
1218  }
1219  else if(rDeviceRegion.getPolyPolygon())
1220  {
1221  aRegion = vcl::Region(PixelToLogic(*rDeviceRegion.getPolyPolygon()));
1222  }
1223  else if(rDeviceRegion.getRegionBand())
1224  {
1225  RectangleVector aRectangles;
1226  rDeviceRegion.GetRegionRectangles(aRectangles);
1227  const RectangleVector& rRectangles(aRectangles); // needed to make the '!=' work
1228 
1229  // make reverse run to fill new region bottom-up, this will speed it up due to the used data structuring
1230  for(RectangleVector::const_reverse_iterator aRectIter(rRectangles.rbegin()); aRectIter != rRectangles.rend(); ++aRectIter)
1231  {
1232  aRegion.Union(PixelToLogic(*aRectIter));
1233  }
1234  }
1235 
1236  return aRegion;
1237 }
1238 
1239 Point OutputDevice::PixelToLogic( const Point& rDevicePt,
1240  const MapMode& rMapMode ) const
1241 {
1242 
1243  // calculate nothing if default-MapMode
1244  if ( rMapMode.IsDefault() )
1245  return rDevicePt;
1246 
1247  // calculate MapMode-resolution and convert
1248  ImplMapRes aMapRes;
1249  ImplCalcMapResolution(rMapMode, mnDPIX, mnDPIY, aMapRes);
1250 
1251  return Point( ImplPixelToLogic( rDevicePt.X(), mnDPIX,
1252  aMapRes.mnMapScNumX, aMapRes.mnMapScDenomX ) - aMapRes.mnMapOfsX - mnOutOffLogicX,
1253  ImplPixelToLogic( rDevicePt.Y(), mnDPIY,
1254  aMapRes.mnMapScNumY, aMapRes.mnMapScDenomY ) - aMapRes.mnMapOfsY - mnOutOffLogicY );
1255 }
1256 
1258  const MapMode& rMapMode ) const
1259 {
1260 
1261  // calculate nothing if default-MapMode
1262  if ( rMapMode.IsDefault() )
1263  return rDeviceSize;
1264 
1265  // calculate MapMode-resolution and convert
1266  ImplMapRes aMapRes;
1267  ImplCalcMapResolution(rMapMode, mnDPIX, mnDPIY, aMapRes);
1268 
1269  return Size( ImplPixelToLogic( rDeviceSize.Width(), mnDPIX,
1270  aMapRes.mnMapScNumX, aMapRes.mnMapScDenomX ),
1271  ImplPixelToLogic( rDeviceSize.Height(), mnDPIY,
1272  aMapRes.mnMapScNumY, aMapRes.mnMapScDenomY ) );
1273 }
1274 
1276  const MapMode& rMapMode ) const
1277 {
1278  // calculate nothing if default-MapMode
1279  // tdf#141761 see comments above, IsEmpty() removed
1280  if ( rMapMode.IsDefault() )
1281  return rDeviceRect;
1282 
1283  // calculate MapMode-resolution and convert
1284  ImplMapRes aMapRes;
1285  ImplCalcMapResolution(rMapMode, mnDPIX, mnDPIY, aMapRes);
1286 
1287  tools::Rectangle aRetval(
1288  ImplPixelToLogic( rDeviceRect.Left(), mnDPIX, aMapRes.mnMapScNumX, aMapRes.mnMapScDenomX ) - aMapRes.mnMapOfsX - mnOutOffLogicX,
1289  ImplPixelToLogic( rDeviceRect.Top(), mnDPIY, aMapRes.mnMapScNumY, aMapRes.mnMapScDenomY ) - aMapRes.mnMapOfsY - mnOutOffLogicY,
1290  rDeviceRect.IsWidthEmpty() ? 0 : ImplPixelToLogic( rDeviceRect.Right(), mnDPIX, aMapRes.mnMapScNumX, aMapRes.mnMapScDenomX ) - aMapRes.mnMapOfsX - mnOutOffLogicX,
1291  rDeviceRect.IsHeightEmpty() ? 0 : ImplPixelToLogic( rDeviceRect.Bottom(), mnDPIY, aMapRes.mnMapScNumY, aMapRes.mnMapScDenomY ) - aMapRes.mnMapOfsY - mnOutOffLogicY );
1292 
1293  if(rDeviceRect.IsWidthEmpty())
1294  aRetval.SetWidthEmpty();
1295 
1296  if(rDeviceRect.IsHeightEmpty())
1297  aRetval.SetHeightEmpty();
1298 
1299  return aRetval;
1300 }
1301 
1303  const MapMode& rMapMode ) const
1304 {
1305 
1306  // calculate nothing if default-MapMode
1307  if ( rMapMode.IsDefault() )
1308  return rDevicePoly;
1309 
1310  // calculate MapMode-resolution and convert
1311  ImplMapRes aMapRes;
1312  ImplCalcMapResolution(rMapMode, mnDPIX, mnDPIY, aMapRes);
1313 
1314  sal_uInt16 i;
1315  sal_uInt16 nPoints = rDevicePoly.GetSize();
1316  tools::Polygon aPoly( rDevicePoly );
1317 
1318  // get pointer to Point-array (copy data)
1319  const Point* pPointAry = aPoly.GetConstPointAry();
1320 
1321  for ( i = 0; i < nPoints; i++ )
1322  {
1323  const Point* pPt = &(pPointAry[i]);
1324  Point aPt;
1325  aPt.setX( ImplPixelToLogic( pPt->X(), mnDPIX,
1326  aMapRes.mnMapScNumX, aMapRes.mnMapScDenomX ) - aMapRes.mnMapOfsX - mnOutOffLogicX );
1327  aPt.setY( ImplPixelToLogic( pPt->Y(), mnDPIY,
1328  aMapRes.mnMapScNumY, aMapRes.mnMapScDenomY ) - aMapRes.mnMapOfsY - mnOutOffLogicY );
1329  aPoly[i] = aPt;
1330  }
1331 
1332  return aPoly;
1333 }
1334 
1336  const MapMode& rMapMode ) const
1337 {
1338  basegfx::B2DPolygon aTransformedPoly = rPixelPoly;
1339  const basegfx::B2DHomMatrix& rTransformationMatrix = GetInverseViewTransformation( rMapMode );
1340  aTransformedPoly.transform( rTransformationMatrix );
1341  return aTransformedPoly;
1342 }
1343 
1345  const MapMode& rMapMode ) const
1346 {
1347  basegfx::B2DPolyPolygon aTransformedPoly = rPixelPolyPoly;
1348  const basegfx::B2DHomMatrix& rTransformationMatrix = GetInverseViewTransformation( rMapMode );
1349  aTransformedPoly.transform( rTransformationMatrix );
1350  return aTransformedPoly;
1351 }
1352 
1353 #define ENTER1( rSource, pMapModeSource, pMapModeDest ) \
1354  if ( !pMapModeSource ) \
1355  pMapModeSource = &maMapMode; \
1356  if ( !pMapModeDest ) \
1357  pMapModeDest = &maMapMode; \
1358  if ( *pMapModeSource == *pMapModeDest ) \
1359  return rSource; \
1360  \
1361  ImplMapRes aMapResSource; \
1362  ImplMapRes aMapResDest; \
1363  \
1364  if ( !mbMap || pMapModeSource != &maMapMode ) \
1365  { \
1366  if ( pMapModeSource->GetMapUnit() == MapUnit::MapRelative ) \
1367  aMapResSource = maMapRes; \
1368  ImplCalcMapResolution( *pMapModeSource, \
1369  mnDPIX, mnDPIY, aMapResSource ); \
1370  } \
1371  else \
1372  aMapResSource = maMapRes; \
1373  if ( !mbMap || pMapModeDest != &maMapMode ) \
1374  { \
1375  if ( pMapModeDest->GetMapUnit() == MapUnit::MapRelative ) \
1376  aMapResDest = maMapRes; \
1377  ImplCalcMapResolution( *pMapModeDest, \
1378  mnDPIX, mnDPIY, aMapResDest ); \
1379  } \
1380  else \
1381  aMapResDest = maMapRes
1382 
1383 static void verifyUnitSourceDest( MapUnit eUnitSource, MapUnit eUnitDest )
1384 {
1385  DBG_ASSERT( eUnitSource != MapUnit::MapSysFont
1386  && eUnitSource != MapUnit::MapAppFont
1387  && eUnitSource != MapUnit::MapRelative,
1388  "Source MapUnit is not permitted" );
1389  DBG_ASSERT( eUnitDest != MapUnit::MapSysFont
1390  && eUnitDest != MapUnit::MapAppFont
1391  && eUnitDest != MapUnit::MapRelative,
1392  "Destination MapUnit is not permitted" );
1393 }
1394 
1395 namespace
1396 {
1397 auto getCorrectedUnit(MapUnit eMapSrc, MapUnit eMapDst)
1398 {
1401  if (eMapSrc > MapUnit::MapPixel)
1402  SAL_WARN("vcl.gdi", "Invalid source map unit");
1403  else if (eMapDst > MapUnit::MapPixel)
1404  SAL_WARN("vcl.gdi", "Invalid destination map unit");
1405  else if (eMapSrc != eMapDst)
1406  {
1407  // Here 72 PPI is assumed for MapPixel
1408  eSrc = MapToO3tlLength(eMapSrc, o3tl::Length::pt);
1409  eDst = MapToO3tlLength(eMapDst, o3tl::Length::pt);
1410  }
1411  return std::make_pair(eSrc, eDst);
1412 }
1413 }
1414 
1415 #define ENTER4( rMapModeSource, rMapModeDest ) \
1416  ImplMapRes aMapResSource; \
1417  ImplMapRes aMapResDest; \
1418  \
1419  ImplCalcMapResolution( rMapModeSource, 72, 72, aMapResSource ); \
1420  ImplCalcMapResolution( rMapModeDest, 72, 72, aMapResDest )
1421 
1422 // return (n1 * n2 * n3) / (n4 * n5)
1423 static tools::Long fn5( const tools::Long n1,
1424  const tools::Long n2,
1425  const tools::Long n3,
1426  const tools::Long n4,
1427  const tools::Long n5 )
1428 {
1429  if ( n1 == 0 || n2 == 0 || n3 == 0 || n4 == 0 || n5 == 0 )
1430  return 0;
1431  if (std::numeric_limits<tools::Long>::max() / std::abs(n2) < std::abs(n3))
1432  {
1433  // a6 is skipped
1434  BigInt a7 = n2;
1435  a7 *= n3;
1436  a7 *= n1;
1437 
1438  if (std::numeric_limits<tools::Long>::max() / std::abs(n4) < std::abs(n5))
1439  {
1440  BigInt a8 = n4;
1441  a8 *= n5;
1442 
1443  BigInt a9 = a8;
1444  a9 /= 2;
1445  if ( a7.IsNeg() )
1446  a7 -= a9;
1447  else
1448  a7 += a9;
1449 
1450  a7 /= a8;
1451  } // of if
1452  else
1453  {
1454  tools::Long n8 = n4 * n5;
1455 
1456  if ( a7.IsNeg() )
1457  a7 -= n8 / 2;
1458  else
1459  a7 += n8 / 2;
1460 
1461  a7 /= n8;
1462  } // of else
1463  return static_cast<tools::Long>(a7);
1464  } // of if
1465  else
1466  {
1467  tools::Long n6 = n2 * n3;
1468 
1469  if (std::numeric_limits<tools::Long>::max() / std::abs(n1) < std::abs(n6))
1470  {
1471  BigInt a7 = n1;
1472  a7 *= n6;
1473 
1474  if (std::numeric_limits<tools::Long>::max() / std::abs(n4) < std::abs(n5))
1475  {
1476  BigInt a8 = n4;
1477  a8 *= n5;
1478 
1479  BigInt a9 = a8;
1480  a9 /= 2;
1481  if ( a7.IsNeg() )
1482  a7 -= a9;
1483  else
1484  a7 += a9;
1485 
1486  a7 /= a8;
1487  } // of if
1488  else
1489  {
1490  tools::Long n8 = n4 * n5;
1491 
1492  if ( a7.IsNeg() )
1493  a7 -= n8 / 2;
1494  else
1495  a7 += n8 / 2;
1496 
1497  a7 /= n8;
1498  } // of else
1499  return static_cast<tools::Long>(a7);
1500  } // of if
1501  else
1502  {
1503  tools::Long n7 = n1 * n6;
1504 
1505  if (std::numeric_limits<tools::Long>::max() / std::abs(n4) < std::abs(n5))
1506  {
1507  BigInt a7 = n7;
1508  BigInt a8 = n4;
1509  a8 *= n5;
1510 
1511  BigInt a9 = a8;
1512  a9 /= 2;
1513  if ( a7.IsNeg() )
1514  a7 -= a9;
1515  else
1516  a7 += a9;
1517 
1518  a7 /= a8;
1519  return static_cast<tools::Long>(a7);
1520  } // of if
1521  else
1522  {
1523  const tools::Long n8 = n4 * n5;
1524  const tools::Long n8_2 = n8 / 2;
1525 
1526  if( n7 < 0 )
1527  {
1528  if ((n7 - std::numeric_limits<tools::Long>::min()) >= n8_2)
1529  n7 -= n8_2;
1530  }
1531  else if ((std::numeric_limits<tools::Long>::max() - n7) >= n8_2)
1532  n7 += n8_2;
1533 
1534  return n7 / n8;
1535  } // of else
1536  } // of else
1537  } // of else
1538 }
1539 
1540 static tools::Long fn3(const tools::Long n1, const o3tl::Length eFrom, const o3tl::Length eTo)
1541 {
1542  if (n1 == 0 || eFrom == o3tl::Length::invalid || eTo == o3tl::Length::invalid)
1543  return 0;
1544  bool bOverflow;
1545  const auto nResult = o3tl::convert(n1, eFrom, eTo, bOverflow);
1546  if (bOverflow)
1547  {
1548  const auto& [n2, n3] = o3tl::getConversionMulDiv(eFrom, eTo);
1549  BigInt a4 = n1;
1550  a4 *= n2;
1551 
1552  if ( a4.IsNeg() )
1553  a4 -= n3 / 2;
1554  else
1555  a4 += n3 / 2;
1556 
1557  a4 /= n3;
1558  return static_cast<tools::Long>(a4);
1559  } // of if
1560  else
1561  return nResult;
1562 }
1563 
1564 Point OutputDevice::LogicToLogic( const Point& rPtSource,
1565  const MapMode* pMapModeSource,
1566  const MapMode* pMapModeDest ) const
1567 {
1568  ENTER1( rPtSource, pMapModeSource, pMapModeDest );
1569 
1570  return Point( fn5( rPtSource.X() + aMapResSource.mnMapOfsX,
1571  aMapResSource.mnMapScNumX, aMapResDest.mnMapScDenomX,
1572  aMapResSource.mnMapScDenomX, aMapResDest.mnMapScNumX ) -
1573  aMapResDest.mnMapOfsX,
1574  fn5( rPtSource.Y() + aMapResSource.mnMapOfsY,
1575  aMapResSource.mnMapScNumY, aMapResDest.mnMapScDenomY,
1576  aMapResSource.mnMapScDenomY, aMapResDest.mnMapScNumY ) -
1577  aMapResDest.mnMapOfsY );
1578 }
1579 
1581  const MapMode* pMapModeSource,
1582  const MapMode* pMapModeDest ) const
1583 {
1584  ENTER1( rSzSource, pMapModeSource, pMapModeDest );
1585 
1586  return Size( fn5( rSzSource.Width(),
1587  aMapResSource.mnMapScNumX, aMapResDest.mnMapScDenomX,
1588  aMapResSource.mnMapScDenomX, aMapResDest.mnMapScNumX ),
1589  fn5( rSzSource.Height(),
1590  aMapResSource.mnMapScNumY, aMapResDest.mnMapScDenomY,
1591  aMapResSource.mnMapScDenomY, aMapResDest.mnMapScNumY ) );
1592 }
1593 
1595  const MapMode* pMapModeSource,
1596  const MapMode* pMapModeDest ) const
1597 {
1598  ENTER1( rRectSource, pMapModeSource, pMapModeDest );
1599 
1600  return tools::Rectangle( fn5( rRectSource.Left() + aMapResSource.mnMapOfsX,
1601  aMapResSource.mnMapScNumX, aMapResDest.mnMapScDenomX,
1602  aMapResSource.mnMapScDenomX, aMapResDest.mnMapScNumX ) -
1603  aMapResDest.mnMapOfsX,
1604  fn5( rRectSource.Top() + aMapResSource.mnMapOfsY,
1605  aMapResSource.mnMapScNumY, aMapResDest.mnMapScDenomY,
1606  aMapResSource.mnMapScDenomY, aMapResDest.mnMapScNumY ) -
1607  aMapResDest.mnMapOfsY,
1608  fn5( rRectSource.Right() + aMapResSource.mnMapOfsX,
1609  aMapResSource.mnMapScNumX, aMapResDest.mnMapScDenomX,
1610  aMapResSource.mnMapScDenomX, aMapResDest.mnMapScNumX ) -
1611  aMapResDest.mnMapOfsX,
1612  fn5( rRectSource.Bottom() + aMapResSource.mnMapOfsY,
1613  aMapResSource.mnMapScNumY, aMapResDest.mnMapScDenomY,
1614  aMapResSource.mnMapScDenomY, aMapResDest.mnMapScNumY ) -
1615  aMapResDest.mnMapOfsY );
1616 }
1617 
1618 Point OutputDevice::LogicToLogic( const Point& rPtSource,
1619  const MapMode& rMapModeSource,
1620  const MapMode& rMapModeDest )
1621 {
1622  if ( rMapModeSource == rMapModeDest )
1623  return rPtSource;
1624 
1625  MapUnit eUnitSource = rMapModeSource.GetMapUnit();
1626  MapUnit eUnitDest = rMapModeDest.GetMapUnit();
1627  verifyUnitSourceDest( eUnitSource, eUnitDest );
1628 
1629  if (rMapModeSource.IsSimple() && rMapModeDest.IsSimple())
1630  {
1631  const auto& [eFrom, eTo] = getCorrectedUnit(eUnitSource, eUnitDest);
1632  return Point(fn3(rPtSource.X(), eFrom, eTo), fn3(rPtSource.Y(), eFrom, eTo));
1633  }
1634  else
1635  {
1636  ENTER4( rMapModeSource, rMapModeDest );
1637 
1638  return Point( fn5( rPtSource.X() + aMapResSource.mnMapOfsX,
1639  aMapResSource.mnMapScNumX, aMapResDest.mnMapScDenomX,
1640  aMapResSource.mnMapScDenomX, aMapResDest.mnMapScNumX ) -
1641  aMapResDest.mnMapOfsX,
1642  fn5( rPtSource.Y() + aMapResSource.mnMapOfsY,
1643  aMapResSource.mnMapScNumY, aMapResDest.mnMapScDenomY,
1644  aMapResSource.mnMapScDenomY, aMapResDest.mnMapScNumY ) -
1645  aMapResDest.mnMapOfsY );
1646  }
1647 }
1648 
1650  const MapMode& rMapModeSource,
1651  const MapMode& rMapModeDest )
1652 {
1653  if ( rMapModeSource == rMapModeDest )
1654  return rSzSource;
1655 
1656  MapUnit eUnitSource = rMapModeSource.GetMapUnit();
1657  MapUnit eUnitDest = rMapModeDest.GetMapUnit();
1658  verifyUnitSourceDest( eUnitSource, eUnitDest );
1659 
1660  if (rMapModeSource.IsSimple() && rMapModeDest.IsSimple())
1661  {
1662  const auto& [eFrom, eTo] = getCorrectedUnit(eUnitSource, eUnitDest);
1663  return Size(fn3(rSzSource.Width(), eFrom, eTo), fn3(rSzSource.Height(), eFrom, eTo));
1664  }
1665  else
1666  {
1667  ENTER4( rMapModeSource, rMapModeDest );
1668 
1669  return Size( fn5( rSzSource.Width(),
1670  aMapResSource.mnMapScNumX, aMapResDest.mnMapScDenomX,
1671  aMapResSource.mnMapScDenomX, aMapResDest.mnMapScNumX ),
1672  fn5( rSzSource.Height(),
1673  aMapResSource.mnMapScNumY, aMapResDest.mnMapScDenomY,
1674  aMapResSource.mnMapScDenomY, aMapResDest.mnMapScNumY ) );
1675  }
1676 }
1677 
1679  const MapMode& rMapModeSource,
1680  const MapMode& rMapModeDest )
1681 {
1682  if(rMapModeSource == rMapModeDest)
1683  {
1684  return rPolySource;
1685  }
1686 
1687  const basegfx::B2DHomMatrix aTransform(LogicToLogic(rMapModeSource, rMapModeDest));
1688  basegfx::B2DPolygon aPoly(rPolySource);
1689 
1690  aPoly.transform(aTransform);
1691  return aPoly;
1692 }
1693 
1694 basegfx::B2DHomMatrix OutputDevice::LogicToLogic(const MapMode& rMapModeSource, const MapMode& rMapModeDest)
1695 {
1696  basegfx::B2DHomMatrix aTransform;
1697 
1698  if(rMapModeSource == rMapModeDest)
1699  {
1700  return aTransform;
1701  }
1702 
1703  MapUnit eUnitSource = rMapModeSource.GetMapUnit();
1704  MapUnit eUnitDest = rMapModeDest.GetMapUnit();
1705  verifyUnitSourceDest(eUnitSource, eUnitDest);
1706 
1707  if (rMapModeSource.IsSimple() && rMapModeDest.IsSimple())
1708  {
1709  const auto& [eFrom, eTo] = getCorrectedUnit(eUnitSource, eUnitDest);
1710  const double fScaleFactor(eFrom == o3tl::Length::invalid || eTo == o3tl::Length::invalid
1711  ? std::numeric_limits<double>::quiet_NaN()
1712  : o3tl::convert(1.0, eFrom, eTo));
1713  aTransform.set(0, 0, fScaleFactor);
1714  aTransform.set(1, 1, fScaleFactor);
1715  }
1716  else
1717  {
1718  ENTER4(rMapModeSource, rMapModeDest);
1719 
1720  const double fScaleFactorX((double(aMapResSource.mnMapScNumX) * double(aMapResDest.mnMapScDenomX)) / (double(aMapResSource.mnMapScDenomX) * double(aMapResDest.mnMapScNumX)));
1721  const double fScaleFactorY((double(aMapResSource.mnMapScNumY) * double(aMapResDest.mnMapScDenomY)) / (double(aMapResSource.mnMapScDenomY) * double(aMapResDest.mnMapScNumY)));
1722  const double fZeroPointX(double(aMapResSource.mnMapOfsX) * fScaleFactorX - double(aMapResDest.mnMapOfsX));
1723  const double fZeroPointY(double(aMapResSource.mnMapOfsY) * fScaleFactorY - double(aMapResDest.mnMapOfsY));
1724 
1725  aTransform.set(0, 0, fScaleFactorX);
1726  aTransform.set(1, 1, fScaleFactorY);
1727  aTransform.set(0, 2, fZeroPointX);
1728  aTransform.set(1, 2, fZeroPointY);
1729  }
1730 
1731  return aTransform;
1732 }
1733 
1735  const MapMode& rMapModeSource,
1736  const MapMode& rMapModeDest )
1737 {
1738  if ( rMapModeSource == rMapModeDest )
1739  return rRectSource;
1740 
1741  MapUnit eUnitSource = rMapModeSource.GetMapUnit();
1742  MapUnit eUnitDest = rMapModeDest.GetMapUnit();
1743  verifyUnitSourceDest( eUnitSource, eUnitDest );
1744 
1745  tools::Rectangle aRetval;
1746 
1747  if (rMapModeSource.IsSimple() && rMapModeDest.IsSimple())
1748  {
1749  const auto& [eFrom, eTo] = getCorrectedUnit(eUnitSource, eUnitDest);
1750 
1751  auto left = fn3(rRectSource.Left(), eFrom, eTo);
1752  auto top = fn3(rRectSource.Top(), eFrom, eTo);
1753 
1754  // tdf#141761 see comments above, IsEmpty() removed
1755  auto right = rRectSource.IsWidthEmpty() ? 0 : fn3(rRectSource.Right(), eFrom, eTo);
1756  auto bottom = rRectSource.IsHeightEmpty() ? 0 : fn3(rRectSource.Bottom(), eFrom, eTo);
1757 
1758  aRetval = tools::Rectangle(left, top, right, bottom);
1759  }
1760  else
1761  {
1762  ENTER4( rMapModeSource, rMapModeDest );
1763 
1764  auto left = fn5( rRectSource.Left() + aMapResSource.mnMapOfsX,
1765  aMapResSource.mnMapScNumX, aMapResDest.mnMapScDenomX,
1766  aMapResSource.mnMapScDenomX, aMapResDest.mnMapScNumX ) -
1767  aMapResDest.mnMapOfsX;
1768  auto top = fn5( rRectSource.Top() + aMapResSource.mnMapOfsY,
1769  aMapResSource.mnMapScNumY, aMapResDest.mnMapScDenomY,
1770  aMapResSource.mnMapScDenomY, aMapResDest.mnMapScNumY ) -
1771  aMapResDest.mnMapOfsY;
1772 
1773  // tdf#141761 see comments above, IsEmpty() removed
1774  auto right = rRectSource.IsWidthEmpty() ? 0 : fn5( rRectSource.Right() + aMapResSource.mnMapOfsX,
1775  aMapResSource.mnMapScNumX, aMapResDest.mnMapScDenomX,
1776  aMapResSource.mnMapScDenomX, aMapResDest.mnMapScNumX ) -
1777  aMapResDest.mnMapOfsX;
1778  auto bottom = rRectSource.IsHeightEmpty() ? 0 : fn5( rRectSource.Bottom() + aMapResSource.mnMapOfsY,
1779  aMapResSource.mnMapScNumY, aMapResDest.mnMapScDenomY,
1780  aMapResSource.mnMapScDenomY, aMapResDest.mnMapScNumY ) -
1781  aMapResDest.mnMapOfsY;
1782 
1783  aRetval = tools::Rectangle(left, top, right, bottom);
1784  }
1785 
1786  if(rRectSource.IsWidthEmpty())
1787  aRetval.SetWidthEmpty();
1788 
1789  if(rRectSource.IsHeightEmpty())
1790  aRetval.SetHeightEmpty();
1791 
1792  return aRetval;
1793 }
1794 
1796  MapUnit eUnitSource, MapUnit eUnitDest )
1797 {
1798  if ( eUnitSource == eUnitDest )
1799  return nLongSource;
1800 
1801  verifyUnitSourceDest( eUnitSource, eUnitDest );
1802  const auto& [eFrom, eTo] = getCorrectedUnit(eUnitSource, eUnitDest);
1803  return fn3(nLongSource, eFrom, eTo);
1804 }
1805 
1806 void OutputDevice::SetPixelOffset( const Size& rOffset )
1807 {
1808  mnOutOffOrigX = rOffset.Width();
1809  mnOutOffOrigY = rOffset.Height();
1810 
1815 
1816  if( mpAlphaVDev )
1817  mpAlphaVDev->SetPixelOffset( rOffset );
1818 }
1819 
1820 
1822 {
1823  if ( !mbMap )
1824  return static_cast<DeviceCoordinate>(nWidth);
1825 
1826 #if VCL_FLOAT_DEVICE_PIXEL
1827  return (double)nWidth * maMapRes.mfScaleX * mnDPIX;
1828 #else
1829 
1831 #endif
1832 }
1833 
1834 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
sal_uInt16 Count() const
basegfx::B2DHomMatrix GetInverseViewTransformation() const
Definition: map.cxx:820
const Fraction & GetScaleX() const
Definition: mapmod.cxx:142
double getY() const
void SetPixelOffset(const Size &rOffset)
Set an offset in pixel.
Definition: map.cxx:1806
SAL_DLLPRIVATE DeviceCoordinate LogicWidthToDeviceCoordinate(tools::Long nWidth) const
Definition: map.cxx:1821
void SetRelativeMapMode(const MapMode &rNewMapMode)
Definition: map.cxx:720
static auto setMapRes(ImplMapRes &rMapRes, const o3tl::Length eUnit)
Definition: map.cxx:80
static void verifyUnitSourceDest(MapUnit eUnitSource, MapUnit eUnitDest)
Definition: map.cxx:1383
tools::Long mnOutOffLogicX
Additional output offset in logical coordinates, applied in PixelToLogic (used by SetPixelOffset/GetP...
Definition: outdev.hxx:200
void set(sal_uInt16 nRow, sal_uInt16 nColumn, double fValue)
tools::Long mnOutOffOrigY
Additional output pixel offset, applied in LogicToPixel (used by SetPixelOffset/GetPixelOffset) ...
Definition: outdev.hxx:202
bool IsNull() const
Definition: region.hxx:99
static Fraction ImplMakeFraction(tools::Long nN1, tools::Long nN2, tools::Long nD1, tools::Long nD2)
Definition: map.cxx:45
sal_uInt64 left
void Move(tools::Long nHorzMove, tools::Long nVertMove)
Definition: region.cxx:399
SAL_WARN_UNUSED_RESULT Point LogicToLogic(const Point &rPtSource, const MapMode *pMapModeSource, const MapMode *pMapModeDest) const
Definition: map.cxx:1564
constexpr tools::Long Left() const
static SAL_DLLPRIVATE void ImplInitAppFontData(vcl::Window const *pWindow)
Definition: window.cxx:1181
void Union(const tools::Rectangle &rRegion)
Definition: region.cxx:505
long Long
bool IsSimple() const
Definition: mapmod.cxx:146
constexpr Point convert(const Point &rPoint, o3tl::Length eFrom, o3tl::Length eTo)
tools::Long mnOutOffY
Output offset for device output in pixel (pseudo window offset within window system's frames) ...
Definition: outdev.hxx:208
sal_Int32 mnDPIY
Definition: outdev.hxx:212
sal_Int32 mnDPIX
Definition: outdev.hxx:211
void EnableMapMode(bool bEnable=true)
Definition: map.cxx:586
bool mbMap
Definition: outdev.hxx:239
constexpr bool IsHeightEmpty() const
tools::Long mnMapScDenomX
Scaling factor - denominator in X direction.
Definition: ImplMapRes.hxx:32
bool IsDefault() const
Definition: mapmod.cxx:133
const RegionBand * getRegionBand() const
Definition: region.hxx:78
void SetMapMode()
Definition: map.cxx:594
ImplSVGDIData maGDIData
Definition: svdata.hxx:397
tools::Long mnOutOffOrigX
Additional output pixel offset, applied in LogicToPixel (used by SetPixelOffset/GetPixelOffset) ...
Definition: outdev.hxx:198
std::vector< tools::Rectangle > RectangleVector
Definition: region.hxx:34
MapMode maMapMode
Definition: outdev.hxx:234
#define ENTER1(rSource, pMapModeSource, pMapModeDest)
Definition: map.cxx:1353
constexpr tools::Long Width() const
A construction helper for ScopedVclPtr.
Definition: vclptr.hxx:407
int n2
static void ImplCalcMapResolution(const MapMode &rMapMode, tools::Long nDPIX, tools::Long nDPIY, ImplMapRes &rMapRes)
Definition: map.cxx:87
SAL_DLLPRIVATE tools::Long ImplLogicXToDevicePixel(tools::Long nX) const
Convert a logical X coordinate to a device pixel's X coordinate.
Definition: map.cxx:306
#define ENTER4(rMapModeSource, rMapModeDest)
Definition: map.cxx:1415
const Fraction & GetScaleY() const
Definition: mapmod.cxx:144
tools::Long mnMapScDenomY
Scaling factor - denominator in Y direction.
Definition: ImplMapRes.hxx:33
SAL_DLLPRIVATE basegfx::B2DHomMatrix ImplGetDeviceTransformation() const
Get device transformation.
Definition: map.cxx:869
static tools::Long fn5(const tools::Long n1, const tools::Long n2, const tools::Long n3, const tools::Long n4, const tools::Long n5)
Definition: map.cxx:1423
static tools::Long ImplLogicToPixel(tools::Long n, tools::Long nDPI, tools::Long nMapNum, tools::Long nMapDenom)
Definition: map.cxx:244
static tools::Long ImplPixelToLogic(tools::Long n, tools::Long nDPI, tools::Long nMapNum, tools::Long nMapDenom)
Definition: map.cxx:281
ImplSVData * ImplGetSVData()
Definition: svdata.cxx:75
SAL_DLLPRIVATE void ImplInvalidateViewTransform()
Invalidate the view transformation.
Definition: map.cxx:226
bool IsEmpty() const
Definition: region.cxx:228
void ReduceInaccurate(unsigned nSignificantBits)
def right
void SetScaleX(const Fraction &rScaleX)
Definition: mapmod.cxx:110
virtual void ImplInitMapModeObjects()
Definition: map.cxx:718
#define DBG_ASSERT(sCon, aError)
int i
SAL_DLLPRIVATE float ImplFloatLogicHeightToDevicePixel(float fLogicHeight) const
Convert logical height to device pixels, with exact sub-pixel value.
Definition: map.cxx:340
const Point * GetConstPointAry() const
void SetOrigin(const Point &rOrigin)
Definition: mapmod.cxx:104
constexpr tools::Long Right() const
bool mbNewFont
Definition: outdev.hxx:253
SAL_DLLPRIVATE tools::Long ImplLogicWidthToDevicePixel(tools::Long nWidth) const
Convert a logical width to a width in units of device pixels.
Definition: map.cxx:324
tools::Long DeviceCoordinate
void transform(const basegfx::B2DHomMatrix &rMatrix)
void SetScaleY(const Fraction &rScaleY)
Definition: mapmod.cxx:117
constexpr tools::Long Top() const
sal_uInt16 GetSize() const
tools::Long mnMapOfsX
Offset in X direction.
Definition: ImplMapRes.hxx:28
MapUnit GetMapUnit() const
Definition: mapmod.cxx:138
bool IsNeg() const
virtual void SetMetafileMapMode(const MapMode &rNewMapMode, bool bIsRecord)
Definition: map.cxx:710
tools::Long mnMapOfsY
Offset in Y direction.
Definition: ImplMapRes.hxx:29
static tools::Long fn3(const tools::Long n1, const o3tl::Length eFrom, const o3tl::Length eTo)
Definition: map.cxx:1540
void transform(const basegfx::B2DHomMatrix &rMatrix)
constexpr tools::Long Bottom() const
SAL_WARN_UNUSED_RESULT Point PixelToLogic(const Point &rDevicePt) const
Definition: map.cxx:1109
SAL_WARN_UNUSED_RESULT Point LogicToPixel(const Point &rLogicPt) const
Definition: map.cxx:878
const std::optional< basegfx::B2DPolyPolygon > & getB2DPolyPolygon() const
Definition: region.hxx:76
VclPtr< VirtualDevice > mpAlphaVDev
Definition: outdev.hxx:195
SAL_DLLPRIVATE vcl::Region ImplPixelToDevicePixel(const vcl::Region &rRegion) const
Convert a region in pixel units to a region in device pixel units and coords.
Definition: map.cxx:576
ImplMapRes maMapRes
Definition: outdev.hxx:221
sal_Int32 GetDenominator() const
tools::Long mnMapScNumY
Scaling factor - numerator in Y direction.
Definition: ImplMapRes.hxx:31
constexpr tools::Long Height() const
constexpr o3tl::Length MapToO3tlLength(MapUnit eU, o3tl::Length ePixelValue=o3tl::Length::px)
tools::Long mnAppFontX
Definition: svdata.hxx:232
void AddAction(const rtl::Reference< MetaAction > &pAction)
Definition: gdimtf.cxx:562
tools::Long mnMapScNumX
Scaling factor - numerator in X direction.
Definition: ImplMapRes.hxx:30
ImplSVFrameData maFrameData
Definition: svdata.hxx:398
void GetRegionRectangles(RectangleVector &rTarget) const
Definition: region.cxx:1662
sal_Int32 GetNumerator() const
bool mbInitFont
Definition: outdev.hxx:249
const Point & GetOrigin() const
Definition: mapmod.cxx:140
void translate(double fX, double fY)
SAL_DLLPRIVATE tools::Rectangle ImplLogicToDevicePixel(const tools::Rectangle &rLogicRect) const
Convert a logical rectangle to a rectangle in physical device pixel units.
Definition: map.cxx:386
VclPtr< vcl::Window > mpFirstFrame
Definition: svdata.hxx:243
MapUnit
tools::Long mnOutOffX
Output offset for device output in pixel (pseudo window offset within window system's frames) ...
Definition: outdev.hxx:206
const std::optional< tools::PolyPolygon > & getPolyPolygon() const
Definition: region.hxx:77
#define SAL_WARN(area, stream)
std::unique_ptr< ImplOutDevData > mpOutDevData
Definition: outdev.hxx:188
double getX() const
SAL_DLLPRIVATE tools::Rectangle ImplDevicePixelToLogic(const tools::Rectangle &rPixelRect) const
Convert a rectangle in physical pixel units to a rectangle in physical pixel units and coords...
Definition: map.cxx:545
SAL_DLLPRIVATE tools::Long ImplLogicYToDevicePixel(tools::Long nY) const
Convert a logical Y coordinate to a device pixel's Y coordinate.
Definition: map.cxx:315
bool IsValid() const
tools::Long mnOutOffLogicY
Additional output offset in logical coordinates, applied in PixelToLogic (used by SetPixelOffset/GetP...
Definition: outdev.hxx:204
SAL_DLLPRIVATE tools::Long ImplDevicePixelToLogicWidth(tools::Long nWidth) const
Convert device pixels to a width in logical units.
Definition: map.cxx:348
tools::Long mnAppFontY
Definition: svdata.hxx:233
basegfx::B2DHomMatrix GetViewTransformation() const
Definition: map.cxx:792
SAL_DLLPRIVATE tools::Long ImplLogicHeightToDevicePixel(tools::Long nHeight) const
Convert a logical height to a height in units of device pixels.
Definition: map.cxx:332
SAL_DLLPRIVATE tools::Long ImplDevicePixelToLogicHeight(tools::Long nHeight) const
Convert device pixels to a height in logical units.
Definition: map.cxx:356
constexpr bool IsWidthEmpty() const
double div(const double &fNumerator, const double &fDenominator)
GDIMetaFile * mpMetaFile
Definition: outdev.hxx:184
sal_uInt32 count() const