Homework #3 CMSC 131
Due February 19th, 2003 (was Feb 17) Object-Oriented Programming I
  Spring 2004

 

Picture Processing

This goal of this assignment is to have you write your first program.  As with previous homeworks, you must also submit a time log.  This homework will be graded as follows:

What does it mean to write a program from scratch? You always are building on top of some libraries - whether they are provided by the language designers, your instructor, or some third party. A typical first computer program looks something like this:

public class FirstProgram {
    static public void main(String[] args) {
        System.out.println("Hello world!");
    }
}

This creates a class called "FirstProgram", and it's "main" method prints something to the "console". It relies on the "System" class which is provided by Java. Try using Eclipse based on the skills you developed in the previous homework to load in this class, and compile and run it. Note that Java requires that the filename is the same as the primary class in the file.  So, for this example, when you create the class called "FirstProgram, Eclipse will create a file for you called FirstProgram.java.  Can you modify the text so it displays something different?

Here's another simple program:

public class SecondProgram {
    static public void main(String[] args) {
        Picture image = new Image("image.jpg");
        PictureFrame.show(image);
    }
}

This program loads the image "image.jpg" from the directory the program ran from, and creates a window and displays it. It happens to rely on a class provided for you for this homework. Since that class isn't built in to Java, you'll have to tell Eclipse about it in order to run this program. Let's go through the steps of getting this program to run. We'll start by downloading the picture library code, and running the sample program that comes with it.

This is code to support the viewing and manipulation of pictures.  Get the new code using CVS.  We have distributed the code into each student's CVS repository as a new module called "hw3".  You can check it out by following these steps below.

Installing AutoCVS

If you are using a home computer, you must install one more plugin for Eclipse to manage CVS.  (If you are using the WAM computers, then this has already been done, and you do not have to do this step).

As discussed in class, we are using AutoCVS, a plugin for Ecilpse developed by Bill Pugh and Dave Hovemeyer at UMD for this class.  It extends Eclipse's support for CVS in two ways. 

  1. It automatically updates your workspace with the latest version of your code from the repository whenever you startup Eclipse and commits any changes to the repository whenever you save your file.
  2. It provides a mechanism to submit your code to us by marking a specific version of your code in the repository as the one for us to look at.

To use AutoCVS, you must first install it as follows:

Getting the code

Your CVS repository will be stored on a new set of machines run by the CS department called the "Linux Lab".  You can access your account and password by logging into the http://grades.cs.umd.edu system with your university directory ID and password.  When you log in, click on the "Receive Class Account" link on the yellow bar at the left.  Then, you should immediately change your password by using ssh to log into "linuxlab.csic.umd.edu" (note that you can not use telnet to log into these machines, you must use ssh).  You can change your password by typing "kpasswd".  Once you've done this, you can set up CVS in Eclipse as follows:

Alternatively, if you are having trouble with CVS for some reason, you can manually download and import the code as follows - but note that you need to get CVS working because you will be submitting your project with CVS.
  • Create a new Eclipse project called picture
  • Download and save to disk the file picture-hw3.jar
  • Click on the Pictures project
  • Select File > Import ...
  • Select "Zip file" from the Import dialog window and click Next
  • Click the Browse button and select the picture-hw3.jar file you previously downloaded
  • Make sure the text box after "Into folder" at the bottom says "picture"
  • Click on Finish

Understanding the Picture code

You can now run the code opening the picture project. Select "(default package)" and then PictureDemo.java and run it.  Note that the .jar file itself is also executable and can be run outside of Eclipse.  On Windows or Macintosh, just double-click on it.  On Unix, run 'java -jar picture-hw3.jar'. Let's look at the source code and try to make sense of it.  The main method is repeated here for convenience:

public static void main(String[] args) {
    PictureFrame.show(new RedSquare());
    PictureFrame.show(new RedBlackSquare());

    Picture image = new Image("http://www.cs.umd.edu/~bederson/bederson.gif");
    PictureFrame.show(image);
    PictureFrame.show(new FlipLeftRight(image));

    Picture greenImage = new Green(image);
    Picture flipGreenImage = new FlipLeftRight(greenImage);
    PictureFrame.show(new CombineLeftRight(greenImage, flipGreenImage));
}

The first line calls the show method of the PictureFrame class, and passes in a parameter which is the object created by the call to new RedSquare().  The second line is similar.  By looking at the output of the program, we can guess what is going on.  The show method creates a window containing a picture.  Those pictures are created by the classes RedSquare and RedBlackSquare which we passed in as parameters. The middle group of three lines is similar, but these create a picture from an image file using the Image class.  The Image class creates a picture from an image file sitting on any web server (or local file). It then uses the FlipLeftRight class to make a new image which is a flipped version of the input image. The final group of three lines takes the image that was just loaded and filters it to only show the green colors within the image.  It then creates a flipped version of the green image by using the FlipLeftRight class again.  Finally, it uses one last new class, CombineLeftRight, to combine the two green images (original and flipped images) into one new bigger image and then displays that.

