From Sukender,

"Here is our freshly baked 3DS reader/writer (named 'v0.5' to differentiate from previous one). Changes are against trunk rev. 10819.
Short changelog (from rev 10819):
- Added 3DS writer
- Sync'd with latest lib3DS
- Added options, especially "flattenMatrixTransforms" to get the "old" behaviour (else the reader correctly maps to OSG the transforms from the 3DS file).

What should be done:
- Check with pivot points, with and without "flattenMatrixTransforms" option.
- We ran tests on it, but we can never be 100% sure there is no bug. Testing from the community would of course be helpful."
This commit is contained in:
Robert Osfield
2009-12-04 11:31:04 +00:00
parent c262112fbb
commit 6773aca87a
72 changed files with 11472 additions and 13055 deletions

View File

@@ -1 +1,3 @@
J.E. Hoffmann <je-h@gmx.net>
Sukender (Benoit Neil) <suky0001 at free dot fr>
Thibault Caporal <>

View File

@@ -1,48 +1,40 @@
# List of C files to be compiled as C++ (else CMake sets ".c" to be compiled as pure C)
SET(C_FILES
lib3ds/lib3ds_io.c # Modified to support OSG endianness
)
SET(TARGET_SRC
ReaderWriter3DS.cpp
atmosphere.cpp
background.cpp
camera.cpp
chunk.cpp
ease.cpp
file.cpp
lib3ds_float.cpp
light.cpp
material.cpp
matrix.cpp
mesh.cpp
node.cpp
quat.cpp
readwrite.cpp
shadow.cpp
tcb.cpp
tracks.cpp
vector.cpp
viewport.cpp
WriterNodeVisitor.cpp
WriterCompareTriangle.cpp
${C_FILES}
lib3ds/lib3ds_atmosphere.c
lib3ds/lib3ds_background.c
lib3ds/lib3ds_camera.c
lib3ds/lib3ds_chunk.c
lib3ds/lib3ds_chunktable.c
lib3ds/lib3ds_file.c
lib3ds/lib3ds_light.c
lib3ds/lib3ds_material.c
lib3ds/lib3ds_math.c
lib3ds/lib3ds_matrix.c
lib3ds/lib3ds_mesh.c
lib3ds/lib3ds_node.c
lib3ds/lib3ds_quat.c
lib3ds/lib3ds_shadow.c
lib3ds/lib3ds_track.c
lib3ds/lib3ds_util.c
lib3ds/lib3ds_vector.c
lib3ds/lib3ds_viewport.c
)
SET(TARGET_H
atmosphere.h
background.h
camera.h
chunk.h
chunktable.h
config.h
ease.h
file.h
lib3ds_float.h
light.h
material.h
matrix.h
mesh.h
node.h
quat.h
readwrite.h
shadow.h
tcb.h
tracks.h
types.h
vector.h
viewport.h
WriterNodeVisitor.h
WriterCompareTriangle.h
lib3ds/lib3ds.h
lib3ds/lib3ds_impl.h
)
#### end var setup ###
SETUP_PLUGIN(3ds)
ADD_DEFINITIONS( -DLIB3DS_STATIC ) # lib3ds is included, so we need the flag
SET_SOURCE_FILES_PROPERTIES(${C_FILES} PROPERTIES LANGUAGE "CXX") # Force some files to be compiled as C++

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,135 @@
#include "WriterCompareTriangle.h"
WriterCompareTriangle::WriterCompareTriangle(const osg::Geode & geode, unsigned int nbVertices) : geode(geode)
{
cutscene(nbVertices, geode.getBoundingBox());
}
bool
WriterCompareTriangle::operator()(const std::pair<Triangle, int> & t1,
const std::pair<Triangle, int> & t2) const
{
const osg::Geometry *g = geode.getDrawable( t1.second )->asGeometry();
const osg::Vec3Array * vecs= static_cast<const osg::Vec3Array *>(g->getVertexArray());
const osg::BoundingBox::vec_type v1( (*vecs)[t1.first.t1] );
if (t1.second != t2.second)
{
const osg::Geometry *g = geode.getDrawable( t2.second )->asGeometry();
vecs = static_cast<const osg::Vec3Array *>(g->getVertexArray());
};
const osg::BoundingBox::vec_type v2( (*vecs)[t2.first.t1] );
int val1 = inWhichBox(v1);
int val2 = inWhichBox(v2);
return (val1 < val2);
}
void
WriterCompareTriangle::setMaxMin(unsigned int & nbVerticesX,
unsigned int & nbVerticesY,
unsigned int & nbVerticesZ) const
{
static const unsigned int min = 1;
static const unsigned int max = 5; // Number of blocks used to divide the scene (arbitrary but seems ok)
nbVerticesX = osg::clampBetween<unsigned int>(nbVerticesX, min, max);
nbVerticesY = osg::clampBetween<unsigned int>(nbVerticesY, min, max);
nbVerticesZ = osg::clampBetween<unsigned int>(nbVerticesZ, min, max);
}
void WriterCompareTriangle::cutscene(int nbVertices, const osg::BoundingBox & sceneBox)
{
osg::BoundingBox::vec_type length = sceneBox._max - sceneBox._min;
static const float k = 1.3f; // Arbitrary constant multiplier for density computation ("simulates" non-uniform point distributions)
// Computes "density" of points, and thus the number of blocks to divide the mesh into
unsigned int nbVerticesX = static_cast<unsigned int>( (nbVertices * k) / (length.z() * length.y()) );
unsigned int nbVerticesY = static_cast<unsigned int>( (nbVertices * k) / (length.z() * length.x()) );
unsigned int nbVerticesZ = static_cast<unsigned int>( (nbVertices * k) / (length.x() * length.y()) );
setMaxMin (nbVerticesX, nbVerticesY, nbVerticesZ); // This function prevent from cut scene in too many blocs
osg::notify(osg::ALWAYS) << "Cutting x by " << nbVerticesX << std::endl
<< "Cutting y by " << nbVerticesY << std::endl
<< "Cutting z by " << nbVerticesZ << std::endl;
osg::BoundingBox::value_type blocX = length.x() / nbVerticesX; //This 3 lines set the size of a bloc in x, y and z
osg::BoundingBox::value_type blocY = length.y() / nbVerticesY;
osg::BoundingBox::value_type blocZ = length.z() / nbVerticesZ;
boxList.reserve(nbVerticesX * nbVerticesY * nbVerticesZ);
short yinc = 1;
short xinc = 1;
unsigned int y = 0;
unsigned int x = 0;
for (unsigned int z = 0; z < nbVerticesZ; ++z)
{
while (x < nbVerticesX && x >= 0)
{
while (y < nbVerticesY && y >= 0)
{
osg::BoundingBox::value_type xMin = sceneBox.xMin() + x * blocX;
if (x == 0) //to prevent from mesh with no case
xMin -= 10;
osg::BoundingBox::value_type yMin = sceneBox.yMin() + y * blocY;
if (y == 0) //to prevent from mesh with no case
yMin -= 10;
osg::BoundingBox::value_type zMin = sceneBox.zMin() + z * blocZ;
if (z == 0) //to prevent from mesh with no case
zMin -= 10;
osg::BoundingBox::value_type xMax = sceneBox.xMin() + (x + 1) * blocX;
if (x == nbVerticesX - 1) //to prevent from mesh with no case
xMax += 10;
osg::BoundingBox::value_type yMax = sceneBox.yMin() + (y + 1) * blocY;
if (y == nbVerticesY - 1) //to prevent from mesh with no case
yMax += 10;
osg::BoundingBox::value_type zMax = sceneBox.zMin() + (z + 1) * blocZ;
if (z == nbVerticesZ - 1) //to prevent from mesh with no case
zMax += 10;
boxList.push_back(osg::BoundingBox(xMin, // Add a bloc to the list
yMin,
zMin,
xMax,
yMax,
zMax));
y += yinc;
}
yinc = -yinc;
y += yinc;
x += xinc;
}
xinc = -xinc;
x += xinc;
}
}
int
WriterCompareTriangle::inWhichBox(const osg::BoundingBox::value_type x,
const osg::BoundingBox::value_type y,
const osg::BoundingBox::value_type z) const
{
for (unsigned int i = 0; i < boxList.size(); ++i)
{
if (x >= boxList[i].xMin() &&
x < boxList[i].xMax() &&
y >= boxList[i].yMin() &&
y < boxList[i].yMax() &&
z >= boxList[i].zMin() &&
z < boxList[i].zMax())
{
return i;
}
}
throw "Point is not in any blocs";
}
int WriterCompareTriangle::inWhichBox(const osg::BoundingBox::vec_type & point) const {
return inWhichBox(point.x(), point.y(), point.z());
}

View File

@@ -0,0 +1,51 @@
#ifndef _3DS_WRITER_COMPARE_TRIANGLE_HEADER__
#define _3DS_WRITER_COMPARE_TRIANGLE_HEADER__
#include <osg/Geode>
#include <osg/Geometry>
#include <iostream>
struct Triangle
{
unsigned int t1;
unsigned int t2;
unsigned int t3;
unsigned int material;
};
class WriterCompareTriangle {
public:
WriterCompareTriangle(const osg::Geode & geode, unsigned int nbVertices);
bool operator()(const std::pair<Triangle, int> & t1,
const std::pair<Triangle, int> & t2) const;
private:
void // This function prevent from cut scene in too many blocs
setMaxMin(unsigned int & nbVerticesX,
unsigned int & nbVerticesY,
unsigned int & nbVerticesZ) const;
/**
* Cut the scene in different bloc to sort.
* \param nbVertices is the number of vertice in mesh.
* \param sceneBox contain the size of the scene.
*/
void
cutscene(int nbVertices,
const osg::BoundingBox & sceneBox);
/**
* Find in which box those points are.
* \return the place of the box in the vector.
* \sa See cutScene() about the definition of the boxes for faces sorting.
*/
int inWhichBox(const osg::BoundingBox::value_type x,
const osg::BoundingBox::value_type y,
const osg::BoundingBox::value_type z) const;
int inWhichBox(const osg::BoundingBox::vec_type & point) const;
const osg::Geode & geode;
std::vector<osg::BoundingBox> boxList;
};
#endif // _3DS_WRITER_COMPARE_TRIANGLE_HEADER__

View File

@@ -0,0 +1,843 @@
// -*-c++-*-
/*
* 3DS reader/writer for Open Scene Graph
*
* Copyright (C) ???
*
* Writing support added 2007 by Sukender (Benoit Neil), http://sukender.free.fr,
* strongly inspired by the OBJ writer object by Stephan Huber
*
* The Open Scene Graph (OSG) is a cross platform C++/OpenGL library for
* real-time rendering of large 3D photo-realistic models.
* The OSG homepage is http://www.openscenegraph.org/
*/
#include <osg/io_utils>
#include <osg/CullFace>
#include "WriterNodeVisitor.h"
#include <assert.h>
#include <string.h>
void copyOsgMatrixToLib3dsMatrix(Lib3dsMatrix lib3ds_matrix, const osg::Matrix& osg_matrix)
{
for(int row=0; row<4; ++row) {
lib3ds_matrix[row][0] = osg_matrix.ptr()[row*4+0];
lib3ds_matrix[row][1] = osg_matrix.ptr()[row*4+1];
lib3ds_matrix[row][2] = osg_matrix.ptr()[row*4+2];
lib3ds_matrix[row][3] = osg_matrix.ptr()[row*4+3];
}
}
inline void copyOsgVectorToLib3dsVector(Lib3dsVector lib3ds_vector, const osg::Vec3f& osg_vector) {
lib3ds_vector[0] = osg_vector[0];
lib3ds_vector[1] = osg_vector[1];
lib3ds_vector[2] = osg_vector[2];
}
inline void copyOsgVectorToLib3dsVector(Lib3dsVector lib3ds_vector, const osg::Vec3d& osg_vector) {
lib3ds_vector[0] = osg_vector[0];
lib3ds_vector[1] = osg_vector[1];
lib3ds_vector[2] = osg_vector[2];
}
inline void copyOsgColorToLib3dsColor(Lib3dsVector lib3ds_vector, const osg::Vec4f& osg_vector) {
lib3ds_vector[0] = osg_vector[0];
lib3ds_vector[1] = osg_vector[1];
lib3ds_vector[2] = osg_vector[2];
}
inline void copyOsgColorToLib3dsColor(Lib3dsVector lib3ds_vector, const osg::Vec4d& osg_vector) {
lib3ds_vector[0] = osg_vector[0];
lib3ds_vector[1] = osg_vector[1];
lib3ds_vector[2] = osg_vector[2];
}
inline void copyOsgQuatToLib3dsQuat(float lib3ds_vector[4], const osg::Quat& osg_quat) {
//lib3ds_vector[0] = osg_quat[3]; // Not sure
//lib3ds_vector[1] = osg_quat[0];
//lib3ds_vector[2] = osg_quat[1];
//lib3ds_vector[3] = osg_quat[2];
// 3DS seems to store (angle in radians, axis_x, axis_y, axis_z), but it works with (axis_x, axis_y, axis_z, -angle in radians)!
osg::Quat::value_type angle, x, y, z;
osg_quat.getRotate(angle, x, y, z);
lib3ds_vector[0] = static_cast<float>(x);
lib3ds_vector[1] = static_cast<float>(y);
lib3ds_vector[2] = static_cast<float>(z);
lib3ds_vector[3] = static_cast<float>(-angle);
}
std::string getFileName(const std::string & path) {
unsigned int slashPos = path.find_last_of("/\\");
if (slashPos == std::string::npos) return path;
return path.substr(slashPos+1);
}
/// Checks if a filename (\b not path) is 8.3 (an empty name is never 8.3, and a path is never 8.3).
bool is83(const std::string & s) {
// 012345678901
// ABCDEFGH.ABC
if (s.find_first_of("/\\") != std::string::npos) return false; // It should not be a path, but a filename
unsigned int len = s.length();
if (len > 12 || len == 0) return false;
unsigned int pointPos = s.rfind('.');
if (pointPos == std::string::npos) return len <= 8; // Without point
// With point
if (pointPos > 8) return false;
if (len-1 - pointPos > 3) return false;
return true;
}
/// Tests if the given string is a path supported by 3DS format (8.3, 63 chars max).
bool is3DSpath(const std::string & s) {
unsigned int len = s.length();
if (len >= 64 || len == 0) return false;
unsigned int tokenBegin = 0;
for (unsigned int tokenEnd=0; tokenEnd != std::string::npos; tokenBegin = tokenEnd+1) {
tokenEnd = s.find_first_of("/\\", tokenBegin);
if ( !is83(s.substr(tokenBegin, tokenEnd-tokenBegin-1)) ) return false;
}
return true;
}
/** writes all primitives of a primitive-set out to a stream, decomposes quads to triangles, line-strips to lines etc */
class PrimitiveIndexWriter : public osg::PrimitiveIndexFunctor {
public:
PrimitiveIndexWriter(osg::Geometry * geo,
ListTriangle & listTriangles,
unsigned int drawable_n,
unsigned int material) :
osg::PrimitiveIndexFunctor(),
_drawable_n(drawable_n),
_listTriangles(listTriangles),
_hasNormalCoords(geo->getNormalArray() != NULL),
_hasTexCoords(geo->getTexCoordArray(0) != NULL),
_geo(geo),
_lastFaceIndex(0),
_material(material)
{
}
unsigned int getNextFaceIndex() { return _lastFaceIndex; }
virtual void setVertexArray(unsigned int,const osg::Vec2*) {}
virtual void setVertexArray(unsigned int count,const osg::Vec3* vecs) {}
virtual void setVertexArray(unsigned int,const osg::Vec4* ) {}
virtual void setVertexArray(unsigned int,const osg::Vec2d*) {}
virtual void setVertexArray(unsigned int ,const osg::Vec3d* ) {}
virtual void setVertexArray(unsigned int,const osg::Vec4d* ) {}
// operator for triangles
void writeTriangle(unsigned int i1, unsigned int i2, unsigned int i3)
{
Triangle triangle;
triangle.t1 = i1;
triangle.t2 = i2;
triangle.t3 = i3;
triangle.material = _material;
_listTriangles.push_back(std::make_pair(triangle, _drawable_n));
}
virtual void begin(GLenum mode)
{
_modeCache = mode;
_indexCache.clear();
}
virtual void vertex(unsigned int vert)
{
_indexCache.push_back(vert);
}
virtual void end()
{
if (!_indexCache.empty())
{
drawElements(_modeCache,_indexCache.size(),&_indexCache.front());
}
}
virtual void drawArrays(GLenum mode,GLint first,GLsizei count);
virtual void drawElements(GLenum mode,GLsizei count,const GLubyte* indices)
{
drawElementsImplementation<GLubyte>(mode, count, indices);
}
virtual void drawElements(GLenum mode,GLsizei count,const GLushort* indices)
{
drawElementsImplementation<GLushort>(mode, count, indices);
}
virtual void drawElements(GLenum mode,GLsizei count,const GLuint* indices)
{
drawElementsImplementation<GLuint>(mode, count, indices);
}
protected:
template<typename T>void drawElementsImplementation(GLenum mode, GLsizei count, const T* indices)
{
if (indices==0 || count==0) return;
typedef const T* IndexPointer;
switch(mode)
{
case(GL_TRIANGLES):
{
//lib3ds_mesh_resize_faces(_mesh, _lastFaceIndex + count / 3);
IndexPointer ilast = &indices[count];
for(IndexPointer iptr=indices;iptr<ilast;iptr+=3)
writeTriangle(*iptr,*(iptr+1),*(iptr+2));
break;
}
case(GL_TRIANGLE_STRIP):
{
//lib3ds_mesh_resize_faces(_mesh, _lastFaceIndex + count -2);
IndexPointer iptr = indices;
for(GLsizei i=2;i<count;++i,++iptr)
{
if ((i%2)) writeTriangle(*(iptr),*(iptr+2),*(iptr+1));
else writeTriangle(*(iptr),*(iptr+1),*(iptr+2));
}
break;
}
case(GL_QUADS):
{
//lib3ds_mesh_resize_faces(_mesh, _lastFaceIndex + count /2); // count/4*2
IndexPointer iptr = indices;
for(GLsizei i=3;i<count;i+=4,iptr+=4)
{
writeTriangle(*(iptr),*(iptr+1),*(iptr+2));
writeTriangle(*(iptr),*(iptr+2),*(iptr+3));
}
break;
}
case(GL_QUAD_STRIP):
{
//lib3ds_mesh_resize_faces(_mesh, _lastFaceIndex + (count / 2 -1)*2);
IndexPointer iptr = indices;
for(GLsizei i=3;i<count;i+=2,iptr+=2)
{
writeTriangle(*(iptr),*(iptr+1),*(iptr+2));
writeTriangle(*(iptr+1),*(iptr+3),*(iptr+2));
}
break;
}
case(GL_POLYGON): // treat polygons as GL_TRIANGLE_FAN
case(GL_TRIANGLE_FAN):
{
//lib3ds_mesh_resize_faces(_mesh, _lastFaceIndex + count -2);
IndexPointer iptr = indices;
unsigned int first = *iptr;
++iptr;
for(GLsizei i=2;i<count;++i,++iptr)
{
writeTriangle(first,*(iptr),*(iptr+1));
}
break;
}
case(GL_POINTS):
case(GL_LINES):
case(GL_LINE_STRIP):
case(GL_LINE_LOOP):
// Not handled
break;
default:
// uhm should never come to this point :)
break;
}
}
private:
PrimitiveIndexWriter& operator = (const PrimitiveIndexWriter&) { return *this; }
unsigned int _drawable_n;
ListTriangle & _listTriangles;
GLenum _modeCache;
std::vector<GLuint> _indexCache;
bool _hasNormalCoords, _hasTexCoords;
osg::Geometry* _geo;
unsigned int _lastFaceIndex;
unsigned int _material;
};
void PrimitiveIndexWriter::drawArrays(GLenum mode,GLint first,GLsizei count)
{
switch(mode)
{
case(GL_TRIANGLES):
{
unsigned int pos=first;
for(GLsizei i=2;i<count;i+=3,pos+=3)
{
writeTriangle(pos,pos+1,pos+2);
}
break;
}
case(GL_TRIANGLE_STRIP):
{
unsigned int pos=first;
for(GLsizei i=2;i<count;++i,++pos)
{
if ((i%2)) writeTriangle(pos,pos+2,pos+1);
else writeTriangle(pos,pos+1,pos+2);
}
break;
}
case(GL_QUADS):
{
unsigned int pos=first;
for(GLsizei i=3;i<count;i+=4,pos+=4)
{
writeTriangle(pos,pos+1,pos+2);
writeTriangle(pos,pos+2,pos+3);
}
break;
}
case(GL_QUAD_STRIP):
{
unsigned int pos=first;
for(GLsizei i=3;i<count;i+=2,pos+=2)
{
writeTriangle(pos,pos+1,pos+2);
writeTriangle(pos+1,pos+3,pos+2);
}
break;
}
case(GL_POLYGON): // treat polygons as GL_TRIANGLE_FAN
case(GL_TRIANGLE_FAN):
{
unsigned int pos=first+1;
for(GLsizei i=2;i<count;++i,++pos)
{
writeTriangle(first,pos,pos+1);
}
break;
}
case(GL_POINTS):
case(GL_LINES):
case(GL_LINE_STRIP):
case(GL_LINE_LOOP):
//break;
default:
osg::notify(osg::WARN) << "WriterNodeVisitor :: can't handle mode " << mode << std::endl;
break;
}
}
WriterNodeVisitor::Material::Material(WriterNodeVisitor & writerNodeVisitor, osg::StateSet * stateset, osg::Material* mat, osg::Texture* tex, int index) :
index(index),
diffuse(1,1,1,1),
ambient(0.2,0.2,0.2,1),
specular(0,0,0,1),
shininess(0),
transparency(0),
double_sided(false),
image(NULL),
texture_transparency(false),
texture_no_tile(false)
{
//static unsigned int s_objmaterial_id = 0;
//++s_objmaterial_id;
if (mat) {
assert(stateset);
diffuse = mat->getDiffuse(osg::Material::FRONT);
ambient = mat->getAmbient(osg::Material::FRONT);
specular = mat->getSpecular(osg::Material::FRONT);
shininess = mat->getShininess(osg::Material::FRONT);
transparency = 1-diffuse.w();
name = writerNodeVisitor.getUniqueName(mat->getName(),"mat");
osg::StateAttribute * attribute = stateset->getAttribute(osg::StateAttribute::CULLFACE);
if (!attribute) {
double_sided = true;
} else {
assert(dynamic_cast<osg::CullFace *>(attribute));
osg::CullFace::Mode mode = static_cast<osg::CullFace *>(attribute)->getMode();
if (mode == osg::CullFace::BACK) double_sided = false;
else if (mode == osg::CullFace::FRONT) {
osg::notify(osg::WARN) << "3DS Writer: Reversed face (culled FRONT) not supported yet." << std::endl;
double_sided = false;
}
else {
assert(mode == osg::CullFace::FRONT_AND_BACK);
osg::notify(osg::WARN) << "3DS Writer: Invisible face (culled FRONT_AND_BACK) not supported yet." << std::endl;
double_sided = false;
}
}
}
if (tex) {
osg::Image* img = tex->getImage(0);
if(img)
{
texture_transparency = (stateset->getMode(GL_BLEND) == osg::StateAttribute::ON);
texture_no_tile = (tex->getWrap(osg::Texture2D::WRAP_S) == osg::Texture2D::CLAMP);
image = img;
}
}
if (name.empty()) {
std::stringstream ss;
ss << "m" << index;
name = ss.str();
}
}
/// Creates a unique 3DS name for a given texture, and copies the image file to disk at an appropriate location if necessary.
//std::string WriterNodeVisitor::export3DSTexture(const osg::Image * image, const std::string & texName) {
// std::string extension = osgDB::getFileExtension(texName);
// if (is83(texName))
// {
// std::string newName = texName;
// if (extension.empty())
// newName += ".rgb";
// if (osgDB::Registry::instance()->writeImage(*image, osgDB::concatPaths(_directory, newName), options).status() ==
// osgDB::ReaderWriter::WriteResult::ERROR_IN_WRITING_FILE)
// failedApply();
// return texName;
// }
// if (extension.empty())
// {
// extension = "rgb";
// }
// std::string newName = getUniqueName(texName, "tex");
// newName += "." + extension;
// osgDB::Registry::instance()->writeImage(*image, osgDB::concatPaths(_directory, newName), options);
// return newName;
//}
std::string
getPathRelative(const std::string & srcBad,
const std::string & dstBad)
{
const std::string & src = osgDB::convertFileNameToNativeStyle(srcBad);
const std::string & dst = osgDB::convertFileNameToNativeStyle(dstBad);
std::string::const_iterator itDst = dst.begin();
std::string::const_iterator itSrc = src.begin();
std::string result = "";
while(itDst != dst.end())
{
if (itSrc != src.end() && *itDst == *itSrc)
++itSrc;
else if (!result.empty() || *itDst != '\\')
result += *itDst;
++itDst;
}
if (itSrc != src.end() || !is3DSpath(result))
result = osgDB::getSimpleFileName(dst);
return result;
}
void WriterNodeVisitor::writeMaterials()
{
unsigned int nbMat = _materialMap.size();
lib3ds_file_reserve_materials(file3ds, nbMat, 1);
// Ugly thing: it seems lib3ds_file_insert_material() doesn't support insertion in a random order (else materials are not assigned the right way)
for (unsigned int iMat=0; iMat<nbMat; ++iMat)
{
bool found = false;
for(MaterialMap::iterator itr = _materialMap.begin(); itr != _materialMap.end(); ++itr)
{
const Material & mat = itr->second;
if (mat.index != static_cast<int>(iMat)) continue; // Ugly thing (2)
found = true;
assert(mat.index>=0 && mat.index < static_cast<int>(_materialMap.size()));
Lib3dsMaterial * mat3ds = lib3ds_material_new(getFileName(mat.name).c_str());
copyOsgColorToLib3dsColor(mat3ds->ambient, mat.ambient);
copyOsgColorToLib3dsColor(mat3ds->diffuse, mat.diffuse);
copyOsgColorToLib3dsColor(mat3ds->specular, mat.specular);
mat3ds->shininess = mat.shininess;
mat3ds->transparency = mat.transparency;
mat3ds->two_sided = mat.double_sided ? 1 : 0;
if (mat.image)
{
Lib3dsTextureMap & tex = mat3ds->texture1_map;
std::string path;
if(mat.image->getFileName().empty())
{
std::ostringstream oss;
oss << "Image_" << _imageCount++ << ".rgb";
path = oss.str();
}
else
path = getPathRelative(_srcDirectory, mat.image->getFileName());
// if(!is3DSpath(path))
path = osgDB::getSimpleFileName(path);
strcpy(tex.name, path.c_str());
path = osgDB::concatPaths(_directory, path);
osgDB::makeDirectoryForFile(path);
if (mat.image && mat.image->data()) osgDB::Registry::instance()->writeImage(*(mat.image), path, NULL);
if (mat.texture_transparency) tex.flags |= LIB3DS_TEXTURE_ALPHA_SOURCE;
if (mat.texture_no_tile) tex.flags |= LIB3DS_TEXTURE_NO_TILE;
}
if (!suceedLastApply())
return;
lib3ds_file_insert_material(file3ds, mat3ds, itr->second.index);
break; // Ugly thing (3)
}
if (!found) throw "Implementation error"; // Ugly thing (4)
}
}
std::string WriterNodeVisitor::getUniqueName(const std::string& defaultValue, const std::string & _defaultPrefix, bool nameIsPath) {
if (_defaultPrefix.length()>=4) throw "Default prefix is too long"; // Arbitrarily defined to 3 chars. You can modify this, but you may have to change the code so that finding a number is okay, even when changing the default prefix length.
// Tests if default name is valid and unique
bool defaultIs83 = is83(defaultValue);
bool defaultIsValid = nameIsPath ? is3DSpath(defaultValue) : defaultIs83;
if (defaultIsValid && _nameMap.find(defaultValue) == _nameMap.end()) {
_nameMap.insert(defaultValue);
return defaultValue;
}
std::string defaultPrefix(_defaultPrefix.empty() ? "_" : _defaultPrefix);
unsigned int max_val = 0;
std::string truncDefaultValue = "";
for (unsigned int i = 0; i < std::min<unsigned int>(defaultValue.size(), 4); ++i)
{
if (defaultValue[i] == '.')
{
truncDefaultValue = defaultValue.substr(0, i);
break;
}
}
if (truncDefaultValue.empty())
truncDefaultValue = defaultValue.substr(0, std::min<unsigned int>(defaultValue.size(), 4));
std::map<std::string, unsigned int>::iterator pairPrefix;
defaultIs83 = is83(truncDefaultValue);
if (defaultIs83)
{
max_val = static_cast<unsigned int>(pow(10., 8. - truncDefaultValue.length() - 1)) -1; // defaultPrefix.length()-1 because we add an underscore ("_")
pairPrefix = _mapPrefix.find(truncDefaultValue);
}
if (defaultIs83 && (_mapPrefix.end() == pairPrefix || pairPrefix->second <= max_val))
{
defaultPrefix = truncDefaultValue;
}
else
{
max_val = static_cast<unsigned int>(pow(10., 8. - defaultPrefix.length() - 1)) - 1; // defaultPrefix.length()-1 because we add an underscore ("_")
pairPrefix = _mapPrefix.find(defaultPrefix);
}
unsigned int searchStart = 0;
if (pairPrefix != _mapPrefix.end())
searchStart = pairPrefix->second;
for(unsigned int i = searchStart; i <= max_val; ++i) {
std::stringstream ss;
ss << defaultPrefix << "_" << i;
const std::string & res = ss.str();
if (_nameMap.find(res) == _nameMap.end()) {
if (pairPrefix != _mapPrefix.end())
{
pairPrefix->second = i + 1;
}
else
{
_mapPrefix.insert(std::make_pair(defaultPrefix, i + 1));
}
_nameMap.insert(res);
return res;
}
}
if (defaultPrefix == "_") _lastGeneratedNumberedName = max_val;
throw "No more names available! Is default prefix too long?";
}
int WriterNodeVisitor::processStateSet(osg::StateSet* ss)
{
MaterialMap::const_iterator itr = _materialMap.find(ss);
if (itr != _materialMap.end()) {
assert(itr->second.index>=0);
return itr->second.index;
}
osg::Material* mat = dynamic_cast<osg::Material*>(ss->getAttribute(osg::StateAttribute::MATERIAL));
osg::Texture* tex = dynamic_cast<osg::Texture*>(ss->getTextureAttribute(0, osg::StateAttribute::TEXTURE));
if (mat || tex)
{
int matNum = _lastMaterialIndex;
_materialMap.insert(std::make_pair(osg::ref_ptr<osg::StateSet>(ss), Material(*this, ss, mat, tex, matNum) ));
++_lastMaterialIndex;
return matNum;
}
return -1;
}
/**
* Add a vertice to the index and link him with the Triangle index and the drawable.
* \param index_vert is the map where the vertice are stored.
* \param index is the indice of the vertice's position in the vec3.
* \param drawable_n is the number of the drawable.
* \return the position of the vertice in the final mesh.
*/
unsigned int
WriterNodeVisitor::getMeshIndexForGeometryIndex(MapIndices & index_vert,
unsigned int index,
unsigned int drawable_n)
{
MapIndices::iterator itIndex = index_vert.find(std::make_pair(index, drawable_n));
if (itIndex == index_vert.end()) {
unsigned int indexMesh = index_vert.size();
index_vert.insert(std::make_pair(std::make_pair(index, drawable_n), indexMesh));
return indexMesh;
}
return itIndex->second;
}
void
WriterNodeVisitor::buildMesh(osg::Geode & geo,
MapIndices & index_vert,
bool texcoords,
Lib3dsMesh * mesh)
{
osg::notify(osg::DEBUG_INFO) << "Building Mesh" << std::endl;
if (!mesh) throw "Allocation error"; // TODO
lib3ds_mesh_resize_vertices(mesh, index_vert.size(), texcoords ? 1 : 0, 0);
// Write points
for(MapIndices::iterator it = index_vert.begin(); it != index_vert.end();++it)
{
osg::Geometry *g = geo.getDrawable( it->first.second )->asGeometry();
assert(g->getVertexArray());
if (g->getVertexArray()->getType() != osg::Array::Vec3ArrayType)
throw "Vertex array is not Vec3. Not implemented"; // TODO
const osg::Vec3Array & vecs= *static_cast<osg::Vec3Array *>(g->getVertexArray());
copyOsgVectorToLib3dsVector(mesh->vertices[it->second], vecs[it->first.first]);
}
// Write texture coords (Texture 0 only)
if (texcoords)
{
for(MapIndices::iterator it = index_vert.begin(); it != index_vert.end(); ++it)
{
osg::Geometry *g = geo.getDrawable( it->first.second )->asGeometry();
osg::Array * array = g->getTexCoordArray(0);
if(array)
{
if (g->getTexCoordArray(0)->getType() != osg::Array::Vec2ArrayType)
throw "Texture coords array is not Vec2. Not implemented"; // TODO
const osg::Vec2Array & vecs= *static_cast<osg::Vec2Array *>(array);
mesh->texcos[it->second][0] = vecs[it->first.first][0];
mesh->texcos[it->second][1] = vecs[it->first.first][1];
}
}
}
lib3ds_file_insert_mesh(file3ds, mesh, _lastMeshIndex);
++_lastMeshIndex;
Lib3dsMeshInstanceNode * node3ds = lib3ds_node_new_mesh_instance(mesh, mesh->name, NULL, NULL, NULL);
lib3ds_file_append_node(file3ds, reinterpret_cast<Lib3dsNode*>(node3ds), reinterpret_cast<Lib3dsNode*>(_cur3dsNode));
}
unsigned int
WriterNodeVisitor::calcVertices(osg::Geode & geo)
{
unsigned int numVertice = 0;
for (unsigned int i = 0; i < geo.getNumDrawables(); ++i)
{
osg::Geometry *g = geo.getDrawable( i )->asGeometry();
assert(g->getVertexArray());
if (g->getVertexArray()->getType() != osg::Array::Vec3ArrayType)
throw "Vertex array is not Vec3. Not implemented"; // TODO
const osg::Vec3Array & vecs= *static_cast<osg::Vec3Array *>(g->getVertexArray());
numVertice += vecs.getNumElements();
}
return numVertice;
}
void
WriterNodeVisitor::buildFaces(osg::Geode & geo,
ListTriangle & listTriangles,
bool texcoords)
{
MapIndices index_vert;
unsigned int nbFace = 0;
Lib3dsMesh *mesh = lib3ds_mesh_new( getUniqueName(geo.getName().empty() ? geo.className() : geo.getName(), "geo").c_str() );
unsigned int nbTriangles = listTriangles.size();
lib3ds_mesh_resize_faces(mesh, nbTriangles);
unsigned int nbVertices = calcVertices(geo);
if (listTriangles.size() >= MAX_FACES-2 ||
((nbVertices) >= MAX_VERTICES-2))
{
osg::notify(osg::ALWAYS) << "Sorting elements..." << std::endl;
WriterCompareTriangle cmp(geo, nbVertices);
std::sort(listTriangles.begin(), listTriangles.end(), cmp);
}
for (ListTriangle::iterator it = listTriangles.begin(); it != listTriangles.end(); ++it) //Go through the triangle list to define meshs
{
// Using -2 due to the fact that we treat 3 faces in one time (=the algorithm may overrun the limit by 2).
if ((index_vert.size() >= MAX_VERTICES-2 || // If mesh is full
nbFace >= MAX_FACES-2))
{
// Finnishing mesh
lib3ds_mesh_resize_faces(mesh, nbFace);
buildMesh(geo, index_vert, texcoords, mesh);
// Creating a new mesh
index_vert.clear();
mesh = lib3ds_mesh_new( getUniqueName(geo.getName().empty() ? geo.className() : geo.getName(), "geo").c_str());
nbTriangles -= nbFace;
nbFace = 0;
lib3ds_mesh_resize_faces(mesh, nbTriangles);
}
Lib3dsFace & face = mesh->faces[nbFace++];
face.index[0] = getMeshIndexForGeometryIndex(index_vert, it->first.t1, it->second);
face.index[1] = getMeshIndexForGeometryIndex(index_vert, it->first.t2, it->second);
face.index[2] = getMeshIndexForGeometryIndex(index_vert, it->first.t3, it->second);
face.material = it->first.material;
}
buildMesh(geo, index_vert, texcoords, mesh); //When a Mesh is completed without restriction of vertices number
}
void
WriterNodeVisitor::createListTriangle(osg::Geometry * geo,
ListTriangle & listTriangles,
bool & texcoords,
unsigned int & drawable_n)
{
unsigned int nbVertices = 0;
{
if (geo->getVertexArray() && geo->getVertexArray()->getType() != osg::Array::Vec3ArrayType)
throw "Vertex array is not Vec3. Not implemented"; // TODO
const osg::Vec3Array * vecs = geo->getVertexArray() ? static_cast<osg::Vec3Array *>(geo->getVertexArray()) : NULL;
if (vecs)
{
nbVertices = geo->getVertexArray()->getNumElements();
// Texture coords
if (geo->getTexCoordArray(0) && geo->getTexCoordArray(0)->getType() != osg::Array::Vec2ArrayType)
throw "Texture coords array is not Vec2. Not implemented"; // TODO
const osg::Vec2Array * texvecs = geo->getTexCoordArray(0) ? static_cast<osg::Vec2Array *>(geo->getTexCoordArray(0)) : NULL;
if (texvecs)
{
unsigned int nb = geo->getTexCoordArray(0)->getNumElements();
if (nb != geo->getVertexArray()->getNumElements()) throw "There are more/less texture coords than vertices!";
texcoords = true;
}
}
}
if (nbVertices==0) return;
int material = processStateSet(_currentStateSet.get());
for(unsigned int i = 0; i < geo->getNumPrimitiveSets(); ++i) //Fill the Triangle List
{
osg::PrimitiveSet* ps = geo->getPrimitiveSet(i);
PrimitiveIndexWriter pif(geo, listTriangles, drawable_n, material);
ps->accept(pif);
}
}
bool WriterNodeVisitor::suceedLastApply() const
{
return _suceedLastApply;
}
void WriterNodeVisitor::failedApply()
{
_suceedLastApply = false;
osg::notify(osg::NOTICE) << "Error going through node" << std::endl;
}
void WriterNodeVisitor::apply( osg::Geode &node )
{
pushStateSet(node.getStateSet());
//_nameStack.push_back(node.getName());
//osg::Matrix m = osg::computeLocalToWorld(getNodePath());
unsigned int count = node.getNumDrawables();
ListTriangle listTriangles;
bool texcoords = false;
for ( unsigned int i = 0; i < count; i++ )
{
osg::Geometry *g = node.getDrawable( i )->asGeometry();
if ( g != NULL )
{
pushStateSet(g->getStateSet());
createListTriangle(g, listTriangles, texcoords, i);
popStateSet(g->getStateSet());
}
}
if (count > 0)
{
buildFaces(node, listTriangles, texcoords);
}
popStateSet(node.getStateSet());
//_nameStack.pop_back();
if (suceedLastApply())
traverse(node);
}
void WriterNodeVisitor::apply(osg::Group &node)
{
Lib3dsMeshInstanceNode * parent = _cur3dsNode;
Lib3dsMeshInstanceNode * node3ds = lib3ds_node_new_mesh_instance(NULL, getUniqueName(node.getName().empty() ? node.className() : getFileName(node.getName()), "grp").c_str(), NULL, NULL, NULL);
lib3ds_file_append_node(file3ds, reinterpret_cast<Lib3dsNode*>(node3ds), reinterpret_cast<Lib3dsNode*>(parent));
_cur3dsNode = node3ds;
if (suceedLastApply())
traverse(node);
_cur3dsNode = parent;
}
void WriterNodeVisitor::apply(osg::MatrixTransform &node)
{
Lib3dsMeshInstanceNode * parent = _cur3dsNode;
const osg::Matrix & m = node.getMatrix();
//const osg::Matrix m( osg::computeWorldToLocal(getNodePath()) ); // [NEEDS TESTING!] 3DS matrices always contain world to local transformation (not local transform; ie. from parent)
// Transform data used to be given to lib3ds_node_new_mesh_instance(), but it seems buggy (pivot problem? bug in conversion?).
float pos[3];
float scl[3];
float rot[4];
osg::Vec3 osgScl, osgPos;
osg::Quat osgRot, osgSo;
m.decompose(osgPos, osgRot, osgScl, osgSo);
copyOsgVectorToLib3dsVector(pos, osgPos);
copyOsgVectorToLib3dsVector(scl, osgScl);
copyOsgQuatToLib3dsQuat(rot, osgRot);
Lib3dsMeshInstanceNode * node3ds = lib3ds_node_new_mesh_instance
(NULL, getUniqueName(node.getName().empty() ? node.className() : node.getName(), "mtx").c_str(), pos, scl, rot);
//// Create a mesh instance with no transform and then copy the matrix (doesn't work)
//Lib3dsMeshInstanceNode * node3ds = lib3ds_node_new_mesh_instance
// (NULL, getUniqueName(node.getName().empty() ? node.className() : node.getName(), "mtx").c_str(), NULL, NULL, NULL);
// copyOsgMatrixToLib3dsMatrix(node3ds->base.matrix, m);
lib3ds_file_append_node(file3ds, reinterpret_cast<Lib3dsNode*>(node3ds), reinterpret_cast<Lib3dsNode*>(parent));
_cur3dsNode = node3ds;
if (suceedLastApply())
traverse(node);
_cur3dsNode = parent;
}

View File

@@ -0,0 +1,228 @@
// -*-c++-*-
/*
* 3DS reader/writer for Open Scene Graph
*
* Copyright (C) ???
*
* Writing support added 2007 by Sukender (Benoit Neil), http://sukender.free.fr,
* strongly inspired by the OBJ writer object by Stephan Huber
*
* The Open Scene Graph (OSG) is a cross platform C++/OpenGL library for
* real-time rendering of large 3D photo-realistic models.
* The OSG homepage is http://www.openscenegraph.org/
*/
#ifndef _3DS_WRITER_NODE_VISITOR_HEADER__
#define _3DS_WRITER_NODE_VISITOR_HEADER__
#include <string>
#include <stack>
#include <sstream>
#include <osg/Notify>
#include <osg/Node>
#include <osg/MatrixTransform>
#include <osg/Geode>
#include <osg/Geometry>
#include <osg/StateSet>
#include <osg/Material>
#include <osg/Texture2D>
#include <osg/TexGen>
#include <osg/TexMat>
#include <osgDB/Registry>
#include <osgDB/ReadFile>
#include <osgDB/FileUtils>
#include <osgDB/FileNameUtils>
#include <map>
#include "lib3ds/lib3ds.h"
#include "WriterCompareTriangle.h"
void copyOsgMatrixToLib3dsMatrix(Lib3dsMatrix lib3ds_matrix, const osg::Matrix& osg_matrix);
typedef std::map<std::pair<unsigned int, unsigned int>, unsigned int> MapIndices;
typedef std::vector<std::pair<Triangle, int> > ListTriangle; //the int is the drawable of the triangle
class WriterNodeVisitor: public osg::NodeVisitor {
public:
static const unsigned int MAX_VERTICES = 65000;
static const unsigned int MAX_FACES = MAX_VERTICES;
WriterNodeVisitor(Lib3dsFile * file3ds, const std::string & fileName,
const osgDB::ReaderWriter::Options* options,
const std::string & srcDirectory) :
osg::NodeVisitor(osg::NodeVisitor::TRAVERSE_ALL_CHILDREN),
_suceedLastApply(true),
_srcDirectory(srcDirectory),
file3ds(file3ds),
_currentStateSet(new osg::StateSet()),
_lastGeneratedNumberedName(0),
_lastMaterialIndex(0),
_lastMeshIndex(0),
_cur3dsNode(NULL),
options(options),
_imageCount(0)
{
//supportsOption("flipTexture", "flip texture upside-down");
if (!fileName.empty())
_directory = options->getDatabasePathList().empty() ? osgDB::getFilePath(fileName) : options->getDatabasePathList().front();
}
bool suceedLastApply() const;
void failedApply();
virtual void apply(osg::Geode &node);
virtual void apply(osg::Group &node);
virtual void apply(osg::MatrixTransform &node);
void traverse (osg::Node &node)
{
pushStateSet(node.getStateSet());
osg::NodeVisitor::traverse( node );
popStateSet(node.getStateSet());
}
void pushStateSet(osg::StateSet* ss)
{
if (NULL!=ss) {
// Save our current stateset
_stateSetStack.push(_currentStateSet.get());
// merge with node stateset
_currentStateSet = static_cast<osg::StateSet*>(_currentStateSet->clone(osg::CopyOp::SHALLOW_COPY));
_currentStateSet->merge(*ss);
}
}
void popStateSet(osg::StateSet* ss)
{
if (NULL!=ss) {
// restore the previous stateset
_currentStateSet = _stateSetStack.top();
_stateSetStack.pop();
}
}
void writeMaterials();
///\todo Add support for 2nd texture, opacity_map, bump_map, specular_map, shininess_map, self_illum_map, reflection_map.
class Material {
public:
Material(WriterNodeVisitor & writerNodeVisitor, osg::StateSet * stateset, osg::Material* mat, osg::Texture* tex, int index=-1);
int index; ///< Index in the 3DS file
osg::Vec4 diffuse, ambient, specular;
float shininess;
float transparency;
bool double_sided;
std::string name;
osg::ref_ptr<osg::Image> image;
bool texture_transparency;
bool texture_no_tile;
protected:
Material() : index(-1) {}
};
protected:
struct CompareStateSet
{
bool operator()(const osg::ref_ptr<osg::StateSet>& ss1, const osg::ref_ptr<osg::StateSet>& ss2) const
{
return *ss1 < *ss2;
}
};
private:
WriterNodeVisitor& operator = (const WriterNodeVisitor&) { return *this; }
/**
* Fill the faces field of the mesh and call buildMesh().
* \param geo is the geode who contain vertice and faces.
* \param listTriangles contain all the meshs faces.
* \param texcoords tell us if we have to treat texture coord.
*/
void buildFaces(osg::Geode & geo, ListTriangle & listTriangles, bool texcoords);
/**
* Calculate the number of vertices in the geode.
* \return the number of vertices in the geode.
*/
unsigned int
calcVertices(osg::Geode & geo);
/**
* Build a mesh
* \param geo is the geode who contain vertice and faces
* \param index_vert is the index used to build the new mesh
* \param texcoords tell us if we have to treat texture coord
* \param mesh is the mesh with faces filled
* \return the place of the box in the vector.
* \sa See cutScene() about the definition of the boxes for faces sorting.
*/
void
buildMesh(osg::Geode & geo,
MapIndices & index_vert,
bool texcoords,
Lib3dsMesh *mesh);
/**
* Add a vertice to the index and link him with the Triangle index and the drawable.
* \param index_vert is the map where the vertice are stored.
* \param index is the indice of the vertice's position in the vec3.
* \param drawable_n is the number of the drawable.
* \return the position of the vertice in the final mesh.
*/
unsigned int
getMeshIndexForGeometryIndex(MapIndices & index_vert,
unsigned int index,
unsigned int drawable_n);
/**
* Create the list of faces from the geode.
* \param geo is the geode to study.
* \param listTriangles is the list to fill.
* \param texcoords tell us if we have to treat texture coord.
* \param drawable_n tell us which drawable we are building.
*/
void createListTriangle(osg::Geometry * geo,
ListTriangle & listTriangles,
bool & texcoords,
unsigned int & drawable_n);
int processStateSet(osg::StateSet* stateset);
std::string getUniqueName(const std::string& defaultvalue="", const std::string & defaultPrefix = "", bool nameIsPath = false);
std::string export3DSTexture(const osg::Image * image, const std::string & fileName);
typedef std::stack<osg::ref_ptr<osg::StateSet> > StateSetStack;
typedef std::map< osg::ref_ptr<osg::StateSet>, Material, CompareStateSet> MaterialMap;
bool _suceedLastApply;
std::string _directory;
std::string _srcDirectory;
Lib3dsFile * file3ds;
StateSetStack _stateSetStack;
osg::ref_ptr<osg::StateSet> _currentStateSet;
std::map<std::string, unsigned int> _mapPrefix;
std::set<std::string> _nameMap;
MaterialMap _materialMap;
unsigned int _lastGeneratedNumberedName;
unsigned int _lastMaterialIndex;
unsigned int _lastMeshIndex;
Lib3dsMeshInstanceNode * _cur3dsNode;
const osgDB::ReaderWriter::Options* options;
unsigned int _imageCount;
};
#endif

View File

@@ -1,305 +0,0 @@
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#define LIB3DS_EXPORT
#include "atmosphere.h"
#include "chunk.h"
#include "readwrite.h"
/*!
* \defgroup atmosphere Atmosphere Settings
*
* \author J.E. Hoffmann <je-h@gmx.net>
*/
static Lib3dsBool
fog_read(Lib3dsFog *fog, iostream *strm)
{
Lib3dsChunk c;
Lib3dsWord chunk;
if (!lib3ds_chunk_read_start(&c, LIB3DS_FOG, strm)) {
return(LIB3DS_FALSE);
}
fog->near_plane=lib3ds_float_read(strm);
fog->near_density=lib3ds_float_read(strm);
fog->far_plane=lib3ds_float_read(strm);
fog->far_density=lib3ds_float_read(strm);
lib3ds_chunk_read_tell(&c, strm);
while ((chunk=lib3ds_chunk_read_next(&c, strm))!=0) {
switch (chunk) {
case LIB3DS_LIN_COLOR_F:
{
int i;
for (i=0; i<3; ++i) {
fog->col[i]=lib3ds_float_read(strm);
}
}
break;
case LIB3DS_COLOR_F:
break;
case LIB3DS_FOG_BGND:
{
fog->fog_background=LIB3DS_TRUE;
}
break;
default:
lib3ds_chunk_unknown(chunk);
}
}
lib3ds_chunk_read_end(&c, strm);
return(LIB3DS_TRUE);
}
static Lib3dsBool
layer_fog_read(Lib3dsLayerFog *fog, iostream *strm)
{
Lib3dsChunk c;
Lib3dsWord chunk;
if (!lib3ds_chunk_read_start(&c, LIB3DS_LAYER_FOG, strm)) {
return(LIB3DS_FALSE);
}
fog->near_y=lib3ds_float_read(strm);
fog->far_y=lib3ds_float_read(strm);
fog->density=lib3ds_float_read(strm);
fog->flags=lib3ds_dword_read(strm);
lib3ds_chunk_read_tell(&c, strm);
while ((chunk=lib3ds_chunk_read_next(&c, strm))!=0) {
switch (chunk) {
case LIB3DS_LIN_COLOR_F:
lib3ds_rgb_read(fog->col,strm);
break;
case LIB3DS_COLOR_F:
lib3ds_rgb_read(fog->col,strm);
break;
default:
lib3ds_chunk_unknown(chunk);
}
}
lib3ds_chunk_read_end(&c, strm);
return(LIB3DS_TRUE);
}
static Lib3dsBool
distance_cue_read(Lib3dsDistanceCue *cue, iostream *strm)
{
Lib3dsChunk c;
Lib3dsWord chunk;
if (!lib3ds_chunk_read_start(&c, LIB3DS_DISTANCE_CUE, strm)) {
return(LIB3DS_FALSE);
}
cue->near_plane=lib3ds_float_read(strm);
cue->near_dimming=lib3ds_float_read(strm);
cue->far_plane=lib3ds_float_read(strm);
cue->far_dimming=lib3ds_float_read(strm);
lib3ds_chunk_read_tell(&c, strm);
while ((chunk=lib3ds_chunk_read_next(&c, strm))!=0) {
switch (chunk) {
case LIB3DS_DCUE_BGND:
{
cue->cue_background=LIB3DS_TRUE;
}
break;
default:
lib3ds_chunk_unknown(chunk);
}
}
lib3ds_chunk_read_end(&c, strm);
return(LIB3DS_TRUE);
}
/*!
* \ingroup atmosphere
*/
Lib3dsBool
lib3ds_atmosphere_read(Lib3dsAtmosphere *atmosphere, iostream *strm)
{
Lib3dsChunk c;
if (!lib3ds_chunk_read(&c, strm)) {
return(LIB3DS_FALSE);
}
switch (c.chunk) {
case LIB3DS_FOG:
{
lib3ds_chunk_read_reset(&c, strm);
if (!fog_read(&atmosphere->fog, strm)) {
return(LIB3DS_FALSE);
}
}
break;
case LIB3DS_LAYER_FOG:
{
lib3ds_chunk_read_reset(&c, strm);
if (!layer_fog_read(&atmosphere->layer_fog, strm)) {
return(LIB3DS_FALSE);
}
}
break;
case LIB3DS_DISTANCE_CUE:
{
lib3ds_chunk_read_reset(&c, strm);
if (!distance_cue_read(&atmosphere->dist_cue, strm)) {
return(LIB3DS_FALSE);
}
}
break;
case LIB3DS_USE_FOG:
{
atmosphere->fog.use=LIB3DS_TRUE;
}
break;
case LIB3DS_USE_LAYER_FOG:
{
atmosphere->fog.use=LIB3DS_TRUE;
}
break;
case LIB3DS_USE_DISTANCE_CUE:
{
atmosphere->dist_cue.use=LIB3DS_TRUE;
}
break;
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup atmosphere
*/
Lib3dsBool
lib3ds_atmosphere_write(Lib3dsAtmosphere *atmosphere, iostream *strm)
{
if (atmosphere->fog.use) { /*---- LIB3DS_FOG ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_FOG;
if (!lib3ds_chunk_write_start(&c,strm)) {
return(LIB3DS_FALSE);
}
lib3ds_float_write(atmosphere->fog.near_plane,strm);
lib3ds_float_write(atmosphere->fog.near_density,strm);
lib3ds_float_write(atmosphere->fog.far_plane,strm);
lib3ds_float_write(atmosphere->fog.far_density,strm);
{
Lib3dsChunk c;
c.chunk=LIB3DS_COLOR_F;
c.size=18;
lib3ds_chunk_write(&c,strm);
lib3ds_rgb_write(atmosphere->fog.col,strm);
}
if (atmosphere->fog.fog_background) {
Lib3dsChunk c;
c.chunk=LIB3DS_FOG_BGND;
c.size=6;
lib3ds_chunk_write(&c,strm);
}
if (!lib3ds_chunk_write_end(&c,strm)) {
return(LIB3DS_FALSE);
}
}
if (atmosphere->layer_fog.use) { /*---- LIB3DS_LAYER_FOG ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_LAYER_FOG;
c.size=40;
lib3ds_chunk_write(&c,strm);
lib3ds_float_write(atmosphere->layer_fog.near_y,strm);
lib3ds_float_write(atmosphere->layer_fog.far_y,strm);
lib3ds_float_write(atmosphere->layer_fog.near_y,strm);
lib3ds_dword_write(atmosphere->layer_fog.flags,strm);
{
Lib3dsChunk c;
c.chunk=LIB3DS_COLOR_F;
c.size=18;
lib3ds_chunk_write(&c,strm);
lib3ds_rgb_write(atmosphere->fog.col,strm);
}
}
if (atmosphere->dist_cue.use) { /*---- LIB3DS_DISTANCE_CUE ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_DISTANCE_CUE;
if (!lib3ds_chunk_write_start(&c,strm)) {
return(LIB3DS_FALSE);
}
lib3ds_float_write(atmosphere->dist_cue.near_plane,strm);
lib3ds_float_write(atmosphere->dist_cue.near_dimming,strm);
lib3ds_float_write(atmosphere->dist_cue.far_plane,strm);
lib3ds_float_write(atmosphere->dist_cue.far_dimming,strm);
if (atmosphere->dist_cue.cue_background) {
Lib3dsChunk c;
c.chunk=LIB3DS_DCUE_BGND;
c.size=6;
lib3ds_chunk_write(&c,strm);
}
if (!lib3ds_chunk_write_end(&c,strm)) {
return(LIB3DS_FALSE);
}
}
if (atmosphere->fog.use) { /*---- LIB3DS_USE_FOG ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_USE_FOG;
c.size=6;
lib3ds_chunk_write(&c,strm);
}
if (atmosphere->layer_fog.use) { /*---- LIB3DS_USE_LAYER_FOG ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_USE_LAYER_FOG;
c.size=6;
lib3ds_chunk_write(&c,strm);
}
if (atmosphere->dist_cue.use) { /*---- LIB3DS_USE_DISTANCE_CUE ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_USE_V_GRADIENT;
c.size=6;
lib3ds_chunk_write(&c,strm);
}
return(LIB3DS_TRUE);
}
/*!
\typedef Lib3dsAtmosphere
\ingroup atmosphere
\sa _Lib3dsAtmosphere
*/

View File

@@ -1,103 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_ATMOSPHERE_H
#define INCLUDED_LIB3DS_ATMOSPHERE_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TYPES_H
#include "types.h"
#endif
#include <iostream>
using namespace std;
#ifdef __cplusplus
extern "C" {
#endif
/*!
* Fog atmosphere settings
* \ingroup atmosphere
*/
typedef struct _Lib3dsFog {
Lib3dsBool use;
Lib3dsRgb col;
Lib3dsBool fog_background;
Lib3dsFloat near_plane;
Lib3dsFloat near_density;
Lib3dsFloat far_plane;
Lib3dsFloat far_density;
} Lib3dsFog;
/*!
* Layer fog atmosphere flags
* \ingroup atmosphere
*/
typedef enum _Lib3dsLayerFogFlags {
LIB3DS_BOTTOM_FALL_OFF =0x00000001,
LIB3DS_TOP_FALL_OFF =0x00000002,
LIB3DS_FOG_BACKGROUND =0x00100000
} Lib3dsLayerFogFlags;
/*!
* Layer fog atmosphere settings
* \ingroup atmosphere
*/
typedef struct _Lib3dsLayerFog {
Lib3dsBool use;
Lib3dsDword flags;
Lib3dsRgb col;
Lib3dsFloat near_y;
Lib3dsFloat far_y;
Lib3dsFloat density;
} Lib3dsLayerFog;
/*!
* Distance cue atmosphere settings
* \ingroup atmosphere
*/
typedef struct _Lib3dsDistanceCue {
Lib3dsBool use;
Lib3dsBool cue_background;
Lib3dsFloat near_plane;
Lib3dsFloat near_dimming;
Lib3dsFloat far_plane;
Lib3dsFloat far_dimming;
} Lib3dsDistanceCue;
/*!
* Atmosphere settings
* \ingroup atmosphere
*/
struct _Lib3dsAtmosphere {
Lib3dsFog fog;
Lib3dsLayerFog layer_fog;
Lib3dsDistanceCue dist_cue;
};
extern LIB3DSAPI Lib3dsBool lib3ds_atmosphere_read(Lib3dsAtmosphere *atmosphere, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_atmosphere_write(Lib3dsAtmosphere *atmosphere, iostream *strm);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -1,264 +0,0 @@
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#define LIB3DS_EXPORT
#include "background.h"
#include "chunk.h"
#include "readwrite.h"
#include <string.h>
#include <math.h>
/*!
* \defgroup background Background Settings
*
* \author J.E. Hoffmann <je-h@gmx.net>
*/
static Lib3dsBool
solid_bgnd_read(Lib3dsBackground *background, iostream *strm)
{
Lib3dsChunk c;
Lib3dsWord chunk;
if (!lib3ds_chunk_read_start(&c, LIB3DS_SOLID_BGND, strm)) {
return(LIB3DS_FALSE);
}
while ((chunk=lib3ds_chunk_read_next(&c, strm))!=0) {
switch (chunk) {
case LIB3DS_LIN_COLOR_F:
lib3ds_rgb_read(background->solid.col, strm);
break;
case LIB3DS_COLOR_F:
lib3ds_rgb_read(background->solid.col, strm);
break;
default:
lib3ds_chunk_unknown(chunk);
}
}
lib3ds_chunk_read_end(&c, strm);
return(LIB3DS_TRUE);
}
static Lib3dsBool
v_gradient_read(Lib3dsBackground *background, iostream *strm)
{
Lib3dsChunk c;
Lib3dsWord chunk;
int index[2];
Lib3dsRgb col[2][3];
int have_lin=0;
if (!lib3ds_chunk_read_start(&c, LIB3DS_V_GRADIENT, strm)) {
return(LIB3DS_FALSE);
}
background->gradient.percent=lib3ds_float_read(strm);
lib3ds_chunk_read_tell(&c, strm);
index[0]=index[1]=0;
while ((chunk=lib3ds_chunk_read_next(&c, strm))!=0) {
switch (chunk) {
case LIB3DS_COLOR_F:
lib3ds_rgb_read(col[0][index[0]],strm);
index[0]++;
break;
case LIB3DS_LIN_COLOR_F:
lib3ds_rgb_read(col[1][index[1]],strm);
index[1]++;
have_lin=1;
break;
default:
lib3ds_chunk_unknown(chunk);
}
}
{
int i;
for (i=0; i<3; ++i) {
background->gradient.top[i]=col[have_lin][0][i];
background->gradient.middle[i]=col[have_lin][1][i];
background->gradient.bottom[i]=col[have_lin][2][i];
}
}
lib3ds_chunk_read_end(&c, strm);
return(LIB3DS_TRUE);
}
/*!
* \ingroup background
*/
Lib3dsBool
lib3ds_background_read(Lib3dsBackground *background, iostream *strm)
{
Lib3dsChunk c;
if (!lib3ds_chunk_read(&c, strm)) {
return(LIB3DS_FALSE);
}
switch (c.chunk) {
case LIB3DS_BIT_MAP:
{
if (!lib3ds_string_read(background->bitmap.name, 64, strm)) {
return(LIB3DS_FALSE);
}
}
break;
case LIB3DS_SOLID_BGND:
{
lib3ds_chunk_read_reset(&c, strm);
if (!solid_bgnd_read(background, strm)) {
return(LIB3DS_FALSE);
}
}
break;
case LIB3DS_V_GRADIENT:
{
lib3ds_chunk_read_reset(&c, strm);
if (!v_gradient_read(background, strm)) {
return(LIB3DS_FALSE);
}
}
break;
case LIB3DS_USE_BIT_MAP:
{
background->bitmap.use=LIB3DS_TRUE;
}
break;
case LIB3DS_USE_SOLID_BGND:
{
background->solid.use=LIB3DS_TRUE;
}
break;
case LIB3DS_USE_V_GRADIENT:
{
background->gradient.use=LIB3DS_TRUE;
}
break;
}
return(LIB3DS_TRUE);
}
static Lib3dsBool
colorf_write(Lib3dsRgba rgb, iostream *strm)
{
Lib3dsChunk c;
c.chunk=LIB3DS_COLOR_F;
c.size=18;
lib3ds_chunk_write(&c,strm);
lib3ds_rgb_write(rgb,strm);
c.chunk=LIB3DS_LIN_COLOR_F;
c.size=18;
lib3ds_chunk_write(&c,strm);
lib3ds_rgb_write(rgb,strm);
return(LIB3DS_TRUE);
}
static Lib3dsBool
colorf_defined(Lib3dsRgba rgb)
{
int i;
for (i=0; i<3; ++i) {
if (fabs(rgb[i])>LIB3DS_EPSILON) {
break;
}
}
return(i<3);
}
/*!
* \ingroup background
*/
Lib3dsBool
lib3ds_background_write(Lib3dsBackground *background, iostream *strm)
{
if (strlen(background->bitmap.name)) { /*---- LIB3DS_BIT_MAP ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_BIT_MAP;
c.size=6+1+strlen(background->bitmap.name);
lib3ds_chunk_write(&c,strm);
lib3ds_string_write(background->bitmap.name, strm);
}
if (colorf_defined(background->solid.col)) { /*---- LIB3DS_SOLID_BGND ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_SOLID_BGND;
c.size=42;
lib3ds_chunk_write(&c,strm);
colorf_write(background->solid.col,strm);
}
if (colorf_defined(background->gradient.top) ||
colorf_defined(background->gradient.middle) ||
colorf_defined(background->gradient.bottom)) { /*---- LIB3DS_V_GRADIENT ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_V_GRADIENT;
c.size=118;
lib3ds_chunk_write(&c,strm);
lib3ds_float_write(background->gradient.percent,strm);
colorf_write(background->gradient.top,strm);
colorf_write(background->gradient.middle,strm);
colorf_write(background->gradient.bottom,strm);
}
if (background->bitmap.use) { /*---- LIB3DS_USE_BIT_MAP ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_USE_BIT_MAP;
c.size=6;
lib3ds_chunk_write(&c,strm);
}
if (background->solid.use) { /*---- LIB3DS_USE_SOLID_BGND ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_USE_SOLID_BGND;
c.size=6;
lib3ds_chunk_write(&c,strm);
}
if (background->gradient.use) { /*---- LIB3DS_USE_V_GRADIENT ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_USE_V_GRADIENT;
c.size=6;
lib3ds_chunk_write(&c,strm);
}
return(LIB3DS_TRUE);
}
/*!
\typedef Lib3dsBackground
\ingroup background
\sa _Lib3dsBackground
*/

View File

@@ -1,88 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_BACKGROUND_H
#define INCLUDED_LIB3DS_BACKGROUND_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TYPES_H
#include "types.h"
#endif
#include <iostream>
using namespace std;
#ifdef __cplusplus
extern "C" {
#endif
/*!
* Bitmap background settings
* \ingroup background
*/
typedef struct _Lib3dsBitmap {
Lib3dsBool use;
char name[64];
} Lib3dsBitmap;
/*!
* Solid color background settings
* \ingroup background
*/
typedef struct _Lib3dsSolid {
Lib3dsBool use;
Lib3dsRgb col;
} Lib3dsSolid;
/*!
* Gradient background settings
* \ingroup background
*/
typedef struct _Lib3dsGradient {
Lib3dsBool use;
Lib3dsFloat percent;
Lib3dsRgb top;
Lib3dsRgb middle;
Lib3dsRgb bottom;
} Lib3dsGradient;
/*!
* Background settings
* \ingroup background
*/
struct _Lib3dsBackground {
Lib3dsBitmap bitmap;
Lib3dsSolid solid;
Lib3dsGradient gradient;
};
extern LIB3DSAPI Lib3dsBool lib3ds_background_read(Lib3dsBackground *background, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_background_write(Lib3dsBackground *background, iostream *strm);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -1,203 +0,0 @@
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#define LIB3DS_EXPORT
#include "camera.h"
#include "chunk.h"
#include "readwrite.h"
#include <stdlib.h>
#include <math.h>
#include <string.h>
#include "config.h"
#ifdef WITH_DMALLOC
#include <dmalloc.h>
#endif
/*!
* \defgroup camera Cameras
*
* \author J.E. Hoffmann <je-h@gmx.net>
*/
/*!
* \ingroup camera
*/
Lib3dsCamera*
lib3ds_camera_new(const char *name)
{
Lib3dsCamera *camera;
ASSERT(name);
ASSERT(strlen(name)<64);
camera=(Lib3dsCamera*)calloc(sizeof(Lib3dsCamera), 1);
if (!camera) {
return(0);
}
strcpy(camera->name, name);
camera->fov=45.0f;
return(camera);
}
/*!
* \ingroup camera
*/
void
lib3ds_camera_free(Lib3dsCamera *camera)
{
memset(camera, 0, sizeof(Lib3dsCamera));
free(camera);
}
/*!
* \ingroup camera
*/
void
lib3ds_camera_dump(Lib3dsCamera *camera)
{
ASSERT(camera);
printf(" name: %s\n", camera->name);
printf(" position: (%f, %f, %f)\n",
camera->position[0], camera->position[1], camera->position[2]);
printf(" target (%f, %f, %f)\n",
camera->target[0], camera->target[1], camera->target[2]);
printf(" roll: %f\n", camera->roll);
printf(" fov: %f\n", camera->fov);
printf(" see_cone: %s\n", camera->see_cone ? "yes" : "no");
printf(" near_range: %f\n", camera->near_range);
printf(" far_range: %f\n", camera->near_range);
printf("\n");
}
/*!
* \ingroup camera
*/
Lib3dsBool
lib3ds_camera_read(Lib3dsCamera *camera, iostream *strm)
{
Lib3dsChunk c;
Lib3dsWord chunk;
if (!lib3ds_chunk_read_start(&c, LIB3DS_N_CAMERA, strm)) {
return(LIB3DS_FALSE);
}
{
int i;
for (i=0; i<3; ++i) {
camera->position[i]=lib3ds_float_read(strm);
}
for (i=0; i<3; ++i) {
camera->target[i]=lib3ds_float_read(strm);
}
}
camera->roll=lib3ds_float_read(strm);
{
float s;
s=lib3ds_float_read(strm);
if (fabs(s)<LIB3DS_EPSILON) {
camera->fov=45.0;
}
else {
camera->fov=2400.0f/s;
}
}
lib3ds_chunk_read_tell(&c, strm);
while ((chunk=lib3ds_chunk_read_next(&c, strm))!=0) {
switch (chunk) {
case LIB3DS_CAM_SEE_CONE:
{
camera->see_cone=LIB3DS_TRUE;
}
break;
case LIB3DS_CAM_RANGES:
{
camera->near_range=lib3ds_float_read(strm);
camera->far_range=lib3ds_float_read(strm);
}
break;
default:
lib3ds_chunk_unknown(chunk);
}
}
lib3ds_chunk_read_end(&c, strm);
return(LIB3DS_TRUE);
}
/*!
* \ingroup camera
*/
Lib3dsBool
lib3ds_camera_write(Lib3dsCamera *camera, iostream *strm)
{
Lib3dsChunk c;
c.chunk=LIB3DS_N_CAMERA;
if (!lib3ds_chunk_write_start(&c,strm)) {
return(LIB3DS_FALSE);
}
lib3ds_vector_write(camera->position, strm);
lib3ds_vector_write(camera->target, strm);
lib3ds_float_write(camera->roll, strm);
if (fabs(camera->fov)<LIB3DS_EPSILON) {
lib3ds_float_write(2400.0f/45.0f, strm);
}
else {
lib3ds_float_write(2400.0f/camera->fov, strm);
}
if (camera->see_cone) {
Lib3dsChunk c;
c.chunk=LIB3DS_CAM_SEE_CONE;
c.size=6;
lib3ds_chunk_write(&c, strm);
}
{
Lib3dsChunk c;
c.chunk=LIB3DS_CAM_RANGES;
c.size=14;
lib3ds_chunk_write(&c, strm);
lib3ds_float_write(camera->near_range, strm);
lib3ds_float_write(camera->far_range, strm);
}
if (!lib3ds_chunk_write_end(&c,strm)) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
\typedef Lib3dsCamera
\ingroup camera
\sa _Lib3dsCamera
*/

View File

@@ -1,63 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_CAMERA_H
#define INCLUDED_LIB3DS_CAMERA_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TYPES_H
#include "types.h"
#endif
#include <iostream>
using namespace std;
#ifdef __cplusplus
extern "C" {
#endif
/*!
* Camera object
* \ingroup camera
*/
struct _Lib3dsCamera {
Lib3dsCamera *next;
char name[64];
Lib3dsVector position;
Lib3dsVector target;
Lib3dsFloat roll;
Lib3dsFloat fov;
Lib3dsBool see_cone;
Lib3dsFloat near_range;
Lib3dsFloat far_range;
};
extern LIB3DSAPI Lib3dsCamera* lib3ds_camera_new(const char *name);
extern LIB3DSAPI void lib3ds_camera_free(Lib3dsCamera *mesh);
extern LIB3DSAPI void lib3ds_camera_dump(Lib3dsCamera *camera);
extern LIB3DSAPI Lib3dsBool lib3ds_camera_read(Lib3dsCamera *camera, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_camera_write(Lib3dsCamera *camera, iostream *strm);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -1,307 +0,0 @@
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#define LIB3DS_EXPORT
#include "chunk.h"
#include "readwrite.h"
#include "chunktable.h"
#include <string.h>
#include <stdarg.h>
/*#define LIB3DS_CHUNK_DEBUG*/
/*#define LIB3DS_CHUNK_WARNING*/
/*!
* \defgroup chunk Chunk Handling
*
* \author J.E. Hoffmann <je-h@gmx.net>
*/
static Lib3dsBool enable_dump=LIB3DS_FALSE;
static Lib3dsBool enable_unknown=LIB3DS_FALSE;
static char lib3ds_chunk_level[128]="";
static void
lib3ds_chunk_debug_enter(Lib3dsChunk *)
{
strcat(lib3ds_chunk_level, " ");
}
static void
lib3ds_chunk_debug_leave(Lib3dsChunk *)
{
lib3ds_chunk_level[strlen(lib3ds_chunk_level)-2]=0;
}
static void
lib3ds_chunk_debug_dump(Lib3dsChunk *c)
{
if (enable_dump) {
printf("%s%s (0x%X) size=%u\n",
lib3ds_chunk_level,
lib3ds_chunk_name(c->chunk),
c->chunk,
c->size
);
}
}
/*!
* \ingroup chunk
*/
void
lib3ds_chunk_enable_dump(Lib3dsBool enable, Lib3dsBool unknown)
{
enable_dump=enable;
enable_unknown=unknown;
}
/*!
* \ingroup chunk
*
* Reads a 3d-Studio chunk header from a little endian file stream.
*
* \param c The chunk to store the data.
* \param f The file stream.
*
* \return True on success, False otherwise.
*/
Lib3dsBool
lib3ds_chunk_read(Lib3dsChunk *c, iostream *strm)
{
ASSERT(c);
ASSERT(strm);
c->cur=strm->tellg();
c->chunk=lib3ds_word_read(strm);
c->size=lib3ds_dword_read(strm);
c->end=c->cur+c->size;
c->cur+=6;
if (strm->fail()||(c->size<6)) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup chunk
*/
Lib3dsBool
lib3ds_chunk_read_start(Lib3dsChunk *c, Lib3dsWord chunk, iostream *strm)
{
ASSERT(c);
ASSERT(strm);
if (!lib3ds_chunk_read(c, strm)) {
return(LIB3DS_FALSE);
}
lib3ds_chunk_debug_enter(c);
return((chunk==0) || (c->chunk==chunk));
}
/*!
* \ingroup chunk
*/
void
lib3ds_chunk_read_tell(Lib3dsChunk *c, iostream *strm)
{
c->cur=strm->tellg();
}
/*!
* \ingroup chunk
*/
Lib3dsWord
lib3ds_chunk_read_next(Lib3dsChunk *c, iostream *strm)
{
Lib3dsChunk d;
if (c->cur>=c->end) {
ASSERT(c->cur==c->end);
return(0);
}
strm->seekg((long)c->cur,ios_base::beg);
d.chunk=lib3ds_word_read(strm);
d.size=lib3ds_dword_read(strm);
lib3ds_chunk_debug_dump(&d);
c->cur+=d.size;
return(d.chunk);
}
/*!
* \ingroup chunk
*/
void
lib3ds_chunk_read_reset(Lib3dsChunk *, iostream *strm)
{
strm->seekg(-6,ios_base::cur);
}
/*!
* \ingroup chunk
*/
void
lib3ds_chunk_read_end(Lib3dsChunk *c, iostream *strm)
{
lib3ds_chunk_debug_leave(c);
strm->seekg(c->end,ios_base::beg);
}
/*!
* \ingroup chunk
*
* Writes a 3d-Studio chunk header into a little endian file stream.
*
* \param c The chunk to be written.
* \param f The file stream.
*
* \return True on success, False otherwise.
*/
Lib3dsBool
lib3ds_chunk_write(Lib3dsChunk *c, iostream *strm)
{
ASSERT(c);
if (!lib3ds_word_write(c->chunk, strm)) {
LIB3DS_ERROR_LOG;
return(LIB3DS_FALSE);
}
if (!lib3ds_dword_write(c->size, strm)) {
LIB3DS_ERROR_LOG;
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup chunk
*/
Lib3dsBool
lib3ds_chunk_write_start(Lib3dsChunk *c, iostream *strm)
{
ASSERT(c);
c->size=0;
c->cur=strm->tellp();
if (!lib3ds_word_write(c->chunk, strm)) {
return(LIB3DS_FALSE);
}
if (!lib3ds_dword_write(c->size, strm)) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup chunk
*/
Lib3dsBool
lib3ds_chunk_write_end(Lib3dsChunk *c, iostream *strm)
{
ASSERT(c);
c->size=(Lib3dsDword)(strm->tellp()) - c->cur;
strm->seekp(c->cur+2,ios_base::beg);
if (!lib3ds_dword_write(c->size, strm)) {
LIB3DS_ERROR_LOG;
return(LIB3DS_FALSE);
}
c->cur+=c->size;
strm->seekp(c->cur, ios_base::beg);
if (strm->fail()) {
LIB3DS_ERROR_LOG;
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup chunk
*/
const char*
lib3ds_chunk_name(Lib3dsWord chunk)
{
Lib3dsChunkTable *p;
for (p=lib3ds_chunk_table; p->name!=0; ++p) {
if (p->chunk==chunk) {
return(p->name);
}
}
return("***UNKNOWN***");
}
/*!
* \ingroup chunk
*/
void
lib3ds_chunk_unknown(Lib3dsWord chunk)
{
if (enable_unknown) {
printf("%s***WARNING*** Unknown Chunk: %s (0x%X)\n",
lib3ds_chunk_level,
lib3ds_chunk_name(chunk),
chunk
);
}
}
/*!
* \ingroup chunk
*/
void
lib3ds_chunk_dump_info(const char *format, ...)
{
if (enable_dump) {
char s[1024];
va_list marker;
va_start(marker, format);
vsprintf(s, format, marker);
va_end(marker);
printf("%s%s\n", lib3ds_chunk_level, s);
}
}

View File

@@ -1,292 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_CHUNK_H
#define INCLUDED_LIB3DS_CHUNK_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TYPES_H
#include "types.h"
#endif
#include <iostream>
using namespace std;
#ifdef __cplusplus
extern "C" {
#endif
typedef enum _Lib3dsChunks {
LIB3DS_NULL_CHUNK =0x0000,
LIB3DS_M3DMAGIC =0x4D4D, /*3DS file*/
LIB3DS_SMAGIC =0x2D2D,
LIB3DS_LMAGIC =0x2D3D,
LIB3DS_MLIBMAGIC =0x3DAA, /*MLI file*/
LIB3DS_MATMAGIC =0x3DFF,
LIB3DS_CMAGIC =0xC23D, /*PRJ file*/
LIB3DS_M3D_VERSION =0x0002,
LIB3DS_M3D_KFVERSION =0x0005,
LIB3DS_COLOR_F =0x0010,
LIB3DS_COLOR_24 =0x0011,
LIB3DS_LIN_COLOR_24 =0x0012,
LIB3DS_LIN_COLOR_F =0x0013,
LIB3DS_INT_PERCENTAGE =0x0030,
LIB3DS_FLOAT_PERCENTAGE =0x0031,
LIB3DS_MDATA =0x3D3D,
LIB3DS_MESH_VERSION =0x3D3E,
LIB3DS_MASTER_SCALE =0x0100,
LIB3DS_LO_SHADOW_BIAS =0x1400,
LIB3DS_HI_SHADOW_BIAS =0x1410,
LIB3DS_SHADOW_MAP_SIZE =0x1420,
LIB3DS_SHADOW_SAMPLES =0x1430,
LIB3DS_SHADOW_RANGE =0x1440,
LIB3DS_SHADOW_FILTER =0x1450,
LIB3DS_RAY_BIAS =0x1460,
LIB3DS_O_CONSTS =0x1500,
LIB3DS_AMBIENT_LIGHT =0x2100,
LIB3DS_BIT_MAP =0x1100,
LIB3DS_SOLID_BGND =0x1200,
LIB3DS_V_GRADIENT =0x1300,
LIB3DS_USE_BIT_MAP =0x1101,
LIB3DS_USE_SOLID_BGND =0x1201,
LIB3DS_USE_V_GRADIENT =0x1301,
LIB3DS_FOG =0x2200,
LIB3DS_FOG_BGND =0x2210,
LIB3DS_LAYER_FOG =0x2302,
LIB3DS_DISTANCE_CUE =0x2300,
LIB3DS_DCUE_BGND =0x2310,
LIB3DS_USE_FOG =0x2201,
LIB3DS_USE_LAYER_FOG =0x2303,
LIB3DS_USE_DISTANCE_CUE =0x2301,
LIB3DS_MAT_ENTRY =0xAFFF,
LIB3DS_MAT_NAME =0xA000,
LIB3DS_MAT_AMBIENT =0xA010,
LIB3DS_MAT_DIFFUSE =0xA020,
LIB3DS_MAT_SPECULAR =0xA030,
LIB3DS_MAT_SHININESS =0xA040,
LIB3DS_MAT_SHIN2PCT =0xA041,
LIB3DS_MAT_TRANSPARENCY =0xA050,
LIB3DS_MAT_XPFALL =0xA052,
LIB3DS_MAT_USE_XPFALL =0xA240,
LIB3DS_MAT_REFBLUR =0xA053,
LIB3DS_MAT_SHADING =0xA100,
LIB3DS_MAT_USE_REFBLUR =0xA250,
LIB3DS_MAT_SELF_ILLUM =0xA080,
LIB3DS_MAT_TWO_SIDE =0xA081,
LIB3DS_MAT_DECAL =0xA082,
LIB3DS_MAT_ADDITIVE =0xA083,
LIB3DS_MAT_WIRE =0xA085,
LIB3DS_MAT_FACEMAP =0xA088,
LIB3DS_MAT_PHONGSOFT =0xA08C,
LIB3DS_MAT_WIREABS =0xA08E,
LIB3DS_MAT_WIRE_SIZE =0xA087,
LIB3DS_MAT_TEXMAP =0xA200,
LIB3DS_MAT_SXP_TEXT_DATA =0xA320,
LIB3DS_MAT_TEXMASK =0xA33E,
LIB3DS_MAT_SXP_TEXTMASK_DATA =0xA32A,
LIB3DS_MAT_TEX2MAP =0xA33A,
LIB3DS_MAT_SXP_TEXT2_DATA =0xA321,
LIB3DS_MAT_TEX2MASK =0xA340,
LIB3DS_MAT_SXP_TEXT2MASK_DATA =0xA32C,
LIB3DS_MAT_OPACMAP =0xA210,
LIB3DS_MAT_SXP_OPAC_DATA =0xA322,
LIB3DS_MAT_OPACMASK =0xA342,
LIB3DS_MAT_SXP_OPACMASK_DATA =0xA32E,
LIB3DS_MAT_BUMPMAP =0xA230,
LIB3DS_MAT_SXP_BUMP_DATA =0xA324,
LIB3DS_MAT_BUMPMASK =0xA344,
LIB3DS_MAT_SXP_BUMPMASK_DATA =0xA330,
LIB3DS_MAT_SPECMAP =0xA204,
LIB3DS_MAT_SXP_SPEC_DATA =0xA325,
LIB3DS_MAT_SPECMASK =0xA348,
LIB3DS_MAT_SXP_SPECMASK_DATA =0xA332,
LIB3DS_MAT_SHINMAP =0xA33C,
LIB3DS_MAT_SXP_SHIN_DATA =0xA326,
LIB3DS_MAT_SHINMASK =0xA346,
LIB3DS_MAT_SXP_SHINMASK_DATA =0xA334,
LIB3DS_MAT_SELFIMAP =0xA33D,
LIB3DS_MAT_SXP_SELFI_DATA =0xA328,
LIB3DS_MAT_SELFIMASK =0xA34A,
LIB3DS_MAT_SXP_SELFIMASK_DATA =0xA336,
LIB3DS_MAT_REFLMAP =0xA220,
LIB3DS_MAT_REFLMASK =0xA34C,
LIB3DS_MAT_SXP_REFLMASK_DATA =0xA338,
LIB3DS_MAT_ACUBIC =0xA310,
LIB3DS_MAT_MAPNAME =0xA300,
LIB3DS_MAT_MAP_TILING =0xA351,
LIB3DS_MAT_MAP_TEXBLUR =0xA353,
LIB3DS_MAT_MAP_USCALE =0xA354,
LIB3DS_MAT_MAP_VSCALE =0xA356,
LIB3DS_MAT_MAP_UOFFSET =0xA358,
LIB3DS_MAT_MAP_VOFFSET =0xA35A,
LIB3DS_MAT_MAP_ANG =0xA35C,
LIB3DS_MAT_MAP_COL1 =0xA360,
LIB3DS_MAT_MAP_COL2 =0xA362,
LIB3DS_MAT_MAP_RCOL =0xA364,
LIB3DS_MAT_MAP_GCOL =0xA366,
LIB3DS_MAT_MAP_BCOL =0xA368,
LIB3DS_NAMED_OBJECT =0x4000,
LIB3DS_N_DIRECT_LIGHT =0x4600,
LIB3DS_DL_OFF =0x4620,
LIB3DS_DL_OUTER_RANGE =0x465A,
LIB3DS_DL_INNER_RANGE =0x4659,
LIB3DS_DL_MULTIPLIER =0x465B,
LIB3DS_DL_EXCLUDE =0x4654,
LIB3DS_DL_ATTENUATE =0x4625,
LIB3DS_DL_SPOTLIGHT =0x4610,
LIB3DS_DL_SPOT_ROLL =0x4656,
LIB3DS_DL_SHADOWED =0x4630,
LIB3DS_DL_LOCAL_SHADOW2 =0x4641,
LIB3DS_DL_SEE_CONE =0x4650,
LIB3DS_DL_SPOT_RECTANGULAR =0x4651,
LIB3DS_DL_SPOT_ASPECT =0x4657,
LIB3DS_DL_SPOT_PROJECTOR =0x4653,
LIB3DS_DL_SPOT_OVERSHOOT =0x4652,
LIB3DS_DL_RAY_BIAS =0x4658,
LIB3DS_DL_RAYSHAD =0x4627,
LIB3DS_N_CAMERA =0x4700,
LIB3DS_CAM_SEE_CONE =0x4710,
LIB3DS_CAM_RANGES =0x4720,
LIB3DS_OBJ_HIDDEN =0x4010,
LIB3DS_OBJ_VIS_LOFTER =0x4011,
LIB3DS_OBJ_DOESNT_CAST =0x4012,
LIB3DS_OBJ_DONT_RECVSHADOW =0x4017,
LIB3DS_OBJ_MATTE =0x4013,
LIB3DS_OBJ_FAST =0x4014,
LIB3DS_OBJ_PROCEDURAL =0x4015,
LIB3DS_OBJ_FROZEN =0x4016,
LIB3DS_N_TRI_OBJECT =0x4100,
LIB3DS_POINT_ARRAY =0x4110,
LIB3DS_POINT_FLAG_ARRAY =0x4111,
LIB3DS_FACE_ARRAY =0x4120,
LIB3DS_MSH_MAT_GROUP =0x4130,
LIB3DS_SMOOTH_GROUP =0x4150,
LIB3DS_MSH_BOXMAP =0x4190,
LIB3DS_TEX_VERTS =0x4140,
LIB3DS_MESH_MATRIX =0x4160,
LIB3DS_MESH_COLOR =0x4165,
LIB3DS_MESH_TEXTURE_INFO =0x4170,
LIB3DS_KFDATA =0xB000,
LIB3DS_KFHDR =0xB00A,
LIB3DS_KFSEG =0xB008,
LIB3DS_KFCURTIME =0xB009,
LIB3DS_AMBIENT_NODE_TAG =0xB001,
LIB3DS_OBJECT_NODE_TAG =0xB002,
LIB3DS_CAMERA_NODE_TAG =0xB003,
LIB3DS_TARGET_NODE_TAG =0xB004,
LIB3DS_LIGHT_NODE_TAG =0xB005,
LIB3DS_L_TARGET_NODE_TAG =0xB006,
LIB3DS_SPOTLIGHT_NODE_TAG =0xB007,
LIB3DS_NODE_ID =0xB030,
LIB3DS_NODE_HDR =0xB010,
LIB3DS_PIVOT =0xB013,
LIB3DS_INSTANCE_NAME =0xB011,
LIB3DS_MORPH_SMOOTH =0xB015,
LIB3DS_BOUNDBOX =0xB014,
LIB3DS_POS_TRACK_TAG =0xB020,
LIB3DS_COL_TRACK_TAG =0xB025,
LIB3DS_ROT_TRACK_TAG =0xB021,
LIB3DS_SCL_TRACK_TAG =0xB022,
LIB3DS_MORPH_TRACK_TAG =0xB026,
LIB3DS_FOV_TRACK_TAG =0xB023,
LIB3DS_ROLL_TRACK_TAG =0xB024,
LIB3DS_HOT_TRACK_TAG =0xB027,
LIB3DS_FALL_TRACK_TAG =0xB028,
LIB3DS_HIDE_TRACK_TAG =0xB029,
LIB3DS_POLY_2D = 0x5000,
LIB3DS_SHAPE_OK = 0x5010,
LIB3DS_SHAPE_NOT_OK = 0x5011,
LIB3DS_SHAPE_HOOK = 0x5020,
LIB3DS_PATH_3D = 0x6000,
LIB3DS_PATH_MATRIX = 0x6005,
LIB3DS_SHAPE_2D = 0x6010,
LIB3DS_M_SCALE = 0x6020,
LIB3DS_M_TWIST = 0x6030,
LIB3DS_M_TEETER = 0x6040,
LIB3DS_M_FIT = 0x6050,
LIB3DS_M_BEVEL = 0x6060,
LIB3DS_XZ_CURVE = 0x6070,
LIB3DS_YZ_CURVE = 0x6080,
LIB3DS_INTERPCT = 0x6090,
LIB3DS_DEFORM_LIMIT = 0x60A0,
LIB3DS_USE_CONTOUR = 0x6100,
LIB3DS_USE_TWEEN = 0x6110,
LIB3DS_USE_SCALE = 0x6120,
LIB3DS_USE_TWIST = 0x6130,
LIB3DS_USE_TEETER = 0x6140,
LIB3DS_USE_FIT = 0x6150,
LIB3DS_USE_BEVEL = 0x6160,
LIB3DS_DEFAULT_VIEW = 0x3000,
LIB3DS_VIEW_TOP = 0x3010,
LIB3DS_VIEW_BOTTOM = 0x3020,
LIB3DS_VIEW_LEFT = 0x3030,
LIB3DS_VIEW_RIGHT = 0x3040,
LIB3DS_VIEW_FRONT = 0x3050,
LIB3DS_VIEW_BACK = 0x3060,
LIB3DS_VIEW_USER = 0x3070,
LIB3DS_VIEW_CAMERA = 0x3080,
LIB3DS_VIEW_WINDOW = 0x3090,
LIB3DS_VIEWPORT_LAYOUT_OLD = 0x7000,
LIB3DS_VIEWPORT_DATA_OLD = 0x7010,
LIB3DS_VIEWPORT_LAYOUT = 0x7001,
LIB3DS_VIEWPORT_DATA = 0x7011,
LIB3DS_VIEWPORT_DATA_3 = 0x7012,
LIB3DS_VIEWPORT_SIZE = 0x7020,
LIB3DS_NETWORK_VIEW = 0x7030
} Lib3dsChunks;
typedef struct _Lib3dsChunk {
Lib3dsWord chunk;
Lib3dsDword size;
Lib3dsDword end;
Lib3dsDword cur;
} Lib3dsChunk;
extern LIB3DSAPI void lib3ds_chunk_enable_dump(Lib3dsBool enable, Lib3dsBool unknown);
extern LIB3DSAPI Lib3dsBool lib3ds_chunk_read(Lib3dsChunk *c, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_chunk_read_start(Lib3dsChunk *c, Lib3dsWord chunk, iostream *strm);
extern LIB3DSAPI void lib3ds_chunk_read_tell(Lib3dsChunk *c, iostream *strm);
extern LIB3DSAPI Lib3dsWord lib3ds_chunk_read_next(Lib3dsChunk *c, iostream *strm);
extern LIB3DSAPI void lib3ds_chunk_read_reset(Lib3dsChunk *c, iostream *strm);
extern LIB3DSAPI void lib3ds_chunk_read_end(Lib3dsChunk *c, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_chunk_write(Lib3dsChunk *c, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_chunk_write_start(Lib3dsChunk *c, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_chunk_write_end(Lib3dsChunk *c, iostream *strm);
extern LIB3DSAPI const char* lib3ds_chunk_name(Lib3dsWord chunk);
extern LIB3DSAPI void lib3ds_chunk_unknown(Lib3dsWord chunk);
extern LIB3DSAPI void lib3ds_chunk_dump_info(const char *format, ...);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -1,263 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_CHUNKTABLE_H
#define INCLUDED_LIB3DS_CHUNKTABLE_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_CHUNK_H
#include "chunk.h"
#endif
#ifdef __cplusplus
extern "C" {
#endif
typedef struct _Lib3dsChunkTable {
Lib3dsDword chunk;
const char* name;
} Lib3dsChunkTable;
static Lib3dsChunkTable lib3ds_chunk_table[]={
{LIB3DS_NULL_CHUNK, "LIB3DS_NULL_CHUNK"},
{LIB3DS_M3DMAGIC, "LIB3DS_M3DMAGIC"},
{LIB3DS_SMAGIC, "LIB3DS_SMAGIC"},
{LIB3DS_LMAGIC, "LIB3DS_LMAGIC"},
{LIB3DS_MLIBMAGIC, "LIB3DS_MLIBMAGIC"},
{LIB3DS_MATMAGIC, "LIB3DS_MATMAGIC"},
{LIB3DS_CMAGIC, "LIB3DS_CMAGIC"},
{LIB3DS_M3D_VERSION, "LIB3DS_M3D_VERSION"},
{LIB3DS_M3D_KFVERSION, "LIB3DS_M3D_KFVERSION"},
{LIB3DS_COLOR_F, "LIB3DS_COLOR_F"},
{LIB3DS_COLOR_24, "LIB3DS_COLOR_24"},
{LIB3DS_LIN_COLOR_24, "LIB3DS_LIN_COLOR_24"},
{LIB3DS_LIN_COLOR_F, "LIB3DS_LIN_COLOR_F"},
{LIB3DS_INT_PERCENTAGE, "LIB3DS_INT_PERCENTAGE"},
{LIB3DS_FLOAT_PERCENTAGE, "LIB3DS_FLOAT_PERCENTAGE"},
{LIB3DS_MDATA, "LIB3DS_MDATA"},
{LIB3DS_MESH_VERSION, "LIB3DS_MESH_VERSION"},
{LIB3DS_MASTER_SCALE, "LIB3DS_MASTER_SCALE"},
{LIB3DS_LO_SHADOW_BIAS, "LIB3DS_LO_SHADOW_BIAS"},
{LIB3DS_HI_SHADOW_BIAS, "LIB3DS_HI_SHADOW_BIAS"},
{LIB3DS_SHADOW_MAP_SIZE, "LIB3DS_SHADOW_MAP_SIZE"},
{LIB3DS_SHADOW_SAMPLES, "LIB3DS_SHADOW_SAMPLES"},
{LIB3DS_SHADOW_RANGE, "LIB3DS_SHADOW_RANGE"},
{LIB3DS_SHADOW_FILTER, "LIB3DS_SHADOW_FILTER"},
{LIB3DS_RAY_BIAS, "LIB3DS_RAY_BIAS"},
{LIB3DS_O_CONSTS, "LIB3DS_O_CONSTS"},
{LIB3DS_AMBIENT_LIGHT, "LIB3DS_AMBIENT_LIGHT"},
{LIB3DS_BIT_MAP, "LIB3DS_BIT_MAP"},
{LIB3DS_SOLID_BGND, "LIB3DS_SOLID_BGND"},
{LIB3DS_V_GRADIENT, "LIB3DS_V_GRADIENT"},
{LIB3DS_USE_BIT_MAP, "LIB3DS_USE_BIT_MAP"},
{LIB3DS_USE_SOLID_BGND, "LIB3DS_USE_SOLID_BGND"},
{LIB3DS_USE_V_GRADIENT, "LIB3DS_USE_V_GRADIENT"},
{LIB3DS_FOG, "LIB3DS_FOG"},
{LIB3DS_FOG_BGND, "LIB3DS_FOG_BGND"},
{LIB3DS_LAYER_FOG, "LIB3DS_LAYER_FOG"},
{LIB3DS_DISTANCE_CUE, "LIB3DS_DISTANCE_CUE"},
{LIB3DS_DCUE_BGND, "LIB3DS_DCUE_BGND"},
{LIB3DS_USE_FOG, "LIB3DS_USE_FOG"},
{LIB3DS_USE_LAYER_FOG, "LIB3DS_USE_LAYER_FOG"},
{LIB3DS_USE_DISTANCE_CUE, "LIB3DS_USE_DISTANCE_CUE"},
{LIB3DS_MAT_ENTRY, "LIB3DS_MAT_ENTRY"},
{LIB3DS_MAT_NAME, "LIB3DS_MAT_NAME"},
{LIB3DS_MAT_AMBIENT, "LIB3DS_MAT_AMBIENT"},
{LIB3DS_MAT_DIFFUSE, "LIB3DS_MAT_DIFFUSE"},
{LIB3DS_MAT_SPECULAR, "LIB3DS_MAT_SPECULAR"},
{LIB3DS_MAT_SHININESS, "LIB3DS_MAT_SHININESS"},
{LIB3DS_MAT_SHIN2PCT, "LIB3DS_MAT_SHIN2PCT"},
{LIB3DS_MAT_TRANSPARENCY, "LIB3DS_MAT_TRANSPARENCY"},
{LIB3DS_MAT_XPFALL, "LIB3DS_MAT_XPFALL"},
{LIB3DS_MAT_USE_XPFALL, "LIB3DS_MAT_USE_XPFALL"},
{LIB3DS_MAT_REFBLUR, "LIB3DS_MAT_REFBLUR"},
{LIB3DS_MAT_SHADING, "LIB3DS_MAT_SHADING"},
{LIB3DS_MAT_USE_REFBLUR, "LIB3DS_MAT_USE_REFBLUR"},
{LIB3DS_MAT_SELF_ILLUM, "LIB3DS_MAT_SELF_ILLUM"},
{LIB3DS_MAT_TWO_SIDE, "LIB3DS_MAT_TWO_SIDE"},
{LIB3DS_MAT_DECAL, "LIB3DS_MAT_DECAL"},
{LIB3DS_MAT_ADDITIVE, "LIB3DS_MAT_ADDITIVE"},
{LIB3DS_MAT_WIRE, "LIB3DS_MAT_WIRE"},
{LIB3DS_MAT_FACEMAP, "LIB3DS_MAT_FACEMAP"},
{LIB3DS_MAT_PHONGSOFT, "LIB3DS_MAT_PHONGSOFT"},
{LIB3DS_MAT_WIREABS, "LIB3DS_MAT_WIREABS"},
{LIB3DS_MAT_WIRE_SIZE, "LIB3DS_MAT_WIRE_SIZE"},
{LIB3DS_MAT_TEXMAP, "LIB3DS_MAT_TEXMAP"},
{LIB3DS_MAT_SXP_TEXT_DATA, "LIB3DS_MAT_SXP_TEXT_DATA"},
{LIB3DS_MAT_TEXMASK, "LIB3DS_MAT_TEXMASK"},
{LIB3DS_MAT_SXP_TEXTMASK_DATA, "LIB3DS_MAT_SXP_TEXTMASK_DATA"},
{LIB3DS_MAT_TEX2MAP, "LIB3DS_MAT_TEX2MAP"},
{LIB3DS_MAT_SXP_TEXT2_DATA, "LIB3DS_MAT_SXP_TEXT2_DATA"},
{LIB3DS_MAT_TEX2MASK, "LIB3DS_MAT_TEX2MASK"},
{LIB3DS_MAT_SXP_TEXT2MASK_DATA, "LIB3DS_MAT_SXP_TEXT2MASK_DATA"},
{LIB3DS_MAT_OPACMAP, "LIB3DS_MAT_OPACMAP"},
{LIB3DS_MAT_SXP_OPAC_DATA, "LIB3DS_MAT_SXP_OPAC_DATA"},
{LIB3DS_MAT_OPACMASK, "LIB3DS_MAT_OPACMASK"},
{LIB3DS_MAT_SXP_OPACMASK_DATA, "LIB3DS_MAT_SXP_OPACMASK_DATA"},
{LIB3DS_MAT_BUMPMAP, "LIB3DS_MAT_BUMPMAP"},
{LIB3DS_MAT_SXP_BUMP_DATA, "LIB3DS_MAT_SXP_BUMP_DATA"},
{LIB3DS_MAT_BUMPMASK, "LIB3DS_MAT_BUMPMASK"},
{LIB3DS_MAT_SXP_BUMPMASK_DATA, "LIB3DS_MAT_SXP_BUMPMASK_DATA"},
{LIB3DS_MAT_SPECMAP, "LIB3DS_MAT_SPECMAP"},
{LIB3DS_MAT_SXP_SPEC_DATA, "LIB3DS_MAT_SXP_SPEC_DATA"},
{LIB3DS_MAT_SPECMASK, "LIB3DS_MAT_SPECMASK"},
{LIB3DS_MAT_SXP_SPECMASK_DATA, "LIB3DS_MAT_SXP_SPECMASK_DATA"},
{LIB3DS_MAT_SHINMAP, "LIB3DS_MAT_SHINMAP"},
{LIB3DS_MAT_SXP_SHIN_DATA, "LIB3DS_MAT_SXP_SHIN_DATA"},
{LIB3DS_MAT_SHINMASK, "LIB3DS_MAT_SHINMASK"},
{LIB3DS_MAT_SXP_SHINMASK_DATA, "LIB3DS_MAT_SXP_SHINMASK_DATA"},
{LIB3DS_MAT_SELFIMAP, "LIB3DS_MAT_SELFIMAP"},
{LIB3DS_MAT_SXP_SELFI_DATA, "LIB3DS_MAT_SXP_SELFI_DATA"},
{LIB3DS_MAT_SELFIMASK, "LIB3DS_MAT_SELFIMASK"},
{LIB3DS_MAT_SXP_SELFIMASK_DATA, "LIB3DS_MAT_SXP_SELFIMASK_DATA"},
{LIB3DS_MAT_REFLMAP, "LIB3DS_MAT_REFLMAP"},
{LIB3DS_MAT_REFLMASK, "LIB3DS_MAT_REFLMASK"},
{LIB3DS_MAT_SXP_REFLMASK_DATA, "LIB3DS_MAT_SXP_REFLMASK_DATA"},
{LIB3DS_MAT_ACUBIC, "LIB3DS_MAT_ACUBIC"},
{LIB3DS_MAT_MAPNAME, "LIB3DS_MAT_MAPNAME"},
{LIB3DS_MAT_MAP_TILING, "LIB3DS_MAT_MAP_TILING"},
{LIB3DS_MAT_MAP_TEXBLUR, "LIB3DS_MAT_MAP_TEXBLUR"},
{LIB3DS_MAT_MAP_USCALE, "LIB3DS_MAT_MAP_USCALE"},
{LIB3DS_MAT_MAP_VSCALE, "LIB3DS_MAT_MAP_VSCALE"},
{LIB3DS_MAT_MAP_UOFFSET, "LIB3DS_MAT_MAP_UOFFSET"},
{LIB3DS_MAT_MAP_VOFFSET, "LIB3DS_MAT_MAP_VOFFSET"},
{LIB3DS_MAT_MAP_ANG, "LIB3DS_MAT_MAP_ANG"},
{LIB3DS_MAT_MAP_COL1, "LIB3DS_MAT_MAP_COL1"},
{LIB3DS_MAT_MAP_COL2, "LIB3DS_MAT_MAP_COL2"},
{LIB3DS_MAT_MAP_RCOL, "LIB3DS_MAT_MAP_RCOL"},
{LIB3DS_MAT_MAP_GCOL, "LIB3DS_MAT_MAP_GCOL"},
{LIB3DS_MAT_MAP_BCOL, "LIB3DS_MAT_MAP_BCOL"},
{LIB3DS_NAMED_OBJECT, "LIB3DS_NAMED_OBJECT"},
{LIB3DS_N_DIRECT_LIGHT, "LIB3DS_N_DIRECT_LIGHT"},
{LIB3DS_DL_OFF, "LIB3DS_DL_OFF"},
{LIB3DS_DL_OUTER_RANGE, "LIB3DS_DL_OUTER_RANGE"},
{LIB3DS_DL_INNER_RANGE, "LIB3DS_DL_INNER_RANGE"},
{LIB3DS_DL_MULTIPLIER, "LIB3DS_DL_MULTIPLIER"},
{LIB3DS_DL_EXCLUDE, "LIB3DS_DL_EXCLUDE"},
{LIB3DS_DL_ATTENUATE, "LIB3DS_DL_ATTENUATE"},
{LIB3DS_DL_SPOTLIGHT, "LIB3DS_DL_SPOTLIGHT"},
{LIB3DS_DL_SPOT_ROLL, "LIB3DS_DL_SPOT_ROLL"},
{LIB3DS_DL_SHADOWED, "LIB3DS_DL_SHADOWED"},
{LIB3DS_DL_LOCAL_SHADOW2, "LIB3DS_DL_LOCAL_SHADOW2"},
{LIB3DS_DL_SEE_CONE, "LIB3DS_DL_SEE_CONE"},
{LIB3DS_DL_SPOT_RECTANGULAR, "LIB3DS_DL_SPOT_RECTANGULAR"},
{LIB3DS_DL_SPOT_ASPECT, "LIB3DS_DL_SPOT_ASPECT"},
{LIB3DS_DL_SPOT_PROJECTOR, "LIB3DS_DL_SPOT_PROJECTOR"},
{LIB3DS_DL_SPOT_OVERSHOOT, "LIB3DS_DL_SPOT_OVERSHOOT"},
{LIB3DS_DL_RAY_BIAS, "LIB3DS_DL_RAY_BIAS"},
{LIB3DS_DL_RAYSHAD, "LIB3DS_DL_RAYSHAD"},
{LIB3DS_N_CAMERA, "LIB3DS_N_CAMERA"},
{LIB3DS_CAM_SEE_CONE, "LIB3DS_CAM_SEE_CONE"},
{LIB3DS_CAM_RANGES, "LIB3DS_CAM_RANGES"},
{LIB3DS_OBJ_HIDDEN, "LIB3DS_OBJ_HIDDEN"},
{LIB3DS_OBJ_VIS_LOFTER, "LIB3DS_OBJ_VIS_LOFTER"},
{LIB3DS_OBJ_DOESNT_CAST, "LIB3DS_OBJ_DOESNT_CAST"},
{LIB3DS_OBJ_DONT_RECVSHADOW, "LIB3DS_OBJ_DONT_RECVSHADOW"},
{LIB3DS_OBJ_MATTE, "LIB3DS_OBJ_MATTE"},
{LIB3DS_OBJ_FAST, "LIB3DS_OBJ_FAST"},
{LIB3DS_OBJ_PROCEDURAL, "LIB3DS_OBJ_PROCEDURAL"},
{LIB3DS_OBJ_FROZEN, "LIB3DS_OBJ_FROZEN"},
{LIB3DS_N_TRI_OBJECT, "LIB3DS_N_TRI_OBJECT"},
{LIB3DS_POINT_ARRAY, "LIB3DS_POINT_ARRAY"},
{LIB3DS_POINT_FLAG_ARRAY, "LIB3DS_POINT_FLAG_ARRAY"},
{LIB3DS_FACE_ARRAY, "LIB3DS_FACE_ARRAY"},
{LIB3DS_MSH_MAT_GROUP, "LIB3DS_MSH_MAT_GROUP"},
{LIB3DS_SMOOTH_GROUP, "LIB3DS_SMOOTH_GROUP"},
{LIB3DS_MSH_BOXMAP, "LIB3DS_MSH_BOXMAP"},
{LIB3DS_TEX_VERTS, "LIB3DS_TEX_VERTS"},
{LIB3DS_MESH_MATRIX, "LIB3DS_MESH_MATRIX"},
{LIB3DS_MESH_COLOR, "LIB3DS_MESH_COLOR"},
{LIB3DS_MESH_TEXTURE_INFO, "LIB3DS_MESH_TEXTURE_INFO"},
{LIB3DS_KFDATA, "LIB3DS_KFDATA"},
{LIB3DS_KFHDR, "LIB3DS_KFHDR"},
{LIB3DS_KFSEG, "LIB3DS_KFSEG"},
{LIB3DS_KFCURTIME, "LIB3DS_KFCURTIME"},
{LIB3DS_AMBIENT_NODE_TAG, "LIB3DS_AMBIENT_NODE_TAG"},
{LIB3DS_OBJECT_NODE_TAG, "LIB3DS_OBJECT_NODE_TAG"},
{LIB3DS_CAMERA_NODE_TAG, "LIB3DS_CAMERA_NODE_TAG"},
{LIB3DS_TARGET_NODE_TAG, "LIB3DS_TARGET_NODE_TAG"},
{LIB3DS_LIGHT_NODE_TAG, "LIB3DS_LIGHT_NODE_TAG"},
{LIB3DS_L_TARGET_NODE_TAG, "LIB3DS_L_TARGET_NODE_TAG"},
{LIB3DS_SPOTLIGHT_NODE_TAG, "LIB3DS_SPOTLIGHT_NODE_TAG"},
{LIB3DS_NODE_ID, "LIB3DS_NODE_ID"},
{LIB3DS_NODE_HDR, "LIB3DS_NODE_HDR"},
{LIB3DS_PIVOT, "LIB3DS_PIVOT"},
{LIB3DS_INSTANCE_NAME, "LIB3DS_INSTANCE_NAME"},
{LIB3DS_MORPH_SMOOTH, "LIB3DS_MORPH_SMOOTH"},
{LIB3DS_BOUNDBOX, "LIB3DS_BOUNDBOX"},
{LIB3DS_POS_TRACK_TAG, "LIB3DS_POS_TRACK_TAG"},
{LIB3DS_COL_TRACK_TAG, "LIB3DS_COL_TRACK_TAG"},
{LIB3DS_ROT_TRACK_TAG, "LIB3DS_ROT_TRACK_TAG"},
{LIB3DS_SCL_TRACK_TAG, "LIB3DS_SCL_TRACK_TAG"},
{LIB3DS_MORPH_TRACK_TAG, "LIB3DS_MORPH_TRACK_TAG"},
{LIB3DS_FOV_TRACK_TAG, "LIB3DS_FOV_TRACK_TAG"},
{LIB3DS_ROLL_TRACK_TAG, "LIB3DS_ROLL_TRACK_TAG"},
{LIB3DS_HOT_TRACK_TAG, "LIB3DS_HOT_TRACK_TAG"},
{LIB3DS_FALL_TRACK_TAG, "LIB3DS_FALL_TRACK_TAG"},
{LIB3DS_HIDE_TRACK_TAG, "LIB3DS_HIDE_TRACK_TAG"},
{LIB3DS_POLY_2D, "LIB3DS_POLY_2D"},
{LIB3DS_SHAPE_OK, "LIB3DS_SHAPE_OK"},
{LIB3DS_SHAPE_NOT_OK, "LIB3DS_SHAPE_NOT_OK"},
{LIB3DS_SHAPE_HOOK, "LIB3DS_SHAPE_HOOK"},
{LIB3DS_PATH_3D, "LIB3DS_PATH_3D"},
{LIB3DS_PATH_MATRIX, "LIB3DS_PATH_MATRIX"},
{LIB3DS_SHAPE_2D, "LIB3DS_SHAPE_2D"},
{LIB3DS_M_SCALE, "LIB3DS_M_SCALE"},
{LIB3DS_M_TWIST, "LIB3DS_M_TWIST"},
{LIB3DS_M_TEETER, "LIB3DS_M_TEETER"},
{LIB3DS_M_FIT, "LIB3DS_M_FIT"},
{LIB3DS_M_BEVEL, "LIB3DS_M_BEVEL"},
{LIB3DS_XZ_CURVE, "LIB3DS_XZ_CURVE"},
{LIB3DS_YZ_CURVE, "LIB3DS_YZ_CURVE"},
{LIB3DS_INTERPCT, "LIB3DS_INTERPCT"},
{LIB3DS_DEFORM_LIMIT, "LIB3DS_DEFORM_LIMIT"},
{LIB3DS_USE_CONTOUR, "LIB3DS_USE_CONTOUR"},
{LIB3DS_USE_TWEEN, "LIB3DS_USE_TWEEN"},
{LIB3DS_USE_SCALE, "LIB3DS_USE_SCALE"},
{LIB3DS_USE_TWIST, "LIB3DS_USE_TWIST"},
{LIB3DS_USE_TEETER, "LIB3DS_USE_TEETER"},
{LIB3DS_USE_FIT, "LIB3DS_USE_FIT"},
{LIB3DS_USE_BEVEL, "LIB3DS_USE_BEVEL"},
{LIB3DS_DEFAULT_VIEW, "LIB3DS_DEFAULT_VIEW"},
{LIB3DS_VIEW_TOP, "LIB3DS_VIEW_TOP"},
{LIB3DS_VIEW_BOTTOM, "LIB3DS_VIEW_BOTTOM"},
{LIB3DS_VIEW_LEFT, "LIB3DS_VIEW_LEFT"},
{LIB3DS_VIEW_RIGHT, "LIB3DS_VIEW_RIGHT"},
{LIB3DS_VIEW_FRONT, "LIB3DS_VIEW_FRONT"},
{LIB3DS_VIEW_BACK, "LIB3DS_VIEW_BACK"},
{LIB3DS_VIEW_USER, "LIB3DS_VIEW_USER"},
{LIB3DS_VIEW_CAMERA, "LIB3DS_VIEW_CAMERA"},
{LIB3DS_VIEW_WINDOW, "LIB3DS_VIEW_WINDOW"},
{LIB3DS_VIEWPORT_LAYOUT_OLD, "LIB3DS_VIEWPORT_LAYOUT_OLD"},
{LIB3DS_VIEWPORT_DATA_OLD, "LIB3DS_VIEWPORT_DATA_OLD"},
{LIB3DS_VIEWPORT_LAYOUT, "LIB3DS_VIEWPORT_LAYOUT"},
{LIB3DS_VIEWPORT_DATA, "LIB3DS_VIEWPORT_DATA"},
{LIB3DS_VIEWPORT_DATA_3, "LIB3DS_VIEWPORT_DATA_3"},
{LIB3DS_VIEWPORT_SIZE, "LIB3DS_VIEWPORT_SIZE"},
{LIB3DS_NETWORK_VIEW, "LIB3DS_NETWORK_VIEW"},
{0,0}
};
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -1,12 +0,0 @@
/* config.h. Generated automatically by configure. */
/* config.h.in. Generated automatically from configure.in by autoheader. */
/* Name of package */
#define PACKAGE "lib3ds"
/* Version number of package */
#define VERSION "1.1.0"
/* Define if using the dmalloc debugging malloc package */
/* #undef WITH_DMALLOC */

View File

@@ -1,65 +0,0 @@
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#define LIB3DS_EXPORT
#include "ease.h"
/*!
* \defgroup ease Ease
*
* \author J.E. Hoffmann <je-h@gmx.net>
*/
/*!
* \ingroup ease
*/
Lib3dsFloat
lib3ds_ease(Lib3dsFloat fp, Lib3dsFloat fc, Lib3dsFloat fn,
Lib3dsFloat ease_from, Lib3dsFloat ease_to)
{
Lib3dsDouble s,step;
Lib3dsDouble tofrom;
Lib3dsDouble a;
s=step=(Lib3dsFloat)(fc-fp)/(fn-fp);
tofrom=ease_to+ease_from;
if (tofrom!=0.0) {
if (tofrom>1.0) {
ease_to=(Lib3dsFloat)(ease_to/tofrom);
ease_from=(Lib3dsFloat)(ease_from/tofrom);
}
a=1.0/(2.0-(ease_to+ease_from));
if (step<ease_from) s=a/ease_from*step*step;
else {
if ((1.0-ease_to)<=step) {
step=1.0-step;
s=1.0-a/ease_to*step*step;
}
else {
s=((2.0*step)-ease_from)*a;
}
}
}
return((Lib3dsFloat)s);
}

View File

@@ -1,41 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_EASE_H
#define INCLUDED_LIB3DS_EASE_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TYPES_H
#include "types.h"
#endif
#ifdef __cplusplus
extern "C" {
#endif
extern LIB3DSAPI Lib3dsFloat lib3ds_ease(Lib3dsFloat fp, Lib3dsFloat fc,
Lib3dsFloat fn, Lib3dsFloat ease_from, Lib3dsFloat ease_to);
#ifdef __cplusplus
}
#endif
#endif

File diff suppressed because it is too large Load Diff

View File

@@ -1,111 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_FILE_H
#define INCLUDED_LIB3DS_FILE_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_BACKGROUND_H
#include "background.h"
#endif
#ifndef INCLUDED_LIB3DS_ATMOSPHERE_H
#include "atmosphere.h"
#endif
#ifndef INCLUDED_LIB3DS_SHADOW_H
#include "shadow.h"
#endif
#ifndef INCLUDED_LIB3DS_VIEWPORT_H
#include "viewport.h"
#endif
#include <osgDB/Registry>
#include <iostream>
using namespace std;
#ifdef __cplusplus
extern "C" {
#endif
/*!
* 3ds file structure
* \ingroup file
*/
struct _Lib3dsFile {
Lib3dsDword mesh_version;
Lib3dsWord keyf_revision;
char name[12+1];
Lib3dsFloat master_scale;
Lib3dsVector construction_plane;
Lib3dsRgb ambient;
Lib3dsShadow shadow;
Lib3dsBackground background;
Lib3dsAtmosphere atmosphere;
Lib3dsViewport viewport;
Lib3dsViewport viewport_keyf;
Lib3dsIntd frames;
Lib3dsIntd segment_from;
Lib3dsIntd segment_to;
Lib3dsIntd current_frame;
Lib3dsMaterial *materials;
Lib3dsMesh *meshes;
Lib3dsCamera *cameras;
Lib3dsLight *lights;
Lib3dsNode *nodes;
};
extern LIB3DSAPI Lib3dsFile* lib3ds_file_load(const char *filename, const osgDB::ReaderWriter::Options* options);
extern LIB3DSAPI Lib3dsFile* lib3ds_stream_load(iostream * strm);
extern LIB3DSAPI Lib3dsBool lib3ds_file_save(Lib3dsFile *file, const char *filename);
extern LIB3DSAPI Lib3dsFile* lib3ds_file_new();
extern LIB3DSAPI void lib3ds_file_free(Lib3dsFile *file);
extern LIB3DSAPI void lib3ds_file_eval(Lib3dsFile *file, Lib3dsFloat t);
extern LIB3DSAPI Lib3dsBool lib3ds_file_read(Lib3dsFile *file, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_file_write(Lib3dsFile *file, iostream *strm);
extern LIB3DSAPI void lib3ds_file_insert_material(Lib3dsFile *file, Lib3dsMaterial *material);
extern LIB3DSAPI void lib3ds_file_remove_material(Lib3dsFile *file, Lib3dsMaterial *material);
extern LIB3DSAPI Lib3dsMaterial* lib3ds_file_material_by_name(Lib3dsFile *file, const char *name);
extern LIB3DSAPI void lib3ds_file_dump_materials(Lib3dsFile *file);
extern LIB3DSAPI void lib3ds_file_insert_mesh(Lib3dsFile *file, Lib3dsMesh *mesh);
extern LIB3DSAPI void lib3ds_file_remove_mesh(Lib3dsFile *file, Lib3dsMesh *mesh);
extern LIB3DSAPI Lib3dsMesh* lib3ds_file_mesh_by_name(Lib3dsFile *file, const char *name);
extern LIB3DSAPI void lib3ds_file_dump_meshes(Lib3dsFile *file);
extern LIB3DSAPI void lib3ds_file_dump_instances(Lib3dsFile *file);
extern LIB3DSAPI void lib3ds_file_insert_camera(Lib3dsFile *file, Lib3dsCamera *camera);
extern LIB3DSAPI void lib3ds_file_remove_camera(Lib3dsFile *file, Lib3dsCamera *camera);
extern LIB3DSAPI Lib3dsCamera* lib3ds_file_camera_by_name(Lib3dsFile *file, const char *name);
extern LIB3DSAPI void lib3ds_file_dump_cameras(Lib3dsFile *file);
extern LIB3DSAPI void lib3ds_file_insert_light(Lib3dsFile *file, Lib3dsLight *light);
extern LIB3DSAPI void lib3ds_file_remove_light(Lib3dsFile *file, Lib3dsLight *light);
extern LIB3DSAPI Lib3dsLight* lib3ds_file_light_by_name(Lib3dsFile *file, const char *name);
extern LIB3DSAPI void lib3ds_file_dump_lights(Lib3dsFile *file);
extern LIB3DSAPI Lib3dsNode* lib3ds_file_node_by_name(Lib3dsFile *file, const char* name,
Lib3dsNodeTypes type);
extern LIB3DSAPI Lib3dsNode* lib3ds_file_node_by_id(Lib3dsFile *file, Lib3dsWord node_id);
extern LIB3DSAPI void lib3ds_file_insert_node(Lib3dsFile *file, Lib3dsNode *node);
extern LIB3DSAPI Lib3dsBool lib3ds_file_remove_node(Lib3dsFile *file, Lib3dsNode *node);
extern LIB3DSAPI void lib3ds_file_dump_nodes(Lib3dsFile *file);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,17 @@
Author of lib3ds is Jan Eric Kyprianidis <www.kyprianidis.com>
The following people have contributed additional changes to lib3ds:
Reed Hedges
David Rogers
Edward Falk
Gernot Zeigler
Haik Lorenz
Jean-Charles Quillet
Mike Frysinger
Miles Bader
Tomas Rapkauskas
Torsten Blank
Ralf Corsepius
Stephane Denis

View File

@@ -0,0 +1,340 @@
GNU GENERAL PUBLIC LICENSE
Version 2, June 1991
Copyright (C) 1989, 1991 Free Software Foundation, Inc.
59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
Everyone is permitted to copy and distribute verbatim copies
of this license document, but changing it is not allowed.
Preamble
The licenses for most software are designed to take away your
freedom to share and change it. By contrast, the GNU General Public
License is intended to guarantee your freedom to share and change free
software--to make sure the software is free for all its users. This
General Public License applies to most of the Free Software
Foundation's software and to any other program whose authors commit to
using it. (Some other Free Software Foundation software is covered by
the GNU Library General Public License instead.) You can apply it to
your programs, too.
When we speak of free software, we are referring to freedom, not
price. Our General Public Licenses are designed to make sure that you
have the freedom to distribute copies of free software (and charge for
this service if you wish), that you receive source code or can get it
if you want it, that you can change the software or use pieces of it
in new free programs; and that you know you can do these things.
To protect your rights, we need to make restrictions that forbid
anyone to deny you these rights or to ask you to surrender the rights.
These restrictions translate to certain responsibilities for you if you
distribute copies of the software, or if you modify it.
For example, if you distribute copies of such a program, whether
gratis or for a fee, you must give the recipients all the rights that
you have. You must make sure that they, too, receive or can get the
source code. And you must show them these terms so they know their
rights.
We protect your rights with two steps: (1) copyright the software, and
(2) offer you this license which gives you legal permission to copy,
distribute and/or modify the software.
Also, for each author's protection and ours, we want to make certain
that everyone understands that there is no warranty for this free
software. If the software is modified by someone else and passed on, we
want its recipients to know that what they have is not the original, so
that any problems introduced by others will not reflect on the original
authors' reputations.
Finally, any free program is threatened constantly by software
patents. We wish to avoid the danger that redistributors of a free
program will individually obtain patent licenses, in effect making the
program proprietary. To prevent this, we have made it clear that any
patent must be licensed for everyone's free use or not licensed at all.
The precise terms and conditions for copying, distribution and
modification follow.
GNU GENERAL PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. This License applies to any program or other work which contains
a notice placed by the copyright holder saying it may be distributed
under the terms of this General Public License. The "Program", below,
refers to any such program or work, and a "work based on the Program"
means either the Program or any derivative work under copyright law:
that is to say, a work containing the Program or a portion of it,
either verbatim or with modifications and/or translated into another
language. (Hereinafter, translation is included without limitation in
the term "modification".) Each licensee is addressed as "you".
Activities other than copying, distribution and modification are not
covered by this License; they are outside its scope. The act of
running the Program is not restricted, and the output from the Program
is covered only if its contents constitute a work based on the
Program (independent of having been made by running the Program).
Whether that is true depends on what the Program does.
1. You may copy and distribute verbatim copies of the Program's
source code as you receive it, in any medium, provided that you
conspicuously and appropriately publish on each copy an appropriate
copyright notice and disclaimer of warranty; keep intact all the
notices that refer to this License and to the absence of any warranty;
and give any other recipients of the Program a copy of this License
along with the Program.
You may charge a fee for the physical act of transferring a copy, and
you may at your option offer warranty protection in exchange for a fee.
2. You may modify your copy or copies of the Program or any portion
of it, thus forming a work based on the Program, and copy and
distribute such modifications or work under the terms of Section 1
above, provided that you also meet all of these conditions:
a) You must cause the modified files to carry prominent notices
stating that you changed the files and the date of any change.
b) You must cause any work that you distribute or publish, that in
whole or in part contains or is derived from the Program or any
part thereof, to be licensed as a whole at no charge to all third
parties under the terms of this License.
c) If the modified program normally reads commands interactively
when run, you must cause it, when started running for such
interactive use in the most ordinary way, to print or display an
announcement including an appropriate copyright notice and a
notice that there is no warranty (or else, saying that you provide
a warranty) and that users may redistribute the program under
these conditions, and telling the user how to view a copy of this
License. (Exception: if the Program itself is interactive but
does not normally print such an announcement, your work based on
the Program is not required to print an announcement.)
These requirements apply to the modified work as a whole. If
identifiable sections of that work are not derived from the Program,
and can be reasonably considered independent and separate works in
themselves, then this License, and its terms, do not apply to those
sections when you distribute them as separate works. But when you
distribute the same sections as part of a whole which is a work based
on the Program, the distribution of the whole must be on the terms of
this License, whose permissions for other licensees extend to the
entire whole, and thus to each and every part regardless of who wrote it.
Thus, it is not the intent of this section to claim rights or contest
your rights to work written entirely by you; rather, the intent is to
exercise the right to control the distribution of derivative or
collective works based on the Program.
In addition, mere aggregation of another work not based on the Program
with the Program (or with a work based on the Program) on a volume of
a storage or distribution medium does not bring the other work under
the scope of this License.
3. You may copy and distribute the Program (or a work based on it,
under Section 2) in object code or executable form under the terms of
Sections 1 and 2 above provided that you also do one of the following:
a) Accompany it with the complete corresponding machine-readable
source code, which must be distributed under the terms of Sections
1 and 2 above on a medium customarily used for software interchange; or,
b) Accompany it with a written offer, valid for at least three
years, to give any third party, for a charge no more than your
cost of physically performing source distribution, a complete
machine-readable copy of the corresponding source code, to be
distributed under the terms of Sections 1 and 2 above on a medium
customarily used for software interchange; or,
c) Accompany it with the information you received as to the offer
to distribute corresponding source code. (This alternative is
allowed only for noncommercial distribution and only if you
received the program in object code or executable form with such
an offer, in accord with Subsection b above.)
The source code for a work means the preferred form of the work for
making modifications to it. For an executable work, complete source
code means all the source code for all modules it contains, plus any
associated interface definition files, plus the scripts used to
control compilation and installation of the executable. However, as a
special exception, the source code distributed need not include
anything that is normally distributed (in either source or binary
form) with the major components (compiler, kernel, and so on) of the
operating system on which the executable runs, unless that component
itself accompanies the executable.
If distribution of executable or object code is made by offering
access to copy from a designated place, then offering equivalent
access to copy the source code from the same place counts as
distribution of the source code, even though third parties are not
compelled to copy the source along with the object code.
4. You may not copy, modify, sublicense, or distribute the Program
except as expressly provided under this License. Any attempt
otherwise to copy, modify, sublicense or distribute the Program is
void, and will automatically terminate your rights under this License.
However, parties who have received copies, or rights, from you under
this License will not have their licenses terminated so long as such
parties remain in full compliance.
5. You are not required to accept this License, since you have not
signed it. However, nothing else grants you permission to modify or
distribute the Program or its derivative works. These actions are
prohibited by law if you do not accept this License. Therefore, by
modifying or distributing the Program (or any work based on the
Program), you indicate your acceptance of this License to do so, and
all its terms and conditions for copying, distributing or modifying
the Program or works based on it.
6. Each time you redistribute the Program (or any work based on the
Program), the recipient automatically receives a license from the
original licensor to copy, distribute or modify the Program subject to
these terms and conditions. You may not impose any further
restrictions on the recipients' exercise of the rights granted herein.
You are not responsible for enforcing compliance by third parties to
this License.
7. If, as a consequence of a court judgment or allegation of patent
infringement or for any other reason (not limited to patent issues),
conditions are imposed on you (whether by court order, agreement or
otherwise) that contradict the conditions of this License, they do not
excuse you from the conditions of this License. If you cannot
distribute so as to satisfy simultaneously your obligations under this
License and any other pertinent obligations, then as a consequence you
may not distribute the Program at all. For example, if a patent
license would not permit royalty-free redistribution of the Program by
all those who receive copies directly or indirectly through you, then
the only way you could satisfy both it and this License would be to
refrain entirely from distribution of the Program.
If any portion of this section is held invalid or unenforceable under
any particular circumstance, the balance of the section is intended to
apply and the section as a whole is intended to apply in other
circumstances.
It is not the purpose of this section to induce you to infringe any
patents or other property right claims or to contest validity of any
such claims; this section has the sole purpose of protecting the
integrity of the free software distribution system, which is
implemented by public license practices. Many people have made
generous contributions to the wide range of software distributed
through that system in reliance on consistent application of that
system; it is up to the author/donor to decide if he or she is willing
to distribute software through any other system and a licensee cannot
impose that choice.
This section is intended to make thoroughly clear what is believed to
be a consequence of the rest of this License.
8. If the distribution and/or use of the Program is restricted in
certain countries either by patents or by copyrighted interfaces, the
original copyright holder who places the Program under this License
may add an explicit geographical distribution limitation excluding
those countries, so that distribution is permitted only in or among
countries not thus excluded. In such case, this License incorporates
the limitation as if written in the body of this License.
9. The Free Software Foundation may publish revised and/or new versions
of the General Public License from time to time. Such new versions will
be similar in spirit to the present version, but may differ in detail to
address new problems or concerns.
Each version is given a distinguishing version number. If the Program
specifies a version number of this License which applies to it and "any
later version", you have the option of following the terms and conditions
either of that version or of any later version published by the Free
Software Foundation. If the Program does not specify a version number of
this License, you may choose any version ever published by the Free Software
Foundation.
10. If you wish to incorporate parts of the Program into other free
programs whose distribution conditions are different, write to the author
to ask for permission. For software which is copyrighted by the Free
Software Foundation, write to the Free Software Foundation; we sometimes
make exceptions for this. Our decision will be guided by the two goals
of preserving the free status of all derivatives of our free software and
of promoting the sharing and reuse of software generally.
NO WARRANTY
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
REPAIR OR CORRECTION.
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGES.
END OF TERMS AND CONDITIONS
How to Apply These Terms to Your New Programs
If you develop a new program, and you want it to be of the greatest
possible use to the public, the best way to achieve this is to make it
free software which everyone can redistribute and change under these terms.
To do so, attach the following notices to the program. It is safest
to attach them to the start of each source file to most effectively
convey the exclusion of warranty; and each file should have at least
the "copyright" line and a pointer to where the full notice is found.
<one line to give the program's name and a brief idea of what it does.>
Copyright (C) <year> <name of author>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 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 General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
Also add information on how to contact you by electronic and paper mail.
If the program is interactive, make it output a short notice like this
when it starts in an interactive mode:
Gnomovision version 69, Copyright (C) year name of author
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
This is free software, and you are welcome to redistribute it
under certain conditions; type `show c' for details.
The hypothetical commands `show w' and `show c' should show the appropriate
parts of the General Public License. Of course, the commands you use may
be called something other than `show w' and `show c'; they could even be
mouse-clicks or menu items--whatever suits your program.
You should also get your employer (if you work as a programmer) or your
school, if any, to sign a "copyright disclaimer" for the program, if
necessary. Here is a sample; alter the names:
Yoyodyne, Inc., hereby disclaims all copyright interest in the program
`Gnomovision' (which makes passes at compilers) written by James Hacker.
<signature of Ty Coon>, 1 April 1989
Ty Coon, President of Vice
This General Public License does not permit incorporating your program into
proprietary programs. If your program is a subroutine library, you may
consider it more useful to permit linking proprietary applications with the
library. If this is what you want to do, use the GNU Library General
Public License instead of this License.

View File

@@ -0,0 +1,17 @@
This is a modified subset of lib3DS (v2.0.0-rc1 - 20080909).
The original lib can be found at www.lib3ds.org.
The modifications are for compatibility only (fixes for compilation).
Here is the original README:
-----
Lib3ds is a free toolkit for handling the "3DS" format for 3D model files.
Its main goal is to simplify the creation of 3DS import and export filters.
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.
The official Lib3ds Homepage can be found at: www.lib3ds.org

View File

@@ -0,0 +1,805 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_H
#define INCLUDED_LIB3DS_H
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 <stddef.h>
#ifndef LIB3DSAPI
#if defined(_MSC_VER) && !defined(LIB3DS_STATIC)
#ifdef LIB3DS_EXPORTS
#define LIB3DSAPI __declspec(dllexport)
#else
#define LIB3DSAPI __declspec(dllimport)
#endif
#else
#define LIB3DSAPI
#endif
#endif
#ifdef __cplusplus
extern "C" {
#endif
/** @defgroup api API */
/** @{ */
typedef enum Lib3dsIoSeek {
LIB3DS_SEEK_SET = 0,
LIB3DS_SEEK_CUR = 1,
LIB3DS_SEEK_END = 2
} Lib3dsIoSeek;
typedef enum Lib3dsLogLevel {
LIB3DS_LOG_ERROR = 0,
LIB3DS_LOG_WARN = 1,
LIB3DS_LOG_INFO = 2,
LIB3DS_LOG_DEBUG = 3
} Lib3dsLogLevel;
typedef struct Lib3dsIo {
void* impl;
void* self;
long (*seek_func) (void *self, long offset, Lib3dsIoSeek origin);
long (*tell_func) (void *self);
size_t (*read_func) (void *self, void *buffer, size_t size);
size_t (*write_func)(void *self, const void *buffer, size_t size);
void (*log_func) (void *self, Lib3dsLogLevel level, int indent, const char *msg);
} Lib3dsIo;
/* Atmosphere settings */
typedef struct Lib3dsAtmosphere {
int use_fog;
float fog_color[3];
int fog_background;
float fog_near_plane;
float fog_near_density;
float fog_far_plane;
float fog_far_density;
int use_layer_fog;
unsigned layer_fog_flags;
float layer_fog_color[3];
float layer_fog_near_y;
float layer_fog_far_y;
float layer_fog_density;
int use_dist_cue;
int dist_cue_background; /* bool */
float dist_cue_near_plane;
float dist_cue_near_dimming;
float dist_cue_far_plane;
float dist_cue_far_dimming;
} Lib3dsAtmosphere;
/* Background settings */
typedef struct Lib3dsBackground {
int use_bitmap;
char bitmap_name[64];
int use_solid;
float solid_color[3];
int use_gradient;
float gradient_percent;
float gradient_top[3];
float gradient_middle[3];
float gradient_bottom[3];
} Lib3dsBackground;
/* Shadow settings */
typedef struct Lib3dsShadow {
short map_size; /* Global shadow map size that ranges from 10 to 4096 */
float low_bias; /* Global shadow low bias */
float hi_bias; /* Global shadow hi bias */
float filter; /* Global shadow filter that ranges from 1 (lowest) to 10 (highest) */
float ray_bias; /* Global raytraced shadow bias */
} Lib3dsShadow;
/* Layout view types */
typedef enum Lib3dsViewType {
LIB3DS_VIEW_NOT_USED = 0,
LIB3DS_VIEW_TOP = 1,
LIB3DS_VIEW_BOTTOM = 2,
LIB3DS_VIEW_LEFT = 3,
LIB3DS_VIEW_RIGHT = 4,
LIB3DS_VIEW_FRONT = 5,
LIB3DS_VIEW_BACK = 6,
LIB3DS_VIEW_USER = 7,
LIB3DS_VIEW_SPOTLIGHT = 18,
LIB3DS_VIEW_CAMERA = 65535
} Lib3dsViewType;
/* Layout styles */
typedef enum Lib3dsLayoutStyle {
LIB3DS_LAYOUT_SINGLE = 0,
LIB3DS_LAYOUT_TWO_PANE_VERT_SPLIT = 1,
LIB3DS_LAYOUT_TWO_PANE_HORIZ_SPLIT = 2,
LIB3DS_LAYOUT_FOUR_PANE = 3,
LIB3DS_LAYOUT_THREE_PANE_LEFT_SPLIT = 4,
LIB3DS_LAYOUT_THREE_PANE_BOTTOM_SPLIT = 5,
LIB3DS_LAYOUT_THREE_PANE_RIGHT_SPLIT = 6,
LIB3DS_LAYOUT_THREE_PANE_TOP_SPLIT = 7,
LIB3DS_LAYOUT_THREE_PANE_VERT_SPLIT = 8,
LIB3DS_LAYOUT_THREE_PANE_HORIZ_SPLIT = 9,
LIB3DS_LAYOUT_FOUR_PANE_LEFT_SPLIT = 10,
LIB3DS_LAYOUT_FOUR_PANE_RIGHT_SPLIT = 11
} Lib3dsLayoutStyle;
/* Layout view settings */
typedef struct Lib3dsView {
int type;
unsigned axis_lock;
short position[2];
short size[2];
float zoom;
float center[3];
float horiz_angle;
float vert_angle;
char camera[11];
} Lib3dsView;
#define LIB3DS_LAYOUT_MAX_VIEWS 32
/* Viewport and default view settings */
typedef struct Lib3dsViewport {
int layout_style;
int layout_active;
int layout_swap;
int layout_swap_prior;
int layout_swap_view;
unsigned short layout_position[2];
unsigned short layout_size[2];
int layout_nviews;
Lib3dsView layout_views[LIB3DS_LAYOUT_MAX_VIEWS];
int default_type;
float default_position[3];
float default_width;
float default_horiz_angle;
float default_vert_angle;
float default_roll_angle;
char default_camera[64];
} Lib3dsViewport;
/* Material texture map flags */
typedef enum Lib3dsTextureMapFlags {
LIB3DS_TEXTURE_DECALE = 0x0001,
LIB3DS_TEXTURE_MIRROR = 0x0002,
LIB3DS_TEXTURE_NEGATE = 0x0008,
LIB3DS_TEXTURE_NO_TILE = 0x0010,
LIB3DS_TEXTURE_SUMMED_AREA = 0x0020,
LIB3DS_TEXTURE_ALPHA_SOURCE = 0x0040,
LIB3DS_TEXTURE_TINT = 0x0080,
LIB3DS_TEXTURE_IGNORE_ALPHA = 0x0100,
LIB3DS_TEXTURE_RGB_TINT = 0x0200
} Lib3dsTextureMapFlags;
/* Material texture map */
typedef struct Lib3dsTextureMap {
unsigned user_id;
void* user_ptr;
char name[64];
unsigned flags;
float percent;
float blur;
float scale[2];
float offset[2];
float rotation;
float tint_1[3];
float tint_2[3];
float tint_r[3];
float tint_g[3];
float tint_b[3];
} Lib3dsTextureMap;
/* Auto reflection texture map flags */
typedef enum Lib3dsAutoReflMapFlags {
LIB3DS_AUTOREFL_USE = 0x0001,
LIB3DS_AUTOREFL_READ_FIRST_FRAME_ONLY = 0x0004,
LIB3DS_AUTOREFL_FLAT_MIRROR = 0x0008
} Lib3dsAutoReflMapFlags;
/* Material shading type */
typedef enum Lib3dsShading {
LIB3DS_SHADING_WIRE_FRAME = 0,
LIB3DS_SHADING_FLAT = 1,
LIB3DS_SHADING_GOURAUD = 2,
LIB3DS_SHADING_PHONG = 3,
LIB3DS_SHADING_METAL = 4
} Lib3dsShading;
/** Material */
typedef struct Lib3dsMaterial {
unsigned user_id;
void* user_ptr;
char name[64]; /* Material name */
float ambient[3]; /* Material ambient reflectivity */
float diffuse[3]; /* Material diffuse reflectivity */
float specular[3]; /* Material specular reflectivity */
float shininess; /* Material specular exponent */
float shin_strength;
int use_blur;
float blur;
float transparency;
float falloff;
int is_additive;
int self_illum_flag; /* bool */
float self_illum;
int use_falloff;
int shading;
int soften; /* bool */
int face_map; /* bool */
int two_sided; /* Material visible from back */
int map_decal; /* bool */
int use_wire;
int use_wire_abs;
float wire_size;
Lib3dsTextureMap texture1_map;
Lib3dsTextureMap texture1_mask;
Lib3dsTextureMap texture2_map;
Lib3dsTextureMap texture2_mask;
Lib3dsTextureMap opacity_map;
Lib3dsTextureMap opacity_mask;
Lib3dsTextureMap bump_map;
Lib3dsTextureMap bump_mask;
Lib3dsTextureMap specular_map;
Lib3dsTextureMap specular_mask;
Lib3dsTextureMap shininess_map;
Lib3dsTextureMap shininess_mask;
Lib3dsTextureMap self_illum_map;
Lib3dsTextureMap self_illum_mask;
Lib3dsTextureMap reflection_map;
Lib3dsTextureMap reflection_mask;
unsigned autorefl_map_flags;
int autorefl_map_anti_alias; /* 0=None, 1=Low, 2=Medium, 3=High */
int autorefl_map_size;
int autorefl_map_frame_step;
} Lib3dsMaterial;
/** Object flags for cameras, lights and meshes */
typedef enum Lib3dsObjectFlags {
LIB3DS_OBJECT_HIDDEN = 0x01,
LIB3DS_OBJECT_VIS_LOFTER = 0x02,
LIB3DS_OBJECT_DOESNT_CAST = 0x04,
LIB3DS_OBJECT_MATTE = 0x08,
LIB3DS_OBJECT_DONT_RCVSHADOW = 0x10,
LIB3DS_OBJECT_FAST = 0x20,
LIB3DS_OBJECT_FROZEN = 0x40
} Lib3dsObjectFlags;
/** Camera object */
typedef struct Lib3dsCamera {
unsigned user_id;
void* user_ptr;
char name[64];
unsigned object_flags; /*< @see Lib3dsObjectFlags */
float position[3];
float target[3];
float roll;
float fov;
int see_cone;
float near_range;
float far_range;
} Lib3dsCamera;
/** Light object */
typedef struct Lib3dsLight {
unsigned user_id;
void* user_ptr;
char name[64];
unsigned object_flags;
int spot_light; /* bool */
int see_cone;
float color[3];
float position[3];
float target[3];
float roll;
int off; /* bool */
float outer_range;
float inner_range;
float multiplier;
/*const char** excludes;*/
float attenuation;
int rectangular_spot; /* bool */
int shadowed; /* bool */
float shadow_bias;
float shadow_filter;
int shadow_size;
float spot_aspect;
int use_projector;
char projector[64];
int spot_overshoot; /* bool */
int ray_shadows; /* bool */
float ray_bias;
float hotspot;
float falloff;
} Lib3dsLight;
/* Texture map projection */
typedef enum {
LIB3DS_MAP_NONE = -1,
LIB3DS_MAP_PLANAR = 0,
LIB3DS_MAP_CYLINDRICAL = 1,
LIB3DS_MAP_SPHERICAL = 2
} Lib3dsMapType;
/** Meaning of Lib3dsFace::flags. ABC are points of the current face
(A: is 1st vertex, B is 2nd vertex, C is 3rd vertex) */
typedef enum Lib3dsFaceFlags {
LIB3DS_FACE_VIS_AC = 0x01, /**< Bit 0: Edge visibility AC */
LIB3DS_FACE_VIS_BC = 0x02, /**< Bit 1: Edge visibility BC */
LIB3DS_FACE_VIS_AB = 0x04, /**< Bit 2: Edge visibility AB */
LIB3DS_FACE_WRAP_U = 0x08, /**< Bit 3: Face is at tex U wrap seam */
LIB3DS_FACE_WRAP_V = 0x10, /**< Bit 4: Face is at tex V wrap seam */
LIB3DS_FACE_SELECT_3 = (1<<13), /**< Bit 13: Selection of the face in selection 3*/
LIB3DS_FACE_SELECT_2 = (1<<14), /**< Bit 14: Selection of the face in selection 2*/
LIB3DS_FACE_SELECT_1 = (1<<15) /**< Bit 15: Selection of the face in selection 1*/
} Lib3dsFaceFlags;
typedef struct Lib3dsFace {
unsigned short index[3];
unsigned short flags;
int material;
unsigned smoothing_group;
} Lib3dsFace;
/* Triangular mesh object */
typedef struct Lib3dsMesh {
unsigned user_id;
void* user_ptr;
char name[64]; /**< Mesh name. Don't use more than 8 characters */
unsigned object_flags; /**< @see Lib3dsObjectFlags */
int color; /**< Index to editor palette [0..255] */
float matrix[4][4]; /**< Transformation matrix for mesh data */
unsigned short nvertices; /**< Number of vertices in vertex array (max. 65535) */
float (*vertices)[3];
float (*texcos)[2];
unsigned short* vflags;
unsigned short nfaces; /**< Number of faces in face array (max. 65535) */
Lib3dsFace* faces;
char box_front[64];
char box_back[64];
char box_left[64];
char box_right[64];
char box_top[64];
char box_bottom[64];
int map_type;
float map_pos[3];
float map_matrix[4][4];
float map_scale;
float map_tile[2];
float map_planar_size[2];
float map_cylinder_height;
} Lib3dsMesh;
typedef enum Lib3dsNodeType {
LIB3DS_NODE_AMBIENT_COLOR = 0,
LIB3DS_NODE_MESH_INSTANCE = 1,
LIB3DS_NODE_CAMERA = 2,
LIB3DS_NODE_CAMERA_TARGET = 3,
LIB3DS_NODE_OMNILIGHT = 4,
LIB3DS_NODE_SPOTLIGHT = 5,
LIB3DS_NODE_SPOTLIGHT_TARGET= 6
} Lib3dsNodeType;
typedef enum Lib3dsNodeFlags{
LIB3DS_NODE_HIDDEN = 0x000800,
LIB3DS_NODE_SHOW_PATH = 0x010000,
LIB3DS_NODE_SMOOTHING = 0x020000,
LIB3DS_NODE_MOTION_BLUR = 0x100000,
LIB3DS_NODE_MORPH_MATERIALS = 0x400000
} Lib3dsNodeFlags;
typedef struct Lib3dsNode {
unsigned user_id;
void* user_ptr;
struct Lib3dsNode* next;
struct Lib3dsNode* childs;
struct Lib3dsNode* parent;
Lib3dsNodeType type;
unsigned short node_id; /**< 0..65535 */
char name[64];
unsigned flags;
float matrix[4][4];
} Lib3dsNode;
typedef enum Lib3dsKeyFlags {
LIB3DS_KEY_USE_TENS = 0x01,
LIB3DS_KEY_USE_CONT = 0x02,
LIB3DS_KEY_USE_BIAS = 0x04,
LIB3DS_KEY_USE_EASE_TO = 0x08,
LIB3DS_KEY_USE_EASE_FROM = 0x10
} Lib3dsKeyFlags;
typedef struct Lib3dsKey {
int frame;
unsigned flags;
float tens;
float cont;
float bias;
float ease_to;
float ease_from;
float value[4];
} Lib3dsKey;
typedef enum Lib3dsTrackType {
LIB3DS_TRACK_BOOL = 0,
LIB3DS_TRACK_FLOAT = 1,
LIB3DS_TRACK_VECTOR = 3,
LIB3DS_TRACK_QUAT = 4
} Lib3dsTrackType;
typedef enum {
LIB3DS_TRACK_REPEAT = 0x0001,
LIB3DS_TRACK_SMOOTH = 0x0002,
LIB3DS_TRACK_LOCK_X = 0x0008,
LIB3DS_TRACK_LOCK_Y = 0x0010,
LIB3DS_TRACK_LOCK_Z = 0x0020,
LIB3DS_TRACK_UNLINK_X = 0x0100,
LIB3DS_TRACK_UNLINK_Y = 0x0200,
LIB3DS_TRACK_UNLINK_Z = 0x0400
} Lib3dsTrackFlags;
typedef struct Lib3dsTrack {
unsigned flags;
Lib3dsTrackType type;
int nkeys;
Lib3dsKey* keys;
} Lib3dsTrack;
typedef struct Lib3dsAmbientColorNode {
Lib3dsNode base;
float color[3];
Lib3dsTrack color_track;
} Lib3dsAmbientColorNode;
typedef struct Lib3dsMeshInstanceNode {
Lib3dsNode base;
float pivot[3];
char instance_name[64];
float bbox_min[3];
float bbox_max[3];
int hide;
float pos[3];
float rot[4];
float scl[3];
float morph_smooth;
char morph[64];
Lib3dsTrack pos_track;
Lib3dsTrack rot_track;
Lib3dsTrack scl_track;
Lib3dsTrack hide_track;
} Lib3dsMeshInstanceNode;
typedef struct Lib3dsCameraNode {
Lib3dsNode base;
float pos[3];
float fov;
float roll;
Lib3dsTrack pos_track;
Lib3dsTrack fov_track;
Lib3dsTrack roll_track;
} Lib3dsCameraNode;
typedef struct Lib3dsTargetNode {
Lib3dsNode base;
float pos[3];
Lib3dsTrack pos_track;
} Lib3dsTargetNode;
typedef struct Lib3dsOmnilightNode {
Lib3dsNode base;
float pos[3];
float color[3];
Lib3dsTrack pos_track;
Lib3dsTrack color_track;
} Lib3dsOmnilightNode;
typedef struct Lib3dsSpotlightNode {
Lib3dsNode base;
float pos[3];
float color[3];
float hotspot;
float falloff;
float roll;
Lib3dsTrack pos_track;
Lib3dsTrack color_track;
Lib3dsTrack hotspot_track;
Lib3dsTrack falloff_track;
Lib3dsTrack roll_track;
} Lib3dsSpotlightNode;
typedef struct Lib3dsFile {
unsigned user_id;
void* user_ptr;
unsigned mesh_version;
unsigned keyf_revision;
char name[12+1];
float master_scale;
float construction_plane[3];
float ambient[3];
Lib3dsShadow shadow;
Lib3dsBackground background;
Lib3dsAtmosphere atmosphere;
Lib3dsViewport viewport;
Lib3dsViewport viewport_keyf;
int frames;
int segment_from;
int segment_to;
int current_frame;
int materials_size;
int nmaterials;
Lib3dsMaterial** materials;
int cameras_size;
int ncameras;
Lib3dsCamera** cameras;
int lights_size;
int nlights;
Lib3dsLight** lights;
int meshes_size;
int nmeshes;
Lib3dsMesh** meshes;
Lib3dsNode* nodes;
} Lib3dsFile;
extern LIB3DSAPI Lib3dsFile* lib3ds_file_open(const char *filename);
extern LIB3DSAPI int lib3ds_file_save(Lib3dsFile *file, const char *filename);
extern LIB3DSAPI Lib3dsFile* lib3ds_file_new();
extern LIB3DSAPI void lib3ds_file_free(Lib3dsFile *file);
extern LIB3DSAPI void lib3ds_file_eval(Lib3dsFile *file, float t);
extern LIB3DSAPI int lib3ds_file_read(Lib3dsFile *file, Lib3dsIo *io);
extern LIB3DSAPI int lib3ds_file_write(Lib3dsFile *file, Lib3dsIo *io);
extern LIB3DSAPI void lib3ds_file_reserve_materials(Lib3dsFile *file, int size, int force);
extern LIB3DSAPI void lib3ds_file_insert_material(Lib3dsFile *file, Lib3dsMaterial *material, int index);
extern LIB3DSAPI void lib3ds_file_remove_material(Lib3dsFile *file, int index);
extern LIB3DSAPI int lib3ds_file_material_by_name(Lib3dsFile *file, const char *name);
extern LIB3DSAPI void lib3ds_file_reserve_cameras(Lib3dsFile *file, int size, int force);
extern LIB3DSAPI void lib3ds_file_insert_camera(Lib3dsFile *file, Lib3dsCamera *camera, int index);
extern LIB3DSAPI void lib3ds_file_remove_camera(Lib3dsFile *file, int index);
extern LIB3DSAPI int lib3ds_file_camera_by_name(Lib3dsFile *file, const char *name);
extern LIB3DSAPI void lib3ds_file_reserve_lights(Lib3dsFile *file, int size, int force);
extern LIB3DSAPI void lib3ds_file_insert_light(Lib3dsFile *file, Lib3dsLight *light, int index);
extern LIB3DSAPI void lib3ds_file_remove_light(Lib3dsFile *file, int index);
extern LIB3DSAPI int lib3ds_file_light_by_name(Lib3dsFile *file, const char *name);
extern LIB3DSAPI void lib3ds_file_reserve_meshes(Lib3dsFile *file, int size, int force);
extern LIB3DSAPI void lib3ds_file_insert_mesh(Lib3dsFile *file, Lib3dsMesh *mesh, int index);
extern LIB3DSAPI void lib3ds_file_remove_mesh(Lib3dsFile *file, int index);
extern LIB3DSAPI int lib3ds_file_mesh_by_name(Lib3dsFile *file, const char *name);
extern LIB3DSAPI Lib3dsMesh* lib3ds_file_mesh_for_node(Lib3dsFile *file, Lib3dsNode *node);
extern LIB3DSAPI Lib3dsNode* lib3ds_file_node_by_name(Lib3dsFile *file, const char* name, Lib3dsNodeType type);
extern LIB3DSAPI Lib3dsNode* lib3ds_file_node_by_id(Lib3dsFile *file, unsigned short node_id);
extern LIB3DSAPI void lib3ds_file_append_node(Lib3dsFile *file, Lib3dsNode *node, Lib3dsNode *parent);
extern LIB3DSAPI void lib3ds_file_insert_node(Lib3dsFile *file, Lib3dsNode *node, Lib3dsNode *at);
extern LIB3DSAPI void lib3ds_file_remove_node(Lib3dsFile *file, Lib3dsNode *node);
extern LIB3DSAPI void lib3ds_file_minmax_node_id(Lib3dsFile *file, unsigned short *min_id, unsigned short *max_id);
extern LIB3DSAPI void lib3ds_file_create_nodes_for_meshes(Lib3dsFile *file);
/**
This function computes the bounding box of meshes, cameras
and lights defined in the 3D editor.
\param file The Lib3dsFile object to be examined.
\param include_meshes Include meshes in bounding box calculation.
\param include_cameras Include cameras in bounding box calculation.
\param include_lights Include lights in bounding box calculation.
\param bmin Returned minimum x,y,z values.
\param bmax Returned maximum x,y,z values.
*/
extern LIB3DSAPI void lib3ds_file_bounding_box_of_objects(
Lib3dsFile *file,
int include_meshes,
int include_cameras,
int include_lights,
float bmin[3],
float bmax[3]);
/**
This function computes the bounding box of mesh, camera
and light instances defined in the Keyframer.
\param file The Lib3dsFile object to be examined.
\param include_meshes Include meshes in bounding box calculation.
\param include_cameras Include cameras in bounding box calculation.
\param include_lights Include lights in bounding box calculation.
\param bmin Returned minimum x,y,z values.
\param bmax Returned maximum x,y,z values.
\param matrix A matrix describing the coordinate system to
calculate the bounding box in.
*/
extern LIB3DSAPI void lib3ds_file_bounding_box_of_nodes(
Lib3dsFile *file,
int include_meshes,
int include_cameras,
int include_lights,
float bmin[3],
float bmax[3],
float matrix[4][4]);
extern LIB3DSAPI Lib3dsMaterial* lib3ds_material_new(const char *name);
extern LIB3DSAPI void lib3ds_material_free(Lib3dsMaterial *material);
extern LIB3DSAPI Lib3dsCamera* lib3ds_camera_new(const char *name);
extern LIB3DSAPI void lib3ds_camera_free(Lib3dsCamera *mesh);
extern LIB3DSAPI Lib3dsLight* lib3ds_light_new(const char *name);
extern LIB3DSAPI void lib3ds_light_free(Lib3dsLight *mesh);
extern LIB3DSAPI Lib3dsMesh* lib3ds_mesh_new(const char *name);
extern LIB3DSAPI void lib3ds_mesh_free(Lib3dsMesh *mesh);
extern LIB3DSAPI void lib3ds_mesh_resize_vertices(Lib3dsMesh *mesh, int nvertices, int use_texcos, int use_flags);
extern LIB3DSAPI void lib3ds_mesh_resize_faces(Lib3dsMesh *mesh, int nfaces);
extern LIB3DSAPI void lib3ds_mesh_bounding_box(Lib3dsMesh *mesh, float bmin[3], float bmax[3]);
extern LIB3DSAPI void lib3ds_mesh_calculate_face_normals(Lib3dsMesh *mesh, float (*face_normals)[3]);
extern LIB3DSAPI void lib3ds_mesh_calculate_vertex_normals(Lib3dsMesh *mesh, float (*normals)[3]);
extern LIB3DSAPI Lib3dsNode* lib3ds_node_new(Lib3dsNodeType type);
extern LIB3DSAPI Lib3dsAmbientColorNode* lib3ds_node_new_ambient_color(float color0[3]);
extern LIB3DSAPI Lib3dsMeshInstanceNode* lib3ds_node_new_mesh_instance(Lib3dsMesh *mesh, const char* instance_name, float pos0[3], float scl0[3], float rot0[4]);
extern LIB3DSAPI Lib3dsCameraNode* lib3ds_node_new_camera(Lib3dsCamera *camera);
extern LIB3DSAPI Lib3dsTargetNode* lib3ds_node_new_camera_target(Lib3dsCamera *camera);
extern LIB3DSAPI Lib3dsOmnilightNode* lib3ds_node_new_omnilight(Lib3dsLight *light);
extern LIB3DSAPI Lib3dsSpotlightNode* lib3ds_node_new_spotlight(Lib3dsLight *light);
extern LIB3DSAPI Lib3dsTargetNode* lib3ds_node_new_spotlight_target(Lib3dsLight *light);
extern LIB3DSAPI void lib3ds_node_free(Lib3dsNode *node);
extern LIB3DSAPI void lib3ds_node_eval(Lib3dsNode *node, float t);
extern LIB3DSAPI Lib3dsNode* lib3ds_node_by_name(Lib3dsNode *node, const char* name, Lib3dsNodeType type);
extern LIB3DSAPI Lib3dsNode* lib3ds_node_by_id(Lib3dsNode *node, unsigned short node_id);
extern LIB3DSAPI Lib3dsTrack* lib3ds_track_new(Lib3dsTrackType type, int nkeys);
extern LIB3DSAPI void lib3ds_track_free(Lib3dsTrack *track);
extern LIB3DSAPI void lib3ds_track_resize(Lib3dsTrack *track, int nkeys);
extern LIB3DSAPI void lib3ds_track_eval_bool(Lib3dsTrack *track, int *b, float t);
extern LIB3DSAPI void lib3ds_track_eval_float(Lib3dsTrack *track, float *f, float t);
extern LIB3DSAPI void lib3ds_track_eval_vector(Lib3dsTrack *track, float v[3], float t);
extern LIB3DSAPI void lib3ds_track_eval_quat(Lib3dsTrack *track, float q[4], float t);
/**
Calculates the ease in/out function. See Lib3dsKey for details.
\param fp Previous frame number.
\param fc Current frame number.
\param fn Next frame number.
\param ease_from Ease in value [0, 1.0]
\param ease_to Ease out value [0, 1.0]
*/
extern LIB3DSAPI float lib3ds_math_ease(
float fp,
float fc,
float fn,
float ease_from,
float ease_to);
/**
Computes a point on a n-dimensional cubic hermite spline.
\param v
[out] Result
\param a
[in] First point of the spline.
\param p
[in] Tangent at the first point of the spline.
\param q
[in] Tangent at the second point of the spline.
\param b
[in] Second point of the spline.
\param n
[in] Dimension
\param t
[in] Parameter value [0...1]
*/
extern LIB3DSAPI void lib3ds_math_cubic_interp(
float *v,
float *a,
float *p,
float *q,
float *b,
int n,
float t);
extern LIB3DSAPI void lib3ds_vector_make(
float c[3],
float x,
float y,
float z);
/**
Sets all components of a vector to zero.
\param c
The Pointer to the vector.
*/
extern LIB3DSAPI void lib3ds_vector_zero(
float c[3]);
/**
Copies all components of a vector to another vector.
\param dst
[out] The destination vector.
\param src
[in] The source vector.
*/
extern LIB3DSAPI void lib3ds_vector_copy(
float dst[3],
float src[3]);
/**
Negates all components of a vector.
\param c
The Pointer to the vector.
*/
extern LIB3DSAPI void lib3ds_vector_neg(
float c[3]);
extern LIB3DSAPI void lib3ds_vector_make(float c[3], float x, float y, float z);
extern LIB3DSAPI void lib3ds_vector_zero(float c[3]);
extern LIB3DSAPI void lib3ds_vector_add(float c[3], float a[3], float b[3]);
extern LIB3DSAPI void lib3ds_vector_sub(float c[3], float a[3], float b[3]);
extern LIB3DSAPI void lib3ds_vector_scalar_mul(float c[3], float a[3], float k);
extern LIB3DSAPI void lib3ds_vector_cross(float c[3], float a[3], float b[3]);
extern LIB3DSAPI float lib3ds_vector_dot(float a[3], float b[3]);
extern LIB3DSAPI float lib3ds_vector_length(float c[3]);
extern LIB3DSAPI void lib3ds_vector_normalize(float c[3]);
extern LIB3DSAPI void lib3ds_vector_normal(float n[3], float a[3], float b[3], float c[3]);
extern LIB3DSAPI void lib3ds_vector_min(float c[3], float a[3]);
extern LIB3DSAPI void lib3ds_vector_max(float c[3], float a[3]);
extern LIB3DSAPI void lib3ds_vector_transform(float c[3], float m[4][4], float a[3]);
extern LIB3DSAPI void lib3ds_quat_identity(float c[4]);
extern LIB3DSAPI void lib3ds_quat_copy(float dest[4], float src[4]);
extern LIB3DSAPI void lib3ds_quat_axis_angle(float c[4], float axis[3], float angle);
extern LIB3DSAPI void lib3ds_quat_neg(float c[4]);
extern LIB3DSAPI void lib3ds_quat_cnj(float c[4]);
extern LIB3DSAPI void lib3ds_quat_mul(float c[4], float a[4], float b[4]);
extern LIB3DSAPI void lib3ds_quat_scalar(float c[4], float k);
extern LIB3DSAPI void lib3ds_quat_normalize(float c[4]);
extern LIB3DSAPI void lib3ds_quat_inv(float c[4]);
extern LIB3DSAPI float lib3ds_quat_dot(float a[4], float b[4]);
extern LIB3DSAPI float lib3ds_quat_norm(float c[4]);
extern LIB3DSAPI void lib3ds_quat_ln(float c[4]);
extern LIB3DSAPI void lib3ds_quat_ln_dif(float c[4], float a[4], float b[4]);
extern LIB3DSAPI void lib3ds_quat_exp(float c[4]);
extern LIB3DSAPI void lib3ds_quat_slerp(float c[4], float a[4], float b[4], float t);
extern LIB3DSAPI void lib3ds_quat_squad(float c[4], float a[4], float p[4], float q[4], float b[4], float t);
extern LIB3DSAPI void lib3ds_quat_tangent(float c[4], float p[4], float q[4], float n[4]);
extern LIB3DSAPI void lib3ds_matrix_zero(float m[4][4]);
extern LIB3DSAPI void lib3ds_matrix_identity(float m[4][4]);
extern LIB3DSAPI void lib3ds_matrix_copy(float dest[4][4], float src[4][4]);
extern LIB3DSAPI void lib3ds_matrix_neg(float m[4][4]);
extern LIB3DSAPI void lib3ds_matrix_transpose(float m[4][4]);
extern LIB3DSAPI void lib3ds_matrix_add(float m[4][4], float a[4][4], float b[4][4]);
extern LIB3DSAPI void lib3ds_matrix_sub(float m[4][4], float a[4][4], float b[4][4]);
extern LIB3DSAPI void lib3ds_matrix_mult(float m[4][4], float a[4][4], float b[4][4]);
extern LIB3DSAPI void lib3ds_matrix_scalar(float m[4][4], float k);
extern LIB3DSAPI float lib3ds_matrix_det(float m[4][4]);
extern LIB3DSAPI int lib3ds_matrix_inv(float m[4][4]);
extern LIB3DSAPI void lib3ds_matrix_translate(float m[4][4], float x, float y, float z);
extern LIB3DSAPI void lib3ds_matrix_scale(float m[4][4], float x, float y, float z);
extern LIB3DSAPI void lib3ds_matrix_rotate_quat(float m[4][4], float q[4]);
extern LIB3DSAPI void lib3ds_matrix_rotate(float m[4][4], float angle, float ax, float ay, float az);
extern LIB3DSAPI void lib3ds_matrix_camera(float m[4][4], float pos[3], float tgt[3], float roll);
/* --- Code for OpenSceneGraph --- */
extern LIB3DSAPI void setByteOrder();
/* Definitions for compatibility with previous lib3DS used: */
typedef float Lib3dsMatrix[4][4];
typedef float Lib3dsVector[3];
typedef void Lib3dsUserData;
/* --- (end) Code for OpenSceneGraph --- */
/** @} */
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,253 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
static void
fog_read(Lib3dsAtmosphere *at, Lib3dsIo *io) {
Lib3dsChunk c;
uint16_t chunk;
lib3ds_chunk_read_start(&c, CHK_FOG, io);
at->fog_near_plane = lib3ds_io_read_float(io);
at->fog_near_density = lib3ds_io_read_float(io);
at->fog_far_plane = lib3ds_io_read_float(io);
at->fog_far_density = lib3ds_io_read_float(io);
lib3ds_chunk_read_tell(&c, io);
while ((chunk = lib3ds_chunk_read_next(&c, io)) != 0) {
switch (chunk) {
case CHK_LIN_COLOR_F: {
int i;
for (i = 0; i < 3; ++i) {
at->fog_color[i] = lib3ds_io_read_float(io);
}
}
break;
case CHK_COLOR_F:
break;
case CHK_FOG_BGND: {
at->fog_background = TRUE;
}
break;
default:
lib3ds_chunk_unknown(chunk, io);
}
}
lib3ds_chunk_read_end(&c, io);
}
static void
layer_fog_read(Lib3dsAtmosphere *at, Lib3dsIo *io) {
Lib3dsChunk c;
uint16_t chunk;
int have_lin = FALSE;
lib3ds_chunk_read_start(&c, CHK_LAYER_FOG, io);
at->layer_fog_near_y = lib3ds_io_read_float(io);
at->layer_fog_far_y = lib3ds_io_read_float(io);
at->layer_fog_density = lib3ds_io_read_float(io);
at->layer_fog_flags = lib3ds_io_read_dword(io);
lib3ds_chunk_read_tell(&c, io);
while ((chunk = lib3ds_chunk_read_next(&c, io)) != 0) {
switch (chunk) {
case CHK_LIN_COLOR_F:
lib3ds_io_read_rgb(io, at->layer_fog_color);
have_lin = TRUE;
break;
case CHK_COLOR_F:
lib3ds_io_read_rgb(io, at->layer_fog_color);
break;
default:
lib3ds_chunk_unknown(chunk, io);
}
}
lib3ds_chunk_read_end(&c, io);
}
static void
distance_cue_read(Lib3dsAtmosphere *at, Lib3dsIo *io) {
Lib3dsChunk c;
uint16_t chunk;
lib3ds_chunk_read_start(&c, CHK_DISTANCE_CUE, io);
at->dist_cue_near_plane = lib3ds_io_read_float(io);
at->dist_cue_near_dimming = lib3ds_io_read_float(io);
at->dist_cue_far_plane = lib3ds_io_read_float(io);
at->dist_cue_far_dimming = lib3ds_io_read_float(io);
lib3ds_chunk_read_tell(&c, io);
while ((chunk = lib3ds_chunk_read_next(&c, io)) != 0) {
switch (chunk) {
case CHK_DCUE_BGND: {
at->dist_cue_background = TRUE;
}
break;
default:
lib3ds_chunk_unknown(chunk, io);
}
}
lib3ds_chunk_read_end(&c, io);
}
void
lib3ds_atmosphere_read(Lib3dsAtmosphere *atmosphere, Lib3dsIo *io) {
Lib3dsChunk c;
lib3ds_chunk_read(&c, io);
switch (c.chunk) {
case CHK_FOG: {
lib3ds_chunk_read_reset(&c, io);
fog_read(atmosphere, io);
break;
}
case CHK_LAYER_FOG: {
lib3ds_chunk_read_reset(&c, io);
layer_fog_read(atmosphere, io);
break;
}
case CHK_DISTANCE_CUE: {
lib3ds_chunk_read_reset(&c, io);
distance_cue_read(atmosphere, io);
break;
}
case CHK_USE_FOG: {
atmosphere->use_fog = TRUE;
break;
}
case CHK_USE_LAYER_FOG: {
atmosphere->use_layer_fog = TRUE;
break;
}
case CHK_USE_DISTANCE_CUE: {
atmosphere->use_dist_cue = TRUE;
break;
}
}
}
void
lib3ds_atmosphere_write(Lib3dsAtmosphere *atmosphere, Lib3dsIo *io) {
if (atmosphere->use_fog) { /*---- LIB3DS_FOG ----*/
Lib3dsChunk c;
c.chunk = CHK_FOG;
lib3ds_chunk_write_start(&c, io);
lib3ds_io_write_float(io, atmosphere->fog_near_plane);
lib3ds_io_write_float(io, atmosphere->fog_near_density);
lib3ds_io_write_float(io, atmosphere->fog_far_plane);
lib3ds_io_write_float(io, atmosphere->fog_far_density);
{
Lib3dsChunk c;
c.chunk = CHK_COLOR_F;
c.size = 18;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_rgb(io, atmosphere->fog_color);
}
if (atmosphere->fog_background) {
Lib3dsChunk c;
c.chunk = CHK_FOG_BGND;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
lib3ds_chunk_write_end(&c, io);
}
if (atmosphere->use_layer_fog) { /*---- LIB3DS_LAYER_FOG ----*/
Lib3dsChunk c;
c.chunk = CHK_LAYER_FOG;
c.size = 40;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, atmosphere->layer_fog_near_y);
lib3ds_io_write_float(io, atmosphere->layer_fog_far_y);
lib3ds_io_write_float(io, atmosphere->layer_fog_near_y);
lib3ds_io_write_dword(io, atmosphere->layer_fog_flags);
{
Lib3dsChunk c;
c.chunk = CHK_COLOR_F;
c.size = 18;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_rgb(io, atmosphere->fog_color);
}
}
if (atmosphere->use_dist_cue) { /*---- LIB3DS_DISTANCE_CUE ----*/
Lib3dsChunk c;
c.chunk = CHK_DISTANCE_CUE;
lib3ds_chunk_write_start(&c, io);
lib3ds_io_write_float(io, atmosphere->dist_cue_near_plane);
lib3ds_io_write_float(io, atmosphere->dist_cue_near_dimming);
lib3ds_io_write_float(io, atmosphere->dist_cue_far_plane);
lib3ds_io_write_float(io, atmosphere->dist_cue_far_dimming);
if (atmosphere->dist_cue_background) {
Lib3dsChunk c;
c.chunk = CHK_DCUE_BGND;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
lib3ds_chunk_write_end(&c, io);
}
if (atmosphere->use_fog) { /*---- LIB3DS_USE_FOG ----*/
Lib3dsChunk c;
c.chunk = CHK_USE_FOG;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
if (atmosphere->use_layer_fog) { /*---- LIB3DS_USE_LAYER_FOG ----*/
Lib3dsChunk c;
c.chunk = CHK_USE_LAYER_FOG;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
if (atmosphere->use_dist_cue) { /*---- LIB3DS_USE_DISTANCE_CUE ----*/
Lib3dsChunk c;
c.chunk = CHK_USE_V_GRADIENT;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
}

View File

@@ -0,0 +1,213 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
static void
solid_bgnd_read(Lib3dsBackground *background, Lib3dsIo *io) {
Lib3dsChunk c;
uint16_t chunk;
int have_lin = FALSE;
lib3ds_chunk_read_start(&c, CHK_SOLID_BGND, io);
while ((chunk = lib3ds_chunk_read_next(&c, io)) != 0) {
switch (chunk) {
case CHK_LIN_COLOR_F:
lib3ds_io_read_rgb(io, background->solid_color);
have_lin = TRUE;
break;
case CHK_COLOR_F:
lib3ds_io_read_rgb(io, background->solid_color);
break;
default:
lib3ds_chunk_unknown(chunk, io);
}
}
lib3ds_chunk_read_end(&c, io);
}
static void
v_gradient_read(Lib3dsBackground *background, Lib3dsIo *io) {
Lib3dsChunk c;
uint16_t chunk;
int index[2];
float col[2][3][3];
int have_lin = 0;
lib3ds_chunk_read_start(&c, CHK_V_GRADIENT, io);
background->gradient_percent = lib3ds_io_read_float(io);
lib3ds_chunk_read_tell(&c, io);
index[0] = index[1] = 0;
while ((chunk = lib3ds_chunk_read_next(&c, io)) != 0) {
switch (chunk) {
case CHK_COLOR_F:
lib3ds_io_read_rgb(io, col[0][index[0]]);
index[0]++;
break;
case CHK_LIN_COLOR_F:
lib3ds_io_read_rgb(io, col[1][index[1]]);
index[1]++;
have_lin = 1;
break;
default:
lib3ds_chunk_unknown(chunk, io);
}
}
{
int i;
for (i = 0; i < 3; ++i) {
background->gradient_top[i] = col[have_lin][0][i];
background->gradient_middle[i] = col[have_lin][1][i];
background->gradient_bottom[i] = col[have_lin][2][i];
}
}
lib3ds_chunk_read_end(&c, io);
}
void
lib3ds_background_read(Lib3dsBackground *background, Lib3dsIo *io) {
Lib3dsChunk c;
lib3ds_chunk_read(&c, io);
switch (c.chunk) {
case CHK_BIT_MAP: {
lib3ds_io_read_string(io, background->bitmap_name, 64);
break;
}
case CHK_SOLID_BGND: {
lib3ds_chunk_read_reset(&c, io);
solid_bgnd_read(background, io);
break;
}
case CHK_V_GRADIENT: {
lib3ds_chunk_read_reset(&c, io);
v_gradient_read(background, io);
break;
}
case CHK_USE_BIT_MAP: {
background->use_bitmap = TRUE;
break;
}
case CHK_USE_SOLID_BGND: {
background->use_solid = TRUE;
break;
}
case CHK_USE_V_GRADIENT: {
background->use_gradient = TRUE;
break;
}
}
}
static void
colorf_write(float rgb[3], Lib3dsIo *io) {
Lib3dsChunk c;
c.chunk = CHK_COLOR_F;
c.size = 18;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_rgb(io, rgb);
c.chunk = CHK_LIN_COLOR_F;
c.size = 18;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_rgb(io, rgb);
}
static int
colorf_defined(float rgb[3]) {
int i;
for (i = 0; i < 3; ++i) {
if (fabs(rgb[i]) > LIB3DS_EPSILON) {
break;
}
}
return(i < 3);
}
void
lib3ds_background_write(Lib3dsBackground *background, Lib3dsIo *io) {
if (strlen(background->bitmap_name)) { /*---- LIB3DS_BIT_MAP ----*/
Lib3dsChunk c;
c.chunk = CHK_BIT_MAP;
c.size = 6 + 1 + (uint32_t)strlen(background->bitmap_name);
lib3ds_chunk_write(&c, io);
lib3ds_io_write_string(io, background->bitmap_name);
}
if (colorf_defined(background->solid_color)) { /*---- LIB3DS_SOLID_BGND ----*/
Lib3dsChunk c;
c.chunk = CHK_SOLID_BGND;
c.size = 42;
lib3ds_chunk_write(&c, io);
colorf_write(background->solid_color, io);
}
if (colorf_defined(background->gradient_top) ||
colorf_defined(background->gradient_middle) ||
colorf_defined(background->gradient_bottom)) { /*---- LIB3DS_V_GRADIENT ----*/
Lib3dsChunk c;
c.chunk = CHK_V_GRADIENT;
c.size = 118;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, background->gradient_percent);
colorf_write(background->gradient_top, io);
colorf_write(background->gradient_middle, io);
colorf_write(background->gradient_bottom, io);
}
if (background->use_bitmap) { /*---- LIB3DS_USE_BIT_MAP ----*/
Lib3dsChunk c;
c.chunk = CHK_USE_BIT_MAP;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
if (background->use_solid) { /*---- LIB3DS_USE_SOLID_BGND ----*/
Lib3dsChunk c;
c.chunk = CHK_USE_SOLID_BGND;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
if (background->use_gradient) { /*---- LIB3DS_USE_V_GRADIENT ----*/
Lib3dsChunk c;
c.chunk = CHK_USE_V_GRADIENT;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
}

View File

@@ -0,0 +1,165 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
/*!
* Return a new Lib3dsCamera object.
*
* Object is initialized with the given name and fov=45. All other
* values are 0.
*
* \param name Name of this camera. Must not be NULL. Must be < 64 characters.
*
* \return Lib3dsCamera object or NULL on failure.
*/
Lib3dsCamera*
lib3ds_camera_new(const char *name) {
Lib3dsCamera *camera;
assert(name);
assert(strlen(name) < 64);
camera = (Lib3dsCamera*)calloc(sizeof(Lib3dsCamera), 1);
if (!camera) {
return(0);
}
strcpy(camera->name, name);
camera->fov = 45.0f;
return(camera);
}
/*!
* Free a Lib3dsCamera object and all of its resources.
*
* \param camera Lib3dsCamera object to be freed.
*/
void
lib3ds_camera_free(Lib3dsCamera *camera) {
memset(camera, 0, sizeof(Lib3dsCamera));
free(camera);
}
/*!
* Read a camera definition from a file.
*
* This function is called by lib3ds_file_read(), and you probably
* don't want to call it directly.
*
* \param camera A Lib3dsCamera to be filled in.
* \param io A Lib3dsIo object previously set up by the caller.
*
* \see lib3ds_file_read
*/
void
lib3ds_camera_read(Lib3dsCamera *camera, Lib3dsIo *io) {
Lib3dsChunk c;
uint16_t chunk;
lib3ds_chunk_read_start(&c, CHK_N_CAMERA, io);
{
int i;
for (i = 0; i < 3; ++i) {
camera->position[i] = lib3ds_io_read_float(io);
}
for (i = 0; i < 3; ++i) {
camera->target[i] = lib3ds_io_read_float(io);
}
}
camera->roll = lib3ds_io_read_float(io);
{
float s;
s = lib3ds_io_read_float(io);
if (fabs(s) < LIB3DS_EPSILON) {
camera->fov = 45.0;
} else {
camera->fov = 2400.0f / s;
}
}
lib3ds_chunk_read_tell(&c, io);
while ((chunk = lib3ds_chunk_read_next(&c, io)) != 0) {
switch (chunk) {
case CHK_CAM_SEE_CONE: {
camera->see_cone = TRUE;
}
break;
case CHK_CAM_RANGES: {
camera->near_range = lib3ds_io_read_float(io);
camera->far_range = lib3ds_io_read_float(io);
}
break;
default:
lib3ds_chunk_unknown(chunk, io);
}
}
lib3ds_chunk_read_end(&c, io);
}
/*!
* Write a camera definition to a file.
*
* This function is called by lib3ds_file_write(), and you probably
* don't want to call it directly.
*
* \param camera A Lib3dsCamera to be written.
* \param io A Lib3dsIo object previously set up by the caller.
*
* \see lib3ds_file_write
*/
void
lib3ds_camera_write(Lib3dsCamera *camera, Lib3dsIo *io) {
Lib3dsChunk c;
c.chunk = CHK_N_CAMERA;
lib3ds_chunk_write_start(&c, io);
lib3ds_io_write_vector(io, camera->position);
lib3ds_io_write_vector(io, camera->target);
lib3ds_io_write_float(io, camera->roll);
if (fabs(camera->fov) < LIB3DS_EPSILON) {
lib3ds_io_write_float(io, 2400.0f / 45.0f);
} else {
lib3ds_io_write_float(io, 2400.0f / camera->fov);
}
if (camera->see_cone) {
Lib3dsChunk c;
c.chunk = CHK_CAM_SEE_CONE;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
{
Lib3dsChunk c;
c.chunk = CHK_CAM_RANGES;
c.size = 14;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, camera->near_range);
lib3ds_io_write_float(io, camera->far_range);
}
lib3ds_chunk_write_end(&c, io);
}

View File

@@ -0,0 +1,146 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
/*#define LIB3DS_CHUNK_DEBUG*/
/*#define LIB3DS_CHUNK_WARNING*/
/*!
* Reads a 3d-Studio chunk header from a little endian file stream.
*
* \param c The chunk to store the data.
* \param io The file stream.
*
* \return True on success, False otherwise.
*/
void
lib3ds_chunk_read(Lib3dsChunk *c, Lib3dsIo *io) {
assert(c);
assert(io);
c->cur = lib3ds_io_tell(io);
c->chunk = lib3ds_io_read_word(io);
c->size = lib3ds_io_read_dword(io);
c->end = c->cur + c->size;
c->cur += 6;
if (c->size < 6) {
lib3ds_io_log(io, LIB3DS_LOG_ERROR, "Invalid chunk header.");
}
}
void
lib3ds_chunk_read_start(Lib3dsChunk *c, uint16_t chunk, Lib3dsIo *io) {
assert(c);
assert(io);
lib3ds_chunk_read(c, io);
if ((chunk != 0) && (c->chunk != chunk)) {
lib3ds_io_log(io, LIB3DS_LOG_ERROR, "Unexpected chunk found.");
}
((Lib3dsIoImpl*)io->impl)->log_indent++;
}
void
lib3ds_chunk_read_tell(Lib3dsChunk *c, Lib3dsIo *io) {
c->cur = lib3ds_io_tell(io);
}
uint16_t
lib3ds_chunk_read_next(Lib3dsChunk *c, Lib3dsIo *io) {
Lib3dsChunk d;
if (c->cur >= c->end) {
assert(c->cur == c->end);
return 0;
}
lib3ds_io_seek(io, (long)c->cur, LIB3DS_SEEK_SET);
d.chunk = lib3ds_io_read_word(io);
d.size = lib3ds_io_read_dword(io);
c->cur += d.size;
if (io->log_func) {
lib3ds_io_log(io, LIB3DS_LOG_INFO, "%s (0x%X) size=%lu", lib3ds_chunk_name(d.chunk), d.chunk, d.size);
}
return d.chunk;
}
void
lib3ds_chunk_read_reset(Lib3dsChunk *c, Lib3dsIo *io) {
lib3ds_io_seek(io, -6, LIB3DS_SEEK_CUR);
}
void
lib3ds_chunk_read_end(Lib3dsChunk *c, Lib3dsIo *io) {
((Lib3dsIoImpl*)io->impl)->log_indent--;
lib3ds_io_seek(io, c->end, LIB3DS_SEEK_SET);
}
/*!
* Writes a 3d-Studio chunk header into a little endian file stream.
*
* \param c The chunk to be written.
* \param io The file stream.
*
* \return True on success, False otherwise.
*/
void
lib3ds_chunk_write(Lib3dsChunk *c, Lib3dsIo *io) {
assert(c);
lib3ds_io_write_word(io, c->chunk);
lib3ds_io_write_dword(io, c->size);
}
void
lib3ds_chunk_write_start(Lib3dsChunk *c, Lib3dsIo *io) {
assert(c);
c->size = 0;
c->cur = lib3ds_io_tell(io);
lib3ds_io_write_word(io, c->chunk);
lib3ds_io_write_dword(io, c->size);
}
void
lib3ds_chunk_write_end(Lib3dsChunk *c, Lib3dsIo *io) {
assert(c);
c->size = lib3ds_io_tell(io) - c->cur;
lib3ds_io_seek(io, c->cur + 2, LIB3DS_SEEK_SET);
lib3ds_io_write_dword(io, c->size);
c->cur += c->size;
lib3ds_io_seek(io, c->cur, LIB3DS_SEEK_SET);
}
void
lib3ds_chunk_unknown(uint16_t chunk, Lib3dsIo *io) {
if (io->log_func) {
lib3ds_io_log(io, LIB3DS_LOG_WARN, "Unknown Chunk: %s (0x%X)", lib3ds_chunk_name(chunk), chunk);
}
}

View File

@@ -0,0 +1,259 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
typedef struct Lib3dsChunkTable {
uint32_t chunk;
const char* name;
} Lib3dsChunkTable;
static Lib3dsChunkTable lib3ds_chunk_table[] = {
{CHK_NULL_CHUNK, "NULL_CHUNK"},
{CHK_M3DMAGIC, "M3DMAGIC"},
{CHK_SMAGIC, "SMAGIC"},
{CHK_LMAGIC, "LMAGIC"},
{CHK_MLIBMAGIC, "MLIBMAGIC"},
{CHK_MATMAGIC, "MATMAGIC"},
{CHK_CMAGIC, "CMAGIC"},
{CHK_M3D_VERSION, "M3D_VERSION"},
{CHK_M3D_KFVERSION, "M3D_KFVERSION"},
{CHK_COLOR_F, "COLOR_F"},
{CHK_COLOR_24, "COLOR_24"},
{CHK_LIN_COLOR_24, "LIN_COLOR_24"},
{CHK_LIN_COLOR_F, "LIN_COLOR_F"},
{CHK_INT_PERCENTAGE, "INT_PERCENTAGE"},
{CHK_FLOAT_PERCENTAGE, "FLOAT_PERCENTAGE"},
{CHK_MDATA, "MDATA"},
{CHK_MESH_VERSION, "MESH_VERSION"},
{CHK_MASTER_SCALE, "MASTER_SCALE"},
{CHK_LO_SHADOW_BIAS, "LO_SHADOW_BIAS"},
{CHK_HI_SHADOW_BIAS, "HI_SHADOW_BIAS"},
{CHK_SHADOW_MAP_SIZE, "SHADOW_MAP_SIZE"},
{CHK_SHADOW_SAMPLES, "SHADOW_SAMPLES"},
{CHK_SHADOW_RANGE, "SHADOW_RANGE"},
{CHK_SHADOW_FILTER, "SHADOW_FILTER"},
{CHK_RAY_BIAS, "RAY_BIAS"},
{CHK_O_CONSTS, "O_CONSTS"},
{CHK_AMBIENT_LIGHT, "AMBIENT_LIGHT"},
{CHK_BIT_MAP, "BIT_MAP"},
{CHK_SOLID_BGND, "SOLID_BGND"},
{CHK_V_GRADIENT, "V_GRADIENT"},
{CHK_USE_BIT_MAP, "USE_BIT_MAP"},
{CHK_USE_SOLID_BGND, "USE_SOLID_BGND"},
{CHK_USE_V_GRADIENT, "USE_V_GRADIENT"},
{CHK_FOG, "FOG"},
{CHK_FOG_BGND, "FOG_BGND"},
{CHK_LAYER_FOG, "LAYER_FOG"},
{CHK_DISTANCE_CUE, "DISTANCE_CUE"},
{CHK_DCUE_BGND, "DCUE_BGND"},
{CHK_USE_FOG, "USE_FOG"},
{CHK_USE_LAYER_FOG, "USE_LAYER_FOG"},
{CHK_USE_DISTANCE_CUE, "USE_DISTANCE_CUE"},
{CHK_MAT_ENTRY, "MAT_ENTRY"},
{CHK_MAT_NAME, "MAT_NAME"},
{CHK_MAT_AMBIENT, "MAT_AMBIENT"},
{CHK_MAT_DIFFUSE, "MAT_DIFFUSE"},
{CHK_MAT_SPECULAR, "MAT_SPECULAR"},
{CHK_MAT_SHININESS, "MAT_SHININESS"},
{CHK_MAT_SHIN2PCT, "MAT_SHIN2PCT"},
{CHK_MAT_TRANSPARENCY, "MAT_TRANSPARENCY"},
{CHK_MAT_XPFALL, "MAT_XPFALL"},
{CHK_MAT_USE_XPFALL, "MAT_USE_XPFALL"},
{CHK_MAT_REFBLUR, "MAT_REFBLUR"},
{CHK_MAT_SHADING, "MAT_SHADING"},
{CHK_MAT_USE_REFBLUR, "MAT_USE_REFBLUR"},
{CHK_MAT_SELF_ILLUM, "MAT_SELF_ILLUM"},
{CHK_MAT_TWO_SIDE, "MAT_TWO_SIDE"},
{CHK_MAT_DECAL, "MAT_DECAL"},
{CHK_MAT_ADDITIVE, "MAT_ADDITIVE"},
{CHK_MAT_SELF_ILPCT, "MAT_SELF_ILPCT"},
{CHK_MAT_WIRE, "MAT_WIRE"},
{CHK_MAT_FACEMAP, "MAT_FACEMAP"},
{CHK_MAT_PHONGSOFT, "MAT_PHONGSOFT"},
{CHK_MAT_WIREABS, "MAT_WIREABS"},
{CHK_MAT_WIRE_SIZE, "MAT_WIRE_SIZE"},
{CHK_MAT_TEXMAP, "MAT_TEXMAP"},
{CHK_MAT_SXP_TEXT_DATA, "MAT_SXP_TEXT_DATA"},
{CHK_MAT_TEXMASK, "MAT_TEXMASK"},
{CHK_MAT_SXP_TEXTMASK_DATA, "MAT_SXP_TEXTMASK_DATA"},
{CHK_MAT_TEX2MAP, "MAT_TEX2MAP"},
{CHK_MAT_SXP_TEXT2_DATA, "MAT_SXP_TEXT2_DATA"},
{CHK_MAT_TEX2MASK, "MAT_TEX2MASK"},
{CHK_MAT_SXP_TEXT2MASK_DATA, "MAT_SXP_TEXT2MASK_DATA"},
{CHK_MAT_OPACMAP, "MAT_OPACMAP"},
{CHK_MAT_SXP_OPAC_DATA, "MAT_SXP_OPAC_DATA"},
{CHK_MAT_OPACMASK, "MAT_OPACMASK"},
{CHK_MAT_SXP_OPACMASK_DATA, "MAT_SXP_OPACMASK_DATA"},
{CHK_MAT_BUMPMAP, "MAT_BUMPMAP"},
{CHK_MAT_SXP_BUMP_DATA, "MAT_SXP_BUMP_DATA"},
{CHK_MAT_BUMPMASK, "MAT_BUMPMASK"},
{CHK_MAT_SXP_BUMPMASK_DATA, "MAT_SXP_BUMPMASK_DATA"},
{CHK_MAT_SPECMAP, "MAT_SPECMAP"},
{CHK_MAT_SXP_SPEC_DATA, "MAT_SXP_SPEC_DATA"},
{CHK_MAT_SPECMASK, "MAT_SPECMASK"},
{CHK_MAT_SXP_SPECMASK_DATA, "MAT_SXP_SPECMASK_DATA"},
{CHK_MAT_SHINMAP, "MAT_SHINMAP"},
{CHK_MAT_SXP_SHIN_DATA, "MAT_SXP_SHIN_DATA"},
{CHK_MAT_SHINMASK, "MAT_SHINMASK"},
{CHK_MAT_SXP_SHINMASK_DATA, "MAT_SXP_SHINMASK_DATA"},
{CHK_MAT_SELFIMAP, "MAT_SELFIMAP"},
{CHK_MAT_SXP_SELFI_DATA, "MAT_SXP_SELFI_DATA"},
{CHK_MAT_SELFIMASK, "MAT_SELFIMASK"},
{CHK_MAT_SXP_SELFIMASK_DATA, "MAT_SXP_SELFIMASK_DATA"},
{CHK_MAT_REFLMAP, "MAT_REFLMAP"},
{CHK_MAT_REFLMASK, "MAT_REFLMASK"},
{CHK_MAT_SXP_REFLMASK_DATA, "MAT_SXP_REFLMASK_DATA"},
{CHK_MAT_ACUBIC, "MAT_ACUBIC"},
{CHK_MAT_MAPNAME, "MAT_MAPNAME"},
{CHK_MAT_MAP_TILING, "MAT_MAP_TILING"},
{CHK_MAT_MAP_TEXBLUR, "MAT_MAP_TEXBLUR"},
{CHK_MAT_MAP_USCALE, "MAT_MAP_USCALE"},
{CHK_MAT_MAP_VSCALE, "MAT_MAP_VSCALE"},
{CHK_MAT_MAP_UOFFSET, "MAT_MAP_UOFFSET"},
{CHK_MAT_MAP_VOFFSET, "MAT_MAP_VOFFSET"},
{CHK_MAT_MAP_ANG, "MAT_MAP_ANG"},
{CHK_MAT_MAP_COL1, "MAT_MAP_COL1"},
{CHK_MAT_MAP_COL2, "MAT_MAP_COL2"},
{CHK_MAT_MAP_RCOL, "MAT_MAP_RCOL"},
{CHK_MAT_MAP_GCOL, "MAT_MAP_GCOL"},
{CHK_MAT_MAP_BCOL, "MAT_MAP_BCOL"},
{CHK_NAMED_OBJECT, "NAMED_OBJECT"},
{CHK_N_DIRECT_LIGHT, "N_DIRECT_LIGHT"},
{CHK_DL_OFF, "DL_OFF"},
{CHK_DL_OUTER_RANGE, "DL_OUTER_RANGE"},
{CHK_DL_INNER_RANGE, "DL_INNER_RANGE"},
{CHK_DL_MULTIPLIER, "DL_MULTIPLIER"},
{CHK_DL_EXCLUDE, "DL_EXCLUDE"},
{CHK_DL_ATTENUATE, "DL_ATTENUATE"},
{CHK_DL_SPOTLIGHT, "DL_SPOTLIGHT"},
{CHK_DL_SPOT_ROLL, "DL_SPOT_ROLL"},
{CHK_DL_SHADOWED, "DL_SHADOWED"},
{CHK_DL_LOCAL_SHADOW2, "DL_LOCAL_SHADOW2"},
{CHK_DL_SEE_CONE, "DL_SEE_CONE"},
{CHK_DL_SPOT_RECTANGULAR, "DL_SPOT_RECTANGULAR"},
{CHK_DL_SPOT_ASPECT, "DL_SPOT_ASPECT"},
{CHK_DL_SPOT_PROJECTOR, "DL_SPOT_PROJECTOR"},
{CHK_DL_SPOT_OVERSHOOT, "DL_SPOT_OVERSHOOT"},
{CHK_DL_RAY_BIAS, "DL_RAY_BIAS"},
{CHK_DL_RAYSHAD, "DL_RAYSHAD"},
{CHK_N_CAMERA, "N_CAMERA"},
{CHK_CAM_SEE_CONE, "CAM_SEE_CONE"},
{CHK_CAM_RANGES, "CAM_RANGES"},
{CHK_OBJ_HIDDEN, "OBJ_HIDDEN"},
{CHK_OBJ_VIS_LOFTER, "OBJ_VIS_LOFTER"},
{CHK_OBJ_DOESNT_CAST, "OBJ_DOESNT_CAST"},
{CHK_OBJ_DONT_RCVSHADOW, "OBJ_DONT_RCVSHADOW"},
{CHK_OBJ_MATTE, "OBJ_MATTE"},
{CHK_OBJ_FAST, "OBJ_FAST"},
{CHK_OBJ_PROCEDURAL, "OBJ_PROCEDURAL"},
{CHK_OBJ_FROZEN, "OBJ_FROZEN"},
{CHK_N_TRI_OBJECT, "N_TRI_OBJECT"},
{CHK_POINT_ARRAY, "POINT_ARRAY"},
{CHK_POINT_FLAG_ARRAY, "POINT_FLAG_ARRAY"},
{CHK_FACE_ARRAY, "FACE_ARRAY"},
{CHK_MSH_MAT_GROUP, "MSH_MAT_GROUP"},
{CHK_SMOOTH_GROUP, "SMOOTH_GROUP"},
{CHK_MSH_BOXMAP, "MSH_BOXMAP"},
{CHK_TEX_VERTS, "TEX_VERTS"},
{CHK_MESH_MATRIX, "MESH_MATRIX"},
{CHK_MESH_COLOR, "MESH_COLOR"},
{CHK_MESH_TEXTURE_INFO, "MESH_TEXTURE_INFO"},
{CHK_KFDATA, "KFDATA"},
{CHK_KFHDR, "KFHDR"},
{CHK_KFSEG, "KFSEG"},
{CHK_KFCURTIME, "KFCURTIME"},
{CHK_AMBIENT_NODE_TAG, "AMBIENT_NODE_TAG"},
{CHK_OBJECT_NODE_TAG, "OBJECT_NODE_TAG"},
{CHK_CAMERA_NODE_TAG, "CAMERA_NODE_TAG"},
{CHK_TARGET_NODE_TAG, "TARGET_NODE_TAG"},
{CHK_LIGHT_NODE_TAG, "LIGHT_NODE_TAG"},
{CHK_L_TARGET_NODE_TAG, "L_TARGET_NODE_TAG"},
{CHK_SPOTLIGHT_NODE_TAG, "SPOTLIGHT_NODE_TAG"},
{CHK_NODE_ID, "NODE_ID"},
{CHK_NODE_HDR, "NODE_HDR"},
{CHK_PIVOT, "PIVOT"},
{CHK_INSTANCE_NAME, "INSTANCE_NAME"},
{CHK_MORPH_SMOOTH, "MORPH_SMOOTH"},
{CHK_BOUNDBOX, "BOUNDBOX"},
{CHK_POS_TRACK_TAG, "POS_TRACK_TAG"},
{CHK_COL_TRACK_TAG, "COL_TRACK_TAG"},
{CHK_ROT_TRACK_TAG, "ROT_TRACK_TAG"},
{CHK_SCL_TRACK_TAG, "SCL_TRACK_TAG"},
{CHK_MORPH_TRACK_TAG, "MORPH_TRACK_TAG"},
{CHK_FOV_TRACK_TAG, "FOV_TRACK_TAG"},
{CHK_ROLL_TRACK_TAG, "ROLL_TRACK_TAG"},
{CHK_HOT_TRACK_TAG, "HOT_TRACK_TAG"},
{CHK_FALL_TRACK_TAG, "FALL_TRACK_TAG"},
{CHK_HIDE_TRACK_TAG, "HIDE_TRACK_TAG"},
{CHK_POLY_2D, "POLY_2D"},
{CHK_SHAPE_OK, "SHAPE_OK"},
{CHK_SHAPE_NOT_OK, "SHAPE_NOT_OK"},
{CHK_SHAPE_HOOK, "SHAPE_HOOK"},
{CHK_PATH_3D, "PATH_3D"},
{CHK_PATH_MATRIX, "PATH_MATRIX"},
{CHK_SHAPE_2D, "SHAPE_2D"},
{CHK_M_SCALE, "M_SCALE"},
{CHK_M_TWIST, "M_TWIST"},
{CHK_M_TEETER, "M_TEETER"},
{CHK_M_FIT, "M_FIT"},
{CHK_M_BEVEL, "M_BEVEL"},
{CHK_XZ_CURVE, "XZ_CURVE"},
{CHK_YZ_CURVE, "YZ_CURVE"},
{CHK_INTERPCT, "INTERPCT"},
{CHK_DEFORM_LIMIT, "DEFORM_LIMIT"},
{CHK_USE_CONTOUR, "USE_CONTOUR"},
{CHK_USE_TWEEN, "USE_TWEEN"},
{CHK_USE_SCALE, "USE_SCALE"},
{CHK_USE_TWIST, "USE_TWIST"},
{CHK_USE_TEETER, "USE_TEETER"},
{CHK_USE_FIT, "USE_FIT"},
{CHK_USE_BEVEL, "USE_BEVEL"},
{CHK_DEFAULT_VIEW, "DEFAULT_VIEW"},
{CHK_VIEW_TOP, "VIEW_TOP"},
{CHK_VIEW_BOTTOM, "VIEW_BOTTOM"},
{CHK_VIEW_LEFT, "VIEW_LEFT"},
{CHK_VIEW_RIGHT, "VIEW_RIGHT"},
{CHK_VIEW_FRONT, "VIEW_FRONT"},
{CHK_VIEW_BACK, "VIEW_BACK"},
{CHK_VIEW_USER, "VIEW_USER"},
{CHK_VIEW_CAMERA, "VIEW_CAMERA"},
{CHK_VIEW_WINDOW, "VIEW_WINDOW"},
{CHK_VIEWPORT_LAYOUT_OLD, "VIEWPORT_LAYOUT_OLD"},
{CHK_VIEWPORT_DATA_OLD, "VIEWPORT_DATA_OLD"},
{CHK_VIEWPORT_LAYOUT, "VIEWPORT_LAYOUT"},
{CHK_VIEWPORT_DATA, "VIEWPORT_DATA"},
{CHK_VIEWPORT_DATA_3, "VIEWPORT_DATA_3"},
{CHK_VIEWPORT_SIZE, "VIEWPORT_SIZE"},
{CHK_NETWORK_VIEW, "NETWORK_VIEW"},
{0, 0}
};
const char*
lib3ds_chunk_name(uint16_t chunk) {
Lib3dsChunkTable *p;
for (p = lib3ds_chunk_table; p->name != 0; ++p) {
if (p->chunk == chunk) {
return(p->name);
}
}
return("***UNKNOWN***");
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,388 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_IMPL_H
#define INCLUDED_LIB3DS_IMPL_H
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds.h"
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
#include <math.h>
#include <float.h>
#include <assert.h>
#include <setjmp.h>
#include <stdarg.h>
#ifdef _MSC_VER
#pragma warning ( disable : 4996 )
#endif
#ifndef _MSC_VER
#include <stdint.h>
#else
typedef unsigned __int8 uint8_t;
typedef unsigned __int16 uint16_t;
typedef unsigned __int32 uint32_t;
typedef signed __int8 int8_t;
typedef signed __int16 int16_t;
typedef signed __int32 int32_t;
#endif
#ifndef TRUE
#define TRUE 1
#endif
#ifndef FALSE
#define FALSE 0
#endif
#define LIB3DS_EPSILON (1e-5)
#define LIB3DS_PI 3.14159265358979323846
#define LIB3DS_TWOPI (2.0*LIB3DS_PI)
#define LIB3DS_HALFPI (LIB3DS_PI/2.0)
#define LIB3DS_RAD_TO_DEG(x) ((180.0/LIB3DS_PI)*(x))
#define LIB3DS_DEG_TO_RAD(x) ((LIB3DS_PI/180.0)*(x))
#ifdef __cplusplus
extern "C" {
#endif
typedef enum Lib3dsChunks {
CHK_NULL_CHUNK =0x0000,
CHK_M3DMAGIC =0x4D4D, /*3DS file*/
CHK_SMAGIC =0x2D2D,
CHK_LMAGIC =0x2D3D,
CHK_MLIBMAGIC =0x3DAA, /*MLI file*/
CHK_MATMAGIC =0x3DFF,
CHK_CMAGIC =0xC23D, /*PRJ file*/
CHK_M3D_VERSION =0x0002,
CHK_M3D_KFVERSION =0x0005,
CHK_COLOR_F =0x0010,
CHK_COLOR_24 =0x0011,
CHK_LIN_COLOR_24 =0x0012,
CHK_LIN_COLOR_F =0x0013,
CHK_INT_PERCENTAGE =0x0030,
CHK_FLOAT_PERCENTAGE =0x0031,
CHK_MDATA =0x3D3D,
CHK_MESH_VERSION =0x3D3E,
CHK_MASTER_SCALE =0x0100,
CHK_LO_SHADOW_BIAS =0x1400,
CHK_HI_SHADOW_BIAS =0x1410,
CHK_SHADOW_MAP_SIZE =0x1420,
CHK_SHADOW_SAMPLES =0x1430,
CHK_SHADOW_RANGE =0x1440,
CHK_SHADOW_FILTER =0x1450,
CHK_RAY_BIAS =0x1460,
CHK_O_CONSTS =0x1500,
CHK_AMBIENT_LIGHT =0x2100,
CHK_BIT_MAP =0x1100,
CHK_SOLID_BGND =0x1200,
CHK_V_GRADIENT =0x1300,
CHK_USE_BIT_MAP =0x1101,
CHK_USE_SOLID_BGND =0x1201,
CHK_USE_V_GRADIENT =0x1301,
CHK_FOG =0x2200,
CHK_FOG_BGND =0x2210,
CHK_LAYER_FOG =0x2302,
CHK_DISTANCE_CUE =0x2300,
CHK_DCUE_BGND =0x2310,
CHK_USE_FOG =0x2201,
CHK_USE_LAYER_FOG =0x2303,
CHK_USE_DISTANCE_CUE =0x2301,
CHK_MAT_ENTRY =0xAFFF,
CHK_MAT_NAME =0xA000,
CHK_MAT_AMBIENT =0xA010,
CHK_MAT_DIFFUSE =0xA020,
CHK_MAT_SPECULAR =0xA030,
CHK_MAT_SHININESS =0xA040,
CHK_MAT_SHIN2PCT =0xA041,
CHK_MAT_TRANSPARENCY =0xA050,
CHK_MAT_XPFALL =0xA052,
CHK_MAT_USE_XPFALL =0xA240,
CHK_MAT_REFBLUR =0xA053,
CHK_MAT_SHADING =0xA100,
CHK_MAT_USE_REFBLUR =0xA250,
CHK_MAT_SELF_ILLUM =0xA080,
CHK_MAT_TWO_SIDE =0xA081,
CHK_MAT_DECAL =0xA082,
CHK_MAT_ADDITIVE =0xA083,
CHK_MAT_SELF_ILPCT =0xA084,
CHK_MAT_WIRE =0xA085,
CHK_MAT_FACEMAP =0xA088,
CHK_MAT_PHONGSOFT =0xA08C,
CHK_MAT_WIREABS =0xA08E,
CHK_MAT_WIRE_SIZE =0xA087,
CHK_MAT_TEXMAP =0xA200,
CHK_MAT_SXP_TEXT_DATA =0xA320,
CHK_MAT_TEXMASK =0xA33E,
CHK_MAT_SXP_TEXTMASK_DATA =0xA32A,
CHK_MAT_TEX2MAP =0xA33A,
CHK_MAT_SXP_TEXT2_DATA =0xA321,
CHK_MAT_TEX2MASK =0xA340,
CHK_MAT_SXP_TEXT2MASK_DATA =0xA32C,
CHK_MAT_OPACMAP =0xA210,
CHK_MAT_SXP_OPAC_DATA =0xA322,
CHK_MAT_OPACMASK =0xA342,
CHK_MAT_SXP_OPACMASK_DATA =0xA32E,
CHK_MAT_BUMPMAP =0xA230,
CHK_MAT_SXP_BUMP_DATA =0xA324,
CHK_MAT_BUMPMASK =0xA344,
CHK_MAT_SXP_BUMPMASK_DATA =0xA330,
CHK_MAT_SPECMAP =0xA204,
CHK_MAT_SXP_SPEC_DATA =0xA325,
CHK_MAT_SPECMASK =0xA348,
CHK_MAT_SXP_SPECMASK_DATA =0xA332,
CHK_MAT_SHINMAP =0xA33C,
CHK_MAT_SXP_SHIN_DATA =0xA326,
CHK_MAT_SHINMASK =0xA346,
CHK_MAT_SXP_SHINMASK_DATA =0xA334,
CHK_MAT_SELFIMAP =0xA33D,
CHK_MAT_SXP_SELFI_DATA =0xA328,
CHK_MAT_SELFIMASK =0xA34A,
CHK_MAT_SXP_SELFIMASK_DATA =0xA336,
CHK_MAT_REFLMAP =0xA220,
CHK_MAT_REFLMASK =0xA34C,
CHK_MAT_SXP_REFLMASK_DATA =0xA338,
CHK_MAT_ACUBIC =0xA310,
CHK_MAT_MAPNAME =0xA300,
CHK_MAT_MAP_TILING =0xA351,
CHK_MAT_MAP_TEXBLUR =0xA353,
CHK_MAT_MAP_USCALE =0xA354,
CHK_MAT_MAP_VSCALE =0xA356,
CHK_MAT_MAP_UOFFSET =0xA358,
CHK_MAT_MAP_VOFFSET =0xA35A,
CHK_MAT_MAP_ANG =0xA35C,
CHK_MAT_MAP_COL1 =0xA360,
CHK_MAT_MAP_COL2 =0xA362,
CHK_MAT_MAP_RCOL =0xA364,
CHK_MAT_MAP_GCOL =0xA366,
CHK_MAT_MAP_BCOL =0xA368,
CHK_NAMED_OBJECT =0x4000,
CHK_N_DIRECT_LIGHT =0x4600,
CHK_DL_OFF =0x4620,
CHK_DL_OUTER_RANGE =0x465A,
CHK_DL_INNER_RANGE =0x4659,
CHK_DL_MULTIPLIER =0x465B,
CHK_DL_EXCLUDE =0x4654,
CHK_DL_ATTENUATE =0x4625,
CHK_DL_SPOTLIGHT =0x4610,
CHK_DL_SPOT_ROLL =0x4656,
CHK_DL_SHADOWED =0x4630,
CHK_DL_LOCAL_SHADOW2 =0x4641,
CHK_DL_SEE_CONE =0x4650,
CHK_DL_SPOT_RECTANGULAR =0x4651,
CHK_DL_SPOT_ASPECT =0x4657,
CHK_DL_SPOT_PROJECTOR =0x4653,
CHK_DL_SPOT_OVERSHOOT =0x4652,
CHK_DL_RAY_BIAS =0x4658,
CHK_DL_RAYSHAD =0x4627,
CHK_N_CAMERA =0x4700,
CHK_CAM_SEE_CONE =0x4710,
CHK_CAM_RANGES =0x4720,
CHK_OBJ_HIDDEN =0x4010,
CHK_OBJ_VIS_LOFTER =0x4011,
CHK_OBJ_DOESNT_CAST =0x4012,
CHK_OBJ_DONT_RCVSHADOW =0x4017,
CHK_OBJ_MATTE =0x4013,
CHK_OBJ_FAST =0x4014,
CHK_OBJ_PROCEDURAL =0x4015,
CHK_OBJ_FROZEN =0x4016,
CHK_N_TRI_OBJECT =0x4100,
CHK_POINT_ARRAY =0x4110,
CHK_POINT_FLAG_ARRAY =0x4111,
CHK_FACE_ARRAY =0x4120,
CHK_MSH_MAT_GROUP =0x4130,
CHK_SMOOTH_GROUP =0x4150,
CHK_MSH_BOXMAP =0x4190,
CHK_TEX_VERTS =0x4140,
CHK_MESH_MATRIX =0x4160,
CHK_MESH_COLOR =0x4165,
CHK_MESH_TEXTURE_INFO =0x4170,
CHK_KFDATA =0xB000,
CHK_KFHDR =0xB00A,
CHK_KFSEG =0xB008,
CHK_KFCURTIME =0xB009,
CHK_AMBIENT_NODE_TAG =0xB001,
CHK_OBJECT_NODE_TAG =0xB002,
CHK_CAMERA_NODE_TAG =0xB003,
CHK_TARGET_NODE_TAG =0xB004,
CHK_LIGHT_NODE_TAG =0xB005,
CHK_L_TARGET_NODE_TAG =0xB006,
CHK_SPOTLIGHT_NODE_TAG =0xB007,
CHK_NODE_ID =0xB030,
CHK_NODE_HDR =0xB010,
CHK_PIVOT =0xB013,
CHK_INSTANCE_NAME =0xB011,
CHK_MORPH_SMOOTH =0xB015,
CHK_BOUNDBOX =0xB014,
CHK_POS_TRACK_TAG =0xB020,
CHK_COL_TRACK_TAG =0xB025,
CHK_ROT_TRACK_TAG =0xB021,
CHK_SCL_TRACK_TAG =0xB022,
CHK_MORPH_TRACK_TAG =0xB026,
CHK_FOV_TRACK_TAG =0xB023,
CHK_ROLL_TRACK_TAG =0xB024,
CHK_HOT_TRACK_TAG =0xB027,
CHK_FALL_TRACK_TAG =0xB028,
CHK_HIDE_TRACK_TAG =0xB029,
CHK_POLY_2D = 0x5000,
CHK_SHAPE_OK = 0x5010,
CHK_SHAPE_NOT_OK = 0x5011,
CHK_SHAPE_HOOK = 0x5020,
CHK_PATH_3D = 0x6000,
CHK_PATH_MATRIX = 0x6005,
CHK_SHAPE_2D = 0x6010,
CHK_M_SCALE = 0x6020,
CHK_M_TWIST = 0x6030,
CHK_M_TEETER = 0x6040,
CHK_M_FIT = 0x6050,
CHK_M_BEVEL = 0x6060,
CHK_XZ_CURVE = 0x6070,
CHK_YZ_CURVE = 0x6080,
CHK_INTERPCT = 0x6090,
CHK_DEFORM_LIMIT = 0x60A0,
CHK_USE_CONTOUR = 0x6100,
CHK_USE_TWEEN = 0x6110,
CHK_USE_SCALE = 0x6120,
CHK_USE_TWIST = 0x6130,
CHK_USE_TEETER = 0x6140,
CHK_USE_FIT = 0x6150,
CHK_USE_BEVEL = 0x6160,
CHK_DEFAULT_VIEW = 0x3000,
CHK_VIEW_TOP = 0x3010,
CHK_VIEW_BOTTOM = 0x3020,
CHK_VIEW_LEFT = 0x3030,
CHK_VIEW_RIGHT = 0x3040,
CHK_VIEW_FRONT = 0x3050,
CHK_VIEW_BACK = 0x3060,
CHK_VIEW_USER = 0x3070,
CHK_VIEW_CAMERA = 0x3080,
CHK_VIEW_WINDOW = 0x3090,
CHK_VIEWPORT_LAYOUT_OLD = 0x7000,
CHK_VIEWPORT_DATA_OLD = 0x7010,
CHK_VIEWPORT_LAYOUT = 0x7001,
CHK_VIEWPORT_DATA = 0x7011,
CHK_VIEWPORT_DATA_3 = 0x7012,
CHK_VIEWPORT_SIZE = 0x7020,
CHK_NETWORK_VIEW = 0x7030
} Lib3dsChunks;
typedef struct Lib3dsChunk {
uint16_t chunk;
uint32_t size;
uint32_t end;
uint32_t cur;
} Lib3dsChunk;
extern void lib3ds_chunk_read(Lib3dsChunk *c, Lib3dsIo *io);
extern void lib3ds_chunk_read_start(Lib3dsChunk *c, uint16_t chunk, Lib3dsIo *io);
extern void lib3ds_chunk_read_tell(Lib3dsChunk *c, Lib3dsIo *io);
extern uint16_t lib3ds_chunk_read_next(Lib3dsChunk *c, Lib3dsIo *io);
extern void lib3ds_chunk_read_reset(Lib3dsChunk *c, Lib3dsIo *io);
extern void lib3ds_chunk_read_end(Lib3dsChunk *c, Lib3dsIo *io);
extern void lib3ds_chunk_write(Lib3dsChunk *c, Lib3dsIo *io);
extern void lib3ds_chunk_write_start(Lib3dsChunk *c, Lib3dsIo *io);
extern void lib3ds_chunk_write_end(Lib3dsChunk *c, Lib3dsIo *io);
extern const char* lib3ds_chunk_name(uint16_t chunk);
extern void lib3ds_chunk_unknown(uint16_t chunk, Lib3dsIo *io);
typedef struct Lib3dsIoImpl {
jmp_buf jmpbuf;
int log_indent;
void *tmp_mem;
Lib3dsNode *tmp_node;
} Lib3dsIoImpl;
extern void lib3ds_io_setup(Lib3dsIo *io);
extern void lib3ds_io_cleanup(Lib3dsIo *io);
extern long lib3ds_io_seek(Lib3dsIo *io, long offset, Lib3dsIoSeek origin);
extern long lib3ds_io_tell(Lib3dsIo *io);
extern size_t lib3ds_io_read(Lib3dsIo *io, void *buffer, size_t size);
extern size_t lib3ds_io_write(Lib3dsIo *io, const void *buffer, size_t size);
extern void lib3ds_io_log(Lib3dsIo *io, Lib3dsLogLevel level, const char *format, ...);
extern void lib3ds_io_log_indent(Lib3dsIo *io, int indent);
extern void lib3ds_io_read_error(Lib3dsIo *io);
extern void lib3ds_io_write_error(Lib3dsIo *io);
extern uint8_t lib3ds_io_read_byte(Lib3dsIo *io);
extern uint16_t lib3ds_io_read_word(Lib3dsIo *io);
extern uint32_t lib3ds_io_read_dword(Lib3dsIo *io);
extern int8_t lib3ds_io_read_intb(Lib3dsIo *io);
extern int16_t lib3ds_io_read_intw(Lib3dsIo *io);
extern int32_t lib3ds_io_read_intd(Lib3dsIo *io);
extern float lib3ds_io_read_float(Lib3dsIo *io);
extern void lib3ds_io_read_vector(Lib3dsIo *io, float v[3]);
extern void lib3ds_io_read_rgb(Lib3dsIo *io, float rgb[3]);
extern void lib3ds_io_read_string(Lib3dsIo *io, char *s, int buflen);
extern void lib3ds_io_write_byte(Lib3dsIo *io, uint8_t b);
extern void lib3ds_io_write_word(Lib3dsIo *io, uint16_t w);
extern void lib3ds_io_write_dword(Lib3dsIo *io, uint32_t d);
extern void lib3ds_io_write_intb(Lib3dsIo *io, int8_t b);
extern void lib3ds_io_write_intw(Lib3dsIo *io, int16_t w);
extern void lib3ds_io_write_intd(Lib3dsIo *io, int32_t d);
extern void lib3ds_io_write_float(Lib3dsIo *io, float l);
extern void lib3ds_io_write_vector(Lib3dsIo *io, float v[3]);
extern void lib3ds_io_write_rgb(Lib3dsIo *io, float rgb[3]);
extern void lib3ds_io_write_string(Lib3dsIo *io, const char *s);
extern void lib3ds_atmosphere_read(Lib3dsAtmosphere *atmosphere, Lib3dsIo *io);
extern void lib3ds_atmosphere_write(Lib3dsAtmosphere *atmosphere, Lib3dsIo *io);
extern void lib3ds_background_read(Lib3dsBackground *background, Lib3dsIo *io);
extern void lib3ds_background_write(Lib3dsBackground *background, Lib3dsIo *io);
extern void lib3ds_shadow_read(Lib3dsShadow *shadow, Lib3dsIo *io);
extern void lib3ds_shadow_write(Lib3dsShadow *shadow, Lib3dsIo *io);
extern void lib3ds_viewport_read(Lib3dsViewport *viewport, Lib3dsIo *io);
extern void lib3ds_viewport_write(Lib3dsViewport *viewport, Lib3dsIo *io);
extern void lib3ds_material_read(Lib3dsMaterial *material, Lib3dsIo *io);
extern void lib3ds_material_write(Lib3dsMaterial *material, Lib3dsIo *io);
extern void lib3ds_camera_read(Lib3dsCamera *camera, Lib3dsIo *io);
extern void lib3ds_camera_write(Lib3dsCamera *camera, Lib3dsIo *io);
extern void lib3ds_light_read(Lib3dsLight *light, Lib3dsIo *io);
extern void lib3ds_light_write(Lib3dsLight *light, Lib3dsIo *io);
extern void lib3ds_mesh_read(Lib3dsFile *file, Lib3dsMesh *mesh, Lib3dsIo *io);
extern void lib3ds_mesh_write(Lib3dsFile *file, Lib3dsMesh *mesh, Lib3dsIo *io);
extern void lib3ds_track_read(Lib3dsTrack *track, Lib3dsIo *io);
extern void lib3ds_track_write(Lib3dsTrack *track, Lib3dsIo *io);
extern void lib3ds_node_read(Lib3dsNode *node, Lib3dsIo *io);
extern void lib3ds_node_write(Lib3dsNode *node, uint16_t node_id, uint16_t parent_id, Lib3dsIo *io);
typedef void (*Lib3dsFreeFunc)(void *ptr);
extern void* lib3ds_util_realloc_array(void *ptr, int old_size, int new_size, int element_size);
extern void lib3ds_util_reserve_array(void ***ptr, int *n, int *size, int new_size, int force, Lib3dsFreeFunc free_func);
extern void lib3ds_util_insert_array(void ***ptr, int *n, int *size, void *element, int index);
extern void lib3ds_util_remove_array(void ***ptr, int *n, int index, Lib3dsFreeFunc free_func);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,521 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
/* --- Code for OpenSceneGraph --- */
#include "lib3ds.h" // For setByteOrder()
#include <osg/Endian>
static bool s_requiresByteSwap = false;
extern LIB3DSAPI void setByteOrder()
{
s_requiresByteSwap = osg::getCpuByteOrder()==osg::BigEndian;
}
/* --- (end) Code for OpenSceneGraph --- */
typedef union {
uint32_t dword_value;
float float_value;
} Lib3dsDwordFloat;
void
lib3ds_io_setup(Lib3dsIo *io) {
assert(io);
io->impl = calloc(sizeof(Lib3dsIoImpl), 1);
}
void
lib3ds_io_cleanup(Lib3dsIo *io) {
Lib3dsIoImpl *impl;
assert(io);
impl = (Lib3dsIoImpl*)io->impl;
if (impl->tmp_mem) {
free(impl->tmp_mem);
impl->tmp_mem = NULL;
}
if (impl->tmp_node) {
lib3ds_node_free(impl->tmp_node);
impl->tmp_node = NULL;
}
free(impl);
}
long
lib3ds_io_seek(Lib3dsIo *io, long offset, Lib3dsIoSeek origin) {
assert(io);
if (!io || !io->seek_func) {
return 0;
}
return (*io->seek_func)(io->self, offset, origin);
}
long
lib3ds_io_tell(Lib3dsIo *io) {
assert(io);
if (!io || !io->tell_func) {
return 0;
}
return (*io->tell_func)(io->self);
}
size_t
lib3ds_io_read(Lib3dsIo *io, void *buffer, size_t size) {
assert(io);
if (!io || !io->read_func) {
return 0;
}
return (*io->read_func)(io->self, buffer, size);
}
size_t
lib3ds_io_write(Lib3dsIo *io, const void *buffer, size_t size) {
assert(io);
if (!io || !io->write_func) {
return 0;
}
return (*io->write_func)(io->self, buffer, size);
}
static void
lib3ds_io_log_str(Lib3dsIo *io, Lib3dsLogLevel level, const char *str) {
if (!io || !io->log_func)
return;
(*io->log_func)(io->self, level, ((Lib3dsIoImpl*)io->impl)->log_indent, str);
}
void
lib3ds_io_log(Lib3dsIo *io, Lib3dsLogLevel level, const char *format, ...) {
va_list args;
/* FIXME */ char str[1024];
assert(io);
if (!io || !io->log_func)
return;
va_start(args, format);
/* FIXME: */ vsprintf(str, format, args);
lib3ds_io_log_str(io, level, str);
if (level == LIB3DS_LOG_ERROR) {
longjmp(((Lib3dsIoImpl*)io->impl)->jmpbuf, 1);
}
}
void
lib3ds_io_log_indent(Lib3dsIo *io, int indent) {
assert(io);
if (!io)
return;
((Lib3dsIoImpl*)io->impl)->log_indent += indent;
}
void
lib3ds_io_read_error(Lib3dsIo *io) {
lib3ds_io_log(io, LIB3DS_LOG_ERROR, "Reading from input stream failed.");
}
void
lib3ds_io_write_error(Lib3dsIo *io) {
lib3ds_io_log(io, LIB3DS_LOG_ERROR, "Writing to output stream failed.");
}
/*!
* Read a byte from a file stream.
*/
uint8_t
lib3ds_io_read_byte(Lib3dsIo *io) {
uint8_t b;
assert(io);
lib3ds_io_read(io, &b, 1);
return(b);
}
/**
* Read a word from a file stream in little endian format.
*/
uint16_t
lib3ds_io_read_word(Lib3dsIo *io) {
uint8_t b[2];
uint16_t w;
assert(io);
lib3ds_io_read(io, b, 2);
w = ((uint16_t)b[1] << 8) |
((uint16_t)b[0]);
/* --- Code for OpenSceneGraph --- */
if (s_requiresByteSwap)
{
osg::swapBytes2((char*)w);
}
/* --- (end) Code for OpenSceneGraph --- */
return(w);
}
/*!
* Read a dword from file a stream in little endian format.
*/
uint32_t
lib3ds_io_read_dword(Lib3dsIo *io) {
uint8_t b[4];
uint32_t d;
assert(io);
lib3ds_io_read(io, b, 4);
d = ((uint32_t)b[3] << 24) |
((uint32_t)b[2] << 16) |
((uint32_t)b[1] << 8) |
((uint32_t)b[0]);
/* --- Code for OpenSceneGraph --- */
if (s_requiresByteSwap)
{
osg::swapBytes4((char*)d);
}
/* --- (end) Code for OpenSceneGraph --- */
return(d);
}
/*!
* Read a signed byte from a file stream.
*/
int8_t
lib3ds_io_read_intb(Lib3dsIo *io) {
int8_t b;
assert(io);
lib3ds_io_read(io, &b, 1);
return(b);
}
/*!
* Read a signed word from a file stream in little endian format.
*/
int16_t
lib3ds_io_read_intw(Lib3dsIo *io) {
uint8_t b[2];
uint16_t w;
assert(io);
lib3ds_io_read(io, b, 2);
w = ((uint16_t)b[1] << 8) |
((uint16_t)b[0]);
/* --- Code for OpenSceneGraph --- */
if (s_requiresByteSwap)
{
osg::swapBytes2((char*)w);
}
/* --- (end) Code for OpenSceneGraph --- */
return((int16_t)w);
}
/*!
* Read a signed dword a from file stream in little endian format.
*/
int32_t
lib3ds_io_read_intd(Lib3dsIo *io) {
uint8_t b[4];
uint32_t d;
assert(io);
lib3ds_io_read(io, b, 4);
d = ((uint32_t)b[3] << 24) |
((uint32_t)b[2] << 16) |
((uint32_t)b[1] << 8) |
((uint32_t)b[0]);
/* --- Code for OpenSceneGraph --- */
if (s_requiresByteSwap)
{
osg::swapBytes4((char*)d);
}
/* --- (end) Code for OpenSceneGraph --- */
return((int32_t)d);
}
/*!
* Read a float from a file stream in little endian format.
*/
float
lib3ds_io_read_float(Lib3dsIo *io) {
uint8_t b[4];
Lib3dsDwordFloat d;
assert(io);
lib3ds_io_read(io, b, 4);
d.dword_value = ((uint32_t)b[3] << 24) |
((uint32_t)b[2] << 16) |
((uint32_t)b[1] << 8) |
((uint32_t)b[0]);
/* --- Code for OpenSceneGraph --- */
if (s_requiresByteSwap)
{
osg::swapBytes4((char*)d.dword_value);
}
/* --- (end) Code for OpenSceneGraph --- */
return d.float_value;
}
/*!
* Read a vector from a file stream in little endian format.
*
* \param io IO input handle.
* \param v The vector to store the data.
*/
void
lib3ds_io_read_vector(Lib3dsIo *io, float v[3]) {
assert(io);
v[0] = lib3ds_io_read_float(io);
v[1] = lib3ds_io_read_float(io);
v[2] = lib3ds_io_read_float(io);
}
void
lib3ds_io_read_rgb(Lib3dsIo *io, float rgb[3]) {
assert(io);
rgb[0] = lib3ds_io_read_float(io);
rgb[1] = lib3ds_io_read_float(io);
rgb[2] = lib3ds_io_read_float(io);
}
/*!
* Read a zero-terminated string from a file stream.
*
* \param io IO input handle.
* \param s The buffer to store the read string.
* \param buflen Buffer length.
*
* \return True on success, False otherwise.
*/
void
lib3ds_io_read_string(Lib3dsIo *io, char *s, int buflen) {
char c;
int k = 0;
assert(io);
for (;;) {
if (lib3ds_io_read(io, &c, 1) != 1) {
lib3ds_io_read_error(io);
}
*s++ = c;
if (!c) {
break;
}
++k;
if (k >= buflen) {
lib3ds_io_log(io, LIB3DS_LOG_ERROR, "Invalid string in input stream.");
}
}
}
/*!
* Writes a byte into a file stream.
*/
void
lib3ds_io_write_byte(Lib3dsIo *io, uint8_t b) {
assert(io);
if (lib3ds_io_write(io, &b, 1) != 1) {
lib3ds_io_write_error(io);
}
}
/*!
* Writes a word into a little endian file stream.
*/
void
lib3ds_io_write_word(Lib3dsIo *io, uint16_t w) {
/* --- Code for OpenSceneGraph --- */
if (s_requiresByteSwap)
{
osg::swapBytes2((char*)w);
}
/* --- (end) Code for OpenSceneGraph --- */
uint8_t b[2];
assert(io);
b[1] = ((uint16_t)w & 0xFF00) >> 8;
b[0] = ((uint16_t)w & 0x00FF);
if (lib3ds_io_write(io, b, 2) != 2) {
lib3ds_io_write_error(io);
}
}
/*!
* Writes a dword into a little endian file stream.
*/
void
lib3ds_io_write_dword(Lib3dsIo *io, uint32_t d) {
/* --- Code for OpenSceneGraph --- */
if (s_requiresByteSwap)
{
osg::swapBytes4((char*)d);
}
/* --- (end) Code for OpenSceneGraph --- */
uint8_t b[4];
assert(io);
b[3] = (uint8_t)(((uint32_t)d & 0xFF000000) >> 24);
b[2] = (uint8_t)(((uint32_t)d & 0x00FF0000) >> 16);
b[1] = (uint8_t)(((uint32_t)d & 0x0000FF00) >> 8);
b[0] = (uint8_t)(((uint32_t)d & 0x000000FF));
if (lib3ds_io_write(io, b, 4) != 4) {
lib3ds_io_write_error(io);
}
}
/*!
* Writes a signed byte in a file stream.
*/
void
lib3ds_io_write_intb(Lib3dsIo *io, int8_t b) {
assert(io);
if (lib3ds_io_write(io, &b, 1) != 1) {
lib3ds_io_write_error(io);
}
}
/*!
* Writes a signed word into a little endian file stream.
*/
void
lib3ds_io_write_intw(Lib3dsIo *io, int16_t w) {
/* --- Code for OpenSceneGraph --- */
if (s_requiresByteSwap)
{
osg::swapBytes2((char*)w);
}
/* --- (end) Code for OpenSceneGraph --- */
uint8_t b[2];
assert(io);
b[1] = ((uint16_t)w & 0xFF00) >> 8;
b[0] = ((uint16_t)w & 0x00FF);
if (lib3ds_io_write(io, b, 2) != 2) {
lib3ds_io_write_error(io);
}
}
/*!
* Writes a signed dword into a little endian file stream.
*/
void
lib3ds_io_write_intd(Lib3dsIo *io, int32_t d) {
/* --- Code for OpenSceneGraph --- */
if (s_requiresByteSwap)
{
osg::swapBytes4((char*)d);
}
/* --- (end) Code for OpenSceneGraph --- */
uint8_t b[4];
assert(io);
b[3] = (uint8_t)(((uint32_t)d & 0xFF000000) >> 24);
b[2] = (uint8_t)(((uint32_t)d & 0x00FF0000) >> 16);
b[1] = (uint8_t)(((uint32_t)d & 0x0000FF00) >> 8);
b[0] = (uint8_t)(((uint32_t)d & 0x000000FF));
if (lib3ds_io_write(io, b, 4) != 4) {
lib3ds_io_write_error(io);
}
}
/*!
* Writes a float into a little endian file stream.
*/
void
lib3ds_io_write_float(Lib3dsIo *io, float l) {
uint8_t b[4];
Lib3dsDwordFloat d;
assert(io);
d.float_value = l;
/* --- Code for OpenSceneGraph --- */
if (s_requiresByteSwap)
{
osg::swapBytes4((char*)d.dword_value);
}
/* --- (end) Code for OpenSceneGraph --- */
b[3] = (uint8_t)(((uint32_t)d.dword_value & 0xFF000000) >> 24);
b[2] = (uint8_t)(((uint32_t)d.dword_value & 0x00FF0000) >> 16);
b[1] = (uint8_t)(((uint32_t)d.dword_value & 0x0000FF00) >> 8);
b[0] = (uint8_t)(((uint32_t)d.dword_value & 0x000000FF));
if (lib3ds_io_write(io, b, 4) != 4) {
lib3ds_io_write_error(io);
}
}
/*!
* Writes a vector into a file stream in little endian format.
*/
void
lib3ds_io_write_vector(Lib3dsIo *io, float v[3]) {
int i;
for (i = 0; i < 3; ++i) {
lib3ds_io_write_float(io, v[i]);
}
}
void
lib3ds_io_write_rgb(Lib3dsIo *io, float rgb[3]) {
int i;
for (i = 0; i < 3; ++i) {
lib3ds_io_write_float(io, rgb[i]);
}
}
/*!
* Writes a zero-terminated string into a file stream.
*/
void
lib3ds_io_write_string(Lib3dsIo *io, const char *s) {
size_t len;
assert(io && s);
len = strlen(s);
if (lib3ds_io_write(io, s, len + 1) != len +1) {
lib3ds_io_write_error(io);
}
}

View File

@@ -0,0 +1,323 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
Lib3dsLight*
lib3ds_light_new(const char *name) {
Lib3dsLight *light;
assert(name);
assert(strlen(name) < 64);
light = (Lib3dsLight*)calloc(sizeof(Lib3dsLight), 1);
if (!light) {
return(0);
}
strcpy(light->name, name);
return(light);
}
void
lib3ds_light_free(Lib3dsLight *light) {
memset(light, 0, sizeof(Lib3dsLight));
free(light);
}
static void
spotlight_read(Lib3dsLight *light, Lib3dsIo *io) {
Lib3dsChunk c;
uint16_t chunk;
int i;
lib3ds_chunk_read_start(&c, CHK_DL_SPOTLIGHT, io);
light->spot_light = TRUE;
for (i = 0; i < 3; ++i) {
light->target[i] = lib3ds_io_read_float(io);
}
light->hotspot = lib3ds_io_read_float(io);
light->falloff = lib3ds_io_read_float(io);
lib3ds_chunk_read_tell(&c, io);
while ((chunk = lib3ds_chunk_read_next(&c, io)) != 0) {
switch (chunk) {
case CHK_DL_SPOT_ROLL:
light->roll = lib3ds_io_read_float(io);
break;
case CHK_DL_SHADOWED: {
light->shadowed = TRUE;
break;
}
case CHK_DL_LOCAL_SHADOW2: {
light->shadow_bias = lib3ds_io_read_float(io);
light->shadow_filter = lib3ds_io_read_float(io);
light->shadow_size = lib3ds_io_read_intw(io);
break;
}
case CHK_DL_SEE_CONE: {
light->see_cone = TRUE;
break;
}
case CHK_DL_SPOT_RECTANGULAR: {
light->rectangular_spot = TRUE;
break;
}
case CHK_DL_SPOT_ASPECT: {
light->spot_aspect = lib3ds_io_read_float(io);
break;
}
case CHK_DL_SPOT_PROJECTOR: {
light->use_projector = TRUE;
lib3ds_io_read_string(io, light->projector, 64);
break;
}
case CHK_DL_SPOT_OVERSHOOT: {
light->spot_overshoot = TRUE;
break;
}
case CHK_DL_RAY_BIAS: {
light->ray_bias = lib3ds_io_read_float(io);
break;
}
case CHK_DL_RAYSHAD: {
light->ray_shadows = TRUE;
break;
}
default:
lib3ds_chunk_unknown(chunk, io);
}
}
lib3ds_chunk_read_end(&c, io);
}
void
lib3ds_light_read(Lib3dsLight *light, Lib3dsIo *io) {
Lib3dsChunk c;
uint16_t chunk;
lib3ds_chunk_read_start(&c, CHK_N_DIRECT_LIGHT, io);
{
int i;
for (i = 0; i < 3; ++i) {
light->position[i] = lib3ds_io_read_float(io);
}
}
lib3ds_chunk_read_tell(&c, io);
while ((chunk = lib3ds_chunk_read_next(&c, io)) != 0) {
switch (chunk) {
case CHK_COLOR_F: {
int i;
for (i = 0; i < 3; ++i) {
light->color[i] = lib3ds_io_read_float(io);
}
break;
}
case CHK_DL_OFF:
light->off = TRUE;
break;
case CHK_DL_OUTER_RANGE:
light->outer_range = lib3ds_io_read_float(io);
break;
case CHK_DL_INNER_RANGE:
light->inner_range = lib3ds_io_read_float(io);
break;
case CHK_DL_MULTIPLIER:
light->multiplier = lib3ds_io_read_float(io);
break;
case CHK_DL_EXCLUDE: {
/* FIXME: */
lib3ds_chunk_unknown(chunk, io);
break;
}
case CHK_DL_ATTENUATE:
light->attenuation = lib3ds_io_read_float(io);
break;
case CHK_DL_SPOTLIGHT: {
lib3ds_chunk_read_reset(&c, io);
spotlight_read(light, io);
break;
}
default:
lib3ds_chunk_unknown(chunk, io);
}
}
lib3ds_chunk_read_end(&c, io);
}
void
lib3ds_light_write(Lib3dsLight *light, Lib3dsIo *io) {
Lib3dsChunk c;
c.chunk = CHK_N_DIRECT_LIGHT;
lib3ds_chunk_write_start(&c, io);
lib3ds_io_write_vector(io, light->position);
{ /*---- LIB3DS_COLOR_F ----*/
Lib3dsChunk c;
c.chunk = CHK_COLOR_F;
c.size = 18;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_rgb(io, light->color);
}
if (light->off) { /*---- LIB3DS_DL_OFF ----*/
Lib3dsChunk c;
c.chunk = CHK_DL_OFF;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
{ /*---- LIB3DS_DL_OUTER_RANGE ----*/
Lib3dsChunk c;
c.chunk = CHK_DL_OUTER_RANGE;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, light->outer_range);
}
{ /*---- LIB3DS_DL_INNER_RANGE ----*/
Lib3dsChunk c;
c.chunk = CHK_DL_INNER_RANGE;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, light->inner_range);
}
{ /*---- LIB3DS_DL_MULTIPLIER ----*/
Lib3dsChunk c;
c.chunk = CHK_DL_MULTIPLIER;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, light->multiplier);
}
if (light->attenuation) { /*---- LIB3DS_DL_ATTENUATE ----*/
Lib3dsChunk c;
c.chunk = CHK_DL_ATTENUATE;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
if (light->spot_light) {
Lib3dsChunk c;
c.chunk = CHK_DL_SPOTLIGHT;
lib3ds_chunk_write_start(&c, io);
lib3ds_io_write_vector(io, light->target);
lib3ds_io_write_float(io, light->hotspot);
lib3ds_io_write_float(io, light->falloff);
{ /*---- LIB3DS_DL_SPOT_ROLL ----*/
Lib3dsChunk c;
c.chunk = CHK_DL_SPOT_ROLL;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, light->roll);
}
if (light->shadowed) { /*---- LIB3DS_DL_SHADOWED ----*/
Lib3dsChunk c;
c.chunk = CHK_DL_SHADOWED;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
if ((fabs(light->shadow_bias) > LIB3DS_EPSILON) ||
(fabs(light->shadow_filter) > LIB3DS_EPSILON) ||
(light->shadow_size != 0)) { /*---- LIB3DS_DL_LOCAL_SHADOW2 ----*/
Lib3dsChunk c;
c.chunk = CHK_DL_LOCAL_SHADOW2;
c.size = 16;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, light->shadow_bias);
lib3ds_io_write_float(io, light->shadow_filter);
lib3ds_io_write_intw(io, (int16_t)light->shadow_size);
}
if (light->see_cone) { /*---- LIB3DS_DL_SEE_CONE ----*/
Lib3dsChunk c;
c.chunk = CHK_DL_SEE_CONE;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
if (light->rectangular_spot) { /*---- LIB3DS_DL_SPOT_RECTANGULAR ----*/
Lib3dsChunk c;
c.chunk = CHK_DL_SPOT_RECTANGULAR;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
if (fabs(light->spot_aspect) > LIB3DS_EPSILON) { /*---- LIB3DS_DL_SPOT_ASPECT ----*/
Lib3dsChunk c;
c.chunk = CHK_DL_SPOT_ASPECT;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, light->spot_aspect);
}
if (light->use_projector) { /*---- LIB3DS_DL_SPOT_PROJECTOR ----*/
Lib3dsChunk c;
c.chunk = CHK_DL_SPOT_PROJECTOR;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_string(io, light->projector);
}
if (light->spot_overshoot) { /*---- LIB3DS_DL_SPOT_OVERSHOOT ----*/
Lib3dsChunk c;
c.chunk = CHK_DL_SPOT_OVERSHOOT;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
if (fabs(light->ray_bias) > LIB3DS_EPSILON) { /*---- LIB3DS_DL_RAY_BIAS ----*/
Lib3dsChunk c;
c.chunk = CHK_DL_RAY_BIAS;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, light->ray_bias);
}
if (light->ray_shadows) { /*---- LIB3DS_DL_RAYSHAD ----*/
Lib3dsChunk c;
c.chunk = CHK_DL_RAYSHAD;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
lib3ds_chunk_write_end(&c, io);
}
lib3ds_chunk_write_end(&c, io);
}

View File

@@ -0,0 +1,861 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
static void
initialize_texture_map(Lib3dsTextureMap *map) {
map->flags = 0x10;
map->percent = 1.0f;
map->scale[0] = 1.0f;
map->scale[1] = 1.0f;
}
/*!
* Creates and returns a new, empty Lib3dsMaterial object.
*
* Initial value of the material is a shiny grey.
*
* \return A pointer to the Lib3dsMaterial structure.
* If the structure cannot be allocated, NULL is returned.
*/
Lib3dsMaterial*
lib3ds_material_new(const char* name) {
Lib3dsMaterial *mat;
mat = (Lib3dsMaterial*)calloc(sizeof(Lib3dsMaterial), 1);
if (!mat) {
return(0);
}
if (name) {
strcpy(mat->name, name);
}
mat->ambient[0] = mat->ambient[1] = mat->ambient[2] = 0.588235f;
mat->diffuse[0] = mat->diffuse[1] = mat->diffuse[2] = 0.588235f;
mat->specular[0] = mat->specular[1] = mat->specular[2] = 0.898039f;
mat->shininess = 0.1f;
mat->wire_size = 1.0f;
mat->shading = 3;
initialize_texture_map(&mat->texture1_map);
initialize_texture_map(&mat->texture1_mask);
initialize_texture_map(&mat->texture2_map);
initialize_texture_map(&mat->texture2_mask);
initialize_texture_map(&mat->opacity_map);
initialize_texture_map(&mat->opacity_mask);
initialize_texture_map(&mat->bump_map);
initialize_texture_map(&mat->bump_mask);
initialize_texture_map(&mat->specular_map);
initialize_texture_map(&mat->specular_mask);
initialize_texture_map(&mat->shininess_map);
initialize_texture_map(&mat->shininess_mask);
initialize_texture_map(&mat->self_illum_map);
initialize_texture_map(&mat->self_illum_mask);
initialize_texture_map(&mat->reflection_map);
initialize_texture_map(&mat->reflection_mask);
return(mat);
}
void
lib3ds_material_free(Lib3dsMaterial *material) {
memset(material, 0, sizeof(Lib3dsMaterial));
free(material);
}
static void
color_read(float rgb[3], Lib3dsIo *io) {
Lib3dsChunk c;
uint16_t chunk;
int have_lin = FALSE;
lib3ds_chunk_read_start(&c, 0, io);
while ((chunk = lib3ds_chunk_read_next(&c, io)) != 0) {
switch (chunk) {
case CHK_LIN_COLOR_24: {
int i;
for (i = 0; i < 3; ++i) {
rgb[i] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
}
have_lin = TRUE;
break;
}
case CHK_COLOR_24: {
/* gamma corrected color chunk
replaced in 3ds R3 by LIN_COLOR_24 */
if (!have_lin) {
int i;
for (i = 0; i < 3; ++i) {
rgb[i] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
}
}
break;
}
case CHK_LIN_COLOR_F: {
int i;
for (i = 0; i < 3; ++i) {
rgb[i] = lib3ds_io_read_float(io);
}
have_lin = TRUE;
break;
}
case CHK_COLOR_F: {
if (!have_lin) {
int i;
for (i = 0; i < 3; ++i) {
rgb[i] = lib3ds_io_read_float(io);
}
}
break;
}
default:
lib3ds_chunk_unknown(chunk, io);
}
}
lib3ds_chunk_read_end(&c, io);
}
static void
int_percentage_read(float *p, Lib3dsIo *io) {
Lib3dsChunk c;
uint16_t chunk;
lib3ds_chunk_read_start(&c, 0, io);
while ((chunk = lib3ds_chunk_read_next(&c, io)) != 0) {
switch (chunk) {
case CHK_INT_PERCENTAGE: {
int16_t i = lib3ds_io_read_intw(io);
*p = (float)(1.0 * i / 100.0);
break;
}
default:
lib3ds_chunk_unknown(chunk, io);
}
}
lib3ds_chunk_read_end(&c, io);
}
static void
texture_map_read(Lib3dsTextureMap *map, Lib3dsIo *io) {
Lib3dsChunk c;
uint16_t chunk;
lib3ds_chunk_read_start(&c, 0, io);
while ((chunk = lib3ds_chunk_read_next(&c, io)) != 0) {
switch (chunk) {
case CHK_INT_PERCENTAGE: {
map->percent = 1.0f * lib3ds_io_read_intw(io) / 100.0f;
break;
}
case CHK_MAT_MAPNAME: {
lib3ds_io_read_string(io, map->name, 64);
lib3ds_io_log(io, LIB3DS_LOG_INFO, " NAME=%s", map->name);
break;
}
case CHK_MAT_MAP_TILING: {
map->flags = lib3ds_io_read_word(io);
break;
}
case CHK_MAT_MAP_TEXBLUR:
map->blur = lib3ds_io_read_float(io);
break;
case CHK_MAT_MAP_USCALE:
map->scale[0] = lib3ds_io_read_float(io);
break;
case CHK_MAT_MAP_VSCALE: {
map->scale[1] = lib3ds_io_read_float(io);
break;
}
case CHK_MAT_MAP_UOFFSET: {
map->offset[0] = lib3ds_io_read_float(io);
break;
}
case CHK_MAT_MAP_VOFFSET: {
map->offset[1] = lib3ds_io_read_float(io);
break;
}
case CHK_MAT_MAP_ANG: {
map->rotation = lib3ds_io_read_float(io);
break;
}
case CHK_MAT_MAP_COL1: {
map->tint_1[0] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
map->tint_1[1] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
map->tint_1[2] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
break;
}
case CHK_MAT_MAP_COL2: {
map->tint_2[0] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
map->tint_2[1] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
map->tint_2[2] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
break;
}
case CHK_MAT_MAP_RCOL: {
map->tint_r[0] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
map->tint_r[1] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
map->tint_r[2] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
break;
}
case CHK_MAT_MAP_GCOL: {
map->tint_g[0] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
map->tint_g[1] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
map->tint_g[2] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
break;
}
case CHK_MAT_MAP_BCOL: {
map->tint_b[0] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
map->tint_b[1] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
map->tint_b[2] = 1.0f * lib3ds_io_read_byte(io) / 255.0f;
break;
}
default:
lib3ds_chunk_unknown(chunk,io);
}
}
lib3ds_chunk_read_end(&c, io);
}
void
lib3ds_material_read(Lib3dsMaterial *material, Lib3dsIo *io) {
Lib3dsChunk c;
uint16_t chunk;
assert(material);
lib3ds_chunk_read_start(&c, CHK_MAT_ENTRY, io);
while ((chunk = lib3ds_chunk_read_next(&c, io)) != 0) {
switch (chunk) {
case CHK_MAT_NAME: {
lib3ds_io_read_string(io, material->name, 64);
lib3ds_io_log(io, LIB3DS_LOG_INFO, " NAME=%s", material->name);
break;
}
case CHK_MAT_AMBIENT: {
lib3ds_chunk_read_reset(&c, io);
color_read(material->ambient, io);
break;
}
case CHK_MAT_DIFFUSE: {
lib3ds_chunk_read_reset(&c, io);
color_read(material->diffuse, io);
break;
}
case CHK_MAT_SPECULAR: {
lib3ds_chunk_read_reset(&c, io);
color_read(material->specular, io);
break;
}
case CHK_MAT_SHININESS: {
lib3ds_chunk_read_reset(&c, io);
int_percentage_read(&material->shininess, io);
break;
}
case CHK_MAT_SHIN2PCT: {
lib3ds_chunk_read_reset(&c, io);
int_percentage_read(&material->shin_strength, io);
break;
}
case CHK_MAT_TRANSPARENCY: {
lib3ds_chunk_read_reset(&c, io);
int_percentage_read(&material->transparency, io);
break;
}
case CHK_MAT_XPFALL: {
lib3ds_chunk_read_reset(&c, io);
int_percentage_read(&material->falloff, io);
break;
}
case CHK_MAT_SELF_ILPCT: {
lib3ds_chunk_read_reset(&c, io);
int_percentage_read(&material->self_illum, io);
break;
}
case CHK_MAT_USE_XPFALL: {
material->use_falloff = TRUE;
break;
}
case CHK_MAT_REFBLUR: {
lib3ds_chunk_read_reset(&c, io);
int_percentage_read(&material->blur, io);
break;
}
case CHK_MAT_USE_REFBLUR: {
material->use_blur = TRUE;
break;
}
case CHK_MAT_SHADING: {
material->shading = lib3ds_io_read_intw(io);
break;
}
case CHK_MAT_SELF_ILLUM: {
material->self_illum_flag = TRUE;
break;
}
case CHK_MAT_TWO_SIDE: {
material->two_sided = TRUE;
break;
}
case CHK_MAT_DECAL: {
material->map_decal = TRUE;
break;
}
case CHK_MAT_ADDITIVE: {
material->is_additive = TRUE;
break;
}
case CHK_MAT_FACEMAP: {
material->face_map = TRUE;
break;
}
case CHK_MAT_PHONGSOFT: {
material->soften = TRUE;
break;
}
case CHK_MAT_WIRE: {
material->use_wire = TRUE;
break;
}
case CHK_MAT_WIREABS: {
material->use_wire_abs = TRUE;
break;
}
case CHK_MAT_WIRE_SIZE: {
material->wire_size = lib3ds_io_read_float(io);
break;
}
case CHK_MAT_TEXMAP: {
lib3ds_chunk_read_reset(&c, io);
texture_map_read(&material->texture1_map, io);
break;
}
case CHK_MAT_TEXMASK: {
lib3ds_chunk_read_reset(&c, io);
texture_map_read(&material->texture1_mask, io);
break;
}
case CHK_MAT_TEX2MAP: {
lib3ds_chunk_read_reset(&c, io);
texture_map_read(&material->texture2_map, io);
break;
}
case CHK_MAT_TEX2MASK: {
lib3ds_chunk_read_reset(&c, io);
texture_map_read(&material->texture2_mask, io);
break;
}
case CHK_MAT_OPACMAP: {
lib3ds_chunk_read_reset(&c, io);
texture_map_read(&material->opacity_map, io);
break;
}
case CHK_MAT_OPACMASK: {
lib3ds_chunk_read_reset(&c, io);
texture_map_read(&material->opacity_mask, io);
break;
}
case CHK_MAT_BUMPMAP: {
lib3ds_chunk_read_reset(&c, io);
texture_map_read(&material->bump_map, io);
break;
}
case CHK_MAT_BUMPMASK: {
lib3ds_chunk_read_reset(&c, io);
texture_map_read(&material->bump_mask, io);
break;
}
case CHK_MAT_SPECMAP: {
lib3ds_chunk_read_reset(&c, io);
texture_map_read(&material->specular_map, io);
break;
}
case CHK_MAT_SPECMASK: {
lib3ds_chunk_read_reset(&c, io);
texture_map_read(&material->specular_mask, io);
break;
}
case CHK_MAT_SHINMAP: {
lib3ds_chunk_read_reset(&c, io);
texture_map_read(&material->shininess_map, io);
break;
}
case CHK_MAT_SHINMASK: {
lib3ds_chunk_read_reset(&c, io);
texture_map_read(&material->shininess_mask, io);
break;
}
case CHK_MAT_SELFIMAP: {
lib3ds_chunk_read_reset(&c, io);
texture_map_read(&material->self_illum_map, io);
break;
}
case CHK_MAT_SELFIMASK: {
lib3ds_chunk_read_reset(&c, io);
texture_map_read(&material->self_illum_mask, io);
break;
}
case CHK_MAT_REFLMAP: {
lib3ds_chunk_read_reset(&c, io);
texture_map_read(&material->reflection_map, io);
break;
}
case CHK_MAT_REFLMASK: {
lib3ds_chunk_read_reset(&c, io);
texture_map_read(&material->reflection_mask, io);
break;
}
case CHK_MAT_ACUBIC: {
lib3ds_io_read_intb(io);
material->autorefl_map_anti_alias = lib3ds_io_read_intb(io);
material->autorefl_map_flags = lib3ds_io_read_intw(io);
material->autorefl_map_size = lib3ds_io_read_intd(io);
material->autorefl_map_frame_step = lib3ds_io_read_intd(io);
break;
}
default:
lib3ds_chunk_unknown(chunk, io);
}
}
lib3ds_chunk_read_end(&c, io);
}
static void
color_write(float rgb[3], Lib3dsIo *io) {
Lib3dsChunk c;
c.chunk = CHK_COLOR_24;
c.size = 9;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*rgb[0] + 0.5));
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*rgb[1] + 0.5));
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*rgb[2] + 0.5));
c.chunk = CHK_LIN_COLOR_24;
c.size = 9;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*rgb[0] + 0.5));
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*rgb[1] + 0.5));
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*rgb[2] + 0.5));
}
static void
int_percentage_write(float p, Lib3dsIo *io) {
Lib3dsChunk c;
c.chunk = CHK_INT_PERCENTAGE;
c.size = 8;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_intw(io, (uint8_t)floor(100.0*p + 0.5));
}
static void
texture_map_write(uint16_t chunk, Lib3dsTextureMap *map, Lib3dsIo *io) {
Lib3dsChunk c;
if (strlen(map->name) == 0) {
return;
}
c.chunk = chunk;
lib3ds_chunk_write_start(&c, io);
int_percentage_write(map->percent, io);
{ /*---- CHK_MAT_MAPNAME ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_MAPNAME;
c.size = 6 + (uint32_t)strlen(map->name) + 1;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_string(io, map->name);
}
{ /*---- CHK_MAT_MAP_TILING ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_MAP_TILING;
c.size = 8;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_word(io, (uint16_t)map->flags);
}
{ /*---- CHK_MAT_MAP_TEXBLUR ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_MAP_TEXBLUR;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, map->blur);
}
{ /*---- CHK_MAT_MAP_USCALE ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_MAP_USCALE;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, map->scale[0]);
}
{ /*---- CHK_MAT_MAP_VSCALE ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_MAP_VSCALE;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, map->scale[1]);
}
{ /*---- CHK_MAT_MAP_UOFFSET ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_MAP_UOFFSET;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, map->offset[0]);
}
{ /*---- CHK_MAT_MAP_VOFFSET ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_MAP_VOFFSET;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, map->offset[1]);
}
{ /*---- CHK_MAT_MAP_ANG ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_MAP_ANG;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, map->rotation);
}
{ /*---- CHK_MAT_MAP_COL1 ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_MAP_COL1;
c.size = 9;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*map->tint_1[0] + 0.5));
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*map->tint_1[1] + 0.5));
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*map->tint_1[2] + 0.5));
}
{ /*---- CHK_MAT_MAP_COL2 ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_MAP_COL2;
c.size = 9;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*map->tint_2[0] + 0.5));
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*map->tint_2[1] + 0.5));
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*map->tint_2[2] + 0.5));
}
{ /*---- CHK_MAT_MAP_RCOL ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_MAP_RCOL;
c.size = 9;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*map->tint_r[0] + 0.5));
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*map->tint_r[1] + 0.5));
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*map->tint_r[2] + 0.5));
}
{ /*---- CHK_MAT_MAP_GCOL ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_MAP_GCOL;
c.size = 9;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*map->tint_g[0] + 0.5));
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*map->tint_g[1] + 0.5));
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*map->tint_g[2] + 0.5));
}
{ /*---- CHK_MAT_MAP_BCOL ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_MAP_BCOL;
c.size = 9;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*map->tint_b[0] + 0.5));
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*map->tint_b[1] + 0.5));
lib3ds_io_write_byte(io, (uint8_t)floor(255.0*map->tint_b[2] + 0.5));
}
lib3ds_chunk_write_end(&c, io);
}
void
lib3ds_material_write(Lib3dsMaterial *material, Lib3dsIo *io) {
Lib3dsChunk c;
c.chunk = CHK_MAT_ENTRY;
lib3ds_chunk_write_start(&c, io);
{ /*---- CHK_MAT_NAME ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_NAME;
c.size = 6 + (uint32_t)strlen(material->name) + 1;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_string(io, material->name);
}
{ /*---- CHK_MAT_AMBIENT ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_AMBIENT;
c.size = 24;
lib3ds_chunk_write(&c, io);
color_write(material->ambient, io);
}
{ /*---- CHK_MAT_DIFFUSE ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_DIFFUSE;
c.size = 24;
lib3ds_chunk_write(&c, io);
color_write(material->diffuse, io);
}
{ /*---- CHK_MAT_SPECULAR ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_SPECULAR;
c.size = 24;
lib3ds_chunk_write(&c, io);
color_write(material->specular, io);
}
{ /*---- CHK_MAT_SHININESS ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_SHININESS;
c.size = 14;
lib3ds_chunk_write(&c, io);
int_percentage_write(material->shininess, io);
}
{ /*---- CHK_MAT_SHIN2PCT ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_SHIN2PCT;
c.size = 14;
lib3ds_chunk_write(&c, io);
int_percentage_write(material->shin_strength, io);
}
{ /*---- CHK_MAT_TRANSPARENCY ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_TRANSPARENCY;
c.size = 14;
lib3ds_chunk_write(&c, io);
int_percentage_write(material->transparency, io);
}
{ /*---- CHK_MAT_XPFALL ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_XPFALL;
c.size = 14;
lib3ds_chunk_write(&c, io);
int_percentage_write(material->falloff, io);
}
if (material->use_falloff) { /*---- CHK_MAT_USE_XPFALL ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_USE_XPFALL;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
{ /*---- CHK_MAT_SHADING ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_SHADING;
c.size = 8;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_intw(io, (int16_t)material->shading);
}
{ /*---- CHK_MAT_REFBLUR ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_REFBLUR;
c.size = 14;
lib3ds_chunk_write(&c, io);
int_percentage_write(material->blur, io);
}
if (material->use_blur) { /*---- CHK_MAT_USE_REFBLUR ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_USE_REFBLUR;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
if (material->self_illum_flag) { /*---- CHK_MAT_SELF_ILLUM ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_SELF_ILLUM;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
if (material->two_sided) { /*---- CHK_MAT_TWO_SIDE ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_TWO_SIDE;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
if (material->map_decal) { /*---- CHK_MAT_DECAL ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_DECAL;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
if (material->is_additive) { /*---- CHK_MAT_ADDITIVE ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_ADDITIVE;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
if (material->use_wire) { /*---- CHK_MAT_WIRE ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_WIRE;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
if (material->use_wire_abs) { /*---- CHK_MAT_WIREABS ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_WIREABS;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
{ /*---- CHK_MAT_WIRE_SIZE ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_WIRE_SIZE;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, material->wire_size);
}
if (material->face_map) { /*---- CHK_MAT_FACEMAP ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_FACEMAP;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
if (material->soften) { /*---- CHK_MAT_PHONGSOFT ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_PHONGSOFT;
c.size = 6;
lib3ds_chunk_write(&c, io);
}
texture_map_write(CHK_MAT_TEXMAP, &material->texture1_map, io);
texture_map_write(CHK_MAT_TEXMASK, &material->texture1_mask, io);
texture_map_write(CHK_MAT_TEX2MAP, &material->texture2_map, io);
texture_map_write(CHK_MAT_TEX2MASK, &material->texture2_mask, io);
texture_map_write(CHK_MAT_OPACMAP, &material->opacity_map, io);
texture_map_write(CHK_MAT_OPACMASK, &material->opacity_mask, io);
texture_map_write(CHK_MAT_BUMPMAP, &material->bump_map, io);
texture_map_write(CHK_MAT_BUMPMASK, &material->bump_mask, io);
texture_map_write(CHK_MAT_SPECMAP, &material->specular_map, io);
texture_map_write(CHK_MAT_SPECMASK, &material->specular_mask, io);
texture_map_write(CHK_MAT_SHINMAP, &material->shininess_map, io);
texture_map_write(CHK_MAT_SHINMASK, &material->shininess_mask, io);
texture_map_write(CHK_MAT_SELFIMAP, &material->self_illum_map, io);
texture_map_write(CHK_MAT_SELFIMASK, &material->self_illum_mask, io);
texture_map_write(CHK_MAT_REFLMAP, &material->reflection_map, io);
texture_map_write(CHK_MAT_REFLMASK, &material->reflection_mask, io);
{ /*---- CHK_MAT_ACUBIC ----*/
Lib3dsChunk c;
c.chunk = CHK_MAT_ACUBIC;
c.size = 18;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_intb(io, 0);
lib3ds_io_write_intb(io, (int8_t)material->autorefl_map_anti_alias);
lib3ds_io_write_intw(io, (int16_t)material->autorefl_map_flags);
lib3ds_io_write_intd(io, material->autorefl_map_size);
lib3ds_io_write_intd(io, material->autorefl_map_frame_step);
}
lib3ds_chunk_write_end(&c, io);
}

View File

@@ -0,0 +1,62 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
float
lib3ds_math_ease(float fp, float fc, float fn, float ease_from, float ease_to) {
double s, step;
double tofrom;
double a;
s = step = (float)(fc - fp) / (fn - fp);
tofrom = ease_to + ease_from;
if (tofrom != 0.0) {
if (tofrom > 1.0) {
ease_to = (float)(ease_to / tofrom);
ease_from = (float)(ease_from / tofrom);
}
a = 1.0 / (2.0 - (ease_to + ease_from));
if (step < ease_from) s = a / ease_from * step * step;
else {
if ((1.0 - ease_to) <= step) {
step = 1.0 - step;
s = 1.0 - a / ease_to * step * step;
} else {
s = ((2.0 * step) - ease_from) * a;
}
}
}
return((float)s);
}
void
lib3ds_math_cubic_interp(float *v, float *a, float *p, float *q, float *b, int n, float t) {
float x, y, z, w;
int i;
x = 2 * t * t * t - 3 * t * t + 1;
y = -2 * t * t * t + 3 * t * t;
z = t * t * t - 2 * t * t + t;
w = t * t * t - t * t;
for (i = 0; i < n; ++i) {
v[i] = x * a[i] + y * b[i] + z * p[i] + w * q[i];
}
}

View File

@@ -0,0 +1,466 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
/*!
* Clear a matrix to all zeros.
*
* \param m Matrix to be cleared.
*/
void
lib3ds_matrix_zero(float m[4][4]) {
int i, j;
for (i = 0; i < 4; i++) {
for (j = 0; j < 4; j++) m[i][j] = 0.0f;
}
}
/*!
* Set a matrix to identity.
*
* \param m Matrix to be set.
*/
void
lib3ds_matrix_identity(float m[4][4]) {
int i, j;
for (i = 0; i < 4; i++) {
for (j = 0; j < 4; j++) m[i][j] = 0.0;
}
for (i = 0; i < 4; i++) m[i][i] = 1.0;
}
/*!
* Copy a matrix.
*/
void
lib3ds_matrix_copy(float dest[4][4], float src[4][4]) {
memcpy(dest, src, 16 * sizeof(float));
}
/*!
* Negate a matrix -- all elements negated.
*/
void
lib3ds_matrix_neg(float m[4][4]) {
int i, j;
for (j = 0; j < 4; j++) {
for (i = 0; i < 4; i++) {
m[j][i] = -m[j][i];
}
}
}
/*!
* Transpose a matrix in place.
*/
void
lib3ds_matrix_transpose(float m[4][4]) {
int i, j;
float swp;
for (j = 0; j < 4; j++) {
for (i = j + 1; i < 4; i++) {
swp = m[j][i];
m[j][i] = m[i][j];
m[i][j] = swp;
}
}
}
/*!
* Add two matrices.
*/
void
lib3ds_matrix_add(float m[4][4], float a[4][4], float b[4][4]) {
int i, j;
for (j = 0; j < 4; j++) {
for (i = 0; i < 4; i++) {
m[j][i] = a[j][i] + b[j][i];
}
}
}
/*!
* Subtract two matrices.
*
* \param m Result.
* \param a Addend.
* \param b Minuend.
*/
void
lib3ds_matrix_sub(float m[4][4], float a[4][4], float b[4][4]) {
int i, j;
for (j = 0; j < 4; j++) {
for (i = 0; i < 4; i++) {
m[j][i] = a[j][i] - b[j][i];
}
}
}
/*!
* Multiplies a matrix by a second one (m = m * n).
*/
void
lib3ds_matrix_mult(float m[4][4], float a[4][4], float b[4][4]) {
float tmp[4][4];
int i, j, k;
float ab;
memcpy(tmp, a, 16 * sizeof(float));
for (j = 0; j < 4; j++) {
for (i = 0; i < 4; i++) {
ab = 0.0f;
for (k = 0; k < 4; k++) ab += tmp[k][i] * b[j][k];
m[j][i] = ab;
}
}
}
/*!
* Multiply a matrix by a scalar.
*
* \param m Matrix to be set.
* \param k Scalar.
*/
void
lib3ds_matrix_scalar(float m[4][4], float k) {
int i, j;
for (j = 0; j < 4; j++) {
for (i = 0; i < 4; i++) {
m[j][i] *= k;
}
}
}
static float
det2x2(
float a, float b,
float c, float d) {
return((a)*(d) - (b)*(c));
}
static float
det3x3(
float a1, float a2, float a3,
float b1, float b2, float b3,
float c1, float c2, float c3) {
return(
a1*det2x2(b2, b3, c2, c3) -
b1*det2x2(a2, a3, c2, c3) +
c1*det2x2(a2, a3, b2, b3)
);
}
/*!
* Find determinant of a matrix.
*/
float
lib3ds_matrix_det(float m[4][4]) {
float a1, a2, a3, a4, b1, b2, b3, b4, c1, c2, c3, c4, d1, d2, d3, d4;
a1 = m[0][0];
b1 = m[1][0];
c1 = m[2][0];
d1 = m[3][0];
a2 = m[0][1];
b2 = m[1][1];
c2 = m[2][1];
d2 = m[3][1];
a3 = m[0][2];
b3 = m[1][2];
c3 = m[2][2];
d3 = m[3][2];
a4 = m[0][3];
b4 = m[1][3];
c4 = m[2][3];
d4 = m[3][3];
return(
a1 * det3x3(b2, b3, b4, c2, c3, c4, d2, d3, d4) -
b1 * det3x3(a2, a3, a4, c2, c3, c4, d2, d3, d4) +
c1 * det3x3(a2, a3, a4, b2, b3, b4, d2, d3, d4) -
d1 * det3x3(a2, a3, a4, b2, b3, b4, c2, c3, c4)
);
}
/*!
* Invert a matrix in place.
*
* \param m Matrix to invert.
*
* \return LIB3DS_TRUE on success, LIB3DS_FALSE on failure.
*
* GGemsII, K.Wu, Fast Matrix Inversion
*/
int
lib3ds_matrix_inv(float m[4][4]) {
int i, j, k;
int pvt_i[4], pvt_j[4]; /* Locations of pivot elements */
float pvt_val; /* Value of current pivot element */
float hold; /* Temporary storage */
float determinat;
determinat = 1.0f;
for (k = 0; k < 4; k++) {
/* Locate k'th pivot element */
pvt_val = m[k][k]; /* Initialize for search */
pvt_i[k] = k;
pvt_j[k] = k;
for (i = k; i < 4; i++) {
for (j = k; j < 4; j++) {
if (fabs(m[i][j]) > fabs(pvt_val)) {
pvt_i[k] = i;
pvt_j[k] = j;
pvt_val = m[i][j];
}
}
}
/* Product of pivots, gives determinant when finished */
determinat *= pvt_val;
if (fabs(determinat) < LIB3DS_EPSILON) {
return(FALSE); /* Matrix is singular (zero determinant) */
}
/* "Interchange" rows (with sign change stuff) */
i = pvt_i[k];
if (i != k) { /* If rows are different */
for (j = 0; j < 4; j++) {
hold = -m[k][j];
m[k][j] = m[i][j];
m[i][j] = hold;
}
}
/* "Interchange" columns */
j = pvt_j[k];
if (j != k) { /* If columns are different */
for (i = 0; i < 4; i++) {
hold = -m[i][k];
m[i][k] = m[i][j];
m[i][j] = hold;
}
}
/* Divide column by minus pivot value */
for (i = 0; i < 4; i++) {
if (i != k) m[i][k] /= (-pvt_val) ;
}
/* Reduce the matrix */
for (i = 0; i < 4; i++) {
hold = m[i][k];
for (j = 0; j < 4; j++) {
if (i != k && j != k) m[i][j] += hold * m[k][j];
}
}
/* Divide row by pivot */
for (j = 0; j < 4; j++) {
if (j != k) m[k][j] /= pvt_val;
}
/* Replace pivot by reciprocal (at last we can touch it). */
m[k][k] = 1.0f / pvt_val;
}
/* That was most of the work, one final pass of row/column interchange */
/* to finish */
for (k = 4 - 2; k >= 0; k--) { /* Don't need to work with 1 by 1 corner*/
i = pvt_j[k]; /* Rows to swap correspond to pivot COLUMN */
if (i != k) { /* If rows are different */
for (j = 0; j < 4; j++) {
hold = m[k][j];
m[k][j] = -m[i][j];
m[i][j] = hold;
}
}
j = pvt_i[k]; /* Columns to swap correspond to pivot ROW */
if (j != k) /* If columns are different */
for (i = 0; i < 4; i++) {
hold = m[i][k];
m[i][k] = -m[i][j];
m[i][j] = hold;
}
}
return(TRUE);
}
/*!
* Apply a translation to a matrix.
*/
void
lib3ds_matrix_translate(float m[4][4], float x, float y, float z) {
int i;
for (i = 0; i < 3; i++) {
m[3][i] += m[0][i] * x + m[1][i] * y + m[2][i] * z;
}
}
/*!
* Apply scale factors to a matrix.
*/
void
lib3ds_matrix_scale(float m[4][4], float x, float y, float z) {
int i;
for (i = 0; i < 4; i++) {
m[0][i] *= x;
m[1][i] *= y;
m[2][i] *= z;
}
}
/*!
* Apply a rotation about an arbitrary axis to a matrix.
*/
void
lib3ds_matrix_rotate_quat(float m[4][4], float q[4]) {
float s, xs, ys, zs, wx, wy, wz, xx, xy, xz, yy, yz, zz, l;
float R[4][4];
l = q[0] * q[0] + q[1] * q[1] + q[2] * q[2] + q[3] * q[3];
if (fabs(l) < LIB3DS_EPSILON) {
s = 1.0f;
} else {
s = 2.0f / l;
}
xs = q[0] * s;
ys = q[1] * s;
zs = q[2] * s;
wx = q[3] * xs;
wy = q[3] * ys;
wz = q[3] * zs;
xx = q[0] * xs;
xy = q[0] * ys;
xz = q[0] * zs;
yy = q[1] * ys;
yz = q[1] * zs;
zz = q[2] * zs;
R[0][0] = 1.0f - (yy + zz);
R[1][0] = xy - wz;
R[2][0] = xz + wy;
R[0][1] = xy + wz;
R[1][1] = 1.0f - (xx + zz);
R[2][1] = yz - wx;
R[0][2] = xz - wy;
R[1][2] = yz + wx;
R[2][2] = 1.0f - (xx + yy);
R[3][0] = R[3][1] = R[3][2] = R[0][3] = R[1][3] = R[2][3] = 0.0f;
R[3][3] = 1.0f;
lib3ds_matrix_mult(m, m, R);
}
/*!
* Apply a rotation about an arbitrary axis to a matrix.
*/
void
lib3ds_matrix_rotate(float m[4][4], float angle, float ax, float ay, float az) {
float q[4];
float axis[3];
lib3ds_vector_make(axis, ax, ay, az);
lib3ds_quat_axis_angle(q, axis, angle);
lib3ds_matrix_rotate_quat(m, q);
}
/*!
* Compute a camera matrix based on position, target and roll.
*
* Generates a translate/rotate matrix that maps world coordinates
* to camera coordinates. Resulting matrix does not include perspective
* transform.
*
* \param matrix Destination matrix.
* \param pos Camera position
* \param tgt Camera target
* \param roll Roll angle
*/
void
lib3ds_matrix_camera(float matrix[4][4], float pos[3], float tgt[3], float roll) {
float M[4][4];
float x[3], y[3], z[3];
lib3ds_vector_sub(y, tgt, pos);
lib3ds_vector_normalize(y);
if (y[0] != 0. || y[1] != 0) {
z[0] = 0;
z[1] = 0;
z[2] = 1.0;
} else { /* Special case: looking straight up or down z axis */
z[0] = -1.0;
z[1] = 0;
z[2] = 0;
}
lib3ds_vector_cross(x, y, z);
lib3ds_vector_cross(z, x, y);
lib3ds_vector_normalize(x);
lib3ds_vector_normalize(z);
lib3ds_matrix_identity(M);
M[0][0] = x[0];
M[1][0] = x[1];
M[2][0] = x[2];
M[0][1] = y[0];
M[1][1] = y[1];
M[2][1] = y[2];
M[0][2] = z[0];
M[1][2] = z[1];
M[2][2] = z[2];
lib3ds_matrix_identity(matrix);
lib3ds_matrix_rotate(matrix, roll, 0, 1, 0);
lib3ds_matrix_mult(matrix, matrix, M);
lib3ds_matrix_translate(matrix, -pos[0], -pos[1], -pos[2]);
}

View File

@@ -0,0 +1,677 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
/*!
* Create and return a new empty mesh object.
*
* Mesh is initialized with the name and an identity matrix; all
* other fields are zero.
*
* See Lib3dsFaceFlag for definitions of per-face flags.
*
* \param name Mesh name. Must not be NULL. Must be < 64 characters.
*
* \return mesh object or NULL on error.
*/
Lib3dsMesh*
lib3ds_mesh_new(const char *name) {
Lib3dsMesh *mesh;
assert(name);
assert(strlen(name) < 64);
mesh = (Lib3dsMesh*) calloc(sizeof(Lib3dsMesh), 1);
if (!mesh) {
return (0);
}
strcpy(mesh->name, name);
lib3ds_matrix_identity(mesh->matrix);
mesh->map_type = LIB3DS_MAP_NONE;
return (mesh);
}
/*!
* Free a mesh object and all of its resources.
*
* \param mesh Mesh object to be freed.
*/
void
lib3ds_mesh_free(Lib3dsMesh *mesh) {
lib3ds_mesh_resize_vertices(mesh, 0, 0, 0);
lib3ds_mesh_resize_faces(mesh, 0);
memset(mesh, 0, sizeof(Lib3dsMesh));
free(mesh);
}
void
lib3ds_mesh_resize_vertices(Lib3dsMesh *mesh, int nvertices, int use_texcos, int use_flags) {
assert(mesh);
mesh->vertices = (float (*)[3])lib3ds_util_realloc_array(mesh->vertices, mesh->nvertices, nvertices, 3 * sizeof(float));
mesh->texcos = (float (*)[2])lib3ds_util_realloc_array(
mesh->texcos,
mesh->texcos? mesh->nvertices : 0,
use_texcos? nvertices : 0,
2 * sizeof(float)
);
mesh->vflags = (unsigned short*)lib3ds_util_realloc_array(
mesh->vflags,
mesh->vflags? mesh->nvertices : 0,
use_flags? nvertices : 0,
2 * sizeof(float)
);
mesh->nvertices = (unsigned short)nvertices;
}
void
lib3ds_mesh_resize_faces(Lib3dsMesh *mesh, int nfaces) {
int i;
assert(mesh);
mesh->faces = (Lib3dsFace *)lib3ds_util_realloc_array(mesh->faces, mesh->nfaces, nfaces, sizeof(Lib3dsFace));
for (i = mesh->nfaces; i < nfaces; ++i) {
mesh->faces[i].material = -1;
}
mesh->nfaces = (unsigned short)nfaces;
}
/*!
* Find the bounding box of a mesh object.
*
* \param mesh The mesh object
* \param bmin Returned bounding box
* \param bmax Returned bounding box
*/
void
lib3ds_mesh_bounding_box(Lib3dsMesh *mesh, float bmin[3], float bmax[3]) {
int i;
bmin[0] = bmin[1] = bmin[2] = FLT_MAX;
bmax[0] = bmax[1] = bmax[2] = -FLT_MAX;
for (i = 0; i < mesh->nvertices; ++i) {
lib3ds_vector_min(bmin, mesh->vertices[i]);
lib3ds_vector_max(bmax, mesh->vertices[i]);
}
}
void
lib3ds_mesh_calculate_face_normals(Lib3dsMesh *mesh, float (*face_normals)[3]) {
int i;
if (!mesh->nfaces) {
return;
}
for (i = 0; i < mesh->nfaces; ++i) {
lib3ds_vector_normal(
face_normals[i],
mesh->vertices[mesh->faces[i].index[0]],
mesh->vertices[mesh->faces[i].index[1]],
mesh->vertices[mesh->faces[i].index[2]]
);
}
}
typedef struct Lib3dsFaces {
struct Lib3dsFaces *next;
int index;
float normal[3];
} Lib3dsFaces;
/*!
* Calculates the vertex normals corresponding to the smoothing group
* settings for each face of a mesh.
*
* \param mesh A pointer to the mesh to calculate the normals for.
* \param normals A pointer to a buffer to store the calculated
* normals. The buffer must have the size:
* 3*3*sizeof(float)*mesh->nfaces.
*
* To allocate the normal buffer do for example the following:
* \code
* Lib3dsVector *normals = malloc(3*3*sizeof(float)*mesh->nfaces);
* \endcode
*
* To access the normal of the i-th vertex of the j-th face do the
* following:
* \code
* normals[3*j+i]
* \endcode
*/
void
lib3ds_mesh_calculate_vertex_normals(Lib3dsMesh *mesh, float (*normals)[3]) {
Lib3dsFaces **fl;
Lib3dsFaces *fa;
int i, j;
if (!mesh->nfaces) {
return;
}
fl = (Lib3dsFaces**)calloc(sizeof(Lib3dsFaces*), mesh->nvertices);
fa = (Lib3dsFaces*)malloc(sizeof(Lib3dsFaces) * 3 * mesh->nfaces);
for (i = 0; i < mesh->nfaces; ++i) {
for (j = 0; j < 3; ++j) {
Lib3dsFaces* l = &fa[3*i+j];
float p[3], q[3], n[3];
float len, weight;
l->index = i;
l->next = fl[mesh->faces[i].index[j]];
fl[mesh->faces[i].index[j]] = l;
lib3ds_vector_sub(p, mesh->vertices[mesh->faces[i].index[j<2? j + 1 : 0]], mesh->vertices[mesh->faces[i].index[j]]);
lib3ds_vector_sub(q, mesh->vertices[mesh->faces[i].index[j>0? j - 1 : 2]], mesh->vertices[mesh->faces[i].index[j]]);
lib3ds_vector_cross(n, p, q);
len = lib3ds_vector_length(n);
if (len > 0) {
weight = (float)atan2(len, lib3ds_vector_dot(p, q));
lib3ds_vector_scalar_mul(l->normal, n, weight / len);
} else {
lib3ds_vector_zero(l->normal);
}
}
}
for (i = 0; i < mesh->nfaces; ++i) {
Lib3dsFace *f = &mesh->faces[i];
for (j = 0; j < 3; ++j) {
float n[3];
Lib3dsFaces *p;
Lib3dsFace *pf;
assert(mesh->faces[i].index[j] < mesh->nvertices);
if (f->smoothing_group) {
unsigned smoothing_group = f->smoothing_group;
lib3ds_vector_zero(n);
for (p = fl[mesh->faces[i].index[j]]; p; p = p->next) {
pf = &mesh->faces[p->index];
if (pf->smoothing_group & f->smoothing_group)
smoothing_group |= pf->smoothing_group;
}
for (p = fl[mesh->faces[i].index[j]]; p; p = p->next) {
pf = &mesh->faces[p->index];
if (smoothing_group & pf->smoothing_group) {
lib3ds_vector_add(n, n, p->normal);
}
}
} else {
lib3ds_vector_copy(n, fa[3*i+j].normal);
}
lib3ds_vector_normalize(n);
lib3ds_vector_copy(normals[3*i+j], n);
}
}
free(fa);
free(fl);
}
static void
face_array_read(Lib3dsFile *file, Lib3dsMesh *mesh, Lib3dsIo *io) {
Lib3dsChunk c;
uint16_t chunk;
int i;
uint16_t nfaces;
lib3ds_chunk_read_start(&c, CHK_FACE_ARRAY, io);
lib3ds_mesh_resize_faces(mesh, 0);
nfaces = lib3ds_io_read_word(io);
if (nfaces) {
lib3ds_mesh_resize_faces(mesh, nfaces);
for (i = 0; i < nfaces; ++i) {
mesh->faces[i].index[0] = lib3ds_io_read_word(io);
mesh->faces[i].index[1] = lib3ds_io_read_word(io);
mesh->faces[i].index[2] = lib3ds_io_read_word(io);
mesh->faces[i].flags = lib3ds_io_read_word(io);
}
lib3ds_chunk_read_tell(&c, io);
while ((chunk = lib3ds_chunk_read_next(&c, io)) != 0) {
switch (chunk) {
case CHK_MSH_MAT_GROUP: {
char name[64];
unsigned n;
unsigned i;
int index;
int material;
lib3ds_io_read_string(io, name, 64);
material = lib3ds_file_material_by_name(file, name);
n = lib3ds_io_read_word(io);
for (i = 0; i < n; ++i) {
index = lib3ds_io_read_word(io);
if (index < mesh->nfaces) {
mesh->faces[index].material = material;
} else {
// TODO warning
}
}
break;
}
case CHK_SMOOTH_GROUP: {
int i;
for (i = 0; i < mesh->nfaces; ++i) {
mesh->faces[i].smoothing_group = lib3ds_io_read_dword(io);
}
break;
}
case CHK_MSH_BOXMAP: {
lib3ds_io_read_string(io, mesh->box_front, 64);
lib3ds_io_read_string(io, mesh->box_back, 64);
lib3ds_io_read_string(io, mesh->box_left, 64);
lib3ds_io_read_string(io, mesh->box_right, 64);
lib3ds_io_read_string(io, mesh->box_top, 64);
lib3ds_io_read_string(io, mesh->box_bottom, 64);
break;
}
default:
lib3ds_chunk_unknown(chunk,io);
}
}
}
lib3ds_chunk_read_end(&c, io);
}
void
lib3ds_mesh_read(Lib3dsFile *file, Lib3dsMesh *mesh, Lib3dsIo *io) {
Lib3dsChunk c;
uint16_t chunk;
lib3ds_chunk_read_start(&c, CHK_N_TRI_OBJECT, io);
while ((chunk = lib3ds_chunk_read_next(&c, io)) != 0) {
switch (chunk) {
case CHK_MESH_MATRIX: {
int i, j;
lib3ds_matrix_identity(mesh->matrix);
for (i = 0; i < 4; i++) {
for (j = 0; j < 3; j++) {
mesh->matrix[i][j] = lib3ds_io_read_float(io);
}
}
break;
}
case CHK_MESH_COLOR: {
mesh->color = lib3ds_io_read_byte(io);
break;
}
case CHK_POINT_ARRAY: {
int i;
uint16_t nvertices = lib3ds_io_read_word(io);
lib3ds_mesh_resize_vertices(mesh, nvertices, mesh->texcos != NULL, mesh->vflags != NULL);
for (i = 0; i < mesh->nvertices; ++i) {
lib3ds_io_read_vector(io, mesh->vertices[i]);
}
break;
}
case CHK_POINT_FLAG_ARRAY: {
int i;
uint16_t nflags = lib3ds_io_read_word(io);
uint16_t nvertices = (mesh->nvertices >= nflags)? mesh->nvertices : nflags;
lib3ds_mesh_resize_vertices(mesh, nvertices, mesh->texcos != NULL, 1);
for (i = 0; i < nflags; ++i) {
mesh->vflags[i] = lib3ds_io_read_word(io);
}
break;
}
case CHK_FACE_ARRAY: {
lib3ds_chunk_read_reset(&c, io);
face_array_read(file, mesh, io);
break;
}
case CHK_MESH_TEXTURE_INFO: {
int i, j;
//FIXME: mesh->map_type = lib3ds_io_read_word(io);
for (i = 0; i < 2; ++i) {
mesh->map_tile[i] = lib3ds_io_read_float(io);
}
for (i = 0; i < 3; ++i) {
mesh->map_pos[i] = lib3ds_io_read_float(io);
}
mesh->map_scale = lib3ds_io_read_float(io);
lib3ds_matrix_identity(mesh->map_matrix);
for (i = 0; i < 4; i++) {
for (j = 0; j < 3; j++) {
mesh->map_matrix[i][j] = lib3ds_io_read_float(io);
}
}
for (i = 0; i < 2; ++i) {
mesh->map_planar_size[i] = lib3ds_io_read_float(io);
}
mesh->map_cylinder_height = lib3ds_io_read_float(io);
break;
}
case CHK_TEX_VERTS: {
int i;
uint16_t ntexcos = lib3ds_io_read_word(io);
uint16_t nvertices = (mesh->nvertices >= ntexcos)? mesh->nvertices : ntexcos;;
if (!mesh->texcos) {
lib3ds_mesh_resize_vertices(mesh, nvertices, 1, mesh->vflags != NULL);
}
for (i = 0; i < ntexcos; ++i) {
mesh->texcos[i][0] = lib3ds_io_read_float(io);
mesh->texcos[i][1] = lib3ds_io_read_float(io);
}
break;
}
default:
lib3ds_chunk_unknown(chunk, io);
}
}
if (lib3ds_matrix_det(mesh->matrix) < 0.0) {
/* Flip X coordinate of vertices if mesh matrix
has negative determinant */
float inv_matrix[4][4], M[4][4];
float tmp[3];
int i;
lib3ds_matrix_copy(inv_matrix, mesh->matrix);
lib3ds_matrix_inv(inv_matrix);
lib3ds_matrix_copy(M, mesh->matrix);
lib3ds_matrix_scale(M, -1.0f, 1.0f, 1.0f);
lib3ds_matrix_mult(M, M, inv_matrix);
for (i = 0; i < mesh->nvertices; ++i) {
lib3ds_vector_transform(tmp, M, mesh->vertices[i]);
lib3ds_vector_copy(mesh->vertices[i], tmp);
}
}
lib3ds_chunk_read_end(&c, io);
}
static void
point_array_write(Lib3dsMesh *mesh, Lib3dsIo *io) {
Lib3dsChunk c;
int i;
c.chunk = CHK_POINT_ARRAY;
c.size = 8 + 12 * mesh->nvertices;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_word(io, (uint16_t) mesh->nvertices);
if (lib3ds_matrix_det(mesh->matrix) >= 0.0f) {
for (i = 0; i < mesh->nvertices; ++i) {
lib3ds_io_write_vector(io, mesh->vertices[i]);
}
} else {
/* Flip X coordinate of vertices if mesh matrix
has negative determinant */
float inv_matrix[4][4], M[4][4];
float tmp[3];
lib3ds_matrix_copy(inv_matrix, mesh->matrix);
lib3ds_matrix_inv(inv_matrix);
lib3ds_matrix_copy(M, mesh->matrix);
lib3ds_matrix_scale(M, -1.0f, 1.0f, 1.0f);
lib3ds_matrix_mult(M, M, inv_matrix);
for (i = 0; i < mesh->nvertices; ++i) {
lib3ds_vector_transform(tmp, M, mesh->vertices[i]);
lib3ds_io_write_vector(io, tmp);
}
}
}
static void
flag_array_write(Lib3dsMesh *mesh, Lib3dsIo *io) {
Lib3dsChunk c;
int i;
if (!mesh->vflags) {
return;
}
c.chunk = CHK_POINT_FLAG_ARRAY;
c.size = 8 + 2 * mesh->nvertices;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_word(io, (uint16_t) mesh->nvertices);
for (i = 0; i < mesh->nvertices; ++i) {
lib3ds_io_write_word(io, mesh->vflags[i]);
}
}
static void
face_array_write(Lib3dsFile *file, Lib3dsMesh *mesh, Lib3dsIo *io) {
Lib3dsChunk c;
if (mesh->nfaces == 0) {
return;
}
c.chunk = CHK_FACE_ARRAY;
lib3ds_chunk_write_start(&c, io);
{
int i;
lib3ds_io_write_word(io, (uint16_t) mesh->nfaces);
for (i = 0; i < mesh->nfaces; ++i) {
lib3ds_io_write_word(io, mesh->faces[i].index[0]);
lib3ds_io_write_word(io, mesh->faces[i].index[1]);
lib3ds_io_write_word(io, mesh->faces[i].index[2]);
lib3ds_io_write_word(io, mesh->faces[i].flags);
}
}
{
/*---- MSH_CHK_MAT_GROUP ----*/
Lib3dsChunk c;
int i, j;
uint16_t num;
char *matf = (char*)calloc(sizeof(char), mesh->nfaces);
((Lib3dsIoImpl*)io->impl)->tmp_mem = matf;
assert(matf);
for (i = 0; i < mesh->nfaces; ++i) {
if (!matf[i] && (mesh->faces[i].material >= 0) && (mesh->faces[i].material < file->nmaterials)) {
matf[i] = 1;
num = 1;
for (j = i + 1; j < mesh->nfaces; ++j) {
if (mesh->faces[i].material == mesh->faces[j].material) ++num;
}
c.chunk = CHK_MSH_MAT_GROUP;
c.size = 6 + (uint32_t)strlen(file->materials[mesh->faces[i].material]->name) + 1 + 2 + 2 * num;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_string(io, file->materials[mesh->faces[i].material]->name);
lib3ds_io_write_word(io, num);
lib3ds_io_write_word(io, (uint16_t) i);
for (j = i + 1; j < mesh->nfaces; ++j) {
if (mesh->faces[i].material == mesh->faces[j].material) {
lib3ds_io_write_word(io, (uint16_t) j);
matf[j] = 1;
}
}
}
}
((Lib3dsIoImpl*)io->impl)->tmp_mem = NULL;
free(matf);
}
{
/*---- SMOOTH_GROUP ----*/
Lib3dsChunk c;
int i;
c.chunk = CHK_SMOOTH_GROUP;
c.size = 6 + 4 * mesh->nfaces;
lib3ds_chunk_write(&c, io);
for (i = 0; i < mesh->nfaces; ++i) {
lib3ds_io_write_dword(io, mesh->faces[i].smoothing_group);
}
}
{
/*---- MSH_BOXMAP ----*/
Lib3dsChunk c;
if (strlen(mesh->box_front) ||
strlen(mesh->box_back) ||
strlen(mesh->box_left) ||
strlen(mesh->box_right) ||
strlen(mesh->box_top) ||
strlen(mesh->box_bottom)) {
c.chunk = CHK_MSH_BOXMAP;
lib3ds_chunk_write_start(&c, io);
lib3ds_io_write_string(io, mesh->box_front);
lib3ds_io_write_string(io, mesh->box_back);
lib3ds_io_write_string(io, mesh->box_left);
lib3ds_io_write_string(io, mesh->box_right);
lib3ds_io_write_string(io, mesh->box_top);
lib3ds_io_write_string(io, mesh->box_bottom);
lib3ds_chunk_write_end(&c, io);
}
}
lib3ds_chunk_write_end(&c, io);
}
static void
texco_array_write(Lib3dsMesh *mesh, Lib3dsIo *io) {
Lib3dsChunk c;
int i;
if (!mesh->texcos) {
return;
}
c.chunk = CHK_TEX_VERTS;
c.size = 8 + 8 * mesh->nvertices;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_word(io, mesh->nvertices);
for (i = 0; i < mesh->nvertices; ++i) {
lib3ds_io_write_float(io, mesh->texcos[i][0]);
lib3ds_io_write_float(io, mesh->texcos[i][1]);
}
}
void
lib3ds_mesh_write(Lib3dsFile *file, Lib3dsMesh *mesh, Lib3dsIo *io) {
Lib3dsChunk c;
c.chunk = CHK_N_TRI_OBJECT;
lib3ds_chunk_write_start(&c, io);
point_array_write(mesh, io);
texco_array_write(mesh, io);
if (mesh->map_type != LIB3DS_MAP_NONE) { /*---- LIB3DS_MESH_TEXTURE_INFO ----*/
Lib3dsChunk c;
int i, j;
c.chunk = CHK_MESH_TEXTURE_INFO;
c.size = 92;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_word(io, (uint16_t)mesh->map_type);
for (i = 0; i < 2; ++i) {
lib3ds_io_write_float(io, mesh->map_tile[i]);
}
lib3ds_io_write_vector(io, mesh->map_pos);
lib3ds_io_write_float(io, mesh->map_scale);
for (i = 0; i < 4; i++) {
for (j = 0; j < 3; j++) {
lib3ds_io_write_float(io, mesh->map_matrix[i][j]);
}
}
for (i = 0; i < 2; ++i) {
lib3ds_io_write_float(io, mesh->map_planar_size[i]);
}
lib3ds_io_write_float(io, mesh->map_cylinder_height);
}
flag_array_write(mesh, io);
{
/*---- LIB3DS_MESH_MATRIX ----*/
Lib3dsChunk c;
int i, j;
c.chunk = CHK_MESH_MATRIX;
c.size = 54;
lib3ds_chunk_write(&c, io);
for (i = 0; i < 4; i++) {
for (j = 0; j < 3; j++) {
lib3ds_io_write_float(io, mesh->matrix[i][j]);
}
}
}
if (mesh->color) { /*---- LIB3DS_MESH_COLOR ----*/
Lib3dsChunk c;
c.chunk = CHK_MESH_COLOR;
c.size = 7;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_byte(io, (uint8_t)mesh->color);
}
face_array_write(file, mesh, io);
lib3ds_chunk_write_end(&c, io);
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,294 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
/*!
* Set a quaternion to Identity
*/
void
lib3ds_quat_identity(float c[4]) {
c[0] = c[1] = c[2] = 0.0f;
c[3] = 1.0f;
}
/*!
* Copy a quaternion.
*/
void
lib3ds_quat_copy(float dest[4], float src[4]) {
int i;
for (i = 0; i < 4; ++i) {
dest[i] = src[i];
}
}
/*!
* Compute a quaternion from axis and angle.
*
* \param c Computed quaternion
* \param axis Rotation axis
* \param angle Angle of rotation, radians.
*/
void
lib3ds_quat_axis_angle(float c[4], float axis[3], float angle) {
double omega, s;
double l;
l = sqrt(axis[0] * axis[0] + axis[1] * axis[1] + axis[2] * axis[2]);
if (l < LIB3DS_EPSILON) {
c[0] = c[1] = c[2] = 0.0f;
c[3] = 1.0f;
} else {
omega = -0.5 * angle;
s = sin(omega) / l;
c[0] = (float)s * axis[0];
c[1] = (float)s * axis[1];
c[2] = (float)s * axis[2];
c[3] = (float)cos(omega);
}
}
/*!
* Negate a quaternion
*/
void
lib3ds_quat_neg(float c[4]) {
int i;
for (i = 0; i < 4; ++i) {
c[i] = -c[i];
}
}
/*!
* Compute the conjugate of a quaternion
*/
void
lib3ds_quat_cnj(float c[4]) {
int i;
for (i = 0; i < 3; ++i) {
c[i] = -c[i];
}
}
/*!
* Multiply two quaternions.
*
* \param c Result
* \param a,b Inputs
*/
void
lib3ds_quat_mul(float c[4], float a[4], float b[4]) {
float qa[4], qb[4];
lib3ds_quat_copy(qa, a);
lib3ds_quat_copy(qb, b);
c[0] = qa[3] * qb[0] + qa[0] * qb[3] + qa[1] * qb[2] - qa[2] * qb[1];
c[1] = qa[3] * qb[1] + qa[1] * qb[3] + qa[2] * qb[0] - qa[0] * qb[2];
c[2] = qa[3] * qb[2] + qa[2] * qb[3] + qa[0] * qb[1] - qa[1] * qb[0];
c[3] = qa[3] * qb[3] - qa[0] * qb[0] - qa[1] * qb[1] - qa[2] * qb[2];
}
/*!
* Multiply a quaternion by a scalar.
*/
void
lib3ds_quat_scalar(float c[4], float k) {
int i;
for (i = 0; i < 4; ++i) {
c[i] *= k;
}
}
/*!
* Normalize a quaternion.
*/
void
lib3ds_quat_normalize(float c[4]) {
double l, m;
l = sqrt(c[0] * c[0] + c[1] * c[1] + c[2] * c[2] + c[3] * c[3]);
if (fabs(l) < LIB3DS_EPSILON) {
c[0] = c[1] = c[2] = 0.0f;
c[3] = 1.0f;
} else {
int i;
m = 1.0f / l;
for (i = 0; i < 4; ++i) {
c[i] = (float)(c[i] * m);
}
}
}
/*!
* Compute the inverse of a quaternion.
*/
void
lib3ds_quat_inv(float c[4]) {
double l, m;
l = sqrt(c[0] * c[0] + c[1] * c[1] + c[2] * c[2] + c[3] * c[3]);
if (fabs(l) < LIB3DS_EPSILON) {
c[0] = c[1] = c[2] = 0.0f;
c[3] = 1.0f;
} else {
m = 1.0f / l;
c[0] = (float)(-c[0] * m);
c[1] = (float)(-c[1] * m);
c[2] = (float)(-c[2] * m);
c[3] = (float)(c[3] * m);
}
}
/*!
* Compute the dot-product of a quaternion.
*/
float
lib3ds_quat_dot(float a[4], float b[4]) {
return(a[0]*b[0] + a[1]*b[1] + a[2]*b[2] + a[3]*b[3]);
}
float
lib3ds_quat_norm(float c[4]) {
return(c[0]*c[0] + c[1]*c[1] + c[2]*c[2] + c[3]*c[3]);
}
void
lib3ds_quat_ln(float c[4]) {
double om, s, t;
s = sqrt(c[0] * c[0] + c[1] * c[1] + c[2] * c[2]);
om = atan2(s, (double)c[3]);
if (fabs(s) < LIB3DS_EPSILON) {
t = 0.0f;
} else {
t = om / s;
}
{
int i;
for (i = 0; i < 3; ++i) {
c[i] = (float)(c[i] * t);
}
c[3] = 0.0f;
}
}
void
lib3ds_quat_ln_dif(float c[4], float a[4], float b[4]) {
float invp[4];
lib3ds_quat_copy(invp, a);
lib3ds_quat_inv(invp);
lib3ds_quat_mul(c, invp, b);
lib3ds_quat_ln(c);
}
void
lib3ds_quat_exp(float c[4]) {
double om, sinom;
om = sqrt(c[0] * c[0] + c[1] * c[1] + c[2] * c[2]);
if (fabs(om) < LIB3DS_EPSILON) {
sinom = 1.0f;
} else {
sinom = sin(om) / om;
}
{
int i;
for (i = 0; i < 3; ++i) {
c[i] = (float)(c[i] * sinom);
}
c[3] = (float)cos(om);
}
}
void
lib3ds_quat_slerp(float c[4], float a[4], float b[4], float t) {
double l;
double om, sinom;
double sp, sq;
float flip = 1.0f;
int i;
l = a[0] * b[0] + a[1] * b[1] + a[2] * b[2] + a[3] * b[3];
if (l < 0) {
flip = -1.0f;
l = -l;
}
om = acos(l);
sinom = sin(om);
if (fabs(sinom) > LIB3DS_EPSILON) {
sp = sin((1.0f - t) * om) / sinom;
sq = sin(t * om) / sinom;
} else {
sp = 1.0f - t;
sq = t;
}
sq *= flip;
for (i = 0; i < 4; ++i) {
c[i] = (float)(sp * a[i] + sq * b[i]);
}
}
void
lib3ds_quat_squad(float c[4], float a[4], float p[4], float q[4], float b[4], float t) {
float ab[4];
float pq[4];
lib3ds_quat_slerp(ab, a, b, t);
lib3ds_quat_slerp(pq, p, q, t);
lib3ds_quat_slerp(c, ab, pq, 2*t*(1 - t));
}
void
lib3ds_quat_tangent(float c[4], float p[4], float q[4], float n[4]) {
float dn[4], dp[4], x[4];
int i;
lib3ds_quat_ln_dif(dn, q, n);
lib3ds_quat_ln_dif(dp, q, p);
for (i = 0; i < 4; i++) {
x[i] = -1.0f / 4.0f * (dn[i] + dp[i]);
}
lib3ds_quat_exp(x);
lib3ds_quat_mul(c, q, x);
}
void
lib3ds_quat_dump(float q[4]) {
printf("%f %f %f %f\n", q[0], q[1], q[2], q[3]);
}

View File

@@ -0,0 +1,96 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
void
lib3ds_shadow_read(Lib3dsShadow *shadow, Lib3dsIo *io) {
Lib3dsChunk c;
lib3ds_chunk_read(&c, io);
switch (c.chunk) {
case CHK_SHADOW_MAP_SIZE: {
shadow->map_size = lib3ds_io_read_intw(io);
break;
}
case CHK_LO_SHADOW_BIAS: {
shadow->low_bias = lib3ds_io_read_float(io);
break;
}
case CHK_HI_SHADOW_BIAS: {
shadow->hi_bias = lib3ds_io_read_float(io);
break;
}
case CHK_SHADOW_FILTER: {
shadow->filter = lib3ds_io_read_float(io);
break;
}
case CHK_RAY_BIAS: {
shadow->ray_bias = lib3ds_io_read_float(io);
break;
}
}
}
void
lib3ds_shadow_write(Lib3dsShadow *shadow, Lib3dsIo *io) {
if (fabs(shadow->low_bias) > LIB3DS_EPSILON) { /*---- CHK_LO_SHADOW_BIAS ----*/
Lib3dsChunk c;
c.chunk = CHK_LO_SHADOW_BIAS;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, shadow->low_bias);
}
if (fabs(shadow->hi_bias) > LIB3DS_EPSILON) { /*---- CHK_HI_SHADOW_BIAS ----*/
Lib3dsChunk c;
c.chunk = CHK_HI_SHADOW_BIAS;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, shadow->hi_bias);
}
if (shadow->map_size) { /*---- CHK_SHADOW_MAP_SIZE ----*/
Lib3dsChunk c;
c.chunk = CHK_SHADOW_MAP_SIZE;
c.size = 8;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_intw(io, shadow->map_size);
}
if (fabs(shadow->filter) > LIB3DS_EPSILON) { /*---- CHK_SHADOW_FILTER ----*/
Lib3dsChunk c;
c.chunk = CHK_SHADOW_FILTER;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, shadow->filter);
}
if (fabs(shadow->ray_bias) > LIB3DS_EPSILON) { /*---- CHK_RAY_BIAS ----*/
Lib3dsChunk c;
c.chunk = CHK_RAY_BIAS;
c.size = 10;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_float(io, shadow->ray_bias);
}
}

View File

@@ -0,0 +1,551 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
Lib3dsTrack*
lib3ds_track_new(Lib3dsTrackType type, int nkeys) {
Lib3dsTrack *track = (Lib3dsTrack*)calloc(sizeof(Lib3dsTrack), 1);
track->type = type;
lib3ds_track_resize(track, nkeys);
return track;
}
void
lib3ds_track_free(Lib3dsTrack *track) {
assert(track);
lib3ds_track_resize(track, 0);
memset(track, 0, sizeof(Lib3dsTrack));
free(track);
}
void
lib3ds_track_resize(Lib3dsTrack *track, int nkeys) {
char *p;
assert(track);
if (track->nkeys == nkeys)
return;
p = (char*)realloc(track->keys, sizeof(Lib3dsKey) * nkeys);
if (nkeys > track->nkeys) {
memset(p + (sizeof(Lib3dsKey)*track->nkeys), 0, sizeof(Lib3dsKey)*(nkeys - track->nkeys));
}
track->keys = (Lib3dsKey*)p;
track->nkeys = nkeys;
}
static void
pos_key_setup(int n, Lib3dsKey *pp, Lib3dsKey *pc, Lib3dsKey *pn, float *dd, float *ds) {
float tm, cm, cp, bm, bp, tmcm, tmcp, ksm, ksp, kdm, kdp, c;
float dt, fp, fn;
float delm[3], delp[3];
int i;
assert(pc);
fp = fn = 1.0f;
if (pp && pn) {
dt = 0.5f * (pn->frame - pp->frame);
fp = (float)(pc->frame - pp->frame) / dt;
fn = (float)(pn->frame - pc->frame) / dt;
c = (float)fabs(pc->cont);
fp = fp + c - c * fp;
fn = fn + c - c * fn;
}
cm = 1.0f - pc->cont;
tm = 0.5f * (1.0f - pc->tens);
cp = 2.0f - cm;
bm = 1.0f - pc->bias;
bp = 2.0f - bm;
tmcm = tm * cm;
tmcp = tm * cp;
ksm = tmcm * bp * fp;
ksp = tmcp * bm * fp;
kdm = tmcp * bp * fn;
kdp = tmcm * bm * fn;
for (i = 0; i < n; ++i) delm[i] = delp[i] = 0;
if (pp) {
for (i = 0; i < n; ++i) delm[i] = pc->value[i] - pp->value[i];
}
if (pn) {
for (i = 0; i < n; ++i) delp[i] = pn->value[i] - pc->value[i];
}
if (!pp) {
for (i = 0; i < n; ++i) delm[i] = delp[i];
}
if (!pn) {
for (i = 0; i < n; ++i) delp[i] = delm[i];
}
for (i = 0; i < n; ++i) {
ds[i] = ksm * delm[i] + ksp * delp[i];
dd[i] = kdm * delm[i] + kdp * delp[i];
}
}
static void
rot_key_setup(Lib3dsKey *prev, Lib3dsKey *cur, Lib3dsKey *next, float a[4], float b[4]) {
float tm, cm, cp, bm, bp, tmcm, tmcp, ksm, ksp, kdm, kdp, c;
float dt, fp, fn;
float q[4], qm[4], qp[4], qa[4], qb[4];
int i;
assert(cur);
if (prev) {
if (cur->value[3] > LIB3DS_TWOPI - LIB3DS_EPSILON) {
lib3ds_quat_axis_angle(qm, cur->value, 0.0f);
lib3ds_quat_ln(qm);
} else {
lib3ds_quat_copy(q, prev->value);
if (lib3ds_quat_dot(q, cur->value) < 0) lib3ds_quat_neg(q);
lib3ds_quat_ln_dif(qm, q, cur->value);
}
}
if (next) {
if (next->value[3] > LIB3DS_TWOPI - LIB3DS_EPSILON) {
lib3ds_quat_axis_angle(qp, next->value, 0.0f);
lib3ds_quat_ln(qp);
} else {
lib3ds_quat_copy(q, next->value);
if (lib3ds_quat_dot(q, cur->value) < 0) lib3ds_quat_neg(q);
lib3ds_quat_ln_dif(qp, cur->value, q);
}
}
if (!prev) lib3ds_quat_copy(qm, qp);
if (!next) lib3ds_quat_copy(qp, qm);
fp = fn = 1.0f;
cm = 1.0f - cur->cont;
if (prev && next) {
dt = 0.5f * (next->frame - prev->frame);
fp = (float)(cur->frame - prev->frame) / dt;
fn = (float)(next->frame - cur->frame) / dt;
c = (float)fabs(cur->cont);
fp = fp + c - c * fp;
fn = fn + c - c * fn;
}
tm = 0.5f * (1.0f - cur->tens);
cp = 2.0f - cm;
bm = 1.0f - cur->bias;
bp = 2.0f - bm;
tmcm = tm * cm;
tmcp = tm * cp;
ksm = 1.0f - tmcm * bp * fp;
ksp = -tmcp * bm * fp;
kdm = tmcp * bp * fn;
kdp = tmcm * bm * fn - 1.0f;
for (i = 0; i < 4; i++) {
qa[i] = 0.5f * (kdm * qm[i] + kdp * qp[i]);
qb[i] = 0.5f * (ksm * qm[i] + ksp * qp[i]);
}
lib3ds_quat_exp(qa);
lib3ds_quat_exp(qb);
lib3ds_quat_mul(a, cur->value, qa);
lib3ds_quat_mul(b, cur->value, qb);
}
static void
quat_for_index(Lib3dsTrack *track, int index, float q[4]) {
float p[4];
int i;
lib3ds_quat_identity(q);
for (i = 0; i <= index; ++i) {
lib3ds_quat_axis_angle(p, track->keys[i].value, track->keys[i].value[3]);
lib3ds_quat_mul(q, p, q);
}
}
static int
find_index(Lib3dsTrack *track, float t, float *u) {
int i;
float nt;
int t0, t1;
assert(track);
assert(track->nkeys > 0);
if (track->nkeys <= 1)
return -1;
t0 = track->keys[0].frame;
t1 = track->keys[track->nkeys-1].frame;
if (track->flags & LIB3DS_TRACK_REPEAT) {
nt = (float)fmod(t - t0, t1 - t0) + t0;
} else {
nt = t;
}
if (nt <= t0) {
return -1;
}
if (nt >= t1) {
return track->nkeys;
}
for (i = 1; i < track->nkeys; ++i) {
if (nt < track->keys[i].frame)
break;
}
*u = nt - (float)track->keys[i-1].frame;
*u /= (float)(track->keys[i].frame - track->keys[i-1].frame);
assert((*u >= 0.0f) && (*u <= 1.0f));
return i;
}
static void
setup_segment(Lib3dsTrack *track, int index, Lib3dsKey *pp, Lib3dsKey *p0, Lib3dsKey *p1, Lib3dsKey *pn) {
int ip, in;
pp->frame = pn->frame = -1;
if (index >= 2) {
ip = index - 2;
*pp = track->keys[index - 2];
} else {
if (track->flags & LIB3DS_TRACK_SMOOTH) {
ip = track->nkeys - 2;
*pp = track->keys[track->nkeys - 2];
pp->frame = track->keys[track->nkeys - 2].frame - (track->keys[track->nkeys - 1].frame - track->keys[0].frame);
}
else ip = -1; // Avoids a compiler warning
}
*p0 = track->keys[index - 1];
*p1 = track->keys[index];
if (index < (int)track->nkeys - 1) {
in = index + 1;
*pn = track->keys[index + 1];
} else {
if (track->flags & LIB3DS_TRACK_SMOOTH) {
in = 1;
*pn = track->keys[1];
pn->frame = track->keys[1].frame + (track->keys[track->nkeys-1].frame - track->keys[0].frame);
}
}
if (track->type == LIB3DS_TRACK_QUAT) {
float q[4];
if (pp->frame >= 0) {
quat_for_index(track, ip, pp->value);
} else {
lib3ds_quat_identity(pp->value);
}
quat_for_index(track, index - 1, p0->value);
lib3ds_quat_axis_angle(q, track->keys[index].value, track->keys[index].value[3]);
lib3ds_quat_mul(p1->value, q, p0->value);
if (pn->frame >= 0) {
lib3ds_quat_axis_angle(q, track->keys[in].value, track->keys[in].value[3]);
lib3ds_quat_mul(pn->value, q, p1->value);
} else {
lib3ds_quat_identity(pn->value);
}
}
}
void
lib3ds_track_eval_bool(Lib3dsTrack *track, int *b, float t) {
*b = FALSE;
if (track) {
int index;
float u;
assert(track->type == LIB3DS_TRACK_BOOL);
if (!track->nkeys) {
return;
}
index = find_index(track, t, &u);
if (index < 0) {
*b = FALSE;
return;
}
if (index >= track->nkeys) {
*b = !(track->nkeys & 1);
return;
}
*b = !(index & 1);
}
}
static void
track_eval_linear(Lib3dsTrack *track, float *value, float t) {
Lib3dsKey pp, p0, p1, pn;
float u;
int index;
float dsp[3], ddp[3], dsn[3], ddn[3];
assert(track);
if (!track->nkeys) {
int i;
for (i = 0; i < track->type; ++i) value[i] = 0.0f;
return;
}
index = find_index(track, t, &u);
if (index < 0) {
int i;
for (i = 0; i < track->type; ++i) value[i] = track->keys[0].value[i];
return;
}
if (index >= track->nkeys) {
int i;
for (i = 0; i < track->type; ++i) value[i] = track->keys[track->nkeys-1].value[i];
return;
}
setup_segment(track, index, &pp, &p0, &p1, &pn);
pos_key_setup(track->type, pp.frame>=0? &pp : NULL, &p0, &p1, ddp, dsp);
pos_key_setup(track->type, &p0, &p1, pn.frame>=0? &pn : NULL, ddn, dsn);
lib3ds_math_cubic_interp(
value,
p0.value,
ddp,
dsn,
p1.value,
track->type,
u
);
}
void
lib3ds_track_eval_float(Lib3dsTrack *track, float *f, float t) {
*f = 0;
if (track) {
assert(track->type == LIB3DS_TRACK_FLOAT);
track_eval_linear(track, f, t);
}
}
void
lib3ds_track_eval_vector(Lib3dsTrack *track, float v[3], float t) {
lib3ds_vector_zero(v);
if (track) {
assert(track->type == LIB3DS_TRACK_VECTOR);
track_eval_linear(track, v, t);
}
}
void
lib3ds_track_eval_quat(Lib3dsTrack *track, float q[4], float t) {
lib3ds_quat_identity(q);
if (track) {
Lib3dsKey pp, p0, p1, pn;
float u;
int index;
float ap[4], bp[4], an[4], bn[4];
assert(track->type == LIB3DS_TRACK_QUAT);
if (!track->nkeys) {
return;
}
index = find_index(track, t, &u);
if (index < 0) {
lib3ds_quat_axis_angle(q, track->keys[0].value, track->keys[0].value[3]);
return;
}
if (index >= track->nkeys) {
quat_for_index(track, track->nkeys - 1, q);
return;
}
setup_segment(track, index, &pp, &p0, &p1, &pn);
rot_key_setup(pp.frame>=0? &pp : NULL, &p0, &p1, ap, bp);
rot_key_setup(&p0, &p1, pn.frame>=0? &pn : NULL, an, bn);
lib3ds_quat_squad(q, p0.value, ap, bn, p1.value, u);
}
}
static void
tcb_read(Lib3dsKey *key, Lib3dsIo *io) {
key->flags = lib3ds_io_read_word(io);
if (key->flags & LIB3DS_KEY_USE_TENS) {
key->tens = lib3ds_io_read_float(io);
}
if (key->flags & LIB3DS_KEY_USE_CONT) {
key->cont = lib3ds_io_read_float(io);
}
if (key->flags & LIB3DS_KEY_USE_BIAS) {
key->bias = lib3ds_io_read_float(io);
}
if (key->flags & LIB3DS_KEY_USE_EASE_TO) {
key->ease_to = lib3ds_io_read_float(io);
}
if (key->flags & LIB3DS_KEY_USE_EASE_FROM) {
key->ease_from = lib3ds_io_read_float(io);
}
}
void
lib3ds_track_read(Lib3dsTrack *track, Lib3dsIo *io) {
unsigned nkeys;
unsigned i;
track->flags = lib3ds_io_read_word(io);
lib3ds_io_read_dword(io);
lib3ds_io_read_dword(io);
nkeys = lib3ds_io_read_intd(io);
lib3ds_track_resize(track, nkeys);
switch (track->type) {
case LIB3DS_TRACK_BOOL:
for (i = 0; i < nkeys; ++i) {
track->keys[i].frame = lib3ds_io_read_intd(io);
tcb_read(&track->keys[i], io);
}
break;
case LIB3DS_TRACK_FLOAT:
for (i = 0; i < nkeys; ++i) {
track->keys[i].frame = lib3ds_io_read_intd(io);
tcb_read(&track->keys[i], io);
track->keys[i].value[0] = lib3ds_io_read_float(io);
}
break;
case LIB3DS_TRACK_VECTOR:
for (i = 0; i < nkeys; ++i) {
track->keys[i].frame = lib3ds_io_read_intd(io);
tcb_read(&track->keys[i], io);
lib3ds_io_read_vector(io, track->keys[i].value);
}
break;
case LIB3DS_TRACK_QUAT:
for (i = 0; i < nkeys; ++i) {
track->keys[i].frame = lib3ds_io_read_intd(io);
tcb_read(&track->keys[i], io);
track->keys[i].value[3] = lib3ds_io_read_float(io);
lib3ds_io_read_vector(io, track->keys[i].value);
}
break;
/*case LIB3DS_TRACK_MORPH:
for (i = 0; i < nkeys; ++i) {
track->keys[i].frame = lib3ds_io_read_intd(io);
tcb_read(&track->keys[i].tcb, io);
lib3ds_io_read_string(io, track->keys[i].data.m.name, 64);
}
break;*/
default:
break;
}
}
void
tcb_write(Lib3dsKey *key, Lib3dsIo *io) {
lib3ds_io_write_word(io, (uint16_t)key->flags);
if (key->flags & LIB3DS_KEY_USE_TENS) {
lib3ds_io_write_float(io, key->tens);
}
if (key->flags & LIB3DS_KEY_USE_CONT) {
lib3ds_io_write_float(io, key->cont);
}
if (key->flags & LIB3DS_KEY_USE_BIAS) {
lib3ds_io_write_float(io, key->bias);
}
if (key->flags & LIB3DS_KEY_USE_EASE_TO) {
lib3ds_io_write_float(io, key->ease_to);
}
if (key->flags & LIB3DS_KEY_USE_EASE_FROM) {
lib3ds_io_write_float(io, key->ease_from);
}
}
void
lib3ds_track_write(Lib3dsTrack *track, Lib3dsIo *io) {
int i;
lib3ds_io_write_word(io, (uint16_t)track->flags);
lib3ds_io_write_dword(io, 0);
lib3ds_io_write_dword(io, 0);
lib3ds_io_write_dword(io, track->nkeys);
switch (track->type) {
case LIB3DS_TRACK_BOOL:
for (i = 0; i < track->nkeys; ++i) {
lib3ds_io_write_intd(io, track->keys[i].frame);
tcb_write(&track->keys[i], io);
}
break;
case LIB3DS_TRACK_FLOAT:
for (i = 0; i < track->nkeys; ++i) {
lib3ds_io_write_intd(io, track->keys[i].frame);
tcb_write(&track->keys[i], io);
lib3ds_io_write_float(io, track->keys[i].value[0]);
}
break;
case LIB3DS_TRACK_VECTOR:
for (i = 0; i < track->nkeys; ++i) {
lib3ds_io_write_intd(io, track->keys[i].frame);
tcb_write(&track->keys[i], io);
lib3ds_io_write_vector(io, track->keys[i].value);
}
break;
case LIB3DS_TRACK_QUAT:
for (i = 0; i < track->nkeys; ++i) {
lib3ds_io_write_intd(io, track->keys[i].frame);
tcb_write(&track->keys[i], io);
lib3ds_io_write_float(io, track->keys[i].value[3]);
lib3ds_io_write_vector(io, track->keys[i].value);
}
break;
/*case LIB3DS_TRACK_MORPH:
for (i = 0; i < track->nkeys; ++i) {
lib3ds_io_write_intd(io, track->keys[i].frame);
tcb_write(&track->keys[i].tcb, io);
lib3ds_io_write_string(io, track->keys[i].data.m.name);
}
break;*/
}
}

View File

@@ -0,0 +1,89 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
void* lib3ds_util_realloc_array(void *ptr, int old_size, int new_size, int element_size) {
if (!ptr)
old_size = 0;
if (old_size != new_size) {
ptr = realloc(ptr, element_size * new_size);
if (old_size < new_size) {
memset((char*)ptr + element_size * old_size, 0, element_size * (new_size - old_size));
}
}
return ptr;
}
void lib3ds_util_reserve_array(void ***ptr, int *n, int *size, int new_size, int force, Lib3dsFreeFunc free_func) {
assert(ptr && n && size);
if ((*size < new_size) || force) {
if (force && free_func) {
int i;
for (i = new_size; i < *n; ++i) {
free_func((*ptr)[i]);
(*ptr)[i] = 0;
}
}
*ptr = (void**)realloc(*ptr, sizeof(void*) * new_size);
*size = new_size;
if (*n > new_size) {
*n = new_size;
}
}
}
void lib3ds_util_insert_array(void ***ptr, int *n, int *size, void *element, int index) {
int i;
assert(ptr && n && size && element);
i = ((index >= 0) && (index < *n)) ? index : *n;
if (i >= *size) {
int new_size = 2 * (*size);
#ifdef _DEBUG
if (new_size < 1) {
new_size = 1;
}
#else
if (new_size < 32) {
new_size = 32;
}
#endif
lib3ds_util_reserve_array(ptr, n, size, new_size, FALSE, NULL);
}
assert(*ptr);
if (i < *n) {
memmove(&(*ptr)[i+1], &(*ptr)[i], sizeof(void*) * (*n - i));
}
(*ptr)[i] = element;
*n = *n + 1;
}
void lib3ds_util_remove_array(void ***ptr, int *n, int index, Lib3dsFreeFunc free_func) {
assert(ptr && n);
if ((index >= 0) && (index < *n)) {
assert(*ptr);
free_func((*ptr)[index]);
if (index < *n - 1) {
memmove(&(*ptr)[index], &(*ptr)[index+1], sizeof(void*) * (*n - index - 1));
}
*n = *n - 1;
}
}

View File

@@ -0,0 +1,246 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
void
lib3ds_vector_make(float c[3], float x, float y, float z) {
c[0] = x;
c[1] = y;
c[2] = z;
}
void
lib3ds_vector_zero(float c[3]) {
int i;
for (i = 0; i < 3; ++i) {
c[i] = 0.0f;
}
}
void
lib3ds_vector_copy(float dst[3], float src[3]) {
int i;
for (i = 0; i < 3; ++i) {
dst[i] = src[i];
}
}
/*!
* Add two vectors.
*
* \param c Result.
* \param a First addend.
* \param b Second addend.
*/
void
lib3ds_vector_add(float c[3], float a[3], float b[3]) {
int i;
for (i = 0; i < 3; ++i) {
c[i] = a[i] + b[i];
}
}
/*!
* Subtract two vectors.
*
* \param c Result.
* \param a Addend.
* \param b Minuend.
*/
void
lib3ds_vector_sub(float c[3], float a[3], float b[3]) {
int i;
for (i = 0; i < 3; ++i) {
c[i] = a[i] - b[i];
}
}
/*!
* Multiply a vector by a scalar.
*
* \param c Vector to be multiplied.
* \param k Scalar.
*/
void
lib3ds_vector_scalar_mul(float c[3], float a[3], float k) {
int i;
for (i = 0; i < 3; ++i) {
c[i] = a[i] * k;
}
}
/*!
* Compute cross product.
*
* \param c Result.
* \param a First vector.
* \param b Second vector.
*/
void
lib3ds_vector_cross(float c[3], float a[3], float b[3]) {
c[0] = a[1] * b[2] - a[2] * b[1];
c[1] = a[2] * b[0] - a[0] * b[2];
c[2] = a[0] * b[1] - a[1] * b[0];
}
/*!
* Compute dot product.
*
* \param a First vector.
* \param b Second vector.
*
* \return Dot product.
*/
float
lib3ds_vector_dot(float a[3], float b[3]) {
return(a[0]*b[0] + a[1]*b[1] + a[2]*b[2]);
}
/*!
* Compute length of vector.
*
* Computes |c| = sqrt(x*x + y*y + z*z)
*
* \param c Vector to compute.
*
* \return Length of vector.
*/
float
lib3ds_vector_length(float c[3]) {
return((float)sqrt(c[0]*c[0] + c[1]*c[1] + c[2]*c[2]));
}
/*!
* Normalize a vector.
*
* Scales a vector so that its length is 1.0.
*
* \param c Vector to normalize.
*/
void
lib3ds_vector_normalize(float c[3]) {
float l, m;
l = (float)sqrt(c[0] * c[0] + c[1] * c[1] + c[2] * c[2]);
if (fabs(l) < LIB3DS_EPSILON) {
if ((c[0] >= c[1]) && (c[0] >= c[2])) {
c[0] = 1.0f;
c[1] = c[2] = 0.0f;
} else
if (c[1] >= c[2]) {
c[1] = 1.0f;
c[0] = c[2] = 0.0f;
} else {
c[2] = 1.0f;
c[0] = c[1] = 0.0f;
}
} else {
m = 1.0f / l;
c[0] *= m;
c[1] *= m;
c[2] *= m;
}
}
/*!
* Compute a vector normal to two line segments.
*
* Computes the normal vector to the lines b-a and b-c.
*
* \param n Returned normal vector.
* \param a Endpoint of first line.
* \param b Base point of both lines.
* \param c Endpoint of second line.
*/
void
lib3ds_vector_normal(float n[3], float a[3], float b[3], float c[3]) {
float p[3], q[3];
lib3ds_vector_sub(p, c, b);
lib3ds_vector_sub(q, a, b);
lib3ds_vector_cross(n, p, q);
lib3ds_vector_normalize(n);
}
/*!
* Multiply a point by a transformation matrix.
*
* Applies the given transformation matrix to the given point. With some
* transformation matrices, a vector may also be transformed.
*
* \param c Result.
* \param m Transformation matrix.
* \param a Input point.
*/
void
lib3ds_vector_transform(float c[3], float m[4][4], float a[3]) {
c[0] = m[0][0] * a[0] + m[1][0] * a[1] + m[2][0] * a[2] + m[3][0];
c[1] = m[0][1] * a[0] + m[1][1] * a[1] + m[2][1] * a[2] + m[3][1];
c[2] = m[0][2] * a[0] + m[1][2] * a[1] + m[2][2] * a[2] + m[3][2];
}
/*!
* c[i] = min(c[i], a[i]);
*
* Computes minimum values of x,y,z independently.
*/
void
lib3ds_vector_min(float c[3], float a[3]) {
int i;
for (i = 0; i < 3; ++i) {
if (a[i] < c[i]) {
c[i] = a[i];
}
}
}
/*!
* c[i] = max(c[i], a[i]);
*
* Computes maximum values of x,y,z independently.
*/
void
lib3ds_vector_max(float c[3], float a[3]) {
int i;
for (i = 0; i < 3; ++i) {
if (a[i] > c[i]) {
c[i] = a[i];
}
}
}
void
lib3ds_vector_dump(float c[3]) {
fprintf(stderr, "%f %f %f\n", c[0], c[1], c[2]);
}

View File

@@ -0,0 +1,296 @@
/*
Copyright (C) 1996-2008 by Jan Eric Kyprianidis <www.kyprianidis.com>
All rights reserved.
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 2.1 of the License, or
(at your option) any later version.
Thisprogram 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 "lib3ds_impl.h"
void
lib3ds_viewport_read(Lib3dsViewport *viewport, Lib3dsIo *io) {
Lib3dsChunk c;
uint16_t chunk;
memset(viewport, 0, sizeof(*viewport));
lib3ds_chunk_read_start(&c, 0, io);
switch (c.chunk) {
case CHK_VIEWPORT_LAYOUT: {
int cur = 0;
viewport->layout_style = lib3ds_io_read_word(io);
viewport->layout_active = lib3ds_io_read_intw(io);
lib3ds_io_read_intw(io);
viewport->layout_swap = lib3ds_io_read_intw(io);
lib3ds_io_read_intw(io);
viewport->layout_swap_prior = lib3ds_io_read_intw(io);
viewport->layout_swap_view = lib3ds_io_read_intw(io);
lib3ds_chunk_read_tell(&c, io);
while ((chunk = lib3ds_chunk_read_next(&c, io)) != 0) {
switch (chunk) {
case CHK_VIEWPORT_SIZE: {
viewport->layout_position[0] = lib3ds_io_read_word(io);
viewport->layout_position[1] = lib3ds_io_read_word(io);
viewport->layout_size[0] = lib3ds_io_read_word(io);
viewport->layout_size[1] = lib3ds_io_read_word(io);
break;
}
case CHK_VIEWPORT_DATA_3: {
if (cur < LIB3DS_LAYOUT_MAX_VIEWS) {
lib3ds_io_read_intw(io);
viewport->layout_views[cur].axis_lock = lib3ds_io_read_word(io);
viewport->layout_views[cur].position[0] = lib3ds_io_read_intw(io);
viewport->layout_views[cur].position[1] = lib3ds_io_read_intw(io);
viewport->layout_views[cur].size[0] = lib3ds_io_read_intw(io);
viewport->layout_views[cur].size[1] = lib3ds_io_read_intw(io);
viewport->layout_views[cur].type = lib3ds_io_read_word(io);
viewport->layout_views[cur].zoom = lib3ds_io_read_float(io);
lib3ds_io_read_vector(io, viewport->layout_views[cur].center);
viewport->layout_views[cur].horiz_angle = lib3ds_io_read_float(io);
viewport->layout_views[cur].vert_angle = lib3ds_io_read_float(io);
lib3ds_io_read(io, viewport->layout_views[cur].camera, 11);
++cur;
}
break;
}
case CHK_VIEWPORT_DATA:
/* 3DS R2 & R3 chunk unsupported */
break;
default:
lib3ds_chunk_unknown(chunk, io);
}
}
break;
}
case CHK_DEFAULT_VIEW: {
while ((chunk = lib3ds_chunk_read_next(&c, io)) != 0) {
switch (chunk) {
case CHK_VIEW_TOP: {
viewport->default_type = LIB3DS_VIEW_TOP;
lib3ds_io_read_vector(io, viewport->default_position);
viewport->default_width = lib3ds_io_read_float(io);
break;
}
case CHK_VIEW_BOTTOM: {
viewport->default_type = LIB3DS_VIEW_BOTTOM;
lib3ds_io_read_vector(io, viewport->default_position);
viewport->default_width = lib3ds_io_read_float(io);
break;
}
case CHK_VIEW_LEFT: {
viewport->default_type = LIB3DS_VIEW_LEFT;
lib3ds_io_read_vector(io, viewport->default_position);
viewport->default_width = lib3ds_io_read_float(io);
break;
}
case CHK_VIEW_RIGHT: {
viewport->default_type = LIB3DS_VIEW_RIGHT;
lib3ds_io_read_vector(io, viewport->default_position);
viewport->default_width = lib3ds_io_read_float(io);
break;
}
case CHK_VIEW_FRONT: {
viewport->default_type = LIB3DS_VIEW_FRONT;
lib3ds_io_read_vector(io, viewport->default_position);
viewport->default_width = lib3ds_io_read_float(io);
break;
}
case CHK_VIEW_BACK: {
viewport->default_type = LIB3DS_VIEW_BACK;
lib3ds_io_read_vector(io, viewport->default_position);
viewport->default_width = lib3ds_io_read_float(io);
break;
}
case CHK_VIEW_USER: {
viewport->default_type = LIB3DS_VIEW_USER;
lib3ds_io_read_vector(io, viewport->default_position);
viewport->default_width = lib3ds_io_read_float(io);
viewport->default_horiz_angle = lib3ds_io_read_float(io);
viewport->default_vert_angle = lib3ds_io_read_float(io);
viewport->default_roll_angle = lib3ds_io_read_float(io);
break;
}
case CHK_VIEW_CAMERA: {
viewport->default_type = LIB3DS_VIEW_CAMERA;
lib3ds_io_read(io, viewport->default_camera, 11);
break;
}
default:
lib3ds_chunk_unknown(chunk, io);
}
}
break;
}
}
lib3ds_chunk_read_end(&c, io);
}
void
lib3ds_viewport_write(Lib3dsViewport *viewport, Lib3dsIo *io) {
if (viewport->layout_nviews) {
Lib3dsChunk c;
int i;
c.chunk = CHK_VIEWPORT_LAYOUT;
lib3ds_chunk_write_start(&c, io);
lib3ds_io_write_word(io, (uint16_t)viewport->layout_style);
lib3ds_io_write_intw(io, (int16_t)viewport->layout_active);
lib3ds_io_write_intw(io, (int16_t)0);
lib3ds_io_write_intw(io, (int16_t)viewport->layout_swap);
lib3ds_io_write_intw(io, (int16_t)0);
lib3ds_io_write_intw(io, (int16_t)viewport->layout_swap_prior);
lib3ds_io_write_intw(io, (int16_t)viewport->layout_swap_view);
{
Lib3dsChunk c;
c.chunk = CHK_VIEWPORT_SIZE;
c.size = 14;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_intw(io, viewport->layout_position[0]);
lib3ds_io_write_intw(io, viewport->layout_position[1]);
lib3ds_io_write_intw(io, viewport->layout_size[0]);
lib3ds_io_write_intw(io, viewport->layout_size[1]);
}
for (i = 0; i < viewport->layout_nviews; ++i) {
Lib3dsChunk c;
c.chunk = CHK_VIEWPORT_DATA_3;
c.size = 55;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_intw(io, 0);
lib3ds_io_write_word(io, (uint16_t)viewport->layout_views[i].axis_lock);
lib3ds_io_write_intw(io, (int16_t)viewport->layout_views[i].position[0]);
lib3ds_io_write_intw(io, (int16_t)viewport->layout_views[i].position[1]);
lib3ds_io_write_intw(io, (int16_t)viewport->layout_views[i].size[0]);
lib3ds_io_write_intw(io, (int16_t)viewport->layout_views[i].size[1]);
lib3ds_io_write_word(io, (int16_t)viewport->layout_views[i].type);
lib3ds_io_write_float(io, viewport->layout_views[i].zoom);
lib3ds_io_write_vector(io, viewport->layout_views[i].center);
lib3ds_io_write_float(io, viewport->layout_views[i].horiz_angle);
lib3ds_io_write_float(io, viewport->layout_views[i].vert_angle);
lib3ds_io_write(io, viewport->layout_views[i].camera, 11);
}
lib3ds_chunk_write_end(&c, io);
}
if (viewport->default_type) {
Lib3dsChunk c;
c.chunk = CHK_DEFAULT_VIEW;
lib3ds_chunk_write_start(&c, io);
switch (viewport->default_type) {
case LIB3DS_VIEW_TOP: {
Lib3dsChunk c;
c.chunk = CHK_VIEW_TOP;
c.size = 22;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_vector(io, viewport->default_position);
lib3ds_io_write_float(io, viewport->default_width);
break;
}
case LIB3DS_VIEW_BOTTOM: {
Lib3dsChunk c;
c.chunk = CHK_VIEW_BOTTOM;
c.size = 22;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_vector(io, viewport->default_position);
lib3ds_io_write_float(io, viewport->default_width);
break;
}
case LIB3DS_VIEW_LEFT: {
Lib3dsChunk c;
c.chunk = CHK_VIEW_LEFT;
c.size = 22;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_vector(io, viewport->default_position);
lib3ds_io_write_float(io, viewport->default_width);
break;
}
case LIB3DS_VIEW_RIGHT: {
Lib3dsChunk c;
c.chunk = CHK_VIEW_RIGHT;
c.size = 22;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_vector(io, viewport->default_position);
lib3ds_io_write_float(io, viewport->default_width);
break;
}
case LIB3DS_VIEW_FRONT: {
Lib3dsChunk c;
c.chunk = CHK_VIEW_FRONT;
c.size = 22;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_vector(io, viewport->default_position);
lib3ds_io_write_float(io, viewport->default_width);
break;
}
case LIB3DS_VIEW_BACK: {
Lib3dsChunk c;
c.chunk = CHK_VIEW_BACK;
c.size = 22;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_vector(io, viewport->default_position);
lib3ds_io_write_float(io, viewport->default_width);
break;
}
case LIB3DS_VIEW_USER: {
Lib3dsChunk c;
c.chunk = CHK_VIEW_USER;
c.size = 34;
lib3ds_chunk_write(&c, io);
lib3ds_io_write_vector(io, viewport->default_position);
lib3ds_io_write_float(io, viewport->default_width);
lib3ds_io_write_float(io, viewport->default_horiz_angle);
lib3ds_io_write_float(io, viewport->default_vert_angle);
lib3ds_io_write_float(io, viewport->default_roll_angle);
break;
}
case LIB3DS_VIEW_CAMERA: {
Lib3dsChunk c;
c.chunk = CHK_VIEW_CAMERA;
c.size = 17;
lib3ds_chunk_write(&c, io);
lib3ds_io_write(io, viewport->default_camera, 11);
break;
}
}
lib3ds_chunk_write_end(&c, io);
}
}

View File

@@ -1,47 +0,0 @@
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#define LIB3DS_EXPORT
#include "lib3ds_float.h"
/*!
* \defgroup float Floating Point Mathematics
*
* \author J.E. Hoffmann <je-h@gmx.net>
*/
/*!
* \ingroup float
*/
Lib3dsFloat
lib3ds_float_cubic(Lib3dsFloat a, Lib3dsFloat p, Lib3dsFloat q, Lib3dsFloat b, Lib3dsFloat t)
{
Lib3dsDouble x,y,z,w;
x=2*t*t*t - 3*t*t + 1;
y=-2*t*t*t + 3*t*t;
z=t*t*t - 2*t*t + t;
w=t*t*t - t*t;
return((Lib3dsFloat)(x*a + y*b + z*p + w*q));
}

View File

@@ -1,41 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_FLOAT_H
#define INCLUDED_LIB3DS_FLOAT_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TYPES_H
#include "types.h"
#endif
#ifdef __cplusplus
extern "C" {
#endif
extern LIB3DSAPI Lib3dsFloat lib3ds_float_cubic(Lib3dsFloat a, Lib3dsFloat p,
Lib3dsFloat q, Lib3dsFloat b, Lib3dsFloat t);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -1,429 +0,0 @@
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#define LIB3DS_EXPORT
#include "light.h"
#include "chunk.h"
#include "readwrite.h"
#include <stdlib.h>
#include <math.h>
#include <string.h>
#include "config.h"
#ifdef WITH_DMALLOC
#include <dmalloc.h>
#endif
/*!
* \defgroup light Lights
*
* \author J.E. Hoffmann <je-h@gmx.net>
*/
/*!
\typedef Lib3dsLight
\ingroup light
\sa _Lib3dsLight
*/
/*!
* \ingroup light
*/
Lib3dsLight*
lib3ds_light_new(const char *name)
{
Lib3dsLight *light;
ASSERT(name);
ASSERT(strlen(name)<64);
light=(Lib3dsLight*)calloc(sizeof(Lib3dsLight), 1);
if (!light) {
return(0);
}
strcpy(light->name, name);
return(light);
}
/*!
* \ingroup light
*/
void
lib3ds_light_free(Lib3dsLight *light)
{
memset(light, 0, sizeof(Lib3dsLight));
free(light);
}
/*!
* \ingroup light
*/
void
lib3ds_light_dump(Lib3dsLight *light)
{
ASSERT(light);
printf(" name: %s\n", light->name);
printf(" spot_light: %s\n", light->spot_light ? "yes" : "no");
printf(" see_cone: %s\n", light->see_cone ? "yes" : "no");
printf(" color: (%f, %f, %f)\n",
light->color[0], light->color[1], light->color[2]);
printf(" position (%f, %f, %f)\n",
light->position[0], light->position[1], light->position[2]);
printf(" spot (%f, %f, %f)\n",
light->spot[0], light->spot[1], light->spot[2]);
printf(" roll: %f\n", light->roll);
printf(" off: %s\n", light->off ? "yes" : "no");
printf(" outer_range: %f\n", light->outer_range);
printf(" inner_range: %f\n", light->inner_range);
printf(" multiplier: %f\n", light->multiplier);
printf(" attenuation: %f\n", light->attenuation);
printf(" rectangular_spot: %s\n", light->rectangular_spot ? "yes" : "no");
printf(" shadowed: %s\n", light->shadowed ? "yes" : "no");
printf(" shadow_bias: %f\n", light->shadow_bias);
printf(" shadow_filter: %f\n", light->shadow_filter);
printf(" shadow_size: %d\n", light->shadow_size);
printf(" spot_aspect: %f\n", light->spot_aspect);
printf(" use_projector: %s\n", light->use_projector ? "yes" : "no");
printf(" projector: %s\n", light->projector);
printf(" spot_overshoot: %i\n", static_cast<int>(light->spot_overshoot));
printf(" ray_shadows: %s\n", light->ray_shadows ? "yes" : "no");
printf(" ray_bias: %f\n", light->ray_bias);
printf(" hot_spot: %f\n", light->hot_spot);
printf(" fall_off: %f\n", light->fall_off);
printf("\n");
}
/*!
* \ingroup light
*/
static Lib3dsBool
spotlight_read(Lib3dsLight *light, iostream *strm)
{
Lib3dsChunk c;
Lib3dsWord chunk;
int i;
if (!lib3ds_chunk_read_start(&c, LIB3DS_DL_SPOTLIGHT, strm)) {
return(LIB3DS_FALSE);
}
light->spot_light=LIB3DS_TRUE;
for (i=0; i<3; ++i) {
light->spot[i]=lib3ds_float_read(strm);
}
light->hot_spot = lib3ds_float_read(strm);
light->fall_off = lib3ds_float_read(strm);
lib3ds_chunk_read_tell(&c, strm);
while ((chunk=lib3ds_chunk_read_next(&c, strm))!=0) {
switch (chunk) {
case LIB3DS_DL_SPOT_ROLL:
{
light->roll=lib3ds_float_read(strm);
}
break;
case LIB3DS_DL_SHADOWED:
{
light->shadowed=LIB3DS_TRUE;
}
break;
case LIB3DS_DL_LOCAL_SHADOW2:
{
light->shadow_bias=lib3ds_float_read(strm);
light->shadow_filter=lib3ds_float_read(strm);
light->shadow_size=lib3ds_intw_read(strm);
}
break;
case LIB3DS_DL_SEE_CONE:
{
light->see_cone=LIB3DS_TRUE;
}
break;
case LIB3DS_DL_SPOT_RECTANGULAR:
{
light->rectangular_spot=LIB3DS_TRUE;
}
break;
case LIB3DS_DL_SPOT_ASPECT:
{
light->spot_aspect=lib3ds_float_read(strm);
}
break;
case LIB3DS_DL_SPOT_PROJECTOR:
{
light->use_projector=LIB3DS_TRUE;
if (!lib3ds_string_read(light->projector, 64, strm)) {
return(LIB3DS_FALSE);
}
}
case LIB3DS_DL_SPOT_OVERSHOOT:
{
light->spot_overshoot=LIB3DS_TRUE;
}
break;
case LIB3DS_DL_RAY_BIAS:
{
light->ray_bias=lib3ds_float_read(strm);
}
break;
case LIB3DS_DL_RAYSHAD:
{
light->ray_shadows=LIB3DS_TRUE;
}
break;
default:
lib3ds_chunk_unknown(chunk);
}
}
lib3ds_chunk_read_end(&c, strm);
return(LIB3DS_TRUE);
}
/*!
* \ingroup light
*/
Lib3dsBool
lib3ds_light_read(Lib3dsLight *light, iostream * strm)
{
Lib3dsChunk c;
Lib3dsWord chunk;
if (!lib3ds_chunk_read_start(&c, LIB3DS_N_DIRECT_LIGHT, strm)) {
return(LIB3DS_FALSE);
}
{
int i;
for (i=0; i<3; ++i) {
light->position[i]=lib3ds_float_read(strm);
}
}
lib3ds_chunk_read_tell(&c, strm);
while ((chunk=lib3ds_chunk_read_next(&c, strm))!=0) {
switch (chunk) {
case LIB3DS_COLOR_F:
{
int i;
for (i=0; i<3; ++i) {
light->color[i]=lib3ds_float_read(strm);
}
}
break;
case LIB3DS_DL_OFF:
{
light->off=LIB3DS_TRUE;
}
break;
case LIB3DS_DL_OUTER_RANGE:
{
light->outer_range=lib3ds_float_read(strm);
}
break;
case LIB3DS_DL_INNER_RANGE:
{
light->inner_range=lib3ds_float_read(strm);
}
break;
case LIB3DS_DL_MULTIPLIER:
{
light->multiplier=lib3ds_float_read(strm);
}
break;
case LIB3DS_DL_EXCLUDE:
{
/* FIXME: */
lib3ds_chunk_unknown(chunk);
}
case LIB3DS_DL_ATTENUATE:
{
light->attenuation=lib3ds_float_read(strm);
}
break;
case LIB3DS_DL_SPOTLIGHT:
{
lib3ds_chunk_read_reset(&c, strm);
if (!spotlight_read(light, strm)) {
return(LIB3DS_FALSE);
}
}
break;
default:
lib3ds_chunk_unknown(chunk);
}
}
lib3ds_chunk_read_end(&c, strm);
return(LIB3DS_TRUE);
}
/*!
* \ingroup light
*/
Lib3dsBool
lib3ds_light_write(Lib3dsLight *light, iostream *strm)
{
Lib3dsChunk c;
c.chunk=LIB3DS_N_DIRECT_LIGHT;
if (!lib3ds_chunk_write_start(&c,strm)) {
return(LIB3DS_FALSE);
}
lib3ds_vector_write(light->position, strm);
{ /*---- LIB3DS_COLOR_F ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_COLOR_F;
c.size=18;
lib3ds_chunk_write(&c, strm);
lib3ds_rgb_write(light->color,strm);
}
if (light->off) { /*---- LIB3DS_DL_OFF ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_DL_OFF;
c.size=6;
lib3ds_chunk_write(&c, strm);
}
{ /*---- LIB3DS_DL_OUTER_RANGE ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_DL_OUTER_RANGE;
c.size=10;
lib3ds_chunk_write(&c, strm);
lib3ds_float_write(light->outer_range,strm);
}
{ /*---- LIB3DS_DL_INNER_RANGE ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_DL_INNER_RANGE;
c.size=10;
lib3ds_chunk_write(&c, strm);
lib3ds_float_write(light->inner_range,strm);
}
{ /*---- LIB3DS_DL_MULTIPLIER ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_DL_MULTIPLIER;
c.size=10;
lib3ds_chunk_write(&c, strm);
lib3ds_float_write(light->multiplier, strm);
}
if (light->attenuation) { /*---- LIB3DS_DL_ATTENUATE ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_DL_ATTENUATE;
c.size=6;
lib3ds_chunk_write(&c, strm);
}
if (light->spot_light) {
Lib3dsChunk c;
c.chunk=LIB3DS_DL_SPOTLIGHT;
if (!lib3ds_chunk_write_start(&c,strm)) {
return(LIB3DS_FALSE);
}
lib3ds_vector_write(light->spot, strm);
lib3ds_float_write(light->hot_spot, strm);
lib3ds_float_write(light->fall_off, strm);
{ /*---- LIB3DS_DL_SPOT_ROLL ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_DL_SPOT_ROLL;
c.size=10;
lib3ds_chunk_write(&c, strm);
lib3ds_float_write(light->roll,strm);
}
if (light->shadowed) { /*---- LIB3DS_DL_SHADOWED ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_DL_SHADOWED;
c.size=6;
lib3ds_chunk_write(&c, strm);
}
if ((fabs(light->shadow_bias)>LIB3DS_EPSILON) ||
(fabs(light->shadow_filter)>LIB3DS_EPSILON) ||
(light->shadow_size!=0)) { /*---- LIB3DS_DL_LOCAL_SHADOW2 ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_DL_LOCAL_SHADOW2;
c.size=16;
lib3ds_chunk_write(&c, strm);
lib3ds_float_write(light->shadow_bias,strm);
lib3ds_float_write(light->shadow_filter,strm);
lib3ds_intw_write(light->shadow_size,strm);
}
if (light->see_cone) { /*---- LIB3DS_DL_SEE_CONE ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_DL_SEE_CONE;
c.size=6;
lib3ds_chunk_write(&c, strm);
}
if (light->rectangular_spot) { /*---- LIB3DS_DL_SPOT_RECTANGULAR ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_DL_SPOT_RECTANGULAR;
c.size=6;
lib3ds_chunk_write(&c, strm);
}
if (fabs(light->spot_aspect)>LIB3DS_EPSILON) { /*---- LIB3DS_DL_SPOT_ASPECT ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_DL_SPOT_ASPECT;
c.size=10;
lib3ds_chunk_write(&c, strm);
lib3ds_float_write(light->spot_aspect,strm);
}
if (light->use_projector) { /*---- LIB3DS_DL_SPOT_PROJECTOR ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_DL_SPOT_PROJECTOR;
c.size=10;
lib3ds_chunk_write(&c, strm);
lib3ds_string_write(light->projector,strm);
}
if (light->spot_overshoot) { /*---- LIB3DS_DL_SPOT_OVERSHOOT ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_DL_SPOT_OVERSHOOT;
c.size=6;
lib3ds_chunk_write(&c, strm);
}
if (fabs(light->ray_bias)>LIB3DS_EPSILON) { /*---- LIB3DS_DL_RAY_BIAS ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_DL_RAY_BIAS;
c.size=10;
lib3ds_chunk_write(&c, strm);
lib3ds_float_write(light->ray_bias,strm);
}
if (light->ray_shadows) { /*---- LIB3DS_DL_RAYSHAD ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_DL_RAYSHAD;
c.size=6;
lib3ds_chunk_write(&c, strm);
}
if (!lib3ds_chunk_write_end(&c,strm)) {
return(LIB3DS_FALSE);
}
}
if (!lib3ds_chunk_write_end(&c,strm)) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}

View File

@@ -1,82 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_LIGHT_H
#define INCLUDED_LIB3DS_LIGHT_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TYPES_H
#include "types.h"
#endif
#include <iostream>
using namespace std;
#ifdef __cplusplus
extern "C" {
#endif
/*!
* Light
* \ingroup light
*/
struct _Lib3dsLight {
Lib3dsLight *next;
char name[64];
Lib3dsBool spot_light;
Lib3dsBool see_cone;
Lib3dsRgb color;
Lib3dsVector position;
Lib3dsVector spot;
Lib3dsFloat roll;
Lib3dsBool off;
Lib3dsFloat outer_range;
Lib3dsFloat inner_range;
Lib3dsFloat multiplier;
/*const char** excludes;*/
Lib3dsFloat attenuation;
Lib3dsBool rectangular_spot;
Lib3dsBool shadowed;
Lib3dsFloat shadow_bias;
Lib3dsFloat shadow_filter;
Lib3dsIntw shadow_size;
Lib3dsFloat spot_aspect;
Lib3dsBool use_projector;
char projector[64];
Lib3dsIntd spot_overshoot;
Lib3dsBool ray_shadows;
Lib3dsFloat ray_bias;
Lib3dsFloat hot_spot;
Lib3dsFloat fall_off;
};
extern LIB3DSAPI Lib3dsLight* lib3ds_light_new(const char *name);
extern LIB3DSAPI void lib3ds_light_free(Lib3dsLight *mesh);
extern LIB3DSAPI void lib3ds_light_dump(Lib3dsLight *light);
extern LIB3DSAPI Lib3dsBool lib3ds_light_read(Lib3dsLight *light, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_light_write(Lib3dsLight *light, iostream *strm);
#ifdef __cplusplus
}
#endif
#endif

File diff suppressed because it is too large Load Diff

View File

@@ -1,171 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_MATERIAL_H
#define INCLUDED_LIB3DS_MATERIAL_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TYPES_H
#include "types.h"
#endif
#include <iostream>
using namespace std;
#ifdef __cplusplus
extern "C" {
#endif
/*!
* \ingroup material
*/
typedef enum _Lib3dsTextureMapFlags {
LIB3DS_DECALE =0x0001,
LIB3DS_MIRROR =0x0002,
LIB3DS_NEGATE =0x0004,
LIB3DS_NO_TILE =0x0008,
LIB3DS_SUMMED_AREA =0x0010,
LIB3DS_ALPHA_SOURCE =0x0020,
LIB3DS_TINT =0x0040,
LIB3DS_IGNORE_ALPHA =0x0080,
LIB3DS_RGB_TINT =0x0100
} Lib3dsTextureMapFlags;
/*!
* Mateial texture map
* \ingroup material
*/
typedef struct _Lib3dsTextureMap {
char name[64];
Lib3dsDword flags;
Lib3dsFloat percent;
Lib3dsFloat blur;
Lib3dsFloat scale[2];
Lib3dsFloat offset[2];
Lib3dsFloat rotation;
Lib3dsRgb tint_1;
Lib3dsRgb tint_2;
Lib3dsRgb tint_r;
Lib3dsRgb tint_g;
Lib3dsRgb tint_b;
} Lib3dsTextureMap;
/*!
* \ingroup material
*/
typedef enum _Lib3dsAutoReflMapFlags {
LIB3DS_USE_REFL_MAP =0x0001,
LIB3DS_READ_FIRST_FRAME_ONLY =0x0004,
LIB3DS_FLAT_MIRROR =0x0008
} Lib3dsAutoReflectionMapFlags;
/*!
* \ingroup material
*/
typedef enum _Lib3dsAutoReflMapAntiAliasLevel {
LIB3DS_ANTI_ALIAS_NONE =0,
LIB3DS_ANTI_ALIAS_LOW =1,
LIB3DS_ANTI_ALIAS_MEDIUM =2,
LIB3DS_ANTI_ALIAS_HIGH =3
} Lib3dsAutoReflMapAntiAliasLevel;
/*!
* Auto reflection map settings
* \ingroup material
*/
typedef struct _Lib3dsAutoReflMap {
Lib3dsDword flags;
Lib3dsIntd level;
Lib3dsIntd size;
Lib3dsIntd frame_step;
} Lib3dsAutoReflMap;
/*!
* \ingroup material
*/
typedef enum _Lib3dsMaterialShading {
LIB3DS_WIRE_FRAME =0,
LIB3DS_FLAT =1,
LIB3DS_GOURAUD =2,
LIB3DS_PHONG =3,
LIB3DS_METAL =4
} Lib3dsMaterialShading;
/*!
* Material
* \ingroup material
*/
struct _Lib3dsMaterial {
Lib3dsUserData user;
Lib3dsMaterial *next;
char name[64];
Lib3dsRgba ambient;
Lib3dsRgba diffuse;
Lib3dsRgba specular;
Lib3dsFloat shininess;
Lib3dsFloat shin_strength;
Lib3dsBool use_blur;
Lib3dsFloat blur;
Lib3dsFloat transparency;
Lib3dsFloat falloff;
Lib3dsBool additive;
Lib3dsBool use_falloff;
Lib3dsBool self_illum;
Lib3dsIntw shading;
Lib3dsBool soften;
Lib3dsBool face_map;
Lib3dsBool two_sided;
Lib3dsBool map_decal;
Lib3dsBool use_wire;
Lib3dsBool use_wire_abs;
Lib3dsFloat wire_size;
Lib3dsTextureMap texture1_map;
Lib3dsTextureMap texture1_mask;
Lib3dsTextureMap texture2_map;
Lib3dsTextureMap texture2_mask;
Lib3dsTextureMap opacity_map;
Lib3dsTextureMap opacity_mask;
Lib3dsTextureMap bump_map;
Lib3dsTextureMap bump_mask;
Lib3dsTextureMap specular_map;
Lib3dsTextureMap specular_mask;
Lib3dsTextureMap shininess_map;
Lib3dsTextureMap shininess_mask;
Lib3dsTextureMap self_illum_map;
Lib3dsTextureMap self_illum_mask;
Lib3dsTextureMap reflection_map;
Lib3dsTextureMap reflection_mask;
Lib3dsAutoReflMap autorefl_map;
};
extern LIB3DSAPI Lib3dsMaterial* lib3ds_material_new();
extern LIB3DSAPI void lib3ds_material_free(Lib3dsMaterial *material);
extern LIB3DSAPI void lib3ds_material_dump(Lib3dsMaterial *material);
extern LIB3DSAPI Lib3dsBool lib3ds_material_read(Lib3dsMaterial *material, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_material_write(Lib3dsMaterial *material, iostream *strm);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -1,643 +0,0 @@
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#define LIB3DS_EXPORT
#include "matrix.h"
#include "quat.h"
#include "vector.h"
#include <string.h>
#include <math.h>
/*!
* \defgroup matrix Matrix Mathematics
*
* \author J.E. Hoffmann <je-h@gmx.net>
*/
/*!
* \typedef Lib3dsMatrix
* \ingroup matrix
*/
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_zero(Lib3dsMatrix m)
{
int i,j;
for (i=0; i<4; i++) {
for (j=0; j<4; j++) m[i][j]=0.0f;
}
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_identity(Lib3dsMatrix m)
{
int i,j;
for (i=0; i<4; i++) {
for (j=0; j<4; j++) m[i][j]=0.0;
}
for (i=0; i<4; i++) m[i][i]=1.0;
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_copy(Lib3dsMatrix dest, Lib3dsMatrix src)
{
memcpy(dest, src, sizeof(Lib3dsMatrix));
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_neg(Lib3dsMatrix m)
{
int i,j;
for (j=0; j<4; j++) {
for (i=0; i<4; i++) {
m[j][i]=-m[j][i];
}
}
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_abs(Lib3dsMatrix m)
{
int i,j;
for (j=0; j<4; j++) {
for (i=0; i<4; i++) {
m[j][i]=(Lib3dsFloat)fabs(m[j][i]);
}
}
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_transpose(Lib3dsMatrix m)
{
int i,j;
Lib3dsFloat swp;
for (j=0; j<4; j++) {
for (i=j+1; i<4; i++) {
swp=m[j][i];
m[j][i]=m[i][j];
m[i][j]=swp;
}
}
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_add(Lib3dsMatrix m, Lib3dsMatrix a, Lib3dsMatrix b)
{
int i,j;
for (j=0; j<4; j++) {
for (i=0; i<4; i++) {
m[j][i]=a[j][i]+b[j][i];
}
}
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_sub(Lib3dsMatrix m, Lib3dsMatrix a, Lib3dsMatrix b)
{
int i,j;
for (j=0; j<4; j++) {
for (i=0; i<4; i++) {
m[j][i]=a[j][i]-b[j][i];
}
}
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_mul(Lib3dsMatrix m, Lib3dsMatrix a, Lib3dsMatrix b)
{
int i,j,k;
Lib3dsFloat ab;
for (j=0; j<4; j++) {
for (i=0; i<4; i++) {
ab=0.0f;
for (k=0; k<4; k++) ab+=a[k][i]*b[j][k];
m[j][i]=ab;
}
}
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_scalar(Lib3dsMatrix m, Lib3dsFloat k)
{
int i,j;
for (j=0; j<4; j++) {
for (i=0; i<4; i++) {
m[j][i]*=k;
}
}
}
static Lib3dsFloat
det2x2(
Lib3dsFloat a, Lib3dsFloat b,
Lib3dsFloat c, Lib3dsFloat d)
{
return((a)*(d)-(b)*(c));
}
static Lib3dsFloat
det3x3(
Lib3dsFloat a1, Lib3dsFloat a2, Lib3dsFloat a3,
Lib3dsFloat b1, Lib3dsFloat b2, Lib3dsFloat b3,
Lib3dsFloat c1, Lib3dsFloat c2, Lib3dsFloat c3)
{
return(
a1*det2x2(b2,b3,c2,c3)-
b1*det2x2(a2,a3,c2,c3)+
c1*det2x2(a2,a3,b2,b3)
);
}
/*!
* \ingroup matrix
*/
Lib3dsFloat
lib3ds_matrix_det(Lib3dsMatrix m)
{
Lib3dsFloat a1,a2,a3,a4,b1,b2,b3,b4,c1,c2,c3,c4,d1,d2,d3,d4;
a1 = m[0][0];
b1 = m[1][0];
c1 = m[2][0];
d1 = m[3][0];
a2 = m[0][1];
b2 = m[1][1];
c2 = m[2][1];
d2 = m[3][1];
a3 = m[0][2];
b3 = m[1][2];
c3 = m[2][2];
d3 = m[3][2];
a4 = m[0][3];
b4 = m[1][3];
c4 = m[2][3];
d4 = m[3][3];
return(
a1 * det3x3(b2, b3, b4, c2, c3, c4, d2, d3, d4)-
b1 * det3x3(a2, a3, a4, c2, c3, c4, d2, d3, d4)+
c1 * det3x3(a2, a3, a4, b2, b3, b4, d2, d3, d4)-
d1 * det3x3(a2, a3, a4, b2, b3, b4, c2, c3, c4)
);
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_adjoint(Lib3dsMatrix m)
{
Lib3dsFloat a1,a2,a3,a4,b1,b2,b3,b4,c1,c2,c3,c4,d1,d2,d3,d4;
a1 = m[0][0];
b1 = m[1][0];
c1 = m[2][0];
d1 = m[3][0];
a2 = m[0][1];
b2 = m[1][1];
c2 = m[2][1];
d2 = m[3][1];
a3 = m[0][2];
b3 = m[1][2];
c3 = m[2][2];
d3 = m[3][2];
a4 = m[0][3];
b4 = m[1][3];
c4 = m[2][3];
d4 = m[3][3];
m[0][0]= det3x3 (b2, b3, b4, c2, c3, c4, d2, d3, d4);
m[0][1]= -det3x3 (a2, a3, a4, c2, c3, c4, d2, d3, d4);
m[0][2]= det3x3 (a2, a3, a4, b2, b3, b4, d2, d3, d4);
m[0][3]= -det3x3 (a2, a3, a4, b2, b3, b4, c2, c3, c4);
m[1][0]= -det3x3 (b1, b3, b4, c1, c3, c4, d1, d3, d4);
m[1][1]= det3x3 (a1, a3, a4, c1, c3, c4, d1, d3, d4);
m[1][2]= -det3x3 (a1, a3, a4, b1, b3, b4, d1, d3, d4);
m[1][3]= det3x3 (a1, a3, a4, b1, b3, b4, c1, c3, c4);
m[2][0]= det3x3 (b1, b2, b4, c1, c2, c4, d1, d2, d4);
m[2][1]= -det3x3 (a1, a2, a4, c1, c2, c4, d1, d2, d4);
m[2][2]= det3x3 (a1, a2, a4, b1, b2, b4, d1, d2, d4);
m[2][3]= -det3x3 (a1, a2, a4, b1, b2, b4, c1, c2, c4);
m[3][0]= -det3x3 (b1, b2, b3, c1, c2, c3, d1, d2, d3);
m[3][1]= det3x3 (a1, a2, a3, c1, c2, c3, d1, d2, d3);
m[3][2]= -det3x3 (a1, a2, a3, b1, b2, b3, d1, d2, d3);
m[3][3]= det3x3 (a1, a2, a3, b1, b2, b3, c1, c2, c3);
}
/*!
* \ingroup matrix
*
* GGemsII, K.Wu, Fast Matrix Inversion
*/
Lib3dsBool
lib3ds_matrix_inv(Lib3dsMatrix m)
{
int i,j,k;
int pvt_i[4], pvt_j[4]; /* Locations of pivot elements */
Lib3dsFloat pvt_val; /* Value of current pivot element */
Lib3dsFloat hold; /* Temporary storage */
Lib3dsFloat determinat;
determinat = 1.0f;
for (k=0; k<4; k++) {
/* Locate k'th pivot element */
pvt_val=m[k][k]; /* Initialize for search */
pvt_i[k]=k;
pvt_j[k]=k;
for (i=k; i<4; i++) {
for (j=k; j<4; j++) {
if (fabs(m[i][j]) > fabs(pvt_val)) {
pvt_i[k]=i;
pvt_j[k]=j;
pvt_val=m[i][j];
}
}
}
/* Product of pivots, gives determinant when finished */
determinat*=pvt_val;
if (fabs(determinat)<LIB3DS_EPSILON) {
return(LIB3DS_FALSE); /* Matrix is singular (zero determinant) */
}
/* "Interchange" rows (with sign change stuff) */
i=pvt_i[k];
if (i!=k) { /* If rows are different */
for (j=0; j<4; j++) {
hold=-m[k][j];
m[k][j]=m[i][j];
m[i][j]=hold;
}
}
/* "Interchange" columns */
j=pvt_j[k];
if (j!=k) { /* If columns are different */
for (i=0; i<4; i++) {
hold=-m[i][k];
m[i][k]=m[i][j];
m[i][j]=hold;
}
}
/* Divide column by minus pivot value */
for (i=0; i<4; i++) {
if (i!=k) m[i][k]/=( -pvt_val) ;
}
/* Reduce the matrix */
for (i=0; i<4; i++) {
hold = m[i][k];
for (j=0; j<4; j++) {
if (i!=k && j!=k) m[i][j]+=hold*m[k][j];
}
}
/* Divide row by pivot */
for (j=0; j<4; j++) {
if (j!=k) m[k][j]/=pvt_val;
}
/* Replace pivot by reciprocal (at last we can touch it). */
m[k][k] = 1.0f/pvt_val;
}
/* That was most of the work, one final pass of row/column interchange */
/* to finish */
for (k=4-2; k>=0; k--) { /* Don't need to work with 1 by 1 corner*/
i=pvt_j[k]; /* Rows to swap correspond to pivot COLUMN */
if (i!=k) { /* If rows are different */
for(j=0; j<4; j++) {
hold = m[k][j];
m[k][j]=-m[i][j];
m[i][j]=hold;
}
}
j=pvt_i[k]; /* Columns to swap correspond to pivot ROW */
if (j!=k) /* If columns are different */
for (i=0; i<4; i++) {
hold=m[i][k];
m[i][k]=-m[i][j];
m[i][j]=hold;
}
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_translate_xyz(Lib3dsMatrix m, Lib3dsFloat x, Lib3dsFloat y, Lib3dsFloat z)
{
int i;
for (i=0; i<3; i++) {
m[3][i]+= m[0][i]*x + m[1][i]*y + m[2][i]*z;
}
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_translate(Lib3dsMatrix m, Lib3dsVector t)
{
int i;
for (i=0; i<3; i++) {
m[3][i]+= m[0][i]*t[0] + m[1][i]*t[1] + m[2][i]*t[2];
}
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_scale_xyz(Lib3dsMatrix m, Lib3dsFloat x, Lib3dsFloat y, Lib3dsFloat z)
{
int i;
for (i=0; i<4; i++) {
m[0][i]*=x;
m[1][i]*=y;
m[2][i]*=z;
}
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_scale(Lib3dsMatrix m, Lib3dsVector s)
{
int i;
for (i=0; i<4; i++) {
m[0][i]*=s[0];
m[1][i]*=s[1];
m[2][i]*=s[2];
}
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_rotate_x(Lib3dsMatrix m, Lib3dsFloat phi)
{
Lib3dsFloat SinPhi,CosPhi;
Lib3dsFloat a1[4],a2[4];
SinPhi=(Lib3dsFloat)sin(phi);
CosPhi=(Lib3dsFloat)cos(phi);
memcpy(a1,m[1],4*sizeof(Lib3dsFloat));
memcpy(a2,m[2],4*sizeof(Lib3dsFloat));
m[1][0]=CosPhi*a1[0]+SinPhi*a2[0];
m[1][1]=CosPhi*a1[1]+SinPhi*a2[1];
m[1][2]=CosPhi*a1[2]+SinPhi*a2[2];
m[1][3]=CosPhi*a1[3]+SinPhi*a2[3];
m[2][0]=-SinPhi*a1[0]+CosPhi*a2[0];
m[2][1]=-SinPhi*a1[1]+CosPhi*a2[1];
m[2][2]=-SinPhi*a1[2]+CosPhi*a2[2];
m[2][3]=-SinPhi*a1[3]+CosPhi*a2[3];
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_rotate_y(Lib3dsMatrix m, Lib3dsFloat phi)
{
Lib3dsFloat SinPhi,CosPhi;
Lib3dsFloat a0[4],a2[4];
SinPhi=(Lib3dsFloat)sin(phi);
CosPhi=(Lib3dsFloat)cos(phi);
memcpy(a0,m[0],4*sizeof(Lib3dsFloat));
memcpy(a2,m[2],4*sizeof(Lib3dsFloat));
m[0][0]=CosPhi*a0[0]-SinPhi*a2[0];
m[0][1]=CosPhi*a0[1]-SinPhi*a2[1];
m[0][2]=CosPhi*a0[2]-SinPhi*a2[2];
m[0][3]=CosPhi*a0[3]-SinPhi*a2[3];
m[2][0]=SinPhi*a0[0]+CosPhi*a2[0];
m[2][1]=SinPhi*a0[1]+CosPhi*a2[1];
m[2][2]=SinPhi*a0[2]+CosPhi*a2[2];
m[2][3]=SinPhi*a0[3]+CosPhi*a2[3];
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_rotate_z(Lib3dsMatrix m, Lib3dsFloat phi)
{
Lib3dsFloat SinPhi,CosPhi;
Lib3dsFloat a0[4],a1[4];
SinPhi=(Lib3dsFloat)sin(phi);
CosPhi=(Lib3dsFloat)cos(phi);
memcpy(a0,m[0],4*sizeof(Lib3dsFloat));
memcpy(a1,m[1],4*sizeof(Lib3dsFloat));
m[0][0]=CosPhi*a0[0]+SinPhi*a1[0];
m[0][1]=CosPhi*a0[1]+SinPhi*a1[1];
m[0][2]=CosPhi*a0[2]+SinPhi*a1[2];
m[0][3]=CosPhi*a0[3]+SinPhi*a1[3];
m[1][0]=-SinPhi*a0[0]+CosPhi*a1[0];
m[1][1]=-SinPhi*a0[1]+CosPhi*a1[1];
m[1][2]=-SinPhi*a0[2]+CosPhi*a1[2];
m[1][3]=-SinPhi*a0[3]+CosPhi*a1[3];
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_rotate(Lib3dsMatrix m, Lib3dsQuat q)
{
Lib3dsFloat s,xs,ys,zs,wx,wy,wz,xx,xy,xz,yy,yz,zz,l;
Lib3dsMatrix a,b;
lib3ds_matrix_copy(a, m);
l=q[0]*q[0] + q[1]*q[1] + q[2]*q[2] + q[3]*q[3];
if (fabs(l)<LIB3DS_EPSILON) {
s=1.0f;
}
else {
s=2.0f/l;
}
xs = q[0] * s; ys = q[1] * s; zs = q[2] * s;
wx = q[3] * xs; wy = q[3] * ys; wz = q[3] * zs;
xx = q[0] * xs; xy = q[0] * ys; xz = q[0] * zs;
yy = q[1] * ys; yz = q[1] * zs; zz = q[2] * zs;
b[0][0]=1.0f - (yy +zz);
b[1][0]=xy - wz;
b[2][0]=xz + wy;
b[0][1]=xy + wz;
b[1][1]=1.0f - (xx +zz);
b[2][1]=yz - wx;
b[0][2]=xz - wy;
b[1][2]=yz + wx;
b[2][2]=1.0f - (xx + yy);
b[3][0]=b[3][1]=b[3][2]=b[0][3]=b[1][3]=b[2][3]=0.0f;
b[3][3]=1.0f;
lib3ds_matrix_mul(m,a,b);
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_rotate_axis(Lib3dsMatrix m, Lib3dsVector axis, Lib3dsFloat angle)
{
Lib3dsQuat q;
lib3ds_quat_axis_angle(q,axis,angle);
lib3ds_matrix_rotate(m,q);
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_camera(Lib3dsMatrix matrix, Lib3dsVector pos,
Lib3dsVector tgt, Lib3dsFloat roll)
{
Lib3dsMatrix M,R;
Lib3dsVector x, y, z;
lib3ds_vector_sub(y, tgt, pos);
lib3ds_vector_normalize(y);
z[0] = 0;
z[1] = 0;
z[2] = 1.0;
lib3ds_vector_cross(x, y, z);
lib3ds_vector_cross(z, x, y);
lib3ds_vector_normalize(x);
lib3ds_vector_normalize(y);
lib3ds_matrix_identity(M);
M[0][0] = x[0];
M[1][0] = x[1];
M[2][0] = x[2];
M[0][1] = y[0];
M[1][1] = y[1];
M[2][1] = y[2];
M[0][2] = z[0];
M[1][2] = z[1];
M[2][2] = z[2];
lib3ds_matrix_identity(R);
lib3ds_matrix_rotate_y(R, roll);
lib3ds_matrix_mul(matrix, R,M);
lib3ds_matrix_translate_xyz(matrix, -pos[0],-pos[1],-pos[2]);
}
/*!
* \ingroup matrix
*/
void
lib3ds_matrix_dump(Lib3dsMatrix matrix)
{
int i,j;
for (i=0; i<4; ++i) {
for (j=0; j<3; ++j) {
printf("%f ", matrix[j][i]);
}
printf("%f\n", matrix[j][i]);
}
}

View File

@@ -1,67 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_MATRIX_H
#define INCLUDED_LIB3DS_MATRIX_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TYPES_H
#include "types.h"
#endif
#ifdef __cplusplus
extern "C" {
#endif
extern LIB3DSAPI void lib3ds_matrix_zero(Lib3dsMatrix m);
extern LIB3DSAPI void lib3ds_matrix_identity(Lib3dsMatrix m);
extern LIB3DSAPI void lib3ds_matrix_copy(Lib3dsMatrix dest, Lib3dsMatrix src);
extern LIB3DSAPI void lib3ds_matrix_neg(Lib3dsMatrix m);
extern LIB3DSAPI void lib3ds_matrix_abs(Lib3dsMatrix m);
extern LIB3DSAPI void lib3ds_matrix_transpose(Lib3dsMatrix m);
extern LIB3DSAPI void lib3ds_matrix_add(Lib3dsMatrix m, Lib3dsMatrix a, Lib3dsMatrix b);
extern LIB3DSAPI void lib3ds_matrix_sub(Lib3dsMatrix m, Lib3dsMatrix a, Lib3dsMatrix b);
extern LIB3DSAPI void lib3ds_matrix_mul(Lib3dsMatrix m, Lib3dsMatrix a, Lib3dsMatrix b);
extern LIB3DSAPI void lib3ds_matrix_scalar(Lib3dsMatrix m, Lib3dsFloat k);
extern LIB3DSAPI Lib3dsFloat lib3ds_matrix_det(Lib3dsMatrix m);
extern LIB3DSAPI void lib3ds_matrix_adjoint(Lib3dsMatrix m);
extern LIB3DSAPI Lib3dsBool lib3ds_matrix_inv(Lib3dsMatrix m);
void lib3ds_matrix_translate_xyz(Lib3dsMatrix m, Lib3dsFloat x,
Lib3dsFloat y, Lib3dsFloat z);
extern LIB3DSAPI void lib3ds_matrix_translate(Lib3dsMatrix m, Lib3dsVector t);
extern LIB3DSAPI void lib3ds_matrix_scale_xyz(Lib3dsMatrix m, Lib3dsFloat x,
Lib3dsFloat y, Lib3dsFloat z);
extern LIB3DSAPI void lib3ds_matrix_scale(Lib3dsMatrix m, Lib3dsVector s);
extern LIB3DSAPI void lib3ds_matrix_rotate_x(Lib3dsMatrix m, Lib3dsFloat phi);
extern LIB3DSAPI void lib3ds_matrix_rotate_y(Lib3dsMatrix m, Lib3dsFloat phi);
extern LIB3DSAPI void lib3ds_matrix_rotate_z(Lib3dsMatrix m, Lib3dsFloat phi);
extern LIB3DSAPI void lib3ds_matrix_rotate(Lib3dsMatrix m, Lib3dsQuat q);
extern LIB3DSAPI void lib3ds_matrix_rotate_axis(Lib3dsMatrix m,
Lib3dsVector axis, Lib3dsFloat angle);
extern LIB3DSAPI void lib3ds_matrix_camera(Lib3dsMatrix matrix, Lib3dsVector pos,
Lib3dsVector tgt, Lib3dsFloat roll);
extern LIB3DSAPI void lib3ds_matrix_dump(Lib3dsMatrix matrix);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -1,967 +0,0 @@
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#define LIB3DS_EXPORT
#include "mesh.h"
#include "readwrite.h"
#include "chunk.h"
#include "vector.h"
#include "matrix.h"
#include <stdlib.h>
#include <string.h>
#include <math.h>
#include "config.h"
#ifdef WITH_DMALLOC
#include <dmalloc.h>
#endif
/*!
* \defgroup mesh Meshes
*
* \author J.E. Hoffmann <je-h@gmx.net>
*/
static Lib3dsBool
face_array_read(Lib3dsMesh *mesh, iostream *strm)
{
Lib3dsChunk c;
Lib3dsWord chunk;
int i;
int faces;
if (!lib3ds_chunk_read_start(&c, LIB3DS_FACE_ARRAY, strm)) {
return(LIB3DS_FALSE);
}
lib3ds_mesh_free_face_list(mesh);
faces=lib3ds_word_read(strm);
if (faces) {
if (!lib3ds_mesh_new_face_list(mesh, faces)) {
LIB3DS_ERROR_LOG;
return(LIB3DS_FALSE);
}
for (i=0; i<faces; ++i) {
strcpy(mesh->faceL[i].material, "");
mesh->faceL[i].points[0]=lib3ds_word_read(strm);
mesh->faceL[i].points[1]=lib3ds_word_read(strm);
mesh->faceL[i].points[2]=lib3ds_word_read(strm);
mesh->faceL[i].flags=lib3ds_word_read(strm);
}
lib3ds_chunk_read_tell(&c, strm);
while ((chunk=lib3ds_chunk_read_next(&c, strm))!=0) {
switch (chunk) {
case LIB3DS_SMOOTH_GROUP:
{
unsigned i;
for (i=0; i<mesh->faces; ++i) {
mesh->faceL[i].smoothing=lib3ds_dword_read(strm);
}
}
break;
case LIB3DS_MSH_MAT_GROUP:
{
char name[64];
unsigned faces;
unsigned i;
unsigned index;
if (!lib3ds_string_read(name, 64, strm)) {
return(LIB3DS_FALSE);
}
faces=lib3ds_word_read(strm);
for (i=0; i<faces; ++i) {
index=lib3ds_word_read(strm);
ASSERT(index<mesh->faces);
strcpy(mesh->faceL[index].material, name);
}
}
break;
case LIB3DS_MSH_BOXMAP:
{
char name[64];
if (!lib3ds_string_read(name, 64, strm)) {
return(LIB3DS_FALSE);
}
strcpy(mesh->box_map.front, name);
if (!lib3ds_string_read(name, 64, strm)) {
return(LIB3DS_FALSE);
}
strcpy(mesh->box_map.back, name);
if (!lib3ds_string_read(name, 64, strm)) {
return(LIB3DS_FALSE);
}
strcpy(mesh->box_map.left, name);
if (!lib3ds_string_read(name, 64, strm)) {
return(LIB3DS_FALSE);
}
strcpy(mesh->box_map.right, name);
if (!lib3ds_string_read(name, 64, strm)) {
return(LIB3DS_FALSE);
}
strcpy(mesh->box_map.top, name);
if (!lib3ds_string_read(name, 64, strm)) {
return(LIB3DS_FALSE);
}
strcpy(mesh->box_map.bottom, name);
}
break;
default:
lib3ds_chunk_unknown(chunk);
}
}
}
lib3ds_chunk_read_end(&c, strm);
return(LIB3DS_TRUE);
}
/*!
* \ingroup mesh
*/
Lib3dsMesh*
lib3ds_mesh_new(const char *name)
{
Lib3dsMesh *mesh;
ASSERT(name);
ASSERT(strlen(name)<64);
mesh=(Lib3dsMesh*)calloc(sizeof(Lib3dsMesh), 1);
if (!mesh) {
return(0);
}
strcpy(mesh->name, name);
lib3ds_matrix_identity(mesh->matrix);
mesh->map_data.maptype=LIB3DS_MAP_NONE;
return(mesh);
}
/*!
* \ingroup mesh
*/
void
lib3ds_mesh_free(Lib3dsMesh *mesh)
{
lib3ds_mesh_free_point_list(mesh);
lib3ds_mesh_free_flag_list(mesh);
lib3ds_mesh_free_texel_list(mesh);
lib3ds_mesh_free_face_list(mesh);
memset(mesh, 0, sizeof(Lib3dsMesh));
free(mesh);
}
/*!
* \ingroup mesh
*/
Lib3dsBool
lib3ds_mesh_new_point_list(Lib3dsMesh *mesh, Lib3dsDword points)
{
ASSERT(mesh);
if (mesh->pointL) {
ASSERT(mesh->points);
lib3ds_mesh_free_point_list(mesh);
}
ASSERT(!mesh->pointL && !mesh->points);
mesh->points=0;
mesh->pointL=(Lib3dsPoint*)calloc(sizeof(Lib3dsPoint)*points,1);
if (!mesh->pointL) {
LIB3DS_ERROR_LOG;
return(LIB3DS_FALSE);
}
mesh->points=points;
return(LIB3DS_TRUE);
}
/*!
* \ingroup mesh
*/
void
lib3ds_mesh_free_point_list(Lib3dsMesh *mesh)
{
ASSERT(mesh);
if (mesh->pointL) {
ASSERT(mesh->points);
free(mesh->pointL);
mesh->pointL=0;
mesh->points=0;
}
else {
ASSERT(!mesh->points);
}
}
/*!
* \ingroup mesh
*/
Lib3dsBool
lib3ds_mesh_new_flag_list(Lib3dsMesh *mesh, Lib3dsDword flags)
{
ASSERT(mesh);
if (mesh->flagL) {
ASSERT(mesh->flags);
lib3ds_mesh_free_flag_list(mesh);
}
ASSERT(!mesh->flagL && !mesh->flags);
mesh->flags=0;
mesh->flagL=(Lib3dsWord*)calloc(sizeof(Lib3dsWord)*flags,1);
if (!mesh->flagL) {
LIB3DS_ERROR_LOG;
return(LIB3DS_FALSE);
}
mesh->flags=flags;
return(LIB3DS_TRUE);
}
/*!
* \ingroup mesh
*/
void
lib3ds_mesh_free_flag_list(Lib3dsMesh *mesh)
{
ASSERT(mesh);
if (mesh->flagL) {
ASSERT(mesh->flags);
free(mesh->flagL);
mesh->flagL=0;
mesh->flags=0;
}
else {
ASSERT(!mesh->flags);
}
}
/*!
* \ingroup mesh
*/
Lib3dsBool
lib3ds_mesh_new_texel_list(Lib3dsMesh *mesh, Lib3dsDword texels)
{
ASSERT(mesh);
if (mesh->texelL) {
ASSERT(mesh->texels);
lib3ds_mesh_free_texel_list(mesh);
}
ASSERT(!mesh->texelL && !mesh->texels);
mesh->texels=0;
mesh->texelL=(Lib3dsTexel*) calloc(sizeof(Lib3dsTexel)*texels,1);
if (!mesh->texelL) {
LIB3DS_ERROR_LOG;
return(LIB3DS_FALSE);
}
mesh->texels=texels;
return(LIB3DS_TRUE);
}
/*!
* \ingroup mesh
*/
void
lib3ds_mesh_free_texel_list(Lib3dsMesh *mesh)
{
ASSERT(mesh);
if (mesh->texelL) {
ASSERT(mesh->texels);
free(mesh->texelL);
mesh->texelL=0;
mesh->texels=0;
}
else {
ASSERT(!mesh->texels);
}
}
/*!
* \ingroup mesh
*/
Lib3dsBool
lib3ds_mesh_new_face_list(Lib3dsMesh *mesh, Lib3dsDword faces)
{
ASSERT(mesh);
if (mesh->faceL) {
ASSERT(mesh->faces);
lib3ds_mesh_free_face_list(mesh);
}
ASSERT(!mesh->faceL && !mesh->faces);
mesh->faces=0;
mesh->faceL=(Lib3dsFace*)calloc(sizeof(Lib3dsFace)*faces,1);
if (!mesh->faceL) {
LIB3DS_ERROR_LOG;
return(LIB3DS_FALSE);
}
mesh->faces=faces;
return(LIB3DS_TRUE);
}
/*!
* \ingroup mesh
*/
void
lib3ds_mesh_free_face_list(Lib3dsMesh *mesh)
{
ASSERT(mesh);
if (mesh->faceL) {
ASSERT(mesh->faces);
free(mesh->faceL);
mesh->faceL=0;
mesh->faces=0;
}
else {
ASSERT(!mesh->faces);
}
}
typedef struct _Lib3dsFaces Lib3dsFaces;
struct _Lib3dsFaces {
Lib3dsFaces *next;
Lib3dsFace *face;
};
/*!
* \ingroup mesh
*/
void
lib3ds_mesh_bounding_box(Lib3dsMesh *mesh, Lib3dsVector min, Lib3dsVector max)
{
unsigned i,j;
Lib3dsFloat v;
if (!mesh->points) {
lib3ds_vector_zero(min);
lib3ds_vector_zero(max);
return;
}
lib3ds_vector_copy(min, mesh->pointL[0].pos);
lib3ds_vector_copy(max, mesh->pointL[0].pos);
for (i=1; i<mesh->points; ++i) {
for (j=0; j<3; ++j) {
v=mesh->pointL[i].pos[j];
if (v<min[j]) {
min[j]=v;
}
if (v>max[j]) {
max[j]=v;
}
}
};
}
/*!
* Calculates the vertex normals corresponding to the smoothing group
* settings for each face of a mesh.
*
* \param mesh A pointer to the mesh to calculate the normals for.
* \param normalL A pointer to a buffer to store the calculated
* normals. The buffer must have the size:
* 3*sizeof(Lib3dsVector)*mesh->faces.
*
* To allocate the normal buffer do for example the following:
* \code
* Lib3dsVector *normalL = malloc(3*sizeof(Lib3dsVector)*mesh->faces);
* \endcode
*
* To access the normal of the i-th vertex of the j-th face do the
* following:
* \code
* normalL[3*j+i]
* \endcode
*/
void
lib3ds_mesh_calculate_normals(Lib3dsMesh *mesh, Lib3dsVector *normalL)
{
Lib3dsFaces **fl;
Lib3dsFaces *fa;
unsigned i,j,k;
if (!mesh->faces) {
return;
}
fl=(Lib3dsFaces**)calloc(sizeof(Lib3dsFaces*),mesh->points);
ASSERT(fl);
fa=(Lib3dsFaces*)calloc(sizeof(Lib3dsFaces),3*mesh->faces);
ASSERT(fa);
k=0;
for (i=0; i<mesh->faces; ++i) {
Lib3dsFace *f=&mesh->faceL[i];
for (j=0; j<3; ++j) {
Lib3dsFaces* l=&fa[k++];
ASSERT(f->points[j]<mesh->points);
l->face=f;
l->next=fl[f->points[j]];
fl[f->points[j]]=l;
}
}
for (i=0; i<mesh->faces; ++i) {
Lib3dsFace *f=&mesh->faceL[i];
for (j=0; j<3; ++j) {
Lib3dsVector n,N[32];
Lib3dsFaces *p;
int k,l;
int found;
ASSERT(f->points[j]<mesh->points);
if (f->smoothing) {
lib3ds_vector_zero(n);
k=0;
for (p=fl[f->points[j]]; p; p=p->next) {
found=0;
for (l=0; l<k; ++l) {
if (fabs(lib3ds_vector_dot(N[l], p->face->normal)-1.0)<1e-5) {
found=1;
break;
}
}
if (!found) {
if (f->smoothing & p->face->smoothing) {
lib3ds_vector_add(n,n, p->face->normal);
lib3ds_vector_copy(N[k], p->face->normal);
++k;
}
}
}
}
else {
lib3ds_vector_copy(n, f->normal);
}
lib3ds_vector_normalize(n);
lib3ds_vector_copy(normalL[3*i+j], n);
}
}
free(fa);
free(fl);
}
/*!
* This function prints data associated with the specified mesh such as
* vertex and point lists.
*
* \param mesh Points to a mesh that you wish to view the data for.
*
* \return None
*
* \warning WIN32: Should only be used in a console window not in a GUI.
*
* \ingroup mesh
*/
void
lib3ds_mesh_dump(Lib3dsMesh *mesh)
{
unsigned i;
Lib3dsVector p;
ASSERT(mesh);
printf(" %s vertices=%d faces=%d\n",
mesh->name,
mesh->points,
mesh->faces
);
printf(" matrix:\n");
lib3ds_matrix_dump(mesh->matrix);
printf(" point list:\n");
for (i=0; i<mesh->points; ++i) {
lib3ds_vector_copy(p, mesh->pointL[i].pos);
printf (" %8f %8f %8f\n", p[0], p[1], p[2]);
}
printf(" facelist:\n");
for (i=0; i<mesh->points; ++i) {
printf (" %4d %4d %4d smoothing:%X\n",
mesh->faceL[i].points[0],
mesh->faceL[i].points[1],
mesh->faceL[i].points[2],
static_cast<int>(mesh->faceL[i].smoothing)
);
}
}
/*!
* \ingroup mesh
*/
Lib3dsBool
lib3ds_mesh_read(Lib3dsMesh *mesh, iostream *strm)
{
Lib3dsChunk c;
Lib3dsWord chunk;
if (!lib3ds_chunk_read_start(&c, LIB3DS_N_TRI_OBJECT, strm)) {
return(LIB3DS_FALSE);
}
while ((chunk=lib3ds_chunk_read_next(&c, strm))!=0) {
switch (chunk) {
case LIB3DS_MESH_MATRIX:
{
int i,j;
lib3ds_matrix_identity(mesh->matrix);
for (i=0; i<4; i++) {
for (j=0; j<3; j++) {
mesh->matrix[i][j]=lib3ds_float_read(strm);
}
}
}
break;
case LIB3DS_MESH_COLOR:
{
mesh->color=lib3ds_byte_read(strm);
}
break;
case LIB3DS_POINT_ARRAY:
{
unsigned i,j;
unsigned points;
lib3ds_mesh_free_point_list(mesh);
points=lib3ds_word_read(strm);
if (points) {
if (!lib3ds_mesh_new_point_list(mesh, points)) {
LIB3DS_ERROR_LOG;
return(LIB3DS_FALSE);
}
for (i=0; i<mesh->points; ++i) {
for (j=0; j<3; ++j) {
mesh->pointL[i].pos[j]=lib3ds_float_read(strm);
}
}
ASSERT((!mesh->flags) || (mesh->points==mesh->flags));
ASSERT((!mesh->texels) || (mesh->points==mesh->texels));
}
}
break;
case LIB3DS_POINT_FLAG_ARRAY:
{
unsigned i;
unsigned flags;
lib3ds_mesh_free_flag_list(mesh);
flags=lib3ds_word_read(strm);
if (flags) {
if (!lib3ds_mesh_new_flag_list(mesh, flags)) {
LIB3DS_ERROR_LOG;
return(LIB3DS_FALSE);
}
for (i=0; i<mesh->flags; ++i) {
mesh->flagL[i]=lib3ds_word_read(strm);
}
ASSERT((!mesh->points) || (mesh->flags==mesh->points));
ASSERT((!mesh->texels) || (mesh->flags==mesh->texels));
}
}
break;
case LIB3DS_FACE_ARRAY:
{
lib3ds_chunk_read_reset(&c, strm);
if (!face_array_read(mesh, strm)) {
return(LIB3DS_FALSE);
}
}
break;
case LIB3DS_MESH_TEXTURE_INFO:
{
int i,j;
for (i=0; i<2; ++i) {
mesh->map_data.tile[i]=lib3ds_float_read(strm);
}
for (i=0; i<3; ++i) {
mesh->map_data.pos[i]=lib3ds_float_read(strm);
}
mesh->map_data.scale=lib3ds_float_read(strm);
lib3ds_matrix_identity(mesh->map_data.matrix);
for (i=0; i<4; i++) {
for (j=0; j<3; j++) {
mesh->map_data.matrix[i][j]=lib3ds_float_read(strm);
}
}
for (i=0; i<2; ++i) {
mesh->map_data.planar_size[i]=lib3ds_float_read(strm);
}
mesh->map_data.cylinder_height=lib3ds_float_read(strm);
}
break;
case LIB3DS_TEX_VERTS:
{
unsigned i;
unsigned texels;
lib3ds_mesh_free_texel_list(mesh);
texels=lib3ds_word_read(strm);
if (texels) {
if (!lib3ds_mesh_new_texel_list(mesh, texels)) {
LIB3DS_ERROR_LOG;
return(LIB3DS_FALSE);
}
for (i=0; i<mesh->texels; ++i) {
mesh->texelL[i][0]=lib3ds_float_read(strm);
mesh->texelL[i][1]=lib3ds_float_read(strm);
}
ASSERT((!mesh->points) || (mesh->texels==mesh->points));
ASSERT((!mesh->flags) || (mesh->texels==mesh->flags));
}
}
break;
default:
lib3ds_chunk_unknown(chunk);
}
}
{
unsigned j;
for (j=0; j<mesh->faces; ++j) {
ASSERT(mesh->faceL[j].points[0]<mesh->points);
ASSERT(mesh->faceL[j].points[1]<mesh->points);
ASSERT(mesh->faceL[j].points[2]<mesh->points);
lib3ds_vector_normal(
mesh->faceL[j].normal,
mesh->pointL[mesh->faceL[j].points[0]].pos,
mesh->pointL[mesh->faceL[j].points[1]].pos,
mesh->pointL[mesh->faceL[j].points[2]].pos
);
}
}
lib3ds_chunk_read_end(&c, strm);
return(LIB3DS_TRUE);
}
static Lib3dsBool
point_array_write(Lib3dsMesh *mesh, iostream *strm)
{
Lib3dsChunk c;
unsigned i;
if (!mesh->points || !mesh->pointL) {
return(LIB3DS_TRUE);
}
ASSERT(mesh->points<0x10000);
c.chunk=LIB3DS_POINT_ARRAY;
c.size=8+12*mesh->points;
lib3ds_chunk_write(&c, strm);
lib3ds_word_write((Lib3dsWord)mesh->points, strm);
for (i=0; i<mesh->points; ++i) {
lib3ds_vector_write(mesh->pointL[i].pos, strm);
}
return(LIB3DS_TRUE);
}
static Lib3dsBool
flag_array_write(Lib3dsMesh *mesh, iostream *strm)
{
Lib3dsChunk c;
unsigned i;
if (!mesh->flags || !mesh->flagL) {
return(LIB3DS_TRUE);
}
ASSERT(mesh->flags<0x10000);
c.chunk=LIB3DS_POINT_FLAG_ARRAY;
c.size=8+2*mesh->flags;
lib3ds_chunk_write(&c, strm);
lib3ds_word_write((Lib3dsWord)mesh->flags, strm);
for (i=0; i<mesh->flags; ++i) {
lib3ds_word_write(mesh->flagL[i], strm);
}
return(LIB3DS_TRUE);
}
static Lib3dsBool
face_array_write(Lib3dsMesh *mesh, iostream *strm)
{
Lib3dsChunk c;
if (!mesh->faces || !mesh->faceL) {
return(LIB3DS_TRUE);
}
ASSERT(mesh->faces<0x10000);
c.chunk=LIB3DS_FACE_ARRAY;
if (!lib3ds_chunk_write_start(&c, strm)) {
return(LIB3DS_FALSE);
}
{
unsigned i;
lib3ds_word_write((Lib3dsWord)mesh->faces, strm);
for (i=0; i<mesh->faces; ++i) {
lib3ds_word_write(mesh->faceL[i].points[0], strm);
lib3ds_word_write(mesh->faceL[i].points[1], strm);
lib3ds_word_write(mesh->faceL[i].points[2], strm);
lib3ds_word_write(mesh->faceL[i].flags, strm);
}
}
{ /*---- MSH_MAT_GROUP ----*/
Lib3dsChunk c;
unsigned i,j;
Lib3dsWord num;
char *matf=(char*)calloc(sizeof(char), mesh->faces);
if (!matf) {
return(LIB3DS_FALSE);
}
for (i=0; i<mesh->faces; ++i) {
if (!matf[i] && strlen(mesh->faceL[i].material)) {
matf[i]=1;
num=1;
for (j=i+1; j<mesh->faces; ++j) {
if (strcmp(mesh->faceL[i].material, mesh->faceL[j].material)==0) ++num;
}
c.chunk=LIB3DS_MSH_MAT_GROUP;
c.size=6+ strlen(mesh->faceL[i].material)+1 +2+2*num;
lib3ds_chunk_write(&c, strm);
lib3ds_string_write(mesh->faceL[i].material, strm);
lib3ds_word_write(num, strm);
lib3ds_word_write((Lib3dsWord)i, strm);
for (j=i+1; j<mesh->faces; ++j) {
if (strcmp(mesh->faceL[i].material, mesh->faceL[j].material)==0) {
lib3ds_word_write((Lib3dsWord)j, strm);
matf[j]=1;
}
}
}
}
free(matf);
}
{ /*---- SMOOTH_GROUP ----*/
Lib3dsChunk c;
unsigned i;
c.chunk=LIB3DS_SMOOTH_GROUP;
c.size=6+4*mesh->faces;
lib3ds_chunk_write(&c, strm);
for (i=0; i<mesh->faces; ++i) {
lib3ds_dword_write(mesh->faceL[i].smoothing, strm);
}
}
{ /*---- MSH_BOXMAP ----*/
Lib3dsChunk c;
if (strlen(mesh->box_map.front) ||
strlen(mesh->box_map.back) ||
strlen(mesh->box_map.left) ||
strlen(mesh->box_map.right) ||
strlen(mesh->box_map.top) ||
strlen(mesh->box_map.bottom)) {
c.chunk=LIB3DS_MSH_BOXMAP;
if (!lib3ds_chunk_write_start(&c, strm)) {
return(LIB3DS_FALSE);
}
lib3ds_string_write(mesh->box_map.front, strm);
lib3ds_string_write(mesh->box_map.back, strm);
lib3ds_string_write(mesh->box_map.left, strm);
lib3ds_string_write(mesh->box_map.right, strm);
lib3ds_string_write(mesh->box_map.top, strm);
lib3ds_string_write(mesh->box_map.bottom, strm);
if (!lib3ds_chunk_write_end(&c, strm)) {
return(LIB3DS_FALSE);
}
}
}
if (!lib3ds_chunk_write_end(&c, strm)) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
static Lib3dsBool
texel_array_write(Lib3dsMesh *mesh, iostream *strm)
{
Lib3dsChunk c;
unsigned i;
if (!mesh->texels || !mesh->texelL) {
return(LIB3DS_TRUE);
}
ASSERT(mesh->texels<0x10000);
c.chunk=LIB3DS_TEX_VERTS;
c.size=8+8*mesh->texels;
lib3ds_chunk_write(&c, strm);
lib3ds_word_write((Lib3dsWord)mesh->texels, strm);
for (i=0; i<mesh->texels; ++i) {
lib3ds_float_write(mesh->texelL[i][0], strm);
lib3ds_float_write(mesh->texelL[i][1], strm);
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup mesh
*/
Lib3dsBool
lib3ds_mesh_write(Lib3dsMesh *mesh, iostream *strm)
{
Lib3dsChunk c;
c.chunk=LIB3DS_N_TRI_OBJECT;
if (!lib3ds_chunk_write_start(&c,strm)) {
return(LIB3DS_FALSE);
}
if (!point_array_write(mesh, strm)) {
return(LIB3DS_FALSE);
}
if (!texel_array_write(mesh, strm)) {
return(LIB3DS_FALSE);
}
if (mesh->map_data.maptype!=LIB3DS_MAP_NONE) { /*---- LIB3DS_MESH_TEXTURE_INFO ----*/
Lib3dsChunk c;
int i,j;
c.chunk=LIB3DS_MESH_TEXTURE_INFO;
c.size=92;
if (!lib3ds_chunk_write(&c,strm)) {
return(LIB3DS_FALSE);
}
lib3ds_word_write(mesh->map_data.maptype, strm);
for (i=0; i<2; ++i) {
lib3ds_float_write(mesh->map_data.tile[i], strm);
}
for (i=0; i<3; ++i) {
lib3ds_float_write(mesh->map_data.pos[i], strm);
}
lib3ds_float_write(mesh->map_data.scale, strm);
for (i=0; i<4; i++) {
for (j=0; j<3; j++) {
lib3ds_float_write(mesh->map_data.matrix[i][j], strm);
}
}
for (i=0; i<2; ++i) {
lib3ds_float_write(mesh->map_data.planar_size[i], strm);
}
lib3ds_float_write(mesh->map_data.cylinder_height, strm);
}
if (!flag_array_write(mesh, strm)) {
return(LIB3DS_FALSE);
}
{ /*---- LIB3DS_MESH_MATRIX ----*/
Lib3dsChunk c;
int i,j;
c.chunk=LIB3DS_MESH_MATRIX;
c.size=54;
if (!lib3ds_chunk_write(&c,strm)) {
return(LIB3DS_FALSE);
}
for (i=0; i<4; i++) {
for (j=0; j<3; j++) {
lib3ds_float_write(mesh->matrix[i][j], strm);
}
}
}
if (mesh->color) { /*---- LIB3DS_MESH_COLOR ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_MESH_COLOR;
c.size=7;
if (!lib3ds_chunk_write(&c,strm)) {
return(LIB3DS_FALSE);
}
lib3ds_byte_write(mesh->color, strm);
}
if (!face_array_write(mesh, strm)) {
return(LIB3DS_FALSE);
}
if (!lib3ds_chunk_write_end(&c,strm)) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
\typedef Lib3dsFace
\ingroup mesh
\sa _Lib3dsFace
*/
/*!
\typedef Lib3dsBoxMap
\ingroup mesh
\sa _Lib3dsBoxMap
*/
/*!
\typedef Lib3dsMapData
\ingroup mesh
\sa _Lib3dsMapData
*/
/*!
\typedef Lib3dsMesh
\ingroup mesh
\sa _Lib3dsMesh
*/

View File

@@ -1,140 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_MESH_H
#define INCLUDED_LIB3DS_MESH_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TYPES_H
#include "types.h"
#endif
#include <iostream>
using namespace std;
#ifdef __cplusplus
extern "C" {
#endif
/*!
* Triangular mesh point
* \ingroup mesh
*/
typedef struct _Lib3dsPoint {
Lib3dsVector pos;
} Lib3dsPoint;
/*!
* Triangular mesh face
* \ingroup mesh
*/
struct _Lib3dsFace {
Lib3dsUserData user;
char material[64];
Lib3dsWord points[3];
Lib3dsWord flags;
Lib3dsDword smoothing;
Lib3dsVector normal;
};
/*!
* Triangular mesh box mapping settings
* \ingroup mesh
*/
struct _Lib3dsBoxMap {
char front[64];
char back[64];
char left[64];
char right[64];
char top[64];
char bottom[64];
};
/*!
* Lib3dsMapData maptype
* \ingroup tracks
*/
typedef enum {
LIB3DS_MAP_NONE =0xFFFF,
LIB3DS_MAP_PLANAR =0,
LIB3DS_MAP_CYLINDRICAL =1,
LIB3DS_MAP_SPHERICAL =2
} Lib3dsMapType;
/*!
* Triangular mesh texture mapping data
* \ingroup mesh
*/
struct _Lib3dsMapData {
Lib3dsWord maptype;
Lib3dsVector pos;
Lib3dsMatrix matrix;
Lib3dsFloat scale;
Lib3dsFloat tile[2];
Lib3dsFloat planar_size[2];
Lib3dsFloat cylinder_height;
};
/*!
* Triangular mesh object
* \ingroup mesh
*/
struct _Lib3dsMesh {
Lib3dsUserData user;
Lib3dsMesh *next;
char name[64];
Lib3dsByte color;
Lib3dsMatrix matrix;
Lib3dsDword points;
Lib3dsPoint *pointL;
Lib3dsDword flags;
Lib3dsWord *flagL;
Lib3dsDword texels;
Lib3dsTexel *texelL;
Lib3dsDword faces;
Lib3dsFace *faceL;
Lib3dsBoxMap box_map;
Lib3dsMapData map_data;
};
extern LIB3DSAPI Lib3dsMesh* lib3ds_mesh_new(const char *name);
extern LIB3DSAPI void lib3ds_mesh_free(Lib3dsMesh *mesh);
extern LIB3DSAPI Lib3dsBool lib3ds_mesh_new_point_list(Lib3dsMesh *mesh, Lib3dsDword points);
extern LIB3DSAPI void lib3ds_mesh_free_point_list(Lib3dsMesh *mesh);
extern LIB3DSAPI Lib3dsBool lib3ds_mesh_new_flag_list(Lib3dsMesh *mesh, Lib3dsDword flags);
extern LIB3DSAPI void lib3ds_mesh_free_flag_list(Lib3dsMesh *mesh);
extern LIB3DSAPI Lib3dsBool lib3ds_mesh_new_texel_list(Lib3dsMesh *mesh, Lib3dsDword texels);
extern LIB3DSAPI void lib3ds_mesh_free_texel_list(Lib3dsMesh *mesh);
extern LIB3DSAPI Lib3dsBool lib3ds_mesh_new_face_list(Lib3dsMesh *mesh, Lib3dsDword flags);
extern LIB3DSAPI void lib3ds_mesh_free_face_list(Lib3dsMesh *mesh);
extern LIB3DSAPI void lib3ds_mesh_bounding_box(Lib3dsMesh *mesh, Lib3dsVector min, Lib3dsVector max);
extern LIB3DSAPI void lib3ds_mesh_calculate_normals(Lib3dsMesh *mesh, Lib3dsVector *normalL);
extern LIB3DSAPI void lib3ds_mesh_dump(Lib3dsMesh *mesh);
extern LIB3DSAPI Lib3dsBool lib3ds_mesh_read(Lib3dsMesh *mesh, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_mesh_write(Lib3dsMesh *mesh, iostream *strm);
#ifdef __cplusplus
}
#endif
#endif

File diff suppressed because it is too large Load Diff

View File

@@ -1,173 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_NODE_H
#define INCLUDED_LIB3DS_NODE_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TRACKS_H
#include "tracks.h"
#endif
#include <iostream>
using namespace std;
#ifdef __cplusplus
extern "C" {
#endif
/*!
* Scene graph ambient color node data
* \ingroup node
*/
typedef struct _Lib3dsAmbientData {
Lib3dsRgb col;
Lib3dsLin3Track col_track;
} Lib3dsAmbientData;
/*!
* Scene graph object instance node data
* \ingroup node
*/
typedef struct _Lib3dsObjectData {
Lib3dsVector pivot;
char instance[64];
Lib3dsVector bbox_min;
Lib3dsVector bbox_max;
Lib3dsVector pos;
Lib3dsLin3Track pos_track;
Lib3dsQuat rot;
Lib3dsQuatTrack rot_track;
Lib3dsVector scl;
Lib3dsLin3Track scl_track;
Lib3dsFloat morph_smooth;
char morph[64];
Lib3dsMorphTrack morph_track;
Lib3dsBool hide;
Lib3dsBoolTrack hide_track;
} Lib3dsObjectData;
/*!
* Scene graph camera node data
* \ingroup node
*/
typedef struct _Lib3dsCameraData {
Lib3dsVector pos;
Lib3dsLin3Track pos_track;
Lib3dsFloat fov;
Lib3dsLin1Track fov_track;
Lib3dsFloat roll;
Lib3dsLin1Track roll_track;
} Lib3dsCameraData;
/*!
* Scene graph camera target node data
* \ingroup node
*/
typedef struct _Lib3dsTargetData {
Lib3dsVector pos;
Lib3dsLin3Track pos_track;
} Lib3dsTargetData;
/*!
* Scene graph light node data
* \ingroup node
*/
typedef struct _Lib3dsLightData {
Lib3dsVector pos;
Lib3dsLin3Track pos_track;
Lib3dsRgb col;
Lib3dsLin3Track col_track;
Lib3dsFloat hotspot;
Lib3dsLin1Track hotspot_track;
Lib3dsFloat falloff;
Lib3dsLin1Track falloff_track;
Lib3dsFloat roll;
Lib3dsLin1Track roll_track;
} Lib3dsLightData;
/*!
* Scene graph spotlight target node data
* \ingroup node
*/
typedef struct _Lib3dsSpotData {
Lib3dsVector pos;
Lib3dsLin3Track pos_track;
} Lib3dsSpotData;
/*!
* Scene graph node data union
* \ingroup node
*/
typedef union _Lib3dsNodeData {
Lib3dsAmbientData ambient;
Lib3dsObjectData object;
Lib3dsCameraData camera;
Lib3dsTargetData target;
Lib3dsLightData light;
Lib3dsSpotData spot;
} Lib3dsNodeData;
/*!
* \ingroup node
*/
#define LIB3DS_NO_PARENT 65535
/*!
* Scene graph node
* \ingroup node
*/
struct _Lib3dsNode {
Lib3dsUserData user;
Lib3dsNode *next;\
Lib3dsNode *childs;\
Lib3dsNode *parent;\
Lib3dsNodeTypes type;\
Lib3dsWord node_id;\
char name[64];\
Lib3dsWord flags1;\
Lib3dsWord flags2;\
Lib3dsWord parent_id;
Lib3dsMatrix matrix;
Lib3dsNodeData data;
};
extern LIB3DSAPI Lib3dsNode* lib3ds_node_new_ambient();
extern LIB3DSAPI Lib3dsNode* lib3ds_node_new_object();
extern LIB3DSAPI Lib3dsNode* lib3ds_node_new_camera();
extern LIB3DSAPI Lib3dsNode* lib3ds_node_new_target();
extern LIB3DSAPI Lib3dsNode* lib3ds_node_new_light();
extern LIB3DSAPI Lib3dsNode* lib3ds_node_new_spot();
extern LIB3DSAPI void lib3ds_node_free(Lib3dsNode *node);
extern LIB3DSAPI void lib3ds_node_eval(Lib3dsNode *node, Lib3dsFloat t);
extern LIB3DSAPI Lib3dsNode* lib3ds_node_by_name(Lib3dsNode *node, const char* name,
Lib3dsNodeTypes type);
extern LIB3DSAPI Lib3dsNode* lib3ds_node_by_id(Lib3dsNode *node, Lib3dsWord node_id);
extern LIB3DSAPI void lib3ds_node_dump(Lib3dsNode *node, Lib3dsIntd level);
extern LIB3DSAPI Lib3dsBool lib3ds_node_read(Lib3dsNode *node, Lib3dsFile *file, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_node_write(Lib3dsNode *node, Lib3dsFile *file, iostream *strm);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -1,392 +0,0 @@
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#define LIB3DS_EXPORT
#include "quat.h"
#include <math.h>
/*!
* \defgroup quat Quaternion Mathematics
*
* \author J.E. Hoffmann <je-h@gmx.net>
*/
/*!
* \typedef Lib3dsQuat
* \ingroup quat
*/
/*!
* \ingroup quat
*/
void
lib3ds_quat_zero(Lib3dsQuat c)
{
c[0]=c[1]=c[2]=c[3]=0.0f;
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_identity(Lib3dsQuat c)
{
c[0]=c[1]=c[2]=0.0f;
c[3]=1.0f;
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_copy(Lib3dsQuat dest, Lib3dsQuat src)
{
int i;
for (i=0; i<4; ++i) {
dest[i]=src[i];
}
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_axis_angle(Lib3dsQuat c, Lib3dsVector axis, Lib3dsFloat angle)
{
Lib3dsDouble omega,s;
Lib3dsDouble l;
l=sqrt(axis[0]*axis[0] + axis[1]*axis[1] + axis[2]*axis[2]);
if (l<LIB3DS_EPSILON) {
c[0]=c[1]=c[2]=0.0f;
c[3]=1.0f;
}
else {
omega=-0.5*angle;
s=sin(omega)/l;
c[0]=(Lib3dsFloat)s*axis[0];
c[1]=(Lib3dsFloat)s*axis[1];
c[2]=(Lib3dsFloat)s*axis[2];
c[3]=(Lib3dsFloat)cos(omega);
}
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_neg(Lib3dsQuat c)
{
int i;
for (i=0; i<4; ++i) {
c[i]=-c[i];
}
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_abs(Lib3dsQuat c)
{
int i;
for (i=0; i<4; ++i) {
c[i]=(Lib3dsFloat)fabs(c[i]);
}
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_cnj(Lib3dsQuat c)
{
int i;
for (i=0; i<3; ++i) {
c[i]=-c[i];
}
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_mul(Lib3dsQuat c, Lib3dsQuat a, Lib3dsQuat b)
{
c[0]=a[3]*b[0] + a[0]*b[3] + a[1]*b[2] - a[2]*b[1];
c[1]=a[3]*b[1] + a[1]*b[3] + a[2]*b[0] - a[0]*b[2];
c[2]=a[3]*b[2] + a[2]*b[3] + a[0]*b[1] - a[1]*b[0];
c[3]=a[3]*b[3] - a[0]*b[0] - a[1]*b[1] - a[2]*b[2];
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_scalar(Lib3dsQuat c, Lib3dsFloat k)
{
int i;
for (i=0; i<4; ++i) {
c[i]*=k;
}
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_normalize(Lib3dsQuat c)
{
Lib3dsDouble l,m;
l=sqrt(c[0]*c[0] + c[1]*c[1] + c[2]*c[2] + c[3]*c[3]);
if (fabs(l)<LIB3DS_EPSILON) {
c[0]=c[1]=c[2]=0.0f;
c[3]=1.0f;
}
else {
int i;
m=1.0f/l;
for (i=0; i<4; ++i) {
c[i]=(Lib3dsFloat)(c[i]*m);
}
}
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_inv(Lib3dsQuat c)
{
Lib3dsDouble l,m;
l=sqrt(c[0]*c[0] + c[1]*c[1] + c[2]*c[2] + c[3]*c[3]);
if (fabs(l)<LIB3DS_EPSILON) {
c[0]=c[1]=c[2]=0.0f;
c[3]=1.0f;
}
else {
m=1.0f/l;
c[0]=(Lib3dsFloat)(-c[0]*m);
c[1]=(Lib3dsFloat)(-c[1]*m);
c[2]=(Lib3dsFloat)(-c[2]*m);
c[3]=(Lib3dsFloat)(c[3]*m);
}
}
/*!
* \ingroup quat
*/
Lib3dsFloat
lib3ds_quat_dot(Lib3dsQuat a, Lib3dsQuat b)
{
return(a[0]*b[0] + a[1]*b[1] + a[2]*b[2] + a[3]*b[3]);
}
/*!
* \ingroup quat
*/
Lib3dsFloat
lib3ds_quat_squared(Lib3dsQuat c)
{
return(c[0]*c[0] + c[1]*c[1] + c[2]*c[2] + c[3]*c[3]);
}
/*!
* \ingroup quat
*/
Lib3dsFloat
lib3ds_quat_length(Lib3dsQuat c)
{
return((Lib3dsFloat)sqrt(c[0]*c[0] + c[1]*c[1] + c[2]*c[2] + c[3]*c[3]));
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_ln(Lib3dsQuat c)
{
Lib3dsDouble om,s,t;
s=sqrt(c[0]*c[0] + c[1]*c[1] + c[2]*c[2]);
om=atan2(s,(Lib3dsDouble)c[3]);
if (fabs(s)<LIB3DS_EPSILON) {
t=0.0f;
}
else {
t=om/s;
}
{
int i;
for (i=0; i<3; ++i) {
c[i]=(Lib3dsFloat)(c[i]*t);
}
c[3]=0.0f;
}
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_ln_dif(Lib3dsQuat c, Lib3dsQuat a, Lib3dsQuat b)
{
Lib3dsQuat invp;
lib3ds_quat_copy(invp, a);
lib3ds_quat_inv(invp);
lib3ds_quat_mul(c, invp, b);
lib3ds_quat_ln(c);
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_exp(Lib3dsQuat c)
{
Lib3dsDouble om,sinom;
om=sqrt(c[0]*c[0] + c[1]*c[1] + c[2]*c[2]);
if (fabs(om)<LIB3DS_EPSILON) {
sinom=1.0f;
}
else {
sinom=sin(om)/om;
}
{
int i;
for (i=0; i<3; ++i) {
c[i]=(Lib3dsFloat)(c[i]*sinom);
}
c[3]=(Lib3dsFloat)cos(om);
}
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_slerp(Lib3dsQuat c, Lib3dsQuat a, Lib3dsQuat b, Lib3dsFloat t)
{
Lib3dsDouble l;
Lib3dsDouble om,sinom;
Lib3dsDouble sp,sq;
Lib3dsQuat q;
l=a[0]*b[0] + a[1]*b[1] + a[2]*b[2] + a[3]*b[3];
if ((1.0+l)>LIB3DS_EPSILON) {
if (fabs(l)>1.0f) l/=fabs(l);
om=acos(l);
sinom=sin(om);
if (fabs(sinom)>LIB3DS_EPSILON) {
sp=sin((1.0f-t)*om)/sinom;
sq=sin(t*om)/sinom;
}
else {
sp=1.0f-t;
sq=t;
}
c[0]=(Lib3dsFloat)(sp*a[0] + sq*b[0]);
c[1]=(Lib3dsFloat)(sp*a[1] + sq*b[1]);
c[2]=(Lib3dsFloat)(sp*a[2] + sq*b[2]);
c[3]=(Lib3dsFloat)(sp*a[3] + sq*b[3]);
}
else {
q[0]=-a[1];
q[1]=a[0];
q[2]=-a[3];
q[3]=a[2];
sp=sin((1.0-t)*LIB3DS_HALFPI);
sq=sin(t*LIB3DS_HALFPI);
c[0]=(Lib3dsFloat)(sp*a[0] + sq*q[0]);
c[1]=(Lib3dsFloat)(sp*a[1] + sq*q[1]);
c[2]=(Lib3dsFloat)(sp*a[2] + sq*q[2]);
c[3]=(Lib3dsFloat)(sp*a[3] + sq*q[3]);
}
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_squad(Lib3dsQuat c, Lib3dsQuat a, Lib3dsQuat p, Lib3dsQuat q,
Lib3dsQuat b, Lib3dsFloat t)
{
Lib3dsQuat ab;
Lib3dsQuat pq;
lib3ds_quat_slerp(ab,a,b,t);
lib3ds_quat_slerp(pq,p,q,t);
lib3ds_quat_slerp(c,ab,pq,2*t*(1-t));
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_tangent(Lib3dsQuat c, Lib3dsQuat p, Lib3dsQuat q, Lib3dsQuat n)
{
Lib3dsQuat dn,dp,x;
int i;
lib3ds_quat_ln_dif(dn, q, n);
lib3ds_quat_ln_dif(dp, q, p);
for (i=0; i<4; i++) {
x[i]=-1.0f/4.0f*(dn[i]+dp[i]);
}
lib3ds_quat_exp(x);
lib3ds_quat_mul(c,q,x);
}
/*!
* \ingroup quat
*/
void
lib3ds_quat_dump(Lib3dsQuat q)
{
printf("%f %f %f %f\n", q[0], q[1], q[2], q[3]);
}

View File

@@ -1,61 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_QUAT_H
#define INCLUDED_LIB3DS_QUAT_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TYPES_H
#include "types.h"
#endif
#ifdef __cplusplus
extern "C" {
#endif
extern LIB3DSAPI void lib3ds_quat_zero(Lib3dsQuat c);
extern LIB3DSAPI void lib3ds_quat_identity(Lib3dsQuat c);
extern LIB3DSAPI void lib3ds_quat_copy(Lib3dsQuat dest, Lib3dsQuat src);
extern LIB3DSAPI void lib3ds_quat_axis_angle(Lib3dsQuat c, Lib3dsVector axis, Lib3dsFloat angle);
extern LIB3DSAPI void lib3ds_quat_neg(Lib3dsQuat c);
extern LIB3DSAPI void lib3ds_quat_abs(Lib3dsQuat c);
extern LIB3DSAPI void lib3ds_quat_cnj(Lib3dsQuat c);
extern LIB3DSAPI void lib3ds_quat_mul(Lib3dsQuat c, Lib3dsQuat a, Lib3dsQuat b);
extern LIB3DSAPI void lib3ds_quat_scalar(Lib3dsQuat c, Lib3dsFloat k);
extern LIB3DSAPI void lib3ds_quat_normalize(Lib3dsQuat c);
extern LIB3DSAPI void lib3ds_quat_inv(Lib3dsQuat c);
extern LIB3DSAPI Lib3dsFloat lib3ds_quat_dot(Lib3dsQuat a, Lib3dsQuat b);
extern LIB3DSAPI Lib3dsFloat lib3ds_quat_squared(Lib3dsQuat c);
extern LIB3DSAPI Lib3dsFloat lib3ds_quat_length(Lib3dsQuat c);
extern LIB3DSAPI void lib3ds_quat_ln(Lib3dsQuat c);
extern LIB3DSAPI void lib3ds_quat_ln_dif(Lib3dsQuat c, Lib3dsQuat a, Lib3dsQuat b);
extern LIB3DSAPI void lib3ds_quat_exp(Lib3dsQuat c);
extern LIB3DSAPI void lib3ds_quat_slerp(Lib3dsQuat c, Lib3dsQuat a, Lib3dsQuat b, Lib3dsFloat t);
extern LIB3DSAPI void lib3ds_quat_squad(Lib3dsQuat c, Lib3dsQuat a, Lib3dsQuat p, Lib3dsQuat q,
Lib3dsQuat b, Lib3dsFloat t);
extern LIB3DSAPI void lib3ds_quat_tangent(Lib3dsQuat c, Lib3dsQuat p, Lib3dsQuat q, Lib3dsQuat n);
extern LIB3DSAPI void lib3ds_quat_dump(Lib3dsQuat q);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -1,546 +0,0 @@
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#define LIB3DS_EXPORT
#include "readwrite.h"
#include <osg/Endian>
/*!
* \defgroup readwrite Portable Binary Input/Ouput
*
* \author J.E. Hoffmann <je-h@gmx.net>
*/
static bool s_requiresByteSwap = false;
extern LIB3DSAPI void setByteOrder()
{
s_requiresByteSwap = osg::getCpuByteOrder()==osg::BigEndian;
}
/*!
* \ingroup readwrite
*
* Read a byte from a file stream.
*
* \param f Input file stream.
*
* \return The byte read.
*/
Lib3dsByte
lib3ds_byte_read(iostream *strm)
{
Lib3dsByte b;
ASSERT(strm);
strm->read((char*)&b,1);
return(b);
}
/**
* Read a word from a file stream in little endian format.
*
* \param f Input file stream.
*
* \return The word read.
*/
Lib3dsWord
lib3ds_word_read(iostream *strm)
{
Lib3dsByte b[2];
Lib3dsWord w;
ASSERT(strm);
strm->read((char*)&b,2);
w=((Lib3dsWord)b[1] << 8) |
((Lib3dsWord)b[0]);
return(w);
}
/*!
* \ingroup readwrite
*
* Read a dword from file a stream in little endian format.
*
* \param f Input file stream.
*
* \return The dword read.
*/
Lib3dsDword
lib3ds_dword_read(iostream *strm)
{
Lib3dsByte b[4];
Lib3dsDword d;
ASSERT(strm);
strm->read((char*)&b,4);
d=((Lib3dsDword)b[3] << 24) |
((Lib3dsDword)b[2] << 16) |
((Lib3dsDword)b[1] << 8) |
((Lib3dsDword)b[0]);
return(d);
}
/*!
* \ingroup readwrite
*
* Read a signed byte from a file stream.
*
* \param f Input file stream.
*
* \return The signed byte read.
*/
Lib3dsIntb
lib3ds_intb_read(iostream *strm)
{
Lib3dsIntb b;
ASSERT(strm);
strm->read((char*)&b,1);
return(b);
}
/*!
* \ingroup readwrite
*
* Read a signed word from a file stream in little endian format.
*
* \param f Input file stream.
*
* \return The signed word read.
*/
Lib3dsIntw
lib3ds_intw_read(iostream *strm)
{
Lib3dsByte b[2];
ASSERT(strm);
strm->read((char*)&b,2);
if (s_requiresByteSwap)
{
osg::swapBytes2((char*)b);
}
return (*((Lib3dsIntw*)b));
}
/*!
* \ingroup readwrite
*
* Read a signed dword a from file stream in little endian format.
*
* \param f Input file stream.
*
* \return The signed dword read.
*/
Lib3dsIntd
lib3ds_intd_read(iostream *strm)
{
Lib3dsByte b[4];
ASSERT(strm);
strm->read((char*)&b,4);
if (s_requiresByteSwap)
{
osg::swapBytes4((char*)b);
}
return (*((Lib3dsIntd*)b));
}
/*!
* \ingroup readwrite
*
* Read a float from a file stream in little endian format.
*
* \param f Input file stream.
*
* \return The float read.
*/
Lib3dsFloat
lib3ds_float_read(iostream *strm)
{
Lib3dsByte b[4];
ASSERT(strm);
b[0]=b[1]=b[2]=b[3]=0;
strm->read((char*)&b,4);
if (s_requiresByteSwap)
{
osg::swapBytes4((char*)b);
}
return (*((Lib3dsFloat*)b));
}
/*!
* \ingroup readwrite
* \ingroup vector
*
* Read a vector from a file stream in little endian format.
*
* \param v The vector to store the data.
* \param f Input file stream.
*
* \return The float read.
*/
Lib3dsBool
lib3ds_vector_read(Lib3dsVector v, iostream *strm)
{
v[0]=lib3ds_float_read(strm);
v[1]=lib3ds_float_read(strm);
v[2]=lib3ds_float_read(strm);
if (strm->fail()) {
return(LIB3DS_FALSE);
}
/*printf("lib3ds_vector_read %f %f %f\n",v[0],v[1],v[2]);*/
return(LIB3DS_TRUE);
}
/*!
* \ingroup readwrite
*/
Lib3dsBool
lib3ds_rgb_read(Lib3dsRgb rgb, iostream *strm)
{
rgb[0]=lib3ds_float_read(strm);
rgb[1]=lib3ds_float_read(strm);
rgb[2]=lib3ds_float_read(strm);
if (strm->fail()) {
return(LIB3DS_FALSE);
}
/*printf("lib3ds_rgb_read %f %f %f\n",rgb[0],rgb[1],rgb[2]);*/
return(LIB3DS_TRUE);
}
/*!
* \ingroup readwrite
*
* Read a zero-terminated string from a file stream.
*
* \param s The buffer to store the read string.
* \param buflen Buffer length.
* \param f The input file stream.
*
* \return True on success, False otherwise.
*/
Lib3dsBool
lib3ds_string_read(char *s, int buflen, iostream *strm)
{
int k=0;
ASSERT(s);
s--;
do
{
s++;
k++;
strm->read(s,1);
} while ((*s!=0) && (k<buflen));
if (strm->fail()) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup readwrite
*
* Writes a byte into a file stream.
*
* \param b The byte to write to the file stream.
* \param f The input file stream.
*
* \return True on success, False otherwise.
*/
Lib3dsBool
lib3ds_byte_write(Lib3dsByte b, iostream *strm)
{
ASSERT(strm);
strm->write((char*)&b,1);
if (strm->fail()) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup readwrite
*
* Writes a word into a little endian file stream.
*
* \param w The word to write to the file stream.
* \param f The input file stream.
*
* \return True on success, False otherwise.
*/
Lib3dsBool
lib3ds_word_write(Lib3dsWord w, iostream *strm)
{
Lib3dsByte b[2];
ASSERT(strm);
b[1]=(Lib3dsByte)(((Lib3dsWord)w & 0xFF00) >> 8);
b[0]=(Lib3dsByte)((Lib3dsWord)w & 0x00FF);
strm->write((char*)b,2);
if (strm->fail()) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup readwrite
*
* Writes a dword into a little endian file stream.
*
* \param d The dword to write to the file stream.
* \param f The input file stream.
*
* \return True on success, False otherwise.
*/
Lib3dsBool
lib3ds_dword_write(Lib3dsDword d, iostream *strm)
{
Lib3dsByte b[4];
ASSERT(strm);
b[3]=(Lib3dsByte)(((Lib3dsDword)d & 0xFF000000) >> 24);
b[2]=(Lib3dsByte)(((Lib3dsDword)d & 0x00FF0000) >> 16);
b[1]=(Lib3dsByte)(((Lib3dsDword)d & 0x0000FF00) >> 8);
b[0]=(Lib3dsByte)(((Lib3dsDword)d & 0x000000FF));
strm->write((char*)b,4);
if (strm->fail()) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup readwrite
*
* Writes a signed byte in a file stream.
*
* \param b The signed byte to write to the file stream.
* \param f The input file stream.
*
* \return True on success, False otherwise.
*/
Lib3dsBool
lib3ds_intb_write(Lib3dsIntb b, iostream *strm)
{
ASSERT(strm);
strm->write((const char*)&b,1);
if (strm->fail()) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup readwrite
*
* Writes a signed word into a little endian file stream.
*
* \param w The signed word to write to the file stream.
* \param f The input file stream.
*
* \return True on success, False otherwise.
*/
Lib3dsBool
lib3ds_intw_write(Lib3dsIntw w, iostream *strm)
{
Lib3dsByte b[2];
ASSERT(strm);
b[1]=(Lib3dsByte)(((Lib3dsWord)w & 0xFF00) >> 8);
b[0]=(Lib3dsByte)((Lib3dsWord)w & 0x00FF);
strm->write((const char*)b,2);
if (strm->fail()) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup readwrite
*
* Writes a signed dword into a little endian file stream.
*
* \param d The signed dword to write to the file stream.
* \param f The input file stream.
*
* \return True on success, False otherwise.
*/
Lib3dsBool
lib3ds_intd_write(Lib3dsIntd d, iostream *strm)
{
Lib3dsByte b[4];
ASSERT(strm);
b[3]=(Lib3dsByte)(((Lib3dsDword)d & 0xFF000000) >> 24);
b[2]=(Lib3dsByte)(((Lib3dsDword)d & 0x00FF0000) >> 16);
b[1]=(Lib3dsByte)(((Lib3dsDword)d & 0x0000FF00) >> 8);
b[0]=(Lib3dsByte)(((Lib3dsDword)d & 0x000000FF));
strm->write((const char*)b,4);
if (strm->fail()) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup readwrite
*
* Writes a float into a little endian file stream.
*
* \param f The float to write to the file stream.
* \param f The input file stream.
*
* \return True on success, False otherwise.
*/
Lib3dsBool
lib3ds_float_write(Lib3dsFloat l, iostream *strm)
{
ASSERT(strm);
Lib3dsByte b[4];
Lib3dsByte* ptr = (Lib3dsByte*) (&l);
if (s_requiresByteSwap)
{
b[3] = *ptr++;
b[2] = *ptr++;
b[1] = *ptr++;
b[0] = *ptr++;
}
else
{
b[0] = *ptr++;
b[1] = *ptr++;
b[2] = *ptr++;
b[3] = *ptr++;
}
strm->write((char*)b,4);
if (strm->fail()) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup readwrite
* \ingroup vector
*
* Writes a vector into a file stream in little endian format.
*
* \param v The vector to write to the file stream.
* \param f Input file stream.
*/
Lib3dsBool
lib3ds_vector_write(Lib3dsVector v, iostream *strm)
{
if (!lib3ds_float_write(v[0], strm)) {
return(LIB3DS_FALSE);
}
if (!lib3ds_float_write(v[1], strm)) {
return(LIB3DS_FALSE);
}
if (!lib3ds_float_write(v[2], strm)) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup readwrite
*/
Lib3dsBool
lib3ds_rgb_write(Lib3dsRgb rgb, iostream *strm)
{
if (!lib3ds_float_write(rgb[0], strm)) {
return(LIB3DS_FALSE);
}
if (!lib3ds_float_write(rgb[1], strm)) {
return(LIB3DS_FALSE);
}
if (!lib3ds_float_write(rgb[2], strm)) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup readwrite
*
* Writes a zero-terminated string into a file stream.
*
* \param f The float to write to the file stream.
* \param f The input file stream.
*
* \return True on success, False otherwise.
*/
Lib3dsBool
lib3ds_string_write(const char *s, iostream *strm)
{
ASSERT(s);
ASSERT(strm);
do strm->write(s,1); while (*s++);
if (strm->fail()) {
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}

View File

@@ -1,63 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_READWRITE_H
#define INCLUDED_LIB3DS_READWRITE_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TYPES_H
#include "types.h"
#endif
#include <iostream>
using namespace std;
#ifdef __cplusplus
extern "C" {
#endif
extern LIB3DSAPI void setByteOrder();
extern LIB3DSAPI Lib3dsByte lib3ds_byte_read(iostream *strm);
extern LIB3DSAPI Lib3dsWord lib3ds_word_read(iostream *strm);
extern LIB3DSAPI Lib3dsDword lib3ds_dword_read(iostream *strm);
extern LIB3DSAPI Lib3dsIntb lib3ds_intb_read(iostream *strm);
extern LIB3DSAPI Lib3dsIntw lib3ds_intw_read(iostream *strm);
extern LIB3DSAPI Lib3dsIntd lib3ds_intd_read(iostream *strm);
extern LIB3DSAPI Lib3dsFloat lib3ds_float_read(iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_vector_read(Lib3dsVector v, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_rgb_read(Lib3dsRgb rgb, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_string_read(char *s, int buflen, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_byte_write(Lib3dsByte b, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_word_write(Lib3dsWord w, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_dword_write(Lib3dsDword d, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_intb_write(Lib3dsIntb b, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_intw_write(Lib3dsIntw w, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_intd_write(Lib3dsIntd d, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_float_write(Lib3dsFloat l, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_vector_write(Lib3dsVector v, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_rgb_write(Lib3dsRgb rgb, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_string_write(const char *s, iostream *strm);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -1,160 +0,0 @@
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#define LIB3DS_EXPORT
#include "shadow.h"
#include "chunk.h"
#include "readwrite.h"
#include <math.h>
/*!
* \defgroup shadow Shadow Map Settings
*
* \author J.E. Hoffmann <je-h@gmx.net>
*/
/*!
* \ingroup shadow
*/
Lib3dsBool
lib3ds_shadow_read(Lib3dsShadow *shadow, iostream *strm)
{
Lib3dsChunk c;
if (!lib3ds_chunk_read(&c, strm)) {
return(LIB3DS_FALSE);
}
switch (c.chunk) {
case LIB3DS_SHADOW_MAP_SIZE:
{
shadow->map_size=lib3ds_intw_read(strm);
}
break;
case LIB3DS_LO_SHADOW_BIAS:
{
shadow->lo_bias=lib3ds_float_read(strm);
}
break;
case LIB3DS_HI_SHADOW_BIAS:
{
shadow->hi_bias=lib3ds_float_read(strm);
}
break;
case LIB3DS_SHADOW_SAMPLES:
{
shadow->samples=lib3ds_intw_read(strm);
}
break;
case LIB3DS_SHADOW_RANGE:
{
shadow->range=lib3ds_intd_read(strm);
}
break;
case LIB3DS_SHADOW_FILTER:
{
shadow->filter=lib3ds_float_read(strm);
}
break;
case LIB3DS_RAY_BIAS:
{
shadow->ray_bias=lib3ds_float_read(strm);
}
break;
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup shadow
*/
Lib3dsBool
lib3ds_shadow_write(Lib3dsShadow *shadow, iostream *strm)
{
if (fabs(shadow->lo_bias)>LIB3DS_EPSILON) { /*---- LIB3DS_LO_SHADOW_BIAS ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_LO_SHADOW_BIAS;
c.size=10;
lib3ds_chunk_write(&c,strm);
lib3ds_float_write(shadow->lo_bias,strm);
}
if (fabs(shadow->hi_bias)>LIB3DS_EPSILON) { /*---- LIB3DS_HI_SHADOW_BIAS ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_HI_SHADOW_BIAS;
c.size=10;
lib3ds_chunk_write(&c,strm);
lib3ds_float_write(shadow->hi_bias,strm);
}
if (shadow->map_size) { /*---- LIB3DS_SHADOW_MAP_SIZE ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_SHADOW_MAP_SIZE;
c.size=8;
lib3ds_chunk_write(&c,strm);
lib3ds_intw_write(shadow->map_size,strm);
}
if (shadow->samples) { /*---- LIB3DS_SHADOW_SAMPLES ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_SHADOW_SAMPLES;
c.size=8;
lib3ds_chunk_write(&c,strm);
lib3ds_intw_write(shadow->samples,strm);
}
if (shadow->range) { /*---- LIB3DS_SHADOW_RANGE ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_SHADOW_RANGE;
c.size=10;
lib3ds_chunk_write(&c,strm);
lib3ds_intd_write(shadow->range,strm);
}
if (fabs(shadow->filter)>LIB3DS_EPSILON) { /*---- LIB3DS_SHADOW_FILTER ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_SHADOW_FILTER;
c.size=10;
lib3ds_chunk_write(&c,strm);
lib3ds_float_write(shadow->filter,strm);
}
if (fabs(shadow->ray_bias)>LIB3DS_EPSILON) { /*---- LIB3DS_RAY_BIAS ----*/
Lib3dsChunk c;
c.chunk=LIB3DS_RAY_BIAS;
c.size=10;
lib3ds_chunk_write(&c,strm);
lib3ds_float_write(shadow->ray_bias,strm);
}
return(LIB3DS_TRUE);
}
/*!
\typedef Lib3dsShadow
\ingroup shadow
\sa _Lib3dsShadow
*/

View File

@@ -1,62 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_SHADOW_H
#define INCLUDED_LIB3DS_SHADOW_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TYPES_H
#include "types.h"
#endif
#include <iostream>
using namespace std;
#ifdef __cplusplus
extern "C" {
#endif
/*!
* Shadow map settings
* \ingroup shadow
*/
struct _Lib3dsShadow {
Lib3dsIntw map_size;
Lib3dsFloat lo_bias;
Lib3dsFloat hi_bias;
Lib3dsIntw samples;
Lib3dsIntd range;
Lib3dsFloat filter;
Lib3dsFloat ray_bias;
};
extern LIB3DSAPI Lib3dsBool lib3ds_shadow_read(Lib3dsShadow *shadow, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_shadow_write(Lib3dsShadow *shadow, iostream *strm);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -1,140 +0,0 @@
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#define LIB3DS_EXPORT
#include "tcb.h"
#include "readwrite.h"
#include <math.h>
/*!
* \defgroup tcb Tension/Continuity/Bias Splines
*
* \author J.E. Hoffmann <je-h@gmx.net>
*/
/*!
* \ingroup tcb
*/
void
lib3ds_tcb(Lib3dsTcb *p, Lib3dsTcb *pc, Lib3dsTcb *c, Lib3dsTcb *nc, Lib3dsTcb *n,
Lib3dsFloat *ksm, Lib3dsFloat *ksp, Lib3dsFloat *kdm, Lib3dsFloat *kdp)
{
Lib3dsFloat tm,cm,cp,bm,bp,tmcm,tmcp,cc;
Lib3dsFloat dt,fp,fn;
if (!pc) {
pc=c;
}
if (!nc) {
nc=c;
}
fp=fn=1.0f;
if (p&&n) {
dt=0.5f*(Lib3dsFloat)(pc->frame-p->frame+n->frame-nc->frame);
fp=((Lib3dsFloat)(pc->frame-p->frame))/dt;
fn=((Lib3dsFloat)(n->frame-nc->frame))/dt;
cc=(Lib3dsFloat)fabs(c->cont);
fp=fp+cc-cc*fp;
fn=fn+cc-cc*fn;
}
cm=1.0f-c->cont;
tm=0.5f*(1.0f-c->tens);
cp=2.0f-cm;
bm=1.0f-c->bias;
bp=2.0f-bm;
tmcm=tm*cm;
tmcp=tm*cp;
*ksm=tmcm*bp*fp;
*ksp=tmcp*bm*fp;
*kdm=tmcp*bp*fn;
*kdp=tmcm*bm*fn;
}
/*!
* \ingroup tcb
*/
Lib3dsBool
lib3ds_tcb_read(Lib3dsTcb *tcb, iostream *strm)
{
Lib3dsWord flags;
tcb->frame=lib3ds_intd_read(strm);
tcb->flags=flags=lib3ds_word_read(strm);
if (flags&LIB3DS_USE_TENSION) {
tcb->tens=lib3ds_float_read(strm);
}
if (flags&LIB3DS_USE_CONTINUITY) {
tcb->cont=lib3ds_float_read(strm);
}
if (flags&LIB3DS_USE_BIAS) {
tcb->bias=lib3ds_float_read(strm);
}
if (flags&LIB3DS_USE_EASE_TO) {
tcb->ease_to=lib3ds_float_read(strm);
}
if (flags&LIB3DS_USE_EASE_FROM) {
tcb->ease_from=lib3ds_float_read(strm);
}
if (strm->fail()){
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}
/*!
* \ingroup tcb
*/
Lib3dsBool
lib3ds_tcb_write(Lib3dsTcb *tcb, iostream *strm)
{
lib3ds_intd_write(tcb->frame,strm);
lib3ds_word_write(tcb->flags,strm);
if (tcb->flags&LIB3DS_USE_TENSION) {
lib3ds_float_write(tcb->tens,strm);
}
if (tcb->flags&LIB3DS_USE_CONTINUITY) {
lib3ds_float_write(tcb->cont,strm);
}
if (tcb->flags&LIB3DS_USE_BIAS) {
lib3ds_float_write(tcb->bias,strm);
}
if (tcb->flags&LIB3DS_USE_EASE_TO) {
lib3ds_float_write(tcb->ease_to,strm);
}
if (tcb->flags&LIB3DS_USE_EASE_FROM) {
lib3ds_float_write(tcb->ease_from,strm);
}
if (strm->fail()){
return(LIB3DS_FALSE);
}
return(LIB3DS_TRUE);
}

View File

@@ -1,67 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_TCB_H
#define INCLUDED_LIB3DS_TCB_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TYPES_H
#include "types.h"
#endif
#include <iostream>
using namespace std;
#ifdef __cplusplus
extern "C" {
#endif
typedef enum _Lib3dsTcbFlags{
LIB3DS_USE_TENSION =0x0001,
LIB3DS_USE_CONTINUITY =0x0002,
LIB3DS_USE_BIAS =0x0004,
LIB3DS_USE_EASE_TO =0x0008,
LIB3DS_USE_EASE_FROM =0x0010
} Lib3dsTcbFlags;
typedef struct _Lib3dsTcb {
Lib3dsIntd frame;
Lib3dsWord flags;
Lib3dsFloat tens;
Lib3dsFloat cont;
Lib3dsFloat bias;
Lib3dsFloat ease_to;
Lib3dsFloat ease_from;
} Lib3dsTcb;
extern LIB3DSAPI void lib3ds_tcb(Lib3dsTcb *p, Lib3dsTcb *pc, Lib3dsTcb *c,
Lib3dsTcb *nc, Lib3dsTcb *n, Lib3dsFloat *ksm, Lib3dsFloat *ksp,
Lib3dsFloat *kdm, Lib3dsFloat *kdp);
extern LIB3DSAPI Lib3dsBool lib3ds_tcb_read(Lib3dsTcb *tcb, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_tcb_write(Lib3dsTcb *tcb, iostream *strm);
#ifdef __cplusplus
}
#endif
#endif

File diff suppressed because it is too large Load Diff

View File

@@ -1,209 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_TRACKS_H
#define INCLUDED_LIB3DS_TRACKS_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TCB_H
#include "tcb.h"
#endif
#ifdef __cplusplus
extern "C" {
#endif
/*!
* Track flags
* \ingroup tracks
*/
typedef enum {
LIB3DS_REPEAT =0x0001,
LIB3DS_SMOOTH =0x0002,
LIB3DS_LOCK_X =0x0008,
LIB3DS_LOCK_Y =0x0010,
LIB3DS_LOCK_Z =0x0020,
LIB3DS_UNLINK_X =0x0100,
LIB3DS_UNLINK_Y =0x0200,
LIB3DS_UNLINK_Z =0x0400
} Lib3dsTrackFlags;
/*!
* Boolean track key
* \ingroup tracks
*/
struct _Lib3dsBoolKey {
Lib3dsTcb tcb;
Lib3dsBoolKey *next;
};
/*!
* Boolean track
* \ingroup tracks
*/
struct _Lib3dsBoolTrack {
Lib3dsDword flags;
Lib3dsBoolKey *keyL;
};
/*!
* Floating-point track key
* \ingroup tracks
*/
struct _Lib3dsLin1Key {
Lib3dsTcb tcb;
Lib3dsLin1Key *next;
Lib3dsFloat value;
Lib3dsFloat dd;
Lib3dsFloat ds;
};
/*!
* Floating-point track
* \ingroup tracks
*/
struct _Lib3dsLin1Track {
Lib3dsDword flags;
Lib3dsLin1Key *keyL;
};
/*!
* Vector track key
* \ingroup tracks
*/
struct _Lib3dsLin3Key {
Lib3dsTcb tcb;
Lib3dsLin3Key *next;
Lib3dsVector value;
Lib3dsVector dd;
Lib3dsVector ds;
};
/*!
* Vector track
* \ingroup tracks
*/
struct _Lib3dsLin3Track {
Lib3dsDword flags;
Lib3dsLin3Key *keyL;
};
/*!
* Rotation track key
* \ingroup tracks
*/
struct _Lib3dsQuatKey {
Lib3dsTcb tcb;
Lib3dsQuatKey *next;
Lib3dsVector axis;
Lib3dsFloat angle;
Lib3dsQuat q;
Lib3dsQuat dd;
Lib3dsQuat ds;
};
/*!
* Rotation track
* \ingroup tracks
*/
struct _Lib3dsQuatTrack {
Lib3dsDword flags;
Lib3dsQuatKey *keyL;
};
/*!
* Morph track key
* \ingroup tracks
*/
struct _Lib3dsMorphKey {
Lib3dsTcb tcb;
Lib3dsMorphKey *next;
char name[64];
};
/*!
* Morph track
* \ingroup tracks
*/
struct _Lib3dsMorphTrack {
Lib3dsDword flags;
Lib3dsMorphKey *keyL;
};
extern LIB3DSAPI Lib3dsBoolKey* lib3ds_bool_key_new();
extern LIB3DSAPI void lib3ds_bool_key_free(Lib3dsBoolKey* key);
extern LIB3DSAPI void lib3ds_bool_track_free_keys(Lib3dsBoolTrack *track);
extern LIB3DSAPI void lib3ds_bool_track_insert(Lib3dsBoolTrack *track, Lib3dsBoolKey* key);
extern LIB3DSAPI void lib3ds_bool_track_remove(Lib3dsBoolTrack *track, Lib3dsIntd frame);
extern LIB3DSAPI void lib3ds_bool_track_eval(Lib3dsBoolTrack *track, Lib3dsBool *p, Lib3dsFloat t);
extern LIB3DSAPI Lib3dsBool lib3ds_bool_track_read(Lib3dsBoolTrack *track, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_bool_track_write(Lib3dsBoolTrack *track, iostream *strm);
extern LIB3DSAPI Lib3dsLin1Key* lib3ds_lin1_key_new();
extern LIB3DSAPI void lib3ds_lin1_key_free(Lib3dsLin1Key* key);
extern LIB3DSAPI void lib3ds_lin1_track_free_keys(Lib3dsLin1Track *track);
extern LIB3DSAPI void lib3ds_lin1_key_setup(Lib3dsLin1Key *p, Lib3dsLin1Key *cp, Lib3dsLin1Key *c,
Lib3dsLin1Key *cn, Lib3dsLin1Key *n);
extern LIB3DSAPI void lib3ds_lin1_track_setup(Lib3dsLin1Track *track);
extern LIB3DSAPI void lib3ds_lin1_track_insert(Lib3dsLin1Track *track, Lib3dsLin1Key *key);
extern LIB3DSAPI void lib3ds_lin1_track_remove(Lib3dsLin1Track *track, Lib3dsIntd frame);
extern LIB3DSAPI void lib3ds_lin1_track_eval(Lib3dsLin1Track *track, Lib3dsFloat *p, Lib3dsFloat t);
extern LIB3DSAPI Lib3dsBool lib3ds_lin1_track_read(Lib3dsLin1Track *track, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_lin1_track_write(Lib3dsLin1Track *track, iostream *strm);
extern LIB3DSAPI Lib3dsLin3Key* lib3ds_lin3_key_new();
extern LIB3DSAPI void lib3ds_lin3_key_free(Lib3dsLin3Key* key);
extern LIB3DSAPI void lib3ds_lin3_track_free_keys(Lib3dsLin3Track *track);
extern LIB3DSAPI void lib3ds_lin3_key_setup(Lib3dsLin3Key *p, Lib3dsLin3Key *cp, Lib3dsLin3Key *c,
Lib3dsLin3Key *cn, Lib3dsLin3Key *n);
extern LIB3DSAPI void lib3ds_lin3_track_setup(Lib3dsLin3Track *track);
extern LIB3DSAPI void lib3ds_lin3_track_insert(Lib3dsLin3Track *track, Lib3dsLin3Key *key);
extern LIB3DSAPI void lib3ds_lin3_track_remove(Lib3dsLin3Track *track, Lib3dsIntd frame);
extern LIB3DSAPI void lib3ds_lin3_track_eval(Lib3dsLin3Track *track, Lib3dsVector p, Lib3dsFloat t);
extern LIB3DSAPI Lib3dsBool lib3ds_lin3_track_read(Lib3dsLin3Track *track, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_lin3_track_write(Lib3dsLin3Track *track, iostream *strm);
extern LIB3DSAPI Lib3dsQuatKey* lib3ds_quat_key_new();
extern LIB3DSAPI void lib3ds_quat_key_free(Lib3dsQuatKey* key);
extern LIB3DSAPI void lib3ds_quat_track_free_keys(Lib3dsQuatTrack *track);
extern LIB3DSAPI void lib3ds_quat_key_setup(Lib3dsQuatKey *p, Lib3dsQuatKey *cp, Lib3dsQuatKey *c,
Lib3dsQuatKey *cn, Lib3dsQuatKey *n);
extern LIB3DSAPI void lib3ds_quat_track_setup(Lib3dsQuatTrack *track);
extern LIB3DSAPI void lib3ds_quat_track_insert(Lib3dsQuatTrack *track, Lib3dsQuatKey *key);
extern LIB3DSAPI void lib3ds_quat_track_remove(Lib3dsQuatTrack *track, Lib3dsIntd frame);
extern LIB3DSAPI void lib3ds_quat_track_eval(Lib3dsQuatTrack *track, Lib3dsQuat p, Lib3dsFloat t);
extern LIB3DSAPI Lib3dsBool lib3ds_quat_track_read(Lib3dsQuatTrack *track, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_quat_track_write(Lib3dsQuatTrack *track, iostream *strm);
extern LIB3DSAPI Lib3dsMorphKey* lib3ds_morph_key_new();
extern LIB3DSAPI void lib3ds_morph_key_free(Lib3dsMorphKey* key);
extern LIB3DSAPI void lib3ds_morph_track_free_keys(Lib3dsMorphTrack *track);
extern LIB3DSAPI void lib3ds_morph_track_insert(Lib3dsMorphTrack *track, Lib3dsMorphKey *key);
extern LIB3DSAPI void lib3ds_morph_track_remove(Lib3dsMorphTrack *track, Lib3dsIntd frame);
extern LIB3DSAPI void lib3ds_morph_track_eval(Lib3dsMorphTrack *track, char *p, Lib3dsFloat t);
extern LIB3DSAPI Lib3dsBool lib3ds_morph_track_read(Lib3dsMorphTrack *track, iostream *strm);
extern LIB3DSAPI Lib3dsBool lib3ds_morph_track_write(Lib3dsMorphTrack *track, iostream *strm);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -1,148 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_TYPES_H
#define INCLUDED_LIB3DS_TYPES_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifdef __cplusplus
extern "C" {
#endif
/*
* #if defined (_LIB3DS_DLL) && defined(_WIN32) && (!defined(__GNUC__))
* #ifdef LIB3DS_EXPORT
* #define LIB3DSAPI __declspec(dllexport)
* #else
* #define LIB3DSAPI __declspec(dllimport)
* #endif
* #else
* #define LIB3DSAPI
* #endif
*/
// within the OSG just use the libary inline, no need to export symbols.
#define LIB3DSAPI
#define LIB3DS_TRUE 1
#define LIB3DS_FALSE 0
typedef int Lib3dsBool;
typedef unsigned char Lib3dsByte;
typedef unsigned short Lib3dsWord;
typedef unsigned int Lib3dsDword;
typedef signed char Lib3dsIntb;
typedef signed short Lib3dsIntw;
typedef signed int Lib3dsIntd;
typedef float Lib3dsFloat;
typedef double Lib3dsDouble;
typedef float Lib3dsVector[3];
typedef float Lib3dsTexel[2];
typedef float Lib3dsQuat[4];
typedef float Lib3dsMatrix[4][4];
typedef float Lib3dsRgb[3];
typedef float Lib3dsRgba[4];
#define LIB3DS_EPSILON (1e-8)
#define LIB3DS_PI 3.14159265358979323846
#define LIB3DS_TWOPI (2.0*LIB3DS_PI)
#define LIB3DS_HALFPI (LIB3DS_PI/2.0)
#define LIB3DS_DEG(x) ((180.0/LIB3DS_PI)*(x))
#define LIB3DS_RAD(x) ((LIB3DS_PI/180.0)*(x))
#ifndef INCLUDED_STDIO_H
#define INCLUDED_STDIO_H
#include <stdio.h>
#endif
#ifdef _DEBUG
#ifndef ASSERT
#include <assert.h>
#define ASSERT(__expr) assert(__expr)
#endif
#define LIB3DS_ERROR_LOG \
{printf("\t***LIB3DS_ERROR_LOG*** %s : %d\n", __FILE__, __LINE__);}
#else
#ifndef ASSERT
#define ASSERT(__expr)
#endif
#define LIB3DS_ERROR_LOG
#endif
typedef struct _Lib3dsFile Lib3dsFile;
typedef struct _Lib3dsBackground Lib3dsBackground;
typedef struct _Lib3dsAtmosphere Lib3dsAtmosphere;
typedef struct _Lib3dsShadow Lib3dsShadow;
typedef struct _Lib3dsViewport Lib3dsViewport;
typedef struct _Lib3dsMaterial Lib3dsMaterial;
typedef struct _Lib3dsFace Lib3dsFace;
typedef struct _Lib3dsBoxMap Lib3dsBoxMap;
typedef struct _Lib3dsMapData Lib3dsMapData;
typedef struct _Lib3dsMesh Lib3dsMesh;
typedef struct _Lib3dsCamera Lib3dsCamera;
typedef struct _Lib3dsLight Lib3dsLight;
typedef struct _Lib3dsBoolKey Lib3dsBoolKey;
typedef struct _Lib3dsBoolTrack Lib3dsBoolTrack;
typedef struct _Lib3dsLin1Key Lib3dsLin1Key;
typedef struct _Lib3dsLin1Track Lib3dsLin1Track;
typedef struct _Lib3dsLin3Key Lib3dsLin3Key;
typedef struct _Lib3dsLin3Track Lib3dsLin3Track;
typedef struct _Lib3dsQuatKey Lib3dsQuatKey;
typedef struct _Lib3dsQuatTrack Lib3dsQuatTrack;
typedef struct _Lib3dsMorphKey Lib3dsMorphKey;
typedef struct _Lib3dsMorphTrack Lib3dsMorphTrack;
typedef enum _Lib3dsNodeTypes {
LIB3DS_UNKNOWN_NODE =0,
LIB3DS_AMBIENT_NODE =1,
LIB3DS_OBJECT_NODE =2,
LIB3DS_CAMERA_NODE =3,
LIB3DS_TARGET_NODE =4,
LIB3DS_LIGHT_NODE =5,
LIB3DS_SPOT_NODE =6
} Lib3dsNodeTypes;
typedef struct _Lib3dsNode Lib3dsNode;
typedef union _Lib3dsUserData {
void *p;
Lib3dsIntd i;
Lib3dsDword d;
Lib3dsFloat f;
Lib3dsMaterial *material;
Lib3dsMesh *mesh;
Lib3dsCamera *camera;
Lib3dsLight *light;
Lib3dsNode *node;
} Lib3dsUserData;
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -1,275 +0,0 @@
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#define LIB3DS_EXPORT
#include "vector.h"
#include <math.h>
/*!
* \defgroup vector Vector Mathematics
*
* \author J.E. Hoffmann <je-h@gmx.net>
*/
/*!
* \typedef Lib3dsVector
* \ingroup vector
*/
/*!
* \ingroup vector
*/
void
lib3ds_vector_zero(Lib3dsVector c)
{
int i;
for (i=0; i<3; ++i) {
c[i]=0.0f;
}
}
/*!
* \ingroup vector
*/
void
lib3ds_vector_copy(Lib3dsVector dest, Lib3dsVector src)
{
int i;
for (i=0; i<3; ++i) {
dest[i]=src[i];
}
}
/*!
* \ingroup vector
*/
void
lib3ds_vector_neg(Lib3dsVector c)
{
int i;
for (i=0; i<3; ++i) {
c[i]=-c[i];
}
}
/*!
* \ingroup vector
*/
void
lib3ds_vector_add(Lib3dsVector c, Lib3dsVector a, Lib3dsVector b)
{
int i;
for (i=0; i<3; ++i) {
c[i]=a[i]+b[i];
}
}
/*!
* \ingroup vector
*/
void
lib3ds_vector_sub(Lib3dsVector c, Lib3dsVector a, Lib3dsVector b)
{
int i;
for (i=0; i<3; ++i) {
c[i]=a[i]-b[i];
}
}
/*!
* \ingroup vector
*/
void
lib3ds_vector_scalar(Lib3dsVector c, Lib3dsFloat k)
{
int i;
for (i=0; i<3; ++i) {
c[i]*=k;
}
}
/*!
* \ingroup vector
*/
void
lib3ds_vector_cross(Lib3dsVector c, Lib3dsVector a, Lib3dsVector b)
{
c[0]=a[1]*b[2] - a[2]*b[1];
c[1]=a[2]*b[0] - a[0]*b[2];
c[2]=a[0]*b[1] - a[1]*b[0];
}
/*!
* \ingroup vector
*/
Lib3dsFloat
lib3ds_vector_dot(Lib3dsVector a, Lib3dsVector b)
{
return(a[0]*b[0] + a[1]*b[1] + a[2]*b[2]);
}
/*!
* \ingroup vector
*/
Lib3dsFloat
lib3ds_vector_squared(Lib3dsVector c)
{
return(c[0]*c[0] + c[1]*c[1] + c[2]*c[2]);
}
/*!
* \ingroup vector
*/
Lib3dsFloat
lib3ds_vector_length(Lib3dsVector c)
{
return((Lib3dsFloat)sqrt(c[0]*c[0] + c[1]*c[1] + c[2]*c[2]));
}
/*!
* \ingroup vector
*/
void
lib3ds_vector_normalize(Lib3dsVector c)
{
Lib3dsFloat l,m;
l=(Lib3dsFloat)sqrt(c[0]*c[0] + c[1]*c[1] + c[2]*c[2]);
if (fabs(l)<LIB3DS_EPSILON) {
c[0]=c[1]=c[2]=0.0f;
if ((c[0]>=c[1]) && (c[0]>=c[2])) {
c[0]=1.0f;
}
else
if (c[1]>=c[2]) {
c[1]=1.0f;
}
else {
c[2]=1.0f;
}
}
else {
m=1.0f/l;
c[0]*=m;
c[1]*=m;
c[2]*=m;
}
}
/*!
* \ingroup vector
*/
void
lib3ds_vector_normal(Lib3dsVector n, Lib3dsVector a, Lib3dsVector b, Lib3dsVector c)
{
Lib3dsVector p,q;
lib3ds_vector_sub(p,c,b);
lib3ds_vector_sub(q,a,b);
lib3ds_vector_cross(n,p,q);
lib3ds_vector_normalize(n);
}
/*!
* \ingroup vector
*/
void
lib3ds_vector_transform(Lib3dsVector c, Lib3dsMatrix m, Lib3dsVector a)
{
c[0]= m[0][0]*a[0] + m[1][0]*a[1] + m[2][0]*a[2] + m[3][0];
c[1]= m[0][1]*a[0] + m[1][1]*a[1] + m[2][1]*a[2] + m[3][1];
c[2]= m[0][2]*a[0] + m[1][2]*a[1] + m[2][2]*a[2] + m[3][2];
}
/*!
* \ingroup vector
*/
void
lib3ds_vector_cubic(Lib3dsVector c, Lib3dsVector a, Lib3dsVector p, Lib3dsVector q,
Lib3dsVector b, Lib3dsFloat t)
{
Lib3dsDouble x,y,z,w;
x=2*t*t*t - 3*t*t + 1;
y=-2*t*t*t + 3*t*t;
z=t*t*t - 2*t*t + t;
w=t*t*t - t*t;
c[0]=(Lib3dsFloat)(x*a[0] + y*b[0] + z*p[0] + w*q[0]);
c[1]=(Lib3dsFloat)(x*a[1] + y*b[1] + z*p[1] + w*q[1]);
c[2]=(Lib3dsFloat)(x*a[2] + y*b[2] + z*p[2] + w*q[2]);
}
/*!
* c[i] = min(c[i], a[i]);
* \ingroup vector
*/
void
lib3ds_vector_min(Lib3dsVector c, Lib3dsVector a)
{
int i;
for (i=0; i<3; ++i) {
if (a[i]<c[i]) {
c[i] = a[i];
}
}
}
/*!
* c[i] = max(c[i], a[i]);
* \ingroup vector
*/
void
lib3ds_vector_max(Lib3dsVector c, Lib3dsVector a)
{
int i;
for (i=0; i<3; ++i) {
if (a[i]>c[i]) {
c[i] = a[i];
}
}
}
/*!
* \ingroup vector
*/
void
lib3ds_vector_dump(Lib3dsVector c)
{
fprintf(stderr, "%f %f %f\n", c[0], c[1], c[2]);
}

View File

@@ -1,58 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_VECTOR_H
#define INCLUDED_LIB3DS_VECTOR_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TYPES_H
#include "types.h"
#endif
#ifdef __cplusplus
extern "C" {
#endif
extern LIB3DSAPI void lib3ds_vector_zero(Lib3dsVector c);
extern LIB3DSAPI void lib3ds_vector_copy(Lib3dsVector dest, Lib3dsVector src);
extern LIB3DSAPI void lib3ds_vector_neg(Lib3dsVector c);
extern LIB3DSAPI void lib3ds_vector_add(Lib3dsVector c, Lib3dsVector a, Lib3dsVector b);
extern LIB3DSAPI void lib3ds_vector_sub(Lib3dsVector c, Lib3dsVector a, Lib3dsVector b);
extern LIB3DSAPI void lib3ds_vector_scalar(Lib3dsVector c, Lib3dsFloat k);
extern LIB3DSAPI void lib3ds_vector_cross(Lib3dsVector c, Lib3dsVector a, Lib3dsVector b);
extern LIB3DSAPI Lib3dsFloat lib3ds_vector_dot(Lib3dsVector a, Lib3dsVector b);
extern LIB3DSAPI Lib3dsFloat lib3ds_vector_squared(Lib3dsVector c);
extern LIB3DSAPI Lib3dsFloat lib3ds_vector_length(Lib3dsVector c);
extern LIB3DSAPI void lib3ds_vector_normalize(Lib3dsVector c);
extern LIB3DSAPI void lib3ds_vector_normal(Lib3dsVector n, Lib3dsVector a,
Lib3dsVector b, Lib3dsVector c);
extern LIB3DSAPI void lib3ds_vector_transform(Lib3dsVector c, Lib3dsMatrix m, Lib3dsVector a);
extern LIB3DSAPI void lib3ds_vector_cubic(Lib3dsVector c, Lib3dsVector a, Lib3dsVector p,
Lib3dsVector q, Lib3dsVector b, Lib3dsFloat t);
extern LIB3DSAPI void lib3ds_vector_min(Lib3dsVector c, Lib3dsVector a);
extern LIB3DSAPI void lib3ds_vector_max(Lib3dsVector c, Lib3dsVector a);
extern LIB3DSAPI void lib3ds_vector_dump(Lib3dsVector c);
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -1,367 +0,0 @@
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#define LIB3DS_EXPORT
#include "viewport.h"
#include "chunk.h"
#include "readwrite.h"
#include <stdlib.h>
#include <string.h>
/*!
* \defgroup viewport Viewport and default view settings
*
* \author J.E. Hoffmann <je-h@gmx.net>
*/
/*!
* \ingroup viewport
*/
Lib3dsBool
lib3ds_viewport_read(Lib3dsViewport *viewport, iostream *strm)
{
Lib3dsChunk c;
Lib3dsWord chunk;
if (!lib3ds_chunk_read_start(&c, 0, strm)) {
return(LIB3DS_FALSE);
}
switch (c.chunk) {
case LIB3DS_VIEWPORT_LAYOUT:
{
int cur=0;
viewport->layout.style=lib3ds_word_read(strm);
viewport->layout.active=lib3ds_intw_read(strm);
lib3ds_intw_read(strm);
viewport->layout.swap=lib3ds_intw_read(strm);
lib3ds_intw_read(strm);
viewport->layout.swap_prior=lib3ds_intw_read(strm);
viewport->layout.swap_view=lib3ds_intw_read(strm);
lib3ds_chunk_read_tell(&c, strm);
while ((chunk=lib3ds_chunk_read_next(&c, strm))!=0) {
switch (chunk) {
case LIB3DS_VIEWPORT_SIZE:
{
viewport->layout.position[0]=lib3ds_word_read(strm);
viewport->layout.position[1]=lib3ds_word_read(strm);
viewport->layout.size[0]=lib3ds_word_read(strm);
viewport->layout.size[1]=lib3ds_word_read(strm);
}
break;
case LIB3DS_VIEWPORT_DATA_3:
{
lib3ds_viewport_set_views(viewport,cur+1);
lib3ds_intw_read(strm);
viewport->layout.viewL[cur].axis_lock=lib3ds_word_read(strm);
viewport->layout.viewL[cur].position[0]=lib3ds_intw_read(strm);
viewport->layout.viewL[cur].position[1]=lib3ds_intw_read(strm);
viewport->layout.viewL[cur].size[0]=lib3ds_intw_read(strm);
viewport->layout.viewL[cur].size[1]=lib3ds_intw_read(strm);
viewport->layout.viewL[cur].type=lib3ds_word_read(strm);
viewport->layout.viewL[cur].zoom=lib3ds_float_read(strm);
lib3ds_vector_read(viewport->layout.viewL[cur].center,strm);
viewport->layout.viewL[cur].horiz_angle=lib3ds_float_read(strm);
viewport->layout.viewL[cur].vert_angle=lib3ds_float_read(strm);
strm->read(viewport->layout.viewL[cur].camera,11);
++cur;
}
break;
case LIB3DS_VIEWPORT_DATA:
/* 3DS R2 & R3 chunk
unsupported */
break;
default:
lib3ds_chunk_unknown(chunk);
}
}
}
break;
case LIB3DS_DEFAULT_VIEW:
{
memset(&viewport->default_view,0,sizeof(Lib3dsDefaultView));
while ((chunk=lib3ds_chunk_read_next(&c, strm))!=0) {
switch (chunk) {
case LIB3DS_VIEW_TOP:
{
viewport->default_view.type=LIB3DS_VIEW_TYPE_TOP;
lib3ds_vector_read(viewport->default_view.position,strm);
viewport->default_view.width=lib3ds_float_read(strm);
}
break;
case LIB3DS_VIEW_BOTTOM:
{
viewport->default_view.type=LIB3DS_VIEW_TYPE_BOTTOM;
lib3ds_vector_read(viewport->default_view.position,strm);
viewport->default_view.width=lib3ds_float_read(strm);
}
break;
case LIB3DS_VIEW_LEFT:
{
viewport->default_view.type=LIB3DS_VIEW_TYPE_LEFT;
lib3ds_vector_read(viewport->default_view.position,strm);
viewport->default_view.width=lib3ds_float_read(strm);
}
break;
case LIB3DS_VIEW_RIGHT:
{
viewport->default_view.type=LIB3DS_VIEW_TYPE_RIGHT;
lib3ds_vector_read(viewport->default_view.position,strm);
viewport->default_view.width=lib3ds_float_read(strm);
}
break;
case LIB3DS_VIEW_FRONT:
{
viewport->default_view.type=LIB3DS_VIEW_TYPE_FRONT;
lib3ds_vector_read(viewport->default_view.position,strm);
viewport->default_view.width=lib3ds_float_read(strm);
}
break;
case LIB3DS_VIEW_BACK:
{
viewport->default_view.type=LIB3DS_VIEW_TYPE_BACK;
lib3ds_vector_read(viewport->default_view.position,strm);
viewport->default_view.width=lib3ds_float_read(strm);
}
break;
case LIB3DS_VIEW_USER:
{
viewport->default_view.type=LIB3DS_VIEW_TYPE_USER;
lib3ds_vector_read(viewport->default_view.position,strm);
viewport->default_view.width=lib3ds_float_read(strm);
viewport->default_view.horiz_angle=lib3ds_float_read(strm);
viewport->default_view.vert_angle=lib3ds_float_read(strm);
viewport->default_view.roll_angle=lib3ds_float_read(strm);
}
break;
case LIB3DS_VIEW_CAMERA:
{
viewport->default_view.type=LIB3DS_VIEW_TYPE_CAMERA;
strm->read(viewport->default_view.camera,11);
}
break;
default:
lib3ds_chunk_unknown(chunk);
}
}
}
break;
}
lib3ds_chunk_read_end(&c, strm);
return(LIB3DS_TRUE);
}
/*!
* \ingroup viewport
*/
void
lib3ds_viewport_set_views(Lib3dsViewport *viewport, Lib3dsDword views)
{
ASSERT(viewport);
if (viewport->layout.views) {
if (views) {
viewport->layout.views=views;
viewport->layout.viewL=(Lib3dsView*)realloc(viewport->layout.viewL, sizeof(Lib3dsView)*views);
}
else {
free(viewport->layout.viewL);
viewport->layout.views=0;
viewport->layout.viewL=0;
}
}
else {
viewport->layout.views=views;
viewport->layout.viewL= views ? (Lib3dsView*)calloc(sizeof(Lib3dsView),views) : 0;
}
}
/*!
* \ingroup viewport
*/
Lib3dsBool
lib3ds_viewport_write(Lib3dsViewport *viewport, iostream *strm)
{
if (viewport->layout.views) {
Lib3dsChunk c;
unsigned i;
c.chunk=LIB3DS_VIEWPORT_LAYOUT;
if (!lib3ds_chunk_write_start(&c,strm)) {
return(LIB3DS_FALSE);
}
lib3ds_word_write(viewport->layout.style,strm);
lib3ds_intw_write(viewport->layout.active,strm);
lib3ds_intw_write(0,strm);
lib3ds_intw_write(viewport->layout.swap,strm);
lib3ds_intw_write(0,strm);
lib3ds_intw_write(viewport->layout.swap_prior,strm);
lib3ds_intw_write(viewport->layout.swap_view,strm);
{
Lib3dsChunk c;
c.chunk=LIB3DS_VIEWPORT_SIZE;
c.size=14;
lib3ds_chunk_write(&c,strm);
lib3ds_intw_write(viewport->layout.position[0],strm);
lib3ds_intw_write(viewport->layout.position[1],strm);
lib3ds_intw_write(viewport->layout.size[0],strm);
lib3ds_intw_write(viewport->layout.size[1],strm);
}
for (i=0; i<viewport->layout.views; ++i) {
Lib3dsChunk c;
c.chunk=LIB3DS_VIEWPORT_DATA_3;
c.size=55;
lib3ds_chunk_write(&c,strm);
lib3ds_intw_write(0,strm);
lib3ds_word_write(viewport->layout.viewL[i].axis_lock,strm);
lib3ds_intw_write(viewport->layout.viewL[i].position[0],strm);
lib3ds_intw_write(viewport->layout.viewL[i].position[1],strm);
lib3ds_intw_write(viewport->layout.viewL[i].size[0],strm);
lib3ds_intw_write(viewport->layout.viewL[i].size[1],strm);
lib3ds_word_write(viewport->layout.viewL[i].type,strm);
lib3ds_float_write(viewport->layout.viewL[i].zoom,strm);
lib3ds_vector_write(viewport->layout.viewL[i].center,strm);
lib3ds_float_write(viewport->layout.viewL[i].horiz_angle,strm);
lib3ds_float_write(viewport->layout.viewL[i].vert_angle,strm);
strm->write(viewport->layout.viewL[i].camera,11);
}
if (!lib3ds_chunk_write_end(&c,strm)) {
return(LIB3DS_FALSE);
}
}
if (viewport->default_view.type) {
Lib3dsChunk c;
c.chunk=LIB3DS_DEFAULT_VIEW;
if (!lib3ds_chunk_write_start(&c,strm)) {
return(LIB3DS_FALSE);
}
switch (viewport->default_view.type) {
case LIB3DS_VIEW_TYPE_TOP:
{
Lib3dsChunk c;
c.chunk=LIB3DS_VIEW_TOP;
c.size=22;
lib3ds_chunk_write(&c,strm);
lib3ds_vector_write(viewport->default_view.position,strm);
lib3ds_float_write(viewport->default_view.width,strm);
}
break;
case LIB3DS_VIEW_TYPE_BOTTOM:
{
Lib3dsChunk c;
c.chunk=LIB3DS_VIEW_BOTTOM;
c.size=22;
lib3ds_chunk_write(&c,strm);
lib3ds_vector_write(viewport->default_view.position,strm);
lib3ds_float_write(viewport->default_view.width,strm);
}
break;
case LIB3DS_VIEW_TYPE_LEFT:
{
Lib3dsChunk c;
c.chunk=LIB3DS_VIEW_LEFT;
c.size=22;
lib3ds_chunk_write(&c,strm);
lib3ds_vector_write(viewport->default_view.position,strm);
lib3ds_float_write(viewport->default_view.width,strm);
}
break;
case LIB3DS_VIEW_TYPE_RIGHT:
{
Lib3dsChunk c;
c.chunk=LIB3DS_VIEW_RIGHT;
c.size=22;
lib3ds_chunk_write(&c,strm);
lib3ds_vector_write(viewport->default_view.position,strm);
lib3ds_float_write(viewport->default_view.width,strm);
}
break;
case LIB3DS_VIEW_TYPE_FRONT:
{
Lib3dsChunk c;
c.chunk=LIB3DS_VIEW_FRONT;
c.size=22;
lib3ds_chunk_write(&c,strm);
lib3ds_vector_write(viewport->default_view.position,strm);
lib3ds_float_write(viewport->default_view.width,strm);
}
break;
case LIB3DS_VIEW_TYPE_BACK:
{
Lib3dsChunk c;
c.chunk=LIB3DS_VIEW_BACK;
c.size=22;
lib3ds_chunk_write(&c,strm);
lib3ds_vector_write(viewport->default_view.position,strm);
lib3ds_float_write(viewport->default_view.width,strm);
}
break;
case LIB3DS_VIEW_TYPE_USER:
{
Lib3dsChunk c;
c.chunk=LIB3DS_VIEW_USER;
c.size=34;
lib3ds_chunk_write(&c,strm);
lib3ds_vector_write(viewport->default_view.position,strm);
lib3ds_float_write(viewport->default_view.width,strm);
lib3ds_float_write(viewport->default_view.horiz_angle,strm);
lib3ds_float_write(viewport->default_view.vert_angle,strm);
lib3ds_float_write(viewport->default_view.roll_angle,strm);
}
break;
case LIB3DS_VIEW_TYPE_CAMERA:
{
Lib3dsChunk c;
c.chunk=LIB3DS_VIEW_CAMERA;
c.size=17;
lib3ds_chunk_write(&c,strm);
strm->write(viewport->default_view.camera,11); // NAH Potential issue here
}
break;
}
if (!lib3ds_chunk_write_end(&c,strm)) {
return(LIB3DS_FALSE);
}
}
return(LIB3DS_TRUE);
}
/*!
\typedef Lib3dsViewport
\ingroup viewport
\sa _Lib3dsViewport
*/

View File

@@ -1,139 +0,0 @@
/* -*- c -*- */
#ifndef INCLUDED_LIB3DS_VIEWPORT_H
#define INCLUDED_LIB3DS_VIEWPORT_H
/*
* The 3D Studio File Format Library
* Copyright (C) 1996-2001 by J.E. Hoffmann <je-h@gmx.net>
* All rights reserved.
*
* 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 2.1 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, write to the Free Software Foundation,
* Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* $Id$
*/
#ifndef INCLUDED_LIB3DS_TYPES_H
#include "types.h"
#endif
#include <iostream>
using namespace std;
#ifdef __cplusplus
extern "C" {
#endif
/*!
* Layout view types
* \ingroup viewport
*/
typedef enum _Lib3dsViewType {
LIB3DS_VIEW_TYPE_NOT_USED =0,
LIB3DS_VIEW_TYPE_TOP =1,
LIB3DS_VIEW_TYPE_BOTTOM =2,
LIB3DS_VIEW_TYPE_LEFT =3,
LIB3DS_VIEW_TYPE_RIGHT =4,
LIB3DS_VIEW_TYPE_FRONT =5,
LIB3DS_VIEW_TYPE_BACK =6,
LIB3DS_VIEW_TYPE_USER =7,
LIB3DS_VIEW_TYPE_SPOTLIGHT =18,
LIB3DS_VIEW_TYPE_CAMERA =65535
} Lib3dsViewType;
/*!
* Layout view settings
* \ingroup viewport
*/
typedef struct _Lib3dsView {
Lib3dsWord type;
Lib3dsWord axis_lock;
Lib3dsIntw position[2];
Lib3dsIntw size[2];
Lib3dsFloat zoom;
Lib3dsVector center;
Lib3dsFloat horiz_angle;
Lib3dsFloat vert_angle;
char camera[11];
} Lib3dsView;
/*!
* Layout styles
* \ingroup viewport
*/
typedef enum _Lib3dsLayoutStyle {
LIB3DS_LAYOUT_SINGLE =0,
LIB3DS_LAYOUT_TWO_PANE_VERT_SPLIT =1,
LIB3DS_LAYOUT_TWO_PANE_HORIZ_SPLIT =2,
LIB3DS_LAYOUT_FOUR_PANE =3,
LIB3DS_LAYOUT_THREE_PANE_LEFT_SPLIT =4,
LIB3DS_LAYOUT_THREE_PANE_BOTTOM_SPLIT =5,
LIB3DS_LAYOUT_THREE_PANE_RIGHT_SPLIT =6,
LIB3DS_LAYOUT_THREE_PANE_TOP_SPLIT =7,
LIB3DS_LAYOUT_THREE_PANE_VERT_SPLIT =8,
LIB3DS_LAYOUT_THREE_PANE_HORIZ_SPLIT =9,
LIB3DS_LAYOUT_FOUR_PANE_LEFT_SPLIT =10,
LIB3DS_LAYOUT_FOUR_PANE_RIGHT_SPLIT =11
} Lib3dsLayoutStyle;
/*!
* Viewport layout settings
* \ingroup viewport
*/
typedef struct _Lib3dsLayout {
Lib3dsWord style;
Lib3dsIntw active;
Lib3dsIntw swap;
Lib3dsIntw swap_prior;
Lib3dsIntw swap_view;
Lib3dsWord position[2];
Lib3dsWord size[2];
Lib3dsDword views;
Lib3dsView *viewL;
} Lib3dsLayout;
/*!
* Default view settings
* \ingroup viewport
*/
typedef struct _Lib3dsDefaultView {
Lib3dsWord type;
Lib3dsVector position;
Lib3dsFloat width;
Lib3dsFloat horiz_angle;
Lib3dsFloat vert_angle;
Lib3dsFloat roll_angle;
char camera[64];
} Lib3dsDefaultView;
/*!
* Viewport and default view settings
* \ingroup viewport
*/
struct _Lib3dsViewport {
Lib3dsLayout layout;
Lib3dsDefaultView default_view;
};
extern LIB3DSAPI Lib3dsBool lib3ds_viewport_read(Lib3dsViewport *viewport, iostream *strm);
extern LIB3DSAPI void lib3ds_viewport_set_views(Lib3dsViewport *viewport, Lib3dsDword views);
extern LIB3DSAPI Lib3dsBool lib3ds_viewport_write(Lib3dsViewport *viewport, iostream *strm);
#ifdef __cplusplus
}
#endif
#endif