diff --git a/README.md b/README.md index e0455ba..1eec646 100644 --- a/README.md +++ b/README.md @@ -4,6 +4,8 @@ The gallery owns one definite 720 px canvas so its nested Grid examples cannot each reinterpret the surrounding viewport width. It fits a compact GUI Emacs window with at least 760 px of body width. `etaf-playground` remains the separate higher-level Component and Runtime showcase. +Standalone fixture renders use the same compact 720 px default viewport unless the caller dynamically binds `ebox-viewport-width`; viewport-based references therefore stay inside the example canvas. + ```elisp (require 'ebox-playground) (ebox-playground-open) diff --git a/README.zh-CN.md b/README.zh-CN.md index 84bad85..8eaa9f5 100644 --- a/README.zh-CN.md +++ b/README.zh-CN.md @@ -4,6 +4,8 @@ 画廊统一拥有一个明确的 720 px 画布,因此嵌套 Grid 不会各自重新解释外层视口宽度。只要 GUI Emacs 的正文区域不小于 760 px,它就能完整显示。高层 Component/Runtime 展示仍由独立的 `etaf-playground` 提供。 +独立 fixture 渲染默认也使用紧凑的 720 px 视口;如果调用方动态绑定了 `ebox-viewport-width`,则保留调用方的值。因此依赖 viewport 的参考例子也会保持在示例画布内。 + ```elisp (require 'ebox-playground) (ebox-playground-open) diff --git a/ebox-playground.el b/ebox-playground.el index eb9cf1c..2c4cefc 100644 --- a/ebox-playground.el +++ b/ebox-playground.el @@ -51,13 +51,15 @@ (defun ebox-dsl-render () "Render the current Ebox DSL buffer into a preview buffer." (interactive) - (let* ((source (ebox-playground--source-form)) - (name (format "*Ebox Preview: %s*" - (or (buffer-file-name) (buffer-name)))) - (node (ebox-build source))) - (ebox-display-buffer name node) - (message "Rendered Ebox DSL into %s" name) - (get-buffer name))) + (let ((ebox-viewport-width + (ebox-playground--effective-viewport-width))) + (let* ((source (ebox-playground--source-form)) + (name (format "*Ebox Preview: %s*" + (or (buffer-file-name) (buffer-name)))) + (node (ebox-build source))) + (ebox-display-buffer name node) + (message "Rendered Ebox DSL into %s" name) + (get-buffer name)))) ;;;###autoload (add-to-list 'auto-mode-alist '("\\.ebox\\'" . ebox-dsl-mode)) @@ -77,6 +79,24 @@ :type 'file :group 'ebox-playground) +(defcustom ebox-playground-default-viewport-width 720 + "Viewport width used when a caller does not provide one explicitly." + :type 'positive-integer + :group 'ebox-playground) + +(defun ebox-playground--effective-viewport-width () + "Return the caller's viewport width or the compact playground default." + (if (and (numberp ebox-viewport-width) + (> ebox-viewport-width 0)) + (floor ebox-viewport-width) + ebox-playground-default-viewport-width)) + +(defun ebox-playground--render-node-to-buffer (buffer node) + "Render NODE into BUFFER using the effective playground viewport width." + (let ((ebox-viewport-width + (ebox-playground--effective-viewport-width))) + (ebox-render-to-buffer buffer node))) + (defun ebox-playground--static-value-p (value) "Return non-nil when VALUE is a literal or explicitly quoted form." (or (null value) (numberp value) (stringp value) (characterp value) @@ -138,23 +158,26 @@ ;;;###autoload (defun ebox-playground-view (&optional file) "Build the Ebox DSL form in FILE without buffer side effects." - (ebox-build - (ebox-playground--evaluate-form - (ebox-playground--read-file - (expand-file-name (or file ebox-playground-default-file)))))) + (let ((ebox-viewport-width + (ebox-playground--effective-viewport-width))) + (ebox-build + (ebox-playground--evaluate-form + (ebox-playground--read-file + (expand-file-name (or file ebox-playground-default-file))))))) ;;;###autoload (defun ebox-playground-open (&optional buffer-name) "Render the default Ebox DSL example into BUFFER-NAME and return its buffer." (interactive) - (ebox-render-to-buffer (or buffer-name ebox-playground-buffer-name) - (ebox-playground-view))) + (ebox-playground--render-node-to-buffer + (or buffer-name ebox-playground-buffer-name) + (ebox-playground-view))) ;;;###autoload (defun ebox-playground-open-file (file &optional buffer-name) "Render Ebox DSL FILE into BUFFER-NAME and return its buffer." (interactive "fEbox DSL file: ") - (ebox-render-to-buffer + (ebox-playground--render-node-to-buffer (or buffer-name (format "*Ebox Preview: %s*" (file-name-nondirectory file))) (ebox-playground-view file))) diff --git a/examples/comprehensive.ebox b/examples/comprehensive.ebox index 4862d53..18ea608 100644 --- a/examples/comprehensive.ebox +++ b/examples/comprehensive.ebox @@ -3,13 +3,13 @@ :padding '(1 (16)) :border "#334155" :bgcolor "#F8FAFC" :color "#0F172A" :text-align 'center) - (spacer :height 1) + (spacer :width '(viewport) :height 1 :bgcolor "#F8FAFC") (box :content "Width rule in this file\nContainer sections use auto width. Fixed widths remain only where the example demonstrates exact item sizing, basis, min-width, or max-width." :padding '(0 (14)) :border "#64748B" :bgcolor "#F8FAFC" :color "#111827" :wrap-mode 'word) - (spacer :height 1) + (spacer :width '(viewport) :height 1 :bgcolor "#F8FAFC") (flex :margin '(1 0 0 1) :padding '(1 (8)) diff --git a/examples/flex-reference.ebox b/examples/flex-reference.ebox index 802662e..4f4a346 100644 --- a/examples/flex-reference.ebox +++ b/examples/flex-reference.ebox @@ -4,7 +4,7 @@ :padding '(1 (24)) :border "#2F3437" :bgcolor "#FAF7F0" :color "#1F2328" :text-align 'center) - (spacer :height 1) + (spacer :width '(viewport) :height 1 :bgcolor "#FAF7F0") (box :content "Container property: :flex-direction\nMain axis selection. Reverse values swap main-start and main-end while keeping source order intact." :padding '(0 (18)) :border "#D97757" @@ -18,38 +18,38 @@ (flex :width '(220) :height 4 :padding '(0 (8)) :border "#D97757" :border-top-p nil :bgcolor "#FFF8F2" :flex-direction 'row :column-gap '(10) :align-items 'center - (item (box :content "A" :width '(42) :height 1 :bgcolor "#F7C8B3" :text-align 'center)) - (item (box :content "B" :width '(42) :height 1 :bgcolor "#F0A88F" :text-align 'center)) - (item (box :content "C" :width '(42) :height 1 :bgcolor "#D97757" :color "#FFFFFF" :text-align 'center)))) + (item (box :content "A" :width '(42) :height 1 :bgcolor "#F7C8B3" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(42) :height 1 :bgcolor "#F0A88F" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :width '(42) :height 1 :bgcolor "#D97757" :color "#1F2328" :text-align 'center)))) (column (box :content "row-reverse" :width '(220) :padding '(0 (10)) :border "#D97757" :bgcolor "#FFFDF8" :color "#3D3A35" :text-align 'center) (flex :width '(220) :height 4 :padding '(0 (8)) :border "#D97757" :border-top-p nil :bgcolor "#FFF8F2" :flex-direction 'row-reverse :column-gap '(10) :align-items 'center - (item (box :content "A" :width '(42) :height 1 :bgcolor "#F7C8B3" :text-align 'center)) - (item (box :content "B" :width '(42) :height 1 :bgcolor "#F0A88F" :text-align 'center)) - (item (box :content "C" :width '(42) :height 1 :bgcolor "#D97757" :color "#FFFFFF" :text-align 'center)))) + (item (box :content "A" :width '(42) :height 1 :bgcolor "#F7C8B3" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(42) :height 1 :bgcolor "#F0A88F" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :width '(42) :height 1 :bgcolor "#D97757" :color "#1F2328" :text-align 'center)))) (column (box :content "column" :width '(220) :padding '(0 (10)) :border "#D97757" :bgcolor "#FFFDF8" :color "#3D3A35" :text-align 'center) (flex :width '(220) :height 6 :padding '(0 (8)) :border "#D97757" :border-top-p nil :bgcolor "#FFF8F2" :flex-direction 'column :row-gap 1 :align-items 'stretch - (item (box :content "A" :height 1 :bgcolor "#F7C8B3" :text-align 'center)) - (item (box :content "B" :height 1 :bgcolor "#F0A88F" :text-align 'center)) - (item (box :content "C" :height 1 :bgcolor "#D97757" :color "#FFFFFF" :text-align 'center)))) + (item (box :content "A" :height 1 :bgcolor "#F7C8B3" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :height 1 :bgcolor "#F0A88F" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :height 1 :bgcolor "#D97757" :color "#1F2328" :text-align 'center)))) (column (box :content "column-reverse" :width '(220) :padding '(0 (10)) :border "#D97757" :bgcolor "#FFFDF8" :color "#3D3A35" :text-align 'center) (flex :width '(220) :height 6 :padding '(0 (8)) :border "#D97757" :border-top-p nil :bgcolor "#FFF8F2" :flex-direction 'column-reverse :row-gap 1 :align-items 'stretch - (item (box :content "A" :height 1 :bgcolor "#F7C8B3" :text-align 'center)) - (item (box :content "B" :height 1 :bgcolor "#F0A88F" :text-align 'center)) - (item (box :content "C" :height 1 :bgcolor "#D97757" :color "#FFFFFF" :text-align 'center))))) + (item (box :content "A" :height 1 :bgcolor "#F7C8B3" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :height 1 :bgcolor "#F0A88F" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :height 1 :bgcolor "#D97757" :color "#1F2328" :text-align 'center))))) - (spacer :height 1) + (spacer :width '(viewport) :height 1 :bgcolor "#FAF7F0") (box :content "Container property: :flex-wrap\nLine creation. nowrap keeps one flex line; wrap creates new lines; wrap-reverse stacks lines from the opposite cross side." :padding '(0 (18)) :border "#5E7F6A" @@ -63,29 +63,29 @@ (flex :max-width '(293) :padding '(0 (8)) :border "#5E7F6A" :border-top-p nil :bgcolor "#F8FCF8" :flex-wrap 'nowrap :column-gap '(8) :align-items 'center - (item :flex-shrink 1 (box :content "A" :width '(92) :height 1 :bgcolor "#DCEBDD" :text-align 'center)) - (item :flex-shrink 1 (box :content "B" :width '(92) :height 1 :bgcolor "#BFD6C2" :text-align 'center)) - (item :flex-shrink 1 (box :content "C" :width '(92) :height 1 :bgcolor "#8FAF95" :text-align 'center)))) + (item :flex-shrink 1 (box :content "A" :width '(92) :height 1 :bgcolor "#DCEBDD" :color "#1F2328" :text-align 'center)) + (item :flex-shrink 1 (box :content "B" :width '(92) :height 1 :bgcolor "#BFD6C2" :color "#1F2328" :text-align 'center)) + (item :flex-shrink 1 (box :content "C" :width '(92) :height 1 :bgcolor "#8FAF95" :color "#1F2328" :text-align 'center)))) (column (box :content "wrap" :max-width '(293) :padding '(0 (10)) :border "#5E7F6A" :bgcolor "#FFFDF8" :color "#3D3A35" :text-align 'center) (flex :max-width '(293) :padding '(0 (8)) :border "#5E7F6A" :border-top-p nil :bgcolor "#F8FCF8" :flex-wrap 'wrap :column-gap '(8) :row-gap 1 - (item :flex-shrink 0 (box :content "A 118" :width '(118) :height 1 :bgcolor "#DCEBDD" :text-align 'center)) - (item :flex-shrink 0 (box :content "B 118" :width '(118) :height 1 :bgcolor "#BFD6C2" :text-align 'center)) - (item :flex-shrink 0 (box :content "C 118" :width '(118) :height 1 :bgcolor "#8FAF95" :text-align 'center)))) + (item :flex-shrink 0 (box :content "A 118" :width '(118) :height 1 :bgcolor "#DCEBDD" :color "#1F2328" :text-align 'center)) + (item :flex-shrink 0 (box :content "B 118" :width '(118) :height 1 :bgcolor "#BFD6C2" :color "#1F2328" :text-align 'center)) + (item :flex-shrink 0 (box :content "C 118" :width '(118) :height 1 :bgcolor "#8FAF95" :color "#1F2328" :text-align 'center)))) (column (box :content "wrap-reverse" :max-width '(293) :padding '(0 (10)) :border "#5E7F6A" :bgcolor "#FFFDF8" :color "#3D3A35" :text-align 'center) (flex :max-width '(293) :padding '(0 (8)) :border "#5E7F6A" :border-top-p nil :bgcolor "#F8FCF8" :flex-wrap 'wrap-reverse :column-gap '(8) :row-gap 1 - (item :flex-shrink 0 (box :content "A 118" :width '(118) :height 1 :bgcolor "#DCEBDD" :text-align 'center)) - (item :flex-shrink 0 (box :content "B 118" :width '(118) :height 1 :bgcolor "#BFD6C2" :text-align 'center)) - (item :flex-shrink 0 (box :content "C 118" :width '(118) :height 1 :bgcolor "#8FAF95" :text-align 'center))))) + (item :flex-shrink 0 (box :content "A 118" :width '(118) :height 1 :bgcolor "#DCEBDD" :color "#1F2328" :text-align 'center)) + (item :flex-shrink 0 (box :content "B 118" :width '(118) :height 1 :bgcolor "#BFD6C2" :color "#1F2328" :text-align 'center)) + (item :flex-shrink 0 (box :content "C 118" :width '(118) :height 1 :bgcolor "#8FAF95" :color "#1F2328" :text-align 'center))))) - (spacer :height 1) + (spacer :width '(viewport) :height 1 :bgcolor "#FAF7F0") (box :content "Container property: :flex-flow\nShorthand for direction and wrapping. These examples use one property to set both behaviors." :padding '(0 (18)) :border "#6F6A95" @@ -99,20 +99,20 @@ (flex :max-width '(440) :padding '(0 (8)) :border "#6F6A95" :border-top-p nil :bgcolor "#FBF9FF" :flex-flow '(row wrap) :gap '(1 (12)) - (item (box :content "A" :width '(170) :height 1 :bgcolor "#E4DEF4" :text-align 'center)) - (item (box :content "B" :width '(170) :height 1 :bgcolor "#CBC2E3" :text-align 'center)) - (item (box :content "C wraps" :width '(170) :height 1 :bgcolor "#AFA3D1" :text-align 'center)))) + (item (box :content "A" :width '(170) :height 1 :bgcolor "#E4DEF4" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(170) :height 1 :bgcolor "#CBC2E3" :color "#1F2328" :text-align 'center)) + (item (box :content "C wraps" :width '(170) :height 1 :bgcolor "#AFA3D1" :color "#1F2328" :text-align 'center)))) (column (box :content ":flex-flow (column wrap)" :max-width '(440) :padding '(0 (10)) :border "#6F6A95" :bgcolor "#FFFDF8" :color "#3D3A35" :text-align 'center) (flex :max-width '(440) :padding '(0 (8)) :border "#6F6A95" :border-top-p nil :bgcolor "#FBF9FF" :flex-flow '(column wrap) :gap '(1 (12)) - (item (box :content "A" :width '(140) :height 1 :bgcolor "#E4DEF4" :text-align 'center)) - (item (box :content "B" :width '(140) :height 1 :bgcolor "#CBC2E3" :text-align 'center)) - (item (box :content "C new column" :width '(140) :height 1 :bgcolor "#AFA3D1" :text-align 'center))))) + (item (box :content "A" :width '(140) :height 1 :bgcolor "#E4DEF4" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(140) :height 1 :bgcolor "#CBC2E3" :color "#1F2328" :text-align 'center)) + (item (box :content "C new column" :width '(140) :height 1 :bgcolor "#AFA3D1" :color "#1F2328" :text-align 'center))))) - (spacer :height 1) + (spacer :width '(viewport) :height 1 :bgcolor "#FAF7F0") (box :content "Container property: :justify-content\nMain-axis packing after sizing. Distributed values change the space before, between, and after items." :padding '(0 (18)) :border "#3F6D88" @@ -121,57 +121,57 @@ :border "#3F6D88" :border-top-p nil :bgcolor "#F6FBFD" (column - (box :content "flex-start" :width '(146) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "flex-start" :width '(146) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(146) :border "#3F6D88" :border-top-p nil :bgcolor "#F6FBFD" :justify-content 'flex-start - (item (box :content "A" :width '(28) :height 1 :bgcolor "#CAE6F0" :text-align 'center)) - (item (box :content "B" :width '(28) :height 1 :bgcolor "#A8D2E2" :text-align 'center)))) + (item (box :content "A" :width '(28) :height 1 :bgcolor "#CAE6F0" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(28) :height 1 :bgcolor "#A8D2E2" :color "#1F2328" :text-align 'center)))) (column - (box :content "center" :width '(146) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "center" :width '(146) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(146) :border "#3F6D88" :border-top-p nil :bgcolor "#F6FBFD" :justify-content 'center - (item (box :content "A" :width '(28) :height 1 :bgcolor "#CAE6F0" :text-align 'center)) - (item (box :content "B" :width '(28) :height 1 :bgcolor "#A8D2E2" :text-align 'center)))) + (item (box :content "A" :width '(28) :height 1 :bgcolor "#CAE6F0" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(28) :height 1 :bgcolor "#A8D2E2" :color "#1F2328" :text-align 'center)))) (column - (box :content "flex-end" :width '(146) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "flex-end" :width '(146) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(146) :border "#3F6D88" :border-top-p nil :bgcolor "#F6FBFD" :justify-content 'flex-end - (item (box :content "A" :width '(28) :height 1 :bgcolor "#CAE6F0" :text-align 'center)) - (item (box :content "B" :width '(28) :height 1 :bgcolor "#A8D2E2" :text-align 'center)))) + (item (box :content "A" :width '(28) :height 1 :bgcolor "#CAE6F0" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(28) :height 1 :bgcolor "#A8D2E2" :color "#1F2328" :text-align 'center)))) (column - (box :content "space-between" :width '(146) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "space-between" :width '(146) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(146) :border "#3F6D88" :border-top-p nil :bgcolor "#F6FBFD" :justify-content 'space-between - (item (box :content "A" :width '(28) :height 1 :bgcolor "#CAE6F0" :text-align 'center)) - (item (box :content "B" :width '(28) :height 1 :bgcolor "#A8D2E2" :text-align 'center)))) + (item (box :content "A" :width '(28) :height 1 :bgcolor "#CAE6F0" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(28) :height 1 :bgcolor "#A8D2E2" :color "#1F2328" :text-align 'center)))) (column - (box :content "space-around" :width '(146) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "space-around" :width '(146) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(146) :border "#3F6D88" :border-top-p nil :bgcolor "#F6FBFD" :justify-content 'space-around - (item (box :content "A" :width '(28) :height 1 :bgcolor "#CAE6F0" :text-align 'center)) - (item (box :content "B" :width '(28) :height 1 :bgcolor "#A8D2E2" :text-align 'center)))) + (item (box :content "A" :width '(28) :height 1 :bgcolor "#CAE6F0" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(28) :height 1 :bgcolor "#A8D2E2" :color "#1F2328" :text-align 'center)))) (column - (box :content "space-evenly" :width '(146) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "space-evenly" :width '(146) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(146) :border "#3F6D88" :border-top-p nil :bgcolor "#F6FBFD" :justify-content 'space-evenly - (item (box :content "A" :width '(28) :height 1 :bgcolor "#CAE6F0" :text-align 'center)) - (item (box :content "B" :width '(28) :height 1 :bgcolor "#A8D2E2" :text-align 'center)))) + (item (box :content "A" :width '(28) :height 1 :bgcolor "#CAE6F0" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(28) :height 1 :bgcolor "#A8D2E2" :color "#1F2328" :text-align 'center)))) (column - (box :content "start" :width '(176) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "start" :width '(176) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :border "#3F6D88" :border-top-p nil :bgcolor "#F6FBFD" :justify-content 'start - (item (box :content "start" :width '(70) :height 1 :bgcolor "#CAE6F0" :text-align 'center)))) + (item (box :content "start" :width '(70) :height 1 :bgcolor "#CAE6F0" :color "#1F2328" :text-align 'center)))) (column - (box :content "end" :width '(176) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "end" :width '(176) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :border "#3F6D88" :border-top-p nil :bgcolor "#F6FBFD" :justify-content 'end - (item (box :content "end" :width '(70) :height 1 :bgcolor "#A8D2E2" :text-align 'center)))) + (item (box :content "end" :width '(70) :height 1 :bgcolor "#A8D2E2" :color "#1F2328" :text-align 'center)))) (column - (box :content "left" :width '(176) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "left" :width '(176) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :border "#3F6D88" :border-top-p nil :bgcolor "#F6FBFD" :justify-content 'left - (item (box :content "left" :width '(70) :height 1 :bgcolor "#7DB8CE" :text-align 'center)))) + (item (box :content "left" :width '(70) :height 1 :bgcolor "#7DB8CE" :color "#1F2328" :text-align 'center)))) (column - (box :content "right" :width '(176) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "right" :width '(176) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :border "#3F6D88" :border-top-p nil :bgcolor "#F6FBFD" :justify-content 'right - (item (box :content "right" :width '(70) :height 1 :bgcolor "#5F9CB5" :text-align 'center)))) + (item (box :content "right" :width '(70) :height 1 :bgcolor "#5F9CB5" :color "#1F2328" :text-align 'center)))) (column - (box :content "normal" :width '(176) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "normal" :width '(176) :padding '(0 (4)) :border "#3F6D88" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :border "#3F6D88" :border-top-p nil :bgcolor "#F6FBFD" :justify-content 'normal (item (box :content "normal" :width '(70) :height 1 :bgcolor "#3F6D88" :color "#FFFFFF" :text-align 'center))))) - (spacer :height 1) + (spacer :width '(viewport) :height 1 :bgcolor "#FAF7F0") (box :content "Container property: :align-items\nCross-axis alignment inside each flex line. Stretch/normal enlarge auto-sized items; start/end/center move shorter ones." :padding '(0 (18)) :border "#9A6B43" @@ -180,56 +180,56 @@ :border "#9A6B43" :border-top-p nil :bgcolor "#FFFAF5" (column - (box :content "flex-start" :width '(176) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "flex-start" :width '(176) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 5 :border "#9A6B43" :border-top-p nil :bgcolor "#FFFAF5" :align-items 'flex-start - (item (box :content "short" :width '(68) :height 1 :bgcolor "#F1D0AF" :text-align 'center)) - (item (box :content "tall\nitem\nsets line" :width '(78) :height 3 :bgcolor "#D9AD83" :text-align 'center)))) + (item (box :content "short" :width '(68) :height 1 :bgcolor "#F1D0AF" :color "#1F2328" :text-align 'center)) + (item (box :content "tall\nitem\nsets line" :width '(78) :height 3 :bgcolor "#D9AD83" :color "#1F2328" :text-align 'center)))) (column - (box :content "center" :width '(176) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "center" :width '(176) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 5 :border "#9A6B43" :border-top-p nil :bgcolor "#FFFAF5" :align-items 'center - (item (box :content "short" :width '(68) :height 1 :bgcolor "#F1D0AF" :text-align 'center)) - (item (box :content "tall\nitem\nsets line" :width '(78) :height 3 :bgcolor "#D9AD83" :text-align 'center)))) + (item (box :content "short" :width '(68) :height 1 :bgcolor "#F1D0AF" :color "#1F2328" :text-align 'center)) + (item (box :content "tall\nitem\nsets line" :width '(78) :height 3 :bgcolor "#D9AD83" :color "#1F2328" :text-align 'center)))) (column - (box :content "flex-end" :width '(176) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "flex-end" :width '(176) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 5 :border "#9A6B43" :border-top-p nil :bgcolor "#FFFAF5" :align-items 'flex-end - (item (box :content "short" :width '(68) :height 1 :bgcolor "#F1D0AF" :text-align 'center)) - (item (box :content "tall\nitem\nsets line" :width '(78) :height 3 :bgcolor "#D9AD83" :text-align 'center)))) + (item (box :content "short" :width '(68) :height 1 :bgcolor "#F1D0AF" :color "#1F2328" :text-align 'center)) + (item (box :content "tall\nitem\nsets line" :width '(78) :height 3 :bgcolor "#D9AD83" :color "#1F2328" :text-align 'center)))) (column - (box :content "stretch" :width '(176) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "stretch" :width '(176) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 5 :border "#9A6B43" :border-top-p nil :bgcolor "#FFFAF5" :align-items 'stretch - (item (box :content "auto height stretches" :width '(72) :bgcolor "#F1D0AF" :text-align 'center)) - (item (box :content "line height" :width '(78) :height 3 :bgcolor "#D9AD83" :text-align 'center)))) + (item (box :content "auto height stretches" :width '(72) :bgcolor "#F1D0AF" :color "#1F2328" :text-align 'center)) + (item (box :content "line height" :width '(78) :height 3 :bgcolor "#D9AD83" :color "#1F2328" :text-align 'center)))) (column - (box :content "baseline" :width '(176) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "baseline" :width '(176) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 5 :border "#9A6B43" :border-top-p nil :bgcolor "#FFFAF5" :align-items 'baseline - (item (box :content "baseline" :width '(90) :height 1 :bgcolor "#BA8456" :text-align 'center)))) + (item (box :content "baseline" :width '(90) :height 1 :bgcolor "#BA8456" :color "#1F2328" :text-align 'center)))) (column - (box :content "start" :width '(146) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "start" :width '(146) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(146) :height 4 :border "#9A6B43" :border-top-p nil :bgcolor "#FFFAF5" :align-items 'start - (item (box :content "start" :width '(62) :height 1 :bgcolor "#F1D0AF" :text-align 'center)))) + (item (box :content "start" :width '(62) :height 1 :bgcolor "#F1D0AF" :color "#1F2328" :text-align 'center)))) (column - (box :content "end" :width '(146) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "end" :width '(146) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(146) :height 4 :border "#9A6B43" :border-top-p nil :bgcolor "#FFFAF5" :align-items 'end - (item (box :content "end" :width '(62) :height 1 :bgcolor "#D9AD83" :text-align 'center)))) + (item (box :content "end" :width '(62) :height 1 :bgcolor "#D9AD83" :color "#1F2328" :text-align 'center)))) (column - (box :content "self-start" :width '(146) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "self-start" :width '(146) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(146) :height 4 :border "#9A6B43" :border-top-p nil :bgcolor "#FFFAF5" :align-items 'self-start - (item (box :content "self-start" :width '(78) :height 1 :bgcolor "#BA8456" :text-align 'center)))) + (item (box :content "self-start" :width '(78) :height 1 :bgcolor "#BA8456" :color "#1F2328" :text-align 'center)))) (column - (box :content "self-end" :width '(146) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "self-end" :width '(146) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(146) :height 4 :border "#9A6B43" :border-top-p nil :bgcolor "#FFFAF5" :align-items 'self-end (item (box :content "self-end" :width '(70) :height 1 :bgcolor "#9A6B43" :color "#FFFFFF" :text-align 'center)))) (column - (box :content "normal" :width '(146) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "normal" :width '(146) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(146) :height 4 :border "#9A6B43" :border-top-p nil :bgcolor "#FFFAF5" :align-items 'normal (item (box :content "normal" :width '(62) :bgcolor "#7A5132" :color "#FFFFFF" :text-align 'center)))) (column - (box :content "stretch note" :width '(146) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "stretch note" :width '(146) :padding '(0 (4)) :border "#9A6B43" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (box :content "normal behaves stretch-like for auto cross size in this DSL." :width '(146) :height 4 :padding '(0 (8)) :border "#9A6B43" :border-top-p nil :bgcolor "#FFFAF5" :color "#3A2A1D"))) - (spacer :height 1) + (spacer :width '(viewport) :height 1 :bgcolor "#FAF7F0") (box :content "Container property: :align-content\nCross-axis packing between multiple flex lines. It has no visible effect on a nowrap single-line container." :padding '(0 (18)) :border "#7C6A2F" @@ -238,89 +238,89 @@ :border "#7C6A2F" :border-top-p nil :bgcolor "#FFFDF0" (column - (box :content "flex-start" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "flex-start" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 7 :border "#7C6A2F" :border-top-p nil :bgcolor "#FFFDF0" :flex-wrap 'wrap :align-content 'flex-start :row-gap 1 :column-gap '(8) - (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :text-align 'center)) - (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :text-align 'center)) - (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :text-align 'center)))) + (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :color "#1F2328" :text-align 'center)))) (column - (box :content "center" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "center" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 7 :border "#7C6A2F" :border-top-p nil :bgcolor "#FFFDF0" :flex-wrap 'wrap :align-content 'center :row-gap 1 :column-gap '(8) - (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :text-align 'center)) - (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :text-align 'center)) - (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :text-align 'center)))) + (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :color "#1F2328" :text-align 'center)))) (column - (box :content "flex-end" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "flex-end" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 7 :border "#7C6A2F" :border-top-p nil :bgcolor "#FFFDF0" :flex-wrap 'wrap :align-content 'flex-end :row-gap 1 :column-gap '(8) - (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :text-align 'center)) - (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :text-align 'center)) - (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :text-align 'center)))) + (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :color "#1F2328" :text-align 'center)))) (column - (box :content "space-between" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "space-between" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 7 :border "#7C6A2F" :border-top-p nil :bgcolor "#FFFDF0" :flex-wrap 'wrap :align-content 'space-between :row-gap 1 :column-gap '(8) - (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :text-align 'center)) - (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :text-align 'center)) - (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :text-align 'center)))) + (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :color "#1F2328" :text-align 'center)))) (column - (box :content "space-around" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "space-around" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 7 :border "#7C6A2F" :border-top-p nil :bgcolor "#FFFDF0" :flex-wrap 'wrap :align-content 'space-around :row-gap 1 :column-gap '(8) - (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :text-align 'center)) - (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :text-align 'center)) - (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :text-align 'center)))) + (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :color "#1F2328" :text-align 'center)))) (column - (box :content "space-evenly" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "space-evenly" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 7 :border "#7C6A2F" :border-top-p nil :bgcolor "#FFFDF0" :flex-wrap 'wrap :align-content 'space-evenly :row-gap 1 :column-gap '(8) - (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :text-align 'center)) - (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :text-align 'center)) - (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :text-align 'center)))) + (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :color "#1F2328" :text-align 'center)))) (column - (box :content "stretch" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "stretch" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 7 :border "#7C6A2F" :border-top-p nil :bgcolor "#FFFDF0" :flex-wrap 'wrap :align-content 'stretch :row-gap 1 :column-gap '(8) - (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :text-align 'center)) - (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :text-align 'center)) - (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :text-align 'center)))) + (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :color "#1F2328" :text-align 'center)))) (column - (box :content "start" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "start" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 7 :border "#7C6A2F" :border-top-p nil :bgcolor "#FFFDF0" :flex-wrap 'wrap :align-content 'start :row-gap 1 :column-gap '(8) - (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :text-align 'center)) - (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :text-align 'center)) - (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :text-align 'center)))) + (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :color "#1F2328" :text-align 'center)))) (column - (box :content "end" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "end" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 7 :border "#7C6A2F" :border-top-p nil :bgcolor "#FFFDF0" :flex-wrap 'wrap :align-content 'end :row-gap 1 :column-gap '(8) - (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :text-align 'center)) - (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :text-align 'center)) - (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :text-align 'center)))) + (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :color "#1F2328" :text-align 'center)))) (column - (box :content "baseline" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "baseline" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 7 :border "#7C6A2F" :border-top-p nil :bgcolor "#FFFDF0" :flex-wrap 'wrap :align-content 'baseline :row-gap 1 :column-gap '(8) - (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :text-align 'center)) - (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :text-align 'center)) - (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :text-align 'center)))) + (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :color "#1F2328" :text-align 'center)))) (column - (box :content "normal" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "normal" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 7 :border "#7C6A2F" :border-top-p nil :bgcolor "#FFFDF0" :flex-wrap 'wrap :align-content 'normal :row-gap 1 :column-gap '(8) - (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :text-align 'center)) - (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :text-align 'center)) - (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :text-align 'center)))) + (item (box :content "A" :width '(78) :height 1 :bgcolor "#EEE1A8" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(78) :height 1 :bgcolor "#D9C46D" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :width '(78) :height 1 :bgcolor "#B89B3D" :color "#1F2328" :text-align 'center)))) (column - (box :content "nowrap note" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :text-align 'center) + (box :content "nowrap note" :width '(176) :padding '(0 (4)) :border "#7C6A2F" :bgcolor "#FFFDF8" :color "#1F2328" :text-align 'center) (flex :width '(176) :height 7 :border "#7C6A2F" :border-top-p nil :bgcolor "#FFFDF0" :flex-wrap 'nowrap :align-content 'normal :row-gap 1 :column-gap '(8) - (item (box :content "single line" :width '(96) :height 1 :bgcolor "#EEE1A8" :text-align 'center))))) + (item (box :content "single line" :width '(96) :height 1 :bgcolor "#EEE1A8" :color "#1F2328" :text-align 'center))))) - (spacer :height 1) + (spacer :width '(viewport) :height 1 :bgcolor "#FAF7F0") (box :content "Container properties: :gap, :row-gap, :column-gap\n:gaps define spacing between flex items and flex lines. Explicit row/column values override matching sides." :padding '(0 (18)) :border "#3D7068" @@ -334,27 +334,27 @@ (flex :max-width '(293) :border "#3D7068" :border-top-p nil :bgcolor "#F7FCFB" :flex-wrap 'wrap :gap '(1 (14)) - (item (box :content "A" :width '(104) :height 1 :bgcolor "#CDEBE5" :text-align 'center)) - (item (box :content "B" :width '(104) :height 1 :bgcolor "#9FD5CB" :text-align 'center)) - (item (box :content "C" :width '(104) :height 1 :bgcolor "#71BDB0" :text-align 'center)))) + (item (box :content "A" :width '(104) :height 1 :bgcolor "#CDEBE5" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(104) :height 1 :bgcolor "#9FD5CB" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :width '(104) :height 1 :bgcolor "#71BDB0" :color "#1F2328" :text-align 'center)))) (column (box :content ":row-gap 2" :max-width '(293) :padding '(0 (10)) :border "#3D7068" :bgcolor "#FFFDF8" :color "#3D3A35" :text-align 'center) (flex :max-width '(293) :border "#3D7068" :border-top-p nil :bgcolor "#F7FCFB" :flex-wrap 'wrap :row-gap 2 :column-gap '(8) - (item (box :content "A" :width '(104) :height 1 :bgcolor "#CDEBE5" :text-align 'center)) - (item (box :content "B" :width '(104) :height 1 :bgcolor "#9FD5CB" :text-align 'center)) - (item (box :content "C" :width '(104) :height 1 :bgcolor "#71BDB0" :text-align 'center)))) + (item (box :content "A" :width '(104) :height 1 :bgcolor "#CDEBE5" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(104) :height 1 :bgcolor "#9FD5CB" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :width '(104) :height 1 :bgcolor "#71BDB0" :color "#1F2328" :text-align 'center)))) (column (box :content ":column-gap (32)" :max-width '(293) :padding '(0 (10)) :border "#3D7068" :bgcolor "#FFFDF8" :color "#3D3A35" :text-align 'center) (flex :max-width '(293) :border "#3D7068" :border-top-p nil :bgcolor "#F7FCFB" :flex-wrap 'wrap :row-gap 1 :column-gap '(32) - (item (box :content "A" :width '(104) :height 1 :bgcolor "#CDEBE5" :text-align 'center)) - (item (box :content "B" :width '(104) :height 1 :bgcolor "#9FD5CB" :text-align 'center)) - (item (box :content "C" :width '(104) :height 1 :bgcolor "#71BDB0" :text-align 'center))))) + (item (box :content "A" :width '(104) :height 1 :bgcolor "#CDEBE5" :color "#1F2328" :text-align 'center)) + (item (box :content "B" :width '(104) :height 1 :bgcolor "#9FD5CB" :color "#1F2328" :text-align 'center)) + (item (box :content "C" :width '(104) :height 1 :bgcolor "#71BDB0" :color "#1F2328" :text-align 'center))))) - (spacer :height 1) + (spacer :width '(viewport) :height 1 :bgcolor "#FAF7F0") (box :content "Item property: :order\nVisual ordering sorts by :order, then source order. The labels expose both values." :padding '(0 (18)) :border "#8E4A63" @@ -362,12 +362,12 @@ (flex :height 5 :padding '(0 (12)) :border "#8E4A63" :border-top-p nil :bgcolor "#FFF8FA" :column-gap '(12) :align-items 'center - (item :order 3 (box :content "source 1\n:order 3" :width '(150) :height 2 :bgcolor "#F2C4D2" :text-align 'center)) - (item :order 1 (box :content "source 2\n:order 1" :width '(150) :height 2 :bgcolor "#DEA4B7" :text-align 'center)) - (item :order 2 (box :content "source 3\n:order 2" :width '(150) :height 2 :bgcolor "#C87F9A" :text-align 'center)) + (item :order 3 (box :content "source 1\n:order 3" :width '(150) :height 2 :bgcolor "#F2C4D2" :color "#1F2328" :text-align 'center)) + (item :order 1 (box :content "source 2\n:order 1" :width '(150) :height 2 :bgcolor "#DEA4B7" :color "#1F2328" :text-align 'center)) + (item :order 2 (box :content "source 3\n:order 2" :width '(150) :height 2 :bgcolor "#C87F9A" :color "#1F2328" :text-align 'center)) (item :order 1 (box :content "source 4\nsame order" :width '(150) :height 2 :bgcolor "#A95F7C" :color "#FFFFFF" :text-align 'center))) - (spacer :height 1) + (spacer :width '(viewport) :height 1 :bgcolor "#FAF7F0") (box :content "Item sizing: :flex-grow, :flex-shrink, :flex-basis, and child :width\nFlex starts from basis or width/content, then distributes positive or negative space." :padding '(0 (18)) :border "#2F5F7C" @@ -379,9 +379,9 @@ (flex :padding '(0 (12)) :border "#2F5F7C" :border-top-p nil :bgcolor "#F8FCFE" :column-gap '(10) - (item :flex-grow 1 :flex-basis '(120) (box :content "grow 1\nbasis 120" :height 2 :bgcolor "#C7E3F0" :text-align 'center)) - (item :flex-grow 2 :flex-basis '(120) (box :content "grow 2\nbasis 120" :height 2 :bgcolor "#96C7DD" :text-align 'center)) - (item :flex-grow 3 :flex-basis '(120) (box :content "grow 3\nbasis 120" :height 2 :bgcolor "#5FA4C2" :text-align 'center)))) + (item :flex-grow 1 :flex-basis '(120) (box :content "grow 1\nbasis 120" :height 2 :bgcolor "#C7E3F0" :color "#1F2328" :text-align 'center)) + (item :flex-grow 2 :flex-basis '(120) (box :content "grow 2\nbasis 120" :height 2 :bgcolor "#96C7DD" :color "#1F2328" :text-align 'center)) + (item :flex-grow 3 :flex-basis '(120) (box :content "grow 3\nbasis 120" :height 2 :bgcolor "#5FA4C2" :color "#1F2328" :text-align 'center)))) (column (box :content "Shrink factors: overflowing bases lose space by weighted shrink." :padding '(0 (12)) :border "#2F5F7C" :border-top-p nil @@ -389,9 +389,9 @@ (flex :padding '(0 (12)) :border "#2F5F7C" :border-top-p nil :bgcolor "#F8FCFE" :column-gap '(10) - (item :flex-shrink 1 :flex-basis '(320) (box :content "shrink 1\nbasis 320" :height 2 :bgcolor "#C7E3F0" :text-align 'center)) - (item :flex-shrink 3 :flex-basis '(320) (box :content "shrink 3\nbasis 320" :height 2 :bgcolor "#96C7DD" :text-align 'center)) - (item :flex-shrink 5 :flex-basis '(320) (box :content "shrink 5\nbasis 320" :height 2 :bgcolor "#5FA4C2" :text-align 'center)))) + (item :flex-shrink 1 :flex-basis '(320) (box :content "shrink 1\nbasis 320" :height 2 :bgcolor "#C7E3F0" :color "#1F2328" :text-align 'center)) + (item :flex-shrink 3 :flex-basis '(320) (box :content "shrink 3\nbasis 320" :height 2 :bgcolor "#96C7DD" :color "#1F2328" :text-align 'center)) + (item :flex-shrink 5 :flex-basis '(320) (box :content "shrink 5\nbasis 320" :height 2 :bgcolor "#5FA4C2" :color "#1F2328" :text-align 'center)))) (column (box :content "Basis versus width: explicit basis overrides width; auto basis uses width/content." :padding '(0 (12)) :border "#2F5F7C" :border-top-p nil @@ -399,9 +399,9 @@ (flex :padding '(0 (12)) :border "#2F5F7C" :border-top-p nil :bgcolor "#F8FCFE" :column-gap '(10) - (item :flex-basis '(120) (box :content "basis 120\nwidth 240" :width '(240) :height 2 :bgcolor "#C7E3F0" :text-align 'center)) - (item :flex-basis 'auto (box :content "basis auto\nwidth 240" :width '(240) :height 2 :bgcolor "#96C7DD" :text-align 'center)) - (item :flex '(1 1 (160)) (box :content "flex tuple\nbasis 160" :width '(240) :height 2 :bgcolor "#5FA4C2" :text-align 'center)))) + (item :flex-basis '(120) (box :content "basis 120\nwidth 240" :width '(240) :height 2 :bgcolor "#C7E3F0" :color "#1F2328" :text-align 'center)) + (item :flex-basis 'auto (box :content "basis auto\nwidth 240" :width '(240) :height 2 :bgcolor "#96C7DD" :color "#1F2328" :text-align 'center)) + (item :flex '(1 1 (160)) (box :content "flex tuple\nbasis 160" :width '(240) :height 2 :bgcolor "#5FA4C2" :color "#1F2328" :text-align 'center)))) (column (box :content "Intrinsic basis keywords: content, min-content, and max-content derive size from text." :padding '(0 (12)) :border "#2F5F7C" :border-top-p nil @@ -410,13 +410,13 @@ :border-top-p nil :bgcolor "#F8FCFE" :flex-wrap 'wrap :row-gap 1 :column-gap '(10) (item :flex-shrink 0 :flex-basis 'content - (box :content "content\nnatural text" :width '(180) :height 2 :bgcolor "#C7E3F0" :text-align 'center)) + (box :content "content\nnatural text" :width '(180) :height 2 :bgcolor "#C7E3F0" :color "#1F2328" :text-align 'center)) (item :flex-shrink 0 :flex-basis 'min-content - (box :content "min-content\nwrap choices" :width '(180) :height 2 :bgcolor "#96C7DD" :text-align 'center)) + (box :content "min-content\nwrap choices" :width '(180) :height 2 :bgcolor "#96C7DD" :color "#1F2328" :text-align 'center)) (item :flex-shrink 0 :flex-basis 'max-content - (box :content "max-content\nkeeps phrase width" :width '(180) :height 2 :bgcolor "#5FA4C2" :text-align 'center)))) + (box :content "max-content\nkeeps phrase width" :width '(180) :height 2 :bgcolor "#5FA4C2" :color "#1F2328" :text-align 'center)))) - (spacer :height 1) + (spacer :width '(viewport) :height 1 :bgcolor "#FAF7F0") (box :content "Item property: :flex shorthand\nSupported forms: number, none, auto, initial, and (grow shrink basis). Longhands can override shorthand parts." :padding '(0 (18)) :border "#52612F" @@ -424,14 +424,14 @@ (flex :height 7 :padding '(0 (12)) :border "#52612F" :border-top-p nil :bgcolor "#FCFDF6" :flex-wrap 'wrap :row-gap 1 :column-gap '(8) :align-items 'center - (item :flex 1 (box :content ":flex 1\n= 1 1 0" :bgcolor "#DDE8B2" :text-align 'center)) - (item :flex 'none (box :content ":flex none\n= 0 0 auto" :width '(140) :bgcolor "#C5D681" :text-align 'center)) - (item :flex 'auto (box :content ":flex auto\n= 1 1 auto" :width '(140) :bgcolor "#AABE59" :text-align 'center)) - (item :flex 'initial (box :content ":flex initial\n= 0 1 auto" :width '(140) :bgcolor "#8D9E3C" :text-align 'center)) + (item :flex 1 (box :content ":flex 1\n= 1 1 0" :bgcolor "#DDE8B2" :color "#1F2328" :text-align 'center)) + (item :flex 'none (box :content ":flex none\n= 0 0 auto" :width '(140) :bgcolor "#C5D681" :color "#1F2328" :text-align 'center)) + (item :flex 'auto (box :content ":flex auto\n= 1 1 auto" :width '(140) :bgcolor "#AABE59" :color "#1F2328" :text-align 'center)) + (item :flex 'initial (box :content ":flex initial\n= 0 1 auto" :width '(140) :bgcolor "#8D9E3C" :color "#1F2328" :text-align 'center)) (item :flex '(2 1 (120)) :flex-basis '(160) (box :content ":flex (2 1 120)\nthen basis 160" :bgcolor "#66762D" :color "#FFFFFF" :text-align 'center))) - (spacer :height 1) + (spacer :width '(viewport) :height 1 :bgcolor "#FAF7F0") (box :content "Item property: :align-self\nPer-item cross-axis override. auto inherits :align-items; other values replace the container setting." :padding '(0 (18)) :border "#7B4D38" @@ -440,9 +440,9 @@ :border-top-p nil :bgcolor "#FFFAF7" :align-items 'flex-start :flex-wrap 'wrap :row-gap 1 :column-gap '(10) - (item :align-self 'auto (box :content "auto\ninherits start" :width '(118) :height 2 :bgcolor "#EFC7B6" :text-align 'center)) - (item :align-self 'flex-start (box :content "flex-start" :width '(118) :height 2 :bgcolor "#DBA58D" :text-align 'center)) - (item :align-self 'center (box :content "center" :width '(118) :height 2 :bgcolor "#BF7F63" :text-align 'center)) + (item :align-self 'auto (box :content "auto\ninherits start" :width '(118) :height 2 :bgcolor "#EFC7B6" :color "#1F2328" :text-align 'center)) + (item :align-self 'flex-start (box :content "flex-start" :width '(118) :height 2 :bgcolor "#DBA58D" :color "#1F2328" :text-align 'center)) + (item :align-self 'center (box :content "center" :width '(118) :height 2 :bgcolor "#BF7F63" :color "#1F2328" :text-align 'center)) (item :align-self 'flex-end (box :content "flex-end" :width '(118) :height 2 :bgcolor "#9D6048" :color "#FFFFFF" :text-align 'center)) (item :align-self 'stretch (box :content "stretch\nauto cross" :width '(118) :bgcolor "#7B4D38" :color "#FFFFFF" :text-align 'center)) (item :align-self 'normal (box :content "normal\nstretch-like" :width '(118) :bgcolor "#5D3929" :color "#FFFFFF" :text-align 'center))) @@ -450,13 +450,13 @@ :border-top-p nil :bgcolor "#FFFAF7" :align-items 'flex-start :flex-wrap 'wrap :row-gap 1 :column-gap '(10) - (item :align-self 'start (box :content "start" :width '(118) :height 2 :bgcolor "#EFC7B6" :text-align 'center)) - (item :align-self 'end (box :content "end" :width '(118) :height 2 :bgcolor "#DBA58D" :text-align 'center)) - (item :align-self 'self-start (box :content "self-start" :width '(118) :height 2 :bgcolor "#BF7F63" :text-align 'center)) + (item :align-self 'start (box :content "start" :width '(118) :height 2 :bgcolor "#EFC7B6" :color "#1F2328" :text-align 'center)) + (item :align-self 'end (box :content "end" :width '(118) :height 2 :bgcolor "#DBA58D" :color "#1F2328" :text-align 'center)) + (item :align-self 'self-start (box :content "self-start" :width '(118) :height 2 :bgcolor "#BF7F63" :color "#1F2328" :text-align 'center)) (item :align-self 'self-end (box :content "self-end" :width '(118) :height 2 :bgcolor "#9D6048" :color "#FFFFFF" :text-align 'center)) (item :align-self 'baseline (box :content "baseline" :width '(118) :height 2 :bgcolor "#7B4D38" :color "#FFFFFF" :text-align 'center))) - (spacer :height 1) + (spacer :width '(viewport) :height 1 :bgcolor "#FAF7F0") (box :content "Summary\nUse direction and wrap to create lines, basis/width to choose starting sizes, grow/shrink to distribute space, then justify/align properties to pack items and lines." :padding '(1 (24)) :border "#2F3437" diff --git a/examples/grid-reference.ebox b/examples/grid-reference.ebox index dafe3f8..8bd48aa 100644 --- a/examples/grid-reference.ebox +++ b/examples/grid-reference.ebox @@ -7,7 +7,7 @@ :bgcolor "#FFFDF8" :face 'bold :text-align 'center) - (spacer :height 1) + (spacer :width '(720) :height 1 :bgcolor "#FAF7F0") (box :content "01 TRACK SIZING\nFixed pixels, intrinsic auto tracks, and fractional space share one definite canvas." :width '(720) @@ -41,7 +41,7 @@ :color "#28485B" :bgcolor "#D9EAF2" :text-align 'center)) - (spacer :height 1) + (spacer :width '(720) :height 1 :bgcolor "#FAF7F0") (box :content "02 TRACK FUNCTIONS\n`minmax` protects a readable minimum while `repeat` expands a compact template." :width '(720) @@ -91,7 +91,7 @@ :color "#26402F" :bgcolor "#D4E6D7" :text-align 'center)) - (spacer :height 1) + (spacer :width '(720) :height 1 :bgcolor "#FAF7F0") (box :content "03 IMPLICIT TRACKS + AUTO-FLOW\nDeclared tracks establish the map; auto rows, auto columns, and flow fill the rest." :width '(720) @@ -124,7 +124,7 @@ (box :content "AUTO ROW 2 / A" :padding '(0 (8)) :color "#203A4A" :bgcolor "#E5F2F7" :text-align 'center) (box :content "AUTO ROW 2 / B" :padding '(0 (8)) :color "#203A4A" :bgcolor "#D7EAF1" :text-align 'center) (box :content "AUTO ROW 2 / C" :padding '(0 (8)) :color "#203A4A" :bgcolor "#C8E1EB" :text-align 'center)) - (spacer :height 1) + (spacer :width '(720) :height 1 :bgcolor "#FAF7F0") (box :content "COLUMN FLOW · :grid-auto-columns ((220))" :width '(720) :padding '(0 (12)) @@ -147,7 +147,7 @@ (box :content "COL 1 / ROW 2" :padding '(0 (8)) :color "#203A4A" :bgcolor "#C3DFEA" :text-align 'center) (box :content "AUTO COL 2 / ROW 1" :padding '(0 (8)) :color "#203A4A" :bgcolor "#A9D0DE" :text-align 'center) (box :content "AUTO COL 2 / ROW 2" :padding '(0 (8)) :color "#203A4A" :bgcolor "#E5F2F7" :text-align 'center)) - (spacer :height 1) + (spacer :width '(720) :height 1 :bgcolor "#FAF7F0") (box :content "04 PLACEMENT + SPANS\nGrid items can target one-based rows and columns, span tracks, or fall back to auto-placement." :width '(720) @@ -183,7 +183,7 @@ :padding '(0 (8)) :color "#332B4B" :bgcolor "#AFA3D1" :text-align 'center)) (box :content "AUTO\nREMAINDER" :padding '(0 (8)) :color "#332B4B" :bgcolor "#EDE9F6" :text-align 'center)) - (spacer :height 1) + (spacer :width '(720) :height 1 :bgcolor "#FAF7F0") (box :content "05 ITEM ALIGNMENT\n`:justify-items` controls the inline axis; `:align-items` controls the block axis inside each cell." :width '(720) @@ -226,7 +226,7 @@ (box :content "END" :padding '(0 (8)) :color "#513718" :bgcolor "#F3E4C7" :text-align 'center) (box :content "INLINE END" :padding '(0 (8)) :color "#513718" :bgcolor "#EAD2A6" :text-align 'center) (box :content "BLOCK STRETCH" :padding '(0 (8)) :color "#513718" :bgcolor "#E1C18A" :text-align 'center)) - (spacer :height 1) + (spacer :width '(720) :height 1 :bgcolor "#FAF7F0") (box :content "06 CONTENT ALIGNMENT\nWhen tracks do not consume the full canvas, `:justify-content` and `:align-content` distribute the leftover space." :width '(720) @@ -277,7 +277,7 @@ (box :content "EVEN" :padding '(0 (8)) :color "#1E4148" :bgcolor "#B5DDE0" :text-align 'center) (box :content "LY" :padding '(0 (8)) :color "#1E4148" :bgcolor "#9ACED2" :text-align 'center) (box :content "TRACKS" :padding '(0 (8)) :color "#1E4148" :bgcolor "#DDF1F2" :text-align 'center)) - (spacer :height 1) + (spacer :width '(720) :height 1 :bgcolor "#FAF7F0") (box :content "GRID TOOLKIT :grid-template-columns · :grid-template-rows · :grid-auto-columns · :grid-auto-rows · :grid-auto-flow · :gap · :grid-row-gap · :grid-column-gap · :justify-items · :align-items · :justify-content · :align-content · :grid-column · :grid-row · :grid-column-span · :grid-row-span" :width '(720) diff --git a/examples/public-layout-gallery.ebox b/examples/public-layout-gallery.ebox index d798b59..13e43ca 100644 --- a/examples/public-layout-gallery.ebox +++ b/examples/public-layout-gallery.ebox @@ -7,7 +7,7 @@ :bgcolor "#FFFDF8" :face 'bold :text-align 'center) - (spacer :height 1) + (spacer :width '(720) :height 1 :bgcolor "#FAF7F0") (box :content "01 FIXED + FRACTIONAL\nA definite Grid width divides into one exact track and one flexible track." :width '(720) :padding '(0 (16)) @@ -32,7 +32,7 @@ :grid-column '(1 :span 2) :width '(718) :padding '(1 0) :color "#663322" :bgcolor "#FFFDF8" :text-align 'center :wrap-mode 'word)) - (spacer :height 1) + (spacer :width '(720) :height 1 :bgcolor "#FAF7F0") (box :content "02 EXPLICIT PLACEMENT\nSpan columns, target cells, and leave the remaining nodes to auto placement." :width '(720) :padding '(0 (16)) @@ -60,7 +60,7 @@ :text-align 'center :color "#24422D" :bgcolor "#E3F0E5") (box :content "STABLE CELLS" :width '(278) :padding '(1 0) :text-align 'center :color "#24422D" :bgcolor "#D4E6D7")) - (spacer :height 1) + (spacer :width '(720) :height 1 :bgcolor "#FAF7F0") (box :content "03 PUBLIC COMPOSITION\nColumn, Flex, and Grid share the same public node contract." :width '(720) :padding '(0 (16)) @@ -88,7 +88,7 @@ :flex-grow 1 :flex-shrink 1 :flex-basis '(200) :min-width '(180) :padding '(1 (12)) :color "#6B3020" :bgcolor "#F1D4C9")) - (spacer :height 1) + (spacer :width '(720) :height 1 :bgcolor "#FAF7F0") (box :content "PUBLIC CONTRACT ebox-create · ebox-column · ebox-flex · ebox-grid · ebox-spacer" :width '(720) :padding '(0 (16)) diff --git a/tests/ebox-playground-tests.el b/tests/ebox-playground-tests.el index 7ebd254..3dbf182 100644 --- a/tests/ebox-playground-tests.el +++ b/tests/ebox-playground-tests.el @@ -17,6 +17,26 @@ "Return a color from executable DSL property code." "#123456") +(defun ebox-playground-test--boxes (form) + "Return every nested BOX form in FORM." + (when (consp form) + (append (when (eq (car form) 'box) + (list form)) + (cl-mapcan #'ebox-playground-test--boxes form)))) + +(ert-deftest ebox-playground-tinted-content-has-explicit-ink () + "Every tinted content box in the public fixtures should set its text color." + (dolist (file (append ebox-playground-test--fixtures + '("public-layout-gallery.ebox"))) + (let ((form (ebox-playground--read-file + (expand-file-name (concat "examples/" file) + ebox-playground-directory)))) + (dolist (box (ebox-playground-test--boxes form)) + (let ((properties (cdr box))) + (when (and (memq :content properties) + (memq :bgcolor properties)) + (should (memq :color properties)))))))) + (ert-deftest ebox-playground-uses-only-public-layout-apis () "The example should build and render through the public Ebox entry point." (let* ((node (ebox-playground-view)) @@ -53,6 +73,36 @@ (should (stringp text)) (should (cl-every (lambda (width) (<= width 720)) widths)))))) +(ert-deftest ebox-playground-flex-reference-uses-a-compact-default-viewport () + "The public Flex file entry point should use the compact default viewport." + (let ((path (expand-file-name "examples/flex-reference.ebox" + ebox-playground-directory)) + (name " *ebox-playground-flex-viewport-test*")) + (unwind-protect + (progn + (ebox-playground-open-file path name) + (with-current-buffer name + (let ((widths (mapcar #'ebox-string-pixel-width + (ebox-string-lines (buffer-string))))) + (should (cl-every (lambda (width) (<= width 720)) widths))))) + (ebox-playground-close name)))) + +(ert-deftest ebox-playground-fixed-reference-spacers-paint-the-canvas () + "Fixed-width reference separators should keep a continuous canvas surface." + (dolist (file '("grid-reference.ebox" "public-layout-gallery.ebox")) + (let* ((path (expand-file-name (concat "examples/" file) + ebox-playground-directory)) + (lines (ebox-string-lines + (ebox-render (ebox-playground-view path)))) + (separators 0)) + (dolist (line lines) + (when (equal (get-text-property 0 'display line) + '(space :width (720))) + (setq separators (1+ separators)) + (should (equal (get-text-property 0 'face line) + '(:background "#FAF7F0"))))) + (should (> separators 0))))) + (ert-deftest ebox-playground-grid-reference-covers-public-properties () "The Grid reference should name every public Grid property in the fixture." (let ((source (with-temp-buffer