[SOLVED] CS compiler /* wavefront.cpp

$25

File Name: CS_compiler_/*_wavefront.cpp.zip
File Size: 263.76 KB

5/5 - (1 vote)

/* wavefront.cpp
*/

#include headers.h
#include gpuProgram.h
#include linalg.h

#include
#include
#include

#ifdef HAVE_PNG
#include #endif

#include wavefront.h

boolwfModel::newGroupWithNewMaterial = false;
boolwfModel::verticesAreCW = false;

unsigned char wfMaterial::defaultTexmap[] = { 255, 255, 255, 255, 255, 255,
255, 255, 255, 255, 255, 255 };

/* Read a Wavefront model into this structure.See ObjectFile.html
* for a description of the Wavefront file format.This code is from
* the Nate Robins GLM library.
*/

void wfModel::read( char *filename )

{
FILE* file;
charbuf[1000];
float x, y, z;
wfGroup*currentGroup;
wfMaterial *currentMaterial;
int nextGroupNum = 0;

// Counts of different vertex formats

int numVTN = 0;
int numVT = 0;
int numVN = 0;
int numV = 0;

/* init */

vertices.clear();
normals.clear();
texcoords.clear();
facetnorms.clear();
materials.clear();
groups.clear();

pathname = strdup(filename);

groups.add( new wfGroup( default ) );
currentGroup = groups[0];

materials.add( new wfMaterial( default ) );
currentMaterial = materials[0];

currentGroup->material = currentMaterial;

/* open the file */

file = fopen(filename, r);
if (!file) {
cerr << “wfModel::read() failed: can’t open data file ‘” << filename << “‘.” << endl;exit(-1);}/* process each line */lineNum = 0;while(fscanf(file, “%s”, buf) != EOF) {lineNum++;if (strncmp( buf, “transform”, 9 ) == 0) {for (int r=0; r<4; r++)for (int c=0; c<4; c++) {float val;fscanf( file, “%f”, &val );objToWorldTransform[r][c] = val;}} else {int v = 0, n = 0, t = 0;wfTriangle *tri, *prevTri;switch(buf[0]) {case ‘#’:/* comment *//* eat up rest of line */fgets(buf, sizeof(buf), file);break;case ‘s’:/* smoothing group … ignore *//* eat up rest of line */fgets(buf, sizeof(buf), file);break;case ‘v’:/* v, vn, vt */switch(buf[1]) {case ‘’:/* vertex */fscanf(file, “%f %f %f”, &x, &y, &z );vertices.add( vec3(x,y,z) );break;case ‘n’:/* normal */fscanf(file, “%f %f %f”, &x, &y, &z );normals.add( vec3(x,y,z).normalize() );break;case ‘t’:/* texcoord */fscanf(file, “%f %f”, &x, &y );texcoords.add( vec3(x,y,0) );fgets(buf, sizeof(buf), file); // skip rest of linebreak;}break;case ‘m’:/* mtllib filename */fgets(buf, sizeof(buf), file);sscanf(buf, “%s %s”, buf, buf);mtllibname = strdup(buf);readMaterialLibrary( buf );break;case ‘u’:/* usemtl name */if (newGroupWithNewMaterial) {char buffer[100];sprintf( buffer, “g%d”, nextGroupNum++ );currentGroup = findGroup( buffer );}fgets(buf, sizeof(buf), file);sscanf(buf, “%s %s”, buf, buf);currentGroup->material = currentMaterial = findMaterial( buf );
break;

case g:/* group */
/* eat up rest of line */
fgets(buf, sizeof(buf), file);
sscanf(buf, %s, buf);
if (buf[0] ==
)
currentGroup = findGroup( default );
else
currentGroup = findGroup( buf );
currentGroup->material = currentMaterial;
break;

case f:/* face */

fscanf(file, %s, buf);

/* can be one of %d, %d//%d, %d/%d, or %d/%d/%d */

tri = new wfTriangle();

if (strstr(buf, //)) {/* v//n */

numVN++;

/* First three vertices define a triangle */

sscanf(buf, %d//%d, &v, &n);v; checkVindex(v); n; tri->vindices[0] = v; tri->nindices[0] = n;
fscanf(file, %d//%d, &v, &n);v; checkVindex(v); n; tri->vindices[1] = v; tri->nindices[1] = n;
fscanf(file, %d//%d, &v, &n);v; checkVindex(v); n; tri->vindices[2] = v; tri->nindices[2] = n;

currentGroup->triangles.add( tri );

/* More vertices (a convex polygon) are converted to a fan of triangles: */

while(fscanf(file, %d//%d, &v, &n) > 0) {

v; checkVindex(v); n;

prevTri = tri;
tri = new wfTriangle();

tri->vindices[0] = prevTri->vindices[0];
tri->nindices[0] = prevTri->nindices[0];
tri->vindices[1] = prevTri->vindices[2];
tri->nindices[1] = prevTri->nindices[2];
tri->vindices[2] = v;
tri->nindices[2] = n;

currentGroup->triangles.add( tri );
}

} else if (sscanf(buf, %d/%d/%d, &v, &t, &n) == 3) {/* v/t/n */

numVTN++;

v; checkVindex(v); n; t;

tri->vindices[0] = v;
tri->tindices[0] = t;
tri->nindices[0] = n;
fscanf(file, %d/%d/%d, &v, &t, &n);v; checkVindex(v); n; t;
tri->vindices[1] = v;
tri->tindices[1] = t;
tri->nindices[1] = n;
fscanf(file, %d/%d/%d, &v, &t, &n);v; checkVindex(v); n; t;
tri->vindices[2] = v;
tri->tindices[2] = t;
tri->nindices[2] = n;

currentGroup->triangles.add( tri );

while(fscanf(file, %d/%d/%d, &v, &t, &n) > 0) {

v; checkVindex(v); n; t;

prevTri = tri;
tri = new wfTriangle();

tri->vindices[0] = prevTri->vindices[0];
tri->tindices[0] = prevTri->tindices[0];
tri->nindices[0] = prevTri->nindices[0];
tri->vindices[1] = prevTri->vindices[2];
tri->tindices[1] = prevTri->tindices[2];
tri->nindices[1] = prevTri->nindices[2];
tri->vindices[2] = v;
tri->tindices[2] = t;
tri->nindices[2] = n;

currentGroup->triangles.add( tri );
}

} else if (sscanf(buf, %d/%d, &v, &t) == 2) { /* v/t */

numVT++;

v; checkVindex(v); t;

tri->vindices[0] = v;
tri->tindices[0] = t;
fscanf(file, %d/%d, &v, &t);v; checkVindex(v); t;
tri->vindices[1] = v;
tri->tindices[1] = t;
fscanf(file, %d/%d, &v, &t);v; checkVindex(v); t;
tri->vindices[2] = v;
tri->tindices[2] = t;

currentGroup->triangles.add( tri );

while(fscanf(file, %d/%d, &v, &t) > 0) {

v; checkVindex(v); t;

prevTri = tri;
tri = new wfTriangle();

tri->vindices[0] = prevTri->vindices[0];
tri->tindices[0] = prevTri->tindices[0];
tri->vindices[1] = prevTri->vindices[2];
tri->tindices[1] = prevTri->tindices[2];
tri->vindices[2] = v;
tri->tindices[2] = t;

currentGroup->triangles.add( tri );
}

} else {/* v */

numV++;

sscanf(buf, %d, &v); v; checkVindex(v);
tri->vindices[0] = v;
fscanf(file, %d, &v); v; checkVindex(v);
tri->vindices[1] = v;
fscanf(file, %d, &v); v; checkVindex(v);
tri->vindices[2] = v;

currentGroup->triangles.add( tri );

while(fscanf(file, %d, &v) > 0) {

v; checkVindex(v);

prevTri = tri;
tri = new wfTriangle();

tri->vindices[0] = prevTri->vindices[0];
tri->vindices[1] = prevTri->vindices[2];
tri->vindices[2] = v;

currentGroup->triangles.add( tri );
}
}
break;

default:
cerr << “Warning: unrecognized Wavefront command on line ” << lineNum << “: ” << buf << endl;break;}}}// Determine a consistent format for each vertexhasVertexNormals = (numVTN > 0 || numVN > 0);
hasVertexTexCoords = (numVTN > 0 || numVT > 0);

// Compute all face normals

for (int g=0; g triangles.size(); i++) {

wfTriangle &tri = *groups[g]->triangles[i];

vec3 d01 = vertices[ tri.vindices[1] ] vertices[ tri.vindices[0] ];
vec3 d02 = vertices[ tri.vindices[2] ] vertices[ tri.vindices[0] ];
vec3 n;

if (verticesAreCW)
n = (d02 ^ d01).normalize();
else
n = (d01 ^ d02).normalize();

tri.findex = facetnorms.size();
facetnorms.add( n );
}

// Find bounding box

min = vec3(MAXFLOAT,MAXFLOAT,MAXFLOAT);
max = vec3(-MAXFLOAT,-MAXFLOAT,-MAXFLOAT);

vec3 sum(0,0,0);
for (int i=0; i max.x)
max.x = vertices[i].x;
if (vertices[i].y > max.y)
max.y = vertices[i].y;
if (vertices[i].z > max.z)
max.z = vertices[i].z;
}
centre = 0.5 * (min + max);
radius = 0.5 * (max min).length();
}

void wfModel::readMaterialLibrary( char *name )

{
FILE* file;
charbuf[1000];
wfMaterial *currentMaterial;
int i;

/* prepend path to the directory of the model file */

char *dir = new char[ strlen( pathname )+1 ];

strcpy( dir, pathname );

char *s = strrchr(dir, /);
if (s)
s[1] = ;
else
dir[0] = ;

char *filename = new char[ strlen(dir) + strlen(name) + 1 ];

strcpy(filename, dir);
strcat(filename, name);

/* open the file */

file = fopen(filename, r);
if (!file) {
cerr << “wfModel::readMaterialLibrary() couldn’t open file ‘” << filename << “‘” << endl;exit(-1);}/* set the default material */if (materials.size() == 0)materials.add( new wfMaterial(“default”) );currentMaterial = materials[0];/* now, read in the data */while(fscanf(file, “%s”, buf) != EOF) {switch(buf[0]) {case ‘#’:/* comment *//* eat up rest of line */fgets(buf, sizeof(buf), file);break;case ‘n’:/* newmtl */fgets(buf, sizeof(buf), file);sscanf(buf, “%s %s”, buf, buf);for (i=0; i name, buf) == 0)
break;
if (i shininess);
/* wavefront shininess is from [0, 1000], so scale for OpenGL */
//currentMaterial->shininess /= 1000.0;
//currentMaterial->shininess *= 128.0;
break;

case K:
switch(buf[1]) {

case d:
fscanf( file, %f %f %f,
&currentMaterial->diffuse[0],
&currentMaterial->diffuse[1],
&currentMaterial->diffuse[2] );
break;

case s:
fscanf( file, %f %f %f,
&currentMaterial->specular[0],
&currentMaterial->specular[1],
&currentMaterial->specular[2] );
break;

case a:
fscanf( file, %f %f %f,
&currentMaterial->ambient[0],
&currentMaterial->ambient[1],
&currentMaterial->ambient[2]);
break;

default:
/* eat up rest of line */
fgets(buf, sizeof(buf), file);
break;
}
break;

case m:/* map_Kd filename */
fgets(buf, sizeof(buf), file);
sscanf(buf, %s %s, buf, buf);

{
// prepend path to the directory of the model file

char *dir = new char[ strlen(pathname) ];
strcpy( dir, pathname );

char *s = strrchr(dir, /);
if (s != NULL) s[1] = ; else dir[0] = ;

char *filename = new char[ strlen(dir) + strlen(buf) + 1 ];

strcpy(filename, dir);
strcat(filename, buf);

// load the texture

currentMaterial->loadTexmap( filename );
delete [] dir;
delete [] filename;
}

break;

default:
/* eat up rest of line */
fgets(buf, sizeof(buf), file);
break;
}
}

delete [] dir;
delete [] filename;
}

/* read a ppm texture map into the material
*/

void wfMaterial::loadTexmap( char *filename )

{
char *p = strrchr( filename, . );
if (p == NULL || strcmp( p, .ppm ) == 0)
texmap = readP6( filename );
else if (strcmp( p, .png ) == 0)
texmap = readPNG( filename );
else {
cerr << “Cannot read ” << filename << “.Only ppm and png files are handled.” << endl;texmap = NULL;}}wfMaterial* wfModel::findMaterial( char *name ){int i;for (i=0; i name ) == 0)
break;

if (i < materials.size())return materials[i];cerr << “Error: Can’t find material ‘” << name << “‘” << endl;return materials[0];}wfGroup* wfModel::findGroup( char *name ){int i;for (i=0; i name ) == 0)
break;

if (i < groups.size())return groups[i];// create a new group of this namegroups.add( new wfGroup(name) );return groups[ groups.size() – 1 ];}class VertexSignature {public:unsigned int sig[3];bool operator == (const VertexSignature p) {return sig[0] == p.sig[0] && sig[1] == p.sig[1] && sig[2] == p.sig[2];}};void wfModel::setupVAO( TextureMode textureMode ){// Note that positions, normals, and texture coordinates can all be// indexed differently in a Wavefront file.But OpenGL permits only// one index per vertex, and the OpenGL vertex encapsulates all// attributes, including position, normal, and texture coordinates.//// So we have to create *another* array of vertices where each// vertex stores position, normal, and texture coordinates and the// face indices index into this new array.unsigned int vertexSize = 3;if (hasVertexNormals)vertexSize += 3;if (hasVertexTexCoords)vertexSize += 2;// Process each group separatelyfor (int i=0; i triangles.size();

if (numTriangles > 0) {

GLfloat *vertexBuffer = new GLfloat[ numTriangles * 3 * vertexSize ];
GLuint *faceIndexBuffer = new GLuint[ numTriangles * 3 ];

unsigned int nVerts = 0;
int nFaces = 0;

VertexSignature *vertSig = new VertexSignature[ numTriangles * 3 ];

for (int j=0; j triangles.size(); j++) {

wfTriangle *tri = thisGroup->triangles[j];

for (int k=0; k<3; k++) {// Find an already-stored vertex with this signature (brute force)VertexSignature vs;vs.sig[0] = tri->vindices[k];
vs.sig[1] = tri->nindices[k];
vs.sig[2] = tri->tindices[k];

unsigned int l;
for (l=0; l vindices[k] ];
if (hasVertexNormals)
* (vec3*) &vertexBuffer[nVerts*vertexSize+3] = normals[ tri->nindices[k] ];
if (hasVertexTexCoords) {
if (hasVertexNormals)
* (vec2*) &vertexBuffer[nVerts*vertexSize+6] = * (vec2*) &texcoords[ tri->tindices[k] ];
else
* (vec2*) &vertexBuffer[nVerts*vertexSize+3] = * (vec2*) &texcoords[ tri->tindices[k] ];
}

vertSig[ nVerts ] = vs;

nVerts++;
}

// Store this vertex index

faceIndexBuffer[ nFaces * 3 + k ] = l;
}

nFaces++;
}

// Set up the VAO

glGenVertexArrays( 1, &thisGroup->VAO );
glBindVertexArray( thisGroup->VAO );

GLuint bufferIDs[2];
glGenBuffers( 2, bufferIDs );

// store faces

glBindBuffer( GL_ELEMENT_ARRAY_BUFFER, bufferIDs[0] );
glBufferData( GL_ELEMENT_ARRAY_BUFFER, nFaces * 3 * sizeof(GLuint), faceIndexBuffer, GL_STATIC_DRAW );

// store vertices

glBindBuffer( GL_ARRAY_BUFFER, bufferIDs[1] );
glBufferData( GL_ARRAY_BUFFER, nVerts * vertexSize * sizeof(GLfloat), vertexBuffer, GL_STATIC_DRAW );

// define attributes

int attribIndex = 0;
unsigned long int accumulatedOffset = 0;

// position = attribute 0

glEnableVertexAttribArray( attribIndex );
glVertexAttribPointer( attribIndex, 3, GL_FLOAT, GL_FALSE, vertexSize * sizeof(GLfloat), (const GLvoid*) accumulatedOffset );
attribIndex++;
accumulatedOffset += 3 * sizeof( float );

// normals?

if (hasVertexNormals) {
glEnableVertexAttribArray( attribIndex );
glVertexAttribPointer( attribIndex, 3, GL_FLOAT, GL_FALSE, vertexSize * sizeof(GLfloat), (const GLvoid*) accumulatedOffset );
attribIndex++;
accumulatedOffset += 3 * sizeof( float );
}

// texture coordinates?

if (hasVertexTexCoords) {
glEnableVertexAttribArray( attribIndex );
glVertexAttribPointer( attribIndex, 2, GL_FLOAT, GL_FALSE, vertexSize * sizeof(GLfloat), (const GLvoid*) accumulatedOffset );
attribIndex++;
accumulatedOffset += 2 * sizeof( float );
}

thisGroup->VAOinitialized = true;

delete [] vertexBuffer;
delete [] faceIndexBuffer;
delete [] vertSig;

glBindVertexArray( 0 );
}
}

initTextures( textureMode );
}

