0

My program resizes the image but the colors are wrong. I'm stuck, can you please help me?

/**
 * Copies a BMP piece by piece, just because.
 */

#include <stdio.h>
#include <stdlib.h>

#include "bmp.h"

int main(int argc, char *argv[])
{
    // ensure proper usage
    if (argc != 4)
    {
        fprintf(stderr, "Usage: ./copy n infile outfile\n");
        return 1;
    }

    // remember factor n
    int n = atoi(argv[1]);

    // to check for factors bigger than 100 or smaller than 1
    if (n < 1 || n > 100)
    {
        fprintf(stderr, "Usage: n between 1 and 100\n");
        return 1;
    }

    // remember filenames
    char *infile = argv[2];
    char *outfile = argv[3];

    // open input file 
    FILE *inptr = fopen(infile, "r");
    if (inptr == NULL)
    {
        fprintf(stderr, "Could not open %s.\n", infile);
        return 2;
    }

    // open output file
    FILE *outptr = fopen(outfile, "w");
    if (outptr == NULL)
    {
        fclose(inptr);
        fprintf(stderr, "Could not create %s.\n", outfile);
        return 3;
    }
    // read infile's BITMAPFILEHEADER
    BITMAPFILEHEADER bf;
    fread(&bf, sizeof(BITMAPFILEHEADER), 1, inptr);

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

    // old hight/width
    int oldHeight = abs(bi.biHeight);
    int oldWidth = bi.biWidth;

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

    // 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;
    }

    // change outfile's BITMAPINFOHEADER
    bi.biWidth *= n;
    bi.biHeight *= n;

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

    // change outfile's biSizeImage
    bi.biSizeImage = ((sizeof(RGBTRIPLE) * bi.biWidth) + padding_out) * abs(bi.biHeight);

    // change outfile's BITMAPFILEHEADER
    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);

    // create array for lines
    RGBTRIPLE line[bi.biWidth];

    // iterate over infile's scanlines
    for (int i = 0; i < oldHeight; i++)
    {
        // iterate over pixels in scanline
        for (int j = 0; j < oldWidth; j++)
        {
            // temporary storage
            RGBTRIPLE triple;

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

            // write RGB triple n times to array
            for (int l = 0; l < n; l++)
            {
                line[j + l] = triple;
            }
        }

        // write scanline n times to outfile
        for (int m = 0; m < n; m++)
        {
            fwrite(line, bi.biWidth * 3, 1, outptr);
            for (int o = 0; o < padding_out; o++)
            {
                fputc(0x00, outptr);
            }
        }

        // skip over padding, if any
        fseek(inptr, padding_in, SEEK_CUR);
    }

    // close infile
    fclose(inptr);

    // close outfile
    fclose(outptr);

    // success
    return 0;
}

1 Answer 1

0

There's a problem here: line[j + l] = triple;.

Using an infile width of 3 and a factor of 3: When j is 0, this will populate indexes 0,1,2. When j is 1: indexes 1,2,3. When j is 2: indexes 2,3,4.

BTW a quick way to format code properly: after you paste it, select it (with the mouse) and click the {} icon in the format bar. You can also edit the question and do the same thing.

You must log in to answer this question.

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