lemur/game.c

89 lines
2.2 KiB
C

#include <audio.h>
#include <assets.h>
#include <controller.h>
#include <game.h>
#include <SDL3/SDL.h>
#include <stdbool.h>
#include <time.h>
int sleepNanos(long int ns) {
struct timespec time;
if (ns < 0) return 0;
time.tv_sec = ns / 1000000000;
time.tv_nsec = ns % 1000000000;
return nanosleep(&time, NULL);
}
long int tickNs() {
struct timespec time;
clock_gettime(CLOCK_MONOTONIC, &time);
return (time.tv_sec * 1000000000) + time.tv_nsec;
}
typedef struct {
GraphicsContext *gfx;
AudioContext aud;
int16_t audioBuffer[834 * 2];
} GameState;
int onFrame(VB *sim) {
static uint8_t leftEye[384*224];
static uint8_t rightEye[384*224];
GameState *state;
void *samples;
uint32_t samplePairs;
state = vbGetUserData(sim);
vbGetPixels(sim, leftEye, 1, 384, rightEye, 1, 384);
gfxUpdateLeftEye(state->gfx, leftEye);
gfxUpdateRightEye(state->gfx, rightEye);
samples = vbGetSamples(sim, NULL, &samplePairs);
audioUpdate(&state->aud, samples, samplePairs * 4);
vbSetSamples(sim, samples, 834);
gfxRender(state->gfx);
return 1;
}
#define MAX_STEP_CLOCKS 20000000
int runGame(VB *sim, GraphicsContext *gfx) {
uint32_t clocks;
SDL_Event event;
GameState state;
ControllerState ctrl;
uint64_t ticks, prevTicks;
state.gfx = gfx;
audioInit(&state.aud);
vbSetSamples(sim, &state.audioBuffer, 834);
vbSetUserData(sim, &state);
vbSetFrameCallback(sim, &onFrame);
ctrlInit(&ctrl);
gfxUpdateLeftEye(gfx, LEFT_EYE_DEFAULT);
gfxUpdateRightEye(gfx, RIGHT_EYE_DEFAULT);
while (1) {
clocks = MAX_STEP_CLOCKS;
prevTicks = tickNs();
vbEmulate(sim, &clocks);
ticks = tickNs();
sleepNanos(((MAX_STEP_CLOCKS - clocks) * 50) - (ticks - prevTicks));
while (SDL_PollEvent(&event)) {
if (event.type == SDL_EVENT_QUIT) {
return 0;
}
if (event.type == SDL_EVENT_KEY_DOWN) {
ctrlKeyDown(&ctrl, event.key.key);
}
if (event.type == SDL_EVENT_KEY_UP) {
ctrlKeyUp(&ctrl, event.key.key);
}
}
vbSetKeys(sim, ctrlKeys(&ctrl));
}
}