#include<sys/types.h>
#include<sys/stat.h>
#include<fcntl.h>
#include<unistd.h>
#include<stdlib.h>
#include<stdio.h>
#include<malloc.h>
#include<string.h>

typedef struct {
	float x,y,z;
	float r,g,b,a;
} Vertex;

typedef struct {
	int p1, p2;
} Edge ;

typedef struct {
	int p1, p2, p3;
} Triangle ;

int ReadGeomFile( char *filename , int *nbv, int *nbt, Vertex **V, Triangle **T )
{
	FILE *fp;
	char line[512];
	char *s;
	int lineno = 1;
	int p1,p2,p3,p4,tri,nbpol,nbpts,nbtri;
	int dummy,tt,lus;
	int i;
	float x,y,z;
	float r,g,b,alpha;
	Vertex *v; Triangle *t;

	if ( (fp = fopen( filename, "r" )) == NULL ) {
		fprintf(stderr,"Could not open file %s.\n",filename);
		return(0);
	}

	if ( (s = fgets( line , 512 , fp )) == NULL ) {
		fprintf(stderr,"Error in file %s near line %d\n",filename,lineno);
		return(0);
	}

	while ( sscanf( line , "%d %d %d" , &nbpts, &nbpol, &dummy ) != 3 ) {
		lineno++;
		if ( (s = fgets( line , 512 , fp )) == NULL ) {
			fprintf(stderr,"Error: wrong format in file %s\n",filename);
			return(0);
		}
	}
	
	v = *V = (Vertex *)malloc(nbpts * sizeof(Vertex) );

	for ( i=0 ; i < nbpts ; ++i ) {
		if ( (s = fgets( line , 512 , fp )) == NULL ) {
			fprintf(stderr,"Error: could not read point %d in file %s\n",
				i+1, filename);
			return(0);
		}

	 	if ( (lus = sscanf( line, "%f %f %f %f %f %f %f", &x, &y, &z, &r, &g, &b, &alpha)) < 3 ) {
			fprintf(stderr,"Error: wrong format for point %d in file %s\n",
				i+1, filename);
			return(0);
		}

		/* Ranger les coordonnees x y z dans v[i] */
		v[i].x = x;
		v[i].y = y;
		v[i].z = z;
		if ( lus > 3 ) {
			/* Ranger les couleurs r g b alpha dans v[i] */
			v[i].r = r;
			v[i].g = g;
			v[i].b = b;
			v[i].a = alpha;
		} else {
			v[i].r = v[i].g = v[i].b = 0.5;
		}
	}


	t = *T = (Triangle *)malloc(2*nbpol * sizeof(Triangle) );
	nbtri = 0;

	for ( i=0 ; i < nbpol ; ++i ) {
		if ( (s = fgets( line , 512 , fp )) == NULL ) {
			fprintf(stderr,"Error: could not read pol %d in file %s\n",
				i+1, filename);
			return(0);
		}

	 	tt = sscanf( line, "%d %d %d %d %d", &tri, &p1, &p2, &p3, &p4 );

		if ( tt < 4 ) {
			fprintf(stderr,"Error: wrong format for pol %d in file %s\n",
				i+1, filename);
			return(0);
		}
		
		if ( tri == 3 ) {
			/* ranger les points dans t[nbtri] */
			t[nbtri].p1 = p1;
			t[nbtri].p2 = p2;
			t[nbtri].p3 = p3;
			nbtri ++;
		}  else
		if ( tri == 4 ) {

			/* Creer DEUX triangles a partir des points p1--p4 */
			/* et les ranger dans le tableau aux emplacements nbtri et nbtri+1 */

			t[nbtri].p1 = p1;
			t[nbtri].p2 = p2;
			t[nbtri].p3 = p3;

			t[nbtri+1].p1 = p1;
			t[nbtri+1].p2 = p3;
			t[nbtri+1].p3 = p4;

			nbtri += 2;

		} else {
			fprintf(stderr,"Warning: ignoring polygon with %d vertices\n", tri);
		}
	}
	fclose(fp);

	*nbv = nbpts;
	*nbt = nbtri;
	return(1);
}

int WriteGeomFile( char *filename , int nbv, int nbt, Vertex *v, Triangle *t )
{
	FILE *fp;
	int i;

	if ( (fp = fopen( filename, "w" )) == NULL ) {
		fprintf(stderr,"Could not open file %s for writing.\n",filename);
		return(0);
	}

	fprintf(fp,"COFF\n%d %d %d\n",nbv,nbt,0);

	for ( i=0 ; i < nbv ; ++i ) {
		fprintf(fp,"\t%9.6f\t%9.6f\t%9.6f\t\t%5.3f\t%5.3f\t%5.3f\t%5.3f\n",
			v[i].x, v[i].y, v[i].z,
			v[i].r, v[i].g, v[i].b, v[i].a
			);
	}

	for ( i=0 ; i < nbt ; ++i ) {
		fprintf(fp,"3\t%3d\t%3d\t%3d\n",
/*			t[i].p1-1, t[i].p2-1, t[i].p3-1 */
			t[i].p1, t[i].p2, t[i].p3 
			);
	}
	fclose(fp);
	return 1;
}

int main( int argc, char **argv )
{
	Vertex *v;
	Triangle *t;
	int nbv,nbt;

	if ( argc > 1 ) {
		int ret = ReadGeomFile(argv[1],&nbv,&nbt,&v,&t);
		printf("ReadFile returned %d (%d vertices and %d triangles)\n",
			ret, nbv, nbt );
		(void)WriteGeomFile( "toto.out", nbv, nbt, v,t );
	} else
		printf("Usage: %s Geomfile\n",argv[0]);
}

