Image-6 Grayscale

< CS101

In this section, we'll look at the structure of grayscale vs. color images, and some code to play with that difference.

Gray Among The RGB

Answer: the RGB scale is calibrated so that when all three red/green/blue numbers of a pixel are equal, the pixel is a shade of gray. Making all the numbers equal, like red=50 green=50 blue=50 drains any bias towards red, green, or blue. If a pixel were red=50 green=75 blue=50 it would be a bit greenish, but making them all equal, it's not towards any particular hue. This works because the displays and other systems using RGB are calibrated so that the all-equal cases are on the black..gray..white spectrum.

Examples of gray colors in RGB:
red green blue color
50 50 50 dark gray
120 120 120 medium gray
200 200 200 light gray
In fact, the original pure black/white colors fit this all-equal pattern too, just using the values 0 and 255.
0 0 0 pure black
255 255 255 pure white

Red Liberty Example Problem


statue of liberty shown only in the red channel

Here is an image of the Statue of Liberty where all of the data is in the red values, so the whole image looks red (we saw this sort of image in an earlier puzzle solution). The green and blue values are all zero. This image looks quite wrong.

For this example, we'll write code to fix this image by copying the red value over to be used as the green and blue value. So for a pixel, if red is 27, set green and blue to also be 27. What is the code to do that? What will be the visual result of this?

red green blue
65 0 0
53 0 0
100 0 0
19 0 0
... 0 0


image-gray1

Solution code:

  // your code here
  pixel.setGreen(pixel.getRed());
  pixel.setBlue(pixel.getRed());
  // Usually code combines setRed() with getRed(),
  // but this code gets a value from one color
  // and sets it into another color.
  // Visual result: grayscale image, since
  // red/blue/green are made equal for each pixel.

Converting Color To Grayscale


the yellow flowers.jpg image

red green blue
pixel-1 200 50 50
pixel-2 0 75 75
pixel-3 100 250 250

Looking at just red or blue or green in isolation, it's hard to tell which pixel is brightest or darkest in the above table. The average combines and summarizes the three values into one number 0..255. The average shows how bright the pixel is, ignoring hue: 0 = totally dark, 255=totally bright, with intermediate average values corresponding to intermediate brightnesses. More complicated brightness measures are possible, but average is simple and works fine for our purposes.

red green blue average
average = (red + green + blue) / 3
pixel-1 200 50 50 100 (medium bright)
pixel-2 0 75 75 50 (darkest)
pixel-3 100 250 250 200 (brightest)

Code To Compute Pixel Average

avg = (pixel.getRed() + pixel.getGreen() + pixel.getBlue())/3;

Grayscale Conversion Algorithm

For this example, we'll write code to change the flowers.jpg image to grayscale, using the "average" strategy: for each pixel, compute the average of its red/green/blue values. This average number represents the brightness of the pixel 0..255. Then set the red, green, and blue values of the pixel to be that average number. The result is a grayscale version of the original color image. Once its working with flowers.jpg, try it with poppy.jpg or oranges.jpg. (Solution code available below)


image-gray2

Solution code:

  // your code here
  avg = (pixel.getRed() + pixel.getGreen() + pixel.getBlue())/3;
  pixel.setRed(avg);
  pixel.setGreen(avg);
  pixel.setBlue(avg);

Grayscale Summary

> exercises