diff --git a/.Jules/palette.md b/.Jules/palette.md index c4e3778..059866f 100644 --- a/.Jules/palette.md +++ b/.Jules/palette.md @@ -25,3 +25,7 @@ ## 2026-03-02 - Hiding the Cursor in CLI Games **Learning:** In terminal applications that require rapid visual updates or where user input doesn't involve typing text, an actively blinking cursor can be a visual distraction. Hiding it during interaction (`\033[?25l`) and rigorously ensuring it is restored (`\033[?25h`) on exit—including signal interrupts—significantly improves the aesthetic and focus. **Action:** Always hide the cursor for interactive CLI games and explicitly restore it across all exit paths, including async-signal-safe signal handlers. + +## 2026-05-24 - Preventing Trailing Artifacts in CLI Applications +**Learning:** When updating dynamic terminal lines via '\r', relying on hardcoded padding spaces to clear previous text is fragile and can leave trailing artifacts if the new text is significantly shorter than the old text. +**Action:** Always use the ANSI escape sequence '\033[K' (Erase in Line) immediately after the carriage return ('\r\033[K') to reliably clear the line before writing new content. diff --git a/.gitignore b/.gitignore index eb2c19a..d07c78a 100644 --- a/.gitignore +++ b/.gitignore @@ -44,3 +44,4 @@ highscore.txt # Persistent data highscore.txt +venv/ diff --git a/src/main.cpp b/src/main.cpp index e72f1da..0231ec5 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -94,7 +94,7 @@ int main() { } for (int i = 3; i > 0; --i) { - std::cout << "\rStarting in " << i << "... " << std::flush; + std::cout << "\r\033[KStarting in " << i << "... " << std::flush; auto start_wait = std::chrono::steady_clock::now(); while (std::chrono::duration_cast(std::chrono::steady_clock::now() - start_wait).count() < 1000) { int elapsed = std::chrono::duration_cast(std::chrono::steady_clock::now() - start_wait).count(); @@ -108,7 +108,7 @@ int main() { } } } - std::cout << "\rGO! \n" << std::flush; + std::cout << "\r\033[KGO!\n" << std::flush; std::this_thread::sleep_for(std::chrono::milliseconds(200)); tcflush(STDIN_FILENO, TCIFLUSH); @@ -137,10 +137,10 @@ int main() { } if (updateUI) { - std::cout << "\r" << CLR_SCORE << "Score: " << score << CLR_RESET << " " + std::cout << "\r\033[K" << CLR_SCORE << "Score: " << score << CLR_RESET << " " << (hardMode ? CLR_HARD "[HARD MODE]" : CLR_NORM "[NORMAL MODE]") << (score > initialHighscore && initialHighscore > 0 ? " NEW BEST! 🥳" : "") - << " " << std::flush; + << std::flush; updateUI = false; } }