aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRatakor <ratakor@disroot.org>2023-08-26 01:54:36 -0400
committerRatakor <ratakor@disroot.org>2023-08-26 11:08:44 -0400
commitd6291ee61713703ee64cffefd5668384c6d773cd (patch)
treee5b8cb23804a42a1fa64a00fe72ebfd696b5e1b3
parentacd76931e0e7924e9bf2add0af38cb3658624fc5 (diff)
Victory message bug fix + remove deprecated func
Fix victory message being shown after quit then relaunch a game with 2048 and when getting 2048 after launching a game that had cells with 4096 or more but not 2048. Remove deprecated readUntilDelimiter function call. Rename global variables with clearer names.
-rw-r--r--src/Board.zig66
-rw-r--r--src/main.zig12
-rw-r--r--src/term.zig4
3 files changed, 46 insertions, 36 deletions
diff --git a/src/Board.zig b/src/Board.zig
index 9e003bd..43b95fa 100644
--- a/src/Board.zig
+++ b/src/Board.zig
@@ -68,7 +68,6 @@ pub fn init(size: usize) !*Board {
board.highscore = 0;
board.score = 0;
board.turns = 0;
- board.win = false;
board.prev = try allocator.create(Board);
board.tmp = try allocator.create(Board);
board.prev.cells = try createBoard(size);
@@ -77,6 +76,7 @@ pub fn init(size: usize) !*Board {
try board.addRandom();
try board.addRandom();
}
+ board.win = gameWon(board.cells);
boardCopy(board.prev, board);
return board;
}
@@ -99,6 +99,14 @@ pub fn reset(self: *Board) void {
self.win = false;
}
+fn readNextVal(comptime T: type, reader: anytype, fixed_buffer_stream: anytype) !T {
+ var fbs = fixed_buffer_stream;
+ try reader.streamUntilDelimiter(fbs.writer(), '\n', fbs.buffer.len);
+ const output = fbs.getWritten();
+ fbs.reset();
+ return try fmt.parseInt(T, output, 10);
+}
+
fn load(self: *Board) !bool {
var buf: [4096]u8 = undefined;
var path: []u8 = undefined;
@@ -120,20 +128,20 @@ fn load(self: *Board) !bool {
defer f.close();
errdefer cwd.deleteFile(self.savefile) catch {};
- var buf_reader = io.bufferedReader(f.reader());
- const reader = buf_reader.reader();
+ var br = io.bufferedReader(f.reader());
+ const br_reader = br.reader();
+
var nbuf: [32]u8 = undefined;
- const highscore = try reader.readUntilDelimiter(nbuf[0..], '\n');
- self.highscore = try fmt.parseInt(u64, highscore, 10);
- const score = try reader.readUntilDelimiter(nbuf[0..], '\n');
- self.score = try fmt.parseInt(u64, score, 10);
- const turns = try reader.readUntilDelimiter(nbuf[0..], '\n');
- self.turns = try fmt.parseInt(usize, turns, 10);
+ var fbs = io.fixedBufferStream(&nbuf);
+ self.highscore = try readNextVal(u64, br_reader, fbs);
+ self.score = try readNextVal(u64, br_reader, fbs);
+ self.turns = try readNextVal(usize, br_reader, fbs);
+
var i: usize = 0;
while (i < self.size) : (i += 1) {
var j: usize = 0;
while (j < self.size) : (j += 1) {
- self.cells[i][j] = try reader.readByte();
+ self.cells[i][j] = try br_reader.readByte();
}
}
@@ -150,19 +158,19 @@ pub fn save(self: *Board) !void {
defer f.close();
errdefer cwd.deleteFile(self.savefile) catch {};
- var buf_writer = io.bufferedWriter(f.writer());
- const fwriter = buf_writer.writer();
- try fwriter.print("{d}\n{d}\n{d}\n", .{
+ var bw = io.bufferedWriter(f.writer());
+ const bw_writer = bw.writer();
+ try bw_writer.print("{d}\n{d}\n{d}\n", .{
self.highscore,
self.score,
self.turns,
});
for (self.cells) |row| {
for (row) |cell| {
- try fwriter.writeByte(cell);
+ try bw_writer.writeByte(cell);
}
}
- try buf_writer.flush();
+ try bw.flush();
}
fn findTarget(row: []u8, x: u8, stop: u8) u8 {
@@ -228,7 +236,7 @@ fn slide(self: *Board) bool {
row[t] = row[x];
} else if (row[t] == row[x]) {
row[t] += 1;
- self.score += @as(u32, 1) << @intCast(row[t]);
+ self.score += @as(u64, 1) << @intCast(row[t]);
stop = t + 1;
}
row[x] = 0;
@@ -289,10 +297,10 @@ pub fn undo(self: *Board) void {
boardCopy(self, self.prev);
}
-fn hasValue(board: [][]u8, comptime val: u8) bool {
+fn gameWon(board: [][]u8) bool {
for (board) |row| {
for (row) |cell| {
- if (cell == val)
+ if (cell >= 11)
return true;
}
}
@@ -312,20 +320,22 @@ fn findPairOneWay(board: [][]u8) bool {
}
pub fn gameOver(self: *Board) bool {
- if (hasValue(self.cells, 0))
- return false;
+ for (self.cells) |row| {
+ for (row) |cell| {
+ if (cell == 0)
+ return false; // has empty cells
+ }
+ }
if (findPairOneWay(self.cells))
return false;
rotateRight(self.cells);
defer rotateLeft(self.cells);
- if (findPairOneWay(self.cells))
- return false;
- return true;
+ return !findPairOneWay(self.cells);
}
fn setColors(cell: u8) !void {
try term.setFg(term.Color.black);
- const real = @as(u32, 1) << @intCast(cell);
+ const real = @as(u64, 1) << @intCast(cell);
switch (real) {
2 => try term.setBg(term.Color.red),
4 => try term.setBg(term.Color.green),
@@ -405,7 +415,7 @@ pub fn draw(self: *Board) !void {
if (cell == 0) {
try writer.writeAll(" ยท ");
} else {
- const real = @as(u32, 1) << @intCast(cell);
+ const real = @as(u64, 1) << @intCast(cell);
const digits = countDigits(real);
// TODO kinda unsafe negative
var n = CELL_SIZE - digits;
@@ -427,16 +437,16 @@ pub fn draw(self: *Board) !void {
try term.resetColor();
try writer.writeAll("\n");
}
- if (!self.win and hasValue(self.cells, 11)) {
+ if (!self.win and gameWon(self.cells)) {
self.win = true;
try print(self, "VICTORY!");
- } else if (gameOver(self)) {
+ } else if (self.gameOver()) {
try print(self, "GAME OVER");
} else {
try writer.writeAll("\n");
}
try term.cursorUp();
- try main.buf_writer.flush();
+ try main.buffered_writer.flush();
}
test "rotation" {
diff --git a/src/main.zig b/src/main.zig
index 942f73d..6a02d08 100644
--- a/src/main.zig
+++ b/src/main.zig
@@ -4,10 +4,10 @@ const args = @import("args.zig");
const Board = @import("Board.zig");
const term = @import("term.zig");
-pub var buf_writer = std.io.bufferedWriter(std.io.getStdOut().writer());
-pub const writer = buf_writer.writer();
-var buffer: [std.mem.page_size]u8 = undefined;
-var fba = std.heap.FixedBufferAllocator.init(&buffer);
+pub var buffered_writer = std.io.bufferedWriter(std.io.getStdOut().writer());
+pub const writer = buffered_writer.writer();
+var alloc_buffer: [std.mem.page_size]u8 = undefined;
+var fba = std.heap.FixedBufferAllocator.init(&alloc_buffer);
pub const allocator = fba.allocator();
var board: *Board = undefined;
@@ -45,7 +45,7 @@ pub fn main() !void {
'd', 'l', 67 => success = board.moveRight(),
'q' => {
try board.print("QUIT? (y/n)");
- try buf_writer.flush();
+ try buffered_writer.flush();
if (try reader.readByte() == 'y') {
break;
}
@@ -53,7 +53,7 @@ pub fn main() !void {
},
'r' => {
try board.print("RESTART? (y/n)");
- try buf_writer.flush();
+ try buffered_writer.flush();
if (try reader.readByte() == 'y') {
board.reset();
try board.addRandom();
diff --git a/src/term.zig b/src/term.zig
index 49b8f7e..f95c8f2 100644
--- a/src/term.zig
+++ b/src/term.zig
@@ -52,7 +52,7 @@ pub fn init() !void {
try enterAlt();
try clear();
try resetColor();
- try main.buf_writer.flush();
+ try main.buffered_writer.flush();
}
pub fn deinit() !void {
@@ -62,7 +62,7 @@ pub fn deinit() !void {
try leaveAlt();
try showCursor();
try resetColor();
- try main.buf_writer.flush();
+ try main.buffered_writer.flush();
}
pub inline fn clear() !void {