41 if (
callback(x1, y1, user_data) == 0) {
46 const int sign_x = (x2 > x1) ? 1 : -1;
47 const int sign_y = (y2 > y1) ? 1 : -1;
49 const int delta_x = (sign_x == 1) ? (x2 - x1) : (x1 - x2);
50 const int delta_y = (sign_y == 1) ? (y2 - y1) : (y1 - y2);
52 const int delta_x_step = delta_x * 2;
53 const int delta_y_step = delta_y * 2;
55 if (delta_x >= delta_y) {
57 int error = delta_y_step - delta_x;
61 if (
error || (sign_x == 1)) {
63 error -= delta_x_step;
70 error += delta_y_step;
72 if (
callback(x1, y1, user_data) == 0) {
79 int error = delta_x_step - delta_y;
83 if (
error || (sign_y == 1)) {
85 error -= delta_y_step;
92 error += delta_x_step;
94 if (
callback(x1, y1, user_data) == 0) {
124#define ORDERED_SWAP(ty, a, b) \
130#define ORDERED_SWAP_BY(ty, a, b, by) \
131 if ((a by) > (b by)) { \
136#define ORDER_VARS2(ty, a, b) \
138 ORDERED_SWAP(ty, a, b); \
142#define ORDER_VARS3_BY(ty, a, b, c, by) \
144 ORDERED_SWAP_BY(ty, b, c, by); \
145 ORDERED_SWAP_BY(ty, a, c, by); \
146 ORDERED_SWAP_BY(ty, a, b, by); \
164 const float inv_slope1,
165 const float inv_slope2,
166 void (*
callback)(
int x,
int x_end,
int y,
void *),
169 float cur_x1 =
float(p[0]);
170 float cur_x2 = cur_x1;
172 const int min_y = p[1];
173 const int max_y_end = max_y + 1;
174 for (
int scanline_y = min_y; scanline_y != max_y_end; scanline_y += 1) {
175 callback(
int(cur_x1), 1 +
int(cur_x2), scanline_y, user_data);
176 cur_x1 += inv_slope1;
177 cur_x2 += inv_slope2;
190 const float inv_slope1,
191 const float inv_slope2,
192 void (*
callback)(
int x,
int x_end,
int y,
void *),
195 float cur_x1 =
float(p[0]);
196 float cur_x2 = cur_x1;
198 const int max_y = p[1];
199 const int min_y_end = min_y - 1;
200 for (
int scanline_y = max_y; scanline_y != min_y_end; scanline_y -= 1) {
201 callback(
int(cur_x1), 1 +
int(cur_x2), scanline_y, user_data);
202 cur_x1 -= inv_slope1;
203 cur_x2 -= inv_slope2;
212 void (*
callback)(
int x,
int x_end,
int y,
void *),
221 if (p2[1] == p3[1]) {
228 else if (p1[1] == p2[1]) {
243 const float inv_slope_p21 =
inv_slope(p2, p1);
244 const float inv_slope_p31 =
inv_slope(p3, p1);
245 const float inv_slope_p32 =
inv_slope(p3, p2);
247 float inv_slope1_max, inv_slope2_max;
248 float inv_slope2_min, inv_slope1_min;
250 if (inv_slope_p21 < inv_slope_p31) {
251 inv_slope1_max = inv_slope_p21;
252 inv_slope2_max = inv_slope_p31;
253 inv_slope2_min = inv_slope_p31;
254 inv_slope1_min = inv_slope_p32;
257 inv_slope1_max = inv_slope_p31;
258 inv_slope2_max = inv_slope_p21;
259 inv_slope2_min = inv_slope_p32;
260 inv_slope1_min = inv_slope_p31;
274#undef ORDERED_SWAP_BY
287 const int(*
verts)[2] =
static_cast<const int(*)[2]
>(verts_p);
288 const int *a =
static_cast<const int *
>(a_p);
289 const int *
b =
static_cast<const int *
>(b_p);
290 const int *co_a =
verts[a[0]];
291 const int *co_b =
verts[
b[0]];
293 if (co_a[1] < co_b[1]) {
296 if (co_a[1] > co_b[1]) {
299 if (co_a[0] < co_b[0]) {
302 if (co_a[0] > co_b[0]) {
306 const int *co = co_a;
309 int ord = (((co_b[0] - co[0]) * (co_a[1] - co[1])) - ((co_a[0] - co[0]) * (co_b[1] - co[1])));
324 void (*
callback)(
int x,
int x_end,
int y,
void *),
330 int(*span_y)[2] =
static_cast<int(*)[2]
>(
334 for (
int i_curr = 0, i_prev =
int(
verts.size() - 1); i_curr <
verts.size(); i_prev = i_curr++) {
335 const int *co_prev =
verts[i_prev];
336 const int *co_curr =
verts[i_curr];
338 if (co_prev[1] != co_curr[1]) {
340 if ((
min_ii(co_prev[1], co_curr[1]) >= ymax) || (
max_ii(co_prev[1], co_curr[1]) < ymin)) {
344 int *s = span_y[span_y_len++];
345 if (co_prev[1] < co_curr[1]) {
360 (
void *)
verts.data());
365 } *node_x =
static_cast<NodeX *
>(
369 int span_y_index = 0;
370 if (span_y_len != 0 &&
verts[span_y[0][0]][1] < ymin) {
371 while ((span_y_index < span_y_len) && (
verts[span_y[span_y_index][0]][1] < ymin)) {
373 if (
verts[span_y[span_y_index][1]][1] >= ymin) {
374 NodeX *n = &node_x[node_x_len++];
375 n->span_y_index = span_y_index;
382 for (
int pixel_y = ymin; pixel_y < ymax; pixel_y++) {
383 bool is_sorted =
true;
384 bool do_remove =
false;
386 for (
int i = 0, x_ix_prev = INT_MIN; i < node_x_len; i++) {
387 NodeX *n = &node_x[i];
388 const int *s = span_y[n->span_y_index];
389 const int *co_prev =
verts[s[0]];
390 const int *co_curr =
verts[s[1]];
392 BLI_assert(co_prev[1] < pixel_y && co_curr[1] >= pixel_y);
394 const double x = (co_prev[0] - co_curr[0]);
395 const double y = (co_prev[1] - co_curr[1]);
396 const double y_px = (pixel_y - co_curr[1]);
397 const int x_ix =
int(
double(co_curr[0]) + ((y_px / y) * x));
400 if (is_sorted && (x_ix_prev > x_ix)) {
403 if (do_remove ==
false && co_curr[1] == pixel_y) {
410 if (is_sorted ==
false) {
412 const int node_x_end = node_x_len - 1;
413 while (i < node_x_end) {
414 if (node_x[i].x > node_x[i + 1].x) {
415 SWAP(NodeX, node_x[i], node_x[i + 1]);
427 for (
int i = 0; i < node_x_len; i += 2) {
428 int x_src = node_x[i].x;
429 int x_dst = node_x[i + 1].x;
444 callback(x_src - xmin, x_dst - xmin, pixel_y - ymin, user_data);
451 if (do_remove ==
true) {
453 for (
int i_src = 0; i_src < node_x_len; i_src += 1) {
454 const int *s = span_y[node_x[i_src].span_y_index];
455 const int *co =
verts[s[1]];
456 if (co[1] != pixel_y) {
457 if (i_dst != i_src) {
459 node_x[i_dst].span_y_index = node_x[i_src].span_y_index;
468 while ((span_y_index < span_y_len) && (
verts[span_y[span_y_index][0]][1] == pixel_y)) {
473 NodeX *n = &node_x[node_x_len++];
474 n->span_y_index = span_y_index;
MINLINE int min_ii(int a, int b)
MINLINE int max_ii(int a, int b)
void BLI_qsort_r(void *a, size_t n, size_t es, BLI_sort_cmp_t cmp, void *thunk)
Read Guarded memory(de)allocation.
void BLI_bitmap_draw_2d_poly_v2i_n(const int xmin, const int ymin, const int xmax, const int ymax, const Span< int2 > verts, void(*callback)(int x, int x_end, int y, void *), void *user_data)
static int draw_poly_v2i_n__span_y_sort(const void *a_p, const void *b_p, void *verts_p)
static float inv_slope(const int a[2], const int b[2])
void BLI_bitmap_draw_2d_line_v2v2i(const int p1[2], const int p2[2], bool(*callback)(int, int, void *), void *user_data)
void BLI_bitmap_draw_2d_tri_v2i(const int p1[2], const int p2[2], const int p3[2], void(*callback)(int x, int x_end, int y, void *), void *user_data)
static void draw_tri_flat_max(const int p[2], const int max_y, const float inv_slope1, const float inv_slope2, void(*callback)(int x, int x_end, int y, void *), void *user_data)
static void draw_tri_flat_min(const int p[2], const int min_y, const float inv_slope1, const float inv_slope2, void(*callback)(int x, int x_end, int y, void *), void *user_data)
#define ORDER_VARS3_BY(ty, a, b, c, by)
#define ORDER_VARS2(ty, a, b)
local_group_size(16, 16) .push_constant(Type b
DEGForeachIDComponentCallback callback
draw_view in_light_buf[] float
draw_view push_constant(Type::INT, "radiance_src") .push_constant(Type capture_info_buf storage_buf(1, Qualifier::READ, "ObjectBounds", "bounds_buf[]") .push_constant(Type draw_view int
void *(* MEM_mallocN)(size_t len, const char *str)
void MEM_freeN(void *vmemh)
static void error(const char *str)