Skip to content

Commit

Permalink
JS: Fix stride calculation for images with odd widths.
Browse files Browse the repository at this point in the history
  • Loading branch information
fancycode committed Nov 2, 2020
1 parent 3a023f9 commit d97b79f
Show file tree
Hide file tree
Showing 2 changed files with 14 additions and 9 deletions.
12 changes: 8 additions & 4 deletions libheif/heif_emscripten.h
Expand Up @@ -88,6 +88,10 @@ static emscripten::val heif_js_context_get_list_of_top_level_image_IDs(
return result;
}

static int round_odd(int v) {
return (int) ((v / 2.0) + 0.5);
}

static emscripten::val heif_js_decode_image(struct heif_image_handle* handle,
enum heif_colorspace colorspace, enum heif_chroma chroma)
{
Expand Down Expand Up @@ -122,13 +126,13 @@ static emscripten::val heif_js_decode_image(struct heif_image_handle* handle,
int stride_v;
const uint8_t* plane_v = heif_image_get_plane_readonly(image,
heif_channel_Cr, &stride_v);
data.resize((width * height) + (width * height / 2));
data.resize((width * height) + (2 * round_odd(width) * round_odd(height)));
char* dest = const_cast<char*>(data.data());
strided_copy(dest, plane_y, width, height, stride_y);
strided_copy(dest + (width * height), plane_u,
width / 2, height / 2, stride_u);
strided_copy(dest + (width * height) + (width * height / 4),
plane_v, width / 2, height / 2, stride_v);
round_odd(width), round_odd(height), stride_u);
strided_copy(dest + (width * height) + (round_odd(width) * round_odd(height)),
plane_v, round_odd(width), round_odd(height), stride_v);
}
break;
case heif_colorspace_RGB: {
Expand Down
11 changes: 6 additions & 5 deletions post.js
Expand Up @@ -75,12 +75,13 @@ HeifImage.prototype.display = function(image_data, callback) {
var x2;
var i = 0;
var maxi = w*h;
var y = this.data;
var u = this.data.subarray(w * h, w * h + (w * h / 4));
var v = this.data.subarray(w * h + (w * h / 4), w * h + (w * h / 2));
var stridey = w;
var strideu = Math.floor(w / 2);
var stridev = Math.floor(w / 2);
var strideu = Math.ceil(w / 2);
var stridev = Math.ceil(w / 2);
var h2 = Math.ceil(h / 2);
var y = this.data;
var u = this.data.subarray(stridey * h, stridey * h + (strideu * h2));
var v = this.data.subarray(stridey * h + (strideu * h2), stridey * h + (strideu * h2) + (stridev * h2));
var dest = image_data.data;
while (i < maxi) {
x2 = (xpos >> 1);
Expand Down

0 comments on commit d97b79f

Please sign in to comment.