Skip to content

Commit 581481c

Browse files
committed
Improve pretty_poly performance
(cherry picked from commit 1077a12ff4fd958a7ea6d9e4fa5a86551eba5126)
1 parent 9124b37 commit 581481c

File tree

2 files changed

+43
-15
lines changed

2 files changed

+43
-15
lines changed

libraries/pico_vector/pretty_poly.cpp

Lines changed: 42 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -79,35 +79,42 @@ namespace pretty_poly {
7979
std::swap(sx, ex);
8080
}
8181

82+
if (ey < 0 || sy >= (int)node_buffer_size) return;
83+
8284
/*sx <<= settings::antialias;
8385
ex <<= settings::antialias;
8486
sy <<= settings::antialias;
8587
ey <<= settings::antialias;*/
8688

8789
int x = sx;
88-
int y = sy;
8990
int e = 0;
9091

9192
int xinc = sign(ex - sx);
9293
int einc = abs(ex - sx) + 1;
93-
94-
// todo: preclamp sy and ey (and therefore count) no need to perform
95-
// that test inside the loop
9694
int dy = ey - sy;
97-
int count = dy;
95+
96+
if (sy < 0) {
97+
e = einc * -sy;
98+
int xjump = e / dy;
99+
e -= dy * xjump;
100+
x += xinc * xjump;
101+
sy = 0;
102+
}
103+
104+
int y = sy;
105+
106+
int count = std::min((int)node_buffer_size, ey) - sy;
98107
debug(" + line segment from %d, %d to %d, %d\n", sx, sy, ex, ey);
99108
// loop over scanlines
100109
while(count--) {
101110
// consume accumulated error
102111
while(e > dy) {e -= dy; x += xinc;}
103112

104-
if(y >= 0 && y < (int)node_buffer_size) {
105-
// clamp node x value to tile bounds
106-
int nx = std::max(std::min(x, (int)(tile_bounds.w << settings::antialias)), 0);
107-
debug(" + adding node at %d, %d\n", x, y);
108-
// add node to node list
109-
nodes[y][node_counts[y]++] = nx;
110-
}
113+
// clamp node x value to tile bounds
114+
int nx = std::max(std::min(x, (int)(tile_bounds.w << settings::antialias)), 0);
115+
debug(" + adding node at %d, %d\n", x, y);
116+
// add node to node list
117+
nodes[y][node_counts[y]++] = nx;
111118

112119
// step to next scanline and accumulate error
113120
y++;
@@ -138,11 +145,17 @@ namespace pretty_poly {
138145
}
139146
}
140147

141-
void render_nodes(const tile_t &tile) {
148+
void render_nodes(const tile_t &tile, rect_t &bounds) {
149+
int maxy = -1;
150+
bounds.y = 0;
151+
bounds.x = tile.bounds.w;
152+
int maxx = 0;
142153
for(auto y = 0; y < (int)node_buffer_size; y++) {
143154
if(node_counts[y] == 0) {
155+
if (y == bounds.y) ++bounds.y;
144156
continue;
145157
}
158+
maxy = y;
146159

147160
std::sort(&nodes[y][0], &nodes[y][0] + node_counts[y]);
148161

@@ -154,13 +167,19 @@ namespace pretty_poly {
154167
continue;
155168
}
156169

170+
bounds.x = std::min(sx >> settings::antialias, bounds.x);
171+
maxx = std::max((ex - 1) >> settings::antialias, maxx);
172+
157173
debug(" - render span at %d from %d to %d\n", y, sx, ex);
158174

159175
for(int x = sx; x < ex; x++) {
160176
tile.data[(x >> settings::antialias) + (y >> settings::antialias) * tile.stride]++;
161177
}
162178
}
163179
}
180+
181+
bounds.w = (maxx >= bounds.x) ? maxx + 1 - bounds.x : 0;
182+
bounds.h = (maxy >= bounds.y) ? maxy + 1 - bounds.y : 0;
164183
}
165184

166185
template<typename T>
@@ -225,7 +244,16 @@ namespace pretty_poly {
225244

226245
debug(" : render the tile\n");
227246
// render the tile
228-
render_nodes(tile);
247+
rect_t bounds;
248+
render_nodes(tile, bounds);
249+
250+
tile.data += bounds.x + tile.stride * bounds.y;
251+
bounds.x += tile.bounds.x;
252+
bounds.y += tile.bounds.y;
253+
tile.bounds = bounds.intersection(tile.bounds);
254+
if (tile.bounds.empty()) {
255+
continue;
256+
}
229257

230258
settings::callback(tile);
231259
}

libraries/pico_vector/pretty_poly.hpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,7 @@ namespace pretty_poly {
6262
template<typename T>
6363
void build_nodes(const contour_t<T> &contour, const tile_t &tile, point_t<int> origin = point_t<int>(0, 0), int scale = 65536);
6464

65-
void render_nodes(const tile_t &tile);
65+
void render_nodes(const tile_t &tile, rect_t &bounds);
6666

6767
template<typename T>
6868
void draw_polygon(T *points, unsigned count);

0 commit comments

Comments
 (0)