home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
OS/2 Shareware BBS: 19 Printer
/
19-Printer.zip
/
PRPCX2.ZIP
/
PCX.C
< prev
next >
Wrap
Text File
|
1992-06-03
|
4KB
|
117 lines
/*+
Name: pcx.c
Author: Kent J. Quirk
Abstract: This file contains subroutines to read PCX files.
-*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "pcx.h"
/**** p c x _ r e a d _ h e a d e r ****
Abstract: Reads the header of a PCX file.
Parameters: A data storage area for the header, an open file.
Returns: The pointer to the data storage area passed, or NULL if error.
Comments: The file should be opened in binary mode.
****************************/
PCX_HDR *pcx_read_header(PCX_HDR *hdr, FILE *f)
{
fseek(f, 0L, SEEK_SET); /* header is at top of file */
if (fread(hdr, 1, sizeof(PCX_HDR), f) != sizeof(PCX_HDR))
return(NULL);
else
return(hdr);
}
/**** p c x _ p r i n t _ h e a d e r ****
Abstract: Printf's a PCX file header data to a given file.
Parameters: The PCX file header, the file to write the data to.
Returns: Nothing
****************************/
void pcx_print_header(PCX_HDR *hdr, FILE *f)
{
char *t;
if (hdr->pcx_id != 0x0A)
{
fprintf(f, "Not a PCX file.\n");
return;
}
switch (hdr->version) {
case 0: t="2.5"; break;
case 2: t="2.8 with palette info."; break;
case 3: t="2.8 without palette info."; break;
case 5: t="3.0"; break;
default: t="unknown."; break;
}
fprintf(f, "PCX Version %s\n", t);
fprintf(f, "Compression: %s\n",
hdr->encoding==1 ? "Run length" : "Unknown");
fprintf(f, "%d bits per pixel\n", hdr->bpp);
fprintf(f, "Image from (%d, %d) to (%d, %d) pixels.\n",
hdr->upleftx, hdr->uplefty, hdr->lorightx, hdr->lorighty);
fprintf(f, "Created on a device with %d x %d dpi resolution.\n",
hdr->display_xres, hdr->display_yres);
fprintf(f, "The image contains %d image planes.\n", hdr->nplanes);
fprintf(f, "There are %d bytes per line of data after decompression.\n",
hdr->bytesperline);
fprintf(f, "There are %ld total bytes in the image.\n",
((long)hdr->lorighty - (long)hdr->uplefty + 1) *
(long)hdr->bytesperline);
return;
}
/**** p c x _ a l l o c _ l i n e ****
Abstract: Allocates enough space to store a complete scan line from the
current PCX file.
Parameters: The header pointer.
Returns: A pointer to a "big enough" block of allocated space, or
null if not enough space or an error occurred.
****************************/
BYTE *pcx_alloc_line(PCX_HDR *hdr)
{
return(calloc(hdr->nplanes, hdr->bytesperline));
}
/**** p c x _ n e x t _ l i n e ****
Abstract: Reads the next line from the PCX file.
Parameters: Pointer to the header, a pointer to the line area (or NULL
for automatic allocation), and the open data file.
Returns: A pointer to the line area, or NULL if there was a problem.
Comments: To read the first line, call pcx_read_header() first.
This sets the file position to the beginning of the data.
****************************/
BYTE *pcx_next_line(PCX_HDR *hdr, BYTE *line, FILE *f)
{
int c, len;
BYTE *dp;
WORD linesize = hdr->nplanes * hdr->bytesperline;
WORD i;
if (line == NULL)
if ((line = pcx_alloc_line(hdr)) == NULL)
return(line);
dp = line; /* point to data */
for (i=0; i<linesize; )
{
if ((c = fgetc(f)) == EOF)
return(NULL);
if ((c & PCX_COMPRESSED) == PCX_COMPRESSED)
{
len = (c & PCX_MASK);
if ((c = fgetc(f)) == EOF)
return(NULL);
memset(dp, (BYTE)c, len);
dp += len;
i += len;
}
else
{
*dp++ = (BYTE)c;
i++;
}
}
return(line);
}