[Libreoffice-commits] core.git: drawinglayer/source svx/source

Libreoffice Gerrit user logerrit at kemper.freedesktop.org
Fri Aug 17 19:28:03 UTC 2018


 drawinglayer/source/processor2d/vclpixelprocessor2d.cxx |   42 -----
 svx/source/unodraw/UnoGraphicExporter.cxx               |  122 +++++++---------
 2 files changed, 59 insertions(+), 105 deletions(-)

New commits:
commit 046df0a876b3d948bb1e14443c00c180bc8cccaa
Author:     Armin Le Grand <Armin.Le.Grand at cib.de>
AuthorDate: Thu Aug 16 20:20:47 2018 +0200
Commit:     Armin Le Grand <Armin.Le.Grand at cib.de>
CommitDate: Fri Aug 17 21:27:40 2018 +0200

    tdf#105998: Enhanced fix for MetafileToBitmap at better place
    
    Change-Id: I220bdbe196a68ef2df25885dceee70e15b760410
    Reviewed-on: https://gerrit.libreoffice.org/59220
    Tested-by: Jenkins
    Reviewed-by: Armin Le Grand <Armin.Le.Grand at cib.de>

diff --git a/drawinglayer/source/processor2d/vclpixelprocessor2d.cxx b/drawinglayer/source/processor2d/vclpixelprocessor2d.cxx
index b1c974de028c..0845c3316643 100644
--- a/drawinglayer/source/processor2d/vclpixelprocessor2d.cxx
+++ b/drawinglayer/source/processor2d/vclpixelprocessor2d.cxx
@@ -41,7 +41,6 @@
 #include "helperwrongspellrenderer.hxx"
 #include <drawinglayer/primitive2d/fillhatchprimitive2d.hxx>
 #include <basegfx/polygon/b2dpolygontools.hxx>
-#include <basegfx/polygon/b2dpolypolygontools.hxx>
 #include <vcl/hatch.hxx>
 #include <tools/diagnose_ex.h>
 #include <sal/log.hxx>
@@ -136,27 +135,6 @@ namespace drawinglayer
                 return true;
             }
 
-            //Resolves: tdf#105998 if we are a hairline along the very right/bottom edge
-            //of the canvas then distort the polygon inwards one pixel right/bottom so that
-            //the hairline falls inside the paintable area and becomes visible
-            Size aSize = mpOutputDevice->GetOutputSize();
-            basegfx::B2DRange aRange = aLocalPolygon.getB2DRange();
-            basegfx::B2DRange aOutputRange = aRange;
-            aOutputRange.transform(maCurrentTransformation);
-            if (std::round(aOutputRange.getMaxX()) == aSize.Width() || std::round(aOutputRange.getMaxY()) == aSize.Height())
-            {
-                basegfx::B2DRange aOnePixel(0, 0, 1, 1);
-                aOnePixel.transform(maCurrentTransformation);
-                double fXOnePixel = 1.0 / aOnePixel.getMaxX();
-                double fYOnePixel = 1.0 / aOnePixel.getMaxY();
-
-                basegfx::B2DPoint aTopLeft(aRange.getMinX(), aRange.getMinY());
-                basegfx::B2DPoint aTopRight(aRange.getMaxX() - fXOnePixel, aRange.getMinY());
-                basegfx::B2DPoint aBottomLeft(aRange.getMinX(), aRange.getMaxY() - fYOnePixel);
-                basegfx::B2DPoint aBottomRight(aRange.getMaxX() - fXOnePixel, aRange.getMaxY() - fYOnePixel);
-                aLocalPolygon = basegfx::utils::distort(aLocalPolygon, aRange, aTopLeft, aTopRight, aBottomLeft, aBottomRight);
-            }
-
             const basegfx::BColor aLineColor(maBColorModifierStack.getModifiedColor(rSource.getBColor()));
 
             mpOutputDevice->SetFillColor();
@@ -204,10 +182,6 @@ namespace drawinglayer
                 return true;
             }
 
-            const basegfx::BColor aLineColor(
-                maBColorModifierStack.getModifiedColor(
-                    rSource.getLineAttribute().getColor()));
-
             double fLineWidth(rSource.getLineAttribute().getWidth());
 
             if(basegfx::fTools::more(fLineWidth, 0.0))
@@ -228,19 +202,9 @@ namespace drawinglayer
                 fLineWidth = 0.0;
             }
 
