home *** CD-ROM | disk | FTP | other *** search
/ GEMini Atari / GEMini_Atari_CD-ROM_Walnut_Creek_December_1993.iso / files / graphics / utility / mgif35s / showfl.c < prev    next >
Encoding:
C/C++ Source or Header  |  1991-06-18  |  8.5 KB  |  475 lines

  1. /*
  2.  *    NOTE: mgif can now display flicker files, too. i used t his before
  3.  *    that was added and thought it might be useful standalone...
  4.  */
  5.  
  6. #undef FULL_SCREEN
  7.  
  8. /*
  9.  *    showfl - display a flicker-mode .FL file
  10.  *
  11.  *    file consists of:
  12.  *
  13.  *    offset    size    item
  14.  *    ------    ----    ---------------------------------
  15.  *    0    10    magic (FLICKER91a)
  16.  *    10    256    header
  17.  *        2    w (in pixels, NOT bytes)
  18.  *        2    h (in pixels, NOT bytes)
  19.  *        252    reserved (should be 0 for FLICKER91a)
  20.  *    266    n    pixel data (3 "screens" holding bytes, 8 pixels
  21.  *            per byte). for widths not evenly divisible by 8,
  22.  *            a partial byte is used. so:
  23.  *
  24.  *                if (w % 8)
  25.  *                    nbytes = ((w + 8) / 8);
  26.  *                else
  27.  *                    nbytes = (w / 8);
  28.  *            and
  29.  *
  30.  *                nlines = h;
  31.  *
  32.  *            n will be 3 * nbytes * nlines. for a 320x200 image,
  33.  *            n is 24000 (similar GIF is 25k to 50k bytes).
  34.  */
  35.  
  36. static char *sccsid = "@(#) showfl 1.0 91/6/6 rosenkra\0\0                 ";
  37. char        *myname = "showfl\0\0\0\0\0\0";
  38. char        *version = "showfl 1.0 91/6/6 rosenkra\0\0\0                   ";
  39.  
  40.  
  41. #include <stdio.h>
  42. #include <osbind.h>
  43.  
  44. #define reg_t        register
  45. #define DBG(x)        /*printf x*/
  46.  
  47. #define SCRNSPACE    48256L    /* buffer size for 3 screens (words) */
  48.                 /* leave extra to word-align */
  49.  
  50. /*
  51.  *    globals:
  52.  */
  53. int    _Width;            /* image size */
  54. int        _Hight;
  55. int    _ScrnBuf[SCRNSPACE];    /* enuf for 3 screens... */
  56. int    *_Scrn;            /* -> first screen */
  57. int    montage = 0;
  58.  
  59. /*
  60.  *    local functions
  61.  */
  62. int    read_fl ();
  63. int    showfl ();
  64.  
  65.  
  66. /*------------------------------*/
  67. /*    main            */
  68. /*------------------------------*/
  69. main (argc, argv)
  70. int    argc;
  71. char   *argv[];
  72. {
  73.     reg_t long    ii;
  74.     reg_t int      *pscrn;
  75.     int        count;
  76.  
  77.  
  78.     /*
  79.      *   align to page boundary
  80.      */
  81.     _Scrn = (int *) (((long) _ScrnBuf + 256L) & 0xFFFFFF00L);
  82.  
  83.  
  84.  
  85.     /*
  86.      *   parse args...
  87.      */
  88.     for (argc--, argv++; (argc && **argv == '-'); argc--, argv++)
  89.     {
  90.         switch (*(*argv+1))
  91.         {
  92.         case 'v':
  93.             printf ("%s\n", version);
  94.             exit (0);            /* NO RETURN */
  95.  
  96.         case 'h':
  97.             usage (0);            /* NO RETURN */
  98.  
  99.         case 'm':
  100.             montage++;
  101.             break;
  102.  
  103.         default:
  104.             break;
  105.         }
  106.     }
  107.  
  108.  
  109.  
  110.     /*
  111.      *   make sure we have at least one file...
  112.      */
  113.     if (argc < 1)
  114.         usage (1);                /* NO RETURN */
  115.  
  116.  
  117.  
  118.     if (montage)
  119.     {
  120.         /*
  121.          *   for either 4 320x200 images or 6 200x200 images. first
  122.          *   read them. note changing ptr into screen buffers...
  123.          */
  124.         pscrn = _Scrn;
  125.         count = 0;
  126.         while (argc--)
  127.         {
  128.             printf ("Reading %s\n", *argv);
  129.             if (!read_fl (*argv, pscrn, &_Width, &_Hight))
  130.             {
  131.                 fprintf (stderr, "read_fl failed for %s\n", *argv);
  132.                 exit (1);
  133.             }
  134.             count++;
  135.             argv++;
  136.             if ((_Width <= 320) && (_Width > 200)
  137.             && (_Hight <= 400) && (_Hight > 200))
  138.             {
  139.                 /*
  140.                  *   2 320x400 images...
  141.                  */
  142.                 if (count == 1)
  143.                     pscrn = (int *) ((long) _Scrn + 40L);
  144.                 else
  145.                     break;
  146.             }
  147.             else if ((_Width <= 320) && (_Width > 200)
  148.             && (_Hight <= 200))
  149.             {
  150.                 /*
  151.                  *   4 320x200 images...
  152.                  */
  153.                 if (count == 1)
  154.                     pscrn = (int *) ((long) _Scrn + 40L);
  155.                 else if (count == 2)
  156.                     pscrn = (int *) ((long) _Scrn + 16000L);
  157.                 else if (count == 3)
  158.                     pscrn = (int *) ((long) _Scrn + 16040L);
  159.                 else
  160.                     break;
  161.             }
  162.             else if ((_Width <= 200) && (_Hight <= 200))
  163.             {
  164.                 /*
  165.                  *   6 200x200 images...
  166.                  */
  167.                 if (count == 1)
  168.                     pscrn = (int *) ((long) _Scrn + 25L);
  169.                 else if (count == 2)
  170.                     pscrn = (int *) ((long) _Scrn + 50L);
  171.                 else if (count == 3)
  172.                     pscrn = (int *) ((long) _Scrn + 16000L);
  173.                 else if (count == 4)
  174.                     pscrn = (int *) ((long) _Scrn + 16025L);
  175.                 else if (count == 5)
  176.                     pscrn = (int *) ((long) _Scrn + 16050L);
  177.                 else
  178.                     break;
  179.             }
  180.             else
  181.                 break;
  182.         }
  183.  
  184.  
  185.         /*
  186.          *   show them all...
  187.          */
  188.         showfl (_Scrn);
  189.     }
  190.     else
  191.     {
  192.         /*
  193.          *   loop on files
  194.          */
  195.         while (argc--)
  196.         {
  197.             /*
  198.              *   read file. if ok, display...
  199.              */
  200.             printf ("Reading %s\n", *argv);
  201.             if (read_fl (*argv, _Scrn, &_Width, &_Hight))
  202.                 showfl (_Scrn);
  203.  
  204.  
  205.             /*
  206.              *   clear screen buffer for next image if there
  207.              *   is one...
  208.              */
  209.             if (argc)
  210.             {
  211.                 pscrn = _ScrnBuf;
  212.                 for (ii = 0L; ii < SCRNSPACE; ii++)
  213.                     *pscrn++ = 0;
  214.                 argv++;
  215.             }
  216.         }
  217.     }
  218.  
  219.     exit (0);
  220. }
  221.  
  222.  
  223.  
  224.  
  225. /*------------------------------*/
  226. /*    read_fl            */
  227. /*------------------------------*/
  228.  
  229. #define NCHUNK        400        /* size of chuck to read */
  230. #define FL3MAGSZ    10        /* size of magic (chars) */
  231. #define FL3HDRSZ    256        /* size of header */
  232. #define MAGIC_FL3    "FLICKER91a"    /* magic string */
  233.  
  234. int read_fl (fname, pscrn, w, h)
  235. char   *fname;                /* file name (in) */
  236. int    *pscrn;                /* where to put screen data (out) */
  237. int    *w;                /* size of image, pixels (out) */
  238. int    *h;
  239. {
  240.  
  241. /*
  242.  *    read the flicker file. return 0 if error else 1.
  243.  */
  244.  
  245.     reg_t char     *pbuf;
  246.     reg_t int      *pint;
  247.     reg_t int    nbytes;
  248.     reg_t int    nlines;
  249.     reg_t long    ii;
  250.     int        fd;
  251.     FILE           *stream;
  252.     char        magic[FL3MAGSZ+10];
  253.     char        header[FL3HDRSZ+10];
  254.     char           *pheader;
  255.  
  256.  
  257.     DBG (("enter read_fl...\n"));
  258.  
  259.     /*
  260.      *   open the .fl file, binary...
  261.      */
  262.     if ((stream = fopenb (fname, "r")) == (FILE *) NULL)
  263.     {
  264.         printf ("Error openning %s.\n", fname);
  265.         return (0);
  266.     }
  267.     fd = fileno (stream);
  268.  
  269.  
  270.  
  271.     /*
  272.      *   read .fl magic
  273.      */
  274.     read (fd, magic, (int) FL3MAGSZ);
  275.     if (strncmp (magic, MAGIC_FL3, 10))
  276.     {
  277.         printf ("Bad magic here...\n");
  278.         fclose (stream);
  279.         return (0);
  280.     }
  281.  
  282.  
  283.  
  284.     /*
  285.      *   read .fl header:
  286.      *
  287.      *    offset    size    item
  288.      *    ------    ----    -----------------------------------------
  289.      *    0    2    width (pixels)
  290.      *    2    2    height (pixels)
  291.      */
  292.     if (header & 1)        pheader = (char *) (&header[1]);
  293.     else            pheader = (char *) (&header[0]);
  294.  
  295.     read (fd, pheader, (int) FL3HDRSZ);
  296.  
  297.     pint = &pheader[0];    *w = *pint;
  298.     pint = &pheader[2];    *h = *pint;
  299.  
  300.  
  301.  
  302. #ifdef FULL_SCREEN
  303.     /*
  304.      *   read the screens, sequentially. each screen is 32000 and there
  305.      *   are 3 screens for a total of 96000 bytes. work with NCHUNK bytes
  306.      *   at a time.
  307.      */
  308.     pbuf = (char *) pscrn;
  309.     for (ii = 0L; ii < 96000L/NCHUNK; ii++)    /* number of reads */
  310.     {
  311.         read (fd, pbuf, (int) NCHUNK);
  312.  
  313.         pbuf += (long) NCHUNK;
  314.     }
  315. #else
  316.     /*
  317.      *   this is space-saver version. we only need the actual pixels,
  318.      *   not the whole screen saved. find actual byte count for files
  319.      *   with w not evenly divisible by 8.
  320.      */
  321.     if ((int) *w % 8)
  322.         nbytes = ((*w + 8) >> 3);
  323.     else
  324.         nbytes = (*w >> 3);
  325.     nlines = *h;
  326.  
  327.     /* screen 1 */
  328.     for (pbuf = (char *) pscrn, ii = 0L; ii < nlines; ii++)
  329.     {
  330.         read (fd, pbuf, nbytes);
  331.         pbuf += 80L;        /* 640x400 screen has 80 bytes/line */
  332.     }
  333.  
  334.     /* screen 2 */
  335.     for (pbuf = (char *) ((long) pscrn + 32000L), ii = 0L; ii < nlines; ii++)
  336.     {
  337.         read (fd, pbuf, nbytes);
  338.         pbuf += 80L;
  339.     }
  340.  
  341.     /* screen 3 */
  342.     for (pbuf = (char *) ((long) pscrn + 64000L), ii = 0L; ii < nlines; ii++)
  343.     {
  344.         read (fd, pbuf, nbytes);
  345.         pbuf += 80L;
  346.     }
  347. #endif
  348.  
  349.  
  350.     /*
  351.      *   done. return success...
  352.      */
  353.     fclose (stream);
  354.     DBG (("read_fl returning...\n"));
  355.  
  356.     return (1);
  357. }
  358.  
  359.  
  360.  
  361.  
  362. /*------------------------------*/
  363. /*    showfl            */
  364. /*------------------------------*/
  365. int showfl (s0)
  366. int    *s0;
  367. {
  368.  
  369. /*
  370.  *    show a flicker image already in memory. for 640x400 ONLY!!!
  371.  *    returns char read to stop the display as low byte of int.
  372.  */
  373.  
  374.     reg_t long    ii;
  375.     reg_t char     *ps1;
  376.     reg_t char     *ps2;
  377.     char           *old1;
  378.     char           *old2;
  379.     int           *s1, *s2, *s3;
  380.     long        ret;
  381.  
  382.  
  383.     DBG (("enter showfl...\n"));
  384.  
  385.     /*
  386.      *   remember old screen
  387.      */
  388.     old1 = Logbase ();
  389.     old2 = Physbase ();
  390.  
  391.  
  392.  
  393.     /*
  394.      *   clear these (phys and logical)
  395.      */
  396.     ps1 = old1;
  397.     ps2 = old2;
  398.     for (ii = 0L; ii < 32000L; ii++)
  399.     {
  400.         *ps1++ = 0;
  401.         *ps2++ = 0;
  402.     }
  403.  
  404.  
  405.  
  406.     /*
  407.      *   set phys screen to first screen
  408.      */
  409.     Setscreen (old2, s0, -1);
  410.  
  411.  
  412.  
  413.     /*
  414.      *   set pointers
  415.      */
  416.     s1 = (int *) Physbase ();
  417.     s2 = (int *) ((long) s1 + 32000L);
  418.     s3 = (int *) ((long) s2 + 32000L);
  419.  
  420.  
  421.  
  422.     /*
  423.      *   display until a key is pressed
  424.      */
  425.     do
  426.     {
  427.         Setscreen (old2, s1, -1);    Vsync ();
  428.         Setscreen (old2, s2, -1);    Vsync ();
  429.         Setscreen (old2, s3, -1);    Vsync ();
  430.  
  431.     } while (!Bconstat (2));
  432.  
  433.  
  434.  
  435.     /*
  436.      *   get the key...
  437.      */
  438.     ret = Bconin (2) & 0x000000ffL;
  439.  
  440.  
  441.  
  442.     /*
  443.      *   reset screen
  444.      */
  445.     Setscreen (old1, old2, -1);
  446.  
  447.  
  448.  
  449.     /*
  450.      *   clear keypresses
  451.      */
  452.     while (Bconstat (2))
  453.         Bconin (2);
  454.  
  455.  
  456.     /*
  457.      *   done.
  458.      */
  459.     return ((int) ret);
  460. }
  461.  
  462.  
  463.  
  464.  
  465. /*------------------------------*/
  466. /*    usage            */
  467. /*------------------------------*/
  468. usage (excode)
  469. int    excode;
  470. {
  471.     printf ("Usage: %s [-m] file.fl ...\n", myname);
  472.     exit (excode);
  473. }
  474.  
  475.