home *** CD-ROM | disk | FTP | other *** search
/ APDL Public Domain 1 / APDL_PD1A.iso / graphics / conversion / makepcx / source / c / pcxcli < prev    next >
Encoding:
Text File  |  1991-12-08  |  9.7 KB  |  381 lines

  1. /*******************************************************************************
  2.  
  3.     pcxCLI.c
  4.  
  5.     (c) Daniel Pead 1991
  6.  
  7.     $Header$
  8.  
  9.     Command line interface to MakePCX - Link with o.makepcx
  10.     
  11.     Converts RISC-OS Sprites into Zsoft PCX V5 files.
  12.  
  13.     Requires a GETOPT function such as GNU getopt.
  14.  
  15.     Syntax:
  16.  
  17.         makepcx [-s <name | n | *> ]  [-p <palette> | -d <palette> ]
  18.                 [-o <path|name>]
  19.                 <spritefile>
  20.  
  21.             -s <name>        : Process only sprite called "name" from file
  22.             -s <n>            : Process only <n>th sprite from file (default 1)
  23.             -s *            : Process all sprites in file
  24.             -d <palette>    : Set default palette, where palette is:
  25.                                 1            : BBC TTL rgb
  26.                                 2              : RISC_OS Desktop (default)
  27.                                 <file>        : Read from palette file
  28.                               Only affects sprites without a palette.
  29.             -p <palette>    : Set palette for all sprites.
  30.             -o <path>        : Set output file for single sprite conversions
  31.                               or output path for multiple sprites.  
  32.             <spritefile>    : Source sprite file
  33.         
  34.     This software may be freely distributed
  35.  
  36. $Log$
  37.  
  38. *******************************************************************************/
  39.  
  40.  
  41. #include <stdio.h>
  42. #include <stdlib.h>
  43. #include <stddef.h>
  44. #include <string.h>
  45. #include <ctype.h>
  46.  
  47. #include <errno.h>
  48. #include <sprite.h> 
  49. #include <kernel.h>
  50. #include <swis.h>
  51. #include <getopt.h>
  52.  
  53. #include "h.makepcx"
  54.  
  55. /*******************************************************************************
  56.  
  57.     Syntax message
  58.  
  59. *******************************************************************************/
  60.  
  61. void syntax(void)
  62. {
  63.     puts ( 
  64.         "\nConverts RISC-OS Sprites into Zsoft PCX V5 files.\n\n"
  65.         "Syntax:\n\n"
  66.         "   makepcx [-s <name | n | *> ]  [-p <palette> | -d <palette> ]\n"
  67.         "           [-o <path|name>]\n"
  68.         "           <spritefile>\n\n"
  69.         "       -s <name>       : Process only sprite called <name> from file\n"
  70.         "       -s <n>          : Process only <n>th sprite from file (default 1)\n"
  71.         "       -s *            : Process all sprites in file\n"
  72.         "       -d <palette>    : Set default palette, where palette is:\n"
  73.         "                           1           : BBC TTL rgb\n"
  74.         "                           2           : RISC_OS Desktop (default)\n"
  75.         "                           <file>      : Read from palette file\n"
  76.         "                         Only affects sprites without a palette.\n"
  77.         "       -p <palette>    : Set palette for all sprites.\n"
  78.         "       -o <path>       : Set output file for single sprite conversions\n"
  79.         "                         or output path for multiple sprites.  \n"
  80.         "       <spritefile>    : Source sprite file\n"
  81.     );
  82. }
  83.  
  84. /*******************************************************************************
  85.  
  86.     Main function - CLI interface
  87.  
  88. *******************************************************************************/
  89.  
  90. int main(int argc, char * argv[])
  91. {
  92.     char pcxpath[128];        /* Pathname for writing PCX file         */
  93.     char * out_name_start;    /* Point to insert image name in above     */
  94.     char * sp_file_name;    /* Name of sprite file                    */
  95.     int pcxpathlen;            /* Length of output path name            */
  96.     FILE * pcxfile;            /* Output file handle                    */
  97.  
  98.     int ftype;                /* File type as returned by ftype()        */
  99.     
  100.     char sprite_name[13];    /* Sprite name to convert                       */
  101.     int sprite_number;        /* >0 : sprite number, =0 : use name <0 : all */
  102.     
  103.     int sp_area_len;        /* Length of sprite area required         */
  104.     sprite_area * sp_area_p;/* Pointer to sprite area                */
  105.     sprite_ptr sp_p;        /* Pointer to sprite                    */
  106.  
  107.  
  108.     os_error * oserr_p;        /* Error returned by OS call            */
  109.     
  110.     char opt;                /* CLI option letter                    */
  111.     int count;                /* Number of sprites to translate        */
  112.  
  113.     /* Defaults */
  114.     
  115.     pcxpathlen = 0;    
  116.     sprite_number = 1; /* Default - convert first sprite in file */
  117.  
  118.     /*************************************************************************/
  119.     /* Get option arguments                                                  */
  120.     /*************************************************************************/
  121.     
  122.     optind = 0;
  123.     
  124.     while ( (opt = getopt ( argc, argv, "s:S:d:D:o:O:" ) ) != (char) EOF )
  125.      {
  126.          switch ( tolower(opt) )
  127.          {
  128.              case 's' :  /* -s : Selects which sprite(s) from file to convert */
  129.  
  130.                         if ( strisnum(optarg) )
  131.                          {
  132.                              /* -s <n> : Convert <n>th sprite in file */
  133.  
  134.                             if ( (sprite_number = atoi ( optarg ))<=0 )
  135.                                 do_error("Sprite number must be >0\n",0);
  136.  
  137.                         }
  138.                         else
  139.  
  140.                             if ( *optarg == '*' )
  141.                             {
  142.                                 /* -s * : Convert all sprites */
  143.                                 
  144.                                 sprite_number = -1;
  145.                             }
  146.                             else
  147.                             {
  148.                                 /* -s <name> : Convert named sprite */
  149.                                 
  150.                                 strncpy ( sprite_name, optarg, 12 );
  151.                                 sprite_number = 0;
  152.                             }
  153.                         break;
  154.  
  155.  
  156.             /* -p <palette> and -d <palette> */
  157.                                     
  158.             case 'p' :    force_pal = TRUE;
  159.                         /* vvv fall through! vvv */
  160.                         
  161.             case 'd' :    switch ( *optarg )
  162.                         {
  163.                             case '1' :    /* -d 1 : BBC palette (TTL RGB) */
  164.                                         default_pal_type = 0;
  165.                                         break;
  166.                                         
  167.                             case '2' :    /* -d 2 : RiscOS Desktop palette */
  168.                                         default_pal_type = 1;
  169.                                         break;
  170.                                         
  171.                             default :    /* -d <file> : Not yet supported */
  172.                                         do_error ( "Opt -%c <file> coming RSN\n",opt);
  173.                                         /*
  174.                                         default_pal_type = 3;
  175.                                         if (!load_default_palette(optarg))
  176.                                             do_error (
  177.                                                 "Can't load palette \"%s\"/n",
  178.                                                 optarg
  179.                                             ); */
  180.                                         break;
  181.                         }
  182.                         break;
  183.  
  184.             case 'o' :    /* -o <name> : Set output filename/pathname */
  185.                         strncpy ( pcxpath, optarg, 128 );
  186.                         pcxpathlen = strlen(pcxpath);
  187.                         break;
  188.  
  189.             default:    /* Error - give syntax message */
  190.                         syntax();
  191.                         exit(0);
  192.         }
  193.     }
  194.  
  195.     /*************************************************************************/
  196.     /* Decide on path name for output PCX file(s)                              */
  197.     /*************************************************************************/
  198.     
  199.     if (!pcxpathlen)
  200.     {
  201.         /* Default path name */
  202.         strcpy ( pcxpath, "pcx." );
  203.         pcxpathlen = 4;
  204.     }
  205.  
  206.     /* Pointer to where sprite name is inserted */
  207.  
  208.     out_name_start = &pcxpath[pcxpathlen];
  209.     
  210.     /* Is it a path or full file name ? */
  211.  
  212.     if ( pcxpath[pcxpathlen-1] == '.' )
  213.     {
  214.         /* Remove '.' for now */
  215.         pcxpath[--pcxpathlen] = 0;
  216.         --out_name_start;
  217.     }
  218.     else
  219.     {
  220.         if ( sprite_number >= 0 )
  221.         {
  222.             /* It's a file name - override sprite name */
  223.             out_name_start = NULL;
  224.         }
  225.         /* Otherwise - it's a path name */
  226.     }
  227.  
  228.     if ( (127 - pcxpathlen)<14 ) do_error ( "-o path name too long!\n",0);
  229.     
  230.     if ( out_name_start )
  231.     {
  232.         /* Check for and, if not there, create output directory */
  233.  
  234.         ftype = finfo(pcxpath, NULL);
  235.         if ( ftype != FINFO_DIR )
  236.             if (ftype != FINFO_ERR || mkdir(pcxpath) )
  237.                 do_error ( "Can't create the directory %s\n", (int) pcxpath );
  238.  
  239.         /* Now append the '.' */
  240.  
  241.         strncat ( pcxpath, ".", 127 );
  242.         pcxpathlen++;
  243.         out_name_start++;
  244.     }
  245.  
  246.  
  247.     /*************************************************************************/
  248.     /* Load in input sprite file                                             */
  249.     /*************************************************************************/
  250.  
  251.     /* Check that user has supplied an input file name! */
  252.     
  253.     if ( optind >= argc )
  254.     {
  255.         syntax();
  256.         exit(0);
  257.     }
  258.     
  259.     sp_file_name = argv[optind];
  260.     
  261. #ifdef DEBUG
  262.     printf ( "Loading %s\n", sp_file_name );
  263. #endif
  264.  
  265.     /* Get file type & length */
  266.     
  267.     ftype = finfo ( sp_file_name, &sp_area_len );    
  268.  
  269.     if (ftype!=0xFF9)
  270.         do_error("\"%s\" not the name of a sprite file.\n",(int) sp_file_name);
  271.  
  272.     /* Allocate memory for sprite area & initialise */
  273.  
  274.     sp_area_len += 4;    /* First word of sprite area not included in file */ 
  275.     
  276.     sp_area_p = (sprite_area *) malloc ( sp_area_len );
  277.  
  278.     if (!sp_area_p)
  279.         do_error("No room for sprite in memory (need %d bytes)\n",sp_area_len);
  280.     
  281.     sprite_area_initialise ( sp_area_p, sp_area_len );
  282.  
  283. #ifdef DEBUG
  284.     printf ( "Loading sprites %d\n", sp_file_name );
  285. #endif
  286.  
  287.     /* Load in sprite file */
  288.     
  289.     if ( oserr_p = sprite_area_load ( sp_area_p, sp_file_name ) )
  290.         do_os_error(oserr_p);    
  291.  
  292.  
  293.     /*************************************************************************/
  294.     /* Locate sprite(s) to convert                                              */
  295.     /*************************************************************************/
  296.         
  297.     count = 1;
  298.     
  299.     if (sprite_number < 0 )
  300.     {
  301.         /* All sprites in file */
  302.         
  303.         sp_p = sprite_find ( sp_area_p, 1, NULL, NULL );
  304.         if ( !sp_p ) do_error ("Empty sprite file!\n",0);
  305.         count = sp_area_p->number;
  306.     }
  307.     else
  308.     {
  309.         /* Find sprite by name or number */
  310.         sp_p = sprite_find ( sp_area_p, sprite_number, sprite_name, NULL );
  311.  
  312.         if ( !sp_p )
  313.         {
  314.             if (sprite_number > 0 )
  315.                 do_error ( "Required sprite (#%d) not in file\n", sprite_number);
  316.             else
  317.                 do_error ( "Required sprite (%s) not in file\n",(int)sprite_name);
  318.         }
  319.     }
  320.  
  321.     /*************************************************************************/
  322.     /* Now convert sprites to PCX format                                     */
  323.     /*************************************************************************/
  324.     
  325.     while ( count-- )
  326.     {
  327.         /* Set o/p file name */
  328.         
  329.         if (out_name_start)
  330.             sprintf ( out_name_start, "%-12s", sp_h(sp_p).name );
  331.  
  332. #ifdef DEBUG
  333.         printf ( "Converting %-12s to %s\n",sp_h(sp_p).name, pcxpath );
  334. #endif
  335.  
  336.         /* Open o/p file */
  337.  
  338.         if ( ! (pcxfile = fopen ( pcxpath , "wb" ) ) )
  339.             do_error("Can't open output file %s\n",(int) pcxpath); 
  340.  
  341.         /* Do the conversion */
  342.         
  343.         make_pcx ( sp_area_p, sp_p, pcxfile );
  344.  
  345.         /* Close file & set type */
  346.         
  347.         fclose ( pcxfile );
  348.         settype ( pcxpath, PCX_TYPE );     
  349.  
  350.         /* Get pointer to next sprite */
  351.         
  352.         sp_p = (sprite_ptr) ( ((int)sp_p) + sp_h(sp_p).next );
  353.     }
  354.     return 0;
  355. }
  356.  
  357.  
  358. /*******************************************************************************
  359.  
  360.     Error actions for RISC-OS, CLIB and program errors respectively
  361.  
  362. *******************************************************************************/
  363.  
  364. void do_os_error(os_error * oserr)
  365. {
  366.     fprintf ( stderr, "OS Error %x : %s\n", oserr->errnum, oserr->errmess );
  367.     exit ( oserr->errnum );
  368. }
  369.  
  370. void do_c_error( int c_err )
  371. {
  372.     fprintf ( stderr, "CLIB Error %x : %s\n", c_err, strerror(c_err) );
  373.     exit ( c_err );
  374. }
  375.  
  376. void do_error ( char * string, int param )
  377. {
  378.     fprintf ( stderr, string, param );
  379.     exit ( 0 );
  380. }
  381.