mirror of https://github.com/aap/librw.git
implemented cameras for streaming
This commit is contained in:
parent
02c809625a
commit
da0417571d
250
src/clump.cpp
250
src/clump.cpp
|
@ -2,6 +2,7 @@
|
|||
#include <cstdlib>
|
||||
#include <cstring>
|
||||
#include <cassert>
|
||||
#include <cmath>
|
||||
|
||||
#include <new>
|
||||
|
||||
|
@ -23,7 +24,8 @@ Frame*
|
|||
Frame::create(void)
|
||||
{
|
||||
Frame *f = (Frame*)malloc(PluginBase::s_size);
|
||||
f->object.init(0, 0);
|
||||
assert(f != NULL);
|
||||
f->object.init(Frame::ID, 0);
|
||||
f->objectList.init();
|
||||
f->child = NULL;
|
||||
f->next = NULL;
|
||||
|
@ -56,13 +58,13 @@ Frame::destroy(void)
|
|||
Frame *child;
|
||||
if(parent){
|
||||
// remove from child list
|
||||
child = parent->child;
|
||||
if(child == this)
|
||||
parent->child = this->next;
|
||||
else{
|
||||
for(child = child->next; child != this; child = child->next)
|
||||
;
|
||||
child->next = this->next;
|
||||
child = parent->child;
|
||||
if(child == this)
|
||||
parent->child = this->next;
|
||||
else{
|
||||
for(child = child->next; child != this; child = child->next)
|
||||
;
|
||||
child->next = this->next;
|
||||
}
|
||||
this->object.parent = NULL;
|
||||
// Doesn't seem to make much sense, blame criterion.
|
||||
|
@ -77,10 +79,10 @@ void
|
|||
Frame::destroyHierarchy(void)
|
||||
{
|
||||
Frame *next;
|
||||
for(Frame *child = this->child; child; child = next){
|
||||
next = child->next;
|
||||
child->destroyHierarchy();
|
||||
}
|
||||
for(Frame *child = this->child; child; child = next){
|
||||
next = child->next;
|
||||
child->destroyHierarchy();
|
||||
}
|
||||
this->destructPlugins();
|
||||
free(this);
|
||||
}
|
||||
|
@ -104,7 +106,7 @@ Frame::addChild(Frame *child)
|
|||
Frame*
|
||||
Frame::removeChild(void)
|
||||
{
|
||||
Frame *parent = (Frame*)this->object.parent;
|
||||
Frame *parent = this->getParent();
|
||||
if(parent->child == this)
|
||||
parent->child = this->next;
|
||||
else{
|
||||
|
@ -150,7 +152,7 @@ Frame::updateLTM(void)
|
|||
{
|
||||
if(!this->dirty)
|
||||
return;
|
||||
Frame *parent = (Frame*)this->object.parent;
|
||||
Frame *parent = this->getParent();
|
||||
if(parent){
|
||||
parent->updateLTM();
|
||||
matrixMult(this->ltm, parent->ltm, this->matrix);
|
||||
|
@ -179,8 +181,8 @@ Frame::setDirty(void)
|
|||
void
|
||||
Frame::setHierarchyRoot(Frame *root)
|
||||
{
|
||||
this->root = root;
|
||||
for(Frame *child = this->child; child; child = child->next)
|
||||
this->root = root;
|
||||
for(Frame *child = this->child; child; child = child->next)
|
||||
child->setHierarchyRoot(root);
|
||||
}
|
||||
|
||||
|
@ -196,7 +198,7 @@ Frame::cloneAndLink(Frame *clonedroot)
|
|||
frame->root = clonedroot;
|
||||
this->root = frame; // Remember cloned frame
|
||||
for(Frame *child = this->child; child; child = child->next){
|
||||
Frame *clonedchild = child->cloneAndLink(clonedroot);
|
||||
Frame *clonedchild = child->cloneAndLink(clonedroot);
|
||||
clonedchild->next = frame->child;
|
||||
frame->child = clonedchild;
|
||||
clonedchild->object.parent = frame;
|
||||
|
@ -240,9 +242,11 @@ Clump*
|
|||
Clump::create(void)
|
||||
{
|
||||
Clump *clump = (Clump*)malloc(PluginBase::s_size);
|
||||
clump->object.init(2, 0);
|
||||
assert(clump != NULL);
|
||||
clump->object.init(Clump::ID, 0);
|
||||
clump->atomics.init();
|
||||
clump->lights.init();
|
||||
clump->cameras.init();
|
||||
clump->constructPlugins();
|
||||
return clump;
|
||||
}
|
||||
|
@ -273,6 +277,8 @@ Clump::destroy(void)
|
|||
Atomic::fromClump(lnk)->destroy();
|
||||
FORLIST(lnk, this->lights)
|
||||
Light::fromClump(lnk)->destroy();
|
||||
FORLIST(lnk, this->cameras)
|
||||
Camera::fromClump(lnk)->destroy();
|
||||
if(f = this->getFrame())
|
||||
f->destroyHierarchy();
|
||||
free(this);
|
||||
|
@ -296,6 +302,15 @@ Clump::countLights(void)
|
|||
return n;
|
||||
}
|
||||
|
||||
int32
|
||||
Clump::countCameras(void)
|
||||
{
|
||||
int32 n = 0;
|
||||
FORLIST(l, this->cameras)
|
||||
n++;
|
||||
return n;
|
||||
}
|
||||
|
||||
Clump*
|
||||
Clump::streamRead(Stream *stream)
|
||||
{
|
||||
|
@ -307,15 +322,17 @@ Clump::streamRead(Stream *stream)
|
|||
stream->read(buf, length);
|
||||
int32 numAtomics = buf[0];
|
||||
int32 numLights = 0;
|
||||
if(version > 0x33000)
|
||||
int32 numCameras = 0;
|
||||
if(version > 0x33000){
|
||||
numLights = buf[1];
|
||||
// ignore cameras
|
||||
numCameras = buf[2];
|
||||
}
|
||||
|
||||
// Frame list
|
||||
Frame **frameList;
|
||||
int32 numFrames;
|
||||
clump->frameListStreamRead(stream, &frameList, &numFrames);
|
||||
clump->object.parent = (void*)frameList[0];
|
||||
clump->setFrame(frameList[0]);
|
||||
|
||||
Geometry **geometryList = 0;
|
||||
if(version >= 0x30400){
|
||||
|
@ -350,6 +367,17 @@ Clump::streamRead(Stream *stream)
|
|||
clump->addLight(l);
|
||||
}
|
||||
|
||||
// Cameras
|
||||
for(int32 i = 0; i < numCameras; i++){
|
||||
int32 frm;
|
||||
assert(findChunk(stream, ID_STRUCT, NULL, NULL));
|
||||
frm = stream->readI32();
|
||||
assert(findChunk(stream, ID_CAMERA, NULL, NULL));
|
||||
Camera *cam = Camera::streamRead(stream);
|
||||
cam->setFrame(frameList[frm]);
|
||||
clump->addCamera(cam);
|
||||
}
|
||||
|
||||
delete[] frameList;
|
||||
|
||||
clump->streamReadPlugins(stream);
|
||||
|
@ -368,9 +396,9 @@ Clump::streamWrite(Stream *stream)
|
|||
writeChunkHeader(stream, ID_STRUCT, size);
|
||||
stream->write(buf, size);
|
||||
|
||||
int32 numFrames = ((Frame*)this->object.parent)->count();
|
||||
int32 numFrames = this->getFrame()->count();
|
||||
Frame **flist = new Frame*[numFrames];
|
||||
makeFrameList((Frame*)this->object.parent, flist);
|
||||
makeFrameList(this->getFrame(), flist);
|
||||
|
||||
this->frameListStreamWrite(stream, flist, numFrames);
|
||||
|
||||
|
@ -390,7 +418,7 @@ Clump::streamWrite(Stream *stream)
|
|||
|
||||
FORLIST(lnk, this->lights){
|
||||
Light *l = Light::fromClump(lnk);
|
||||
int frm = findPointer((void*)l->object.parent, (void**)flist, numFrames);
|
||||
int frm = findPointer(l->getFrame(), (void**)flist, numFrames);
|
||||
if(frm < 0)
|
||||
return false;
|
||||
writeChunkHeader(stream, ID_STRUCT, 4);
|
||||
|
@ -398,6 +426,16 @@ Clump::streamWrite(Stream *stream)
|
|||
l->streamWrite(stream);
|
||||
}
|
||||
|
||||
FORLIST(lnk, this->cameras){
|
||||
Camera *c = Camera::fromClump(lnk);
|
||||
int frm = findPointer(c->getFrame(), (void**)flist, numFrames);
|
||||
if(frm < 0)
|
||||
return false;
|
||||
writeChunkHeader(stream, ID_STRUCT, 4);
|
||||
stream->writeI32(frm);
|
||||
c->streamWrite(stream);
|
||||
}
|
||||
|
||||
delete[] flist;
|
||||
|
||||
this->streamWritePlugins(stream);
|
||||
|
@ -421,26 +459,30 @@ Clump::streamGetSize(void)
|
|||
if(version > 0x33000)
|
||||
size += 8; // numLights, numCameras
|
||||
|
||||
// frame list
|
||||
int32 numFrames = ((Frame*)this->object.parent)->count();
|
||||
// Frame list
|
||||
int32 numFrames = this->getFrame()->count();
|
||||
size += 12 + 12 + 4 + numFrames*(sizeof(FrameStreamData)+12);
|
||||
sizeCB((Frame*)this->object.parent, (void*)&size);
|
||||
sizeCB(this->getFrame(), (void*)&size);
|
||||
|
||||
if(rw::version >= 0x30400){
|
||||
// geometry list
|
||||
// Geometry list
|
||||
size += 12 + 12 + 4;
|
||||
FORLIST(lnk, this->atomics)
|
||||
size += 12 + Atomic::fromClump(lnk)->geometry->streamGetSize();
|
||||
}
|
||||
|
||||
// atomics
|
||||
// Atomics
|
||||
FORLIST(lnk, this->atomics)
|
||||
size += 12 + Atomic::fromClump(lnk)->streamGetSize();
|
||||
|
||||
// light
|
||||
// Lights
|
||||
FORLIST(lnk, this->lights)
|
||||
size += 16 + 12 + Light::fromClump(lnk)->streamGetSize();
|
||||
|
||||
// Cameras
|
||||
FORLIST(lnk, this->cameras)
|
||||
size += 16 + 12 + Camera::fromClump(lnk)->streamGetSize();
|
||||
|
||||
size += 12 + this->streamGetPluginSize();
|
||||
return size;
|
||||
}
|
||||
|
@ -513,7 +555,7 @@ Clump::frameListStreamWrite(Stream *stream, Frame **frameList, int32 numFrames)
|
|||
buf.pos[0] = f->matrix[12];
|
||||
buf.pos[1] = f->matrix[13];
|
||||
buf.pos[2] = f->matrix[14];
|
||||
buf.parent = findPointer((void*)f->object.parent, (void**)frameList,
|
||||
buf.parent = findPointer(f->getParent(), (void**)frameList,
|
||||
numFrames);
|
||||
buf.matflag = f->matflag;
|
||||
stream->write(&buf, sizeof(buf));
|
||||
|
@ -530,12 +572,13 @@ Atomic*
|
|||
Atomic::create(void)
|
||||
{
|
||||
Atomic *atomic = (Atomic*)malloc(PluginBase::s_size);
|
||||
atomic->object.init(1, 0);
|
||||
assert(atomic != NULL);
|
||||
atomic->object.init(Atomic::ID, 0);
|
||||
atomic->geometry = NULL;
|
||||
atomic->pipeline = NULL;
|
||||
atomic->constructPlugins();
|
||||
return atomic;
|
||||
}
|
||||
}
|
||||
|
||||
Atomic*
|
||||
Atomic::clone()
|
||||
|
@ -596,7 +639,7 @@ Atomic::streamWriteClump(Stream *stream, Frame **frameList, int32 numFrames)
|
|||
return false;
|
||||
writeChunkHeader(stream, ID_ATOMIC, this->streamGetSize());
|
||||
writeChunkHeader(stream, ID_STRUCT, rw::version < 0x30400 ? 12 : 16);
|
||||
buf[0] = findPointer((void*)this->object.parent, (void**)frameList, numFrames);
|
||||
buf[0] = findPointer(this->getFrame(), (void**)frameList, numFrames);
|
||||
|
||||
if(version < 0x30400){
|
||||
stream->write(buf, sizeof(int[3]));
|
||||
|
@ -702,15 +745,15 @@ Light*
|
|||
Light::create(int32 type)
|
||||
{
|
||||
Light *light = (Light*)malloc(PluginBase::s_size);
|
||||
light->object.init(3, type);
|
||||
assert(light != NULL);
|
||||
light->object.init(Light::ID, type);
|
||||
light->radius = 0.0f;
|
||||
light->color[0] = 1.0f;
|
||||
light->color[1] = 1.0f;
|
||||
light->color[2] = 1.0f;
|
||||
light->color[3] = 1.0f;
|
||||
light->red = 1.0f;
|
||||
light->green = 1.0f;
|
||||
light->blue = 1.0f;
|
||||
light->minusCosAngle = 1.0f;
|
||||
light->object.privateFlags = 1;
|
||||
light->object.flags = 1 | 2;
|
||||
light->object.flags = LIGHTATOMICS | LIGHTWORLD;
|
||||
light->inClump.init();
|
||||
light->constructPlugins();
|
||||
return light;
|
||||
|
@ -723,6 +766,27 @@ Light::destroy(void)
|
|||
free(this);
|
||||
}
|
||||
|
||||
void
|
||||
Light::setAngle(float32 angle)
|
||||
{
|
||||
this->minusCosAngle = -cos(angle);
|
||||
}
|
||||
|
||||
float32
|
||||
Light::getAngle(void)
|
||||
{
|
||||
return acos(-this->minusCosAngle);
|
||||
}
|
||||
|
||||
void
|
||||
Light::setColor(float32 r, float32 g, float32 b)
|
||||
{
|
||||
this->red = r;
|
||||
this->green = g;
|
||||
this->blue = b;
|
||||
this->object.privateFlags = r == g && r == b;
|
||||
}
|
||||
|
||||
struct LightChunkData
|
||||
{
|
||||
float32 radius;
|
||||
|
@ -735,18 +799,20 @@ struct LightChunkData
|
|||
Light*
|
||||
Light::streamRead(Stream *stream)
|
||||
{
|
||||
uint32 version;
|
||||
LightChunkData buf;
|
||||
assert(findChunk(stream, ID_STRUCT, NULL, NULL));
|
||||
assert(findChunk(stream, ID_STRUCT, NULL, &version));
|
||||
stream->read(&buf, sizeof(LightChunkData));
|
||||
Light *light = Light::create(buf.type);
|
||||
light->radius = buf.radius;
|
||||
light->color[0] = buf.red;
|
||||
light->color[1] = buf.green;
|
||||
light->color[2] = buf.blue;
|
||||
light->color[3] = 1.0f;
|
||||
light->minusCosAngle = buf.minusCosAngle;
|
||||
light->setColor(buf.red, buf.green, buf.blue);
|
||||
float32 a = buf.minusCosAngle;
|
||||
if(version >= 0x30300)
|
||||
light->minusCosAngle = a;
|
||||
else
|
||||
// tan -> -cos
|
||||
light->minusCosAngle = -1.0f/sqrt(a*a+1.0f);
|
||||
light->object.flags = (uint8)buf.flags;
|
||||
|
||||
light->streamReadPlugins(stream);
|
||||
return light;
|
||||
}
|
||||
|
@ -758,10 +824,13 @@ Light::streamWrite(Stream *stream)
|
|||
writeChunkHeader(stream, ID_LIGHT, this->streamGetSize());
|
||||
writeChunkHeader(stream, ID_STRUCT, sizeof(LightChunkData));
|
||||
buf.radius = this->radius;
|
||||
buf.red = this->color[0];
|
||||
buf.green = this->color[1];
|
||||
buf.blue = this->color[2];
|
||||
buf.minusCosAngle = this->minusCosAngle;
|
||||
buf.red = this->red;
|
||||
buf.green = this->green;
|
||||
buf.blue = this->blue;
|
||||
if(version >= 0x30300)
|
||||
buf.minusCosAngle = this->minusCosAngle;
|
||||
else
|
||||
buf.minusCosAngle = tan(acos(-this->minusCosAngle));
|
||||
buf.flags = this->object.flags;
|
||||
buf.type = this->object.subType;
|
||||
stream->write(&buf, sizeof(LightChunkData));
|
||||
|
@ -776,4 +845,83 @@ Light::streamGetSize(void)
|
|||
return 12 + sizeof(LightChunkData) + 12 + this->streamGetPluginSize();
|
||||
}
|
||||
|
||||
//
|
||||
// Camera
|
||||
//
|
||||
|
||||
Camera*
|
||||
Camera::create(void)
|
||||
{
|
||||
Camera *cam = (Camera*)malloc(PluginBase::s_size);
|
||||
cam->object.init(Camera::ID, 0);
|
||||
cam->constructPlugins();
|
||||
return cam;
|
||||
}
|
||||
|
||||
Camera*
|
||||
Camera::clone(void)
|
||||
{
|
||||
Camera *cam = Camera::create();
|
||||
cam->object.copy(&this->object);
|
||||
cam->copyPlugins(this);
|
||||
return cam;
|
||||
}
|
||||
|
||||
void
|
||||
Camera::destroy(void)
|
||||
{
|
||||
this->destructPlugins();
|
||||
free(this);
|
||||
}
|
||||
|
||||
struct CameraChunkData
|
||||
{
|
||||
V2d viewWindow;
|
||||
V2d viewOffset;
|
||||
float32 nearClip, farClip;
|
||||
float32 fogPlane;
|
||||
int32 projection;
|
||||
};
|
||||
|
||||
Camera*
|
||||
Camera::streamRead(Stream *stream)
|
||||
{
|
||||
CameraChunkData buf;
|
||||
assert(findChunk(stream, ID_STRUCT, NULL, NULL));
|
||||
stream->read(&buf, sizeof(CameraChunkData));
|
||||
Camera *cam = Camera::create();
|
||||
cam->viewWindow = buf.viewWindow;
|
||||
cam->viewOffset = buf.viewOffset;
|
||||
cam->nearClip = buf.nearClip;
|
||||
cam->farClip = buf.farClip;
|
||||
cam->fogPlane = buf.fogPlane;
|
||||
cam->projection = buf.projection;
|
||||
cam->streamReadPlugins(stream);
|
||||
return cam;
|
||||
|
||||
}
|
||||
|
||||
bool
|
||||
Camera::streamWrite(Stream *stream)
|
||||
{
|
||||
CameraChunkData buf;
|
||||
writeChunkHeader(stream, ID_CAMERA, this->streamGetSize());
|
||||
writeChunkHeader(stream, ID_STRUCT, sizeof(CameraChunkData));
|
||||
buf.viewWindow = this->viewWindow;
|
||||
buf.viewOffset = this->viewOffset;
|
||||
buf.nearClip = this->nearClip;
|
||||
buf.farClip = this->farClip;
|
||||
buf.fogPlane = this->fogPlane;
|
||||
buf.projection = this->projection;
|
||||
stream->write(&buf, sizeof(CameraChunkData));
|
||||
this->streamWritePlugins(stream);
|
||||
return true;
|
||||
}
|
||||
|
||||
uint32
|
||||
Camera::streamGetSize(void)
|
||||
{
|
||||
return 12 + sizeof(CameraChunkData) + 12 + this->streamGetPluginSize();
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -19,7 +19,8 @@ Geometry*
|
|||
Geometry::create(int32 numVerts, int32 numTris, uint32 flags)
|
||||
{
|
||||
Geometry *geo = (Geometry*)malloc(PluginBase::s_size);
|
||||
geo->object.init(8, 0);
|
||||
assert(geo != NULL);
|
||||
geo->object.init(Geometry::ID, 0);
|
||||
geo->geoflags = flags & 0xFF00FFFF;
|
||||
geo->numTexCoordSets = (flags & 0xFF0000) >> 16;
|
||||
if(geo->numTexCoordSets == 0)
|
||||
|
@ -70,7 +71,7 @@ void
|
|||
Geometry::destroy(void)
|
||||
{
|
||||
this->refCount--;
|
||||
if(this->refCount == 0){
|
||||
if(this->refCount <= 0){
|
||||
this->destructPlugins();
|
||||
delete[] this->colors;
|
||||
for(int32 i = 0; i < this->numTexCoordSets; i++)
|
||||
|
@ -301,10 +302,10 @@ bool32
|
|||
Geometry::hasColoredMaterial(void)
|
||||
{
|
||||
for(int32 i = 0; i < this->numMaterials; i++)
|
||||
if(this->materialList[i]->color[0] != 255 ||
|
||||
this->materialList[i]->color[1] != 255 ||
|
||||
this->materialList[i]->color[2] != 255 ||
|
||||
this->materialList[i]->color[3] != 255)
|
||||
if(this->materialList[i]->color.red != 255 ||
|
||||
this->materialList[i]->color.green != 255 ||
|
||||
this->materialList[i]->color.blue != 255 ||
|
||||
this->materialList[i]->color.alpha != 255)
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
|
@ -406,8 +407,9 @@ Material*
|
|||
Material::create(void)
|
||||
{
|
||||
Material *mat = (Material*)malloc(PluginBase::s_size);
|
||||
assert(mat != NULL);
|
||||
mat->texture = NULL;
|
||||
memset(mat->color, 0xFF, 4);
|
||||
memset(&mat->color, 0xFF, 4);
|
||||
mat->surfaceProps.ambient = 1.0f;
|
||||
mat->surfaceProps.specular = 1.0f;
|
||||
mat->surfaceProps.diffuse = 1.0f;
|
||||
|
@ -421,14 +423,12 @@ Material*
|
|||
Material::clone(void)
|
||||
{
|
||||
Material *mat = Material::create();
|
||||
mat->color[0] = this->color[0];
|
||||
mat->color[1] = this->color[1];
|
||||
mat->color[2] = this->color[2];
|
||||
mat->color[3] = this->color[3];
|
||||
mat->color = this->color;
|
||||
mat->surfaceProps = this->surfaceProps;
|
||||
mat->texture = this->texture;
|
||||
if(mat->texture)
|
||||
if(this->texture){
|
||||
mat->texture = this->texture;
|
||||
mat->texture->refCount++;
|
||||
}
|
||||
mat->pipeline = this->pipeline;
|
||||
mat->copyPlugins(this);
|
||||
return mat;
|
||||
|
@ -438,7 +438,7 @@ void
|
|||
Material::destroy(void)
|
||||
{
|
||||
this->refCount--;
|
||||
if(this->refCount == 0){
|
||||
if(this->refCount <= 0){
|
||||
this->destructPlugins();
|
||||
if(this->texture)
|
||||
this->texture->destroy();
|
||||
|
@ -449,7 +449,7 @@ Material::destroy(void)
|
|||
struct MatStreamData
|
||||
{
|
||||
int32 flags; // unused according to RW
|
||||
uint8 color[4];
|
||||
RGBA color;
|
||||
int32 unused;
|
||||
int32 textured;
|
||||
};
|
||||
|
@ -465,10 +465,7 @@ Material::streamRead(Stream *stream)
|
|||
assert(findChunk(stream, ID_STRUCT, NULL, &version));
|
||||
stream->read(&buf, sizeof(buf));
|
||||
Material *mat = Material::create();
|
||||
mat->color[0] = buf.color[0];
|
||||
mat->color[1] = buf.color[1];
|
||||
mat->color[2] = buf.color[2];
|
||||
mat->color[3] = buf.color[3];
|
||||
mat->color = buf.color;
|
||||
if(version < 0x30400){
|
||||
mat->surfaceProps.ambient = 1.0f;
|
||||
mat->surfaceProps.specular = 1.0f;
|
||||
|
@ -501,10 +498,7 @@ Material::streamWrite(Stream *stream)
|
|||
writeChunkHeader(stream, ID_STRUCT, sizeof(MatStreamData)
|
||||
+ (rw::version >= 0x30400 ? 12 : 0));
|
||||
|
||||
buf.color[0] = this->color[0];
|
||||
buf.color[1] = this->color[1];
|
||||
buf.color[2] = this->color[2];
|
||||
buf.color[3] = this->color[3];
|
||||
buf.color = this->color;
|
||||
buf.flags = 0;
|
||||
buf.unused = 0;
|
||||
buf.textured = this->texture != NULL;
|
||||
|
|
|
@ -33,7 +33,8 @@ TexDictionary*
|
|||
TexDictionary::create(void)
|
||||
{
|
||||
TexDictionary *dict = (TexDictionary*)malloc(PluginBase::s_size);
|
||||
dict->object.init(6, 0);
|
||||
assert(dict != NULL);
|
||||
dict->object.init(TexDictionary::ID, 0);
|
||||
dict->textures.init();
|
||||
dict->constructPlugins();
|
||||
return dict;
|
||||
|
@ -42,6 +43,8 @@ TexDictionary::create(void)
|
|||
void
|
||||
TexDictionary::destroy(void)
|
||||
{
|
||||
FORLIST(lnk, this->textures)
|
||||
Texture::fromDict(lnk)->destroy();
|
||||
this->destructPlugins();
|
||||
free(this);
|
||||
}
|
||||
|
@ -50,7 +53,7 @@ int32
|
|||
TexDictionary::count(void)
|
||||
{
|
||||
int32 n = 0;
|
||||
FORLIST(l, this->textures)
|
||||
FORLIST(lnk, this->textures)
|
||||
n++;
|
||||
return n;
|
||||
}
|
||||
|
@ -114,6 +117,7 @@ Texture*
|
|||
Texture::create(Raster *raster)
|
||||
{
|
||||
Texture *tex = (Texture*)malloc(PluginBase::s_size);
|
||||
assert(tex != NULL);
|
||||
tex->dict = NULL;
|
||||
tex->inDict.init();
|
||||
memset(tex->name, 0, 32);
|
||||
|
@ -129,8 +133,12 @@ void
|
|||
Texture::destroy(void)
|
||||
{
|
||||
this->refCount--;
|
||||
if(this->refCount == 0){
|
||||
if(this->refCount <= 0){
|
||||
this->destructPlugins();
|
||||
if(this->dict)
|
||||
this->inDict.remove();
|
||||
if(this->raster)
|
||||
this->raster->destroy();
|
||||
free(this);
|
||||
}
|
||||
}
|
||||
|
@ -281,6 +289,7 @@ Image*
|
|||
Image::create(int32 width, int32 height, int32 depth)
|
||||
{
|
||||
Image *img = (Image*)malloc(sizeof(*img));
|
||||
assert(img != NULL);
|
||||
img->flags = 0;
|
||||
img->width = width;
|
||||
img->height = height;
|
||||
|
@ -387,6 +396,7 @@ Image::getFilename(const char *name)
|
|||
}else
|
||||
for(int i = 0; i < numSearchPaths; i++){
|
||||
s = (char*)malloc(strlen(p)+len);
|
||||
assert(s != NULL);
|
||||
strcpy(s, p);
|
||||
strcat(s, name);
|
||||
f = fopen(s, "r");
|
||||
|
@ -569,6 +579,7 @@ Raster*
|
|||
Raster::create(int32 width, int32 height, int32 depth, int32 format, int32 platform)
|
||||
{
|
||||
Raster *raster = (Raster*)malloc(PluginBase::s_size);
|
||||
assert(raster != NULL);
|
||||
raster->platform = platform ? platform : rw::platform;
|
||||
raster->type = format & 0x7;
|
||||
raster->flags = format & 0xF8;
|
||||
|
|
162
src/rwobjects.h
162
src/rwobjects.h
|
@ -1,5 +1,23 @@
|
|||
namespace rw {
|
||||
|
||||
struct RGBA
|
||||
{
|
||||
uint8 red;
|
||||
uint8 green;
|
||||
uint8 blue;
|
||||
uint8 alpha;
|
||||
};
|
||||
|
||||
struct V2d
|
||||
{
|
||||
float32 x, y;
|
||||
};
|
||||
|
||||
struct V3d
|
||||
{
|
||||
float32 x, y, z;
|
||||
};
|
||||
|
||||
struct LLLink
|
||||
{
|
||||
LLLink *next;
|
||||
|
@ -44,10 +62,11 @@ struct LinkList
|
|||
}
|
||||
};
|
||||
|
||||
// Have to be careful since the link might be deleted.
|
||||
#define FORLIST(_link, _list) \
|
||||
for(LLLink *_link = (_list).link.next; \
|
||||
(_link) != (_list).end(); \
|
||||
(_link) = (_link)->next)
|
||||
for(LLLink *_next = NULL, *_link = (_list).link.next; \
|
||||
_next = (_link)->next, (_link) != (_list).end(); \
|
||||
(_link) = _next)
|
||||
|
||||
struct Object
|
||||
{
|
||||
|
@ -77,6 +96,7 @@ struct Frame : PluginBase<Frame>
|
|||
{
|
||||
typedef Frame *(*Callback)(Frame *f, void *data);
|
||||
|
||||
enum { ID = 0 };
|
||||
Object object;
|
||||
LinkList objectList;
|
||||
float32 matrix[16];
|
||||
|
@ -90,7 +110,6 @@ struct Frame : PluginBase<Frame>
|
|||
int32 matflag;
|
||||
bool dirty;
|
||||
|
||||
// MEM create, clonehiearchy, destroy, destroy hierarchy
|
||||
static Frame *create(void);
|
||||
Frame *cloneHierarchy(void);
|
||||
void destroy(void);
|
||||
|
@ -99,8 +118,7 @@ struct Frame : PluginBase<Frame>
|
|||
Frame *removeChild(void);
|
||||
Frame *forAllChildren(Callback cb, void *data);
|
||||
Frame *getParent(void){
|
||||
return (Frame*)this->object.parent;
|
||||
}
|
||||
return (Frame*)this->object.parent; }
|
||||
int32 count(void);
|
||||
void updateLTM(void);
|
||||
void setDirty(void);
|
||||
|
@ -122,6 +140,9 @@ struct ObjectWithFrame : Object
|
|||
if(f)
|
||||
f->objectList.add(&this->inFrame);
|
||||
}
|
||||
static ObjectWithFrame *fromFrame(LLLink *lnk){
|
||||
return LLLinkGetData(lnk, ObjectWithFrame, inFrame);
|
||||
}
|
||||
};
|
||||
|
||||
struct HAnimKeyFrame
|
||||
|
@ -172,7 +193,6 @@ struct Image
|
|||
uint8 *pixels;
|
||||
uint8 *palette;
|
||||
|
||||
// MEM create, destroy
|
||||
static Image *create(int32 width, int32 height, int32 depth);
|
||||
void destroy(void);
|
||||
void allocate(void);
|
||||
|
@ -212,10 +232,8 @@ struct Raster : PluginBase<Raster>
|
|||
|
||||
static int32 nativeOffsets[NUM_PLATFORMS];
|
||||
|
||||
// MEM create, destroy
|
||||
static Raster *create(int32 width, int32 height, int32 depth, int32 format, int32 platform = 0);
|
||||
void destroy(void);
|
||||
|
||||
static Raster *createFromImage(Image *image);
|
||||
uint8 *lock(int32 level);
|
||||
void unlock(int32 level);
|
||||
|
@ -267,12 +285,10 @@ struct Texture : PluginBase<Texture>
|
|||
uint32 filterAddressing; // VVVVUUUU FFFFFFFF
|
||||
int32 refCount;
|
||||
|
||||
// MEM create, addref, destroy
|
||||
static Texture *create(Raster *raster);
|
||||
void destroy(void);
|
||||
static Texture *fromDict(LLLink *lnk){
|
||||
return LLLinkGetData(lnk, Texture, inDict);
|
||||
}
|
||||
return LLLinkGetData(lnk, Texture, inDict); }
|
||||
static Texture *streamRead(Stream *stream);
|
||||
bool streamWrite(Stream *stream);
|
||||
uint32 streamGetSize(void);
|
||||
|
@ -307,12 +323,11 @@ struct SurfaceProperties
|
|||
struct Material : PluginBase<Material>
|
||||
{
|
||||
Texture *texture;
|
||||
uint8 color[4];
|
||||
RGBA color;
|
||||
SurfaceProperties surfaceProps;
|
||||
Pipeline *pipeline;
|
||||
int32 refCount;
|
||||
|
||||
// MEM create, clone, addref, destroy
|
||||
static Material *create(void);
|
||||
Material *clone(void);
|
||||
void destroy(void);
|
||||
|
@ -414,6 +429,7 @@ struct InstanceDataHeader
|
|||
|
||||
struct Geometry : PluginBase<Geometry>
|
||||
{
|
||||
enum { ID = 8 };
|
||||
Object object;
|
||||
uint32 geoflags; // TODO: rename
|
||||
int32 numTriangles;
|
||||
|
@ -437,7 +453,6 @@ struct Geometry : PluginBase<Geometry>
|
|||
|
||||
int32 refCount;
|
||||
|
||||
// MEM create, addref, destroy
|
||||
static Geometry *create(int32 numVerts, int32 numTris, uint32 flags);
|
||||
void destroy(void);
|
||||
static Geometry *streamRead(Stream *stream);
|
||||
|
@ -494,50 +509,26 @@ void registerSkinPlugin(void);
|
|||
|
||||
struct Clump;
|
||||
|
||||
struct Light : PluginBase<Light>
|
||||
{
|
||||
ObjectWithFrame object;
|
||||
float32 radius;
|
||||
float32 color[4];
|
||||
float32 minusCosAngle;
|
||||
|
||||
// clump link handled by plugin in RW
|
||||
Clump *clump;
|
||||
LLLink inClump;
|
||||
|
||||
// MEM create, destroy
|
||||
static Light *create(int32 type);
|
||||
void destroy(void);
|
||||
void setFrame(Frame *f) { this->object.setFrame(f); }
|
||||
static Light *fromClump(LLLink *lnk){
|
||||
return LLLinkGetData(lnk, Light, inClump);
|
||||
}
|
||||
static Light *streamRead(Stream *stream);
|
||||
bool streamWrite(Stream *stream);
|
||||
uint32 streamGetSize(void);
|
||||
};
|
||||
|
||||
struct Atomic : PluginBase<Atomic>
|
||||
{
|
||||
enum { ID = 1 };
|
||||
ObjectWithFrame object;
|
||||
Geometry *geometry;
|
||||
Clump *clump;
|
||||
LLLink inClump;
|
||||
ObjPipeline *pipeline;
|
||||
|
||||
// MEM create, clone, destroy
|
||||
static Atomic *create(void);
|
||||
Atomic *clone(void);
|
||||
void destroy(void);
|
||||
void setFrame(Frame *f) { this->object.setFrame(f); }
|
||||
Frame *getFrame(void) { return (Frame*)this->object.parent; }
|
||||
static Atomic *fromClump(LLLink *lnk){
|
||||
return LLLinkGetData(lnk, Atomic, inClump);
|
||||
}
|
||||
return LLLinkGetData(lnk, Atomic, inClump); }
|
||||
static Atomic *streamReadClump(Stream *stream,
|
||||
Frame **frameList, Geometry **geometryList);
|
||||
bool streamWriteClump(Stream *stream,
|
||||
Frame **frameList, int32 numFrames);
|
||||
Frame **frameList, int32 numframes);
|
||||
uint32 streamGetSize(void);
|
||||
ObjPipeline *getPipeline(void);
|
||||
|
||||
|
@ -548,14 +539,77 @@ extern ObjPipeline *defaultPipelines[NUM_PLATFORMS];
|
|||
|
||||
void registerAtomicRightsPlugin(void);
|
||||
|
||||
struct Light : PluginBase<Light>
|
||||
{
|
||||
enum { ID = 3 };
|
||||
ObjectWithFrame object;
|
||||
float32 radius;
|
||||
float32 red, green, blue;
|
||||
float32 minusCosAngle;
|
||||
|
||||
// clump link handled by plugin in RW
|
||||
Clump *clump;
|
||||
LLLink inClump;
|
||||
|
||||
static Light *create(int32 type);
|
||||
void destroy(void);
|
||||
void setFrame(Frame *f) { this->object.setFrame(f); }
|
||||
Frame *getFrame(void){ return (Frame*)this->object.parent; }
|
||||
static Light *fromClump(LLLink *lnk){
|
||||
return LLLinkGetData(lnk, Light, inClump); }
|
||||
void setAngle(float32 angle);
|
||||
float32 getAngle(void);
|
||||
void setColor(float32 r, float32 g, float32 b);
|
||||
static Light *streamRead(Stream *stream);
|
||||
bool streamWrite(Stream *stream);
|
||||
uint32 streamGetSize(void);
|
||||
|
||||
enum Type {
|
||||
DIRECTIONAL = 1,
|
||||
AMBIENT,
|
||||
POINT = 0x80, // positioned
|
||||
SPOT,
|
||||
SOFTSPOT,
|
||||
};
|
||||
enum Flags {
|
||||
LIGHTATOMICS = 1,
|
||||
LIGHTWORLD = 2
|
||||
};
|
||||
};
|
||||
|
||||
struct Camera : PluginBase<Camera>
|
||||
{
|
||||
enum { ID = 4 };
|
||||
ObjectWithFrame object;
|
||||
V2d viewWindow;
|
||||
V2d viewOffset;
|
||||
float32 nearClip, farClip;
|
||||
float32 fogPlane;
|
||||
int32 projection;
|
||||
|
||||
Clump *clump;
|
||||
LLLink inClump;
|
||||
|
||||
static Camera *create(void);
|
||||
Camera *clone(void);
|
||||
void destroy(void);
|
||||
void setFrame(Frame *f) { this->object.setFrame(f); }
|
||||
Frame *getFrame(void){ return (Frame*)this->object.parent; }
|
||||
static Camera *fromClump(LLLink *lnk){
|
||||
return LLLinkGetData(lnk, Camera, inClump); }
|
||||
static Camera *streamRead(Stream *stream);
|
||||
bool streamWrite(Stream *stream);
|
||||
uint32 streamGetSize(void);
|
||||
};
|
||||
|
||||
struct Clump : PluginBase<Clump>
|
||||
{
|
||||
Object object;
|
||||
enum { ID = 2 };
|
||||
ObjectWithFrame object;
|
||||
LinkList atomics;
|
||||
LinkList lights;
|
||||
// cameras not implemented
|
||||
LinkList cameras;
|
||||
|
||||
// MEM create, clone, destroy
|
||||
static Clump *create(void);
|
||||
Clump *clone(void);
|
||||
void destroy(void);
|
||||
|
@ -569,27 +623,29 @@ struct Clump : PluginBase<Clump>
|
|||
l->clump = this;
|
||||
this->lights.append(&l->inClump);
|
||||
}
|
||||
int32 countCameras(void);
|
||||
void addCamera(Camera *c){
|
||||
c->clump = this;
|
||||
this->cameras.append(&c->inClump);
|
||||
}
|
||||
void setFrame(Frame *f){
|
||||
this->object.parent = f;
|
||||
}
|
||||
this->object.parent = f; }
|
||||
Frame *getFrame(void){
|
||||
return (Frame*)this->object.parent;
|
||||
}
|
||||
return (Frame*)this->object.parent; }
|
||||
static Clump *streamRead(Stream *stream);
|
||||
bool streamWrite(Stream *stream);
|
||||
uint32 streamGetSize(void);
|
||||
|
||||
void frameListStreamRead(Stream *stream, Frame ***flp, int32 *nf);
|
||||
void frameListStreamWrite(Stream *stream, Frame **flp, int32 nf);
|
||||
|
||||
};
|
||||
|
||||
struct TexDictionary : PluginBase<TexDictionary>
|
||||
{
|
||||
enum { ID = 6 };
|
||||
Object object;
|
||||
LinkList textures;
|
||||
|
||||
// MEM create, destroy
|
||||
static TexDictionary *create(void);
|
||||
void destroy(void);
|
||||
int32 count(void);
|
||||
|
@ -603,6 +659,8 @@ struct TexDictionary : PluginBase<TexDictionary>
|
|||
uint32 streamGetSize(void);
|
||||
};
|
||||
|
||||
extern TexDictionary *currentTexDictionary;
|
||||
|
||||
struct Animation;
|
||||
|
||||
struct AnimInterpolatorInfo
|
||||
|
@ -643,8 +701,6 @@ struct AnimInterpolator
|
|||
AnimInterpolator(Animation *anim);
|
||||
};
|
||||
|
||||
extern TexDictionary *currentTexDictionary;
|
||||
|
||||
struct UVAnimKeyFrame
|
||||
{
|
||||
UVAnimKeyFrame *prev;
|
||||
|
|
|
@ -420,7 +420,7 @@ RslGeometryForAllMaterials(RslGeometry *geometry, RslMaterialCallBack fpCallBack
|
|||
struct RslMaterialChunkInfo
|
||||
{
|
||||
int32 flags;
|
||||
RslRGBA color; // used
|
||||
RGBA color; // used
|
||||
int32 unused;
|
||||
bool32 textured; // used
|
||||
SurfaceProperties surfaceProps;
|
||||
|
|
|
@ -42,14 +42,6 @@ typedef RslAtomic *(*RslAtomicCallBack)(RslAtomic *atomic, void *data);
|
|||
typedef RslMaterial *(*RslMaterialCallBack)(RslMaterial *material, void *data);
|
||||
typedef RslTexture *(*RslTextureCallBack)(RslTexture *texture, void *pData);
|
||||
|
||||
struct RslRGBA
|
||||
{
|
||||
uint8 red;
|
||||
uint8 green;
|
||||
uint8 blue;
|
||||
uint8 alpha;
|
||||
};
|
||||
|
||||
struct RslV3d
|
||||
{
|
||||
float32 x, y, z;
|
||||
|
@ -311,7 +303,7 @@ struct RslMaterial {
|
|||
char *texname;
|
||||
RslTexture *texture;
|
||||
};
|
||||
RslRGBA color;
|
||||
RGBA color;
|
||||
uint32 refCount;
|
||||
RslMatFX *matfx;
|
||||
};
|
||||
|
|
|
@ -125,10 +125,7 @@ convertMaterial(RslMaterial *m)
|
|||
Material *rwm;
|
||||
rwm = Material::create();
|
||||
|
||||
rwm->color[0] = m->color.red;
|
||||
rwm->color[1] = m->color.green;
|
||||
rwm->color[2] = m->color.blue;
|
||||
rwm->color[3] = m->color.alpha;
|
||||
rwm->color = m->color;
|
||||
if(m->texture)
|
||||
rwm->texture = convertTexture(m->texture);
|
||||
|
||||
|
|
Loading…
Reference in New Issue