Kaydet (Commit) 046df0a8 authored tarafından Armin Le Grand's avatar Armin Le Grand

tdf#105998: Enhanced fix for MetafileToBitmap at better place

Change-Id: I220bdbe196a68ef2df25885dceee70e15b760410
Reviewed-on: https://gerrit.libreoffice.org/59220
Tested-by: Jenkins
Reviewed-by: 's avatarArmin Le Grand <Armin.Le.Grand@cib.de>
üst bc28d51c
......@@ -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));
......
......@@ -178,11 +178,7 @@ namespace {
/** creates a bitmap that is optionally transparent from a metafile
*/
BitmapEx GetBitmapFromMetaFile( const GDIMetaFile& rMtf, bool bTransparent, const Size* pSize )
{
BitmapEx aBmpEx;
if(bTransparent)
BitmapEx GetBitmapFromMetaFile( const GDIMetaFile& rMtf, const Size* pSize )
{
// use new primitive conversion tooling
basegfx::B2DRange aRange(basegfx::B2DPoint(0.0, 0.0));
......@@ -208,53 +204,47 @@ namespace {
aRange.expand(basegfx::B2DPoint(aSize100th.Width(), aSize100th.Height()));
}
aBmpEx = convertMetafileToBitmapEx(rMtf, aRange, nMaximumQuadraticPixels);
}
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
// 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));
if(!aRect.IsEmpty() && !aHairlineRect.IsEmpty())
if(!aRect.IsEmpty())
{
if(aRect.Right() == aHairlineRect.Right() || aRect.Bottom() == aHairlineRect.Bottom())
{
if(aTargetSize.Width())
{
aTargetSize.AdjustWidth( -1 );
}
// 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()));
if(aTargetSize.Height())
{
aTargetSize.AdjustHeight( -1 );
}
}
}
}
// 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());
const GraphicConversionParameters aParameters(
aTargetSize,
true, // allow unlimited size
aDrawinglayerOpt.IsAntiAliasing(),
aDrawinglayerOpt.IsSnapHorVerLinesToDiscrete());
const Graphic aGraphic(rMtf);
// 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()));
aBmpEx = aGraphic.GetBitmapEx(aParameters);
aBmpEx.SetPrefMapMode( rMtf.GetPrefMapMode() );
aBmpEx.SetPrefSize( rMtf.GetPrefSize() );
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
{
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment