Phase 1 Step 1 of the architecture roadmap. The old cssx.sx (cssx-resolve, cssx-process-token, cssx-template, old tw function) is superseded by the ~tw component system in tw.sx. - Delete shared/sx/templates/cssx.sx - Remove cssx.sx from all load lists (sx_server.ml, run_tests.ml, mcp_tree.ml, compile-modules.js, bundle.sh, sx-build-all.sh) - Replace (tw "tokens") inline style calls with (~tw :tokens "tokens") in layouts.sx and not-found.sx - Remove _css-hash / init-css-tracking / SX-Css header plumbing (dead code — ~tw/flush + flush-collected-styles handle CSS now) - Remove sx-css-classes param and meta tag from shell template - Update stale data-cssx references to data-sx-css in tests Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
191 lines
5.8 KiB
Plaintext
191 lines
5.8 KiB
Plaintext
(defisland
|
|
~layouts/header
|
|
(&key path)
|
|
(let
|
|
((families (list "violet" "rose" "blue" "emerald" "amber" "cyan" "red" "teal" "pink" "indigo"))
|
|
(store
|
|
(if (client?) (def-store "header-color" (fn () {:idx (signal 0) :shade (signal 500)})) nil))
|
|
(idx (if store (get store "idx") (signal 0)))
|
|
(shade (if store (get store "shade") (signal 500)))
|
|
(current-family
|
|
(computed (fn () (nth families (mod (deref idx) (len families)))))))
|
|
(div
|
|
(~tw :tokens "block max-w-3xl mx-auto px-4 pt-8 pb-4 text-center")
|
|
(a
|
|
:href "/sx/"
|
|
:sx-get "/sx/"
|
|
:sx-target "#sx-content"
|
|
:sx-select "#sx-content"
|
|
:sx-swap "innerHTML"
|
|
:sx-push-url "true"
|
|
(~tw :tokens "block no-underline")
|
|
(lake
|
|
:id "logo"
|
|
(span
|
|
(~tw
|
|
:tokens "block mb-2 text-violet-699 text-4xl font-bold font-mono")
|
|
"(<sx>)")))
|
|
(p
|
|
(~tw :tokens "mb-1 text-stone-500 text-lg")
|
|
"The framework-free "
|
|
(span
|
|
(~tw :tokens "font-bold")
|
|
:style (str
|
|
"color:"
|
|
(colour (deref current-family) (deref shade))
|
|
";"
|
|
"cursor:pointer;transition:color 0.3s,font-weight 0.3s;")
|
|
:on-click (fn
|
|
(e)
|
|
(batch
|
|
(fn
|
|
()
|
|
(swap! idx inc)
|
|
(reset! shade (+ 400 (* (mod (* (deref idx) 137) 5) 50))))))
|
|
"reactive")
|
|
" hypermedium")
|
|
(lake
|
|
:id "copyright"
|
|
(p
|
|
(~tw :tokens "text-stone-400 text-xs")
|
|
"© Giles Bradshaw 2026"
|
|
(when
|
|
path
|
|
(span
|
|
(~tw :tokens "text-stone-300 text-xs")
|
|
:style "margin-left:0.5em;"
|
|
(str "· " path))))))))
|
|
|
|
(defcomp
|
|
~layouts/nav-sibling-row
|
|
(&key node siblings is-leaf level depth)
|
|
:affinity :server
|
|
(let*
|
|
((sibs (or siblings (list)))
|
|
(count (len sibs))
|
|
(row-opacity
|
|
(if
|
|
(and level depth (> depth 0))
|
|
(+ (* (/ level depth) 0.75) 0.25)
|
|
1)))
|
|
(when
|
|
(> count 0)
|
|
(let*
|
|
((idx (find-nav-index sibs node))
|
|
(prev-idx (mod (+ (- idx 1) count) count))
|
|
(next-idx (mod (+ idx 1) count))
|
|
(prev-node (nth sibs prev-idx))
|
|
(next-node (nth sibs next-idx)))
|
|
(div
|
|
(~tw
|
|
:tokens "w-full max-w-3xl mx-auto px-4 py-2 grid grid-cols-3 items-center")
|
|
:style (str "opacity:" row-opacity ";transition:opacity 0.3s;")
|
|
(a
|
|
:href (get prev-node "href")
|
|
:sx-get (get prev-node "href")
|
|
:sx-target "#sx-content"
|
|
:sx-select "#sx-content"
|
|
:sx-swap "innerHTML"
|
|
:sx-push-url "true"
|
|
(~tw :tokens "text-right min-w-0 truncate text-stone-500 text-sm")
|
|
(str "← " (get prev-node "label")))
|
|
(a
|
|
:href (get node "href")
|
|
:sx-get (get node "href")
|
|
:sx-target "#sx-content"
|
|
:sx-select "#sx-content"
|
|
:sx-swap "innerHTML"
|
|
:sx-push-url "true"
|
|
(~tw
|
|
:tokens (str
|
|
"text-center min-w-0 truncate px-1 "
|
|
(if
|
|
is-leaf
|
|
"text-violet-700 text-2xl font-bold"
|
|
"text-violet-700 text-lg font-semibold")))
|
|
(get node "label"))
|
|
(a
|
|
:href (get next-node "href")
|
|
:sx-get (get next-node "href")
|
|
:sx-target "#sx-content"
|
|
:sx-select "#sx-content"
|
|
:sx-swap "innerHTML"
|
|
:sx-push-url "true"
|
|
(~tw :tokens "text-left min-w-0 truncate text-stone-500 text-sm")
|
|
(str (get next-node "label") " →")))))))
|
|
|
|
(defcomp
|
|
~layouts/nav-children
|
|
(&key items)
|
|
:affinity :server
|
|
(div
|
|
(~tw :tokens "max-w-3xl mx-auto px-4 py-3")
|
|
(div
|
|
(~tw :tokens "flex flex-wrap justify-center gap-2")
|
|
(map
|
|
(fn
|
|
(item)
|
|
(a
|
|
:href (get item "href")
|
|
:sx-get (get item "href")
|
|
:sx-target "#sx-content"
|
|
:sx-select "#sx-content"
|
|
:sx-swap "innerHTML"
|
|
:sx-push-url "true"
|
|
(~tw
|
|
:tokens "px-3 py-1.5 rounded border transition-colors text-violet-700 text-sm border-violet-200")
|
|
(get item "label")))
|
|
items))))
|
|
|
|
(defcomp
|
|
~layouts/doc
|
|
(&key path &rest children)
|
|
:affinity :server
|
|
(let*
|
|
((nav-state (resolve-nav-path sx-nav-tree (or path "/")))
|
|
(trail (or (get nav-state "trail") (list)))
|
|
(trail-len (len trail))
|
|
(depth (+ trail-len 1)))
|
|
(<>
|
|
(div
|
|
:id "sx-nav"
|
|
(~tw :tokens "mb-6")
|
|
:sx-swap-oob "innerHTML"
|
|
(div
|
|
:id "logo-opacity"
|
|
:style (str
|
|
"opacity:"
|
|
(+ (* (/ 1 depth) 0.75) 0.25)
|
|
";"
|
|
"transition:opacity 0.3s;")
|
|
(~layouts/header :path (or path "/")))
|
|
(map-indexed
|
|
(fn
|
|
(i crumb)
|
|
(~layouts/nav-sibling-row
|
|
:node (get crumb "node")
|
|
:siblings (get crumb "siblings")
|
|
:is-leaf (= i (- trail-len 1))
|
|
:level (+ i 2)
|
|
:depth depth))
|
|
trail)
|
|
(when
|
|
(get nav-state "children")
|
|
(~layouts/nav-children :items (get nav-state "children"))))
|
|
(div :id "sx-content" (error-boundary children) (~tw/flush)))))
|
|
|
|
(defcomp ~layouts/docs-layout-full () nil)
|
|
|
|
(defcomp ~layouts/docs-layout-oob () nil)
|
|
|
|
(defcomp ~layouts/docs-layout-mobile () nil)
|
|
|
|
(defcomp ~layouts/standalone-docs-layout-full () nil)
|
|
|
|
(defcomp
|
|
~layouts/standalone-docs-layout-oob
|
|
(&key content)
|
|
(~shared:layout/oob-sx :content content))
|
|
|
|
(defcomp ~layouts/standalone-docs-layout-mobile () nil)
|