200 lines
6.4 KiB
Clojure
200 lines
6.4 KiB
Clojure
(ns tui.ansi-test
|
|
"Unit tests for ANSI escape codes and string utilities."
|
|
(:require [clojure.test :refer [deftest testing is]]
|
|
[clojure.string :as str]
|
|
[tui.ansi :as ansi]))
|
|
|
|
;; === Style Tests ===
|
|
|
|
(deftest style-foreground-test
|
|
(testing "applies foreground colors"
|
|
(let [result (ansi/style "text" :fg :red)]
|
|
(is (str/includes? result "31m"))
|
|
(is (str/includes? result "text"))
|
|
(is (str/ends-with? result ansi/reset))))
|
|
|
|
(testing "applies bright foreground colors"
|
|
(let [result (ansi/style "text" :fg :bright-red)]
|
|
(is (str/includes? result "91m"))))
|
|
|
|
(testing "applies gray/grey alias"
|
|
(let [gray (ansi/style "text" :fg :gray)
|
|
grey (ansi/style "text" :fg :grey)]
|
|
(is (= gray grey))
|
|
(is (str/includes? gray "90m")))))
|
|
|
|
(deftest style-background-test
|
|
(testing "applies background colors"
|
|
(let [result (ansi/style "text" :bg :blue)]
|
|
(is (str/includes? result "44m"))
|
|
(is (str/includes? result "text")))))
|
|
|
|
(deftest style-attributes-test
|
|
(testing "applies bold"
|
|
(let [result (ansi/style "text" :bold true)]
|
|
(is (str/includes? result "1m"))))
|
|
|
|
(testing "applies dim"
|
|
(let [result (ansi/style "text" :dim true)]
|
|
(is (str/includes? result "2m"))))
|
|
|
|
(testing "applies italic"
|
|
(let [result (ansi/style "text" :italic true)]
|
|
(is (str/includes? result "3m"))))
|
|
|
|
(testing "applies underline"
|
|
(let [result (ansi/style "text" :underline true)]
|
|
(is (str/includes? result "4m"))))
|
|
|
|
(testing "applies inverse"
|
|
(let [result (ansi/style "text" :inverse true)]
|
|
(is (str/includes? result "7m"))))
|
|
|
|
(testing "applies strikethrough"
|
|
(let [result (ansi/style "text" :strike true)]
|
|
(is (str/includes? result "9m")))))
|
|
|
|
(deftest style-combined-test
|
|
(testing "combines multiple styles"
|
|
(let [result (ansi/style "text" :fg :red :bold true :underline true)]
|
|
(is (str/includes? result "31")) ; Red
|
|
(is (str/includes? result "1")) ; Bold
|
|
(is (str/includes? result "4"))))) ; Underline
|
|
|
|
(deftest style-no-styles-test
|
|
(testing "returns plain text when no styles"
|
|
(is (= "text" (ansi/style "text")))))
|
|
|
|
;; === Color Helper Tests ===
|
|
|
|
(deftest fg-helper-test
|
|
(testing "fg helper applies foreground color"
|
|
(let [result (ansi/fg :green "text")]
|
|
(is (str/includes? result "32m"))
|
|
(is (str/includes? result "text")))))
|
|
|
|
(deftest bg-helper-test
|
|
(testing "bg helper applies background color"
|
|
(let [result (ansi/bg :yellow "text")]
|
|
(is (str/includes? result "43m"))
|
|
(is (str/includes? result "text")))))
|
|
|
|
;; === 256 Color Tests ===
|
|
|
|
(deftest fg-256-test
|
|
(testing "applies 256-color foreground"
|
|
(let [result (ansi/fg-256 196 "text")]
|
|
(is (str/includes? result "38;5;196m"))
|
|
(is (str/includes? result "text")))))
|
|
|
|
(deftest bg-256-test
|
|
(testing "applies 256-color background"
|
|
(let [result (ansi/bg-256 21 "text")]
|
|
(is (str/includes? result "48;5;21m"))
|
|
(is (str/includes? result "text")))))
|
|
|
|
;; === True Color Tests ===
|
|
|
|
(deftest fg-rgb-test
|
|
(testing "applies RGB foreground"
|
|
(let [result (ansi/fg-rgb 255 128 64 "text")]
|
|
(is (str/includes? result "38;2;255;128;64m"))
|
|
(is (str/includes? result "text")))))
|
|
|
|
(deftest bg-rgb-test
|
|
(testing "applies RGB background"
|
|
(let [result (ansi/bg-rgb 0 128 255 "text")]
|
|
(is (str/includes? result "48;2;0;128;255m"))
|
|
(is (str/includes? result "text")))))
|
|
|
|
;; === String Utility Tests ===
|
|
|
|
(deftest visible-length-test
|
|
(testing "returns length of plain text"
|
|
(is (= 5 (ansi/visible-length "hello")))
|
|
(is (= 0 (ansi/visible-length ""))))
|
|
|
|
(testing "excludes ANSI codes from length"
|
|
(let [styled (ansi/style "hello" :fg :red :bold true)]
|
|
(is (= 5 (ansi/visible-length styled)))))
|
|
|
|
(testing "handles multiple ANSI sequences"
|
|
(let [text (str (ansi/fg :red "red") (ansi/fg :blue "blue"))]
|
|
(is (= 7 (ansi/visible-length text))))))
|
|
|
|
(deftest pad-right-test
|
|
(testing "pads string to width"
|
|
(is (= "hi " (ansi/pad-right "hi" 5)))
|
|
(is (= "hello" (ansi/pad-right "hello" 5))))
|
|
|
|
(testing "does not truncate if longer"
|
|
(is (= "hello" (ansi/pad-right "hello" 3))))
|
|
|
|
(testing "handles styled text"
|
|
(let [styled (ansi/style "hi" :fg :red)
|
|
padded (ansi/pad-right styled 5)]
|
|
(is (= 5 (ansi/visible-length padded))))))
|
|
|
|
(deftest pad-left-test
|
|
(testing "pads string on left"
|
|
(is (= " hi" (ansi/pad-left "hi" 5)))
|
|
(is (= "hello" (ansi/pad-left "hello" 5))))
|
|
|
|
(testing "does not truncate if longer"
|
|
(is (= "hello" (ansi/pad-left "hello" 3)))))
|
|
|
|
(deftest pad-center-test
|
|
(testing "centers string"
|
|
(is (= " hi " (ansi/pad-center "hi" 5)))
|
|
(is (= " hi " (ansi/pad-center "hi" 6))))
|
|
|
|
(testing "handles odd padding"
|
|
(is (= " x " (ansi/pad-center "x" 3)))))
|
|
|
|
(deftest truncate-test
|
|
(testing "truncates long strings"
|
|
(is (= "hel\u2026" (ansi/truncate "hello" 4)))
|
|
(is (= "h\u2026" (ansi/truncate "hello" 2))))
|
|
|
|
(testing "does not truncate short strings"
|
|
(is (= "hi" (ansi/truncate "hi" 5)))
|
|
(is (= "hello" (ansi/truncate "hello" 5)))))
|
|
|
|
;; === Box Characters Tests ===
|
|
|
|
(deftest box-chars-test
|
|
(testing "all border styles have required characters"
|
|
(doseq [[style chars] ansi/box-chars]
|
|
(is (contains? chars :tl) (str style " missing :tl"))
|
|
(is (contains? chars :tr) (str style " missing :tr"))
|
|
(is (contains? chars :bl) (str style " missing :bl"))
|
|
(is (contains? chars :br) (str style " missing :br"))
|
|
(is (contains? chars :h) (str style " missing :h"))
|
|
(is (contains? chars :v) (str style " missing :v")))))
|
|
|
|
;; === Escape Sequence Constants Tests ===
|
|
|
|
(deftest escape-sequences-test
|
|
(testing "escape sequences are strings"
|
|
(is (string? ansi/clear-screen))
|
|
(is (string? ansi/clear-line))
|
|
(is (string? ansi/cursor-home))
|
|
(is (string? ansi/hide-cursor))
|
|
(is (string? ansi/show-cursor))
|
|
(is (string? ansi/enter-alt-screen))
|
|
(is (string? ansi/exit-alt-screen)))
|
|
|
|
(testing "escape sequences start with ESC"
|
|
(is (str/starts-with? ansi/clear-screen "\u001b"))
|
|
(is (str/starts-with? ansi/cursor-home "\u001b"))))
|
|
|
|
(deftest cursor-movement-test
|
|
(testing "cursor-to generates correct sequence"
|
|
(is (= "\u001b[5;10H" (ansi/cursor-to 5 10))))
|
|
|
|
(testing "cursor movement functions"
|
|
(is (= "\u001b[3A" (ansi/cursor-up 3)))
|
|
(is (= "\u001b[2B" (ansi/cursor-down 2)))
|
|
(is (= "\u001b[4C" (ansi/cursor-forward 4)))
|
|
(is (= "\u001b[1D" (ansi/cursor-back 1)))))
|