void wfModel::draw( GPUProgram * gpuProg )

{
for (int i=0; i VAOinitialized) {

// Set up material properties

groups[i]->material->setMaterial( true, true, gpuProg );

// Render

glBindVertexArray( groups[i]->VAO );
glDrawElements( GL_TRIANGLES, 3 * groups[i]->triangles.size(), GL_UNSIGNED_INT, 0 );
glBindVertexArray( 0 );

groups[i]->material->unsetMaterial( true, true, gpuProg );
}
}

void wfMaterial::setMaterial( bool useTextures, bool useMaterial, GPUProgram * gpuProg )

{
if (useMaterial) {
gpuProg->setVec3( kd, vec3( &diffuse[0] ) );
gpuProg->setVec3( ks, vec3( &specular[0] ) );
gpuProg->setVec3( Ia, vec3( &ambient[0] ) );
gpuProg->setVec3( Ie, vec3( &emissive[0] ) );
gpuProg->setFloat( shininess, shininess );
} else {
gpuProg->setVec3( kd, vec3(1,1,1) );
gpuProg->setVec3( ks, vec3(0,0,0) );
gpuProg->setVec3( Ia, vec3(0,0,0) );
gpuProg->setVec3( Ie, vec3(0,0,0) );
gpuProg->setFloat( shininess, 400 );
}

if (useTextures && texmap != NULL) {
glActiveTexture( GL_TEXTURE0 );
glBindTexture( GL_TEXTURE_2D, textureID );
gpuProg->setInt( objTexture, 0 );
gpuProg->setInt( texturing, 1 );
} else
gpuProg->setInt( texturing, 0 );

}

