X-Git-Url: https://plomlompom.com/repos/test.html?a=blobdiff_plain;f=roguelike.c;h=cba46ad44675453f749cf51d4a5f6acad68405fe;hb=6977fdf9517c4d4c46673ac047fb1dd9d6130556;hp=532ae70ec08993b5b8666773e3f725f10a3e1614;hpb=cff3e45e2913b44b88bb75ed10a4931a224a943e;p=plomrogue
diff --git a/roguelike.c b/roguelike.c
index 532ae70..cba46ad 100644
--- a/roguelike.c
+++ b/roguelike.c
@@ -1,12 +1,50 @@
#include
+#include
#include
#include
#include
+#include
+#include
#include "windows.h"
#include "draw_wins.h"
#include "roguelike.h"
#include "keybindings.h"
+uint16_t rrand(char use_seed, uint32_t new_seed) {
+// Pseudo-random number generator (LGC algorithm). Use instead of rand() to ensure portable predictability.
+ static uint32_t seed;
+ if (0 != use_seed)
+ seed = new_seed;
+ seed = ((seed * 1103515245) + 12345) % 2147483648; // Values as recommended by POSIX.1-2001 (see rand(3)).
+ return (seed / 65536); } // Ignore least significant 16 bits (they are less random).
+
+uint32_t load_seed() {
+// Load seed integer from seed file.
+ uint32_t seed;
+ const uint16_t nchar = UCHAR_MAX + 1;
+ FILE * file = fopen("seed", "r");
+ unsigned char a = fgetc(file);
+ unsigned char b = fgetc(file);
+ unsigned char c = fgetc(file);
+ unsigned char d = fgetc(file);
+ seed = (a * nchar * nchar * nchar) + (b * nchar * nchar) + (c * nchar) + d;
+ fclose(file);
+ return seed; }
+
+void save_seed(uint32_t seed) {
+// Save seed integer to seed file.
+ const uint16_t nchar = UCHAR_MAX + 1;
+ unsigned char a = seed / (nchar * nchar * nchar);
+ unsigned char b = (seed - (a * nchar * nchar * nchar)) / (nchar * nchar);
+ unsigned char c = (seed - ((a * nchar * nchar * nchar) + (b * nchar * nchar))) / nchar;
+ unsigned char d = seed % nchar;
+ FILE * file = fopen("seed", "w");
+ fputc(a, file);
+ fputc(b, file);
+ fputc(c, file);
+ fputc(d, file);
+ fclose(file); }
+
void toggle_window (struct WinMeta * win_meta, struct Win * win) {
// Toggle display of window win.
if (0 != win->curses)
@@ -29,11 +67,11 @@ void growshrink_active_window (struct WinMeta * win_meta, char change) {
width++;
resize_active_window (win_meta, height, width); } }
-struct Map init_map () {
+struct Map init_map (uint32_t seed) {
// Initialize map with some experimental start values.
struct Map map;
- map.width = 96;
- map.height = 32;
+ map.width = 64;
+ map.height = 64;
map.offset_x = 0;
map.offset_y = 0;
map.cells = malloc(map.width * map.height);
@@ -42,7 +80,7 @@ struct Map init_map () {
for (y = 0; y < map.height; y++)
for (x = 0; x < map.width; x++) {
terrain = '.';
- ran = rand();
+ ran = rrand(0, 0);
if ( 0 == ran % ((x*x) / 3 + 1)
|| 0 == ran % ((y*y) / 3 + 1)
|| 0 == ran % ((map.width - x - 1) * (map.width - x - 1) / 3 + 1)
@@ -65,9 +103,9 @@ void map_scroll (struct Map * map, char dir) {
void next_turn (struct World * world) {
// Increment turn and move enemy.
world->turn++;
- char d = rand() % 5;
- char ty = world->monster->y;
- char tx = world->monster->x;
+ char d = rrand(0, 0) % 5;
+ uint16_t ty = world->monster->y;
+ uint16_t tx = world->monster->x;
if (1 == d)
ty++;
else if (2 == d)
@@ -107,8 +145,8 @@ void move_player (struct World * world, char d) {
static char prev = 0;
char success = 0;
char * dir;
- char ty = world->player->y;
- char tx = world->player->x;
+ uint16_t ty = world->player->y;
+ uint16_t tx = world->player->x;
if ('s' == d) {
dir = "south";
ty++; }
@@ -143,26 +181,33 @@ void move_player (struct World * world, char d) {
prev = success * d;
next_turn (world); }
-void player_wait(struct World * world) {
+void player_wait (struct World * world) {
// Make player wait one turn.
next_turn (world);
update_log (world, "\nYou wait."); }
-int main () {
+int main (int argc, char *argv[]) {
+ uint32_t seed;
+ if (0 == access("seed", F_OK))
+ seed = load_seed();
+ else
+ seed = time(NULL);
+ rrand(1, seed);
+
struct World world;
init_keybindings(&world);
world.turn = 0;
world.log = calloc(1, sizeof(char));
update_log (&world, "Start!");
- struct Map map = init_map();
+ struct Map map = init_map(seed);
world.map = ↦
struct Player player;
- player.y = 16;
- player.x = 16;
+ player.y = 8;
+ player.x = 8;
world.player = &player;
struct Monster monster;
- monster.y = 16;
- monster.x = 80;
+ monster.y = 55;
+ monster.x = 55;
world.monster = &monster;
WINDOW * screen = initscr();
@@ -218,6 +263,8 @@ int main () {
keyswin_move_selection (&world, 'd');
else if (key == get_action_key(world.keybindings, "keys mod"))
keyswin_mod_key (&world, &win_meta);
+ else if (key == get_action_key(world.keybindings, "save seed"))
+ save_seed(seed);
else if (key == get_action_key(world.keybindings, "map up"))
map_scroll (&map, 'n');
else if (key == get_action_key(world.keybindings, "map down"))