0

is there a way to read image pixels or any data considering the image using FILE fopen in C? I'm not interested in libraries. I tried to read the image data with fgetc but it prints out some numbers which don't make any sense.

EDIT: I know it's supposed to print out numbers but I was expecting numbers that represent each pixels.

EDIT: I'm looking for documentation links that will help me comprehend how jpeg or png formats work and store data.

  • 1
    Yes, there is a way. But it's very complicated without a library. Basically you need to rewrite the code for decoding jpeg and png images which is far from trivial. But anyway what output did you expect when you read image data with `fgetc`. – Jabberwocky Oct 15 '21 at 07:21
  • 1
    What do you expect? Any file is just a bunch of bytes. If you printf these bytes as numbers, they come out as numbers. To interpret these numebrs, you need to know the exact format of the image file. It's time for you to read a lot of documentation... – the busybee Oct 15 '21 at 07:28
  • what kind of image format are you interested in? PBM is easy to parse from C. See https://en.wikipedia.org/wiki/Netpbm – tstanisl Oct 15 '21 at 07:33
  • i have time to read documentations but I don't know where to find them. Can you guys give me a link that will help me comprehend how to achieve this without a library? – Trailblazer17 Oct 15 '21 at 07:34
  • i was expecting colors in binary line by line – Trailblazer17 Oct 15 '21 at 07:35
  • Please [edit] your question and show us _how_ you want the colors in binary printed line by line. Do you want RGB values, in decimal? Do you want other image properties like size, color depth, color table on indexed data, ...? What formats do you want to read? There are so many. – the busybee Oct 15 '21 at 08:10

4 Answers4

1

If you really want to be able to read and write images, simply, via a FILE pointer, you'll want to look at a file format called a .ppm. (Portable Pixel Map.) This assumes, of course, that you can convert your image files to a .ppm, but that is easily achievable with the imagemagick command-line tool. You can use imagemagick to convert the .ppms you write to any output type you like.

The format is insanely simple:

  • Starts with the two character (the "magic number") "P6"
  • The P6 is followed by a whitespace, then the width (in ascii) of the image.
  • The width is followed by a whitespace, then the height (in ascii) of the image.
  • The last bit of the header is the "maximum value" of an entry. Just use 255. Follow this with a whitespace.
  • After that, you just write, in binary, RGB values. One unsigned char per channel.

Example:

P6 128 128 255
[128 * 128 * 3 bytes of data go here, in row major order. The top-left 
 pixel is first, then the pixel to the right of it. When you get to the 
 end of a row, just write the first pixel of the next row. That's all 
 there is. No other header info, no terminators, etc.]

Example:

#include <stdio.h>
void main() {
  FILE * out;
  out = fopen("color_test.ppm", "wb");
  fprintf(out, "P6 256 256 255\n");
  for(int r=0; r<256; r++) {
    for(int b=0; b<256; b++) {
      fputc(r, out);
      fputc(0, out);
      fputc(b, out);
    }
  }
  fclose(out);
}

This generates:

Image with reds in the vertical (0 at top and 255 at bottom) and blues along the bottem, with 0 at the left.

Reading files is similarly easy. You can just pull them into a 3d array of unsigned chars, manipulate them in memory however you like, then write that data back out to another file much as my example does here.

Sniggerfardimungus
  • 11,583
  • 10
  • 52
  • 97
0

I don't quite understand what you want to do, but C language is a low level programming language. Of course, there will be nothing but numbers in memory.

The easiest way to store an image in C is creating a matrix structure and keeping the RGB values. The numbers you mention can be the RGB values ​​of each pixel.

0

You can read images without using libraries, but it's a lot of work.

For example, libjpeg-turbo is probably the most popular library for reading JPEG images:

https://github.com/libjpeg-turbo/libjpeg-turbo

It's around 50,000 lines of C and assembly.

Interestingly, it includes functions to read and write some other formats (these routines are used by the command-line JPEG tools for file format conversion). For example, here's the code used by libjpeg-turbo to load a BMP image:

https://github.com/libjpeg-turbo/libjpeg-turbo/blob/main/rdbmp.c

About 700 lines, though it can only read a subset of BMPs.

jcupitt
  • 10,213
  • 2
  • 23
  • 39
  • What makes it so much hard to read jpeg images? – Trailblazer17 Oct 15 '21 at 09:45
  • JPEG is quite a complicated format -- images are stored as huffman-coded DCT coefficients. More modern formats are more difficult again: JPEG-XL, the successor, needs almost 200,000 lines of C++ to read. – jcupitt Oct 15 '21 at 09:52
  • so then operating systems and browsers have a tool for reading jpeg files right? – Trailblazer17 Oct 15 '21 at 10:09
  • That's right, they mostly use libjpeg-turbo, the project I linked in the answer. It's interesting to read (if a bit complex). – jcupitt Oct 15 '21 at 10:25
0

If your looking on how to read RGB values from a pixel click this and if you are looking for libraries then libjpeg and libpng will help you.