void wfMaterial::unsetMaterial( bool useTextures, bool useMaterial, GPUProgram * gpuProg )

{
return;

if (useTextures && texmap != NULL) {

// Free texture unit 0

glActiveTexture( GL_TEXTURE0 );
glBindTexture( GL_TEXTURE_2D, 0 );
}

gpuProg->setInt( texturing, 0 );

glDisable(GL_BLEND);
}

void wfMaterial::storeTexture( TextureMode textureMode )

{
// Register it with OpenGL

glActiveTexture( GL_TEXTURE0 );
glBindTexture( GL_TEXTURE_2D, textureID );

glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT );
glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT );

glPixelStorei( GL_UNPACK_ALIGNMENT, 1 );

// set texture lookup mode

if (textureMode == NEAREST) {

glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST );
glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST );

} else if (textureMode == LINEAR) {

glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST );
glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR );

} else if (textureMode == MIPMAP_NEAREST) {

glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST );
glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_NEAREST );

} else if (textureMode == MIPMAP_LINEAR) {

glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST );
glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR );

} else {

cerr << “Unknown texture mode: ” << textureMode << endl; exit(1);}// Store the textureglTexImage2D( GL_TEXTURE_2D, 0, (hasAlpha ? GL_RGBA : GL_RGB), width, height, 0,(hasAlpha ? GL_RGBA : GL_RGB), GL_UNSIGNED_BYTE, texmap );// Build mipmapsglGenerateMipmap( GL_TEXTURE_2D );}/* Initialize the textures by assigning each an OpenGL ID and storing * each with OpenGL. */void wfModel::initTextures( TextureMode textureMode ){// Assign IDs to any textures without IDsfor (int i=0; i material->texmap != NULL && groups[i]->material->textureID == 0) {
glGenTextures(1, &(groups[i]->material->textureID) );
}

