0

I am working now since 2 days on this code and really don't find the mistake. My guess is that something with the fseek is wrong, but I can't manage to resolve it.

The output image (large.bmp) has at least the same color as the input image (small.bmp) but the white box in the middle is somewhat different.

When I try to compare my outfiles header with the staff solution the height seems the problem, it is different:

22 LONG biHeight 0000000c (argv[1]) fffffff4 (argv[2])

Can somebody give me a hint what may be the problem? Thanks

Here is the relevant code:

// updating header info
BITMAPFILEHEADER bf;
BITMAPINFOHEADER bi;

// read infile's BITMAPFILEHEADER
fread(&bf, sizeof(BITMAPFILEHEADER), 1, inptr);

// read infile's BITMAPINFOHEADER
fread(&bi, sizeof(BITMAPINFOHEADER), 1, inptr);

// ensure infile is (likely) a 24-bit uncompressed BMP 4.0
if (bf.bfType != 0x4d42 || bf.bfOffBits != 54 || bi.biSize != 40 || 
    bi.biBitCount != 24 || bi.biCompression != 0)
{
    fclose(outptr);
    fclose(inptr);
    fprintf(stderr, "Unsupported file format.\n");
    return 4;
}

// determine padding for scanlines
int padding = (4 - (bi.biWidth * sizeof(RGBTRIPLE)) % 4) % 4;

//updating header info
int biWidthInput = bi.biWidth;
int biHeightInput = abs(bi.biHeight);
bi.biWidth = bi.biWidth*n;
bi.biHeight = abs(bi.biHeight)*n;
int padding_new = (4 - (bi.biWidth * sizeof(RGBTRIPLE)) % 4) % 4;
bi.biSizeImage = ((sizeof(RGBTRIPLE)*bi.biWidth) + padding_new) * abs(bi.biHeight);
bf.bfSize = bi.biSizeImage + sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER);

// write outfile's BITMAPFILEHEADER
fwrite(&bf, sizeof(BITMAPFILEHEADER), 1, outptr);

// write outfile's BITMAPINFOHEADER
fwrite(&bi, sizeof(BITMAPINFOHEADER), 1, outptr);

//resize horizontally and vertically

for (int i=0; i< abs(biHeightInput); i++) {
    for (int l=0; l<n; l++) {
        for (int k=0; k<biWidthInput; k++) {
            RGBTRIPLE triple;

            // read RGB triple from infile
            fread(&triple, sizeof(RGBTRIPLE), 1, inptr);

            for (int j=0; j<n; j++) {

                // write RGB triple to outfile
                fwrite (&triple, sizeof(RGBTRIPLE), 1, outptr);
            }

        }
         // skip over padding, if any

        fseek(inptr, padding, SEEK_CUR);

        // then add it back (to demonstrate how)
        for (int m = 0; m<padding_new; m++) {
            fputc(0x00, outptr);
        }
    }

}

// close infile
fclose(inptr);

// close outfile
fclose(outptr);

// success
return 0;

}

0

2 Answers 2

1

While the logical image height is the absolute value, you need to preserve the sign of the height field when resizing, as it describes the direction of the rows (top-down or bottom-up). The example image has a negative height (meaning it's stored upside down), and your resized image also should be that way.

So remove the abs from bi.biHeight = abs(bi.biHeight)*n;

And you quickly run out of input, too. You might want to fseek backwards to re-read the current line multiple times (n times per input line), or store the current line in memory to write it n times.

0

Thanks you so much. Everything works fine now. You saved me a lot of time wondering what the error may be. I am really grateful for that!

Not the answer you're looking for? Browse other questions tagged .