don't split polypolygon in canvas if not needed (tdf#135395)

Those polygons will be merged back in Skia because of
12147e0322e0fdd1b561c94e7ebd3fdd69ceaac0, which is costly with
tdf#135395. And if the only reason for the splitting is that
the polygon requires a winding rule but DrawPolyPolygon() uses
evenodd rule, then simply convert the polygon to the evenodd rule.

Change-Id: Iba5ec31d6d6407f734b20badc80c846071068d40
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/100976
Tested-by: Jenkins
Reviewed-by: Luboš Luňák <l.lunak@collabora.com>
diff --git a/canvas/source/vcl/canvashelper.cxx b/canvas/source/vcl/canvashelper.cxx
index 78a0ae3..fcfabb8 100644
--- a/canvas/source/vcl/canvashelper.cxx
+++ b/canvas/source/vcl/canvashelper.cxx
@@ -25,6 +25,7 @@
#include <basegfx/polygon/b2dlinegeometry.hxx>
#include <basegfx/polygon/b2dpolygon.hxx>
#include <basegfx/polygon/b2dpolygontools.hxx>
#include <basegfx/polygon/b2dpolypolygoncutter.hxx>
#include <basegfx/polygon/b2dpolypolygontools.hxx>
#include <basegfx/range/b2drectangle.hxx>
#include <basegfx/utils/canvastools.hxx>
@@ -394,24 +395,33 @@ namespace vclcanvas
            // user coordinates.
            aStrokedPolyPoly.transform( aMatrix );

            // TODO(F2): When using alpha here, must handle that via
            // temporary surface or somesuch.

            // Note: the generated stroke poly-polygon is NOT free of
            // self-intersections. Therefore, if we would render it
            // via OutDev::DrawPolyPolygon(), on/off fill would
            // generate off areas on those self-intersections.
            for( sal_uInt32 i=0; i<aStrokedPolyPoly.count(); ++i )
            if(aStrokedPolyPoly.isClosed())
            {
                const basegfx::B2DPolygon& polygon = aStrokedPolyPoly.getB2DPolygon( i );
                if( polygon.isClosed()) {
                    mpOutDevProvider->getOutDev().DrawPolygon( polygon );
                    if( mp2ndOutDevProvider )
                        mp2ndOutDevProvider->getOutDev().DrawPolygon( polygon );
                } else {
                    mpOutDevProvider->getOutDev().DrawPolyLine( polygon );
                    if( mp2ndOutDevProvider )
                        mp2ndOutDevProvider->getOutDev().DrawPolyLine( polygon );
                // Note: the generated stroke poly-polygon is NOT free of
                // self-intersections. Therefore, if we would render it
                // directly via OutDev::DrawPolyPolygon(), on/off fill would
                // generate off areas on those self-intersections.
                aStrokedPolyPoly = basegfx::utils::createNonzeroConform( aStrokedPolyPoly );
                mpOutDevProvider->getOutDev().DrawPolyPolygon( aStrokedPolyPoly );
                if( mp2ndOutDevProvider )
                    mp2ndOutDevProvider->getOutDev().DrawPolyPolygon( aStrokedPolyPoly );
            }
            else
            {
                // TODO(F2): When using alpha here, must handle that via
                // temporary surface or somesuch.
                for( sal_uInt32 i=0; i<aStrokedPolyPoly.count(); ++i )
                {
                    const basegfx::B2DPolygon& polygon = aStrokedPolyPoly.getB2DPolygon( i );
                    if( polygon.isClosed()) {
                        mpOutDevProvider->getOutDev().DrawPolygon( polygon );
                        if( mp2ndOutDevProvider )
                            mp2ndOutDevProvider->getOutDev().DrawPolygon( polygon );
                    } else {
                        mpOutDevProvider->getOutDev().DrawPolyLine( polygon );
                        if( mp2ndOutDevProvider )
                            mp2ndOutDevProvider->getOutDev().DrawPolyLine( polygon );
                    }
                }
            }
        }