/************
*
* This file is part of a tool for producing 3D content in the PRC format.
* Copyright (C) 2008 Orest Shardt <shardtor (at) gmail dot com>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this program. If not, see <
http://www.gnu.org/licenses/>.
*
*************/
#include "../include/prc/oPRCFile.h"
#include <cstdlib>
#include <fstream>
#include <iomanip>
#include <iostream>
#include <unistd.h>
using namespace std;
void readPoints(istream &is, unsigned int n, double p[][3])
{
for(unsigned int i = 0; i < n; ++i)
{
is >> p[i][0] >> p[i][1] >> p[i][2];
}
if(!is)
{
cerr << "Error reading list of points." << endl;
exit(1);
}
}
void readDoubles(istream &is, unsigned int n, double d[])
{
for(unsigned int i = 0; i < n; ++i)
{
is >> d[i];
}
if(!is)
{
cerr << "Error reading list of doubles." << endl;
exit(1);
}
}
int main(int argc, char **argv)
{
const char *oFileName = "output.prc";
int c;
opterr = 0;
while ((c = getopt (argc, argv, "o:")) != -1)
switch (c)
{
case 'o':
oFileName = optarg;
break;
case '?':
if (optopt == 'o')
cerr << "Option '-o' requires an argument, the filename." << endl;
else
cerr << "Unrecognized option '-" << (char)optopt << "'." << endl;
exit(1);
break;
default:
exit(1);
}
istream *ins = NULL;
if(optind < argc)
{
ins = new ifstream(argv[optind]);
if(!*ins)
{
cerr << "Error opening input file " << argv[optind] << endl;
exit(1);
}
}
else
{
ins = &cin;
}
ofstream outf(oFileName);
if(!outf)
{
cerr << "Error opening output file " << oFileName << endl;
exit(1);
}
oPRCFile oPRC(outf);
string entityType;
while(*ins)
{
*ins >> entityType;
if(!*ins) break;
if(entityType == "Line")
{
double r,g,b,a;
unsigned int numberOfPoints;
*ins >> r >> g >> b >> a >> numberOfPoints;
if(!*ins)
{
cerr << "Error reading line data." << endl;
exit(1);
}
else
{
double (*points)[3] = new double[numberOfPoints][3];
readPoints(*ins,numberOfPoints,points);
oPRC.add(new PRCline(&oPRC,numberOfPoints,points,
*new RGBAColour(r,g,b,a)));
}
}
else if(entityType == "Curve")
{
double r,g,b,a;
unsigned int numberOfPoints;
unsigned int degree;
*ins >> r >> g >> b >> a >> degree >> numberOfPoints;
if(!*ins)
{
cerr << "Error reading curve data." << endl;
exit(1);
}
else
{
double (*points)[3] = new double[numberOfPoints][3];
double *knots = new double[degree+numberOfPoints+1];
readPoints(*ins,numberOfPoints,points);
readDoubles(*ins,degree+numberOfPoints+1,knots);
oPRC.add(new PRCcurve(&oPRC,degree,numberOfPoints,points,
knots,*new RGBAColour(r,g,b,a)));
}
}
else if(entityType == "Surface")
{
double r,g,b,a;
unsigned int numberOfPointsU,numberOfPointsV;
unsigned int degreeU,degreeV;
*ins >> r >> g >> b >> a >> degreeU >> degreeV >> numberOfPointsU
>> numberOfPointsV;
if(!*ins)
{
cerr << "Error reading surface data." << endl;
exit(1);
}
else
{
double (*points)[3] = new double[numberOfPointsU*numberOfPointsV][3];
double *knotsU = new double[degreeU+numberOfPointsU+1];
double *knotsV = new double[degreeV+numberOfPointsV+1];
readPoints(*ins,numberOfPointsU*numberOfPointsV,points);
readDoubles(*ins,degreeU+numberOfPointsU+1,knotsU);
readDoubles(*ins,degreeV+numberOfPointsV+1,knotsV);
oPRC.add(new PRCsurface(&oPRC,degreeU,degreeV,numberOfPointsU,
numberOfPointsV,points,knotsU,knotsV,
*new RGBAColour(r,g,b,a)));
}
}
else
{
cerr << "Unrecognized entity type " << entityType << endl;
exit(1);
}
}
if(ins && ins != &cin)
delete ins;
oPRC.finish();
outf.close();
return 0;
}