mirror of
https://github.com/XProger/OpenLara.git
synced 2025-08-21 20:35:17 +02:00
#16 remap mesh offsets, fix VAO for sprite sequences
This commit is contained in:
10
src/format.h
10
src/format.h
@@ -3,8 +3,6 @@
|
|||||||
|
|
||||||
#include "utils.h"
|
#include "utils.h"
|
||||||
|
|
||||||
#define TR1_DEMO
|
|
||||||
|
|
||||||
#define MAX_RESERVED_ENTITIES 64
|
#define MAX_RESERVED_ENTITIES 64
|
||||||
#define MAX_SECRETS_COUNT 16
|
#define MAX_SECRETS_COUNT 16
|
||||||
|
|
||||||
@@ -703,7 +701,7 @@ namespace TR {
|
|||||||
bool secrets[MAX_SECRETS_COUNT];
|
bool secrets[MAX_SECRETS_COUNT];
|
||||||
void *cameraController;
|
void *cameraController;
|
||||||
|
|
||||||
Level(Stream &stream) {
|
Level(Stream &stream, bool demo) {
|
||||||
// read version
|
// read version
|
||||||
stream.read(version);
|
stream.read(version);
|
||||||
// tiles
|
// tiles
|
||||||
@@ -776,9 +774,8 @@ namespace TR {
|
|||||||
for (int i = 0; i < spriteSequencesCount; i++)
|
for (int i = 0; i < spriteSequencesCount; i++)
|
||||||
spriteSequences[i].sCount = -spriteSequences[i].sCount;
|
spriteSequences[i].sCount = -spriteSequences[i].sCount;
|
||||||
|
|
||||||
#ifdef TR1_DEMO
|
if (demo)
|
||||||
stream.read(palette, 256);
|
stream.read(palette, 256);
|
||||||
#endif
|
|
||||||
|
|
||||||
// cameras
|
// cameras
|
||||||
stream.read(cameras, stream.read(camerasCount));
|
stream.read(cameras, stream.read(camerasCount));
|
||||||
@@ -807,9 +804,8 @@ namespace TR {
|
|||||||
// palette
|
// palette
|
||||||
stream.seek(32 * 256); // skip lightmap palette
|
stream.seek(32 * 256); // skip lightmap palette
|
||||||
|
|
||||||
#ifndef TR1_DEMO
|
if (!demo)
|
||||||
stream.read(palette, 256);
|
stream.read(palette, 256);
|
||||||
#endif
|
|
||||||
|
|
||||||
// cinematic frames for cameras
|
// cinematic frames for cameras
|
||||||
stream.read(cameraFrames, stream.read(cameraFramesCount));
|
stream.read(cameraFrames, stream.read(cameraFramesCount));
|
||||||
|
@@ -13,7 +13,7 @@ namespace Game {
|
|||||||
void init() {
|
void init() {
|
||||||
Core::init();
|
Core::init();
|
||||||
Stream stream("LEVEL2_DEMO.PHD");
|
Stream stream("LEVEL2_DEMO.PHD");
|
||||||
level = new Level(stream);
|
level = new Level(stream, true);
|
||||||
|
|
||||||
#ifndef __EMSCRIPTEN__
|
#ifndef __EMSCRIPTEN__
|
||||||
//Sound::play(Sound::openWAD("05_Lara's_Themes.wav"), 1, 1, 0);
|
//Sound::play(Sound::openWAD("05_Lara's_Themes.wav"), 1, 1, 0);
|
||||||
@@ -36,7 +36,6 @@ namespace Game {
|
|||||||
Core::clear(vec4(0.0f));
|
Core::clear(vec4(0.0f));
|
||||||
Core::setViewport(0, 0, Core::width, Core::height);
|
Core::setViewport(0, 0, Core::width, Core::height);
|
||||||
Core::setBlending(bmAlpha);
|
Core::setBlending(bmAlpha);
|
||||||
|
|
||||||
level->render();
|
level->render();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -171,12 +171,12 @@ struct Lara : Controller {
|
|||||||
pos = vec3(30800, -7936, 22131);
|
pos = vec3(30800, -7936, 22131);
|
||||||
angle = vec3(0.0f, 0.0f, 0.0f);
|
angle = vec3(0.0f, 0.0f, 0.0f);
|
||||||
getEntity().room = 58;
|
getEntity().room = 58;
|
||||||
*/
|
|
||||||
// level 2 (block)
|
// level 2 (block)
|
||||||
pos = vec3(60843, 1024, 30557);
|
pos = vec3(60843, 1024, 30557);
|
||||||
angle = vec3(0.0f, PI, 0.0f);
|
angle = vec3(0.0f, PI, 0.0f);
|
||||||
getEntity().room = 19;
|
getEntity().room = 19;
|
||||||
/*
|
|
||||||
// level 3a
|
// level 3a
|
||||||
pos = vec3(41015, 3584, 34494);
|
pos = vec3(41015, 3584, 34494);
|
||||||
angle = vec3(0.0f, -PI, 0.0f);
|
angle = vec3(0.0f, -PI, 0.0f);
|
||||||
|
35
src/level.h
35
src/level.h
@@ -30,7 +30,7 @@ struct Level {
|
|||||||
|
|
||||||
float time;
|
float time;
|
||||||
|
|
||||||
Level(Stream &stream) : level{stream}, time(0.0f), lara(NULL) {
|
Level(Stream &stream, bool demo) : level{stream, demo}, time(0.0f), lara(NULL) {
|
||||||
#ifdef _DEBUG
|
#ifdef _DEBUG
|
||||||
Debug::init();
|
Debug::init();
|
||||||
#endif
|
#endif
|
||||||
@@ -324,40 +324,15 @@ struct Level {
|
|||||||
camera->frustum = camFrustum; // pop camera frustum
|
camera->frustum = camFrustum; // pop camera frustum
|
||||||
}
|
}
|
||||||
|
|
||||||
MeshBuilder::MeshInfo* getMeshInfoByOffset(uint32 meshOffset) {
|
void renderMesh(uint32 offsetIndex) {
|
||||||
if (!level.meshOffsets[meshOffset] && meshOffset)
|
MeshBuilder::MeshInfo *m = mesh->meshMap[offsetIndex];
|
||||||
return NULL;
|
if (!m) return; // invisible mesh (offsetIndex > 0 && level.meshOffsets[offsetIndex] == 0) camera target entity etc.
|
||||||
|
|
||||||
for (int i = 0; i < mesh->mCount; i++)
|
|
||||||
if (mesh->meshInfo[i].offset == level.meshOffsets[meshOffset])
|
|
||||||
return &mesh->meshInfo[i];
|
|
||||||
ASSERT(false);
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
void renderMesh(uint32 meshOffset) {
|
|
||||||
MeshBuilder::MeshInfo *m = getMeshInfoByOffset(meshOffset);
|
|
||||||
if (!m) return; // invisible mesh (level.meshOffsets[meshOffset] == 0) camera target entity etc.
|
|
||||||
|
|
||||||
Core::active.shader->setParam(uModel, Core::mModel);
|
Core::active.shader->setParam(uModel, Core::mModel);
|
||||||
mesh->renderMesh(m);
|
mesh->renderMesh(m);
|
||||||
}
|
}
|
||||||
|
|
||||||
float lerpAngle(float a, float b, float t) {
|
quat lerpAngle(const vec3 &a, const vec3 &b, float t) { // TODO: optimization
|
||||||
float d = b - a;
|
|
||||||
if (d >= PI)
|
|
||||||
a += PI * 2.0f;
|
|
||||||
else
|
|
||||||
if (d <= -PI)
|
|
||||||
a -= PI * 2.0f;
|
|
||||||
return a + (b - a) * t;
|
|
||||||
}
|
|
||||||
|
|
||||||
quat lerpAngle(const vec3 &a, const vec3 &b, float t) {
|
|
||||||
// return vec3(lerpAngle(a.x, b.x, t),
|
|
||||||
// lerpAngle(a.y, b.y, t),
|
|
||||||
// lerpAngle(a.z, b.z, t));
|
|
||||||
|
|
||||||
mat4 ma, mb;
|
mat4 ma, mb;
|
||||||
ma.identity();
|
ma.identity();
|
||||||
mb.identity();
|
mb.identity();
|
||||||
|
29
src/mesh.h
29
src/mesh.h
@@ -121,6 +121,7 @@ struct MeshBuilder {
|
|||||||
TR::Collider collider;
|
TR::Collider collider;
|
||||||
} *meshInfo;
|
} *meshInfo;
|
||||||
int mCount;
|
int mCount;
|
||||||
|
MeshInfo **meshMap; // meshInfo by meshOffsetIndex
|
||||||
|
|
||||||
MeshRange *spriteSequences;
|
MeshRange *spriteSequences;
|
||||||
MeshRange shadowBlob;
|
MeshRange shadowBlob;
|
||||||
@@ -211,6 +212,8 @@ struct MeshBuilder {
|
|||||||
}
|
}
|
||||||
aCount += mCount;
|
aCount += mCount;
|
||||||
meshInfo = new MeshInfo[mCount];
|
meshInfo = new MeshInfo[mCount];
|
||||||
|
meshMap = new MeshInfo*[level.meshOffsetsCount];
|
||||||
|
memset(meshMap, 0, sizeof(meshMap[0]) * level.meshOffsetsCount);
|
||||||
|
|
||||||
// get size of mesh for sprite sequences
|
// get size of mesh for sprite sequences
|
||||||
spriteSequences = new MeshRange[level.spriteSequencesCount];
|
spriteSequences = new MeshRange[level.spriteSequencesCount];
|
||||||
@@ -221,8 +224,8 @@ struct MeshBuilder {
|
|||||||
spriteSequences[i].iCount = level.spriteSequences[i].sCount * 6;
|
spriteSequences[i].iCount = level.spriteSequences[i].sCount * 6;
|
||||||
iCount += level.spriteSequences[i].sCount * 6;
|
iCount += level.spriteSequences[i].sCount * 6;
|
||||||
vCount += level.spriteSequences[i].sCount * 4;
|
vCount += level.spriteSequences[i].sCount * 4;
|
||||||
|
aCount += level.spriteSequences[i].sCount;
|
||||||
}
|
}
|
||||||
aCount += level.spriteSequencesCount;
|
|
||||||
|
|
||||||
// get size of simple shadow spot mesh (8 triangles, 8 vertices)
|
// get size of simple shadow spot mesh (8 triangles, 8 vertices)
|
||||||
shadowBlob.vStart = vCount;
|
shadowBlob.vStart = vCount;
|
||||||
@@ -300,6 +303,13 @@ struct MeshBuilder {
|
|||||||
info.center = ptr->center;
|
info.center = ptr->center;
|
||||||
info.collider = ptr->collider;
|
info.collider = ptr->collider;
|
||||||
|
|
||||||
|
if (!info.offset)
|
||||||
|
meshMap[0] = &info;
|
||||||
|
else
|
||||||
|
for (int j = 0; j < level.meshOffsetsCount; j++)
|
||||||
|
if (info.offset == level.meshOffsets[j])
|
||||||
|
meshMap[j] = &info;
|
||||||
|
|
||||||
TR::Vertex *mVertices = (TR::Vertex*)&ptr->vertices;
|
TR::Vertex *mVertices = (TR::Vertex*)&ptr->vertices;
|
||||||
|
|
||||||
OFFSET(ptr->vCount * sizeof(TR::Vertex));
|
OFFSET(ptr->vCount * sizeof(TR::Vertex));
|
||||||
@@ -471,8 +481,18 @@ struct MeshBuilder {
|
|||||||
if (r.sprites.iCount)
|
if (r.sprites.iCount)
|
||||||
mesh->initRange(r.sprites);
|
mesh->initRange(r.sprites);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (int i = 0; i < level.spriteSequencesCount; i++)
|
for (int i = 0; i < level.spriteSequencesCount; i++)
|
||||||
mesh->initRange(spriteSequences[i]);
|
for (int j = 0; j < spriteSequences[i].iCount / 6; j++) { // init VAO for each frame
|
||||||
|
MeshRange range = spriteSequences[i];
|
||||||
|
range.iCount = 6;
|
||||||
|
range.iStart += j * 6;
|
||||||
|
range.vStart += j * 4;
|
||||||
|
mesh->initRange(range);
|
||||||
|
if (j == 0)
|
||||||
|
spriteSequences[i].aIndex = range.aIndex;
|
||||||
|
}
|
||||||
|
|
||||||
for (int i = 0; i < mCount; i++)
|
for (int i = 0; i < mCount; i++)
|
||||||
mesh->initRange(meshInfo[i]);
|
mesh->initRange(meshInfo[i]);
|
||||||
mesh->initRange(shadowBlob);
|
mesh->initRange(shadowBlob);
|
||||||
@@ -483,6 +503,7 @@ struct MeshBuilder {
|
|||||||
delete[] animTexOffsets;
|
delete[] animTexOffsets;
|
||||||
delete[] roomRanges;
|
delete[] roomRanges;
|
||||||
delete[] meshInfo;
|
delete[] meshInfo;
|
||||||
|
delete[] meshMap;
|
||||||
delete[] spriteSequences;
|
delete[] spriteSequences;
|
||||||
delete mesh;
|
delete mesh;
|
||||||
}
|
}
|
||||||
@@ -650,9 +671,7 @@ struct MeshBuilder {
|
|||||||
|
|
||||||
void renderSprite(int sequenceIndex, int frame) {
|
void renderSprite(int sequenceIndex, int frame) {
|
||||||
MeshRange range = spriteSequences[sequenceIndex];
|
MeshRange range = spriteSequences[sequenceIndex];
|
||||||
range.iCount = 6;
|
range.aIndex += frame;
|
||||||
range.iStart += frame * 6;
|
|
||||||
range.vStart += frame * 4;
|
|
||||||
mesh->render(range);
|
mesh->render(range);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user