X-Git-Url: http://git.draconx.ca/gitweb/rrace.git/blobdiff_plain/2529a9651d160ab3a17118d778f5e5584d040765..0a46ad3167e6f87e254288080e3ce89402089afb:/src/game.c diff --git a/src/game.c b/src/game.c index bd1fef9..ca03830 100644 --- a/src/game.c +++ b/src/game.c @@ -1,8 +1,25 @@ /* + * Slide puzzle core game logic + * Copyright © 2022 Nick Bowler + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + * * The RNG implementation is adapted from xoshiro256** and splitmix64 * by David Blackman and Sebastiano Vigna, originally distributed under * the Creative Commons Zero public domain dedication. */ + #include #include #include @@ -136,17 +153,17 @@ void game_reset(struct board *board) uint_fast32_t position; position = board_position(x, y); - if (tiles[i] == TILE_EMPTY) { - board->game[0] = 0x1ffffff ^ position; - board->x = x; - board->y = y; - } else { + if (tiles[i] != TILE_EMPTY) { if (tiles[i] & 1) - board->game[1] |= position; + board->game[0] |= position; if (tiles[i] & 2) - board->game[2] |= position; + board->game[1] |= position; if (tiles[i] & 4) - board->game[3] |= position; + board->game[2] |= position; + } else { + board->game[3] = 0x1ffffff ^ position; + board->x = x; + board->y = y; } } } @@ -179,3 +196,29 @@ int game_do_move(struct board *board, int x, int y) board->y = y; return 0; } + +#define GOAL_MASK 0x739c0 + +int game_check_goal(struct board *board) +{ + int i, ret = 1; + + for (i = 0; i < 3; i++) + ret &= ((board->game[i] & GOAL_MASK) >> 6) == board->goal[i]; + return ret; +} + +void game_finish(struct board *board) +{ + int i; + + for (i = 0; i < 4; i++) { + board->game[i] &= GOAL_MASK; + } + + /* + * Setting both x and y hole location to a bogus value will effectively + * disable the game since there will be no valid moves. + */ + board->x = board->y = -1; +}