V22.0201.002, Machine Organization I, Professor Yap
Fall 1997

NOTES ON PCX FILES

  
0.  WHY PCX files?  Because they are a widely available file format
	and rather simple.  You may want to use them for introducing
	nice graphic images into your games.

	The official name of the PCX format is ``PC Paintbrush file Format''.

1.  An example of using PCX files is the game "Space Jam".  We will
	be using this game to illustrate what we say.

	--The Space Jam program is in two modules: a main module called
		game.asm, with graphics routines in graphics.asm.
	--The standard memory model used is COMPACT, which supports
		one code segment and multiple data segments.  In this
		case, only two data segments are used.
	--Images are stored in pcx format.
	--However, these files are sometimes given the .dat extension.
		As far as I know, .dat is not a standard name.
		The .dat and .pcx files with the same name
		are apparently identical.
	--The game uses video mode 13h, which has resolution 320x200,
		and has a color palette of 256 out of 256K (=64^3)
		colors.
	--There is a ``double_buffer'' that is 64000 bytes in size.

2.  You can learn a lot about pcx files by understanding
	the routine pcx_load (in graphics module).
	Basically the pcx file format has three parts:

	PART 1:
		The first 128 bytes form the header.  See details below.

	PART 3:
		The last 769=1+(3x256) bytes defines the color
		palette.  The bytes are

		ID,R1,G1,B1,R2,G2,B2,R3,...
		
		where ID is a special identifier byte
		and (Ri,Gi,Bi) is the RGB values for
		the $i$th palette register.

		See the routine update_color_register (in graphics module)
		for how this can be used.  For some reason,
		each color component is right-shifted by 2 in this
		routine.  This may have to do with the color
		depth of the particular .pcx images.

	PART 2:
		The main data is stored in this part.
		Pcx_load assumes that this part represent a 320x200 screen,
		but that is not true in general.
		NOTE it is possible for this part NOT to have any
		compression schemes!  (Then each pixel is stored literally).
		But if it is compressed, then the method used is
			RUN-LENGTH ENCODING (RLE). 
		Here is a description of the PCX version of RLE:

		The pixels are grouped as
		(a) a single pixel, or as
		(b) a consecutive group of similar valued pixels.
		Each byte value N that is read is treated as follows:
			(1) if the byte value is less than 192d (=0C0h)
				then it represents a single pixel with
				palette index N. 
			(2) if the byte value is greater than or equal to 192d,
				then it is the number of pixels whose common
				palette index is given by the next byte.

	NOTE: you may want to write a slightly more general version
	of PCX_LOAD which does not assume the screen size is 320x200.

3. Other useful routines in the graphics module:
	show_double_buffer
		-- display the contents of the double_buffer
	set_palette_register
		-- set the color of a particular palette register
	get_palette_register
		-- get the color of a particular palette register
	update_color_register
		-- set the colors of all the palette registers

4. More details about PCX format, taken from p.403,
	``Graphics File Formats'', by C. Wayne Brown
	and Barry J. Shepherd, Manning Pub. Co., Greenwich, CT (1995).

	HEADER:
		Byte#	   DATA		Details
		=====	   ====		=======
		1	signature	Hex A0
		2	version		Version 2.5, 2.8, 3.0 and greater, etc
		3	compression	1=run-length
		4	bits/pixel	per color plane
		5-6	Xmin		Upper left corner
		7-8	Ymin		upper left corner
		9-10	Xmax		Lower right corner
		11-12	Ymax		Lower right corner
		13-14	hor.resolution	
		15-16	ver.resolution	
		17-74	palette
		65	reserved
		66	no.of color planes
		67-68	bytes/line	buffer space needed for decoding
		69-70	palette type	1=grayscale, 2=color
		71-128	filler(not used)

	Image Data:
		Each scan line is encoded separately
		(run-lengths do not cross scan line boundaries).

	Palette (769 bytes):
		Byte 1 is the signature (=0Ch)
		Bytes 2,3,4 = RGB for palette index 1
		Bytes 5,6,7 = RGB for palette index 2
		etc
		
	PCX run-length scheme:
		the first 2 bits of each byte is used to distinguish length
		values from data values.  If a data value already has its
		first 2 bits set, then a length value must be inserted
		in front of the data (regardless of whether there is
		any repetition).  ALGORITHM:

		REPEAT:
		   Val = next byte in compressed data stream
		   IF Val < 192, 
		      THEN
			output Val (as literal value)
		      ELSE
			Count = Val-192
				(this strip off the high order 2 bits)
			Color  = next byte in stream
				output Color, Count number of times. 
		UNTIL the stream is processed. 

5. How to view, create and manipulate PCX files.

	Most graphic image viewers will support pcx formats.
		For example, MICROSOFT PHOTO EDITOR can used to
		read and view pcx formats.
		Another well-known program is XV (unix platform only?).
		In the following, I will illustrate using MS Phote Editor.
	If you get access to any one of these software, you
		can also create and manipulate PCX files.
	Two simple way to create PCX files are:
		(a) by converting from another file in some
			other format.  E.g., you may have some
			.GIF files that you wish to convert to .PCX.
			Any of these software should be able to do this
			conversion (first you read the gif file, then
			you save it in the pcx format!)
		(b) by scanning in a hard copy image (which you
			may draw or paint yourself, for instance).
	To create files that the PCX_LOAD routine can decode
		properly, you need to make sure that the image is

		(a) 320x200 pixels in size
		(b) uses 256 color palette
		(c) uses run-length encoding

	IN MS Photo Editor, you can modify (a) by using the
		resize command.  You should also take care to
		set (b), and when you save your file in the
		pcx format, make sure you choose the RLE
		encoding (default is no encoding).
		You can cut and paste images, do various
		image transformation effects, etc.
	
6. Exercise: rewrite pcx_load to load any pcx image into
	a 64000 size buffer.  However, you only assume that
	the image has 320 pixels per row (but the number of
	rows may be more or less than 200).  If more than
	200 rows, you truncate at 200.  If less than 200 rows,
	you fill it up with 0.  You should read the header
	of the pcx file to verify that it has 320 pixels per
	row (else error).  Also use the header to find out
	how rows of pixels it actually has.
	


GO TO THE TOP