home *** CD-ROM | disk | FTP | other *** search
/ C++ Games Programming / CPPGAMES.ISO / fgl / fglight / manuals.arj / USER13.DOC < prev    next >
Text File  |  1995-02-06  |  32KB  |  757 lines

  1.  
  2.  
  3.  
  4.  
  5.  
  6.  
  7. Chapter 13
  8.  
  9.  
  10.  
  11.  
  12.  
  13. Special Effects                                                                
  14. 288   Fastgraph User's Guide
  15.  
  16.  
  17. Overview
  18.  
  19.      This chapter will discuss the Fastgraph routines that help produce
  20. special visual effects. These include the ability to dissolve the screen
  21. contents in small increments, scroll areas of the screen, change the physical
  22. origin of the screen, and set up a split screen environment. The accompanying
  23. example programs illustrate how to use these routines to produce some
  24. interesting effects.
  25.  
  26.  
  27. Screen Dissolving
  28.  
  29.      Screen dissolving is the process of replacing the entire screen contents
  30. in random small increments instead of all at once. Fastgraph includes two
  31. routines, fg_fadeout and fg_fadein, for this purpose. The fg_fadeout routine
  32. incrementally replaces the visual page contents with pixels of the current
  33. color, while fg_fadein incrementally replaces the visual page contents with
  34. the hidden page contents (that is, the page defined in the most recent call to
  35. fg_sethpage). Both routines accept an integer argument that defines the delay
  36. between each incremental replacement. A value of zero means to perform the
  37. replacement as quickly as possible, while 1 is slightly slower, 2 is slower
  38. yet, and so forth. The fg_fadeout and fg_fadein routines have no effect in
  39. text video modes and always work with video pages, even if a virtual buffer is
  40. active.
  41.  
  42.      Example 13-1 shows how to use fg_fadeout. The program, which runs in any
  43. graphics video mode, first fills the screen with a rectangle of color 2. After
  44. waiting for a keystroke, the program incrementally replaces the screen
  45. contents with pixels of color 15 (the current color index when fg_fadeout is
  46. called). After another keystroke, the program exits gracefully.
  47.  
  48.                                  Example 13-1.
  49.  
  50.                   #include <fastgraf.h>
  51.                   void main(void);
  52.  
  53.                   void main()
  54.                   {
  55.                      int old_mode;
  56.  
  57.                      fg_initpm();
  58.                      old_mode = fg_getmode();
  59.                      fg_setmode(fg_automode());
  60.  
  61.                      fg_setcolor(2);
  62.                      fg_rect(0,fg_getmaxx(),0,fg_getmaxy());
  63.                      fg_waitkey();
  64.  
  65.                      fg_setcolor(15);
  66.                      fg_fadeout(0);
  67.                      fg_waitkey();
  68.  
  69.                      fg_setmode(old_mode);
  70.                      fg_reset();
  71.                   }                                                            
  72.                                             Chapter 13:  Special Effects   289
  73.  
  74.  
  75.  
  76.      Example 13-2 shows how to use fg_fadein in any 320x200 color graphics
  77. video mode. The program first fills the screen with a rectangle of color 2 and
  78. then fills video page 1 with a rectangle of color 1. After waiting for a
  79. keystroke, the program incrementally transfers the contents of page 1 to the
  80. visual page. After the call to fg_fadein, both page 0 (the visual page) and
  81. page 1 (the hidden page) will contain rectangles of color 1 that fill the
  82. entire video page. Finally, the program waits for another keystroke before
  83. returning to DOS.
  84.  
  85.                                  Example 13-2.
  86.  
  87.                  #include <fastgraf.h>
  88.                  #include <stdio.h>
  89.                  #include <stdlib.h>
  90.                  void main(void);
  91.  
  92.                  void main()
  93.                  {
  94.                     int new_mode, old_mode;
  95.  
  96.                     fg_initpm();
  97.                     new_mode = fg_bestmode(320,200,2);
  98.                     if (new_mode < 0 || new_mode == 12) {
  99.                        printf("This program requires a 320 ");
  100.                        printf("x 200 color graphics mode.\n");
  101.                        exit(1);
  102.                        }
  103.                     old_mode = fg_getmode();
  104.                     fg_setmode(new_mode);
  105.                     fg_allocate(1);
  106.                     fg_sethpage(1);
  107.  
  108.                     fg_setcolor(2);
  109.                     fg_rect(0,319,0,199);
  110.                     fg_setpage(1);
  111.                     fg_setcolor(1);
  112.                     fg_rect(0,319,0,199);
  113.                     fg_waitkey();
  114.  
  115.                     fg_fadein(0);
  116.                     fg_waitkey();
  117.  
  118.                     fg_freepage(1);
  119.                     fg_setmode(old_mode);
  120.                     fg_reset();
  121.                  }
  122.  
  123.  
  124.      You also can produce some appealing visual effects by replacing the
  125. screen contents in a non-random fashion using the fg_restore or fg_transfer
  126. routines. For example, you could copy the hidden page contents to the visual
  127. page through a series of concentric rectangular areas, each slightly larger
  128. than the previous, until the entire screen is copied. Another interesting
  129. effect is to start around the screen perimeter and proceed toward the screen   
  130. 290   Fastgraph User's Guide
  131.  
  132. center, thus producing a "snake-like" effect. Experimenting with such
  133. techniques may reveal other effects that suit your application.
  134.  
  135.  
  136. Scrolling
  137.  
  138.      Another useful effect is scrolling, and Fastgraph provides a routine that
  139. performs vertical scrolling within a given region of the active video page.
  140. The fg_scroll routine scrolls a region defined in screen space or character
  141. space. It can scroll up or down and offers two types of scrolling: circular
  142. and end-off. In circular scrolling, rows that scroll off one edge of the
  143. defined region appear at its opposite edge. In end-off scrolling, such rows
  144. simply wind up above or below the scrolling area. The following diagrams
  145. illustrate the two types of scrolling.
  146.  
  147.                  end-off scrolling            circular scrolling
  148.  
  149.                before         after          before         after
  150.  
  151.                                 C                             B
  152.                   A                             A
  153.  
  154.                                 A                             A
  155.                   B                             B
  156.  
  157.  
  158.      In these diagrams, the area bounded by the double lines is the scrolling
  159. region, as specified in the call to fg_scroll. Also, the scrolling direction
  160. is assumed to be down (that is, toward the bottom of the screen), and the
  161. number of rows to scroll is the height of the area designated B. The number of
  162. rows to scroll is often called the scrolling increment.
  163.  
  164.      For the end-off scrolling example, the scrolling operation transfers
  165. region A downward so part of it is copied into area B. The area C (which is
  166. the same size as area B) at the top of the scrolling region is filled with
  167. pixels of the current color index (as defined in the most recent call to
  168. fg_setcolor), and the original contents of area B are lost. The circular
  169. scrolling example also copies region A downward into the original area B.
  170. Unlike end-off scrolling, however, circular scrolling preserves the area B by
  171. copying it to the opposite edge of the scrolling region.
  172.  
  173.      The fg_scroll routine takes six arguments. The first four define the
  174. scrolling region in the order minimum x coordinate, maximum x coordinate,
  175. minimum y coordinate, and maximum y coordinate. In graphics video modes, the x
  176. coordinates are extended to byte boundaries if needed. The fifth argument is
  177. the scrolling increment. It specifies the number of rows to scroll. If it is
  178. positive, the scrolling direction is toward the bottom of the screen; if it is
  179. negative, the scrolling direction is toward the top of the screen. The sixth
  180. and final argument specifies the scroll type. If this value is zero, the
  181. scroll will be circular; if it is any other value, the scroll will be end-off.
  182. If the scroll type is circular, Fastgraph will use the hidden page (as defined
  183. in the most recent call to fg_sethpage) as a workspace (more specifically, the
  184. area bounded by the scrolling region extremes on the hidden page will be
  185. used). The fg_scroll routine is disabled when a virtual buffer is active.      
  186.                                             Chapter 13:  Special Effects   291
  187.  
  188.      We'll now present three example programs that use the fg_scroll routine.
  189. Example 13-3 runs in any 320x200 graphics video mode. The program displays two
  190. lines of text ("line one" and "line two") in the upper left corner of the
  191. screen against a white background. It then uses fg_scroll to move the second
  192. line down four pixel rows using an end-off scroll. After waiting for a
  193. keystroke, the program again uses fg_scroll to move the text back to its
  194. original position. Note especially how fg_setcolor is used before the first
  195. call to fg_scroll to replace the "scrolled off" rows with pixels of color 15,
  196. thus preserving the white background.
  197.  
  198.                                  Example 13-3.
  199.  
  200.                  #include <fastgraf.h>
  201.                  #include <stdio.h>
  202.                  #include <stdlib.h>
  203.                  void main(void);
  204.  
  205.                  void main()
  206.                  {
  207.                     int new_mode, old_mode;
  208.  
  209.                     fg_initpm();
  210.                     new_mode = fg_bestmode(320,200,1);
  211.                     if (new_mode < 0 || new_mode == 12) {
  212.                        printf("This program requires a 320 ");
  213.                        printf("x 200 color graphics mode.\n");
  214.                        exit(1);
  215.                        }
  216.                     old_mode = fg_getmode();
  217.                     fg_setmode(new_mode);
  218.  
  219.                     fg_setcolor(15);
  220.                     fg_rect(0,319,0,199);
  221.                     fg_setcolor(10);
  222.                     fg_text("line one",8);
  223.                     fg_locate(1,0);
  224.                     fg_text("line two",8);
  225.                     fg_waitkey();
  226.  
  227.                     fg_setcolor(15);
  228.                     fg_scroll(0,63,8,15,4,1);
  229.                     fg_waitkey();
  230.                     fg_scroll(0,63,12,19,-4,1);
  231.                     fg_waitkey();
  232.  
  233.                     fg_setmode(old_mode);
  234.                     fg_reset();
  235.                  }
  236.  
  237.  
  238.      Example 13-4 is similar to example 13-3, but it runs in the 80-column
  239. color text mode (mode 3). In text modes, we cannot scroll half a character row
  240. as in example 13-3, so the program scrolls the minimum one row instead.
  241.  
  242.                                  Example 13-4.                                 
  243. 292   Fastgraph User's Guide
  244.  
  245.                           #include <fastgraf.h>
  246.                           void main(void);
  247.  
  248.                           void main()
  249.                           {
  250.                              int old_mode;
  251.  
  252.                              fg_initpm();
  253.                              old_mode = fg_getmode();
  254.                              fg_setmode(3);
  255.                              fg_cursor(0);
  256.  
  257.                              fg_setcolor(7);
  258.                              fg_rect(0,79,0,24);
  259.                              fg_setattr(10,7,0);
  260.                              fg_text("line one",8);
  261.                              fg_locate(1,0);
  262.                              fg_text("line two",8);
  263.                              fg_waitkey();
  264.  
  265.                              fg_setcolor(7);
  266.                              fg_scroll(0,7,1,1,1,1);
  267.                              fg_waitkey();
  268.                              fg_scroll(0,7,2,2,-1,1);
  269.                              fg_waitkey();
  270.  
  271.                              fg_setmode(old_mode);
  272.                              fg_reset();
  273.                           }
  274.  
  275.  
  276.      Example 13-5, the final scrolling example, demonstrates a circular
  277. scroll. The program runs in any 320x200 color graphics video mode; note the
  278. use of video page 1 for the workspace required when fg_scroll performs a
  279. circular scroll. The program first fills the screen with a light blue
  280. rectangle (cyan in CGA), displays a smaller white rectangle in the center of
  281. the screen, and then uses fg_move, fg_draw, and fg_paint to display a light
  282. green star (magenta in CGA) within the white rectangle. The program executes a
  283. while loop to scroll the star upward in four-pixel increments. Because the
  284. scroll is circular, rows of the star that "scroll off" the top edge of the
  285. white rectangle (whose height is the same as the scrolling region) reappear at
  286. its bottom edge. The use of fg_waitfor within the loop simply slows down the
  287. scroll. The scrolling continues until any key is pressed.
  288.  
  289.                                  Example 13-5.
  290.  
  291.                  #include <conio.h>
  292.                  #include <fastgraf.h>
  293.                  #include <stdio.h>
  294.                  #include <stdlib.h>
  295.                  void main(void);
  296.  
  297.                  void main()
  298.                  {
  299.                     int new_mode, old_mode;                                    
  300.                                             Chapter 13:  Special Effects   293
  301.  
  302.                     fg_initpm();
  303.                     new_mode = fg_bestmode(320,200,2);
  304.                     if (new_mode < 0 || new_mode == 12) {
  305.                        printf("This program requires a 320 ");
  306.                        printf("x 200 color graphics mode.\n");
  307.                        exit(1);
  308.                        }
  309.                     old_mode = fg_getmode();
  310.                     fg_setmode(new_mode);
  311.                     fg_allocate(1);
  312.                     fg_sethpage(1);
  313.  
  314.                     fg_setcolor(9);
  315.                     fg_rect(0,319,0,199);
  316.                     fg_setcolor(15);
  317.                     fg_rect(132,188,50,150);
  318.  
  319.                     fg_setcolor(10);
  320.                     fg_move(160,67);
  321.                     fg_draw(175,107);
  322.                     fg_draw(140,82);
  323.                     fg_draw(180,82);
  324.                     fg_draw(145,107);
  325.                     fg_draw(160,67);
  326.                     fg_paint(160,77);
  327.                     fg_paint(150,87);
  328.                     fg_paint(160,87);
  329.                     fg_paint(170,87);
  330.                     fg_paint(155,97);
  331.                     fg_paint(165,97);
  332.  
  333.                     while (kbhit() == 0) {
  334.                        fg_waitfor(1);
  335.                        fg_scroll(136,184,50,150,-4,0);
  336.                        }
  337.                     fg_waitkey();
  338.  
  339.                     fg_freepage(1);
  340.                     fg_setmode(old_mode);
  341.                     fg_reset();
  342.                  }
  343.  
  344.  
  345.  
  346. Changing the Screen Origin
  347.  
  348.      Fastgraph includes two routines for changing the screen origin. By
  349. changing the screen origin, we simply mean defining the (x,y) coordinate of
  350. the upper left corner of the display area. The fg_pan routine performs this
  351. function in screen space, while the fg_panw routine does in world space.
  352. Neither routine changes the graphics cursor position. Because the function of
  353. fg_pan and fg_panw is to change the screen origin, these routines are not
  354. applicable to virtual buffers.                                                 
  355. 294   Fastgraph User's Guide
  356.  
  357.      Each of these routines has two arguments that specify the x and y
  358. coordinates of the screen origin. For fg_pan, the arguments are integer
  359. quantities. For fg_panw, they are floating point quantities.
  360.  
  361.      In the EGA, VGA, MCGA, XVGA, and SVGA graphics modes (modes 13 to 29),
  362. you can set the screen origin to any (x,y) coordinate position (that is, to
  363. any pixel). In the other graphics modes, certain restrictions exist, as
  364. imposed by specific video hardware. These constraints limit the coordinate
  365. positions that can be used as the screen origin. Fastgraph compensates for
  366. these restrictions by reducing the specified x and y coordinates to values
  367. that are acceptable to the current video mode, as shown in the following
  368. table.
  369.  
  370.                            x will be reduced   y will be reduced
  371.           video mode       to a multiple of:   to a multiple of:
  372.  
  373.               4-5                  8                   2
  374.                6                  16                   2
  375.                9                   4                   4
  376.               11                   8                   4
  377.               12                   4                2 or 3
  378.  
  379. In modes 4 and 5, for instance, the x coordinate will be reduced to a multiple
  380. of 8 pixels, and the y coordinate will be reduced to a multiple of 2 pixels.
  381. In the Hercules low resolution mode (mode 12), the y coordinate reduction
  382. depends on whether or not the specified pixel row is scan doubled.
  383.  
  384.      Example 13-6 shows a useful effect that can be made with fg_pan or
  385. fg_panw. This program uses fg_automode to select a video mode and then draws
  386. an unfilled white rectangle. The top and bottom sides of the rectangle are
  387. intentionally drawn just smaller than the physical screen size. After waiting
  388. for a keystroke, the program uses a for loop to make the rectangle jiggle up
  389. and down. The rectangle moves because fg_pan is called inside the loop to
  390. switch the screen origin between the rectangle's upper left corner and the
  391. original origin. Note also the use of fg_waitfor to cause slight delays after
  392. each call to fg_pan. If we didn't use fg_waitfor, the changing of the origin
  393. would occur so rapidly we wouldn't notice the effect. Finally, the program
  394. restores the original video mode and screen attributes before returning to
  395. DOS.
  396.  
  397.                                  Example 13-6.
  398.  
  399.                   #include <fastgraf.h>
  400.                   #include <stdio.h>
  401.                   #include <stdlib.h>
  402.                   void main(void);
  403.  
  404.                   #define DELAY 2
  405.                   #define JUMP  4
  406.  
  407.                   void main()
  408.                   {
  409.                      int i;
  410.                      int old_mode;
  411.  
  412.                      fg_initpm();                                              
  413.                                             Chapter 13:  Special Effects   295
  414.  
  415.                      old_mode = fg_getmode();
  416.                      fg_setmode(fg_automode());
  417.  
  418.                      fg_setcolor(15);
  419.                      fg_move(0,JUMP);
  420.                      fg_draw(fg_getmaxx(),JUMP);
  421.                      fg_draw(fg_getmaxx(),fg_getmaxy()-JUMP);
  422.                      fg_draw(0,fg_getmaxy()-JUMP);
  423.                      fg_draw(0,JUMP);
  424.                      fg_waitkey();
  425.  
  426.                      for (i = 0; i < 6; i++) {
  427.                         fg_pan(0,JUMP);
  428.                         fg_waitfor(DELAY);
  429.                         fg_pan(0,0);
  430.                         fg_waitfor(DELAY);
  431.                         }
  432.  
  433.                      fg_setmode(old_mode);
  434.                      fg_reset();
  435.                   }
  436.  
  437.  
  438.      The real power of fg_pan becomes clear when it is used with fg_resize to
  439. perform smooth panning. Recall from Chapter 8 that fg_resize changes the video
  440. page dimensions in native EGA and VGA graphics modes (modes 13 to 18), the
  441. extended VGA graphics modes (20 to 23), and the SVGA graphics modes (24 to
  442. 29). We'll now present an example that shows how to use these two routines to
  443. perform panning in the low-resolution EGA graphics mode (mode 13). The method
  444. it uses also would work in any mode that supports video page resizing.
  445.  
  446.      Example 13-7 begins by establishing the video mode and then immediately
  447. calls fg_resize to increase the video page size to 640x400 pixels. Thus, the
  448. video page is now four times its original size. Following this, the program
  449. fills the page (the entire page, not just what is displayed) with a bright
  450. green rectangle with a white border around it. It then displays the message
  451. "Press arrow keys to pan" in the center of the 640x400 page.
  452.  
  453.      The main part of the program is a loop that accepts keystrokes and calls
  454. fg_pan to perform the panning one pixel at a time. When you press any of the
  455. four arrow keys, the program adjusts the x and y coordinates for the screen
  456. origin as directed. For example, pressing the up arrow key scrolls the screen
  457. upward one pixel. When we reach the edge of the video page, the program
  458. prevents further scrolling in that direction. This process continues until you
  459. press the Escape key, at which time the program restores the original video
  460. mode and screen attributes before exiting.
  461.  
  462.                                  Example 13-7.
  463.  
  464.                   #include <fastgraf.h>
  465.                   void main(void);
  466.  
  467.                   void main()
  468.                   {
  469.                      unsigned char key, aux;
  470.                      int old_mode;                                             
  471. 296   Fastgraph User's Guide
  472.  
  473.                      int x, y;
  474.  
  475.                      fg_initpm();
  476.                      old_mode = fg_getmode();
  477.                      fg_setmode(13);
  478.                      fg_resize(640,400);
  479.  
  480.                      fg_setcolor(2);
  481.                      fg_rect(0,fg_getmaxx(),0,fg_getmaxy());
  482.                      fg_setcolor(15);
  483.                      fg_box(0,fg_getmaxx(),0,fg_getmaxy());
  484.                      fg_justify(0,0);
  485.                      fg_move(320,200);
  486.                      fg_print("Press arrow keys to pan.",24);
  487.  
  488.                      x = 0;
  489.                      y = 0;
  490.  
  491.                      do {
  492.                         fg_getkey(&key,&aux);
  493.                         if (aux == 72 && y < 200)
  494.                            y++;
  495.                         else if (aux == 75 && x < 320)
  496.                            x++;
  497.                         else if (aux == 77 && x > 0)
  498.                            x--;
  499.                         else if (aux == 80 && y > 0)
  500.                            y--;
  501.                         fg_pan(x,y);
  502.                      } while (key != 27);
  503.  
  504.                      fg_setmode(old_mode);
  505.                      fg_reset();
  506.                   }
  507.  
  508.  
  509.  
  510. Panning With Virtual Buffers
  511.  
  512.      The fg_pan routine is not suitable for panning a large image through a
  513. small window because it affects the entire screen. However, you can achieve
  514. this type of panning by storing the large image on an off-screen video page or
  515. in a virtual buffer and then copy the appropriate portions of it to the fixed
  516. window on the visual page. Example 13-8 illustrates this technique using a
  517. virtual buffer.
  518.  
  519.                                  Example 13-8.
  520.  
  521.                   #include <fastgraf.h>
  522.                   void main(void);
  523.  
  524.                   #ifdef FG32
  525.                   char buffer[64000];
  526.                   #else
  527.                   char huge buffer[64000];
  528.                   #endif                                                       
  529.                                             Chapter 13:  Special Effects   297
  530.  
  531.  
  532.                   void main()
  533.                   {
  534.                      unsigned char key, aux;
  535.                      int handle;
  536.                      int old_mode;
  537.                      int x, y;
  538.  
  539.                      fg_initpm();
  540.                      old_mode = fg_getmode();
  541.                      fg_setmode(19);
  542.  
  543.                      fg_vbinit();
  544.                      handle = fg_vbdefine(buffer,320,200);
  545.                      fg_vbopen(handle);
  546.                      fg_loadpcx("CORAL.PCX",0);
  547.                      fg_vbclose();
  548.  
  549.                      fg_setcolor(2);
  550.                      fg_fillpage();
  551.                      fg_setcolor(15);
  552.                      fg_box(111,208,69,130);
  553.                      fg_locate(3,8);
  554.                      fg_text("Press arrow keys to pan.",24);
  555.  
  556.                      x = 112;
  557.                      y = 129;
  558.                      fg_vbpaste(x,x+95,y-59,y,112,129);
  559.  
  560.                      do {
  561.                         fg_getkey(&key,&aux);
  562.                         if (aux == 72 && y < 199)
  563.                            y++;
  564.                         else if (aux == 75 && x < 223)
  565.                            x++;
  566.                         else if (aux == 77 && x > 0)
  567.                            x--;
  568.                         else if (aux == 80 && y > 59)
  569.                            y--;
  570.                         fg_vbpaste(x,x+95,y-59,y,112,129);
  571.                      } while (key != 27);
  572.  
  573.                      fg_setmode(old_mode);
  574.                      fg_reset();
  575.                   }
  576.  
  577.  
  578.      Example 13-8 loads our familiar CORAL.PCX image into a 320x200 virtual
  579. buffer. It then sets up a 96x60 region in the middle of the visual page that
  580. will serve as a window into the larger CORAL.PCX image (this region is bounded
  581. horizontally by x=112 and x=207 and vertically by y=70 and y=129). The first
  582. call to fg_vbpaste copies the 96x60 center portion of the virtual buffer to
  583. the visual page window. The panning loop is similar to that of example 13-7,
  584. except it uses fg_vbpaste to update the window contents. Pressing the arrow
  585. keys increments or decrements the coordinates defining the source region in    
  586. 298   Fastgraph User's Guide
  587.  
  588. the virtual buffer. Also, note how we've adjusted the if statements to prevent
  589. fg_vbpaste from accessing pixels outside the virtual buffer.
  590.  
  591.  
  592. Split Screen
  593.  
  594.      Fastgraph provides split screen support for EGA, VGA, MCGA, and XVGA
  595. graphics modes (modes 13 through 23) for applications running on VGA or SVGA
  596. systems. When a split screen is enabled, the top portion of the screen (rows 0
  597. through n-1, where n is the pixel row at which the split screen takes effect)
  598. will contain a subset of the visual video page. The bottom portion (starting
  599. at row n) will contain the first fg_getmaxy()-n+1 rows of video page 0. For
  600. example, suppose we're using a 200-line graphics mode and we enable a split
  601. screen at row 180. If page 1 is the visual video page, the first 180 lines of
  602. the screen would be displayed from rows 0 to 179 from page 1, and the last 20
  603. lines would be displayed from rows 0 to 19 of page 0. A split screen
  604. environment is useful for maintaining a static image, such as a scoreboard or
  605. status box, at the bottom of the screen while scrolling the top portion.
  606.  
  607.      Example 13-9 demonstrates a typical split screen operation in the 320x200
  608. XVGA graphics mode (mode 20). In this example, we'll assume we want to have a
  609. status box occupying the last 20 rows (rows 180 to 199) of the screen, while
  610. the upper 180 rows (0 to 179) will be scrolled vertically. The program begins
  611. by setting the video mode and then calling fg_measure to compute a processor-
  612. dependent delay value for slowing down the scrolling (this technique is
  613. further explained in Chapter 16).
  614.  
  615.      In mode 20, video memory is structured as four 320x200 physical pages.
  616. Page 1 is not visible when we draw the blue box with the white border, so we
  617. don't see it until call fg_setvpage to make page 1 the visual page. This of
  618. course also makes page 0 invisible, so we don't see the 20-pixel high red
  619. hollow box when we draw it on page 0.
  620.  
  621.      Once we've drawn what we've needed on pages 0 and 1, we activate the
  622. split screen by calling fg_split. The single parameter passed to fg_split is
  623. the screen row at which the split screen takes effect, or put another way, the
  624. number of rows in the top portion of the screen. In example 13-9 we call
  625. fg_split(180), so the first 180 rows of page 1 will appear at the top of the
  626. screen, and the first 20 rows of page 0 will appear at the bottom.
  627.  
  628.      Now we're ready to scroll the upper part of the screen (which is now page
  629. 1). Fastgraph's fg_pan routine is suitable for this purpose. We achieve the
  630. upward scrolling by incrementing the fg_pan y coordinate in a loop. We achieve
  631. the downward scrolling by decrementing the y coordinate. We must call fg_stall
  632. (or use another similar method) to force a brief delay between iterations. If
  633. we didn't do this, the full 20-row scrolling would appear almost instantly,
  634. thus losing the scrolling effect. Note that we couldn't use fg_pan to scroll
  635. the upper part of the screen in this manner without setting up a split screen
  636. environment. That's because by default fg_pan applies to the entire screen.
  637. Using the split screen provides us with two independent video pages, and when
  638. page 1 is the active video page, fg_pan doesn't touch page 0.
  639.  
  640.                                  Example 13-9.
  641.  
  642.     #include <fastgraf.h>
  643.     void main(void);                                                           
  644.                                             Chapter 13:  Special Effects   299
  645.  
  646.  
  647.     void main()
  648.     {
  649.        int delay, y;
  650.  
  651.        /* initialize the video environment */
  652.  
  653.        fg_initpm();
  654.        fg_setmode(20);
  655.  
  656.        /* define a processor-dependent panning delay */
  657.  
  658.        delay = fg_measure() / 16;
  659.  
  660.        /* draw a blue box with a white border on page 1 */
  661.  
  662.        fg_setpage(1);
  663.        fg_setcolor(9);
  664.        fg_fillpage();
  665.        fg_setcolor(15);
  666.        fg_box(0,319,0,199);
  667.        fg_move(160,100);
  668.        fg_justify(0,0);
  669.        fg_print("This is page 1",14);
  670.  
  671.        /* display what we just drew on page 1 */
  672.  
  673.        fg_setvpage(1);
  674.        fg_waitkey();
  675.  
  676.        /* draw a red hollow box at the top of page 0 (now invisible) */
  677.  
  678.        fg_setpage(0);
  679.        fg_setcolor(12);
  680.        fg_box(0,319,0,19);
  681.        fg_setcolor(15);
  682.        fg_move(160,10);
  683.        fg_print("SPLIT SCREEN",12);
  684.  
  685.        /* activate the split screen environment, making the first    */
  686.        /* 20 lines of page 0 appear at the bottom of the screen,     */
  687.        /* and making the first 180 lines of page 1 appear at the top */
  688.  
  689.        fg_split(180);
  690.        fg_waitkey();
  691.  
  692.        /* pan upward in one-line increments, displaying the rest of */
  693.        /* page 1                                                    */
  694.  
  695.        fg_setpage(1);
  696.        for (y = 0; y <= 20; y++)
  697.        {
  698.           fg_pan(0,y);
  699.           fg_stall(delay);
  700.        }
  701.        fg_waitkey();                                                           
  702. 300   Fastgraph User's Guide
  703.  
  704.  
  705.        /* pan back down in one-line increments to the original position */
  706.  
  707.        for (y = 20; y >= 0; y--)
  708.        {
  709.           fg_pan(0,y);
  710.           fg_stall(delay);
  711.        }
  712.        fg_waitkey();
  713.  
  714.        /* restore 80x25 text mode and exit */
  715.  
  716.        fg_setmode(3);
  717.        fg_reset();
  718.     }
  719.  
  720.  
  721.      To switch from a split screen environment back to a "single page"
  722. environment, call fg_split with a row parameter equal to the vertical screen
  723. resolution for the current video mode.
  724.  
  725.  
  726. Summary of Special Effects Routines
  727.  
  728.      This section summarizes the functional descriptions of the Fastgraph
  729. routines presented in this chapter. More detailed information about these
  730. routines, including their arguments and return values, may be found in the
  731. Fastgraph Reference Manual.
  732.  
  733.      FG_FADEIN incrementally replaces the visual page contents with the hidden
  734. page contents. This routine has no effect in text video modes and is not
  735. applicable to virtual buffers.
  736.  
  737.      FG_FADEOUT incrementally replaces the visual page contents with pixels of
  738. the current color. This routine has no effect in text video modes and is not
  739. applicable to virtual buffers.
  740.  
  741.      FG_PAN changes the screen origin (the upper left corner of the screen) to
  742. the specified screen space coordinates. This routine has no effect in text
  743. video modes and is not applicable to virtual buffers.
  744.  
  745.      FG_PANW is the world space version of the fg_pan routine.
  746.  
  747.      FG_RESIZE changes the dimensions of a video page in EGA and VGA graphics
  748. modes. This routine is disabled when a virtual buffer is active.
  749.  
  750.      FG_SCROLL vertically scrolls a region of the active video page. The
  751. scrolling may be done either up or down, using either an end-off or circular
  752. method. Circular scrolling uses part of the hidden page as a temporary
  753. workspace. This routine is not functional when a virtual buffer is active.
  754.  
  755.      FG_SPLIT enables or disables a split screen environment in EGA, VGA,
  756. MCGA, and XVGA graphics modes.
  757.