CSE 477: Digital Systems Design
(Spring 1999)

Turning Pictures into .bin Files

In lab #3, we gave you a .bin file to load into the memory.  You might want to create your own picture(s) from .gif, .jpeg, or animated .gif formats.  This page tells you how to do such a conversion.

Overview

The two major parts of this conversion process are:
  • Reducing the image to your screen size and available memory
  • Mapping the colors in your original image to the colors supported by your VGA interface.
  • To perform these conversions, we use the intermediate "portable file format" for images.   There are three types of portable file formats, to support color, grayscale, and black/white pictures.  The one you chose to use will depend on the needs of your project.  Here they are:

    ppm -- Portable pixmap file format
    pgm -- Portable graymap file format
    pbm -- Portable bitmap file format
    (pnm -- Portable any file format)  <--- Utilities support all types

    These file formats are convenient to use since there are a bunch of Unix utilities for image manipulation and conversion.  The portable file type "pnm" is not a file type at all but used to label utilities that can run on any of the three file types: ppm, pgm, and pbm.  Here is an overview of the utilities for each type.  I don't know what all of these do, but you can find out by running "man utility" from a Unix command line.

    ppm
    ppm3d         ppmmake       ppmrelief     ppmtomitsu    ppmtosixel
    ppmbrighten   ppmmerge      ppmshift      ppmtopcx      ppmtotga
    ppmchange     ppmmix        ppmspread     ppmtopgm      ppmtouil
    ppmdim        ppmnorm       ppmtoacad     ppmtopi1      ppmtoxpm
    ppmdist       ppmntsc       ppmtobmp      ppmtopict     ppmtoyuv
    ppmdither     ppmpat        ppmtogif      ppmtopj       ppmtoyuvsplit
    ppmflash      ppmquant      ppmtoicr      ppmtopjxl
    ppmforge      ppmquantall   ppmtoilbm     ppmtopuzz
    ppmhist       ppmqvga       ppmtomap      ppmtorgb3

    pgm
    pgmbentley pgmenhance pgmmerge   pgmoil     pgmtofits  pgmtopbm
    pgmcrater  pgmhist    pgmnoise   pgmramp    pgmtofs    pgmtoppm
    pgmedge    pgmkernel  pgmnorm    pgmtexture pgmtolispm

    pbm
    pbmclean   pbmpscale  pbmtoascii pbmtoepson pbmtolj    pbmtopgm   pbmtox10bm
    pbmlife    pbmreduce  pbmtoatk   pbmtog3    pbmtoln03  pbmtopi3   pbmtoxbm
    pbmmake    pbmtext    pbmtobbnbg pbmtogem   pbmtolps   pbmtopk    pbmtoybm
    pbmmask    pbmto10x   pbmtocmuwm pbmtogo    pbmtomacp  pbmtoplot  pbmtozinc
    pbmmerge   pbmto4425  pbmtoepsi  pbmtoicon  pbmtomgr   pbmtoptx   pbmupc

    pnm
    pnmalias   pnmcrop    pnmflip    pnmmargin  pnmpaste   pnmtile    pnmtosgi
    pnmarith   pnmcut     pnmgamma   pnmmerge   pnmrotate  pnmtoddif  pnmtosir
    pnmcat     pnmdepth   pnmhistmap pnmnlfilt  pnmscale   pnmtofits  pnmtotiff
    pnmcomp    pnmenlarge pnmindex   pnmnoraw   pnmshear   pnmtops    pnmtoxwd
    pnmconvol  pnmfile    pnminvert  pnmpad     pnmsmooth  pnmtorast

    NOTE: The above programs are from hobbes.cs.  On orcas, you might have a slightly different set of utilities.  To see what you programs are available on your local machine, you can use a handy feature of the "tcsh" shell.  From an orcas prompt, run "tcsh".  Then type "ppm^D"  (that is ppm followed by a control-d).  The shell will perform file completion based on your path.  This tells you all the executables in your path that begin with the letters "ppm".  You can do this for "pgm", "pbm", and "pnm" as well.

    In addition, you will need "giftoppm" to convert your image into a portable pixmap.  We have written a C-program for "ppmtobin" which converts an ascii ppm file to a binary file supporting a VGA interface with 6 bit color (2 bits per R, G, B).  We have also written a script which extracts images from an animated gif file and tiles them into a single picture story board, like the scared mouse you animate in lab #3.  This script is called "agiftoppm".  Of course, you will want to use "xv" to view these images.

    Note: you will need to get some files and scripts from: /cse/courses/cse477/1999sp/imageconv/  on orcas.

    Step #1 -- Converting image to appropriate size

    Lets say you have the file "bob.gif" file that is 1024x865.  (If you are looking for a .gif file to play with, you could use /cse/courses/cse477/1999sp/imageconv/u2.gif.) You want it to be 128x128.  First you convert it to a ppm file:
            giftoppm bob.gif > bob.ppm

    Now to convert it to 128x128 you type:
       pnmscale -xsize 128 -ysize 128 bob.ppm > bob2.ppm
     

    Step #2 -- Reducing the color map

    Suppose that your original bob.gif file was 24 bit color and used 143 different colors.  You'd like to reduce this to 6 bit color using any of the 64 colors that our 6-bit VGA interface supports.  The utility "ppmquant" allows you to restrict the choice of 24-bit colors to a specific color map.  We have created a file "map.ppm" that represents all 64 supported colors (try running "xv map.ppm").   Then run:
       ppmquant -map map.ppm bob2.ppm > bob3.ppm

    The resulting file is still represented as 24-bit color but is guaranteed to use only the 64 colors that our VGA interface supports.  ppmquant is nice since it tries to be intelligent about color selection.  Do a "man ppmquant" to find out more.
     

    Step #3 -- Creating a .bin file compatible with our VGA interface

    Now you must reduce the 24-bit color file "bob3.ppm", which uses our 64 colors, to our 6-bit color format.  The program "ppmtobin" performs this conversion.  Our 6-bit format actually uses 8 bits, the first two of which are don't cares.  Hence this program converts the 24 bit format:
        RRRRRRRRGGGGGGGGBBBBBBBB
    to the 8-bit format:
        XXRRGGBB

    It does this with a simple switch statement in the C-code.  For more information you can look at "ppmtobin.cc".   This program takes as input an ASCII version of a ppm file (also called a "no raw" format).  Most of the ppm utilities output a raw format since the file sizes are smaller.  The utility "pnmnoraw" converts a raw ppm file to an ascii file.  Hence, to convert "bob3.ppm" to a bin file, you would run:
       pnmnoraw bob3.ppm > bob4.ppm
       ppmtobin bob4.ppm > bob.bin

    The resulting .bin file can be loaded into your xess board's RAM using "xsram".

    Step #4 -- Putting it all together with pipes

    Typing all of the above commands might seem like a pain, but you can use Unix pipes to prevent the need for intermediate files.  For example, you could just type:
       giftoppm bob.gif  | ppmquant -map map.ppm | pnmscale -xsize 64 -ysize 64 | pnmnoraw | ppmtobin > bob.bin

    which performs steps #1-#3 (note that I've swapped steps #1 and #2 here, but that doesn't matter).  Based on this piped command,  we have written a C-script "giftobin" that takes two arguments (the scaled image sizes) and outputs a bin file.  Hence, you could also just write:
       giftobin 64 64 bob.gif > bob.bin
     

    Step #5 -- Creating an animation

    If you would like to create your own animation from an animated gif source, you now have all the tools to do so.  To extract the multiple images from an animated gif, you must give "giftoppm" the argument "-image X" where X is the frame number to remove.  For the scared mouse animated gif in lab three, we wrote the script "agiftoppm" which builds the story board using the ppm tools.  "mouse.gif" contained 58 frames, so we had to be clever to reduce this to exactly 32, which is how much our memory could support with 64x64 pixel frames.  To make your own animations, you must copy "agiftoppm" and modify it accordingly.  For example, you could have a better scared mouse animation if you reduce the image size to 64x32, allowing all 58 frames to be used.  But the script "agiftoppm" would have to change to make sure the last 6 blank frames do the right thing.

    We have put three animations in /cse/courses/cse477/1999sp/imageconv/ for fun.  They are scaredmouse.gif, dove.gif, and secatwalkn.gif.  The first is from your lab #3.  Try running:
        agiftobin scaredmouse.gif
    and then
        xv scaredmouse.ppm
    to see the script in action.