Add level completion flags
Changelog: - Completing a level will mark it so - Level selects reflects the status of the level completion with text colour - This also prepare to persist these flagsmain
parent
e85dc42f3e
commit
9ebacbc572
|
@ -684,15 +684,18 @@ bool vert_scrollarea_n_items(VertScrollArea_t* scroll_area, unsigned int n_items
|
|||
return true;
|
||||
}
|
||||
|
||||
void vert_scrollarea_insert_item(VertScrollArea_t* scroll_area, char* str, unsigned int item_idx)
|
||||
void vert_scrollarea_insert_item(VertScrollArea_t* scroll_area, char* str, unsigned int item_idx, Color colour)
|
||||
{
|
||||
if (item_idx >= scroll_area->max_items) return;
|
||||
|
||||
float y_pos = scroll_area->item_padding + (scroll_area->item_height + scroll_area->item_padding) * item_idx;
|
||||
|
||||
//DrawRectangle(0, y_pos, scroll_area->display_area.width, scroll_area->item_height, BLANK);
|
||||
DrawTextEx(
|
||||
scroll_area->comp.font,
|
||||
str,
|
||||
(Vector2){0, scroll_area->item_padding + (scroll_area->item_height + scroll_area->item_padding) * item_idx}
|
||||
, scroll_area->item_height, 0, BLACK);
|
||||
(Vector2){0, y_pos}
|
||||
, scroll_area->item_height, 0, colour);
|
||||
}
|
||||
|
||||
unsigned int vert_scrollarea_set_pos(VertScrollArea_t* scroll_area, Vector2 pos)
|
||||
|
|
|
@ -35,7 +35,7 @@ void init_UI(void);
|
|||
void vert_scrollarea_init(VertScrollArea_t* scroll_area, Rectangle display_area, Vector2 canvas_dims);
|
||||
void vert_scrollarea_set_item_dims(VertScrollArea_t* scroll_area, unsigned int item_height, unsigned int item_padding);
|
||||
bool vert_scrollarea_n_items(VertScrollArea_t* scroll_area, unsigned int n_items);
|
||||
void vert_scrollarea_insert_item(VertScrollArea_t* scroll_area, char* str, unsigned int item_idx);
|
||||
void vert_scrollarea_insert_item(VertScrollArea_t* scroll_area, char* str, unsigned int item_idx, Color colour);
|
||||
unsigned int vert_scrollarea_set_pos(VertScrollArea_t* scroll_area, Vector2 pos);
|
||||
void vert_scrollarea_refocus(VertScrollArea_t* scroll_area);
|
||||
void vert_scrollarea_render(VertScrollArea_t* scroll_area);
|
||||
|
|
|
@ -12,6 +12,7 @@ add_library(lib_scenes STATIC
|
|||
scene_systems.c
|
||||
camera_systems.c
|
||||
engine_impl.c
|
||||
save_data.c
|
||||
)
|
||||
target_include_directories(lib_scenes
|
||||
PUBLIC
|
||||
|
|
|
@ -58,4 +58,5 @@ static const uint8_t CONNECTIVITY_TILE_MAPPING[16] = {
|
|||
};
|
||||
|
||||
#define ANIM_FRAME_RATE (1.0f/24)
|
||||
#define SAVE_FILE_NAME "save.dat"
|
||||
#endif // __CONSTANTS_H
|
||||
|
|
|
@ -2,6 +2,7 @@
|
|||
|
||||
#include "keymaps.h"
|
||||
#include "scene_impl.h"
|
||||
#include "save_data.h"
|
||||
#include "game_systems.h"
|
||||
#include "water_flow.h"
|
||||
#include "constants.h"
|
||||
|
@ -530,6 +531,7 @@ static void at_level_start(Scene_t* scene)
|
|||
static void at_level_complete(Scene_t* scene)
|
||||
{
|
||||
LevelSceneData_t* data = &(CONTAINER_OF(scene, LevelScene_t, scene)->data);
|
||||
set_level_completed(data->current_level, true);
|
||||
data->sm.fractional += scene->delta_time;
|
||||
if (data->sm.fractional > 1.0f)
|
||||
{
|
||||
|
|
|
@ -3,6 +3,7 @@
|
|||
#include "gui.h"
|
||||
#include "raymath.h"
|
||||
#include <stdio.h>
|
||||
#include "save_data.h"
|
||||
|
||||
#define LEVEL_PREVIEW_SIZE 430
|
||||
static void level_select_render_func(Scene_t* scene)
|
||||
|
@ -257,15 +258,55 @@ static void level_select_action_remap_func(Scene_t* scene)
|
|||
sc_map_put_64(&scene->action_map, KEY_ENTER, ACTION_CONFIRM);
|
||||
}
|
||||
|
||||
static void render_scroll_canvas(LevelSelectSceneData_t* data)
|
||||
{
|
||||
// Hardcoded buffer size
|
||||
char buf[48];
|
||||
ScrollAreaRenderBegin(&data->scroll_area);
|
||||
ClearBackground(BLANK);
|
||||
if (data->level_pack != NULL)
|
||||
{
|
||||
vert_scrollarea_n_items(&data->scroll_area, data->level_pack->n_levels);
|
||||
for (unsigned int i = 0; i < data->level_pack->n_levels; ++i)
|
||||
{
|
||||
vert_scrollarea_insert_item(&data->scroll_area, data->level_pack->levels[i].level_name, i, (is_level_completed(i)) ? GREEN : BLACK);
|
||||
}
|
||||
for (unsigned int i = data->level_pack->n_levels; i < data->scroll_area.max_items; ++i)
|
||||
{
|
||||
vert_scrollarea_insert_item(&data->scroll_area, "---", i, BLACK);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
for (unsigned int i = 0; i < data->scroll_area.max_items; ++i)
|
||||
{
|
||||
sprintf(buf, "Level %u", i);
|
||||
vert_scrollarea_insert_item(&data->scroll_area, buf, i, BLACK);
|
||||
}
|
||||
}
|
||||
ScrollAreaRenderEnd();
|
||||
}
|
||||
|
||||
static void reset_level_selection_scene(Scene_t* scene)
|
||||
{
|
||||
LevelSelectSceneData_t* data = &(CONTAINER_OF(scene, LevelSelectScene_t, scene)->data);
|
||||
// Re-draw the canvas, in case of completion update
|
||||
render_scroll_canvas(data);
|
||||
|
||||
data->scroll_area.curr_selection = 0;
|
||||
data->update_preview = true;
|
||||
}
|
||||
|
||||
#define FONT_SIZE 22
|
||||
#define TEXT_PADDING 3
|
||||
#define SCROLL_TOTAL_HEIGHT 800
|
||||
void init_level_select_scene(LevelSelectScene_t* scene)
|
||||
{
|
||||
init_scene(&scene->scene, &level_select_do_action, 0);
|
||||
scene->scene.reset_function = &reset_level_selection_scene;
|
||||
scene->data.preview = LoadRenderTexture(LEVEL_PREVIEW_SIZE, LEVEL_PREVIEW_SIZE);
|
||||
scene->data.update_preview = true;
|
||||
scene->scene.action_remap_function = level_select_action_remap_func;
|
||||
scene->scene.action_remap_function = &level_select_action_remap_func;
|
||||
add_scene_layer(
|
||||
&scene->scene, scene->scene.engine->intended_window_size.x,
|
||||
scene->scene.engine->intended_window_size.y,
|
||||
|
@ -283,30 +324,8 @@ void init_level_select_scene(LevelSelectScene_t* scene)
|
|||
if (menu_font != NULL) {
|
||||
scene->data.scroll_area.comp.font = *menu_font;
|
||||
}
|
||||
char buf[32];
|
||||
ScrollAreaRenderBegin(&scene->data.scroll_area);
|
||||
ClearBackground(BLANK);
|
||||
if (scene->data.level_pack != NULL)
|
||||
{
|
||||
vert_scrollarea_n_items(&scene->data.scroll_area, scene->data.level_pack->n_levels);
|
||||
for (unsigned int i = 0; i < scene->data.level_pack->n_levels; ++i)
|
||||
{
|
||||
vert_scrollarea_insert_item(&scene->data.scroll_area, scene->data.level_pack->levels[i].level_name, i);
|
||||
}
|
||||
for (unsigned int i = scene->data.level_pack->n_levels; i < scene->data.scroll_area.max_items; ++i)
|
||||
{
|
||||
vert_scrollarea_insert_item(&scene->data.scroll_area, "---", i);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
for (unsigned int i = 0; i < scene->data.scroll_area.max_items; ++i)
|
||||
{
|
||||
sprintf(buf, "Level %u", i);
|
||||
vert_scrollarea_insert_item(&scene->data.scroll_area, buf, i);
|
||||
}
|
||||
}
|
||||
ScrollAreaRenderEnd();
|
||||
|
||||
render_scroll_canvas(&scene->data);
|
||||
|
||||
sc_array_add(&scene->scene.systems, &level_preview_render_func);
|
||||
sc_array_add(&scene->scene.systems, &level_select_render_func);
|
||||
|
|
|
@ -53,7 +53,7 @@ static void exec_component_function(Scene_t* scene, int sel)
|
|||
switch(sel)
|
||||
{
|
||||
case 0:
|
||||
change_scene(scene->engine, LEVEL_SELECT_SCENE);
|
||||
change_scene_ext(scene->engine, LEVEL_SELECT_SCENE, true);
|
||||
break;
|
||||
case 1:
|
||||
change_scene_ext(scene->engine, OPTIONS_SCENE, true);
|
||||
|
|
|
@ -0,0 +1,47 @@
|
|||
#include "save_data.h"
|
||||
#include "constants.h"
|
||||
|
||||
// Bit flags for level completion.
|
||||
// Expect 30 levels.
|
||||
// Could use a 32bit integer though.
|
||||
// Using array to allow arbitrary length of flags.
|
||||
|
||||
#define NUMBER_OF_BYTES 4
|
||||
static uint8_t completion_flags[NUMBER_OF_BYTES] = {0};
|
||||
|
||||
int load_savedata(uint8_t* bytes, size_t len)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
int writeout_savedata(uint8_t* bytes, size_t len)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
bool is_level_completed(uint32_t level_num)
|
||||
{
|
||||
// 0-indexed
|
||||
|
||||
uint32_t byte_num = level_num >> 3;
|
||||
if (byte_num >= NUMBER_OF_BYTES) return false;
|
||||
|
||||
uint32_t bit_num = level_num % 8;
|
||||
return ((completion_flags[byte_num] >> bit_num) & 1) > 0;
|
||||
}
|
||||
|
||||
void set_level_completed(uint32_t level_num, bool complete)
|
||||
{
|
||||
uint32_t byte_num = level_num >> 3;
|
||||
if (byte_num >= NUMBER_OF_BYTES) return;
|
||||
|
||||
uint32_t bit_num = level_num % 8;
|
||||
if (complete)
|
||||
{
|
||||
completion_flags[byte_num] |= (1 <<bit_num);
|
||||
}
|
||||
else
|
||||
{
|
||||
completion_flags[byte_num] &= ~(1 << bit_num);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,24 @@
|
|||
#ifndef SAVEDATA_SCENES_H
|
||||
#define SAVEDATA_SCENES_H
|
||||
/**
|
||||
* These are data that should persist and accessible by all scenes.
|
||||
* It is expected to be modified over the course of the program lifetime by any scene.
|
||||
*
|
||||
* It is expected that only one save data is loaded and modified at any given time.
|
||||
* Only used to keep track of the completed levels.
|
||||
*
|
||||
* General engine data belongs in the engine layer.
|
||||
*/
|
||||
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
|
||||
int load_savedata(uint8_t* bytes, size_t len);
|
||||
int writeout_savedata(uint8_t* bytes, size_t len);
|
||||
|
||||
bool is_level_completed(uint32_t level_num);
|
||||
void set_level_completed(uint32_t level_num, bool complete);
|
||||
|
||||
#endif // SAVEDATA_SCENES_H
|
Loading…
Reference in New Issue