Note that the source code for all of the examples described here are distributed with this assignment.  This includes RedSquare, RedBlackSquare, FlipLeftRight, Green, and CombineLeftRight.  You should study these examples to learn how pictures can be manipulated which should help you write the classes you have been assigned for this homework.

Here is one more thing for you to try.  Change the image that is displayed to be something that is interesting to you. Change the URL in the line that starts with Picture image = new Image to the URL of any image you like (in GIF, JPG, or PNG format). You can find the URL of an image in any webpage in most web browsers by right-clicking on the image and selecting Properties. Note that you can also replace the URL with a filename of an image stored on the computer you are using.

Writing Code

Now, here's the part of your assignment that requires you to write code. You are going to write some programs that manipulate pictures along the lines that you saw above. This may sound tough at first, but actually, it is easier than it sounds because the utility classes you just used provide a lot of support for dealing with pictures. But first, let's learn a bit about pictures and pixels.

A computer picture (sometimes called an image) is stored as a two-dimensional array of "pixels" - which are little bits of color. Computers represent these (and other) colors with a combination of "pure" red, green and blue colors. It turns out that by varying the amount of red, green and blue in any one spot, you can create what appears to the human eye as any of a wide range of colors. In normal pictures, colors are represented with many different possible values of red, green and blue. The smoothly varying levels of these color components allow for realistic-looking images. But, if you restrict the number of values of red, green and blue, you can make the pictures look unusual. If, for example, you turn off all the red and blue colors, you'll be left with a green-looking picture as you just saw.

The array of pixels representing an picture must be "addressable". This means you there must be a way to tell the computer which pixel is where in the picture. Each picture has a width and a height. These correspond to the number of pixels wide and high the picture is. Computers count pixels in rows and columns from the top-left starting at 0. This means that the top-left pixel is in the 0th row (its y value equals 0) and 0th column (its x value equals 0). Column numbers increment by one as you move to the right all the way to the value width-1, and row numbers increment by one as you move down to height-1.

Finally, let's look at how pixels are managed. Each picture is composed of three color components: red, green and blue. In our library, each color component of our pixels are represented by a floating point number in the range 0.0 (meaning black) and 1.0 (meaning bright color).

Now, let's look at the actual classes in the library.  The utility classes you will use are:

You should read the documentation for these classes (and demo classes).

The Picture interface is key as that defines a new picture. It specifies three methods that any picture must implement.  getWidth() and getHeight() specify the dimensions of the picture, and getColor() specifies the color of each pixel defined for the picture, based on its dimensions.  When you create a class that implements the Picture interface, you are promising that you will implement those three methods.  Then, when you pass your picture into, for example, the PictureFrame.show() utility, those three methods will be called to determine the dimensions and contents of the picture.  Thus, your definition of these three methods completely determine the contents of the picture.

Let's look at some of the example.  RedSquare is extremely simple.  It has a fixed dimension, and every pixel is defined to be red.  RedBlackSquare is a little more interesting.  It has some internal variables that specify the picture dimensions as well as the size of the red inner square.  Then, the getColor() method uses the (x, y) values (which specify which pixel is being asked about) to determine whether the pixel should be red or black.  Finally, if you look at FlipLeftRight, you'll see that it has a constructor that stores an input picture, and uses that picture to specify it's own dimensions as well as to generate the new picture (by taking pixels from a different position from the input picture).

Code Style

Part of your grade will be based on your coding style.  You must do your best to follow the coding style techniques we have discussed in class. This includes a number of characteristics of your code including:

Your Assignment

For this homework, you must write four classes.  Each should create a picture by implementing the Picture interface.  You should fill in the shell classes provided for you in picture-hw3.jar.  The classes must work as follows:

For this assignment, you must turn in your code along with a screenshot of your demo program. Make a screenshot the same way you have done in the previous homework and save it a file called "hw3-screenshot.jpg".  Then, import it into your Eclipse project with these steps:

Now, submit your program by right-clicking on your project and select "Submit Project". Note that this option will only appear if you have successfully installed AutoCVS as described above.  If you decide that you would like to make a change after you have submitted your project, you can resubmit as many times as you like.  We will grade the last project submitted before the deadline (Thursday, February 19th at 6pm - originally Feb 17th).

Be sure to include the following information at the beginning of each code file.

/* Name 1
 * Student ID 1
 * Name 2
 * Student ID 2
 * Homework #3
 */

<your code goes here>

Challenge Problem

For an extra challenge, you can use your creativity and create your own picture generation class.  Please note that this challenge problem is optional, and no extra credit will be given for it.  If you do work on this, you should submit your MyPicture class along with the other files associated with this homework?

For this challenge problem, you should build on what we've learned in class and the code you've already written to create your own picture based on an input picture. Your constructor should have the signature:

    public MyPicture(Picture basePicture);

You must also include a short comment that describes what this picture does and how it works.  This comment should appear immediately before the class definition and should be of the form:

/**
 * MyPicture implements a picture that <explain what it does here>.
 * It works by <explain how it works here>.
 */
public void class MyPicture implements Picture {
    // Your code here
}

Be proud and show off your work.  Upload your creative work to the wiki under Homework #3 Gallery.  We'll take a vote in class to pick a favorite, and the winner will win a small prize.