home *** CD-ROM | disk | FTP | other *** search
/ Graphics Plus / Graphics Plus.iso / general / raytrace / radiance / simplerd.lha / simplerad / FinalFTP / Conv / Off / off2pat.c < prev   
Encoding:
C/C++ Source or Header  |  1992-05-26  |  8.2 KB  |  275 lines

  1. /**********************************************************************/
  2. /* off2pat.c                                                          */
  3. /*                                                                    */
  4. /* Filter for converting from OFF to radiosity patch format           */
  5. /* Takes one OFF geometry input file as input at a time and outputs   */
  6. /* to stdout.                                                         */
  7. /*                                                                    */
  8. /* Copyright (C) 1992, Bernard Kwok                                   */
  9. /* All rights reserved.                                               */
  10. /* Revision 1.0                                                       */
  11. /* May, 1992                                                          */
  12. /**********************************************************************/
  13. #include <stdio.h>
  14. #include <math.h>
  15.  
  16. typedef float Vector[3];
  17. typedef struct {
  18.   int num_vert;
  19.   int vert_id[8];
  20. } Polygon;
  21. typedef struct {
  22.   int num_vert;
  23.   int num_polys;
  24.   int num_edges;
  25.   Vector verts[7500];
  26.   Polygon *polys;
  27. } Off_object;
  28.  
  29. /**********************************************************************/
  30. Off_object off_object;
  31. FILE *off_file;                   /* off input file */
  32. char *off_filename;               /* off filename */
  33. FILE *pat_file;                   /* pat output file */
  34. char *pat_filename;               /* pat filename */
  35. char *ProgName = "off2pat";
  36. int debug = 0;
  37. int reverse_norms = 0;
  38.  
  39. /**********************************************************************/
  40. /* Calculate normal from 3 patch points */
  41. /**********************************************************************/
  42. void calc_norm(p1, p2, p3, n)
  43.      Vector p1, p2, p3;
  44.      double n[3];
  45. {
  46.   double u[3], v[3];
  47.   double length;
  48.   int i;
  49.  
  50.   for (i=0;i<3;i++) {
  51.     u[i] = p2[i] - p1[i];
  52.     v[i] = p3[i] - p1[i];
  53.   }
  54.   n[0] = u[1]*v[2] - u[2]*v[1]; 
  55.   n[1] = u[2]*v[0] - u[0]*v[2]; 
  56.   n[2] = u[0]*v[1] - u[1]*v[0]; 
  57.  
  58.   if ((length = n[0]*n[0] + n[1]*n[1] + n[2]*n[2]) <= 0.0) {
  59.     printf("length %g too small, not normalizing\n", length);
  60.     printf("u = %g,%g,%g; v=%g,%g,%g; n=%g,%g,%g\n", u[0],u[1],u[2],
  61.        v[0],v[1],v[2], n[0],n[1],n[2]);
  62.   } else {
  63.     length = sqrt(length);
  64.     n[0] = n[0] / length;
  65.     n[1] = n[1] / length;
  66.     n[2] = n[2] / length;
  67.   }
  68.   
  69.   if (reverse_norms) {
  70.     n[0] = -n[0]; n[1] = -n[1]; n[2] = -n[2];
  71.   }
  72.   /* printf("Length = %g\n",length);  
  73.      printf("Norm.Normal = %g,%g,%g\n", n[0],n[1],n[2]); */
  74. }
  75.  
  76. /**********************************************************************/
  77. /* Output polygon  for object                                         */
  78. /**********************************************************************/
  79. void Write_pat_poly(poly, poly_id)
  80.      Polygon poly;
  81.      int poly_id;
  82. {
  83.   int k;
  84.   double norm[3];
  85.   Vector vert;
  86.   
  87.   /* Calculate and output patch normals */
  88.   calc_norm(off_object.verts[(poly.vert_id[0]-1)],
  89.          off_object.verts[(poly.vert_id[1]-1)],
  90.          off_object.verts[(poly.vert_id[2]-1)],
  91.          norm);
  92.   printf("    Patch norm%d %d {", poly_id, poly.num_vert);
  93.   for (k=0;k<poly.num_vert;k++)
  94.     printf(" { %g %g %g }", norm[0], norm[1], norm[2]);
  95.   printf(" }\n");
  96.   
  97.   /* Output patch vertices */
  98.   printf("    Patch vert%d %d {", poly_id, poly.num_vert);
  99.   for (k=0;k<poly.num_vert;k++) {
  100.     vert[0] = off_object.verts[(poly.vert_id[k]-1)][0];
  101.     vert[1] = off_object.verts[(poly.vert_id[k]-1)][1];
  102.     vert[2] = off_object.verts[(poly.vert_id[k]-1)][2];
  103.     printf(" { %g %g %g }", vert[0], vert[1], vert[2]);
  104.   }
  105.   printf(" }\n");
  106. }
  107.  
  108. /**********************************************************************/
  109. /* Output the object in pat format */
  110. /**********************************************************************/
  111. void Write_pat_header(namePrimitive, noObject)
  112.      char *namePrimitive;        /* name of the primitive */
  113.      int noObject;            /* number of the object */
  114. {
  115.   printf("Number objects 1\n");
  116.   /* Output object header definition */
  117.   printf("Object %s%d %s {\n", namePrimitive, noObject, namePrimitive);
  118.  
  119.   /* Output ID matrix column order */
  120.   printf("    OWMatrix mat%s%d { 1. 0. 0. 0. 1. 0. 0. 0. 1. 0. 0. 0. }\n");
  121.   
  122.   /* Output surface properties. Reflectance assumed == colour */
  123.   /* Use default properties for object == pure diffuse */
  124.   printf("    Prop prop%s%d { E{ 0.0 0.0 0.0 } ",
  125.      namePrimitive, noObject);
  126.   printf("p{ 0.0 0.0 0.0 } Kd{ 1.0 } Ks{ 0.0 } \n");
  127.  
  128. }
  129.  
  130. /**********************************************************************/
  131. void Write_pat_footer()
  132. {
  133.   /* End delimiter */
  134.   printf("    }\n");
  135.   printf("}\n");
  136. }
  137.  
  138. /**********************************************************************/
  139. /* Write footer */
  140. /**********************************************************************/
  141. void Write_walk_footer()
  142. {
  143.   /* End delimiter */
  144.   printf("}\n");
  145. }
  146.  
  147. /**********************************************************************/
  148. /* Write header */
  149. /**********************************************************************/
  150. void Write_walk_header()
  151. {
  152.   printf("Number polygons %d\n", off_object.num_polys);
  153. }
  154.  
  155. /**********************************************************************/
  156. void Write_walk_poly(poly, poly_id)
  157.      Polygon poly;
  158.      int poly_id;
  159. {
  160.   int i,j,k;
  161.   double norm[3];
  162.   Vector vert;
  163.  
  164.   /* Print patch label */
  165.   printf("Poly %s%d %d {\n", "poly", poly_id, poly.num_vert);
  166.   
  167.   /* Print colour of patch */
  168.   printf("  B { 1.0 1.0 1.0 }\n");
  169.  
  170.   /* Find and print colour of vertices */
  171.   printf("  vtx_B { ");
  172.   for (j=0;j<poly.num_vert;j++)
  173.     printf("{ 1.0 1.0 1.0 } ");
  174.   printf("}\n");
  175.     
  176.   /* Print normals */
  177.   calc_norm(off_object.verts[(poly.vert_id[0]-1)],
  178.         off_object.verts[(poly.vert_id[1]-1)],
  179.         off_object.verts[(poly.vert_id[2]-1)],
  180.         norm);
  181.   printf("  norm {",i);
  182.   for (j=0;j<poly.num_vert;j++) 
  183.     printf(" { %g %g %g } ", norm[0], norm[1], norm[2]);
  184.   printf("}\n");
  185.     
  186.   /* Print vertices */
  187.   printf("  vert {",i);
  188.   for (j=0;j<poly.num_vert;j++) {
  189.     vert[0] = off_object.verts[(poly.vert_id[j]-1)][0];
  190.     vert[1] = off_object.verts[(poly.vert_id[j]-1)][1];
  191.     vert[2] = off_object.verts[(poly.vert_id[j]-1)][2];
  192.     printf(" { %g %g %g } ", vert[0], vert[1], vert[2]);
  193.   }
  194.   printf("}\n");
  195.  
  196.   printf("}\n");
  197. }
  198.  
  199. /**********************************************************************/
  200. /* Read off file */
  201. /**********************************************************************/
  202. void Read_off(filename)
  203.      char *filename;
  204. {
  205.   int i,j;
  206.   float vvalues[3];
  207.   int poly_id = 0;
  208.   Polygon poly;
  209.  
  210.   if (!(off_file = fopen(filename, "r"))) {
  211.     fprintf(stderr,"%s: cannot read off file %s\n", ProgName, filename);
  212.     exit(1);
  213.   }
  214.   fscanf(off_file,"%d %d %d", 
  215.      &(off_object.num_vert),
  216.      &(off_object.num_polys),
  217.      &(off_object.num_edges));
  218.   if (debug)
  219.     printf("%d %d %d\n", off_object.num_vert, off_object.num_polys,
  220.      off_object.num_edges);
  221.  
  222.   /* Print mesh header */
  223.   printf("    NumMeshes 1\n");
  224.   printf("    Mesh mesh%s%d %d {\n", off_filename, 1, off_object.num_polys);
  225.   
  226.   /* Read vertex info */
  227.   for (i=0;i<off_object.num_vert;i++) {
  228.     fscanf(off_file,"%g %g %g\n", &vvalues[0], &vvalues[1], &vvalues[2]);
  229.     off_object.verts[i][0] = vvalues[0];
  230.     off_object.verts[i][1] = vvalues[1];
  231.     off_object.verts[i][2] = vvalues[2];
  232.     if (debug)
  233.       printf("%g %g %g\n", 
  234.          off_object.verts[i][0],
  235.          off_object.verts[i][1],
  236.          off_object.verts[i][2]);
  237.   }
  238.  
  239.   /* Read polygon info */
  240.   for (i=0;i<off_object.num_polys;i++) {
  241.     fscanf(off_file,"%d", &(poly.num_vert));
  242.     if (debug) printf("%d ", poly.num_vert);
  243.     for (j=0;j<poly.num_vert;j++) {
  244.       fscanf(off_file,"%d", &(poly.vert_id[j]));
  245.       if (debug) printf("%d ", poly.vert_id[j]);
  246.     }
  247.     if (debug) printf("\n");
  248.  
  249.     /* Output polygon */
  250.     /* Write_walk_poly(poly, poly_id++); */
  251.     Write_pat_poly(poly, poly_id++);
  252.   }
  253.   fclose(off_file);
  254. }
  255.  
  256. /**********************************************************************/
  257. /* main */
  258. /**********************************************************************/
  259. main(argc, argv)
  260.      int argc;
  261.      char *argv[];
  262. {
  263.   if (argc < 2) {
  264.     printf("usage: %s off_file [r=0/1]\n", ProgName);
  265.     exit(0);
  266.   }
  267.   off_filename = argv[1];
  268.   reverse_norms = atoi(argv[2]);
  269.  
  270.   Write_pat_header(off_filename, 1);
  271.   /* Write_walk_header(); */
  272.   Read_off(off_filename);
  273.   Write_pat_footer();
  274. }
  275.