Note that there are some explanatory texts on larger screens.

plurals
  1. POBilinear Interpolation image resizing marks & 'splotches'
    text
    copied!<p>I'm making an image resizing program in C and at the moment I'm having trouble with the Bilinear Interpolation function (it's one of many I'm using). This problem only arises for 16-bit bitmaps, If I use 24-bit versions, it resizes them perfectly.</p> <p>Here's my code for the Bilinear Interpolation. n_w and n_h are the new widths and heights of the image:</p> <pre><code>#define getelm(x) (((pix+index)-&gt;x)*(1-xdiff)*(1-ydiff))+(((pix+index+1)-&gt;x)*(xdiff)*(1-ydiff))+(((pix+index+o_w)-&gt;x)*(1-xdiff)*(ydiff))+((pix+index+o_w+1)-&gt;x)*xdiff*ydiff int pad = (2*n_w) &amp; 3; if (pad) pad = 4-pad; uint16_t *buffer; if (buf) buffer = malloc(2*n_w); for (i = 0; i &lt; n_h; i++) { for (j = 0; j &lt; n_w; j++) { x = (int)(j*xrat); y = (int)(i*yrat); xdiff = (xrat*j)-x; ydiff = (yrat*i)-y; index = y*o_w+x; uint16_t container = 0; container |= (int)(round(getelm(b))) &lt;&lt; 11; container |= (int)(round(getelm(g))) &lt;&lt; 5; container |= (int)round(getelm(r)); if (buf) *(buffer+j) = container; else fwrite(&amp;container, 1, 2, dest); } if (buf) fwrite(buffer, 1, 2*n_w, dest); fwrite(&amp;pad, 1, pad, dest); } </code></pre> <p>My 24-bit version of this code (where the only difference is that the container is not used and instead 3 8-bit integers hold the RGB values) works beautifully.</p> <p>This code, however, gives weird results. Look at the image below:<img src="https://i.stack.imgur.com/Bk0Su.png" alt="Original image"></p> <p>When I resize this, it gives me this back: <img src="https://i.stack.imgur.com/XQVXy.png" alt="Resized image"></p> <p>I can't see why this would be happening, especially when it works for 24-bit bitmaps, and also that some other resizing algorithms (Nearest Neighbour for example) work with 16-bit in the same way that this should.</p> <p>EDIT: I don't think it's an overflow problem, because adding the following code gives no output when run:</p> <pre><code>if (MAX((int)(getelm(b)), 31) &gt; 31) printf("blue overflow: %.10f\n", (getelm(b))); if (MAX((int)(getelm(g)), 63) &gt; 63) printf("green overflow: %.10f\n", (getelm(g))); if (MAX((int)(getelm(r)), 31) &gt; 31) printf("red overflow: %.10f\n", (getelm(r))); </code></pre> <p>EDIT 2: I don't think it's an underflow problem either, this does nothing:</p> <pre><code>if ((getelm(b)) &lt; 0 || (getelm(g)) &lt; 0 || (getelm(r)) &lt; 0) printf("Underflow\n"); </code></pre>
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload