Re-enable collision and implement game lose screen

This commit is contained in:
Doyle Thai 2016-12-18 19:48:14 +11:00
parent 386e94db91
commit b3760aa3fc
6 changed files with 140 additions and 39 deletions

View File

@ -722,22 +722,67 @@ INTERNAL void gameUpdate(GameState *state, Memory *memory, f32 dt)
multiplierToStringP, V2(0, 0), 0, V4(1.0f, 1.0f, 1.0f, 1.0f), 3, 0); multiplierToStringP, V2(0, 0), 0, V4(1.0f, 1.0f, 1.0f, 1.0f), 3, 0);
/* Process multiplier bar updates */ /* Process multiplier bar updates */
f32 barTimerPenalty = 1.0f; if (!common_isSet(world->flags, gameworldstateflags_player_lost))
if (world->timeSinceLastShot < 1.5f)
{ {
barTimerPenalty = 0.1f; f32 barTimerPenalty = 1.0f;
if (world->timeSinceLastShot < 1.5f)
{
barTimerPenalty = 0.1f;
}
world->scoreMultiplierBarTimer += (barTimerPenalty * dt);
world->timeSinceLastShot += dt;
if (world->scoreMultiplierBarTimer >
world->scoreMultiplierBarThresholdInS)
{
world->scoreMultiplierBarTimer = 0;
world->scoreMultiplier++;
if (world->scoreMultiplier > 9999)
world->scoreMultiplier = 9999;
}
} }
}
world->scoreMultiplierBarTimer += (barTimerPenalty * dt); if (common_isSet(world->flags, gameworldstateflags_player_lost))
world->timeSinceLastShot += dt; {
Font *arial40 = asset_fontGet(&state->assetManager, "Arial", 40);
if (world->scoreMultiplierBarTimer > char *gameOver = "Game Over";
world->scoreMultiplierBarThresholdInS) v2 gameOverP = v2_scale(state->renderer.size, 0.5f);
renderer_stringFixedCentered(
&state->renderer, &state->transientArena, arial40, "Game Over",
gameOverP, V2(0, 0), 0, V4(1, 1, 1, 1), 0, 0);
v2 gameOverSize = asset_fontStringDimInPixels(arial40, gameOver);
v2 replayP = V2(gameOverP.x, gameOverP.y - (gameOverSize.h * 1.2f));
renderer_stringFixedCentered(
&state->renderer, &state->transientArena, arial40,
"Press enter to play again or backspace to return to menu", replayP,
V2(0, 0), 0, V4(1, 1, 1, 1), 0, 0);
if (platform_queryKey(&state->input.keys[keycode_enter],
readkeytype_one_shot, 0.0f))
{ {
world->scoreMultiplierBarTimer = 0; // TODO(doyle): Extract score init default values to some game
world->scoreMultiplier++; // definitions file
world->score = 0;
world->scoreMultiplier = 5;
world->scoreMultiplierBarTimer = 0.0f;
world->scoreMultiplierBarThresholdInS = 2.0f;
if (world->scoreMultiplier > 9999) world->scoreMultiplier = 9999; addPlayer(world);
world->flags ^= gameworldstateflags_player_lost;
}
else if (platform_queryKey(&state->input.keys[keycode_backspace],
readkeytype_one_shot, 0.0f))
{
common_memset((u8 *)world, 0, sizeof(*world));
state->currState = appstate_StartMenuState;
return;
} }
} }
@ -780,11 +825,13 @@ INTERNAL void gameUpdate(GameState *state, Memory *memory, f32 dt)
renderflag_no_texture | renderflag_wireframe); renderflag_no_texture | renderflag_wireframe);
} }
#ifdef DENGINE_DEBUG
if (platform_queryKey(&state->input.keys[keycode_left_square_bracket], if (platform_queryKey(&state->input.keys[keycode_left_square_bracket],
readkeytype_repeat, 0.2f)) readkeytype_repeat, 0.2f))
{ {
addAsteroid(world, (rand() % asteroidsize_count)); addAsteroid(world, (rand() % asteroidsize_count));
} }
#endif
ASSERT(world->entityList[0].id == NULL_ENTITY_ID); ASSERT(world->entityList[0].id == NULL_ENTITY_ID);
for (i32 i = 1; i < world->entityIndex; i++) for (i32 i = 1; i < world->entityIndex; i++)
@ -807,6 +854,17 @@ INTERNAL void gameUpdate(GameState *state, Memory *memory, f32 dt)
DEGREES_TO_RADIANS((entity->rotation + 90.0f)); DEGREES_TO_RADIANS((entity->rotation + 90.0f));
v2 direction = V2(math_cosf(rotation), math_sinf(rotation)); v2 direction = V2(math_cosf(rotation), math_sinf(rotation));
ddP = direction; ddP = direction;
AudioVorbis *thrust =
asset_vorbisGet(&state->assetManager, "thrust");
AudioRenderer *audioRenderer =
getFreeAudioRenderer(world, thrust, 3);
if (audioRenderer)
{
audio_vorbisPlay(&state->transientArena,
&state->audioManager, audioRenderer,
thrust, 1);
}
} }
if (platform_queryKey(&state->input.keys[keycode_space], if (platform_queryKey(&state->input.keys[keycode_space],
@ -1003,6 +1061,14 @@ INTERNAL void gameUpdate(GameState *state, Memory *memory, f32 dt)
colliderB = collideEntity; colliderB = collideEntity;
} }
// Assumptions made that the collision detect system relies on
ASSERT(entitytype_ship < entitytype_asteroid_small);
ASSERT(entitytype_asteroid_small < entitytype_asteroid_medium);
ASSERT(entitytype_asteroid_medium < entitytype_asteroid_large);
ASSERT(entitytype_asteroid_large < entitytype_bullet);
ASSERT(entitytype_asteroid_small + 1 == entitytype_asteroid_medium);
ASSERT(entitytype_asteroid_medium + 1 == entitytype_asteroid_large);
if (colliderA->type >= entitytype_asteroid_small && if (colliderA->type >= entitytype_asteroid_small &&
colliderA->type <= entitytype_asteroid_large) colliderA->type <= entitytype_asteroid_large)
{ {
@ -1092,7 +1158,6 @@ INTERNAL void gameUpdate(GameState *state, Memory *memory, f32 dt)
ASSERT(colliderB->type == entitytype_bullet); ASSERT(colliderB->type == entitytype_bullet);
deleteEntity(world, collisionIndex); deleteEntity(world, collisionIndex);
deleteEntity(world, i--); deleteEntity(world, i--);
world->asteroidCounter--; world->asteroidCounter--;
@ -1126,6 +1191,36 @@ INTERNAL void gameUpdate(GameState *state, Memory *memory, f32 dt)
continue; continue;
} }
else if (colliderA->type == entitytype_ship)
{
if (colliderB->type >= entitytype_asteroid_small &&
colliderB->type <= entitytype_asteroid_large)
{
world->flags |= gameworldstateflags_player_lost;
if (collideEntity->type == entitytype_ship)
{
deleteEntity(world, collisionIndex);
}
else
{
deleteEntity(world, i--);
}
AudioVorbis *explode =
asset_vorbisGet(&state->assetManager, "bang_large");
AudioRenderer *audioRenderer =
getFreeAudioRenderer(world, explode, 3);
if (audioRenderer)
{
audio_vorbisPlay(&state->transientArena,
&state->audioManager, audioRenderer,
explode, 1);
}
continue;
}
}
} }
RenderFlags flags = renderflag_wireframe | renderflag_no_texture; RenderFlags flags = renderflag_wireframe | renderflag_no_texture;
@ -1219,13 +1314,11 @@ INTERNAL void startMenuUpdate(GameState *state, Memory *memory, f32 dt)
menuState->newResolutionRequest = TRUE; menuState->newResolutionRequest = TRUE;
v2 newSize = v2 newSize =
resolutionArray->ptr[menuState->resStringDisplayIndex]; resolutionArray->ptr[menuState->resStringDisplayIndex];
GameWorldState *world = GET_STATE_DATA(
state, &state->persistentArena, GameWorldState);
renderer_updateSize(renderer, &state->assetManager, newSize); renderer_updateSize(renderer, &state->assetManager, newSize);
// TODO(doyle): reset world arena instead of zeroing out struct // TODO(doyle): reset world arena instead of zeroing out struct
GameWorldState *world = GET_STATE_DATA(
state, &state->persistentArena, GameWorldState);
common_memset((u8 *)world, 0, sizeof(GameWorldState)); common_memset((u8 *)world, 0, sizeof(GameWorldState));
debug_init(newSize, *arial15); debug_init(newSize, *arial15);
} }
@ -1327,10 +1420,9 @@ INTERNAL void startMenuUpdate(GameState *state, Memory *memory, f32 dt)
GameWorldState *world = GameWorldState *world =
GET_STATE_DATA(state, &state->persistentArena, GameWorldState); GET_STATE_DATA(state, &state->persistentArena, GameWorldState);
addPlayer(world);
state->currState = appstate_GameWorldState; state->currState = appstate_GameWorldState;
world->flags |= gameworldstateflags_level_started; world->flags |= gameworldstateflags_level_started;
addPlayer(world);
} }
else if (platform_queryKey(&inputBuffer->keys[keycode_o], else if (platform_queryKey(&inputBuffer->keys[keycode_o],
readkeytype_one_shot, KEY_DELAY_NONE)) readkeytype_one_shot, KEY_DELAY_NONE))

View File

@ -35,6 +35,10 @@ INTERNAL void shaderUse(u32 shaderId) { glUseProgram(shaderId); }
void renderer_updateSize(Renderer *renderer, AssetManager *assetManager, v2 windowSize) void renderer_updateSize(Renderer *renderer, AssetManager *assetManager, v2 windowSize)
{ {
renderer->size = windowSize; renderer->size = windowSize;
// renderer->displayScale =
// V2(windowSize.x * 1.0f / renderer->referenceScale.x,
// windowSize.y * 1.0f / renderer->referenceScale.y);
// NOTE(doyle): Value to map a screen coordinate to NDC coordinate // NOTE(doyle): Value to map a screen coordinate to NDC coordinate
renderer->vertexNdcFactor = renderer->vertexNdcFactor =
V2(1.0f / renderer->size.w, 1.0f / renderer->size.h); V2(1.0f / renderer->size.w, 1.0f / renderer->size.h);
@ -48,7 +52,7 @@ void renderer_updateSize(Renderer *renderer, AssetManager *assetManager, v2 wind
renderer->shaderList[i] = asset_shaderGet(assetManager, i); renderer->shaderList[i] = asset_shaderGet(assetManager, i);
shaderUse(renderer->shaderList[i]); shaderUse(renderer->shaderList[i]);
shaderUniformSetMat4fv(renderer->shaderList[i], "projection", shaderUniformSetMat4fv(renderer->shaderList[i], "projection",
projection); projection);
GL_CHECK_ERROR(); GL_CHECK_ERROR();
} }
@ -59,6 +63,7 @@ void renderer_updateSize(Renderer *renderer, AssetManager *assetManager, v2 wind
void renderer_init(Renderer *renderer, AssetManager *assetManager, void renderer_init(Renderer *renderer, AssetManager *assetManager,
MemoryArena_ *persistentArena, v2 windowSize) MemoryArena_ *persistentArena, v2 windowSize)
{ {
renderer->referenceScale = V2(1280, 720);
renderer_updateSize(renderer, assetManager, windowSize); renderer_updateSize(renderer, assetManager, windowSize);
/* Create buffers */ /* Create buffers */

View File

@ -19,10 +19,12 @@ INTERNAL void keyCallback(GLFWwindow *window, int key, int scancode, int action,
{ {
GameState *game = CAST(GameState *)(glfwGetWindowUserPointer(window)); GameState *game = CAST(GameState *)(glfwGetWindowUserPointer(window));
#if 1
if (key == GLFW_KEY_ESCAPE && action == GLFW_PRESS) if (key == GLFW_KEY_ESCAPE && action == GLFW_PRESS)
{ {
glfwSetWindowShouldClose(window, GL_TRUE); glfwSetWindowShouldClose(window, GL_TRUE);
} }
#endif
switch (key) switch (key)
{ {

View File

@ -26,11 +26,9 @@ typedef struct AssetManager
void asset_init(AssetManager *assetManager, MemoryArena_ *arena); void asset_init(AssetManager *assetManager, MemoryArena_ *arena);
/* ////////////////////////////////////////////////////////////////////////////////
********************************* // Texture Managing
* Texture Operations ////////////////////////////////////////////////////////////////////////////////
*********************************
*/
const SubTexture asset_atlasGetSubTex(TexAtlas *const atlas, const SubTexture asset_atlasGetSubTex(TexAtlas *const atlas,
const char *const key); const char *const key);
Texture *asset_texGet(AssetManager *const assetManager, const char *const key); Texture *asset_texGet(AssetManager *const assetManager, const char *const key);
@ -49,11 +47,9 @@ u8 *asset_imageLoad(i32 *width, i32 *height, i32 *bpp, const char *const path,
void asset_imageFree(u8 *image); void asset_imageFree(u8 *image);
/* ////////////////////////////////////////////////////////////////////////////////
********************************* // Animation Asset Managing
* Animation Asset Managing ////////////////////////////////////////////////////////////////////////////////
*********************************
*/
void asset_animAdd(AssetManager *const assetManager, MemoryArena_ *const arena, void asset_animAdd(AssetManager *const assetManager, MemoryArena_ *const arena,
const char *const animName, TexAtlas *const atlas, const char *const animName, TexAtlas *const atlas,
char **const subTextureNames, const i32 numSubTextures, char **const subTextureNames, const i32 numSubTextures,
@ -61,21 +57,17 @@ void asset_animAdd(AssetManager *const assetManager, MemoryArena_ *const arena,
Animation *asset_animGet(AssetManager *const assetManager, Animation *asset_animGet(AssetManager *const assetManager,
const char *const key); const char *const key);
/* ////////////////////////////////////////////////////////////////////////////////
********************************* // Audio
* Audio ////////////////////////////////////////////////////////////////////////////////
*********************************
*/
AudioVorbis *const asset_vorbisGet(AssetManager *const assetManager, AudioVorbis *const asset_vorbisGet(AssetManager *const assetManager,
const char *const key); const char *const key);
const i32 asset_vorbisLoad(AssetManager *assetManager, MemoryArena_ *arena, const i32 asset_vorbisLoad(AssetManager *assetManager, MemoryArena_ *arena,
const char *const path, const char *const key); const char *const path, const char *const key);
/* ////////////////////////////////////////////////////////////////////////////////
********************************* // Everything else
* Everything else ////////////////////////////////////////////////////////////////////////////////
*********************************
*/
const i32 asset_xmlLoad(AssetManager *const assetManager, const i32 asset_xmlLoad(AssetManager *const assetManager,
MemoryArena_ *const arena, MemoryArena_ *const arena,
const PlatformFileRead *const fileRead); const PlatformFileRead *const fileRead);

View File

@ -19,8 +19,10 @@ enum AppState
enum GameWorldStateFlags enum GameWorldStateFlags
{ {
gameworldstateflags_init = (1 << 0), gameworldstateflags_init = (1 << 0),
gameworldstateflags_level_started = (1 << 1), gameworldstateflags_level_started = (1 << 1),
gameworldstateflags_player_lost = (1 << 2),
gameworldstateflags_create_player = (1 << 3),
}; };
typedef struct GameWorldState typedef struct GameWorldState

View File

@ -68,6 +68,7 @@ enum VertexBatchState {
typedef struct Renderer typedef struct Renderer
{ {
// rendererf
u32 shaderList[shaderlist_count]; u32 shaderList[shaderlist_count];
u32 activeShaderId; u32 activeShaderId;
@ -81,6 +82,13 @@ typedef struct Renderer
v2 vertexNdcFactor; v2 vertexNdcFactor;
v2 size; v2 size;
// NOTE(doyle): Reference scale is the size chosen to have the best
// playability based on the sizes of the entity given to the system. Any
// other resoluions will be scaled through the renderer so that objects
// remain the same size in different resolutions.
f32 displayScale;
v2 referenceScale;
RenderGroup groups[128]; RenderGroup groups[128];
i32 groupsInUse; i32 groupsInUse;
i32 groupCapacity; i32 groupCapacity;