-            //Related: tdf#105998 cut and paste as bitmap of shape from draw to
-            //writer.  If we are a hairline along the very right/bottom edge of
-            //the canvas then fallback to defaults which can distort the
-            //hairline inside the paintable area
-            if (fLineWidth == 0.0)
-            {
-                Size aSize = mpOutputDevice->GetOutputSize();
-                basegfx::B2DRange aRange = aHairLinePolyPolygon.getB2DRange();
-                basegfx::B2DRange aOutputRange = aRange;
-                aOutputRange.transform(maCurrentTransformation);
-                if (std::round(aOutputRange.getMaxX()) == aSize.Width() || std::round(aOutputRange.getMaxY()) == aSize.Height())
-                    return false;
-            }
+            const basegfx::BColor aLineColor(
+                maBColorModifierStack.getModifiedColor(
+                    rSource.getLineAttribute().getColor()));
 
             mpOutputDevice->SetFillColor();
             mpOutputDevice->SetLineColor(Color(aLineColor));
diff --git a/svx/source/unodraw/UnoGraphicExporter.cxx b/svx/source/unodraw/UnoGraphicExporter.cxx
index c929114e82cf..b9107915f4c6 100644
--- a/svx/source/unodraw/UnoGraphicExporter.cxx
+++ b/svx/source/unodraw/UnoGraphicExporter.cxx
@@ -178,83 +178,73 @@ namespace {
 
     /** creates a bitmap that is optionally transparent from a metafile
     */
-    BitmapEx GetBitmapFromMetaFile( const GDIMetaFile& rMtf, bool bTransparent, const Size* pSize )
+    BitmapEx GetBitmapFromMetaFile( const GDIMetaFile& rMtf, const Size* pSize )
     {
-        BitmapEx aBmpEx;
+        // use new primitive conversion tooling
+        basegfx::B2DRange aRange(basegfx::B2DPoint(0.0, 0.0));
+        sal_uInt32 nMaximumQuadraticPixels(500000);
 
-        if(bTransparent)
+        if(pSize)
         {
-            // use new primitive conversion tooling
-            basegfx::B2DRange aRange(basegfx::B2DPoint(0.0, 0.0));
-            sal_uInt32 nMaximumQuadraticPixels(500000);
+            // use 100th mm for primitive bitmap converter tool, input is pixel
+            // use a real OutDev to get the correct DPI, the static LogicToLogic assumes 72dpi which is wrong (!)
+            const Size aSize100th(Application::GetDefaultDevice()->PixelToLogic(*pSize, MapMode(MapUnit::Map100thMM)));
 
-            if(pSize)
-            {
-                // use 100th mm for primitive bitmap converter tool, input is pixel
-                // use a real OutDev to get the correct DPI, the static LogicToLogic assumes 72dpi which is wrong (!)
-                const Size aSize100th(Application::GetDefaultDevice()->PixelToLogic(*pSize, MapMode(MapUnit::Map100thMM)));
-
-                aRange.expand(basegfx::B2DPoint(aSize100th.Width(), aSize100th.Height()));
-
-                // when explicitly pixels are requested from the GraphicExporter, use a *very* high limit
-                // of 16gb (4096x4096 pixels), else use the default for the converters
-                nMaximumQuadraticPixels = std::min(sal_uInt32(4096 * 4096), sal_uInt32(pSize->Width() * pSize->Height()));
-            }
-            else
-            {
-                // use 100th mm for primitive bitmap converter tool
-                const Size aSize100th(OutputDevice::LogicToLogic(rMtf.GetPrefSize(), rMtf.GetPrefMapMode(), MapMode(MapUnit::Map100thMM)));
+            aRange.expand(basegfx::B2DPoint(aSize100th.Width(), aSize100th.Height()));
 
-                aRange.expand(basegfx::B2DPoint(aSize100th.Width(), aSize100th.Height()));
-            }
-
-            aBmpEx = convertMetafileToBitmapEx(rMtf, aRange, nMaximumQuadraticPixels);
+            // when explicitly pixels are requested from the GraphicExporter, use a *very* high limit
+            // of 16gb (4096x4096 pixels), else use the default for the converters
+            nMaximumQuadraticPixels = std::min(sal_uInt32(4096 * 4096), sal_uInt32(pSize->Width() * pSize->Height()));
         }
         else
         {
-            const SvtOptionsDrawinglayer aDrawinglayerOpt;
-            Size aTargetSize(0, 0);
-
-            if(pSize)
-            {
-                // #i122820# If a concrete target size in pixels is given, use it
-                aTargetSize = *pSize;
-
-                // get hairline and full bound rect to evtl. reduce given target pixel size when
-                // it is known that it will be expanded to get the right and bottom hairlines right
-                tools::Rectangle aHairlineRect;
-                const tools::Rectangle aRect(rMtf.GetBoundRect(*Application::GetDefaultDevice(), &aHairlineRect));
+            // use 100th mm for primitive bitmap converter tool
+            const Size aSize100th(OutputDevice::LogicToLogic(rMtf.GetPrefSize(), rMtf.GetPrefMapMode(), MapMode(MapUnit::Map100thMM)));
 
-                if(!aRect.IsEmpty() && !aHairlineRect.IsEmpty())
-                {
-                    if(aRect.Right() == aHairlineRect.Right() || aRect.Bottom() == aHairlineRect.Bottom())
-                    {
-                        if(aTargetSize.Width())
-                        {
-                            aTargetSize.AdjustWidth( -1 );
-                        }
-
-                        if(aTargetSize.Height())
-                        {
-                            aTargetSize.AdjustHeight( -1 );
-                        }
-                    }
-                }
-            }
+            aRange.expand(basegfx::B2DPoint(aSize100th.Width(), aSize100th.Height()));
+        }
 
-            const GraphicConversionParameters aParameters(
-                aTargetSize,
-                true, // allow unlimited size
-                aDrawinglayerOpt.IsAntiAliasing(),
-                aDrawinglayerOpt.IsSnapHorVerLinesToDiscrete());
-            const Graphic aGraphic(rMtf);
+        // get hairline and full bound rect to evtl. correct logic size by the
+        // equivalent of one pixel to make those visible at right and bottom
+        tools::Rectangle aHairlineRect;
+        const tools::Rectangle aRect(rMtf.GetBoundRect(*Application::GetDefaultDevice(), &aHairlineRect));
 
-            aBmpEx = aGraphic.GetBitmapEx(aParameters);
-            aBmpEx.SetPrefMapMode( rMtf.GetPrefMapMode() );
-            aBmpEx.SetPrefSize( rMtf.GetPrefSize() );
+        if(!aRect.IsEmpty())
+        {
+            // tdf#105998 Correct the Metafile using information from it's real sizes measured
+            // using rMtf.GetBoundRect above and a copy
+            const Size aOnePixelInMtf(
+                Application::GetDefaultDevice()->PixelToLogic(
+                    Size(1, 1),
+                    rMtf.GetPrefMapMode()));
+            GDIMetaFile aMtf(rMtf);
+            const Size aHalfPixelInMtf(
+                (aOnePixelInMtf.getWidth() + 1) / 2,
+                (aOnePixelInMtf.getHeight() + 1) / 2);
+            const bool bHairlineBR(
+                !aHairlineRect.IsEmpty() && (aRect.Right() == aHairlineRect.Right() || aRect.Bottom() == aHairlineRect.Bottom()));
+
+            // Move the content to (0,0), usually TopLeft ist slightly
+            // negative. For better visualization, add a half pixel, too
+            aMtf.Move(
+                aHalfPixelInMtf.getWidth() - aRect.Left(),
+                aHalfPixelInMtf.getHeight() - aRect.Top());
+
+            // Do not Scale, but set the PrefSize. Some levels deeper the
+            // MetafilePrimitive will add a mapping to the decomposition
+            // (and possibly a clipping) to map the graphic content to
+            // a unit coordinate system.
+            // Size is the measured size plus one pixel if needed (bHairlineBR)
+            // and the moved half pixwel from above
+            aMtf.SetPrefSize(
+                Size(
+                    aRect.getWidth() + (bHairlineBR ? aOnePixelInMtf.getWidth() : 0) + aHalfPixelInMtf.getWidth(),
+                    aRect.getHeight() + (bHairlineBR ? aOnePixelInMtf.getHeight() : 0) + aHalfPixelInMtf.getHeight()));
+
+            return convertMetafileToBitmapEx(aMtf, aRange, nMaximumQuadraticPixels);
         }
 
-        return aBmpEx;
+        return BitmapEx();
     }
 
     Size* CalcSize( sal_Int32 nWidth, sal_Int32 nHeight, const Size& aBoundSize, Size& aOutSize )
@@ -788,7 +778,7 @@ bool GraphicExporter::GetGraphic( ExportSettings const & rSettings, Graphic& aGr
                 if( rSettings.mbTranslucent )
                 {
                     Size aOutSize;
-                    aGraphic = GetBitmapFromMetaFile( aGraphic.GetGDIMetaFile(), true, CalcSize( rSettings.mnWidth, rSettings.mnHeight, aNewSize, aOutSize ) );
+                    aGraphic = GetBitmapFromMetaFile( aGraphic.GetGDIMetaFile(), CalcSize( rSettings.mnWidth, rSettings.mnHeight, aNewSize, aOutSize ) );
                 }
             }
         }
@@ -978,7 +968,7 @@ bool GraphicExporter::GetGraphic( ExportSettings const & rSettings, Graphic& aGr
             if( !bVectorType )
             {
                 Size aOutSize;
-                aGraphic = GetBitmapFromMetaFile( aMtf, rSettings.mbTranslucent, CalcSize( rSettings.mnWidth, rSettings.mnHeight, aBoundSize, aOutSize ) );
+                aGraphic = GetBitmapFromMetaFile( aMtf, CalcSize( rSettings.mnWidth, rSettings.mnHeight, aBoundSize, aOutSize ) );
             }
             else
             {


More information about the Libreoffice-commits mailing list