home *** CD-ROM | disk | FTP | other *** search
/ Graphics 16,000 / graphics-16000.iso / msdos / fractal / fdesi313 / fdes13s / fdestria.c < prev    next >
Text File  |  1990-01-23  |  7KB  |  239 lines

  1. /*
  2.         Triangle operations
  3. */
  4. #include <graphics.h>
  5. #include <float.h>
  6. #include <math.h>
  7.  
  8. typedef struct {
  9.         float row[3];
  10.         float col[3];
  11.     } triangle;
  12.  
  13. #include "fdesign.h"
  14. #include "fdesequa.h"
  15. #include "fdesfile.h"
  16. #include "fdesmenu.h"
  17. #include "fdesmous.h"
  18. #include "fdesplot.h"
  19.  
  20. /*  ****************************************************************** */
  21. int triangle_new(triangle *t,int tcolor)   /* input triangle coordinates from mouse */
  22. {
  23. int rcode;
  24. mouse_state m;
  25.     rcode = mouse_click_grat(&m);        /* point 1 of triangle */
  26.     if (rcode&0x02) return(rcode);
  27.         setcolor(tcolor);
  28.         (*t).row[0] = m.row;
  29.         (*t).col[0] = m.col;
  30.     outtextxy(m.col,m.row,"A");
  31.     mouse_click_grat(&m);        /* point 2 of triangle */
  32.         (*t).row[1] = m.row;
  33.         setcolor(tcolor);
  34.     outtextxy(m.col,m.row,"B");
  35.         (*t).col[1] = m.col;
  36.         line((*t).col[0],(*t).row[0],(*t).col[1],(*t).row[1]);
  37.     rcode = mouse_click_grat(&m);    /* point 3 of triangle */
  38.         setcolor(tcolor);
  39.         (*t).row[2] = m.row;
  40.         (*t).col[2] = m.col;
  41.     outtextxy(m.col,m.row,"C");
  42.         line((*t).col[1],(*t).row[1],(*t).col[2],(*t).row[2]);
  43.         line((*t).col[2],(*t).row[2],(*t).col[0],(*t).row[0]);
  44.     return(rcode);
  45. }
  46.  
  47. void triangle_show(triangle *t)
  48. {
  49.         line((*t).col[0],(*t).row[0],(*t).col[1],(*t).row[1]);
  50.         outtextxy((*t).col[0],(*t).row[0],"A");
  51.         line((*t).col[1],(*t).row[1],(*t).col[2],(*t).row[2]);
  52.         outtextxy((*t).col[1],(*t).row[1],"B");
  53.         line((*t).col[2],(*t).row[2],(*t).col[0],(*t).row[0]);
  54.         outtextxy((*t).col[2],(*t).row[2],"C");
  55. }
  56.  
  57. /*
  58.     Distance of a point to a point
  59. */
  60. float pt_pt_distance(float x1, float y1, float x2, float y2)
  61. {
  62. float d2;
  63.     d2 = (x1-x2)*(x1-x2) + (y1-y2)*(y1-y2);
  64.     if (d2 == 0.0) return (0.0);
  65.     else return (sqrt(d2));
  66. }
  67. /*
  68.         Return closest triangle corner ( 0 1 or 2 )
  69. */
  70. int triangle_corner(triangle *t, float col, float row)
  71. {
  72. float a,b,c;
  73.     a = pt_pt_distance((*t).row[0],(*t).col[0],row,col);
  74.     b = pt_pt_distance((*t).row[1],(*t).col[1],row,col);
  75.     c = pt_pt_distance((*t).row[2],(*t).col[2],row,col);
  76.         if ((a<b)&&(a<c)) return(0);
  77.         if (b<c) return(1);
  78.         else return(2);
  79. }
  80. /*
  81.     Distance of a point to a line
  82. */
  83. float pt_line_distance(float x, float y, float x1, float y1, float x2, float y2)
  84. {
  85. float a,b,e,c;
  86.     if ((x==x1) && (y==y1)) a = 0.0;
  87.     else a = sqrt((x-x1)*(x-x1)+(y-y1)*(y-y1));
  88.     if ((x==x2) && (y==y2)) b = 0.0;
  89.     else b = sqrt((x-x2)*(x-x2)+(y-y2)*(y-y2));
  90.     if ((x1==x2) && (y1==y2)) e = 0.0;
  91.     else e = sqrt((x1-x2)*(x1-x2)+(y1-y2)*(y1-y2));
  92.     if (e != 0.0)
  93.     {
  94.         c = (b*b - a*a - e*e)/(-2*e);
  95.         if ((a*a-c*c) < 0.0) return(0.0);
  96.         else return(sqrt(a*a-c*c));
  97.     }
  98.     else
  99.         return(a);
  100. }
  101. /*
  102.     Distance of a point to a line SEGMENT
  103.     (to locate nearest triangle edge)
  104. */
  105. float pt_lines_distance(float x, float y, float x1, float y1, float x2, float y2)
  106. {
  107. float a,b,e,c;
  108.     if ((x==x1) && (y==y1)) a = 0.0;
  109.     else a = sqrt((x-x1)*(x-x1)+(y-y1)*(y-y1));
  110.     if ((x==x2) && (y==y2)) b = 0.0;
  111.     else b = sqrt((x-x2)*(x-x2)+(y-y2)*(y-y2));
  112.     if ((x1==x2) && (y1==y2)) e = 0.0;
  113.     else e = sqrt((x1-x2)*(x1-x2)+(y1-y2)*(y1-y2));
  114.     if ((a*a + e*e) < (b*b)) return(a);
  115.     if ((b*b + e*e) < (a*a)) return(b);
  116.     if (e != 0.0)
  117.     {
  118.         c = (b*b - a*a - e*e)/(-2*e);
  119.         if ((a*a-c*c) < 0.0) return(0.0);
  120.         else return(sqrt(a*a-c*c));
  121.     }
  122.     else
  123.         return(a);
  124. }
  125. float pt_triangle_distance(float x, float y, triangle *t)
  126. {
  127. float n1,n2,n3;
  128.         n1 = pt_lines_distance(x,y,(*t).col[0],(*t).row[0],(*t).col[1],(*t).row[1]);
  129.         n2 = pt_lines_distance(x,y,(*t).col[1],(*t).row[1],(*t).col[2],(*t).row[2]);
  130.         n3 = pt_lines_distance(x,y,(*t).col[2],(*t).row[2],(*t).col[0],(*t).row[0]);
  131.     if (n2 < n1) n1 = n2;
  132.     if (n3 < n1) n1 = n3;
  133.     return(n1);
  134. }
  135. /*
  136.     Finds the triangle closest to the point specified.
  137.     Returns the triangle number or -1 if the reference triangle.
  138. */
  139. int pt_closest_triangle(float x, float y)
  140. {
  141. float dist[MAXFUNC];
  142. float dist_ref;
  143. int i;
  144. int best_t;
  145.     dist_ref = pt_triangle_distance(x,y,&triangle0);
  146. /*    gotoxy(1,12); printf("%6f",dist_ref);
  147. */    for (i=0; i<num_triangles; i++)
  148.     {
  149.         dist[i] = pt_triangle_distance(x,y,&triangles[i]);
  150. /*        printf(" %6f",dist[i]);
  151. */    }
  152.     /* find minimum */
  153.     best_t = 0;
  154.     for (i=(num_triangles - 1); i>0; i--)
  155.     {
  156.         if (dist[i] < dist[0])
  157.         {
  158.             dist[0] = dist[i];
  159.             best_t = i;
  160.         }
  161.     }
  162.  
  163.     if (dist_ref < dist[0]) return(-1);
  164.     else return(best_t);
  165. }
  166. /*
  167.     Find triangle area.
  168.     Collapsed triangles (base or height = 0) will have an area assuming
  169.     one pixel width (instead of zero).
  170. */
  171. float triangle_area(triangle *t)
  172. {
  173. float base,height;
  174.     /* area is 1/2 base times height */
  175.         base = pt_pt_distance((*t).col[0],(*t).row[0],(*t).col[1],(*t).row[1]);
  176.         height = pt_line_distance((*t).col[2],(*t).row[2],(*t).col[1],(*t).row[1],
  177.                                 (*t).col[0],(*t).row[0]);
  178.         if (base < 1.0) return(5.0*height);  /* && 3.0 was 1.0 */
  179.         else if (height < 1.0) return(5.0*base); /* && 3.0 was 1.0 */
  180.     else return(0.5*base*height);
  181. }
  182.  
  183. /************************************************************************
  184.     Transformation Check if affine
  185. ************************************************************************/
  186. int transform_affine(triangle *t)    /* return 0 if not affine */
  187. {
  188. float ra,rb,rc;
  189. float a,b,c;
  190.         ra = pt_pt_distance(triangle0.row[0],triangle0.col[0],
  191.                             triangle0.row[1],triangle0.col[1]);
  192.         rb = pt_pt_distance(triangle0.row[1],triangle0.col[1],
  193.                             triangle0.row[2],triangle0.col[2]);
  194.         rc = pt_pt_distance(triangle0.row[2],triangle0.col[2],
  195.                             triangle0.row[0],triangle0.col[0]);
  196.         a = pt_pt_distance((*t).row[0],(*t).col[0],(*t).row[1],(*t).col[1]);
  197.         b = pt_pt_distance((*t).row[1],(*t).col[1],(*t).row[2],(*t).col[2]);
  198.         c = pt_pt_distance((*t).row[2],(*t).col[2],(*t).row[0],(*t).col[0]);
  199.     if (a > ra) return(0);
  200.     if (b > rb) return(0);
  201.     if (c > rc) return(0);
  202.     if ((a == ra) && (b == rb) && (c == rc)) return(0);
  203.     return(1);
  204. }
  205. /* *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** ***
  206.         Find screen limits of Triangles
  207.         (used to re-orient Triangles on screen)
  208.    *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** */
  209. void triangles_limits(float *left,float *up,float *right,float *down)
  210. {
  211.  
  212. int i,j;
  213.         *left = *right = triangle0.col[0];
  214.         *up = *down = triangle0.row[0];
  215.  
  216.         for (i=0; i<3; i++)
  217.         {
  218.                 if (triangle0.row[i] < *up) *up = triangle0.row[i];
  219.                 if (triangle0.row[i] > *down) *down = triangle0.row[i];
  220.                 if (triangle0.col[i] < *left) *left = triangle0.col[i];
  221.                 if (triangle0.col[i] > *right) *right = triangle0.col[i];
  222.         }
  223.         for (j=0; j<num_triangles; j++)
  224.         {
  225.                 for (i=0; i<3; i++)
  226.                 {
  227.                         if (triangles[j].row[i] < *up) *up = triangles[j].row[i];
  228.                         if (triangles[j].row[i] > *down) *down = triangles[j].row[i];
  229.                         if (triangles[j].col[i] < *left) *left = triangles[j].col[i];
  230.                         if (triangles[j].col[i] > *right) *right = triangles[j].col[i];
  231.                 }
  232.         }
  233. }
  234.  
  235.  
  236.  
  237.  
  238.  
  239.