home *** CD-ROM | disk | FTP | other *** search
- /**********************************************************************/
- /* off2pat.c */
- /* */
- /* Filter for converting from OFF to radiosity patch format */
- /* Takes one OFF geometry input file as input at a time and outputs */
- /* to stdout. */
- /* */
- /* Copyright (C) 1992, Bernard Kwok */
- /* All rights reserved. */
- /* Revision 1.0 */
- /* May, 1992 */
- /**********************************************************************/
- #include <stdio.h>
- #include <math.h>
-
- typedef float Vector[3];
- typedef struct {
- int num_vert;
- int vert_id[8];
- } Polygon;
- typedef struct {
- int num_vert;
- int num_polys;
- int num_edges;
- Vector verts[7500];
- Polygon *polys;
- } Off_object;
-
- /**********************************************************************/
- Off_object off_object;
- FILE *off_file; /* off input file */
- char *off_filename; /* off filename */
- FILE *pat_file; /* pat output file */
- char *pat_filename; /* pat filename */
- char *ProgName = "off2pat";
- int debug = 0;
- int reverse_norms = 0;
-
- /**********************************************************************/
- /* Calculate normal from 3 patch points */
- /**********************************************************************/
- void calc_norm(p1, p2, p3, n)
- Vector p1, p2, p3;
- double n[3];
- {
- double u[3], v[3];
- double length;
- int i;
-
- for (i=0;i<3;i++) {
- u[i] = p2[i] - p1[i];
- v[i] = p3[i] - p1[i];
- }
- n[0] = u[1]*v[2] - u[2]*v[1];
- n[1] = u[2]*v[0] - u[0]*v[2];
- n[2] = u[0]*v[1] - u[1]*v[0];
-
- if ((length = n[0]*n[0] + n[1]*n[1] + n[2]*n[2]) <= 0.0) {
- printf("length %g too small, not normalizing\n", length);
- printf("u = %g,%g,%g; v=%g,%g,%g; n=%g,%g,%g\n", u[0],u[1],u[2],
- v[0],v[1],v[2], n[0],n[1],n[2]);
- } else {
- length = sqrt(length);
- n[0] = n[0] / length;
- n[1] = n[1] / length;
- n[2] = n[2] / length;
- }
-
- if (reverse_norms) {
- n[0] = -n[0]; n[1] = -n[1]; n[2] = -n[2];
- }
- /* printf("Length = %g\n",length);
- printf("Norm.Normal = %g,%g,%g\n", n[0],n[1],n[2]); */
- }
-
- /**********************************************************************/
- /* Output polygon for object */
- /**********************************************************************/
- void Write_pat_poly(poly, poly_id)
- Polygon poly;
- int poly_id;
- {
- int k;
- double norm[3];
- Vector vert;
-
- /* Calculate and output patch normals */
- calc_norm(off_object.verts[(poly.vert_id[0]-1)],
- off_object.verts[(poly.vert_id[1]-1)],
- off_object.verts[(poly.vert_id[2]-1)],
- norm);
- printf(" Patch norm%d %d {", poly_id, poly.num_vert);
- for (k=0;k<poly.num_vert;k++)
- printf(" { %g %g %g }", norm[0], norm[1], norm[2]);
- printf(" }\n");
-
- /* Output patch vertices */
- printf(" Patch vert%d %d {", poly_id, poly.num_vert);
- for (k=0;k<poly.num_vert;k++) {
- vert[0] = off_object.verts[(poly.vert_id[k]-1)][0];
- vert[1] = off_object.verts[(poly.vert_id[k]-1)][1];
- vert[2] = off_object.verts[(poly.vert_id[k]-1)][2];
- printf(" { %g %g %g }", vert[0], vert[1], vert[2]);
- }
- printf(" }\n");
- }
-
- /**********************************************************************/
- /* Output the object in pat format */
- /**********************************************************************/
- void Write_pat_header(namePrimitive, noObject)
- char *namePrimitive; /* name of the primitive */
- int noObject; /* number of the object */
- {
- printf("Number objects 1\n");
- /* Output object header definition */
- printf("Object %s%d %s {\n", namePrimitive, noObject, namePrimitive);
-
- /* Output ID matrix column order */
- printf(" OWMatrix mat%s%d { 1. 0. 0. 0. 1. 0. 0. 0. 1. 0. 0. 0. }\n");
-
- /* Output surface properties. Reflectance assumed == colour */
- /* Use default properties for object == pure diffuse */
- printf(" Prop prop%s%d { E{ 0.0 0.0 0.0 } ",
- namePrimitive, noObject);
- printf("p{ 0.0 0.0 0.0 } Kd{ 1.0 } Ks{ 0.0 } \n");
-
- }
-
- /**********************************************************************/
- void Write_pat_footer()
- {
- /* End delimiter */
- printf(" }\n");
- printf("}\n");
- }
-
- /**********************************************************************/
- /* Write footer */
- /**********************************************************************/
- void Write_walk_footer()
- {
- /* End delimiter */
- printf("}\n");
- }
-
- /**********************************************************************/
- /* Write header */
- /**********************************************************************/
- void Write_walk_header()
- {
- printf("Number polygons %d\n", off_object.num_polys);
- }
-
- /**********************************************************************/
- void Write_walk_poly(poly, poly_id)
- Polygon poly;
- int poly_id;
- {
- int i,j,k;
- double norm[3];
- Vector vert;
-
- /* Print patch label */
- printf("Poly %s%d %d {\n", "poly", poly_id, poly.num_vert);
-
- /* Print colour of patch */
- printf(" B { 1.0 1.0 1.0 }\n");
-
- /* Find and print colour of vertices */
- printf(" vtx_B { ");
- for (j=0;j<poly.num_vert;j++)
- printf("{ 1.0 1.0 1.0 } ");
- printf("}\n");
-
- /* Print normals */
- calc_norm(off_object.verts[(poly.vert_id[0]-1)],
- off_object.verts[(poly.vert_id[1]-1)],
- off_object.verts[(poly.vert_id[2]-1)],
- norm);
- printf(" norm {",i);
- for (j=0;j<poly.num_vert;j++)
- printf(" { %g %g %g } ", norm[0], norm[1], norm[2]);
- printf("}\n");
-
- /* Print vertices */
- printf(" vert {",i);
- for (j=0;j<poly.num_vert;j++) {
- vert[0] = off_object.verts[(poly.vert_id[j]-1)][0];
- vert[1] = off_object.verts[(poly.vert_id[j]-1)][1];
- vert[2] = off_object.verts[(poly.vert_id[j]-1)][2];
- printf(" { %g %g %g } ", vert[0], vert[1], vert[2]);
- }
- printf("}\n");
-
- printf("}\n");
- }
-
- /**********************************************************************/
- /* Read off file */
- /**********************************************************************/
- void Read_off(filename)
- char *filename;
- {
- int i,j;
- float vvalues[3];
- int poly_id = 0;
- Polygon poly;
-
- if (!(off_file = fopen(filename, "r"))) {
- fprintf(stderr,"%s: cannot read off file %s\n", ProgName, filename);
- exit(1);
- }
- fscanf(off_file,"%d %d %d",
- &(off_object.num_vert),
- &(off_object.num_polys),
- &(off_object.num_edges));
- if (debug)
- printf("%d %d %d\n", off_object.num_vert, off_object.num_polys,
- off_object.num_edges);
-
- /* Print mesh header */
- printf(" NumMeshes 1\n");
- printf(" Mesh mesh%s%d %d {\n", off_filename, 1, off_object.num_polys);
-
- /* Read vertex info */
- for (i=0;i<off_object.num_vert;i++) {
- fscanf(off_file,"%g %g %g\n", &vvalues[0], &vvalues[1], &vvalues[2]);
- off_object.verts[i][0] = vvalues[0];
- off_object.verts[i][1] = vvalues[1];
- off_object.verts[i][2] = vvalues[2];
- if (debug)
- printf("%g %g %g\n",
- off_object.verts[i][0],
- off_object.verts[i][1],
- off_object.verts[i][2]);
- }
-
- /* Read polygon info */
- for (i=0;i<off_object.num_polys;i++) {
- fscanf(off_file,"%d", &(poly.num_vert));
- if (debug) printf("%d ", poly.num_vert);
- for (j=0;j<poly.num_vert;j++) {
- fscanf(off_file,"%d", &(poly.vert_id[j]));
- if (debug) printf("%d ", poly.vert_id[j]);
- }
- if (debug) printf("\n");
-
- /* Output polygon */
- /* Write_walk_poly(poly, poly_id++); */
- Write_pat_poly(poly, poly_id++);
- }
- fclose(off_file);
- }
-
- /**********************************************************************/
- /* main */
- /**********************************************************************/
- main(argc, argv)
- int argc;
- char *argv[];
- {
- if (argc < 2) {
- printf("usage: %s off_file [r=0/1]\n", ProgName);
- exit(0);
- }
- off_filename = argv[1];
- reverse_norms = atoi(argv[2]);
-
- Write_pat_header(off_filename, 1);
- /* Write_walk_header(); */
- Read_off(off_filename);
- Write_pat_footer();
- }
-