home *** CD-ROM | disk | FTP | other *** search
/ Simtel MSDOS 1996 September / Simtel-MSDOS-Sep1996-CD2.iso / disc2 / c / sine.c < prev    next >
C/C++ Source or Header  |  1986-05-31  |  6KB  |  293 lines

  1. 29-May-86 07:33:11-PDT,6294;000000000001
  2. Return-Path: <mtc@ATHENA.MIT.EDU>
  3. Received: FROM ATHENA.MIT.EDU BY USC-ISIB.ARPA WITH TCP ; 29 May 86 07:32:45 PDT
  4. Received: by ATHENA (5.45/4.7)
  5.     id AA04243; Thu, 29 May 86 10:31:56 EDT
  6. Received: by JASON (5.45/4.7)
  7.     id AA09933; Thu, 29 May 86 10:32:11 EDT
  8. Message-Id: <8605291432.AA09933@JASON>
  9. To: info-ibmpc@usc-isib
  10. Subject: SINE.C from Dr Dobbs 5/86
  11. Date: Thu, 29 May 86 10:32:08 -0500
  12. From: Mark Colan <mtc@ATHENA.MIT.EDU>
  13.  
  14. Hi,
  15.  
  16. I typed in the SINE.C example program from Dr Dobb's Journal, May 1986.
  17. The article describes a simple plotting routine for the IBM EGA in
  18. high resolution (640x350) graphics mode.  Author is Nabajyoti Barkakati.
  19.  
  20. The program typed in is nearly but not EXACTLY verbatum.
  21. Execution of the program illustrates the slowness of drawing dots using
  22. the BIOS interface.
  23.  
  24. Enjoy!
  25.  
  26. Mark Colan
  27. MIT Project Athena
  28.  
  29. --------------------------SINE.C BEGINS HERE----------------------------
  30. /*
  31.  * SINE.C
  32.  *
  33.  * Plot sin(x) vs x on an enhanced color display with an IBM enhanced
  34.  * graphics adapter in the high resolution mode.  Purpose is to test
  35.  * the video routines.
  36.  */
  37. #include <stdio.h>
  38. #include <math.h>
  39.  
  40. #define BLUE       1                /* Color number 1 is BLUE        */
  41. #define RED       4                /* Color number 4 is RED        */
  42. #define BOTTOM       4                /* Bottom margin                */
  43. #define TOP     345                /* Top margin                    */
  44. #define LEFT       4                /* Left margin                    */
  45. #define RIGHT     635                /* Right margin                    */
  46. #define TWOPI       6.283            /* approximate value of 2*pi    */
  47. #define MAXPNT    100                /* Points on the sinusoid        */
  48.  
  49. main()
  50. {
  51.     int i, x, y, oldx, oldy, midpoint;
  52.     double xd, yd, ampl;
  53.  
  54.     v_init(RED);                /* initialize the display        */
  55.  
  56.     midpoint = (TOP - BOTTOM)/2;
  57.     ampl = (double)midpoint - (double)BOTTOM;
  58.  
  59.     oldx = LEFT;
  60.     oldy = midpoint;
  61.  
  62.     for (i=0; i<=MAXPNT; i++) {
  63.         yd = ampl * sin(TWOPI * ((double)i)/((double)MAXPNT));
  64.         xd = ((double)RIGHT - (double)LEFT) * (double)i / (double)MAXPNT;
  65.         x = LEFT + (int)xd;
  66.         y = midpoint + (int)yd;
  67.  
  68.         /*
  69.          * Draw a line from the old point to the new point
  70.          */
  71.         v_draw(oldx, oldy, x, y, BLUE);
  72.  
  73.         /*
  74.          * save the new coordinates
  75.          */
  76.         oldx = x;
  77.         oldy = y;
  78.     }
  79.  
  80.     /*
  81.      * Draw a box around the plot
  82.      */
  83.     v_draw(LEFT,    BOTTOM,    RIGHT,    BOTTOM,    BLUE);
  84.     v_draw(RIGHT,    BOTTOM,    RIGHT,    TOP,    BLUE);
  85.     v_draw(RIGHT,    TOP,    LEFT,    TOP,    BLUE);
  86.     v_draw(LEFT,    TOP,    LEFT,    BOTTOM,    BLUE);
  87.  
  88.     exit(0);
  89. }
  90.  
  91.  
  92. /*
  93.  * VIDEO.C
  94.  *
  95.  * This file contains the video display modules.  Uses the int86 function of 
  96.  * Lattice C 2.15 to draw graphs on an enhanced color display with the IBM
  97.  * Enhanced Graphics Adapter.
  98.  *
  99.  * by N. Barkakati, Silver Sprint, MD 20904
  100.  */
  101.  
  102. #include <dos.h>
  103.  
  104. #define    void    int
  105. #define    EGAMODE    16                /* ROM BIOS call: EGA hi res (640x350) mode */
  106. #define MAXROW    24
  107. #define MAXCOLUMN 79
  108. #define MAXYDOT    349                /* max rows on EGA */
  109. #define MAXXDOT    639                /* max columns on EGA */
  110.  
  111. #define BIOS_VIDEO 16            /* BIOS Video service interrupt number */
  112. #define SETMODE    0                /* Service: set video mode */
  113. #define SETCOLOR    11            /* Service: set color palette */
  114. #define WRITE_PIX    12            /* Service: write pixel */
  115.  
  116. static union REGS xr,yr;        /* see dos.h for explanation */
  117.  
  118. /*
  119.  * v _ i n i t
  120.  *
  121.  * Initialize the display:
  122.  *        put EGA into high-resolution mode
  123.  *         set background color
  124.  */
  125. void v_init(bgcolor)
  126.     int bgcolor;
  127. {
  128.     /*
  129.      * set high resolution mode
  130.      */
  131.     xr.h.ah = SETMODE;
  132.     xr.h.al = EGAMODE;
  133.     int86(BIOS_VIDEO, &xr, &yr);
  134.  
  135.     /*
  136.      * set background color
  137.      */
  138.     xr.h.ah = SETCOLOR;
  139.     xr.h.bh = 0;
  140.     xr.h.bl = bgcolor;
  141.     int86(BIOS_VIDEO, &xr, &yr);
  142. }
  143.  
  144. /*
  145.  * v _ d r a w 
  146.  *
  147.  * Draw a line of specified color between the two points (x1,y1)
  148.  * and (x2,y2).  Uses Bresenham's Algorithm described in J.D. Foley
  149.  * and A Van Dam, FUNDAMENTALS OF INTERACTIVE COMPUTER GRAPHICS,
  150.  * Addison-Wesley, 1982, pp.433-435.
  151.  */
  152. void v_draw(x1, y1, x2, y2, color)
  153.     int x1, y1, x2, y2, color;
  154. {
  155.     int dx, dy, incr1, incr2, incr3, d, x, y, xend, yend;
  156.  
  157.     dx = abs(x2-x1);
  158.     dy = abs(y2-y1);
  159.  
  160.     if (dy <= dx) {
  161.         /*
  162.          * absolute value of slope of line is less than 1 
  163.          */
  164.         if (x1 > x2) {
  165.             /*
  166.              * start at point with smaller x coordinate
  167.              */
  168.             x = x2;
  169.             y = y2;
  170.             xend = x1;
  171.             dy = y1-y2;
  172.         } else {
  173.             x = x1;
  174.             y = y1;
  175.             xend = x2;
  176.             dy = y2-y1;
  177.         }
  178.         d = (2 * dy) - dx;
  179.         incr1 = 2 * dy;
  180.         incr2 =  2 * (dy - dx);
  181.         incr3 = 2 * (dy + dx);
  182.         putdot(x, y, color);
  183.         while (x++ < xend) {
  184.             if (d >= 0) {
  185.                 if (dy <= 0) {
  186.                     /*
  187.                      * negative or zero slope
  188.                      */
  189.                     d += incr1;
  190.                 } else {
  191.                     /*
  192.                      * positive slope
  193.                      */
  194.                     y++;
  195.                     d += incr2;
  196.                 }
  197.             } else {
  198.                 if (dy >= 0) {
  199.                     /*
  200.                      * negative or zero slope
  201.                      */
  202.                     d += incr1;
  203.                 } else {
  204.                     /*
  205.                      * positive slope
  206.                      */
  207.                     y--;
  208.                     d += incr3;
  209.                 }
  210.             }
  211.             putdot(x, y, color);
  212.         }
  213.     } else {
  214.         /* 
  215.          * absolute value of slope is greater than 1 
  216.          */
  217.         if (y1 > y2) {
  218.             /*
  219.              * start with smaller y coordinate
  220.              */
  221.             y = y2;
  222.             x = x2;
  223.             yend = y1;
  224.             dx = x1 - x2;
  225.         } else {
  226.             y = y1;
  227.             x = x1;
  228.             yend = y2;
  229.         }
  230.         d = (2 * dx) - dy;
  231.         incr1 = 2 * dx;
  232.         incr2 = 2 * (dx - dy);
  233.         incr3 = 2 * (dx + dy);
  234.         putdot(x, y, color);
  235.         while (y < yend) {
  236.             y++;
  237.             if (d >= 0) {
  238.                 if (dx <= 0) {
  239.                     /*
  240.                      * negative or zero slope
  241.                      */
  242.                     d += incr1;
  243.                 } else {
  244.                     /*
  245.                      * positive slope
  246.                      */
  247.                     x++;
  248.                     d += incr2;
  249.                 }
  250.             } else {
  251.                 if (dx >= 0) {
  252.                     /*
  253.                      * negative or zero slope
  254.                      */
  255.                      d += incr1;
  256.                 } else {
  257.                     /*
  258.                      * positive slope
  259.                      */
  260.                     d += incr3;
  261.                     x--;
  262.                 }
  263.             }
  264.             putdot(x, y, color);
  265.         }
  266.     }
  267. }
  268.  
  269. /*
  270.  * p u t d o t
  271.  *
  272.  * Put a dot of specified color at location (x,y) on screen.  Check if
  273.  * dot coordinates are within screen bounds.
  274.  *
  275.  *                    ^ y-axis
  276.  *                    |_______
  277.  * Convention:        |        |            Origin at lower left corner of screen
  278.  *                    |        |
  279.  *                    |_______|__ x-axis
  280.  *                (0,0)
  281.  */
  282. void putdot(x, y, color)
  283.     int x, y, color;
  284. {
  285.     if ( x<0 | x>MAXXDOT | y<0 | y>MAXYDOT ) return;
  286.  
  287.     xr.x.dx = MAXYDOT - y;
  288.     xr.x.cx = x;
  289.     xr.h.ah = WRITE_PIX;
  290.     xr.h.al = color;
  291.     int86( BIOS_VIDEO, &xr, &yr );
  292. }
  293.