Wire the renderer registry: SVG treatment returns a region click-map

cg-renderer gains a regions slot; the text/svg treatments get real
draw/hit methods; cg-regions-hit + cg-render-apply complete the loop.
Prototype on solitaire: cg-sol--svg returns (image . regions), redisplay
goes through cg-render-game, and [mouse-1] selects-and-acts by reusing the
keyboard pick-up/drop. Adds cgt-keystone-regions; suite 110/110.
This commit is contained in:
Corwin Brust 2026-06-25 09:10:42 -05:00
parent 4dc839e719
commit 287700ddca
4 changed files with 108 additions and 13 deletions

View file

@ -94,7 +94,10 @@ and SPC as an action key. Takes effect the next time a game starts."
(defclass cg-renderer ()
((name :initarg :name :initform 'text :type symbol
:documentation "Symbol naming this treatment."))
:documentation "Symbol naming this treatment.")
(regions :initarg :regions :initform nil
:documentation "Click map from the last draw: list of (RECT . ACTION),
RECT being (X Y W H) in unscaled image pixels."))
"Abstract base class for a display treatment (a \"skin\")."
:abstract t)
@ -114,6 +117,20 @@ Return non-nil when the click was handled.")
"Default method: treat the click as unhandled."
nil)
(defun cg-regions-hit (regions px py)
"Return the ACTION of the first region in REGIONS containing PX, PY.
Each region is (RECT . ACTION) with RECT (X Y W H) in image pixels."
(cl-loop for (rect . action) in regions
for (x y w h) = rect
when (and (>= px x) (< px (+ x w)) (>= py y) (< py (+ y h)))
return action))
(cl-defgeneric cg-render-apply (game action)
"Perform ACTION (returned by a renderer hit) on GAME.
The default does nothing; games specialise this to make clicks act."
(ignore game action)
nil)
(defvar cg-renderers nil
"Alist mapping a treatment name (a symbol) to a `cg-renderer' subclass.
Populate it with `cg-register-renderer' and look entries up with