home *** CD-ROM | disk | FTP | other *** search
/ Computerworld 1996 March / Computerworld_1996-03_cd.bin / idg_cd3 / grafika / fraktaly / frasr192 / rotate.c < prev    next >
C/C++ Source or Header  |  1995-03-21  |  15KB  |  461 lines

  1. /*
  2.     rotate.c - Routines that manipulate the Video DAC on VGA Adapters
  3. */
  4.  
  5. #include <stdlib.h>
  6. #include <stdio.h>
  7. #include <string.h>
  8. #include <time.h>
  9. #include "fractint.h"
  10. #include "helpdefs.h"
  11. #include "prototyp.h"
  12.  
  13. /* routines in this module    */
  14.  
  15. static void pauserotate(void);
  16. static void set_palette(BYTE start[3], BYTE finish[3]);
  17. static void set_palette2(BYTE start[3], BYTE finish[3]);
  18. static void set_palette3(BYTE start[3], BYTE middle[3], BYTE finish[3]);
  19.  
  20. static int paused;            /* rotate-is-paused flag */
  21. static BYTE Red[3]    = {63, 0, 0};    /* for shifted-Fkeys */
  22. static BYTE Green[3]  = { 0,63, 0};
  23. static BYTE Blue[3]   = { 0, 0,63};
  24. static BYTE Black[3]  = { 0, 0, 0};
  25. static BYTE White[3]  = {63,63,63};
  26. static BYTE Yellow[3] = {63,63, 0};
  27. static BYTE Brown[3]  = {31,31, 0};
  28.  
  29. char mapmask[13] = {"*.map"};
  30.  
  31. void rotate(int direction)    /* rotate-the-palette routine */
  32. {
  33. int  kbdchar, more, last, next;
  34. int fkey, step, fstep, istep, jstep, oldstep;
  35. int incr, fromred=0, fromblue=0, fromgreen=0, tored=0, toblue=0, togreen=0;
  36. int i, changecolor, changedirection;
  37. int oldhelpmode;
  38. int rotate_max,rotate_size;
  39.  
  40. static int fsteps[] = {2,4,8,12,16,24,32,40,54,100}; /* (for Fkeys) */
  41.  
  42.    if (gotrealdac == 0            /* ??? no DAC to rotate! */
  43.      || colors < 16) {            /* strange things happen in 2x modes */
  44.       buzzer(2);
  45.       return;
  46.       }
  47.  
  48.    oldhelpmode = helpmode;        /* save the old help mode    */
  49.    helpmode = HELPCYCLING;        /* new help mode        */
  50.  
  51.    paused = 0;                /* not paused            */
  52.    fkey = 0;                /* no random coloring        */
  53.    oldstep = step = 1;            /* single-step            */
  54.    fstep = 1;
  55.    changecolor = -1;            /* no color (rgb) to change    */
  56.    changedirection = 0;         /* no color direction to change */
  57.    incr = 999;                /* ready to randomize        */
  58.    srand((unsigned)time(NULL));     /* randomize things        */
  59.  
  60.    if (direction == 0) {        /* firing up in paused mode?    */
  61.       pauserotate();            /* then force a pause        */
  62.       direction = 1;            /* and set a rotate direction    */
  63.       }
  64.  
  65.    rotate_max = (rotate_hi < colors) ? rotate_hi : colors-1;
  66.    rotate_size = rotate_max - rotate_lo + 1;
  67.    last = rotate_max;            /* last box that was filled    */
  68.    next = rotate_lo;            /* next box to be filled    */
  69.    if (direction < 0) {
  70.       last = rotate_lo;
  71.       next = rotate_max;
  72.       }
  73.  
  74.    more = 1;
  75.    while (more) {
  76.       if (dotmode == 11) {
  77.      if (!paused)
  78.         pauserotate();
  79.      }
  80.       else while(!keypressed()) { /* rotate until key hit, at least once so step=oldstep ok */
  81.      if (fkey > 0) {        /* randomizing is on */
  82.         for (istep = 0; istep < step; istep++) {
  83.            jstep = next + (istep * direction);
  84.            while (jstep < rotate_lo)  jstep += rotate_size;
  85.            while (jstep > rotate_max) jstep -= rotate_size;
  86.            if (++incr > fstep) {    /* time to randomize */
  87.           incr = 1;
  88.                   fstep = ((fsteps[fkey-1]* (rand15() >> 8)) >> 6) + 1;
  89.           fromred   = dacbox[last][0];
  90.           fromgreen = dacbox[last][1];
  91.           fromblue  = dacbox[last][2];
  92.                   tored     = rand15() >> 9;
  93.                   togreen   = rand15() >> 9;
  94.                   toblue    = rand15() >> 9;
  95.           }
  96.            dacbox[jstep][0] = (BYTE)(fromred   + (((tored     - fromred  )*incr)/fstep));
  97.            dacbox[jstep][1] = (BYTE)(fromgreen + (((togreen - fromgreen)*incr)/fstep));
  98.            dacbox[jstep][2] = (BYTE)(fromblue  + (((toblue  - fromblue )*incr)/fstep));
  99.            }
  100.         }
  101.      if (step >= rotate_size) step = oldstep;
  102.      spindac(direction, step);
  103.      }
  104.       if (step >= rotate_size) step = oldstep;
  105.       kbdchar = getakey();
  106.       if (paused && (kbdchar != ' ' 
  107.                  && kbdchar != 'c' 
  108.                  && kbdchar != HOME 
  109.                  && kbdchar != 'C' ))
  110.      paused = 0;            /* clear paused condition    */
  111.       switch (kbdchar) {
  112.      case '+':                      /* '+' means rotate forward     */
  113.          case RIGHT_ARROW:              /* RightArrow = rotate fwd      */
  114.         fkey = 0;
  115.         direction = 1;
  116.         last = rotate_max;
  117.         next = rotate_lo;
  118.         incr = 999;
  119.         break;
  120.      case '-':                      /* '-' means rotate backward    */
  121.          case LEFT_ARROW:               /* LeftArrow = rotate bkwd      */
  122.         fkey = 0;
  123.         direction = -1;
  124.         last = rotate_lo;
  125.         next = rotate_max;
  126.         incr = 999;
  127.         break;
  128.          case UP_ARROW:                 /* UpArrow means speed up       */
  129.         daclearn = 1;
  130.         if (++daccount >= colors) --daccount;
  131.         break;
  132.          case DOWN_ARROW:               /* DownArrow means slow down    */
  133.         daclearn = 1;
  134.         if (daccount > 1) daccount--;
  135.         break;
  136.      case '1':
  137.      case '2':
  138.      case '3':
  139.      case '4':
  140.      case '5':
  141.      case '6':
  142.      case '7':
  143.      case '8':
  144.      case '9':
  145.         step = kbdchar - '0';   /* change step-size */
  146.         if (step > rotate_size) step = rotate_size;
  147.         break;
  148.          case F1:                       /* F1 - F10:                    */
  149.          case F2:                       /* select a shading factor      */
  150.          case F3:
  151.          case F4:
  152.          case F5:
  153.          case F6:
  154.          case F7:
  155.          case F8:
  156.          case F9:
  157.          case F10:
  158. #ifndef XFRACT
  159.             fkey = kbdchar-1058;
  160. #else
  161.             switch (kbdchar) {
  162.                case F1:
  163.                   fkey = 1;break;
  164.                case F2:
  165.                   fkey = 2;break;
  166.                case F3:
  167.                   fkey = 3;break;
  168.                case F4:
  169.                   fkey = 4;break;
  170.                case F5:
  171.                   fkey = 5;break;
  172.                case F6:
  173.                   fkey = 6;break;
  174.                case F7:
  175.                   fkey = 7;break;
  176.                case F8:
  177.                   fkey = 8;break;
  178.                case F9:
  179.                   fkey = 9;break;
  180.                case F10:
  181.                   fkey = 10;break;
  182.             }
  183. #endif
  184.         if (reallyega) fkey = (fkey+1)>>1; /* limit on EGA */
  185.         fstep = 1;
  186.         incr = 999;
  187.         break;
  188.          case ENTER:                    /* enter key: randomize all colors */
  189.          case ENTER_2:                  /* also the Numeric-Keypad Enter */
  190.             fkey = rand15()/3277 + 1;
  191.         if (reallyega)        /* limit on EGAs */
  192.            fkey = (fkey+1)>>1;
  193.         fstep = 1;
  194.         incr = 999;
  195.         oldstep = step;
  196.         step = rotate_size;
  197.         break;
  198.      case 'r':                      /* color changes */
  199.         if (changecolor    == -1) changecolor = 0;
  200.      case 'g':                      /* color changes */
  201.         if (changecolor    == -1) changecolor = 1;
  202.      case 'b':                      /* color changes */
  203.         if (changecolor    == -1) changecolor = 2;
  204.         if (changedirection == 0) changedirection = -1;
  205.      case 'R':                      /* color changes */
  206.         if (changecolor    == -1) changecolor = 0;
  207.      case 'G':                      /* color changes */
  208.         if (changecolor    == -1) changecolor = 1;
  209.      case 'B':                      /* color changes */
  210.         if (dotmode == 11) break;
  211.         if (changecolor    == -1) changecolor = 2;
  212.         if (changedirection == 0) changedirection = 1;
  213.         if (reallyega) break;    /* no sense on real EGAs */
  214.         for (i = 1; i < 256; i++) {
  215.            dacbox[i][changecolor] = (BYTE)(dacbox[i][changecolor] + changedirection);
  216.            if (dacbox[i][changecolor] == 64)
  217.            dacbox[i][changecolor] = 63;
  218.            if (dacbox[i][changecolor] == 255)
  219.           dacbox[i][changecolor] = 0;
  220.            }
  221.         changecolor    = -1;    /* clear flags for next time */
  222.         changedirection = 0;
  223.         paused        = 0;    /* clear any pause */
  224.      case ' ':                      /* use the spacebar as a "pause" toggle */
  225.      case 'c':                      /* for completeness' sake, the 'c' too */
  226.      case 'C':
  227.         pauserotate();        /* pause */
  228.         break;
  229.      case '>':            /* single-step */
  230.      case '.':
  231.      case '<':
  232.      case ',':
  233.         if (kbdchar == '>' || kbdchar == '.') {
  234.            direction = 1;
  235.            last = rotate_max;
  236.            next = rotate_lo;
  237.            incr = 999;
  238.            }
  239.         else {
  240.            direction = -1;
  241.            last = rotate_lo;
  242.            next = rotate_max;
  243.            incr = 999;
  244.            }
  245.         fkey = 0;
  246.         spindac(direction,1);
  247.         if (! paused)
  248.            pauserotate();        /* pause */
  249.         break;
  250.      case 'd':                      /* load colors from "default.map" */
  251.      case 'D':
  252.         if (ValidateLuts("default") != 0)
  253.            break;
  254.         fkey = 0;            /* disable random generation */
  255.         pauserotate();        /* update palette and pause */
  256.         break;
  257.      case 'a':                      /* load colors from "altern.map" */
  258.      case 'A':
  259.         if (ValidateLuts("altern") != 0)
  260.            break;
  261.         fkey = 0;            /* disable random generation */
  262.         pauserotate();        /* update palette and pause */
  263.         break;
  264.      case 'l':                      /* load colors from a specified map */
  265. #ifndef XFRACT /* L is used for RIGHT_ARROW in Unix keyboard mapping */
  266.      case 'L':
  267. #endif
  268.         load_palette();
  269.         fkey = 0;            /* disable random generation */
  270.         pauserotate();        /* update palette and pause */
  271.         break;
  272.      case 's':                      /* save the palette */
  273.      case 'S':
  274.         save_palette();
  275.         fkey = 0;            /* disable random generation */
  276.         pauserotate();        /* update palette and pause */
  277.         break;
  278.          case ESC:                      /* escape */
  279.         more = 0;            /* time to bail out */
  280.         break;
  281.          case HOME:                     /* restore palette */
  282.             memcpy(dacbox,olddacbox,256*3);
  283.             pauserotate();        /* pause */
  284.         break;
  285.      default:            /* maybe a new palette */
  286.         if (reallyega) break;    /* no sense on real EGAs */
  287.         fkey = 0;            /* disable random generation */
  288.         if (kbdchar == 1084) set_palette(Black, White);
  289.         if (kbdchar == SF2) set_palette(Red, Yellow);
  290.         if (kbdchar == SF3) set_palette(Blue, Green);
  291.         if (kbdchar == SF4) set_palette(Black, Yellow);
  292.         if (kbdchar == SF5) set_palette(Black, Red);
  293.         if (kbdchar == SF6) set_palette(Black, Blue);
  294.         if (kbdchar == SF7) set_palette(Black, Green);
  295.         if (kbdchar == SF8) set_palette(Blue, Yellow);
  296.         if (kbdchar == SF9) set_palette(Red, Green);
  297.         if (kbdchar == 1093) set_palette(Green, White);
  298.         if (kbdchar == 1094) set_palette2(Black, White);
  299.         if (kbdchar == 1095) set_palette2(Red, Yellow);
  300.         if (kbdchar == 1096) set_palette2(Blue, Green);
  301.         if (kbdchar == 1097) set_palette2(Black, Yellow);
  302.         if (kbdchar == 1098) set_palette2(Black, Red);
  303.         if (kbdchar == 1099) set_palette2(Black, Blue);
  304.         if (kbdchar == 1100) set_palette2(Black, Green);
  305.         if (kbdchar == 1101) set_palette2(Blue, Yellow);
  306.         if (kbdchar == 1102) set_palette2(Red, Green);
  307.         if (kbdchar == 1103) set_palette2(Green, White);
  308.         if (kbdchar == 1104) set_palette3(Blue, Green, Red);
  309.         if (kbdchar == 1105) set_palette3(Blue, Yellow, Red);
  310.         if (kbdchar == 1106) set_palette3(Red, White, Blue);
  311.         if (kbdchar == 1107) set_palette3(Red, Yellow, White);
  312.         if (kbdchar == 1108) set_palette3(Black, Brown, Yellow);
  313.         if (kbdchar == 1109) set_palette3(Blue, Brown, Green);
  314.         if (kbdchar == 1110) set_palette3(Blue, Green, Green);
  315.         if (kbdchar == 1111) set_palette3(Blue, Green, White);
  316.         if (kbdchar == 1112) set_palette3(Green, Green, White);
  317.         if (kbdchar == 1113) set_palette3(Red, Blue, White);
  318.         pauserotate();  /* update palette and pause */
  319.         break;
  320.      }
  321.       }
  322.  
  323.    helpmode = oldhelpmode;        /* return to previous help mode */
  324. }
  325.  
  326. static void pauserotate()        /* pause-the-rotate routine */
  327. {
  328. int olddaccount;            /* saved dac-count value goes here */
  329. BYTE olddac0,olddac1,olddac2;
  330.  
  331.    if (paused)                /* if already paused , just clear */
  332.       paused = 0;
  333.    else {                /* else set border, wait for a key */
  334.       olddaccount = daccount;
  335.       olddac0 = dacbox[0][0];
  336.       olddac1 = dacbox[0][1];
  337.       olddac2 = dacbox[0][2];
  338.       daccount = 256;
  339.       dacbox[0][0] = 48;
  340.       dacbox[0][1] = 48;
  341.       dacbox[0][2] = 48;
  342.       spindac(0,1);            /* show white border */
  343.       if (dotmode == 11)
  344.       {
  345.          static FCODE o_msg[] = {" Paused in \"color cycling\" mode "};
  346.          char msg[sizeof(o_msg)];
  347.          far_strcpy(msg,o_msg);
  348.          dvid_status(100,msg);
  349.       }
  350. #ifndef XFRACT
  351.       while (!keypressed());          /* wait for any key */
  352. #else
  353.       waitkeypressed(0);                /* wait for any key */
  354. #endif
  355.       if (dotmode == 11)
  356.      dvid_status(0,"");
  357.       dacbox[0][0] = olddac0;
  358.       dacbox[0][1] = olddac1;
  359.       dacbox[0][2] = olddac2;
  360.       spindac(0,1);            /* show black border */
  361.       daccount = olddaccount;
  362.       paused = 1;
  363.       }
  364. }
  365.  
  366. static void set_palette(BYTE start[3], BYTE finish[3])
  367. {
  368.    int i, j;
  369.    dacbox[0][0] = dacbox[0][1] = dacbox[0][2] = 0;
  370.    for(i=1;i<=255;i++)            /* fill the palette    */
  371.       for (j = 0; j < 3; j++)
  372.      dacbox[i][j] = (BYTE)((i*start[j] + (256-i)*finish[j])/255);
  373. }
  374.  
  375. static void set_palette2(BYTE start[3], BYTE finish[3])
  376. {
  377.    int i, j;
  378.    dacbox[0][0] = dacbox[0][1] = dacbox[0][2] = 0;
  379.    for(i=1;i<=128;i++)
  380.       for (j = 0; j < 3; j++) {
  381.      dacbox[i][j]      = (BYTE)((i*finish[j] + (128-i)*start[j] )/128);
  382.      dacbox[i+127][j] = (BYTE)((i*start[j]  + (128-i)*finish[j])/128);
  383.       }
  384. }
  385.  
  386. static void set_palette3(BYTE start[3], BYTE middle[3], BYTE finish[3])
  387. {
  388.    int i, j;
  389.    dacbox[0][0] = dacbox[0][1] = dacbox[0][2] = 0;
  390.    for(i=1;i<=85;i++)
  391.       for (j = 0; j < 3; j++) {
  392.      dacbox[i][j]      = (BYTE)((i*middle[j] + (86-i)*start[j] )/85);
  393.      dacbox[i+85][j]  = (BYTE)((i*finish[j] + (86-i)*middle[j])/85);
  394.      dacbox[i+170][j] = (BYTE)((i*start[j]  + (86-i)*finish[j])/85);
  395.       }
  396. }
  397.  
  398.  
  399. void save_palette()
  400. {
  401.    char palname[FILE_MAX_PATH];
  402.    static FCODE o_msg[] = {"Name of map file to write"};
  403.    char msg[sizeof(o_msg)];
  404.    FILE *dacfile;
  405.    int i,oldhelpmode;
  406.    far_strcpy(msg,o_msg);
  407.    strcpy(palname,MAP_name);
  408.    oldhelpmode = helpmode;
  409.    stackscreen();
  410.    temp1[0] = 0;
  411.    helpmode = HELPCOLORMAP;
  412.    i = field_prompt(0,msg,NULL,temp1,60,NULL);
  413.    unstackscreen();
  414.    if (i != -1 && temp1[0]) {
  415.       if (strchr(temp1,'.') == NULL)
  416.      strcat(temp1,".map");
  417.       merge_pathnames(palname,temp1,2);
  418.       dacfile = fopen(palname,"w");
  419.       if (dacfile == NULL)
  420.      buzzer(2);
  421.       else {
  422. #ifndef XFRACT
  423.      for (i = 0; i < colors; i++)
  424. #else
  425.      for (i = 0; i < 256; i++)
  426. #endif
  427.         fprintf(dacfile, "%3d %3d %3d\n",
  428.             dacbox[i][0] << 2,
  429.             dacbox[i][1] << 2,
  430.             dacbox[i][2] << 2);
  431.      memcpy(olddacbox,dacbox,256*3);
  432.      colorstate = 2;
  433.      strcpy(colorfile,temp1);
  434.      }
  435.       fclose(dacfile);
  436.       }
  437.    helpmode = oldhelpmode;
  438. }
  439.  
  440.  
  441. void load_palette(void)
  442. {
  443.    int i,oldhelpmode;
  444.    char filename[80];
  445.    oldhelpmode = helpmode;
  446.    strcpy(filename,MAP_name);
  447.    stackscreen();
  448.    helpmode = HELPCOLORMAP;
  449.    i = getafilename("Select a MAP File",mapmask,filename);
  450.    unstackscreen();
  451.    if (i >= 0)
  452.    {
  453.       if (ValidateLuts(filename) == 0)
  454.      memcpy(olddacbox,dacbox,256*3);
  455.       merge_pathnames(MAP_name,filename,0);
  456.    }
  457.    helpmode = oldhelpmode;
  458. }
  459.  
  460.  
  461.