[SkiaPaths] Tiling pattern with overlapping paths causes unwanted grid.

When a colored tiling pattern's opacity value is not 1.0, the section
of overlapped patterns will have a different shade of color.
bug_1286.in is not rendered correctly because the patterns' paths
(borders) are overlapping and SkiaPaths chose to use
kDifference_SkPathOp to subtract the latter path from the previous one,
which result in the overlapping paths to have a lighter color than the
pattern itself and displayed as a grid. Need to use kUnion_SkPathOp to
union the overlapping paths and skip stroking the path if the path's
fill color is the same as the stroke color, so that the overlapping
part of the unionized paths won't show in a darker shade.

Bug: pdfium:1342
Change-Id: Ideb665ae42bd077f6fe3be364a056286a520a1e6
Reviewed-on: https://pdfium-review.googlesource.com/c/pdfium/+/60230
Reviewed-by: Lei Zhang <thestig@chromium.org>
Commit-Queue: Hui Yingst <nigi@chromium.org>
diff --git a/core/fxge/skia/fx_skia_device.cpp b/core/fxge/skia/fx_skia_device.cpp
index ad42393..aae7a5d 100644
--- a/core/fxge/skia/fx_skia_device.cpp
+++ b/core/fxge/skia/fx_skia_device.cpp
@@ -787,15 +787,21 @@
     SkCanvas* skCanvas = m_pDriver->SkiaCanvas();
     SkAutoCanvasRestore scoped_save_restore(skCanvas, /*doSave=*/true);
     skCanvas->concat(skMatrix);
+    bool do_stroke = true;
     if (m_fillPath) {
       SkPath strokePath;
       const SkPath* fillPath = &m_skPath;
       if (stroke_alpha) {
         if (m_groupKnockout) {
           skPaint.getFillPath(m_skPath, &strokePath);
-          if (Op(m_skPath, strokePath, SkPathOp::kDifference_SkPathOp,
+          if (m_strokeColor == m_fillColor &&
+              Op(m_skPath, strokePath, SkPathOp::kUnion_SkPathOp,
                  &strokePath)) {
             fillPath = &strokePath;
+            do_stroke = false;
+          } else if (Op(m_skPath, strokePath, SkPathOp::kDifference_SkPathOp,
+                        &strokePath)) {
+            fillPath = &strokePath;
           }
         }
       }
@@ -807,7 +813,7 @@
       DebugShowSkiaDrawPath(m_pDriver.Get(), skCanvas, skPaint, *fillPath);
       skCanvas->drawPath(*fillPath, skPaint);
     }
-    if (stroke_alpha) {
+    if (stroke_alpha && do_stroke) {
       skPaint.setStyle(SkPaint::kStroke_Style);
       skPaint.setColor(m_strokeColor);
 #ifdef _SKIA_SUPPORT_PATHS_
@@ -2050,6 +2056,7 @@
   SkPath skPath = BuildPath(pPathData);
   SkAutoCanvasRestore scoped_save_restore(m_pCanvas, /*doSave=*/true);
   m_pCanvas->concat(skMatrix);
+  bool do_stroke = true;
   if (GetAlternateOrWindingFillMode(fill_mode) && fill_color) {
     skPath.setFillType(GetAlternateOrWindingFillType(fill_mode));
     SkPath strokePath;
@@ -2057,8 +2064,12 @@
     if (is_paint_stroke) {
       if (m_bGroupKnockout) {
         skPaint.getFillPath(skPath, &strokePath);
-        if (Op(skPath, strokePath, SkPathOp::kDifference_SkPathOp,
-               &strokePath)) {
+        if (stroke_color == fill_color &&
+            Op(skPath, strokePath, SkPathOp::kUnion_SkPathOp, &strokePath)) {
+          fillPath = &strokePath;
+          do_stroke = false;
+        } else if (Op(skPath, strokePath, SkPathOp::kDifference_SkPathOp,
+                      &strokePath)) {
           fillPath = &strokePath;
         }
       }
@@ -2071,7 +2082,7 @@
     DebugShowSkiaDrawPath(this, m_pCanvas, skPaint, *fillPath);
     m_pCanvas->drawPath(*fillPath, skPaint);
   }
-  if (is_paint_stroke) {
+  if (is_paint_stroke && do_stroke) {
     skPaint.setStyle(SkPaint::kStroke_Style);
     skPaint.setColor(stroke_color);
 #ifdef _SKIA_SUPPORT_PATHS_