about summary refs log tree commit diff
path: root/converter/pgm/fstopgm.c
diff options
context:
space:
mode:
authorgiraffedata <giraffedata@9d0c8265-081b-0410-96cb-a4ca84ce46f8>2006-08-19 03:12:28 +0000
committergiraffedata <giraffedata@9d0c8265-081b-0410-96cb-a4ca84ce46f8>2006-08-19 03:12:28 +0000
commit1fd361a1ea06e44286c213ca1f814f49306fdc43 (patch)
tree64c8c96cf54d8718847339a403e5e67b922e8c3f /converter/pgm/fstopgm.c
downloadnetpbm-mirror-1fd361a1ea06e44286c213ca1f814f49306fdc43.tar.gz
netpbm-mirror-1fd361a1ea06e44286c213ca1f814f49306fdc43.tar.xz
netpbm-mirror-1fd361a1ea06e44286c213ca1f814f49306fdc43.zip
Create Subversion repository
git-svn-id: http://svn.code.sf.net/p/netpbm/code/trunk@1 9d0c8265-081b-0410-96cb-a4ca84ce46f8
Diffstat (limited to 'converter/pgm/fstopgm.c')
-rw-r--r--converter/pgm/fstopgm.c138
1 files changed, 138 insertions, 0 deletions
diff --git a/converter/pgm/fstopgm.c b/converter/pgm/fstopgm.c
new file mode 100644
index 00000000..2c636f41
--- /dev/null
+++ b/converter/pgm/fstopgm.c
@@ -0,0 +1,138 @@
+/* fstopgm.c - read a Usenix FaceSaver(tm) file and produce a portable graymap
+**
+** Copyright (C) 1989 by Jef Poskanzer.
+**
+** Permission to use, copy, modify, and distribute this software and its
+** documentation for any purpose and without fee is hereby granted, provided
+** that the above copyright notice appear in all copies and that both that
+** copyright notice and this permission notice appear in supporting
+** documentation.  This software is provided "as is" without express or
+** implied warranty.
+*/
+
+#include <string.h>
+
+#include "pgm.h"
+
+static int gethexit ARGS(( FILE* ifp ));
+
+int
+main( argc, argv )
+int argc;
+char *argv[];
+    {
+    FILE *ifp;
+    register gray **grays, *gP;
+    int argn, row;
+    register int col;
+    int maxval;
+    int rows = 0, cols = 0, depth = 0, xrows = 0, xcols = 0, xdepth = 0;
+#define STRSIZE 1000
+    char buf[STRSIZE], firstname[STRSIZE], lastname[STRSIZE], email[STRSIZE];
+
+
+    pgm_init( &argc, argv );
+
+    argn = 1;
+
+    if ( argn < argc )
+	{
+	ifp = pm_openr( argv[argn] );
+	argn++;
+	}
+    else
+	ifp = stdin;
+
+    if ( argn != argc )
+	pm_usage( "[fsfile]" );
+
+    /* Read the FaceSaver(tm) header. */
+    for ( ; ; )
+	{
+	if ( fgets( buf, STRSIZE, ifp ) == (char *) 0 )
+	    pm_error( "error reading header" );
+
+	/* Blank line ends header. */
+	if ( strlen( buf ) == 1 )
+	    break;
+
+	if ( sscanf( buf, "FirstName: %[^\n]", firstname ) == 1 )
+	    ;
+	else if ( sscanf( buf, "LastName: %[^\n]", lastname ) == 1 )
+	    ;
+	else if ( sscanf( buf, "E-mail: %[^\n]", email ) == 1 )
+	    ;
+	else if ( sscanf( buf, "PicData: %d %d %d\n",
+			  &cols, &rows, &depth ) == 3 )
+	    {
+	    if ( depth != 8 )
+		pm_error(
+		    "can't handle 'PicData' depth other than 8" );
+	    }
+	else if ( sscanf( buf, "Image: %d %d %d\n",
+			  &xcols, &xrows, &xdepth ) == 3 )
+	    {
+	    if ( xdepth != 8 )
+		pm_error(
+		    "can't handle 'Image' depth other than 8" );
+	    }
+	}
+    if ( cols <= 0 || rows <= 0 )
+	pm_error( "invalid header" );
+    maxval = pm_bitstomaxval( depth );
+    if ( maxval > PGM_OVERALLMAXVAL )
+	pm_error( "depth %d is too large.  Our maximum is %d",
+              maxval, PGM_OVERALLMAXVAL);
+    if ( xcols != 0 && xrows != 0 && ( xcols != cols || xrows != rows ) )
+	{
+	float rowratio, colratio;
+
+	rowratio = (float) xrows / (float) rows;
+	colratio = (float) xcols / (float) cols;
+	pm_message(
+	    "warning, non-square pixels; to fix do a 'pamscale -%cscale %g'",
+	    rowratio > colratio ? 'y' : 'x',
+	    rowratio > colratio ? rowratio / colratio : colratio / rowratio );
+	}
+
+    /* Now read the hex bits. */
+    grays = pgm_allocarray( cols, rows );
+    for ( row = rows - 1; row >= 0; row--)
+	{
+	for ( col = 0, gP = grays[row]; col < cols; col++, gP++ )
+	    {
+	    *gP = gethexit( ifp ) << 4;
+	    *gP += gethexit( ifp );
+	    }
+	}
+    pm_close( ifp );
+
+    /* And write out the graymap. */
+    pgm_writepgm( stdout, grays, cols, rows, (gray) maxval, 0 );
+    pm_close( stdout );
+
+    exit( 0 );
+    }
+
+static int
+gethexit( ifp )
+FILE *ifp;
+    {
+    register int i;
+    register char c;
+
+    for ( ; ; )
+	{
+	i = getc( ifp );
+	if ( i == EOF )
+	    pm_error( "EOF / read error" );
+	c = (char) i;
+	if ( c >= '0' && c <= '9' )
+	    return c - '0';
+	else if ( c >= 'A' && c <= 'F' )
+	    return c - 'A' + 10;
+	else if ( c >= 'a' && c <= 'f' )
+	    return c - 'a' + 10;
+	/* Else ignore - whitespace. */
+	}
+    }