// Store the textures

for (int i=0; i material->texmap != NULL)
groups[i]->material->storeTexture( textureMode );
}

/* Read a texture from a P6 PPM file
*/

unsigned char *wfMaterial::readP6( char *filename )

{
char buffer[1000];
int i, xdim, ydim;
unsigned char *a, *b, *pa, *pb;

FILE *f = fopen( filename, r );

if (!f) {
cerr << “Open of `” << filename << “‘ failed.
“;exit(1);}// first linedo {i = 0;do fread(&buffer[i],1,1,f);while (buffer[i++] != ‘
‘);} while (buffer[0] == ‘#’);if (strncmp( buffer, “P6″, 2 ) != 0) {cerr << filename << ” is not a P6 file.
“;exit(1);}// second linedo {i = 0;do fread(&buffer[i],1,1,f);while (buffer[i++] != ‘
‘);} while (buffer[0] == ‘#’);buffer[i] = ‘’;sscanf( buffer, “%d %d”, &xdim, &ydim );width = xdim;height = ydim;// third linedo {i = 0;do fread(&buffer[i],1,1,f);while (buffer[i++] != ‘
‘);} while (buffer[0] == ‘#’);if (strncmp( buffer, “255”, 3 ) != 0) {cerr << filename << ” is not a 24-bit file.
“;exit(1);}// read the data (stored top-to-bottom, left-to-right)a = new unsigned char[ xdim * ydim * 3 ];fread( a, xdim*ydim*3, 1, f );// flip the image vertically (stored bottom-to-top, left-to-right)b = new unsigned char[ xdim * ydim * 3 ];for (int i=0; i jmpbuf)
#endif

#define PNG_BYTES_TO_CHECK 8

unsigned char *wfMaterial::readPNG( char *filename )

{
unsigned char *b;

#ifndef HAVE_PNG
cerr << “Trying to read PNG file “” << filename << “”, but the program wasn’t compiled with -DHAVE_PNG.” << endl;exit(-1);return b;#elsepng_structp png_ptr;png_infop info_ptr;unsigned int sig_read = 0;int bit_depth, color_type, interlace_type;char header[PNG_BYTES_TO_CHECK];// Open fileFILE *fp = fopen(filename, “rb”);if (!fp) {cerr << “Can’t open PNG texture file ‘” << filename << “‘.” << endl;exit(-1);}// Check headerfread( header, 1, PNG_BYTES_TO_CHECK, fp );bool is_png = !png_sig_cmp( (png_byte*) &header[0], 0, PNG_BYTES_TO_CHECK);if (!is_png) {cerr << “Texture file ‘” << filename << “‘ is not in PNG format.” << endl;exit(-1);}/* Create and initialize the png_struct with the desired error handler * functions.If you want to use the default stderr and longjump method, * you can supply NULL for the last three parameters.We also supply the * the compiler header file version, so that we know if the application * was compiled with a compatible version of the library.REQUIRED */png_ptr = png_create_read_struct( PNG_LIBPNG_VER_STRING, NULL, NULL, NULL );if (png_ptr == NULL) {cerr << “Can’t initialize PNG file for reading: ” << filename << endl;fclose(fp);exit(-1);}/* Allocate/initialize the memory for image information.REQUIRED. */info_ptr = png_create_info_struct(png_ptr);if (info_ptr == NULL){fclose(fp);png_destroy_read_struct(&png_ptr, (png_infopp)NULL, (png_infopp)NULL);cerr << “Can’t allocate memory to read PNG file: ” << filename << endl;exit(-1);}/* Set error handling if you are using the setjmp/longjmp method (this is * the normal method of doing things with libpng).REQUIRED unless you * set up your own error handlers in the png_create_read_struct() earlier. */if (setjmp(png_jmpbuf(png_ptr))) {/* Free all of the memory associated with the png_ptr and info_ptr */png_destroy_read_struct(&png_ptr, &info_ptr, (png_infopp)NULL);fclose(fp);/* If we get here, we had a problem reading the file */cerr << “Exception occurred while reading PNG file: ” << filename << endl;exit(-1);}/* Set up the input control if you are using standard C streams */png_init_io(png_ptr, fp);/* If we have already read some of the signature */png_set_sig_bytes(png_ptr, PNG_BYTES_TO_CHECK);// Warning: the following does NOT convert grey to RGB:png_read_png( png_ptr, info_ptr, PNG_TRANSFORM_STRIP_16 | PNG_TRANSFORM_PACKING | PNG_TRANSFORM_EXPAND, NULL );// Store in texmapint numChannels = png_get_channels(png_ptr, info_ptr);if (png_get_bit_depth(png_ptr, info_ptr) != 8) {cerr << “Can’t handle PNG files with bit depth other than 8.'” << filename << “‘ has ” << png_get_bit_depth(png_ptr, info_ptr) << ” bits per pixel.” << endl;exit(-1);}width = png_get_image_width(png_ptr,info_ptr);height = png_get_image_height(png_ptr,info_ptr);int imageSize;if (numChannels == 4)imageSize = 4 * width * height;elseimageSize = 3 * width * height;b = pb = new unsigned char[ imageSize ];for (int r=(int)info_ptr->height 1; r >= 0; r) {
png_bytep row = info_ptr->row_pointers[r];
int rowbytes = png_get_rowbytes(png_ptr, info_ptr);
for (int c=0; c < rowbytes; c++)switch (numChannels) {case 1:*(pb)++ = row[c];*(pb)++ = row[c];*(pb)++ = row[c];break;case 2:cerr << “Can’t handle a two-channel PNG file: ” << filename << endl;exit(-1);break;case 3:case 4:*(pb)++ = row[c];break;}}hasAlpha = (numChannels == 4);// Clean up PNG stuffpng_destroy_read_struct(&png_ptr, &info_ptr, (png_infopp)NULL);fclose(fp);return b;#endif}

Reviews

There are no reviews yet.

Only logged in customers who have purchased this product may leave a review.

Shopping Cart
[SOLVED] CS compiler /* wavefront.cpp
$25