Files
cl-tty/src/components/box.lisp
Hermes b0e5c18257 v0.3.0: Rendering pipeline — render dispatch, tree walk, dirty propagation
- render generic function dispatches per component type
- render-screen entry point with sync wrapper
- render-node walks tree, computes layout, calls render
- component-layout-node generic (box/text methods)
- component-children/component-parent generics
- propagate-dirty marks component + ancestors dirty
- box and text now inherit from dirty-mixin
- 6 new tests: render dispatch, layout-node accessor, children,
  dirty propagation, available-width defaults
- 42 component tests, 100% GREEN
2026-05-11 15:12:38 +00:00

55 lines
2.0 KiB
Common Lisp

(in-package :cl-tui.box)
(defclass box (dirty-mixin)
((layout-node :initform (make-layout-node) :accessor box-layout-node
:initarg :layout-node)
(border-style :initform :single :initarg :border-style
:accessor box-border-style)
(title :initform nil :initarg :title :accessor box-title)
(title-align :initform :left :initarg :title-align
:accessor box-title-align)
(fg :initform nil :initarg :fg :accessor box-fg)
(bg :initform nil :initarg :bg :accessor box-bg)))
(defun make-box (&key (border-style :single) title
(title-align :left) fg bg
width height)
(make-instance 'box
:border-style border-style
:title title
:title-align title-align
:fg fg
:bg bg
:layout-node (make-layout-node
:width width
:height height
:direction :column)))
(defun render-box (box backend)
"Render BOX at its computed layout position using BACKEND."
(let ((ln (box-layout-node box))
(bs (box-border-style box))
(title (box-title box))
(fg (box-fg box))
(bg (box-bg box)))
(let ((x (layout-node-x ln))
(y (layout-node-y ln))
(w (layout-node-width ln))
(h (layout-node-height ln)))
(when (or (zerop w) (zerop h) (< w 2) (< h 2))
(return-from render-box (values)))
(when bg
(draw-rect backend x y w h :bg bg))
(when bs
(draw-border backend x y w h :style bs :fg fg :bg bg))
(when title
(let* ((content-w (- w 4))
(tx (+ x 2))
(ty (+ y (if bs 1 0)))
(ta (box-title-align box))
(display (subseq title 0 (min (length title) content-w))))
(case ta
(:center (draw-text backend (+ x (ceiling (- w (length display)) 2)) ty display fg bg))
(:right (draw-text backend (+ x (- w (length display) 2)) ty display fg bg))
(t (draw-text backend tx ty display fg bg))))))))