Add a living Prism component gallery

This commit is contained in:
Gabriel Brown
2026-08-18 06:50:32 -04:00
parent 668983e16d
commit 71ee18048e
4 changed files with 452 additions and 0 deletions
+375
View File
@@ -0,0 +1,375 @@
// A living reference for Panama's shared visual language. This deliberately
// renders the production widgets instead of lookalike mock components, so a
// change to a control or Theme token is visible here immediately.
import Quickshell
import QtQuick
import QtQuick.Layouts
import qs.config
import qs.widgets
ShellRoot {
FloatingWindow {
id: galleryWindow
title: "Panama Prism Gallery"
visible: true
implicitWidth: 1120
implicitHeight: 760
minimumSize: Qt.size(920, 640)
color: Theme.bg
Rectangle {
anchors.fill: parent
color: Theme.bg
PrismEdge {
anchors.top: parent.top
anchors.left: parent.left
anchors.right: parent.right
inset: 0
}
RowLayout {
anchors.fill: parent
anchors.margins: 34
spacing: 34
// Quiet editorial rail: enough context to make screenshots
// self-explanatory without competing with the components.
ColumnLayout {
Layout.preferredWidth: 222
Layout.fillHeight: true
spacing: 0
Rectangle {
Layout.preferredWidth: 38
Layout.preferredHeight: 38
radius: 12
color: Theme.alpha(Theme.fg, 0.07)
ThemedIcon {
anchors.centerIn: parent
size: 20
icon: "applications-graphics-symbolic"
tint: Theme.accent
}
}
Text {
Layout.topMargin: 20
text: "PRISM"
color: Theme.fg
font.family: Theme.fontFamily
font.pixelSize: 26
font.weight: Font.DemiBold
font.letterSpacing: 1.4
}
Text {
Layout.topMargin: 5
Layout.maximumWidth: 210
text: "Panama's living interface reference. Calm by default, vivid with purpose."
color: Theme.fgDim
wrapMode: Text.WordWrap
lineHeight: 1.25
font.family: Theme.fontFamily
font.pixelSize: Theme.fontSize
}
Item { Layout.preferredHeight: 36 }
Repeater {
model: [
{ label: "Tokyo Night Moon", color: Theme.bgHighlight },
{ label: "Signal blue", color: Theme.accent },
{ label: "Prism orchid", color: Theme.accentSecondary }
]
RowLayout {
required property var modelData
Layout.topMargin: 10
spacing: 10
Rectangle {
Layout.preferredWidth: 12
Layout.preferredHeight: 12
radius: 6
color: modelData.color
}
Text {
text: modelData.label
color: Theme.fgDim
font.family: Theme.fontFamily
font.pixelSize: Theme.fontSizeSmall
}
}
}
Item { Layout.fillHeight: true }
Text {
text: "REAL COMPONENTS · LIVE TOKENS"
color: Theme.fgMuted
font.family: Theme.fontFamily
font.pixelSize: 10
font.weight: Font.DemiBold
font.letterSpacing: 1.1
}
}
Rectangle {
Layout.fillWidth: true
Layout.fillHeight: true
radius: Theme.popoverRadius
color: Theme.alpha(Theme.bgPopover, Theme.popoverAlpha)
border.width: 1
border.color: Theme.alpha(Theme.fg, 0.08)
PrismEdge {
anchors.top: parent.top
anchors.left: parent.left
anchors.right: parent.right
inset: parent.radius
}
Flickable {
anchors.fill: parent
anchors.margins: 30
contentWidth: width
contentHeight: content.implicitHeight
clip: true
boundsBehavior: Flickable.StopAtBounds
ColumnLayout {
id: content
width: parent.width
spacing: 28
RowLayout {
Layout.fillWidth: true
ColumnLayout {
spacing: 4
Text {
text: "Interface inventory"
color: Theme.fg
font.family: Theme.fontFamily
font.pixelSize: Theme.fontSizeTitle
font.weight: Font.DemiBold
}
Text {
text: "Production controls in their canonical states"
color: Theme.fgDim
font.family: Theme.fontFamily
font.pixelSize: Theme.fontSize
}
}
Item { Layout.fillWidth: true }
Pill {
interactive: false
horizontalPadding: 12
ThemedIcon {
size: 14
icon: "emblem-ok-symbolic"
tint: Theme.green
}
Text {
text: "TOKYO NIGHT MOON"
color: Theme.fgDim
font.family: Theme.fontFamily
font.pixelSize: 10
font.weight: Font.DemiBold
font.letterSpacing: 0.8
}
}
}
ColumnLayout {
Layout.fillWidth: true
spacing: 12
Text {
text: "QUICK CONTROLS"
color: Theme.fgMuted
font.family: Theme.fontFamily
font.pixelSize: 10
font.weight: Font.DemiBold
font.letterSpacing: 1.1
}
RowLayout {
Layout.fillWidth: true
spacing: 12
Toggle {
id: wifiToggle
Layout.fillWidth: true
icon: "network-wireless-signal-excellent-symbolic"
label: "Wi-Fi"
sublabel: active ? "Connected" : "Off"
active: true
onToggled: active = !active
}
Toggle {
id: bluetoothToggle
Layout.fillWidth: true
icon: "bluetooth-active-symbolic"
label: "Bluetooth"
sublabel: active ? "2 devices" : "Off"
active: false
onToggled: active = !active
}
Toggle {
id: focusToggle
Layout.fillWidth: true
icon: "weather-clear-night-symbolic"
label: "Focus"
sublabel: active ? "Until 5:30" : "Available"
active: false
onToggled: active = !active
}
}
}
ColumnLayout {
Layout.fillWidth: true
spacing: 12
Text {
text: "CONTINUOUS VALUES"
color: Theme.fgMuted
font.family: Theme.fontFamily
font.pixelSize: 10
font.weight: Font.DemiBold
font.letterSpacing: 1.1
}
Rectangle {
Layout.fillWidth: true
Layout.preferredHeight: 126
radius: Theme.cardRadius
color: Theme.alpha(Theme.fg, 0.045)
ColumnLayout {
anchors.fill: parent
anchors.margins: 18
spacing: 12
RowLayout {
Layout.fillWidth: true
Text {
text: "System audio"
color: Theme.fg
font.family: Theme.fontFamily
font.pixelSize: Theme.fontSize
font.weight: Font.Medium
}
Item { Layout.fillWidth: true }
Text {
text: Math.round(volumeSlider.value * 100) + "%"
color: Theme.fgDim
font.family: Theme.fontFamily
font.features: Theme.tabularFigures
font.pixelSize: Theme.fontSize
}
}
ValueSlider {
id: volumeSlider
Layout.fillWidth: true
value: 0.68
icon: "audio-volume-high-symbolic"
onMoved: newValue => volumeSlider.value = newValue
}
}
}
}
ColumnLayout {
Layout.fillWidth: true
spacing: 12
Text {
text: "BAR MATERIAL"
color: Theme.fgMuted
font.family: Theme.fontFamily
font.pixelSize: 10
font.weight: Font.DemiBold
font.letterSpacing: 1.1
}
Rectangle {
Layout.fillWidth: true
Layout.preferredHeight: 74
radius: Theme.cardRadius
color: Theme.alpha(Theme.bg, 0.62)
Row {
anchors.centerIn: parent
spacing: 8
Pill {
ThemedIcon {
size: 15
icon: "view-grid-symbolic"
tint: Theme.accent
}
Text {
text: "1 2 3"
color: Theme.fg
font.family: Theme.fontFamily
font.pixelSize: Theme.fontSizeSmall
}
}
Pill {
ThemedIcon {
size: 15
icon: "edit-copy-symbolic"
tint: Theme.fgDim
}
Text {
text: "Clipboard"
color: Theme.fg
font.family: Theme.fontFamily
font.pixelSize: Theme.fontSizeSmall
}
}
Pill {
ThemedIcon {
size: 15
icon: "appointment-soon-symbolic"
tint: Theme.fgDim
}
Text {
text: "Tue Aug 18 · 4:46 AM"
color: Theme.fg
font.family: Theme.fontFamily
font.features: Theme.tabularFigures
font.pixelSize: Theme.fontSizeSmall
}
}
}
}
}
}
}
}
}
}
}
}
+11
View File
@@ -0,0 +1,11 @@
#!/usr/bin/env bash
set -euo pipefail
gallery="${XDG_CONFIG_HOME:-$HOME/.config}/quickshell/prism-gallery.qml"
if qs -p "$gallery" ipc show >/dev/null 2>&1; then
qs -p "$gallery" kill
else
qs -p "$gallery" --daemonize
fi
+26
View File
@@ -0,0 +1,26 @@
# Upstream inspiration
Panama is its own desktop experience, but it should learn from strong open-source work without obscuring where an idea came from. This ledger records upstream projects that materially influence its architecture or interaction design.
## Omarchy
- Project: [basecamp/omarchy](https://github.com/basecamp/omarchy)
- Reviewed revision: `f32ebbdb730c4e8fe11e4046cef4267e466264ea`
- License: MIT, copyright David Heinemeier Hansson
- Local reference at review time: `/home/gib/Documents/Code/Projects/omarchy`
### Adopted ideas, rebuilt for Panama
- `shell/plugins/osd/Osd.qml` and `OsdModel.js`: inspired the separation between a pure presentation model and a single, click-through per-monitor OSD surface. Panama rebuilt the behavior around freedesktop symbolic icons, Tokyo Night Moon tokens, its Prism glass material, Hyprland's focused monitor, and the existing `wpctl`/`brightnessctl`/`playerctl` keybindings.
- `test/shell.d/osd-test.sh` and Omarchy's broader shell contract suite: reinforced Panama's use of fast model and integration contracts alongside live compositor verification.
- Omarchy's small shared visual primitives: reinforced the decision to maintain `prism-gallery.qml`, which renders Panama's production widgets and Theme tokens instead of duplicating mock-only controls.
No Omarchy user-facing layout or styling was transplanted. Panama keeps its GNOME-derived information architecture, Prism material, Tokyo Night Moon palette, app model, and established interaction choices.
### Candidates still under evaluation
- A command palette for shell actions, with Vicinae remaining the application launcher.
- A plugin boundary for optional bar widgets and services once Panama has enough third-party modules to justify one.
- A small first-run health check for missing desktop dependencies and broken service integrations.
These are research directions, not commitments. They should only land when they improve the daily-driver experience without adding visible complexity or parallel configuration systems.
+40
View File
@@ -0,0 +1,40 @@
#!/usr/bin/env bash
set -euo pipefail
repo_dir="$(cd "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)"
gallery="$repo_dir/config/dot/quickshell/prism-gallery.qml"
launcher="$repo_dir/config/dot/quickshell/scripts/panama-prism-gallery"
fail() {
printf 'Prism gallery contract: %s\n' "$1" >&2
exit 1
}
[[ -f "$gallery" ]] || fail 'the real-component gallery is missing'
[[ -x "$launcher" ]] || fail 'the gallery launcher is missing or not executable'
rg -Fq 'import qs.widgets' "$gallery" || fail 'gallery does not use the shared widget module'
for component in Pill Toggle ValueSlider ThemedIcon PrismEdge; do
rg -q "^[[:space:]]*${component}[[:space:]]*\\{" "$gallery" \
|| fail "gallery does not render the real ${component} component"
done
rg -Fq 'title: "Panama Prism Gallery"' "$gallery" \
|| fail 'gallery does not expose a stable compositor window title'
rg -Fq 'FloatingWindow {' "$gallery" \
|| fail 'gallery must be a normal tiled application window'
if rg -q '#[0-9a-fA-F]{3,8}' "$gallery"; then
fail 'gallery hardcodes a colour instead of using the Theme vocabulary'
fi
if rg -q 'loops:[[:space:]]*(Animation\.Infinite|-1)|running:[[:space:]]*true' "$gallery"; then
fail 'gallery contains an always-running animation'
fi
rg -Fq 'qs -p "$gallery" --daemonize' "$launcher" \
|| fail 'launcher does not start the isolated Quickshell gallery config'
rg -Fq 'qs -p "$gallery" kill' "$launcher" \
|| fail 'launcher cannot close an already-open gallery instance'
printf 'Prism gallery contract: PASS\n'