home *** CD-ROM | disk | FTP | other *** search
/ The C Users' Group Library 1994 August / wc-cdrom-cusersgrouplibrary-1994-08.iso / vol_300 / 328_02 / wgscrlv.c < prev    next >
C/C++ Source or Header  |  1991-04-02  |  6KB  |  228 lines

  1. /*! wgscrollv ()
  2.  *    scroll an area of graphics screen vertically by nr # of pixel rows.
  3.  *    Note that in dealing with text, only multiples of 8 make sense,
  4.  *        but the more general routine is provided for graphic images.
  5.  *
  6.  *    The area is defined by text mode co=ords l,t,r,b
  7.  *    nr is + to scroll down, - to scroll up.
  8.  *     The bottom lines are not changed.
  9.  */
  10. #include  "wscreen.h"
  11. #include  "wsys.h"
  12.  
  13.  
  14.  
  15.  
  16.  
  17. void     wgscrollv ( int l, int t, int r, int b, int nr )
  18.     {
  19.  
  20.  
  21.  
  22.     /* variables used as loop index (counters & ptrs)
  23.      */
  24.     int col;
  25.     unsigned char far *coltarget;
  26.     unsigned char far *colsource;
  27.     unsigned char far *target;
  28.     unsigned char far *source;
  29.  
  30.  
  31.  
  32.     /* virtual loop control ( to set loop bounds and direction )
  33.      *
  34.      *    needed because loops go either top to bottom (scroll up)
  35.      *                    or bottom to top (       dn)
  36.      *
  37.      *    'virtual top' may be actual top or bottom,depending...
  38.      *    similar for bottom.
  39.      *    'virtual_1' is +1 if increasing rows (top->bottom)
  40.      *               -1 if decreasing rows.
  41.      *    'virtual_htarget, _hsource are hercules bank offsets
  42.      *            for target and source rows.
  43.      *    'virtual_hincr' is either +0x2000 or -0x2000, as above.
  44.      *            (hercules bank offsets)
  45.      *    'virtual_h_limit is either 0x8000 or 0x0000 = bank limit.
  46.      */
  47.     int v_t, v_b, v_1, v_htarget, v_hsource, v_hincr, v_hlimit, v_hreset;
  48.     int v_rowincr;
  49.  
  50.     /* convert to pixel co-ords only for counting rows */
  51.     t *= wpychar;
  52.     b = (b+1) * wpychar;
  53.  
  54.  
  55.  
  56.  
  57.     switch ( wmonitor )
  58.         {
  59.     case ('H'):
  60.         /* NOTE addressing hercules graphics ram:
  61.          *    l, r are 'text-mode' addresses.
  62.          *    720 pixels/row, wpxchar pixels per 'x' increment
  63.          *        so 1st factor = wxmax = chars per row
  64.          *    divide t, b, (t+nr) are row numbers in pixel co=ords
  65.          *         ( of bottom, top for source, top for target)
  66.          *    wpxchar/8 =1 always, included only for clarity.
  67.          *
  68.          *    because charsizes are mults of 4, whbank starts at 0;
  69.          *        hnsource starts at 0.
  70.          *        hntarget is  - (nr mod 4)
  71.          */
  72.  
  73.  
  74.  
  75.         if ( nr < 0 )
  76.             {
  77.             /* scrolling up:  want to go top to bottom */
  78.             v_t = t;
  79.             v_b = b;
  80.             v_1 = 1;
  81.             v_hincr = 0x2000;               /* loop up in banks*/
  82.             v_hlimit = 0x8000;
  83.             v_hreset = 0;
  84.             v_rowincr = 720/8;        /* next row, up */
  85.             v_htarget = ( -nr ) % 4 ;    /* herc bank number*/
  86.  
  87.             }
  88.         else
  89.         if ( nr > 0 )
  90.             {
  91.             /* scrolling down: want to go bottom to top */
  92.             v_t =  b;    /* virtual top = actual bottom */
  93.             v_b =  t;
  94.             v_1 = -1;    /* minus one causes row# decrement */
  95.             v_hincr = -0x2000;               /* loop down in banks */
  96.             v_hlimit = 0x0000;
  97.             v_hreset = 0x8000;
  98.             v_rowincr = -720/8;    /* next row, down */
  99.             v_htarget = ( nr ) % 4 ;
  100.  
  101.             }
  102.         else     {
  103.             /* request to scroll 0 rows */
  104.             return;
  105.             }
  106.         v_htarget *= 0x2000;    /* convert bank number to offset */
  107.         v_hsource = 0;        /* herc bank number for source
  108.                      * note source row is mult of 8
  109.                      */
  110.  
  111.         source    =  wpage_ram
  112.             + ( (720/wpxchar)*(  v_t    /4) ) +l;
  113.         target  =  wpage_ram
  114.             + ( (720/wpxchar)*( (v_t+nr)/4) ) +l;
  115.  
  116.  
  117.         while ( v_t != v_b )
  118.             /* loop until virtual top equals virtual bottom */
  119.             {
  120.             /* loop iterates once per row
  121.              */
  122.             if ( v_htarget == v_hlimit )
  123.                 {
  124.                 /* finished one set of 4 banks,
  125.                  * move up/down to next tier.
  126.                  */
  127.                 v_htarget  = v_hreset;
  128.                 target     += v_rowincr;
  129.                 }
  130.             if ( v_hsource == v_hlimit )
  131.                 {
  132.                 /* finished one set of 4 banks,
  133.                  * move up to next tier.
  134.                  */
  135.                 v_hsource = v_hreset;
  136.                 source   += v_rowincr;
  137.                 }
  138.  
  139.             for (     col = l,     coltarget = target,
  140.                         colsource = source;
  141.                 col <=r;
  142.                 ++col, ++coltarget, ++colsource)
  143.                 {
  144.                 /* once per column within each row */
  145.                 *( coltarget + v_htarget ) =
  146.                     *( colsource + v_hsource );
  147.                 }
  148.             v_htarget += v_hincr;    /* if scroll up, subtracts */
  149.             v_hsource += v_hincr;   /* if scroll dn, adds */
  150.             v_t       += v_1;       /* if up, -1, if down +1 */
  151.             }
  152.         break;       /* end hercules mode */
  153.  
  154.     case ( 'E' ):
  155.     case ( 'V' ):
  156.         /* use write mode 1 to scroll the screen */
  157.  
  158.  
  159.         if ( nr < 0 )
  160.             {
  161.             /* scrolling up:  want to go top to bottom */
  162.             v_t = t;
  163.             v_b = b;
  164.             v_1 = 1;
  165.             v_rowincr = 640/wpxchar;        /* next row, up */
  166.             }
  167.         else
  168.         if ( nr > 0 )
  169.             {
  170.             /* scrolling down: want to go bottom to top */
  171.             v_t =  b;    /* virtual top = actual bottom */
  172.             v_b =  t;
  173.             v_1 = -1;    /* minus one causes row# decrement */
  174.             v_rowincr = -640/wpxchar;    /* next row, down */
  175.             }
  176.         else     {
  177.             /* request to scroll 0 rows */
  178.             return;
  179.             }
  180.  
  181.  
  182.         source    =  wpage_ram
  183.             + (wegarowsize)*(  v_t     *wpychar/8)
  184.             + l * (wpxchar/8) ;
  185.         target  =  wpage_ram
  186.             + (wegarowsize)*( (v_t+nr) *wpychar/8)
  187.             + l * (wpxchar/8) ;
  188.  
  189.  
  190.         while ( v_t != v_b )
  191.             /* loop until virtual top equals virtual bottom */
  192.             {
  193.             /* loop iterates once per row
  194.              */
  195.  
  196.             EGA_OUT (2, 0x0F);
  197.             EGA_OUT (5, 1);        /* write mode 1 */
  198.  
  199.  
  200.             for (     col = l,     coltarget = target,
  201.                         colsource = source;
  202.                 col <=r;
  203.                 ++col, ++coltarget, ++colsource)
  204.                 {
  205.                 /* once per column within each row */
  206.                 *( coltarget ) = *( colsource );
  207.                 }
  208.             target    += v_rowincr;    /* if scroll up, subtracts */
  209.             source    += v_rowincr; /* if scroll dn, adds */
  210.             v_t       += v_1;       /* if up, -1, if down +1 */
  211.             }
  212.  
  213.             EGA_OUT (5,0);        /* write mode 0 */
  214.  
  215.  
  216.  
  217.  
  218.         break;
  219.         }    /* end switch on monitor type */
  220.  
  221.  
  222.  
  223.  
  224.  
  225.  
  226.     return;            /* end wgscrollv */
  227.     }
  228.