Ok, so it looks like some of you have either started or finished the prevous step.
Let me know if there are any things you'd like to explore further or if you'd like to skip something in favor of something else. feel free to ask questions or just join the discussion in any way you want.
Anyhow, what I have in mind for today's lesson is to talk about what's behind the pixels we see on our screen.
So, as a first step, start octave.
Since we will be working with images, we need to be able to find files in our computers...since images are files, after all. If you're familiar with DOS or the linux shell, just scroll past this section.
when in octave, type
- Code: Select all
pwd
This command will print your working directory. Files in your working directory can be accessed directly, without needing a full path specified in front of the file name. This means that instead of having to type '/users/daniel/pictures/apedogs/ball.png' I could type only 'ball.png'. You can change your working directory using "cd" as you would in DOS.
To show the contents of the current directory use "dir" or "ls" (equivalent). "cd .." takes you to the parent directory. "cd dir_name" takes you into the directory called "dir_name" if it shows up in the list.
one last thing about directories, no matter which directory you're in, octave can always find the files containing its functions (like sin, that we used last time). This is because octave has a list of places where it always looks. This list can be seen by using typing
- Code: Select all
path
. If you will use a directory often, you can add the path to this directory by using the
- Code: Select all
addpath
command. Help on all the commands I've mentioned here can be accessed by typing "help" followed by the name of the command.
phew! That was even boring for me, but I hope you're still with me, because now comes a little bit of fun stuff.
I would like you to save
this image-file in a folder on your computer.
now, using octave, change the current directory to the one where the image is saved. Then type:
- Code: Select all
I=imread('ballgray.png','png');
This uses a built-in command called "imread" which reads an image from a file and outputs data (which we asked to have stored in a variable called "I"). The name of the file is ballgray.png and the format is Portable Network Graphics (png). Specifying the format is not necessary in most cases, but we do it here to help you figure out what to do in case octave doesn't automatically recognize the format some day.
So we read an image, what now? let's take a look at the variable that was created.
- Code: Select all
whos I
this tells us that:
-The name of the variable is I,
-it has a size of 15x14
-it contains 210 bytes
-and it is of class "uint8".
I figure you can guess what most of this means without me telling you, with the exception of the class, so let's talk about that. uint8 means "unsigned 8-bit integer". unsigned means that there is no "sign" ie. no plus or minus. So data in this class can only be positive.
integer means that we only have whole numbers. 1, 3 ,4, 5000 are integers. 3.1415, 1/2 etc are not. Trying to store a number like 9.9 in a variable of the integer class will result in 9 being saved and 0.9 being ignored.
ok, so we have positive integers, what does the 8-bit tell us?
The 8-bit tells us that we have 8 bits (one byte) to represent the numbers. in octave, do
- Code: Select all
14*15
.
210, right? and how many bytes did "whos I" tell us? 210. That means that each pixel in the image contains one byte of data.
but what does it MEAN!? hehe
well, there are 10 types of people in the world. Those who understand the binary system, and those who don't.
but fear not. you will get it soon enough.
in the decimal system 10 means ten.
in binary 10 means two.
in decimal
1111 means one thousand, one hundred, ten and one, in other words: 10⁰ + 10¹ + 10² + 10³
in binary
1111 means simply : 2⁰ + 2¹ + 2² + 2³
so when we're told that there are 8 bits storing each value we can have any value between
00000000
and
11111111
type (or copy) into octave:
- Code: Select all
2^0 + 2^1 + 2^2 + 2^3 + 2^4 + 2^5 + 2^6 + 2^7
in fact, if you simply type
- Code: Select all
I
you'll get the numeric contents of the image printed on your screen.
Can you imagine what the image looks like? Where are the brightest and darkest parts?
What value would a 50% gray have?
let's look at how the computer translates this image to pixel brightness:
- Code: Select all
imshow(I);
imshow is another built in function that displays a matrix as an image.
ok so far? then let's do one last thing.
to invert an image:
- Code: Select all
I_inv=255-I;
imshow(I_inv);
OR, directly:
- Code: Select all
imshow(255-I);
why? because when a pixel in I is white (255) the difference between 255 and 255 will be 0 (black).
when a pixel in I is black (0) the difference between 255 and 0 will be 255 (white). Everything in between will follow the same logic. However, since there are an even number of values from 0 and 255 there is no true 50% gray. If you had a pixel with value of 128, the inverted image would contain 127 and vice-versa.
Optional bonus-quests:
Load a
color-image with imread and do a "whos". Notice any differences? of course you do.
if you create two equal-sized images, you can now experiment with the photoshop layer blending modes by adding, subtracting and multiplying them.
- Code: Select all
I1=imread('firstimage.png');
I2=imread('secondimage.png');
figure(1)
I_added=I1+I2;
imshow(I_added);
figure(2)
I_subtracted=I1-I2;
imshow(I_subtracted);
figure(3)
I_multiplied=I1.*I2; %the "." makes a pixel-by-pixel multiplication.
imshow(I_multiplied);