home *** CD-ROM | disk | FTP | other *** search
/ Media Share 13 / mediashare_13.zip / mediashare_13 / ZIPPED / PROGRAM / SNIP9404.ZIP / BRESNHAM.C < prev    next >
C/C++ Source or Header  |  1994-04-03  |  4KB  |  156 lines

  1. /*
  2. ** Public Domain mode 13h Bresenham line/circle algorithms
  3. ** By Brian Dessent
  4. **
  5. ** Written for Borland, modified for others by Bob Stout
  6. */
  7.  
  8. #include <stdio.h>
  9. #include <stdlib.h>
  10. #include <dos.h>
  11. #include <conio.h>
  12. #include <time.h>       /* for randomize  */
  13.  
  14. #ifndef __TURBOC__
  15.  #define random(num) (int)(((rand())*(long)(num))/(((long)RAND_MAX)+1))
  16.  #define randomize() srand((unsigned)time(NULL)|1)
  17. #else
  18. #endif
  19.  
  20. #ifndef MK_FP
  21.  #define MK_FP(seg,offset) \
  22.      ((void far *)(((unsigned long)(seg)<<16) | (unsigned)(offset)))
  23. #endif
  24.  
  25. #define SCREEN_WIDTH 320
  26. #define SCREEN_HEIGTH 200
  27. #define MAX_X (SCREEN_WIDTH-1)
  28. #define MAX_Y (SCREEN_HEIGTH-1)
  29.  
  30. /* prototypes */
  31.  
  32. void setmode(int mode);
  33. void plotdot(int x, int y, char c);
  34. void bresenham_line(int x, int y, int x2, int y2, char c);
  35. void bresenham_circle(int xc, int yc, int r, char c);
  36. void main(void);
  37.  
  38. /* code begins */
  39.  
  40. /* uses BIOS to set video mode */
  41.  
  42. void setmode(int mode)
  43. {
  44.       union REGS r;
  45.  
  46.       r.x.ax = mode;
  47.       int86(0x10, &r, &r);
  48. }
  49.  
  50.  
  51. /* plots a dot at (x, y) with color c */
  52.  
  53. void plotdot(int x, int y, char c)
  54. {
  55.       register char far *addr;
  56.  
  57.       if(x < 0 || x > MAX_X || y < 0 || y > MAX_Y)
  58.             return;
  59.  
  60.       addr = MK_FP(0xa000, (SCREEN_WIDTH * y) + x);
  61.       *addr = c;
  62. }
  63.  
  64.  
  65. /* draws a line from (x, y) to (x2, y2) in color c */
  66.  
  67. void bresenham_line(int x, int y, int x2, int y2, char c)
  68. {
  69.       int i, steep = 0, sx, sy, dx, dy, e;
  70.  
  71.       dx = abs(x2 - x);
  72.       sx = ((x2 - x) > 0) ? 1 : -1;
  73.       dy = abs(y2 - y);
  74.       sy = ((y2 - y) > 0) ? 1 : -1;
  75.  
  76.       if(dy > dx)
  77.       {
  78.             steep = 1;
  79.             x ^= y;  /* swap x and y */
  80.             y ^= x;
  81.             x ^= y;
  82.             dx ^= dy; /* swap dx and dy */
  83.             dy ^= dx;
  84.             dx ^= dy;
  85.             sx ^= sy; /* swap sx and sy */
  86.             sy ^= sx;
  87.             sx ^= sy;
  88.       }
  89.  
  90.       e = 2 * dy - dx;
  91.       for(i = 0;i < dx;i++)
  92.       {
  93.             if(steep)
  94.                   plotdot(y, x, c);
  95.             else  plotdot(x, y, c);
  96.             while(e >= 0)
  97.             {
  98.                   y += sy;
  99.                   e -= 2 * dx;
  100.             }
  101.             x += sx;
  102.             e += 2 * dy;
  103.       }
  104.       plotdot(x2, y2, c);
  105. }
  106.  
  107. /* draws a circle at (xc, yc) with radius r in color c
  108. **
  109. ** note: the scaling factor of (SCREEN_WIDTH / SCREEN_HEIGTH) is used when
  110. ** updating d.  This makes round circles.  If you want ellipses, you can
  111. ** modify that ratio.
  112. */
  113.  
  114. void bresenham_circle(int xc, int yc, int r, char c)
  115. {
  116.       int x = 0, y = r, d = 2 * (1 - r);
  117.  
  118.       while(y > 0)
  119.       {
  120.             plotdot(xc + x, yc + y, c);
  121.             plotdot(xc + x, yc - y, c);
  122.             plotdot(xc - x, yc + y, c);
  123.             plotdot(xc - x, yc - y, c);
  124.             if(d + y > 0)
  125.             {
  126.                   y -= 1;
  127.                   d -= (2 * y * SCREEN_WIDTH / SCREEN_HEIGTH) - 1;
  128.             }
  129.             if(x > d)
  130.             {
  131.                   x += 1;
  132.                   d += (2 * x) + 1;
  133.             }
  134.       }
  135. }
  136.  
  137. /* draws random lines and circles until a key is pressed in mode 13h */
  138. /* (draws in colors 0 - 63 only) */
  139.  
  140. void main(void)
  141. {
  142.       int i=0;
  143.  
  144.       randomize();
  145.       setmode(0x13);
  146.       while(!kbhit())
  147.       {
  148.             bresenham_line(random(SCREEN_WIDTH), random(SCREEN_HEIGTH),
  149.                   random(SCREEN_WIDTH), random(SCREEN_HEIGTH), i = ++i % 64);
  150.             bresenham_circle(random(SCREEN_WIDTH), random(SCREEN_HEIGTH),
  151.                   random(50), i = ++i % 64);
  152.       }
  153.       getch();
  154.       setmode(0x03);  /* set to color text mode, clearing screen */
  155. }
  156.