mirror of
https://github.com/ultravideo/uvg266.git
synced 2024-11-23 18:14:06 +00:00
[refwrap] Fix the uvg_get_extended_block_wraparound() and use memcpy
This commit is contained in:
parent
96c6dee6ab
commit
e8633dab1d
|
@ -818,35 +818,54 @@ void uvg_get_extended_block_wraparound_generic(uvg_epol_args *args)
|
|||
bool out_of_bounds_y = (min_y < 0) || (max_y >= args->src_h);
|
||||
|
||||
int min_x = args->blk_x - args->pad_l;
|
||||
int max_x = args->blk_x + args->blk_w + args->pad_r - 1;
|
||||
int max_x = args->blk_x + args->blk_w + args->pad_r;
|
||||
bool out_of_bounds_x = (min_x < 0) || (max_x >= args->src_w);
|
||||
|
||||
if (out_of_bounds_y || out_of_bounds_x) {
|
||||
|
||||
int first_x_start = 0;
|
||||
int first_x_count = 0;
|
||||
|
||||
int second_x_start = 0;
|
||||
int second_x_count = 0;
|
||||
|
||||
|
||||
if (out_of_bounds_x) {
|
||||
if (min_x < 0) { // The block goes over the left edge of the frame.
|
||||
first_x_start = args->src_w + min_x;
|
||||
first_x_count = -min_x;
|
||||
if (max_x >= 0) { // Right side of the block doesn't wrap around the frame so we need to copy it separately.
|
||||
second_x_count = max_x;
|
||||
}
|
||||
} else { // The block wraps around the right edge of the frame.
|
||||
if (min_x >= args->src_w) { // The whole block wraps around the frame so copy in one go.
|
||||
first_x_start = min_x - args->src_w;
|
||||
first_x_count = max_x-min_x;
|
||||
} else { // The left side of the block doesn't wrap around the frame so we need to copy it separately.
|
||||
first_x_start = min_x;
|
||||
first_x_count = args->src_w - min_x;
|
||||
second_x_count = max_x - args->src_w;
|
||||
}
|
||||
}
|
||||
} else { // The block is not over the horizontal edges of the frame, just copy directly
|
||||
first_x_count = max_x-min_x;
|
||||
first_x_start = min_x;
|
||||
}
|
||||
|
||||
*args->ext = args->buf;
|
||||
*args->ext_s = args->pad_l + args->blk_w + args->pad_r;
|
||||
*args->ext_origin = args->buf + args->pad_t * (*args->ext_s) + args->pad_l;
|
||||
|
||||
// Note that stride equals width here.
|
||||
int count_left = CLIP(0, *args->ext_s, -min_x);
|
||||
int count_right = CLIP(0, *args->ext_s, max_x - (args->src_w - 1));
|
||||
int count_middle = CLIP(0, *args->ext_s, *args->ext_s - count_left - count_right);
|
||||
|
||||
// For each row including real padding.
|
||||
// Don't read "don't care" values (SIMD padding). Zero them out.
|
||||
int y;
|
||||
for (y = -args->pad_t; y < args->blk_h + args->pad_b; ++y) {
|
||||
int clipped_y = CLIP(0, args->src_h - 1, args->blk_y + y);
|
||||
uvg_pixel *sample_l = args->src + clipped_y * args->src_s;
|
||||
uvg_pixel *sample_r =
|
||||
args->src + clipped_y * args->src_s + args->src_w - 1;
|
||||
uvg_pixel *src_m = args->src + clipped_y * args->src_s + MAX(min_x, 0);
|
||||
uvg_pixel *dst_l = args->buf + (y + args->pad_t) * (*args->ext_s);
|
||||
uvg_pixel *dst_m = dst_l + count_left;
|
||||
uvg_pixel *dst_r = dst_m + count_middle;
|
||||
for (int i = 0; i < count_left; ++i) *(dst_l + i) = *((sample_r - (count_left-1)) + i);
|
||||
for (int i = 0; i < count_middle; ++i) *(dst_m + i) = *(src_m + i);
|
||||
for (int i = 0; i < count_right; ++i) *(dst_r + i) = *(sample_l + i);
|
||||
uvg_pixel *samples = args->src + clipped_y * args->src_s;
|
||||
uvg_pixel *dst = args->buf + (y + args->pad_t) * (*args->ext_s);
|
||||
|
||||
if (first_x_count) memcpy(dst, samples + first_x_start, first_x_count*sizeof(uvg_pixel));
|
||||
if (second_x_count) memcpy(dst + first_x_count, samples + second_x_start, second_x_count*sizeof(uvg_pixel));
|
||||
}
|
||||
|
||||
for (int y_simd = 0; y_simd < args->pad_b_simd; ++y_simd) {
|
||||
|
|
Loading…
Reference in a new issue