This repository has been archived on 2025-03-02. You can view files and clone it, but cannot push or open issues or pull requests.
neofx-libzoom/player.c

216 lines
6.4 KiB
C
Raw Normal View History

2005-04-18 15:27:00 +00:00
#include <stddef.h>
#include <math.h>
#include <zoom/player.h>
#include <zoom/level.h>
#include <zoom/collision.h>
#include <zoom/math.h>
int input = 0;
int falling = 0;
PLAYER player = {
{0.0, 0.0, 0.0},
0.0, 0.0, 1.0,
100, 100, 0
};
float rotx = 0, roty = 0;
float rotxspeed = 0, rotyspeed = 0;
float objrot = 0;
extern LEVEL level;
void MouseInput(int x, int y) {
roty += x * 0.3;
rotx += y * 0.3;
rotxspeed = rotx * 0.02;
rotyspeed = roty * 0.02;
}
void DoInput(int delta) {
int i, wasfalling = falling;
int g;
VERTEX pos;
int room = player.room;
VECTOR move = {0.0, 0.0, 0.0};
VECTOR v = {0.0, -1.0, 0.0};
float s, c;
float f = 0.0;
VERTEX p1, p2;
VECTOR v1, v2;
MATRIX transform;
objrot += 0.01*delta;
if(objrot > 360.0) objrot -= 360.0;
if(rotx > 0) {
if(rotx < rotxspeed*delta) {player.rotx += rotx; rotx = 0;}
else {player.rotx += rotxspeed*delta; rotx -= rotxspeed*delta;}
}
else if(rotx < 0) {
if(rotx > rotxspeed*delta) {player.rotx += rotx; rotx = 0;}
else {player.rotx += rotxspeed*delta; rotx -= rotxspeed*delta;}
}
if(roty > 0) {
if(roty < rotyspeed*delta) {f = roty; roty = 0;}
else {f = rotyspeed*delta; roty -= rotyspeed*delta;}
}
else if(roty < 0) {
if(roty > rotyspeed*delta) {f = roty; roty = 0;}
else {f = rotyspeed*delta; roty -= rotyspeed*delta;}
}
if(player.rotx > 60) player.rotx = 60;
else if(player.rotx < -60) player.rotx = -60;
s = sin(f/180*M_PI);
c = cos(f/180*M_PI);
f = c*player.rotycos - s*player.rotysin;
player.rotysin = c*player.rotysin + s*player.rotycos;
player.rotycos = f;
s = player.rotysin;
c = player.rotycos;
if(!falling) {
if((input & INPUT_UP) && !(input & INPUT_DOWN)) {
if((input & INPUT_RIGHT) && !(input & INPUT_LEFT)) {
move.x = (s+c)*M_SQRT1_2;
move.z = (s-c)*M_SQRT1_2;
}
else if((input & INPUT_LEFT) && !(input & INPUT_RIGHT)) {
move.x = (s-c)*M_SQRT1_2;
move.z = (-s-c)*M_SQRT1_2;
}
else {
move.x = s;
move.z = -c;
}
}
else if((input & INPUT_DOWN) && !(input & INPUT_UP)) {
if((input & INPUT_RIGHT) && !(input & INPUT_LEFT)) {
move.x = (-s+c)*M_SQRT1_2;
move.z = (s+c)*M_SQRT1_2;
}
else if((input & INPUT_LEFT) && !(input & INPUT_RIGHT)) {
move.x = (-s-c)*M_SQRT1_2;
move.z = (-s+c)*M_SQRT1_2;
}
else {
move.x = -s;
move.z = c;
}
}
else if((input & INPUT_RIGHT) && !(input & INPUT_LEFT)) {
move.x = c;
move.z = s;
}
else if((input & INPUT_LEFT) && !(input & INPUT_RIGHT)) {
move.x = -c;
move.z = -s;
}
if(input & INPUT_OPEN) {
for(i = 0; i < level.rooms[room].nGates; i++) {
if(level.rooms[room].gateinfo[i].state != STATE_CLOSED) continue;
if(CollisionSphereTriangle(player.pos, 1.0, level.rooms[room].gates[i].triangles[0]) ||
CollisionSphereTriangle(player.pos, 1.0, level.rooms[room].gates[i].triangles[1])) {
level.rooms[room].gateinfo[i].state = STATE_OPENING;
level.rooms[room].gateinfo[i].timer = 1000;
}
}
}
}
pos = VectorAdd(player.pos, VectorMul(move, delta/150.0));
if(falling) pos.y -= delta/100.0;
for(i = 0; i < level.rooms[room].nGates; i++) {
if(CollisionSphereTriangle(pos, 0.3, level.rooms[room].gates[i].triangles[0]) ||
CollisionSphereTriangle(pos, 0.3, level.rooms[room].gates[i].triangles[1])) {
if(level.rooms[room].gateinfo[i].state == STATE_OPENED) {
if(CollisionPointTriangle(pos, level.rooms[room].gates[i].triangles[0]) ||
CollisionPointTriangle(pos, level.rooms[room].gates[i].triangles[1])) {
p1 = level.rooms[room].gates[i].point;
v1 = level.rooms[room].gates[i].triangles[0].normal;
level.rooms[room].gateinfo[i].state = STATE_CLOSED;
g = level.rooms[room].gates[i].gate;
room = level.rooms[room].gates[i].room;
p2 = level.rooms[room].gates[g].point;
v2 = VectorNeg(level.rooms[room].gates[g].triangles[0].normal);
level.rooms[room].gateinfo[g].state = STATE_OPENED;
level.rooms[room].gateinfo[g].timer = 5000;
transform = VectorMatrix(p2, v2, p1, v1);
pos = VectorMatrixMul(pos, transform);
v1.x = p1.x + c;
v1.z = p1.z + s;
v1 = VectorMatrixMul(v1, transform);
c = v1.x - p2.x;
s = v1.z - p2.z;
move = VectorSub(VectorMatrixMul(VectorAdd(move, p1), transform), p2);
break;
}
level.rooms[room].gateinfo[i].timer = 5000;
}
else pos = player.pos;
}
}
falling = 1;
for(i = 0; i < level.rooms[room].nTriangles; i++) {
if(level.rooms[room].triangles[i].type == TRIANGLE_WALL &&
CollisionMovingSphereTriangle(VectorSub(pos, VectorMul(move, delta/150.0)), 0.3, move, delta/150.0, level.rooms[room].triangles[i])) {
pos = player.pos;
if(player.room != room) {
level.rooms[room].gateinfo[g].state = STATE_CLOSED;
g = level.rooms[room].gates[g].gate;
room = player.room;
level.rooms[room].gateinfo[g].state = STATE_OPENED;
}
s = player.rotysin;
c = player.rotycos;
falling = 0;
break;
}
else if(level.rooms[room].triangles[i].type == TRIANGLE_FLOOR) {
pos.y -= 1.81;
if(CollisionPointTriangle(pos, level.rooms[room].triangles[i])) {
falling = 0;
pos.y += 1.81;
if(wasfalling && CollisionRayTriangle(pos, v, level.rooms[room].triangles[i], &f)) pos.y -= f - 1.8;
}
else pos.y += 1.81;
}
}
player.pos = pos;
player.room = room;
player.rotysin = s;
player.rotycos = c;
for(i = 0; i < level.rooms[player.room].nObjects; i++) {
pos = VectorSub(level.rooms[player.room].objects[i].pos, player.pos);
pos.y += 0.9;
switch(level.rooms[player.room].objects[i].type) {
case OBJECT_MEDIPAK100:
if((pos.x*pos.x + (pos.y*pos.y)/3 + pos.z*pos.z) < 0.36) level.rooms[player.room].objects[i].visible = 0;
}
}
for(i = 0; i < level.rooms[player.room].nGates; i++) {
if(level.rooms[player.room].gateinfo[i].state == STATE_CLOSED) continue;
if((level.rooms[player.room].gateinfo[i].timer - delta) < 0) {
if(level.rooms[player.room].gateinfo[i].state == STATE_OPENING) {
level.rooms[player.room].gateinfo[i].state = STATE_OPENED;
level.rooms[player.room].gateinfo[i].timer = 5000;
}
else if(level.rooms[player.room].gateinfo[i].state == STATE_OPENED) {
level.rooms[player.room].gateinfo[i].state = STATE_CLOSING;
level.rooms[player.room].gateinfo[i].timer = 1000;
}
else level.rooms[player.room].gateinfo[i].state = STATE_CLOSED;
}
else level.rooms[player.room].gateinfo[i].timer -= delta;
}
}