чување 95c6889a695fa74daf5a7e006a82a38e8633679c
родитељ df36255cf6c3d9aa66e12cf3573d26179c23b94b
Аутор: Страхиња Радић <sr@strahinja.org>
Датум: Mon, 4 Aug 2025 20:24:21 +0200
Implement check for multiple crossed strings; code cleanup
Diffstat:
| M | TODO | | | 3 | --- |
| A | TODO.done | | | 5 | +++++ |
| M | linije.c | | | 452 | +++++++++++++++++++++++++++++++++++++++++++++++++------------------------------ |
измењених датотека: 3, додавања: 285(+), брисања: 175(-)
diff --git a/TODO b/TODO
@@ -3,9 +3,6 @@ TODO
[ ] Game over
-[ ] Handle cases with multiple strings popping when moving one ball (cross
- sections)
-
< > High score?
< > Menu?
diff --git a/TODO.done b/TODO.done
@@ -0,0 +1,5 @@
+Done or canceled todos
+======================
+
+[x] Handle cases with multiple strings popping when moving one ball (cross
+ sections)
diff --git a/linije.c b/linije.c
@@ -63,9 +63,7 @@ enum {
enum {
STATE_IDLE,
STATE_SELECTION,
- STATE_MOVING,
- STATE_FAILURE,
- STATE_SUCCESS
+ STATE_MOVING
};
const char* cell_names[] = {
@@ -88,9 +86,7 @@ const int check_five_deltas[][4] = {
const char* state_descriptions[] = {
"Idle",
"Selecting",
- "Moving",
- "Failed!",
- "Success!"
+ "Moving"
};
const char* help_text[] = {
@@ -124,51 +120,57 @@ struct AnimationState {
struct Cell {
int empty; /* logical variables */
+ int popping;
+ int path;
int starting;
int ending;
- int path;
SDL_FPoint coords;
int contents;
+ struct Cell* down;
struct Cell* left;
- struct Cell* up;
struct Cell* right;
- struct Cell* down;
- struct Cell* path_source; /* previous cell in shortest path */
- struct Cell* path_next; /* next cell in shortest path */
- int path_dist; /* length of shortest path so far */
+ struct Cell* up;
+ struct Cell* path_next; /* next cell in shortest path */
+ struct Cell* path_prev; /* previous cell in shortest path */
+ int path_dist; /* length of shortest path so far */
};
+/* clang-format off */
struct State {
- struct AnimationState animation;
- struct Cell* grid;
- int location_pointer;
- SDL_Point* location_stack;
- SDL_FPoint pointer;
- float cell_scale_factor;
- int display_width; /* Physical, detected */
- int display_height;
- int full_screen;
- int help_shown;
- int mode;
- struct Cell* path_start;
- struct Cell* path_end;
- int redraw;
- SDL_Renderer* renderer;
- int running;
- int screen_width; /* Logical */
- int screen_height;
- unsigned int score;
- SDL_FPoint selection_start, selection_end;
- SDL_Texture* sprites;
- SDL_Texture* ter12_texture;
- SDL_Texture* background;
- SDL_Window* window;
- float text_scale_factor;
+ struct AnimationState animation;
+ SDL_Texture* background;
+ struct Cell* grid;
+ float cell_scale_factor;
+ SDL_Point dialog_dims;
+ int dialog_shown;
+ const char** dialog_text;
+ int display_width; /* Physical, detected */
+ int display_height;
+ int full_screen;
+ int location_pointer;
+ SDL_Point* location_stack;
+ int mode;
+ SDL_FPoint mouse;
+ struct Cell* path_start;
+ struct Cell* path_end;
+ int redraw;
+ SDL_Renderer* renderer;
+ int running;
+ int screen_width; /* Logical */
+ int screen_height;
+ unsigned int score;
+ SDL_FPoint selection_start, selection_end;
+ SDL_Texture* sprites;
+ SDL_Texture* ter12_texture;
+ float text_scale_factor;
+ SDL_Window* window;
};
+/* clang-format on */
void assign_pointFF(const SDL_FPoint* from, SDL_FPoint* to);
void assign_pointIF(const SDL_Point* from, SDL_FPoint* to);
void assign_point_xyIF(const int x, const int y, SDL_FPoint* to);
+void assign_point_xyII(const int x, const int y, SDL_Point* to);
void calculate_delta(struct State* state);
void calculate_grid_origin(const struct State* state, float* sx, float* sy);
void calculate_display_size(struct State* state);
@@ -177,10 +179,11 @@ void cleanup(struct State* state);
void do_exit(const int code, struct State* state);
void draw(struct State* state);
void draw_background(struct State* state, SDL_FRect* bg_rect);
-void draw_help_dialog(struct State* state);
+void draw_dialog(struct State* state);
void draw_text(struct State* state, const int x, const int y,
const int font_width, const int font_height, SDL_Texture* font_tex,
const char* text, ...);
+void erase_cell(struct Cell* c);
void fill_triplet(struct State* state);
void find_shortest_path(struct Cell* c, struct Cell* source, const int dist);
void get_sprite_xy(const char cell, float* x, float* y);
@@ -192,14 +195,18 @@ void grid_coord_to_screen_coordF(const struct State* state, const float x,
float* to_y);
void handle_click(struct State* state);
void handle_event(struct State* state, SDL_Event* event);
-void init_cell(struct Cell* c, const SDL_FPoint* coords);
+void init_cell(struct Cell* c, const int full, const SDL_FPoint* coords);
void init_state(struct State* state);
int load_textures(struct State* state);
int location_pop(struct State* state, SDL_Point* location);
void location_push(struct State* state, const SDL_Point* location);
+void mark_five(struct State* state, SDL_FPoint* start, SDL_FPoint* end);
void mark_path(struct Cell* c);
void next_step(struct State* state);
int passable(const struct State* state, const int x, const int y);
+void pop_strings(struct State* state);
+void prepare_dialog(struct State* state, const int w, const int h,
+ const char** text, const int show);
void print_matrix(const struct Cell* M);
void print_path(struct Cell* c);
void reset(struct State* state);
@@ -237,42 +244,57 @@ assign_point_xyIF(const int x, const int y, SDL_FPoint* to)
}
void
+assign_point_xyII(const int x, const int y, SDL_Point* to)
+{
+ assert(to != NULL);
+ to->x = (float)x;
+ to->y = (float)y;
+}
+
+void
calculate_delta(struct State* state)
{
- struct AnimationState* animation;
+ SDL_FPoint* start = NULL;
+ SDL_FPoint* end = NULL;
+ SDL_FPoint* delta = NULL;
assert(state != NULL);
- animation = &state->animation;
- animation->delta.x
- = fabsf(animation->end.x - animation->start.x) / ANIM_STEPS;
- if (animation->end.x < animation->start.x)
- animation->delta.x *= -1;
- animation->delta.y
- = fabsf(animation->end.y - animation->start.y) / ANIM_STEPS;
- if (animation->end.y < animation->start.y)
- animation->delta.y *= -1;
+
+ start = &state->animation.start;
+ end = &state->animation.end;
+ delta = &state->animation.delta;
+
+ delta->x = fabsf(end->x - start->x) / ANIM_STEPS;
+ if (end->x < start->x)
+ delta->x *= -1;
+ delta->y = fabsf(end->y - start->y) / ANIM_STEPS;
+ if (end->y < start->y)
+ delta->y *= -1;
SDL_LogDebug(SDL_LOG_CATEGORY_APPLICATION,
- "calculate_delta: (%0.2f, %0.2f)", animation->delta.x,
- animation->delta.y);
+ "calculate_delta: (%0.2f, %0.2f)", delta->x, delta->y);
}
void
calculate_grid_origin(const struct State* state, float* sx, float* sy)
{
int cx, cy;
+ float csf;
assert((state != NULL) && (sx != NULL) && (sy != NULL));
- cx = state->screen_width / 2;
- cy = state->screen_height / 2;
- *sx = cx - (state->cell_scale_factor * GRID_WIDTH * CELL_SIZE) / 2;
- *sy = cy - (state->cell_scale_factor * GRID_HEIGHT * CELL_SIZE) / 2;
+ csf = state->cell_scale_factor;
+ cx = state->screen_width / 2;
+ cy = state->screen_height / 2;
+
+ *sx = cx - (csf * GRID_WIDTH * CELL_SIZE) / 2;
+ *sy = cy - (csf * GRID_HEIGHT * CELL_SIZE) / 2;
}
void
calculate_display_size(struct State* state)
{
assert(state != NULL);
+
if (!SDL_GetRenderOutputSize(state->renderer, &state->display_width,
&state->display_height))
{
@@ -288,10 +310,12 @@ calculate_display_size(struct State* state)
void
check_five(struct State* state, struct Cell* c)
{
- struct Cell* current = NULL;
SDL_FPoint start, end;
int x, y, len;
int i;
+ int found_string = 0;
+
+ assert((state != NULL) && (c != NULL));
i = 0;
check_five_loop:
@@ -336,45 +360,20 @@ check_five_loop:
}
if (len > MIN_POP_LEN)
{
- SDL_LogDebug(SDL_LOG_CATEGORY_APPLICATION,
- "check_five: String, from (%0.0f, %0.0f) to (%0.0f, "
- "%0.0f)",
- start.x, start.y, end.x, end.y);
-
- SDL_LogDebug(SDL_LOG_CATEGORY_APPLICATION,
- "for (%0.0f; y != %0.0f + %d; y += %d)",
- start.y, end.y, check_five_deltas[i][3],
- check_five_deltas[i][3]);
- SDL_LogDebug(SDL_LOG_CATEGORY_APPLICATION,
- "for (%0.0f; x != %0.0f + %d; x += %d)",
- start.x, end.x, check_five_deltas[i][2],
- check_five_deltas[i][2]);
- x = start.x;
+ /*x = start.x;
y = start.y;
do
{
- current = &state->grid[INDEX(x, y)];
- SDL_LogDebug(SDL_LOG_CATEGORY_APPLICATION,
- "Before erase: (%0.0f, %0.0f) [%d, %d] is %s",
- current->coords.x,
- current->coords.y,
- x, y,
- cell_names[current->contents]);
- current->contents = CELL_EMPTY;
- current->empty = 1;
- SDL_LogDebug(SDL_LOG_CATEGORY_APPLICATION,
- "After erase: (%0.0f, %0.0f) is %s",
- current->coords.x,
- current->coords.y,
- cell_names[current->contents]);
+ erase_cell(&state->grid[INDEX(x, y)]);
x += check_five_deltas[i][2];
y += check_five_deltas[i][3];
- }
- while (!((x == end.x + check_five_deltas[i][2])
- && (y == end.y + check_five_deltas[i][3])));
+ } while (!((x == end.x + check_five_deltas[i][2])
+ && (y == end.y + check_five_deltas[i][3])));*/
+ mark_five(state, &start, &end);
state->score += len * POP_STRING_CELL_VALUE;
- goto check_five_finish;
+ found_string = 1;
+ //goto check_five_finish;
}
else
{
@@ -385,9 +384,11 @@ check_five_loop:
if (i < sizeof(check_five_deltas) / sizeof(check_five_deltas[0]))
goto check_five_loop;
- fill_triplet(state);
+ if (found_string)
+ pop_strings(state);
+ else
+ fill_triplet(state);
-check_five_finish:
state->mode = STATE_IDLE;
}
@@ -512,8 +513,8 @@ draw(struct State* state)
"Score: %06u F1 = Help Status: %s", state->score,
state_descriptions[state->mode]);
- if (state->help_shown)
- draw_help_dialog(state);
+ if (state->dialog_shown)
+ draw_dialog(state);
/*draw_text(600, screen_height - text_scale_factor * TER12_HEIGHT,
TER12_WIDTH, TER12_HEIGHT, ter12_texture, "(%05.2f, %05.2f)",
@@ -608,18 +609,30 @@ draw_background(struct State* state, SDL_FRect* bg_rect)
SDL_SetRenderTarget(state->renderer, NULL);
}
+/* state is not const because of renderer, etc */
void
-draw_help_dialog(struct State* state)
+draw_dialog(struct State* state)
{
- const char** phelp_text = help_text;
- int sx = state->screen_width / 2 - HELP_DIALOG_WIDTH / 2;
- int sy = state->screen_height / 2 - HELP_DIALOG_HEIGHT / 2;
+ const char** ptext = NULL;
SDL_FRect dialog_rect;
+ float tsf;
+ int w, h;
+ int sx, sy;
+
+ assert(state != NULL);
+ assert(state->dialog_text != NULL);
+
+ ptext = state->dialog_text;
+ w = state->dialog_dims.x;
+ h = state->dialog_dims.y;
+ sx = state->screen_width / 2 - w / 2;
+ sy = state->screen_height / 2 - h / 2;
+ tsf = state->text_scale_factor;
dialog_rect.x = sx;
dialog_rect.y = sy;
- dialog_rect.w = HELP_DIALOG_WIDTH;
- dialog_rect.h = HELP_DIALOG_HEIGHT;
+ dialog_rect.w = w;
+ dialog_rect.h = h;
SDL_SetRenderDrawBlendMode(state->renderer, SDL_BLENDMODE_BLEND);
SDL_SetRenderDrawColor(state->renderer, 0, 0, 0, .75 * 255);
@@ -640,17 +653,15 @@ draw_help_dialog(struct State* state)
dialog_rect.h += 2;
SDL_RenderRect(state->renderer, &dialog_rect);
- while (*phelp_text)
+ while (*ptext)
{
- draw_text(state,
- sx + state->text_scale_factor * (2 * TER12_WIDTH),
+ draw_text(state, sx + tsf * (2 * TER12_WIDTH),
sy
- + (phelp_text - help_text + 1)
- * state->text_scale_factor
+ + (ptext - state->dialog_text + 1) * tsf
* (TER12_HEIGHT + 2),
TER12_WIDTH, TER12_HEIGHT, state->ter12_texture,
- *phelp_text);
- phelp_text++;
+ *ptext);
+ ptext++;
}
}
@@ -661,10 +672,11 @@ draw_text(struct State* state, const int x, const int y, const int font_width,
char buf[PRINT_BUFSIZE];
va_list args;
const char* pbuf = NULL;
- int xstart = 0;
- int ystart = 0;
SDL_FRect source_rect;
SDL_FRect dest_rect;
+ float tsf;
+ int xstart = 0;
+ int ystart = 0;
int index = 0;
int chars_per_row = 0;
char first_char = ' ';
@@ -675,6 +687,8 @@ draw_text(struct State* state, const int x, const int y, const int font_width,
assert(state->text_scale_factor != 0.0f);
assert(font_width != -1);
+ tsf = state->text_scale_factor;
+
va_start(args, text);
vsnprintf(buf, sizeof(buf), text, args);
va_end(args);
@@ -684,8 +698,8 @@ draw_text(struct State* state, const int x, const int y, const int font_width,
dest_rect.x = x;
dest_rect.y = y;
- dest_rect.w = state->text_scale_factor * font_width;
- dest_rect.h = state->text_scale_factor * font_height;
+ dest_rect.w = tsf * font_width;
+ dest_rect.h = tsf * font_height;
if (!SDL_GetTextureSize(font_tex, &tex_w, &tex_h))
{
@@ -697,7 +711,6 @@ draw_text(struct State* state, const int x, const int y, const int font_width,
chars_per_row = tex_w / (font_width + 1);
pbuf = buf;
- // SDL_SetRenderScale(renderer, scale_factor, scale_factor);
while (*pbuf)
{
if (*pbuf >= first_char && *pbuf <= last_char)
@@ -716,11 +729,18 @@ draw_text(struct State* state, const int x, const int y, const int font_width,
SDL_RenderTexture(state->renderer, font_tex, &source_rect,
&dest_rect);
- dest_rect.x += state->text_scale_factor * font_width;
+ dest_rect.x += tsf * font_width;
pbuf++;
}
- // SDL_SetRenderScale(renderer, 1.0f, 1.0f);
+}
+
+void
+erase_cell(struct Cell* c)
+{
+ assert(c != NULL);
+ c->contents = CELL_EMPTY;
+ c->empty = 1;
}
void
@@ -777,8 +797,8 @@ find_shortest_path(struct Cell* c, struct Cell* source, const int dist)
if (c->path_dist > dist)
{
- c->path_dist = dist;
- c->path_source = source;
+ c->path_dist = dist;
+ c->path_prev = source;
}
if (c->ending)
@@ -863,8 +883,8 @@ handle_click(struct State* state)
if (state->mode == STATE_IDLE)
{
calculate_grid_origin(state, &startx, &starty);
- screen_coord_to_grid_coord(state, state->pointer.x,
- state->pointer.y, startx, starty,
+ screen_coord_to_grid_coord(state, state->mouse.x,
+ state->mouse.y, startx, starty,
&state->selection_start.x, &state->selection_start.y);
state->animation.start.x = (int)state->selection_start.x;
state->animation.start.y = (int)state->selection_start.y;
@@ -890,9 +910,9 @@ handle_click(struct State* state)
state->path_start->starting = 1;
SDL_LogDebug(SDL_LOG_CATEGORY_APPLICATION,
"[origin = (%0.2f, %0.2f)] "
- "pointer = (%0.2f, %0.2f) => "
+ "mouse = (%0.2f, %0.2f) => "
"selected = (%0.2f, %0.2f)",
- startx, starty, state->pointer.x, state->pointer.y,
+ startx, starty, state->mouse.x, state->mouse.y,
state->selection_start.x, state->selection_start.y);
state->redraw = 1;
}
@@ -900,9 +920,9 @@ handle_click(struct State* state)
{
state->mode = STATE_MOVING;
calculate_grid_origin(state, &startx, &starty);
- screen_coord_to_grid_coord(state, state->pointer.x,
- state->pointer.y, startx, starty,
- &state->selection_end.x, &state->selection_end.y);
+ screen_coord_to_grid_coord(state, state->mouse.x,
+ state->mouse.y, startx, starty, &state->selection_end.x,
+ &state->selection_end.y);
state->path_end = &state->grid[INDEXFI(state->selection_end.x,
state->selection_end.y)];
@@ -911,9 +931,9 @@ handle_click(struct State* state)
SDL_LogDebug(SDL_LOG_CATEGORY_APPLICATION,
"[origin = (%0.2f, %0.2f)] "
- "pointer = (%0.2f, %0.2f) => "
+ "mouse = (%0.2f, %0.2f) => "
"selected_end = (%0.2f, %0.2f)",
- startx, starty, state->pointer.x, state->pointer.y,
+ startx, starty, state->mouse.x, state->mouse.y,
state->selection_end.x, state->selection_end.y);
SDL_LogDebug(SDL_LOG_CATEGORY_APPLICATION,
@@ -987,8 +1007,11 @@ handle_event(struct State* state, SDL_Event* event)
switch (event->key.key)
{
case SDLK_F1:
- state->help_shown = 1;
- state->redraw = 1;
+ prepare_dialog(state, HELP_DIALOG_WIDTH,
+ HELP_DIALOG_HEIGHT, help_text, 1);
+ SDL_LogDebug(SDL_LOG_CATEGORY_APPLICATION,
+ "Dialog shown: %s",
+ state->dialog_shown ? "YES" : "NO");
break;
case SDLK_RETURN:
if (!(event->key.mod & SDL_KMOD_ALT))
@@ -1001,8 +1024,10 @@ handle_event(struct State* state, SDL_Event* event)
state->full_screen);
break;
case SDLK_ESCAPE:
- state->help_shown = 0;
- state->redraw = 1;
+ state->dialog_shown = 0;
+ state->dialog_text = NULL;
+ assign_point_xyII(-1, -1, &state->dialog_dims);
+ state->redraw = 1;
break;
case SDLK_Q:
if (event->key.mod & SDL_KMOD_CTRL)
@@ -1017,9 +1042,9 @@ handle_event(struct State* state, SDL_Event* event)
handle_click(state);
break;
case SDL_EVENT_MOUSE_MOTION:
- state->pointer.x = event->motion.x;
- state->pointer.y = event->motion.y;
- state->redraw = 1;
+ state->mouse.x = event->motion.x;
+ state->mouse.y = event->motion.y;
+ state->redraw = 1;
break;
}
}
@@ -1042,48 +1067,60 @@ init_animation(struct AnimationState* animation)
}
void
-init_cell(struct Cell* c, const SDL_FPoint* coords)
+init_cell(struct Cell* c, const int full, const SDL_FPoint* coords)
{
- assert((c != NULL) && (coords != NULL));
+ assert(c != NULL);
c->empty = 1;
c->starting = 0;
c->ending = 0;
+ c->popping = 0;
c->path = 0;
- c->coords.x = coords->x;
- c->coords.y = coords->y;
- c->contents = CELL_EMPTY;
- c->left = c->up = c->right = c->down = NULL;
- c->path_source = NULL;
- c->path_dist = INT_MAX;
+ if (full)
+ {
+ assert(coords != NULL);
+ c->coords.x = coords->x;
+ c->coords.y = coords->y;
+ c->down = c->left = c->right = c->up = NULL;
+ }
+ c->contents = CELL_EMPTY;
+ c->path_next = NULL;
+ c->path_prev = NULL;
+ c->path_dist = INT_MAX;
}
void
init_state(struct State* state)
{
assert(state != NULL);
+
init_animation(&state->animation);
+ state->background = NULL;
state->grid = NULL;
- state->location_pointer = 0;
- state->location_stack = NULL;
state->cell_scale_factor = 2.0f;
- state->display_width = DEFAULT_WIDTH;
- state->display_height = DEFAULT_HEIGHT;
- state->full_screen = 1;
- state->help_shown = 0;
- state->path_start = NULL;
- state->path_end = NULL;
- state->redraw = 1;
- state->renderer = NULL;
- state->running = 1;
- state->screen_width = DEFAULT_WIDTH;
- state->screen_height = DEFAULT_HEIGHT;
- state->score = 0;
+ assign_point_xyII(-1, -1, &state->dialog_dims);
+ state->dialog_shown = 0;
+ state->dialog_text = NULL;
+ state->display_width = DEFAULT_WIDTH;
+ state->display_height = DEFAULT_HEIGHT;
+ state->full_screen = 1;
+ state->location_pointer = 0;
+ state->location_stack = NULL;
+ state->mode = STATE_IDLE;
+ assign_point_xyIF(0, 0, &state->mouse);
+ state->path_start = NULL;
+ state->path_end = NULL;
+ state->redraw = 1;
+ state->renderer = NULL;
+ state->running = 1;
+ state->screen_width = DEFAULT_WIDTH;
+ state->screen_height = DEFAULT_HEIGHT;
+ state->score = 0;
+ assign_point_xyIF(-1, -1, &state->selection_start);
+ assign_point_xyIF(-1, -1, &state->selection_end);
state->sprites = NULL;
- state->mode = STATE_IDLE;
state->ter12_texture = NULL;
- state->background = NULL;
- state->window = NULL;
state->text_scale_factor = 2.0f;
+ state->window = NULL;
}
int
@@ -1148,22 +1185,55 @@ location_push(struct State* state, const SDL_Point* location)
}
void
+mark_five(struct State* state, SDL_FPoint* start, SDL_FPoint* end)
+{
+ struct Cell* c = NULL;
+ float dx, dy, x, y;
+
+ assert((state != NULL) && (start != NULL) && (end != NULL));
+ assert(!((start->x == end->x) && (start->y == end->y)));
+
+ dx = end->x - start->x;
+ dy = end->y - start->y;
+ if (dx != 0.0f)
+ dx = dx / fabsf(dx);
+ if (dy != 0.0f)
+ dy = dy / fabsf(dy);
+ SDL_LogDebug(SDL_LOG_CATEGORY_APPLICATION,
+ "check_five: String[%d], from (%0.0f, %0.0f) to (%0.0f, "
+ "%0.0f)",
+ (int)floor(MAX(fabsf(end->x - start->x),
+ fabsf(end->y - start->y)))+1,
+ start->x, start->y, end->x, end->y);
+ x = start->x;
+ y = start->y;
+ do
+ {
+ c = &state->grid[INDEXFI(x, y)];
+ c->popping = 1;
+ x += dx;
+ y += dy;
+ }
+ while(!((x == end->x + dx) && (y == end->y + dy)));
+}
+
+void
mark_path(struct Cell* c)
{
if (!c)
return;
c->path = 1;
- if (c->path_source)
+ if (c->path_prev)
{
- c->path_source->path_next = c;
+ c->path_prev->path_next = c;
SDL_LogDebug(SDL_LOG_CATEGORY_APPLICATION,
"mark_path: Next of (%0.0f, %0.0f) is (%0.0f, %0.0f)",
- c->path_source->coords.x, c->path_source->coords.y,
- c->path_source->path_next->coords.x,
- c->path_source->path_next->coords.y);
+ c->path_prev->coords.x, c->path_prev->coords.y,
+ c->path_prev->path_next->coords.x,
+ c->path_prev->path_next->coords.y);
}
- mark_path(c->path_source);
+ mark_path(c->path_prev);
}
void
@@ -1182,6 +1252,38 @@ passable(const struct State* state, const int x, const int y)
}
void
+pop_strings(struct State* state)
+{
+ struct Cell* c = NULL;
+ int x, y;
+
+ assert(state != NULL);
+ for (y = 0; y < GRID_HEIGHT; y++)
+ for (x = 0; x < GRID_WIDTH; x++)
+ {
+ c = &state->grid[INDEX(x, y)];
+ if (c->popping)
+ {
+ erase_cell(c);
+ c->popping = 0;
+ }
+ }
+}
+
+void
+prepare_dialog(struct State* state, const int w, const int h, const char** text,
+ const int show)
+{
+ assert((state != NULL) && (text != NULL));
+
+ assign_point_xyII(w, h, &state->dialog_dims);
+ state->dialog_text = text;
+ state->dialog_shown = show;
+ if (show)
+ state->redraw = 1;
+}
+
+void
print_matrix(const struct Cell* M)
{
const struct Cell* c = NULL;
@@ -1224,9 +1326,15 @@ print_path(struct Cell* c)
void
reset(struct State* state)
{
+ struct Cell* c = NULL;
+
for (int y = 0; y < GRID_HEIGHT; y++)
for (int x = 0; x < GRID_WIDTH; x++)
- state->grid[INDEX(x, y)].contents = CELL_EMPTY;
+ {
+ c = &state->grid[INDEX(x, y)];
+ c->contents = CELL_EMPTY;
+ c->popping = 0;
+ }
state->mode = STATE_IDLE;
state->selection_start.x = -1;
state->selection_start.y = -1;
@@ -1248,13 +1356,13 @@ reset_path(struct Cell* grid)
for (y = 0; y < GRID_HEIGHT; y++)
for (x = 0; x < GRID_WIDTH; x++)
{
- c = &grid[INDEX(x, y)];
- c->path_source = NULL;
- c->path_next = NULL;
- c->path_dist = INT_MAX;
- c->starting = 0;
- c->ending = 0;
- c->path = 0;
+ c = &grid[INDEX(x, y)];
+ c->path_next = NULL;
+ c->path_prev = NULL;
+ c->path_dist = INT_MAX;
+ c->starting = 0;
+ c->ending = 0;
+ c->path = 0;
}
}
@@ -1489,7 +1597,7 @@ main(int argc, char** argv)
c = &state.grid[INDEX(x, y)];
coords.x = x;
coords.y = y;
- init_cell(c, &coords);
+ init_cell(c, 1, &coords);
if (x > 0)
c->left = &state.grid[INDEX(x - 1, y)];
if (y > 0)
@@ -1526,8 +1634,8 @@ main(int argc, char** argv)
state.animation.active = 0;
SDL_GetMouseState(&px, &py);
- state.pointer.x = px;
- state.pointer.y = py;
+ state.mouse.x = px;
+ state.mouse.y = py;
last_time = SDL_GetTicks();
clock_getcpuclockid(getpid(), &cid);