• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1  /*
2   * Copyright 2019 Google LLC.
3   *
4   * Use of this source code is governed by a BSD-style license that can be
5   * found in the LICENSE file.
6   */
7  
8  #include "gm/gm.h"
9  
10  #include "include/core/SkCanvas.h"
11  #include "include/core/SkPaint.h"
12  #include "include/core/SkPath.h"
13  
14  /**
15   * Repro case for https://bugs.chromium.org/p/chromium/issues/detail?id=913223
16   *
17   * The original bug was filed against square caps, but here we also draw the labyrinth using round
18   * and butt caps.
19   *
20   * Square and round caps expose over-coverage on overlaps when using coverage counting.
21   *
22   * Butt caps expose under-coverage on abutted strokes when using a 'max()' coverage function.
23   */
draw_labyrinth(SkCanvas * canvas,SkPaint::Cap cap)24  static void draw_labyrinth(SkCanvas* canvas, SkPaint::Cap cap) {
25      constexpr static bool kRows[11][12] = {
26          {1,1,1,1,1,1,1,1,1,1,1,1},
27          {0,1,0,1,0,1,0,0,0,0,1,1},
28          {0,0,0,0,1,0,0,0,0,1,1,1},
29          {1,0,1,0,0,0,0,1,0,0,0,0},
30          {0,1,1,0,0,0,0,0,0,1,1,1},
31          {1,0,0,1,0,0,0,0,1,1,1,0},
32          {0,1,0,1,1,1,0,0,1,1,1,0},
33          {1,0,1,0,1,1,1,1,0,1,1,1},
34          {0,0,1,0,0,1,0,0,0,0,0,1},
35          {0,1,1,1,0,0,1,1,1,1,0,0},
36          {1,1,1,1,1,1,1,1,1,1,1,1},
37      };
38  
39      constexpr static bool kCols[13][10] = {
40          {1,1,1,1,0,1,1,1,1,1},
41          {0,0,1,0,0,0,1,1,1,0},
42          {0,1,1,0,1,1,1,0,0,1},
43          {1,1,0,0,0,0,1,0,1,0},
44          {0,0,1,0,1,0,0,0,0,1},
45          {0,0,1,1,1,0,0,0,1,0},
46          {0,1,0,1,1,1,0,0,0,0},
47          {1,1,1,0,1,1,1,0,1,0},
48          {1,1,0,1,1,0,0,0,1,0},
49          {0,0,1,0,0,0,0,0,0,1},
50          {0,0,1,1,0,0,0,0,1,0},
51          {0,0,0,0,0,0,1,0,0,1},
52          {1,1,1,1,1,1,0,1,1,1},
53      };
54  
55      SkPath maze;
56      for (size_t y = 0; y < SK_ARRAY_COUNT(kRows); ++y) {
57          for (size_t x = 0; x < SK_ARRAY_COUNT(kRows[0]); ++x) {
58              if (kRows[y][x]) {
59                  maze.moveTo(x, y);
60                  maze.lineTo(x+1, y);
61              }
62          }
63      }
64      for (size_t x = 0; x < SK_ARRAY_COUNT(kCols); ++x) {
65          for (size_t y = 0; y < SK_ARRAY_COUNT(kCols[0]); ++y) {
66              if (kCols[x][y]) {
67                  maze.moveTo(x, y);
68                  maze.lineTo(x, y+1);
69              }
70          }
71      }
72  
73      SkPaint paint;
74      paint.setStyle(SkPaint::kStroke_Style);
75      paint.setStrokeWidth(.1f);
76      paint.setColor(0xff406060);
77      paint.setAntiAlias(true);
78      paint.setStrokeCap(cap);
79  
80      canvas->translate(10.5, 10.5);
81      canvas->scale(40, 40);
82      canvas->drawPath(maze, paint);
83  }
84  
85  constexpr static int kWidth = 500;
86  constexpr static int kHeight = 420;
87  
DEF_SIMPLE_GM(labyrinth_square,canvas,kWidth,kHeight)88  DEF_SIMPLE_GM(labyrinth_square, canvas, kWidth, kHeight) {
89      draw_labyrinth(canvas, SkPaint::kSquare_Cap);
90  }
91  
DEF_SIMPLE_GM(labyrinth_round,canvas,kWidth,kHeight)92  DEF_SIMPLE_GM(labyrinth_round, canvas, kWidth, kHeight) {
93      draw_labyrinth(canvas, SkPaint::kRound_Cap);
94  }
95  
DEF_SIMPLE_GM(labyrinth_butt,canvas,kWidth,kHeight)96  DEF_SIMPLE_GM(labyrinth_butt, canvas, kWidth, kHeight) {
97      draw_labyrinth(canvas, SkPaint::kButt_Cap);
98  }
99