import random, strutils, terminal const BoardLength = 4 BoardSize = BoardLength * BoardLength Target = 2048 type Operation = enum opInvalid opUp opDown opLeft opRight opQuit opRestart Board = object len: Natural largestNumber: Natural score: Natural rows: array[BoardLength, array[BoardLength, Natural]] func handleKey(c: char): Operation = case c of 'w', 'W': opUp of 'a', 'A': opLeft of 's', 'S': opDown of 'd', 'D': opRight of 'q', 'Q': opQuit of 'r', 'R': opRestart else: opInvalid proc getKey(): Operation = var c = getch() if c == '\e': c = getch() if c == '[': case getch() of 'A': opUp of 'D': opLeft of 'B': opDown of 'C': opRight else: opInvalid else: handleKey c else: handleKey c proc spawnRandom(b: var Board) = if b.len < BoardSize: var x = rand 0..= Target echo board highscore = max(highscore, board.score) echo "Score = ", board.score, " Highscore = ", highscore if not gameover: echo "Press arrow keys or WASD to move, R to Restart, Q to Quit" elif board.largestNumber >= Target: echo "You win! Press R to Restart, Q to Quit" else: echo "Game over! Press R to Restart, Q to Quit" while true: let op = getKey() case op of opRestart: board = initBoard() break of opQuit: break gameLoop of opInvalid: continue elif gameover: continue else: if board.shift op: board.spawnRandom break for i in 1..BoardLength + 7: eraseLine() cursorUp()