diff options
author | Tom Smeding <tom.smeding@gmail.com> | 2019-02-13 23:32:08 +0100 |
---|---|---|
committer | Tom Smeding <tom.smeding@gmail.com> | 2019-02-13 23:32:08 +0100 |
commit | bc598375da7b9a20a35e958afb61dcd690d3d7b7 (patch) | |
tree | 764398251e30ae68920e53aa256d7e30b4cf55a0 /ui.cpp | |
parent | 6175cb1c53772cc92d91a39a254c38bdf8f64905 (diff) |
Play interactively against AI
Diffstat (limited to 'ui.cpp')
-rw-r--r-- | ui.cpp | 109 |
1 files changed, 109 insertions, 0 deletions
@@ -0,0 +1,109 @@ +#include <sstream> +#include <vector> +#include "ui.h" +#include "termio/termio.h" + +using namespace std; + + +static void cursorMove(int dx, int dy) { + if (dx < 0) cout << "\x1B[" << -dx << "D"; + if (dx > 0) cout << "\x1B[" << dx << "C"; + if (dy < 0) cout << "\x1B[" << -dy << "A"; + if (dy > 0) cout << "\x1B[" << dy << "B"; + cout << flush; +} + +int UI::getMove(const Board &bd) { + Bounds bounds = bd.computeBounds(); + const int l = bounds.left; + const int t = bounds.top; + const int w = bounds.right - bounds.left + 1; + const int h = bounds.bottom - bounds.top + 1; + + const auto toIdx = [l, t](int x, int y) { + return BSZ * (t + y) + l + x; + }; + + // -1: edge, 0: open, 1...: stones + vector<vector<int>> cells(h); + for (int y = 0; y < h; y++) { + cells[y].resize(w); + for (int x = 0; x < w; x++) { + int idx = toIdx(x, y); + cells[y][x] = bd[idx]; + if (cells[y][x] == 0 && bd.checkEdge(idx)) { + cells[y][x] = -1; + } + } + } + + for (int y = 0; y < h; y++) { + if (y != 0) cout << endl; + for (int x = 0; x < w; x++) { + if (x != 0) cout << ' '; + if (cells[y][x] == -1) cout << EDGE_STR; + else if (cells[y][x] == 0) cout << OPEN_STR; + else cout << Stone(cells[y][x]); + } + } + + cout << flush; + + cursorMove(-2 * w - 1, -h + 1); + int curx = 0, cury = 0; + const auto cursorXY = [&curx, &cury](int x, int y) { + cursorMove(2 * (x - curx), y - cury); + curx = x; cury = y; + }; + const auto cursorDXDY = [w, h, &curx, &cury, &cursorXY](int dx, int dy) { + int newx = curx + dx, newy = cury + dy; + newx = max(0, min(w - 1, newx)); + newy = max(0, min(h - 1, newy)); + cursorXY(newx, newy); + }; + + bool quit = false; + + initkeyboard(false); + + while (true) { + int key = tgetkey(); + bool done = false; + switch (key) { + case KEY_LEFT: cursorDXDY(-1, 0); break; + case KEY_RIGHT: cursorDXDY(1, 0); break; + case KEY_UP: cursorDXDY(0, -1); break; + case KEY_DOWN: cursorDXDY(0, 1); break; + + case KEY_LF: + case KEY_CR: + if (cells[cury][curx] == -1) done = true; + else bel(); + break; + + case 'q': + quit = true; + done = true; + break; + + default: + bel(); + break; + } + if (done) break; + } + + endkeyboard(); + + int retidx = toIdx(curx, cury); + + cursorXY(0, h - 1); + cout << endl << endl; + + if (quit) { + exit(0); + } + + return retidx; +} |