Browse Source

Checkpoint with some assorted changes, before we break out the CompMatrix and ApplyMatrix big guns.

master
Nico de Poel 3 years ago
parent
commit
8ba6b4b073
  1. 83
      main.c

83
main.c

@ -76,24 +76,34 @@ typedef struct
ps1texture_t front, back;
} ps1skin_t;
ps1mdl_t playerModel = { .position = { -200, 320, 400 }, .rotation = { 0 } };
ps1mdl_t shamblerModel = { .position = { 200, 320, 400 }, .rotation = { 0 } };
ps1mdl_t playerModel = { .position = { -200, 160, 400 }, .rotation = { 0 } };
ps1mdl_t shamblerModel = { .position = { 200, 160, 400 }, .rotation = { 0 } };
ps1skin_t playerSkin, shamblerSkin;
MATRIX color_mtx = {
const MATRIX identity = {
ONE, 0, 0,
0, ONE, 0,
0, 0, ONE,
0, 0, 0,
};
MATRIX light_cols = {
ONE, 0, 0,
ONE, 0, 0,
ONE, 0, 0
};
MATRIX light_mtx = {
MATRIX light_dirs = {
ONE, 0, 0,
0, 0, 0,
0, 0, 0
};
// Scale X coordinates to correct the aspect ratio for the chosen resolution
VECTOR cam_scale = { SCREENWIDTH * ONE / 320 , ONE, ONE };
VECTOR aspect_scale = { SCREENWIDTH * ONE / 320 , ONE, ONE };
VECTOR cam_pos = { 0, 0, 0 };
SVECTOR cam_rot = { 0 };
void loadModel(const u_long* data, ps1mdl_t *mdl)
{
@ -357,9 +367,10 @@ void drawModel(ps1mdl_t *model, ps1skin_t *skin, int frameCounter)
short u0, u1, u2, uoffs, voffs;
int p;
int frameNum = frameCounter % model->header->frameCount;
int vertOffs = frameNum * model->header->vertexCount;
short halfSkinWidth = model->header->skinWidth >> 1;
unsigned short numTriangles = model->header->triangleCount;
int frameNum = frameCounter % model->header->frameCount;
ps1mdl_vertex_t *baseVert = &model->vertices[frameNum * model->header->vertexCount];
int *scale = model->header->scale;
int *translate = model->header->translate;
@ -378,31 +389,48 @@ void drawModel(ps1mdl_t *model, ps1skin_t *skin, int frameCounter)
// - Render
// - Pop matrix
MATRIX mtx, lmtx;
RotMatrix(&model->rotation, &mtx);
ScaleMatrixL(&mtx, &cam_scale); // Aspect ratio correction
TransMatrix(&mtx, &model->position);
MulMatrix0(&light_mtx, &mtx, &lmtx);
// TODO: this can all probably be done much more efficiently with the CompMatrixLV function. Doing it manually first though to better understand it.
MATRIX cam_mtx = identity;
//VECTOR cam_inv_pos = { -cam_pos.vx, -cam_pos.vy, -cam_pos.vz };
ScaleMatrixL(&cam_mtx, &aspect_scale); // Aspect ratio correction
//TransMatrix(&cam_mtx, &cam_inv_pos);
//MATRIX cam_rot_mtx;
//SVECTOR cam_inv_rot = { -cam_rot.vx, -cam_rot.vy, -cam_rot.vz, 0 };
//RotMatrix(&cam_inv_rot, &cam_rot_mtx);
//MulMatrix(&cam_mtx, &cam_rot_mtx);
MATRIX light_mtx;
// MulMatrix0(&light_dirs, &cam_mtx, &light_mtx);
// gte_SetLightMatrix(&light_mtx);
MATRIX model_mtx;
RotMatrix(&model->rotation, &model_mtx);
TransMatrix(&model_mtx, &model->position);
MulMatrix(&model_mtx, &cam_mtx);
MulMatrix0(&light_dirs, &model_mtx, &light_mtx);
gte_SetLightMatrix(&light_mtx);
// Model internal scale and translate, to transform vertices from [0..255] range to a larger dynamic range with appropriate world-relative size
// Swizzle the coordinates because Quake Z is up
// Finding the appropriate scale range here is tricky. Without the << 2 scale the vertex coordinates become so small that you lose depth precision.
MATRIX local = { .m = { ONE << 2, 0, 0, 0, 0, -ONE << 2, 0, ONE << 2, 0 }, .t = { 0 } };
ScaleMatrixL(&local, (VECTOR*)scale);
TransMatrix(&local, (VECTOR*)translate);
MulMatrix(&mtx, &local);
MATRIX local_mtx = { .m = { ONE << 2, 0, 0, 0, 0, -ONE << 2, 0, ONE << 2, 0 }, .t = { 0 } };
ScaleMatrixL(&local_mtx, (VECTOR*)scale);
TransMatrix(&local_mtx, (VECTOR*)translate);
MulMatrix(&model_mtx, &local_mtx);
gte_SetRotMatrix(&mtx);
gte_SetTransMatrix(&mtx);
gte_SetLightMatrix(&lmtx);
// TODO: set these after setting up camera, then use PushMatrix + CompMatrixLV for entities?
gte_SetRotMatrix(&model_mtx);
gte_SetTransMatrix(&model_mtx);
for (int triIdx = 0; triIdx < model->header->triangleCount; ++triIdx)
for (unsigned short triIdx = 0; triIdx < numTriangles; ++triIdx)
{
ps1mdl_triangle_t *tri = &model->triangles[triIdx];
ps1mdl_vertex_t *v0 = &model->vertices[tri->vertexIndex[0] + vertOffs];
ps1mdl_vertex_t *v1 = &model->vertices[tri->vertexIndex[1] + vertOffs];
ps1mdl_vertex_t *v2 = &model->vertices[tri->vertexIndex[2] + vertOffs];
ps1mdl_vertex_t *v0 = &baseVert[tri->vertexIndex[0]];
ps1mdl_vertex_t *v1 = &baseVert[tri->vertexIndex[1]];
ps1mdl_vertex_t *v2 = &baseVert[tri->vertexIndex[2]];
SVECTOR pos0 = { v0->position[0], v0->position[1], v0->position[2], 0 };
SVECTOR pos1 = { v1->position[0], v1->position[1], v1->position[2], 0 };
@ -442,15 +470,14 @@ void drawModel(ps1mdl_t *model, ps1skin_t *skin, int frameCounter)
tex = &skin->back;
}
// TODO: we could get rid of these silly offsets if we just ensure that textures are always page-aligned
uoffs = tex->uoffs, voffs = tex->voffs;
POLY_GT3 *poly = (POLY_GT3*)nextpri;
setPolyGT3(poly);
// Store transformed vertex coordinates in screen space
gte_stsxy0(&poly->x0);
gte_stsxy1(&poly->x1);
gte_stsxy2(&poly->x2);
gte_stsxy3_gt3(poly);
// Copy some values for on-screen debugging
outPos.vx = poly->x0;
@ -486,7 +513,7 @@ void drawStuff(int counter)
FntFlush(-1);
gte_SetBackColor(48, 48, 48); // Ambient light color
gte_SetColorMatrix(&color_mtx); // Light color (up to three different lights)
gte_SetColorMatrix(&light_cols); // Light color (up to three different lights)
drawModel(&playerModel, &playerSkin, counter >> 2);
drawModel(&shamblerModel, &shamblerSkin, counter >> 2);
@ -504,6 +531,8 @@ int main(int argc, const char *argv[])
counter = 0;
while(1)
{
playerModel.rotation.vz = (counter << 2) % ONE;
drawStuff(counter);
// Update display

Loading…
Cancel
Save