aimeat 1.16.2 → 1.18.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/.env.example +6 -1
- package/dist/locales/en.json +166 -4
- package/dist/locales/fi.json +166 -4
- package/dist/public/components/Card.js +17 -3
- package/dist/public/components/Collapsible.js +39 -0
- package/dist/public/components/CopyButton.js +55 -24
- package/dist/public/components/DataTable.js +57 -0
- package/dist/public/components/EmptyState.js +28 -0
- package/dist/public/components/KeyValueRow.js +37 -0
- package/dist/public/components/Modal.js +22 -5
- package/dist/public/components/Pagination.js +70 -0
- package/dist/public/components/SearchBar.js +44 -0
- package/dist/public/components/StatusDot.js +29 -0
- package/dist/public/components/TagList.js +53 -0
- package/dist/public/components/ToggleSwitch.js +28 -0
- package/dist/public/components/index.js +41 -1
- package/dist/public/css/components/tags.css +24 -0
- package/dist/public/css/style-testbed.css +135 -0
- package/dist/public/css/theme.css +556 -34
- package/dist/public/css/views/admin-agent-integration.css +2 -33
- package/dist/public/css/views/admin.css +730 -686
- package/dist/public/css/views/agents-detail.css +402 -14
- package/dist/public/css/views/help.css +2 -1
- package/dist/public/css/views/hobbies.css +53 -33
- package/dist/public/css/views/marketplace.css +73 -60
- package/dist/public/css/views/openclaw.css +12 -6
- package/dist/public/css/views/portal-classic.css +34 -26
- package/dist/public/css/views/portal-dev.css +41 -32
- package/dist/public/css/views/portal.css +14 -18
- package/dist/public/css/views/profile.css +252 -164
- package/dist/public/css/views/public-knowledge-viewer.css +18 -6
- package/dist/public/css/views/scheduler.css +100 -0
- package/dist/public/js/format.js +41 -0
- package/dist/public/js/services/agent-tasks.js +14 -1
- package/dist/public/js/services/generator-spec-validate.js +5 -1
- package/dist/public/js/services/schedules.js +53 -0
- package/dist/public/js/style-testbed.js +170 -0
- package/dist/public/js/theme.js +114 -0
- package/dist/public/spa.html +74 -16
- package/dist/public/style-testbed.html +420 -0
- package/dist/public/views/admin/agent-integration-tab.js +23 -38
- package/dist/public/views/admin/agent-tasks-tab.js +14 -21
- package/dist/public/views/admin/chat-instances-tab.js +1 -1
- package/dist/public/views/admin/config-tab.js +7 -2
- package/dist/public/views/admin/cortex-tab.js +20 -14
- package/dist/public/views/admin/csm-tab.js +22 -18
- package/dist/public/views/admin/directory-tab.js +3 -3
- package/dist/public/views/admin/email-tab.js +23 -28
- package/dist/public/views/admin/federation-tab.js +15 -5
- package/dist/public/views/admin/generator-debug-tab.js +10 -8
- package/dist/public/views/admin/genesis-tab.js +4 -4
- package/dist/public/views/admin/ghii-tab.js +3 -3
- package/dist/public/views/admin/knowledge-tab.js +15 -5
- package/dist/public/views/admin/matching-tab.js +3 -3
- package/dist/public/views/admin/memory-tab.js +16 -20
- package/dist/public/views/admin/msm-tab.js +30 -17
- package/dist/public/views/admin/overview-tab.js +7 -7
- package/dist/public/views/admin/packages-tab.js +10 -9
- package/dist/public/views/admin/portal-tab.js +14 -4
- package/dist/public/views/admin/prompts-tab.js +5 -5
- package/dist/public/views/admin/push-tab.js +15 -4
- package/dist/public/views/admin/realtime-tab.js +3 -3
- package/dist/public/views/admin/services-tab.js +18 -27
- package/dist/public/views/admin/shared.js +48 -58
- package/dist/public/views/admin/sharing-groups-tab.js +5 -10
- package/dist/public/views/admin/stats-tab.js +3 -3
- package/dist/public/views/guides.js +9 -13
- package/dist/public/views/help.js +3 -24
- package/dist/public/views/hobbies.js +47 -41
- package/dist/public/views/marketplace.js +42 -34
- package/dist/public/views/openclaw.js +0 -1
- package/dist/public/views/portal-classic.js +4 -15
- package/dist/public/views/portal-dev.js +28 -30
- package/dist/public/views/portal.js +16 -21
- package/dist/public/views/portfolio.js +11 -12
- package/dist/public/views/profile/access-tab.js +250 -1
- package/dist/public/views/profile/agents/agent-card.js +75 -4
- package/dist/public/views/profile/agents/tab-activity.js +15 -13
- package/dist/public/views/profile/agents/tab-agent-config.js +60 -6
- package/dist/public/views/profile/agents/tab-integration.js +37 -60
- package/dist/public/views/profile/agents/tab-messages.js +10 -1
- package/dist/public/views/profile/agents/tab-quality.js +25 -19
- package/dist/public/views/profile/agents/tab-schedules.js +110 -0
- package/dist/public/views/profile/agents-activity-subtab.js +4 -4
- package/dist/public/views/profile/agents-services-subtab.js +5 -4
- package/dist/public/views/profile/agents-tab.js +141 -37
- package/dist/public/views/profile/agents-tasks-subtab.js +221 -26
- package/dist/public/views/profile/calibrator-batch.js +5 -11
- package/dist/public/views/profile/calibrator-tab.js +4 -9
- package/dist/public/views/profile/chat-sessions-tab.js +9 -5
- package/dist/public/views/profile/email-tab.js +2 -2
- package/dist/public/views/profile/extensions-tab.js +27 -22
- package/dist/public/views/profile/federation-tab.js +4 -1
- package/dist/public/views/profile/foundry-detail.js +22 -23
- package/dist/public/views/profile/foundry-tab.js +12 -13
- package/dist/public/views/profile/generator-dashboard/DebugPanel.js +4 -7
- package/dist/public/views/profile/generator-dashboard/use-dashboard-core.js +4 -1
- package/dist/public/views/profile/generator-dashboard/use-edit-mode.js +3 -2
- package/dist/public/views/profile/generator-detail.js +26 -30
- package/dist/public/views/profile/generator-tab.js +5 -5
- package/dist/public/views/profile/knowledge-tab.js +12 -12
- package/dist/public/views/profile/landing-page.js +100 -149
- package/dist/public/views/profile/memory-tab.js +15 -11
- package/dist/public/views/profile/node-stats-tab.js +3 -3
- package/dist/public/views/profile/nodes-tab.js +10 -3
- package/dist/public/views/profile/notifications-tab.js +3 -3
- package/dist/public/views/profile/packages-tab.js +14 -14
- package/dist/public/views/profile/scheduler-tab.js +340 -0
- package/dist/public/views/profile/services-tab.js +1 -1
- package/dist/public/views/profile/shared.js +16 -12
- package/dist/public/views/profile/wallet-tab.js +27 -50
- package/dist/public/views/profile/work-tab.js +29 -31
- package/dist/public/views/profile.js +24 -0
- package/dist/public/views/public-knowledge-viewer.js +9 -18
- package/dist/src/auth/middleware.d.ts +3 -2
- package/dist/src/auth/middleware.d.ts.map +1 -1
- package/dist/src/auth/middleware.js +78 -3
- package/dist/src/auth/middleware.js.map +1 -1
- package/dist/src/cli/init-wizard.d.ts.map +1 -1
- package/dist/src/cli/init-wizard.js +13 -1
- package/dist/src/cli/init-wizard.js.map +1 -1
- package/dist/src/config.d.ts +6 -0
- package/dist/src/config.d.ts.map +1 -1
- package/dist/src/config.js +12 -1
- package/dist/src/config.js.map +1 -1
- package/dist/src/generated/api-types.d.ts +708 -8
- package/dist/src/generated/api-types.d.ts.map +1 -1
- package/dist/src/mcp/agent-schedules.d.ts +23 -0
- package/dist/src/mcp/agent-schedules.d.ts.map +1 -0
- package/dist/src/mcp/agent-schedules.js +175 -0
- package/dist/src/mcp/agent-schedules.js.map +1 -0
- package/dist/src/mcp/annotations.d.ts.map +1 -1
- package/dist/src/mcp/annotations.js +6 -0
- package/dist/src/mcp/annotations.js.map +1 -1
- package/dist/src/mcp/catalog/definitions.d.ts.map +1 -1
- package/dist/src/mcp/catalog/definitions.js +55 -0
- package/dist/src/mcp/catalog/definitions.js.map +1 -1
- package/dist/src/mcp/catalog/scopes.d.ts.map +1 -1
- package/dist/src/mcp/catalog/scopes.js +12 -0
- package/dist/src/mcp/catalog/scopes.js.map +1 -1
- package/dist/src/mcp/catalog/surfaces.d.ts.map +1 -1
- package/dist/src/mcp/catalog/surfaces.js +2 -0
- package/dist/src/mcp/catalog/surfaces.js.map +1 -1
- package/dist/src/mcp/index.d.ts.map +1 -1
- package/dist/src/mcp/index.js +2 -0
- package/dist/src/mcp/index.js.map +1 -1
- package/dist/src/models/agent-task-schemas.d.ts +6 -0
- package/dist/src/models/agent-task-schemas.d.ts.map +1 -1
- package/dist/src/models/agent-task-schemas.js +6 -0
- package/dist/src/models/agent-task-schemas.js.map +1 -1
- package/dist/src/models/schemas.d.ts +1 -0
- package/dist/src/models/schemas.d.ts.map +1 -1
- package/dist/src/models/schemas.js +4 -0
- package/dist/src/models/schemas.js.map +1 -1
- package/dist/src/routes/access-tokens.d.ts +17 -0
- package/dist/src/routes/access-tokens.d.ts.map +1 -0
- package/dist/src/routes/access-tokens.js +164 -0
- package/dist/src/routes/access-tokens.js.map +1 -0
- package/dist/src/routes/agent-tasks.d.ts +2 -0
- package/dist/src/routes/agent-tasks.d.ts.map +1 -1
- package/dist/src/routes/agent-tasks.js +118 -23
- package/dist/src/routes/agent-tasks.js.map +1 -1
- package/dist/src/routes/agents.d.ts.map +1 -1
- package/dist/src/routes/agents.js +46 -0
- package/dist/src/routes/agents.js.map +1 -1
- package/dist/src/routes/ai.d.ts +6 -9
- package/dist/src/routes/ai.d.ts.map +1 -1
- package/dist/src/routes/ai.js +26 -175
- package/dist/src/routes/ai.js.map +1 -1
- package/dist/src/routes/apps.d.ts.map +1 -1
- package/dist/src/routes/apps.js +104 -34
- package/dist/src/routes/apps.js.map +1 -1
- package/dist/src/routes/auth.d.ts.map +1 -1
- package/dist/src/routes/auth.js +77 -4
- package/dist/src/routes/auth.js.map +1 -1
- package/dist/src/routes/cortex.d.ts +2 -1
- package/dist/src/routes/cortex.d.ts.map +1 -1
- package/dist/src/routes/cortex.js +13 -8
- package/dist/src/routes/cortex.js.map +1 -1
- package/dist/src/routes/extensions.d.ts.map +1 -1
- package/dist/src/routes/extensions.js +85 -51
- package/dist/src/routes/extensions.js.map +1 -1
- package/dist/src/routes/generator.d.ts.map +1 -1
- package/dist/src/routes/generator.js +109 -43
- package/dist/src/routes/generator.js.map +1 -1
- package/dist/src/routes/ghii.d.ts.map +1 -1
- package/dist/src/routes/ghii.js +34 -13
- package/dist/src/routes/ghii.js.map +1 -1
- package/dist/src/routes/libs.d.ts +15 -0
- package/dist/src/routes/libs.d.ts.map +1 -1
- package/dist/src/routes/libs.js +178 -55
- package/dist/src/routes/libs.js.map +1 -1
- package/dist/src/routes/portal.d.ts.map +1 -1
- package/dist/src/routes/portal.js +1 -0
- package/dist/src/routes/portal.js.map +1 -1
- package/dist/src/routes/schedules.d.ts +33 -0
- package/dist/src/routes/schedules.d.ts.map +1 -0
- package/dist/src/routes/schedules.js +380 -0
- package/dist/src/routes/schedules.js.map +1 -0
- package/dist/src/server-bootstrap/config-init.js +2 -2
- package/dist/src/server-bootstrap/config-init.js.map +1 -1
- package/dist/src/server-bootstrap/routes-loader.d.ts.map +1 -1
- package/dist/src/server-bootstrap/routes-loader.js +7 -0
- package/dist/src/server-bootstrap/routes-loader.js.map +1 -1
- package/dist/src/server-bootstrap/service-init.d.ts.map +1 -1
- package/dist/src/server-bootstrap/service-init.js +2 -1
- package/dist/src/server-bootstrap/service-init.js.map +1 -1
- package/dist/src/services/access-token.d.ts +28 -0
- package/dist/src/services/access-token.d.ts.map +1 -0
- package/dist/src/services/access-token.js +37 -0
- package/dist/src/services/access-token.js.map +1 -0
- package/dist/src/services/ai-completion.d.ts +83 -0
- package/dist/src/services/ai-completion.d.ts.map +1 -0
- package/dist/src/services/ai-completion.js +187 -0
- package/dist/src/services/ai-completion.js.map +1 -0
- package/dist/src/services/config-schema.d.ts.map +1 -1
- package/dist/src/services/config-schema.js +3 -0
- package/dist/src/services/config-schema.js.map +1 -1
- package/dist/src/services/generator-prompt-seeds.d.ts.map +1 -1
- package/dist/src/services/generator-prompt-seeds.js +6 -3
- package/dist/src/services/generator-prompt-seeds.js.map +1 -1
- package/dist/src/services/generator-prompts/spec-validate.d.ts.map +1 -1
- package/dist/src/services/generator-prompts/spec-validate.js +6 -2
- package/dist/src/services/generator-prompts/spec-validate.js.map +1 -1
- package/dist/src/services/generator-registration.d.ts +12 -4
- package/dist/src/services/generator-registration.d.ts.map +1 -1
- package/dist/src/services/generator-registration.js +71 -0
- package/dist/src/services/generator-registration.js.map +1 -1
- package/dist/src/services/generator-validate.d.ts +10 -0
- package/dist/src/services/generator-validate.d.ts.map +1 -1
- package/dist/src/services/generator-validate.js +180 -36
- package/dist/src/services/generator-validate.js.map +1 -1
- package/dist/src/services/owner-session.d.ts +43 -0
- package/dist/src/services/owner-session.d.ts.map +1 -0
- package/dist/src/services/owner-session.js +175 -0
- package/dist/src/services/owner-session.js.map +1 -0
- package/dist/src/services/schedule-constraints.d.ts +65 -0
- package/dist/src/services/schedule-constraints.d.ts.map +1 -0
- package/dist/src/services/schedule-constraints.js +106 -0
- package/dist/src/services/schedule-constraints.js.map +1 -0
- package/dist/src/services/scheduler.d.ts +34 -0
- package/dist/src/services/scheduler.d.ts.map +1 -1
- package/dist/src/services/scheduler.js +266 -22
- package/dist/src/services/scheduler.js.map +1 -1
- package/dist/src/services/skill-bundle/generator.js +19 -0
- package/dist/src/services/skill-bundle/generator.js.map +1 -1
- package/dist/src/storage/interface.d.ts +48 -4
- package/dist/src/storage/interface.d.ts.map +1 -1
- package/dist/src/storage/interface.js.map +1 -1
- package/dist/src/storage/providers/mongodb/index.d.ts +31 -0
- package/dist/src/storage/providers/mongodb/index.d.ts.map +1 -1
- package/dist/src/storage/providers/mongodb/index.js +187 -9
- package/dist/src/storage/providers/mongodb/index.js.map +1 -1
- package/dist/src/storage/providers/sqlite/index.d.ts +31 -0
- package/dist/src/storage/providers/sqlite/index.d.ts.map +1 -1
- package/dist/src/storage/providers/sqlite/index.js +131 -8
- package/dist/src/storage/providers/sqlite/index.js.map +1 -1
- package/dist/src/storage/providers/sqlite/repos/agent-task.d.ts.map +1 -1
- package/dist/src/storage/providers/sqlite/repos/agent-task.js +6 -4
- package/dist/src/storage/providers/sqlite/repos/agent-task.js.map +1 -1
- package/dist/src/storage/providers/sqlite/schema.d.ts.map +1 -1
- package/dist/src/storage/providers/sqlite/schema.js +79 -8
- package/dist/src/storage/providers/sqlite/schema.js.map +1 -1
- package/dist/src/storage/repositories/pat.repository.d.ts +40 -0
- package/dist/src/storage/repositories/pat.repository.d.ts.map +1 -0
- package/dist/src/storage/repositories/pat.repository.js +14 -0
- package/dist/src/storage/repositories/pat.repository.js.map +1 -0
- package/dist/src/storage/repositories/scheduler.repository.d.ts +2 -0
- package/dist/src/storage/repositories/scheduler.repository.d.ts.map +1 -1
- package/dist/src/storage/repositories/session.repository.d.ts +51 -0
- package/dist/src/storage/repositories/session.repository.d.ts.map +1 -1
- package/dist/src/storage/repositories/session.repository.js +12 -0
- package/dist/src/storage/repositories/session.repository.js.map +1 -1
- package/dist/src/utils/env-config.d.ts.map +1 -1
- package/dist/src/utils/env-config.js +25 -1
- package/dist/src/utils/env-config.js.map +1 -1
- package/dist/src/utils/env-validator.d.ts.map +1 -1
- package/dist/src/utils/env-validator.js +4 -0
- package/dist/src/utils/env-validator.js.map +1 -1
- package/package.json +1 -1
- package/prisma/schema.prisma +48 -0
package/dist/public/spa.html
CHANGED
|
@@ -46,6 +46,22 @@
|
|
|
46
46
|
<link rel="icon" href="/favicon.svg" type="image/svg+xml">
|
|
47
47
|
<link rel="manifest" href="/manifest.json">
|
|
48
48
|
<meta name="theme-color" content="#FAFAF8">
|
|
49
|
+
<!-- No-flash theme boot: set data-theme on <html> before first paint.
|
|
50
|
+
Plain inline JS (NOT a module — modules defer and reintroduce the flash).
|
|
51
|
+
Unset key = follow OS until the user makes an explicit choice. -->
|
|
52
|
+
<script>
|
|
53
|
+
(function () {
|
|
54
|
+
try {
|
|
55
|
+
var stored = localStorage.getItem('aimeat-theme'); // 'light' | 'dark' | null
|
|
56
|
+
var theme = (stored === 'light' || stored === 'dark')
|
|
57
|
+
? stored
|
|
58
|
+
: (window.matchMedia && window.matchMedia('(prefers-color-scheme: dark)').matches ? 'dark' : 'light');
|
|
59
|
+
document.documentElement.dataset.theme = theme;
|
|
60
|
+
} catch (e) {
|
|
61
|
+
document.documentElement.dataset.theme = 'light';
|
|
62
|
+
}
|
|
63
|
+
})();
|
|
64
|
+
</script>
|
|
49
65
|
<link href="https://fonts.googleapis.com/css2?family=DM+Sans:ital,opsz,wght@0,9..40,300;0,9..40,400;0,9..40,500;0,9..40,600;0,9..40,700;0,9..40,800&family=JetBrains+Mono:wght@400;500&display=swap" rel="stylesheet">
|
|
50
66
|
<link rel="stylesheet" href="/css/theme.css">
|
|
51
67
|
<!-- View CSS preloaded so they are ready before any view renders (prevents FOUC) -->
|
|
@@ -65,6 +81,7 @@
|
|
|
65
81
|
<link rel="stylesheet" href="/css/views/help.css">
|
|
66
82
|
<link rel="stylesheet" href="/css/views/capabilities.css">
|
|
67
83
|
<link rel="stylesheet" href="/css/views/agents-detail.css">
|
|
84
|
+
<link rel="stylesheet" href="/css/views/scheduler.css">
|
|
68
85
|
<link rel="stylesheet" href="/css/views/admin.css">
|
|
69
86
|
<link rel="stylesheet" href="/css/views/admin-agent-integration.css">
|
|
70
87
|
<link rel="stylesheet" href="/css/views/public-knowledge-viewer.css">
|
|
@@ -75,7 +92,9 @@
|
|
|
75
92
|
"preact/hooks": "/lib/preact-hooks.mjs",
|
|
76
93
|
"htm": "/lib/htm.mjs",
|
|
77
94
|
"/js/i18n.js": "/js/i18n.js",
|
|
95
|
+
"/js/theme.js": "/js/theme.js",
|
|
78
96
|
"/js/utils.js": "/js/utils.js",
|
|
97
|
+
"/js/format.js": "/js/format.js",
|
|
79
98
|
"/js/api.js": "/js/api.js",
|
|
80
99
|
"/js/hooks.js": "/js/hooks.js",
|
|
81
100
|
"/js/services/admin.js": "/js/services/admin.js",
|
|
@@ -142,6 +161,18 @@
|
|
|
142
161
|
"/components/Modal.js": "/components/Modal.js",
|
|
143
162
|
"/components/useViewCSS.js": "/components/useViewCSS.js",
|
|
144
163
|
"/components/Markdown.js": "/components/Markdown.js",
|
|
164
|
+
"/components/CopyButton.js": "/components/CopyButton.js",
|
|
165
|
+
"/components/Spinner.js": "/components/Spinner.js",
|
|
166
|
+
"/components/EmptyState.js": "/components/EmptyState.js",
|
|
167
|
+
"/components/ToggleSwitch.js": "/components/ToggleSwitch.js",
|
|
168
|
+
"/components/Card.js": "/components/Card.js",
|
|
169
|
+
"/components/StatusDot.js": "/components/StatusDot.js",
|
|
170
|
+
"/components/TagList.js": "/components/TagList.js",
|
|
171
|
+
"/components/Pagination.js": "/components/Pagination.js",
|
|
172
|
+
"/components/KeyValueRow.js": "/components/KeyValueRow.js",
|
|
173
|
+
"/components/SearchBar.js": "/components/SearchBar.js",
|
|
174
|
+
"/components/DataTable.js": "/components/DataTable.js",
|
|
175
|
+
"/components/Collapsible.js": "/components/Collapsible.js",
|
|
145
176
|
"/lib/live-updates.js": "/lib/live-updates.js",
|
|
146
177
|
"/lib/minidenticons.min.js": "/lib/minidenticons.min.js",
|
|
147
178
|
"/lib/yaml.mjs": "/lib/yaml.mjs",
|
|
@@ -158,7 +189,8 @@
|
|
|
158
189
|
"/js/services/agent-services.js": "/js/services/agent-services.js",
|
|
159
190
|
"/js/services/agent-messages.js": "/js/services/agent-messages.js",
|
|
160
191
|
"/js/services/agent-integration.js": "/js/services/agent-integration.js",
|
|
161
|
-
"/js/services/admin-agent-integration.js": "/js/services/admin-agent-integration.js"
|
|
192
|
+
"/js/services/admin-agent-integration.js": "/js/services/admin-agent-integration.js",
|
|
193
|
+
"/js/services/schedules.js": "/js/services/schedules.js"
|
|
162
194
|
}
|
|
163
195
|
}
|
|
164
196
|
</script>
|
|
@@ -178,6 +210,7 @@
|
|
|
178
210
|
import { useState, useEffect, useCallback } from 'preact/hooks';
|
|
179
211
|
import htm from 'htm';
|
|
180
212
|
import { loadTranslations, t, getLocale, switchLocale, onLocaleChange } from '/js/i18n.js';
|
|
213
|
+
import { initThemeSystem, getTheme, toggleTheme, onThemeChange } from '/js/theme.js';
|
|
181
214
|
// generateStars no longer needed for light theme
|
|
182
215
|
|
|
183
216
|
const html = htm.bind(h);
|
|
@@ -342,10 +375,26 @@
|
|
|
342
375
|
`;
|
|
343
376
|
}
|
|
344
377
|
|
|
378
|
+
// ── Theme Toggle ──
|
|
379
|
+
// Renders next to the language buttons; flips light <-> dark and persists.
|
|
380
|
+
// Shows a moon in light mode (click → dark) and a sun in dark mode.
|
|
381
|
+
function ThemeToggle() {
|
|
382
|
+
const [theme, setThemeState] = useState(getTheme());
|
|
383
|
+
useEffect(() => onThemeChange((next) => setThemeState(next)), []);
|
|
384
|
+
const isDark = theme === 'dark';
|
|
385
|
+
const label = isDark ? t('nav.themeToLight') : t('nav.themeToDark');
|
|
386
|
+
return html`
|
|
387
|
+
<button class="theme-toggle-btn" onClick=${toggleTheme} title=${label} aria-label=${label}>
|
|
388
|
+
${isDark ? '☀' : '☾'}
|
|
389
|
+
</button>
|
|
390
|
+
`;
|
|
391
|
+
}
|
|
392
|
+
|
|
345
393
|
// ── Header Component ──
|
|
346
394
|
function Header({ navigate, locale }) {
|
|
347
395
|
const [session, setSession] = useState(null);
|
|
348
396
|
const [morsels, setMorsels] = useState(null);
|
|
397
|
+
const [menuOpen, setMenuOpen] = useState(false);
|
|
349
398
|
|
|
350
399
|
// Check auth state
|
|
351
400
|
useEffect(() => {
|
|
@@ -395,23 +444,28 @@
|
|
|
395
444
|
</div>
|
|
396
445
|
|
|
397
446
|
<div class="topnav-right">
|
|
398
|
-
<
|
|
399
|
-
|
|
400
|
-
<
|
|
401
|
-
|
|
402
|
-
<a href="/
|
|
403
|
-
<a href="/v1/
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
${t('nav.admin')}
|
|
447
|
+
<button class="topnav-burger" aria-label="Menu" aria-expanded=${menuOpen ? 'true' : 'false'}
|
|
448
|
+
onClick=${() => setMenuOpen(o => !o)}>☰</button>
|
|
449
|
+
<div class="topnav-menu ${menuOpen ? 'open' : ''}">
|
|
450
|
+
<a href="/v1/classic" onClick=${(e) => { handleNav(e, '/v1/classic'); setMenuOpen(false); }} class="${currentPath === '/v1/classic' ? 'active' : ''}">${t('nav.try')}</a>
|
|
451
|
+
<a href="/v1/portal?view=dev" onClick=${(e) => { handleNav(e, '/v1/portal?view=dev'); setMenuOpen(false); }}>${t('nav.devView')}</a>
|
|
452
|
+
<a href="/v1/help" onClick=${(e) => { handleNav(e, '/v1/help'); setMenuOpen(false); }} class="${currentPath === '/v1/help' ? 'active' : ''}">${t('nav.help')}</a>
|
|
453
|
+
${session && html`
|
|
454
|
+
<a href="/app-catalog.html" target="_blank" onClick=${() => setMenuOpen(false)} class="${currentPath === '/app-catalog.html' ? 'active' : ''}">${t('nav.apps') || 'Apps'}</a>
|
|
455
|
+
<a href="/v1/profile" class="profile-link visible ${currentPath === '/v1/profile' ? 'active' : ''}" onClick=${(e) => { handleNav(e, '/v1/profile'); setMenuOpen(false); }}>
|
|
456
|
+
${t('nav.profile')}
|
|
409
457
|
</a>
|
|
458
|
+
${session.roles && session.roles.includes('operator') && html`
|
|
459
|
+
<a href="/v1/admin" class="${currentPath === '/v1/admin' ? 'active' : ''}" onClick=${(e) => { handleNav(e, '/v1/admin'); setMenuOpen(false); }}>
|
|
460
|
+
${t('nav.admin')}
|
|
461
|
+
</a>
|
|
462
|
+
`}
|
|
410
463
|
`}
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
|
|
464
|
+
<div class="topnav-center">
|
|
465
|
+
<${ThemeToggle} />
|
|
466
|
+
<button class="lang-btn ${locale === 'en' ? 'active' : ''}" onClick=${() => handleLangSwitch('en')}>EN</button>
|
|
467
|
+
<button class="lang-btn ${locale === 'fi' ? 'active' : ''}" onClick=${() => handleLangSwitch('fi')}>FI</button>
|
|
468
|
+
</div>
|
|
415
469
|
</div>
|
|
416
470
|
<span class="header-auth-slot" id="headerAuth"></span>
|
|
417
471
|
</div>
|
|
@@ -424,6 +478,10 @@
|
|
|
424
478
|
// Load translations
|
|
425
479
|
await loadTranslations();
|
|
426
480
|
|
|
481
|
+
// Initialize theme system (head snippet already set the initial theme;
|
|
482
|
+
// this keeps meta in sync and tracks OS preference until an explicit choice).
|
|
483
|
+
initThemeSystem();
|
|
484
|
+
|
|
427
485
|
// Load auth library (served from /v1/libs/aimeat-auth.js)
|
|
428
486
|
await new Promise((resolve) => {
|
|
429
487
|
const script = document.createElement('script');
|
|
@@ -0,0 +1,420 @@
|
|
|
1
|
+
<!doctype html>
|
|
2
|
+
<!--
|
|
3
|
+
@file style-testbed.html
|
|
4
|
+
@description Dev-only style-decision testbed for the frontend component
|
|
5
|
+
unification effort. Renders each duplicated UI primitive (buttons, inputs,
|
|
6
|
+
stat cards) as the CANONICAL theme.css version side-by-side with every
|
|
7
|
+
real prefixed clone (.pf / .mk / .hb / .cl / .dv / .adm), using the actual
|
|
8
|
+
stylesheets so the visual differences are truthful. Each clone has a
|
|
9
|
+
decision dropdown; selections are serialized live into a copyable output
|
|
10
|
+
box so the developer can choose what to keep/change and hand it back.
|
|
11
|
+
Reachable at /style-testbed.html on the dev server. Not part of the app
|
|
12
|
+
nav and not a service — purely an internal decision aid.
|
|
13
|
+
@version-history
|
|
14
|
+
v1.0.0 — 2026-06-02 — Initial testbed (buttons, inputs, stat cards)
|
|
15
|
+
v1.1.0 — 2026-06-02 — Add "Add / merge into canonical" decision option; per-clone
|
|
16
|
+
"maps to" annotations (each variant's canonical equivalent); relabel canonical
|
|
17
|
+
Outline as (= secondary) + add Info variant, so "delete clone" is never lossy.
|
|
18
|
+
-->
|
|
19
|
+
<html lang="en" data-theme="dark">
|
|
20
|
+
<head>
|
|
21
|
+
<meta charset="utf-8" />
|
|
22
|
+
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
|
23
|
+
<meta name="robots" content="noindex" />
|
|
24
|
+
<title>AIMEAT — Style Decision Testbed</title>
|
|
25
|
+
<!-- Real app stylesheets so clones render exactly as they do in the app -->
|
|
26
|
+
<link rel="stylesheet" href="/css/theme.css" />
|
|
27
|
+
<link rel="stylesheet" href="/css/views/profile.css" />
|
|
28
|
+
<link rel="stylesheet" href="/css/views/admin.css" />
|
|
29
|
+
<link rel="stylesheet" href="/css/views/marketplace.css" />
|
|
30
|
+
<link rel="stylesheet" href="/css/views/hobbies.css" />
|
|
31
|
+
<link rel="stylesheet" href="/css/views/portal.css" />
|
|
32
|
+
<link rel="stylesheet" href="/css/views/portal-classic.css" />
|
|
33
|
+
<link rel="stylesheet" href="/css/views/portal-dev.css" />
|
|
34
|
+
<link rel="stylesheet" href="/css/views/agents-detail.css" />
|
|
35
|
+
<link rel="stylesheet" href="/css/views/admin-agent-integration.css" />
|
|
36
|
+
<!-- Testbed's own layout (loaded LAST so stb-* wins on equal specificity) -->
|
|
37
|
+
<link rel="stylesheet" href="/css/style-testbed.css" />
|
|
38
|
+
</head>
|
|
39
|
+
<body class="stb">
|
|
40
|
+
<header class="stb-header">
|
|
41
|
+
<div class="stb-header-row">
|
|
42
|
+
<h1 class="stb-title">AIMEAT — Style Decision Testbed</h1>
|
|
43
|
+
<div class="stb-controls">
|
|
44
|
+
<span class="stb-theme-label">Theme:</span>
|
|
45
|
+
<button class="stb-theme-btn" data-theme-set="light" type="button">☀ Light</button>
|
|
46
|
+
<button class="stb-theme-btn" data-theme-set="dark" type="button">☾ Dark</button>
|
|
47
|
+
</div>
|
|
48
|
+
</div>
|
|
49
|
+
<p class="stb-intro">
|
|
50
|
+
Each row shows the <strong>canonical</strong> <code>theme.css</code> primitive on the left,
|
|
51
|
+
then every real <strong>clone</strong> that currently exists. They use the actual stylesheets,
|
|
52
|
+
so what you see is exactly how each looks in the app. For every clone, pick what to do in its
|
|
53
|
+
dropdown. <strong>Toggle light/dark</strong> to judge both. Your choices appear in the copyable
|
|
54
|
+
box at the bottom — paste it back to me and I'll implement it.
|
|
55
|
+
</p>
|
|
56
|
+
<p class="stb-intro stb-muted">
|
|
57
|
+
Decision options: <em>Use canonical as-is</em> = the clone is a redundant duplicate, delete it; its
|
|
58
|
+
variants already exist in canonical (e.g. a clone's "Secondary" <strong>is</strong> canonical
|
|
59
|
+
<code>.btn-outline</code>) · <em>Add / merge into canonical</em> = this look — or a variant canonical
|
|
60
|
+
doesn't have — is worth keeping, so I fold it into <code>theme.css</code> for every view, then delete the
|
|
61
|
+
clone · <em>Leave separate</em> = no change · <em>Delete (dead)</em> = unused, safe to remove.
|
|
62
|
+
<strong>Nothing is ever lost:</strong> "delete clone" only removes a duplicate whose look already lives in
|
|
63
|
+
canonical — if a clone has something canonical lacks, pick <em>Add / merge into canonical</em>. The
|
|
64
|
+
"maps to" line under each clone shows exactly which canonical class each variant becomes.
|
|
65
|
+
Admin (<code>.adm-*</code>) stays its own design system, consolidated separately.
|
|
66
|
+
</p>
|
|
67
|
+
</header>
|
|
68
|
+
|
|
69
|
+
<main class="stb-main" id="stb-main">
|
|
70
|
+
|
|
71
|
+
<!-- ════════════════════════ BUTTONS ════════════════════════ -->
|
|
72
|
+
<section class="stb-family" data-family="Buttons">
|
|
73
|
+
<h2 class="stb-fam-title">Buttons</h2>
|
|
74
|
+
<p class="stb-fam-desc">
|
|
75
|
+
Canonical primary is a pink-ish gradient (#E8564A→#FF6B6B) with a resting "heart" shadow and
|
|
76
|
+
<code>var(--radius-sm)</code>. The profile override re-skins ~150 buttons app-wide (darker/flatter,
|
|
77
|
+
6px radius, no resting shadow). Marketplace/hobbies/classic/dev each reinvent the set.
|
|
78
|
+
</p>
|
|
79
|
+
|
|
80
|
+
<div class="stb-variant-row">
|
|
81
|
+
<!-- Canonical (reference, no decision) -->
|
|
82
|
+
<div class="stb-variant stb-canonical">
|
|
83
|
+
<div class="stb-variant-head"><span class="stb-vname">Canonical · <code>theme.css .btn-*</code></span><span class="stb-tag stb-ref">reference</span></div>
|
|
84
|
+
<div class="stb-specimens">
|
|
85
|
+
<button class="btn-primary" type="button">Primary</button>
|
|
86
|
+
<button class="btn-outline" type="button">Outline (= secondary)</button>
|
|
87
|
+
<button class="btn-danger-solid" type="button">Danger</button>
|
|
88
|
+
<button class="btn-ghost" type="button">Ghost</button>
|
|
89
|
+
<button class="btn-success" type="button">Success</button>
|
|
90
|
+
<button class="btn-info" type="button">Info</button>
|
|
91
|
+
<button class="btn-primary btn-sm" type="button">Small</button>
|
|
92
|
+
</div>
|
|
93
|
+
<p class="stb-map">Full canonical set: <code>btn-primary</code> · <code>btn-outline</code> (secondary) · <code>btn-danger</code>/<code>btn-danger-solid</code> · <code>btn-ghost</code> · <code>btn-success</code> · <code>btn-info</code> · <code>btn-sm</code></p>
|
|
94
|
+
</div>
|
|
95
|
+
|
|
96
|
+
<!-- Profile .pf .btn-primary -->
|
|
97
|
+
<div class="stb-variant" data-clone=".pf .btn-primary" data-sites="~150">
|
|
98
|
+
<div class="stb-variant-head"><span class="stb-vname">Profile · <code>.pf .btn-primary</code></span><span class="stb-tag stb-warn">~150 sites</span></div>
|
|
99
|
+
<div class="stb-specimens pf stb-scope">
|
|
100
|
+
<button class="btn-primary" type="button">Primary</button>
|
|
101
|
+
<button class="btn-outline" type="button">Outline</button>
|
|
102
|
+
<button class="btn-danger-solid" type="button">Danger</button>
|
|
103
|
+
<button class="btn-ghost" type="button">Ghost</button>
|
|
104
|
+
<button class="btn-success" type="button">Success</button>
|
|
105
|
+
<button class="btn-primary btn-sm" type="button">Small</button>
|
|
106
|
+
</div>
|
|
107
|
+
<p class="stb-diff">darker gradient (→#D4493F) · 6px radius · no resting heart-shadow · 8×16 padding · .85rem</p>
|
|
108
|
+
<p class="stb-map">maps to: every variant already exists in canonical (Primary→<code>btn-primary</code>, Outline→<code>btn-outline</code>, Danger→<code>btn-danger-solid</code>, Ghost→<code>btn-ghost</code>, Success→<code>btn-success</code>, Small→<code>btn-sm</code>). Only the <em>look</em> differs.</p>
|
|
109
|
+
<div class="stb-decide-wrap"></div>
|
|
110
|
+
</div>
|
|
111
|
+
|
|
112
|
+
<!-- Profile pkg-card mini buttons -->
|
|
113
|
+
<div class="stb-variant" data-clone=".pf .pkg-card-actions button.primary / .danger" data-sites="4">
|
|
114
|
+
<div class="stb-variant-head"><span class="stb-vname">Profile pkg-card · <code>button.primary/.danger</code></span><span class="stb-tag">4 sites</span></div>
|
|
115
|
+
<div class="stb-specimens pf stb-scope">
|
|
116
|
+
<div class="pkg-card-actions">
|
|
117
|
+
<button class="primary" type="button">Install</button>
|
|
118
|
+
<button class="danger" type="button">Remove</button>
|
|
119
|
+
</div>
|
|
120
|
+
</div>
|
|
121
|
+
<p class="stb-diff">flat-accent mini pills · bare class names (collision-prone) · danger uses hardcoded rgba(239,68,68) (won't theme-flip)</p>
|
|
122
|
+
<p class="stb-map">maps to: Install→<code>btn-primary btn-sm</code> · Remove→<code>btn-danger-solid btn-sm</code> (same as how the knowledge tab already migrated)</p>
|
|
123
|
+
<div class="stb-decide-wrap"></div>
|
|
124
|
+
</div>
|
|
125
|
+
|
|
126
|
+
<!-- Marketplace -->
|
|
127
|
+
<div class="stb-variant" data-clone=".mk-btn*" data-sites="~7">
|
|
128
|
+
<div class="stb-variant-head"><span class="stb-vname">Marketplace · <code>.mk-btn*</code></span><span class="stb-tag">~7 sites</span></div>
|
|
129
|
+
<div class="stb-specimens">
|
|
130
|
+
<button class="mk-btn mk-btn-primary" type="button">Primary</button>
|
|
131
|
+
<button class="mk-btn mk-btn-secondary" type="button">Secondary</button>
|
|
132
|
+
<button class="mk-btn mk-btn-primary mk-btn-sm" type="button">Small</button>
|
|
133
|
+
</div>
|
|
134
|
+
<p class="stb-diff">gradient 2nd stop #E8564A (not #FF6B6B) · 10px radius · no resting shadow · opacity-fade hover</p>
|
|
135
|
+
<p class="stb-map">maps to: Primary→<code>btn-primary</code> · Secondary→<code>btn-outline</code> · Small→<code>btn-sm</code></p>
|
|
136
|
+
<div class="stb-decide-wrap"></div>
|
|
137
|
+
</div>
|
|
138
|
+
|
|
139
|
+
<!-- Hobbies -->
|
|
140
|
+
<div class="stb-variant" data-clone=".hb-btn*" data-sites="~10">
|
|
141
|
+
<div class="stb-variant-head"><span class="stb-vname">Hobbies · <code>.hb-btn*</code></span><span class="stb-tag">~10 sites</span></div>
|
|
142
|
+
<div class="stb-specimens">
|
|
143
|
+
<button class="hb-btn hb-btn-primary" type="button">Primary</button>
|
|
144
|
+
<button class="hb-btn hb-btn-secondary" type="button">Secondary</button>
|
|
145
|
+
<button class="hb-btn hb-btn-danger hb-btn-sm" type="button">Danger</button>
|
|
146
|
+
</div>
|
|
147
|
+
<p class="stb-diff">near-twin of mk-btn · danger hardcodes #ef4444/rgba(239,68,68) (won't theme-flip)</p>
|
|
148
|
+
<p class="stb-map">maps to: Primary→<code>btn-primary</code> · Secondary→<code>btn-outline</code> · Danger→<code>btn-danger</code> · Small→<code>btn-sm</code></p>
|
|
149
|
+
<div class="stb-decide-wrap"></div>
|
|
150
|
+
</div>
|
|
151
|
+
|
|
152
|
+
<!-- Classic portal -->
|
|
153
|
+
<div class="stb-variant" data-clone=".cl-save-btn / .cl-register-btn / .cl-copy-prompt-btn" data-sites="~4">
|
|
154
|
+
<div class="stb-variant-head"><span class="stb-vname">Classic · <code>.cl-*-btn</code></span><span class="stb-tag">~4 sites</span></div>
|
|
155
|
+
<div class="stb-specimens">
|
|
156
|
+
<button class="cl-save-btn" type="button">Save</button>
|
|
157
|
+
<button class="cl-save-btn cl-register-btn" type="button">Register</button>
|
|
158
|
+
<button class="cl-copy-prompt-btn" type="button">Copy prompt</button>
|
|
159
|
+
</div>
|
|
160
|
+
<p class="stb-diff">heavier 700/.92rem · 10px radius · has a .loading spinner state · register hardcodes #22c55e/#16a34a</p>
|
|
161
|
+
<p class="stb-map stb-map-warn">maps to: Save→<code>btn-primary</code> · Register→<code>btn-success</code> · Copy→<code>btn-primary</code>. ⚠ the <code>.loading</code> spinner state has NO canonical equivalent → pick "Add / merge into canonical" to keep it.</p>
|
|
162
|
+
<div class="stb-decide-wrap"></div>
|
|
163
|
+
</div>
|
|
164
|
+
|
|
165
|
+
<!-- Dev portal -->
|
|
166
|
+
<div class="stb-variant" data-clone=".dv-copy-btn / .dv-upload-btn" data-sites="2">
|
|
167
|
+
<div class="stb-variant-head"><span class="stb-vname">Dev portal · <code>.dv-*-btn</code></span><span class="stb-tag">2 sites</span></div>
|
|
168
|
+
<div class="stb-specimens stb-specimens-relative">
|
|
169
|
+
<button class="dv-upload-btn" type="button">Upload</button>
|
|
170
|
+
<span class="stb-mini-note">(<code>.dv-copy-btn</code> is absolute-positioned; uses the --love gradient palette deliberately)</span>
|
|
171
|
+
</div>
|
|
172
|
+
<p class="stb-diff">uses the separate --love1/2/3 brand palette · .copied state hardcodes #22c55e (won't theme-flip)</p>
|
|
173
|
+
<p class="stb-map">maps to: Upload→<code>btn-primary</code> · Copy→<code>btn-ghost</code>/<code>CopyButton</code>. The --love palette is a deliberate dev-portal identity — "Leave separate" is reasonable here.</p>
|
|
174
|
+
<div class="stb-decide-wrap"></div>
|
|
175
|
+
</div>
|
|
176
|
+
|
|
177
|
+
<!-- Dead kpkg -->
|
|
178
|
+
<div class="stb-variant stb-dead" data-clone=".kpkg-btn*" data-sites="0" data-dead="1">
|
|
179
|
+
<div class="stb-variant-head"><span class="stb-vname">Knowledge · <code>.kpkg-btn*</code></span><span class="stb-tag stb-dead-tag">DEAD · 0 sites</span></div>
|
|
180
|
+
<div class="stb-specimens">
|
|
181
|
+
<button class="kpkg-btn kpkg-btn-primary" type="button">Primary</button>
|
|
182
|
+
<button class="kpkg-btn kpkg-btn-danger" type="button">Danger</button>
|
|
183
|
+
</div>
|
|
184
|
+
<p class="stb-diff">orphaned — nothing renders these (knowledge tab already uses canonical btn-outline/btn-danger-solid). Safe to delete.</p>
|
|
185
|
+
<p class="stb-map">maps to: Primary→<code>btn-outline</code>, Danger→<code>btn-danger-solid</code> (already what the knowledge tab uses). But if you like this flat-indigo look, "Add to canonical" keeps it.</p>
|
|
186
|
+
<div class="stb-decide-wrap"></div>
|
|
187
|
+
</div>
|
|
188
|
+
</div>
|
|
189
|
+
|
|
190
|
+
<label class="stb-note-wrap">Family note: <input class="stb-note" data-note="Buttons" type="text" placeholder="e.g. keep profile's deeper red but adopt canonical radius + shadow" /></label>
|
|
191
|
+
</section>
|
|
192
|
+
|
|
193
|
+
<!-- ════════════════════════ INPUTS ════════════════════════ -->
|
|
194
|
+
<section class="stb-family" data-family="Inputs & form fields">
|
|
195
|
+
<h2 class="stb-fam-title">Inputs & form fields</h2>
|
|
196
|
+
<p class="stb-fam-desc">
|
|
197
|
+
Canonical <code>.input-field</code> is 11×14 padding, 1.5px border, .94rem, <code>var(--radius-sm)</code>, with a
|
|
198
|
+
3px accent focus ring. Profile/marketplace/hobbies each redefine size/border/focus. Labels diverge too
|
|
199
|
+
(canonical is UPPERCASE 600; clones are sentence-case 500).
|
|
200
|
+
</p>
|
|
201
|
+
|
|
202
|
+
<div class="stb-variant-row">
|
|
203
|
+
<!-- Canonical -->
|
|
204
|
+
<div class="stb-variant stb-canonical">
|
|
205
|
+
<div class="stb-variant-head"><span class="stb-vname">Canonical · <code>.input-field</code> + <code>.form-label</code></span><span class="stb-tag stb-ref">reference</span></div>
|
|
206
|
+
<div class="stb-specimens stb-specimens-col">
|
|
207
|
+
<label class="form-label">Label</label>
|
|
208
|
+
<input class="input-field" type="text" placeholder="text input" />
|
|
209
|
+
<textarea class="input-field" rows="2" placeholder="textarea"></textarea>
|
|
210
|
+
<select class="input-field"><option>select option</option></select>
|
|
211
|
+
</div>
|
|
212
|
+
</div>
|
|
213
|
+
|
|
214
|
+
<!-- Profile -->
|
|
215
|
+
<div class="stb-variant" data-clone=".pf .input-field + .pf .form-row label" data-sites="66">
|
|
216
|
+
<div class="stb-variant-head"><span class="stb-vname">Profile · <code>.pf .input-field</code></span><span class="stb-tag stb-warn">66 sites</span></div>
|
|
217
|
+
<div class="stb-specimens stb-specimens-col pf stb-scope">
|
|
218
|
+
<div class="form-row"><label>Label</label></div>
|
|
219
|
+
<input class="input-field" type="text" placeholder="text input" />
|
|
220
|
+
<textarea class="input-field" rows="2" placeholder="textarea"></textarea>
|
|
221
|
+
<select class="input-field"><option>select option</option></select>
|
|
222
|
+
</div>
|
|
223
|
+
<p class="stb-diff">10×14 padding · 10px radius · .85rem · var(--bg-surface) bg · focus ring hardcoded rgba(232,86,74,.1) (won't theme-flip)</p>
|
|
224
|
+
<div class="stb-decide-wrap"></div>
|
|
225
|
+
</div>
|
|
226
|
+
|
|
227
|
+
<!-- Marketplace -->
|
|
228
|
+
<div class="stb-variant" data-clone=".mk-form-input / -textarea / -select / -label" data-sites="~15">
|
|
229
|
+
<div class="stb-variant-head"><span class="stb-vname">Marketplace · <code>.mk-form-*</code></span><span class="stb-tag">~15 sites</span></div>
|
|
230
|
+
<div class="stb-specimens stb-specimens-col">
|
|
231
|
+
<div class="mk-form-group">
|
|
232
|
+
<label class="mk-form-label">Label</label>
|
|
233
|
+
<input class="mk-form-input" type="text" placeholder="text input" />
|
|
234
|
+
</div>
|
|
235
|
+
<textarea class="mk-form-textarea" rows="2" placeholder="textarea"></textarea>
|
|
236
|
+
<select class="mk-form-select"><option>select option</option></select>
|
|
237
|
+
</div>
|
|
238
|
+
<p class="stb-diff">1px border · 10px radius · hardcoded system-ui font (not var(--font)) · NO focus ring · sentence-case label</p>
|
|
239
|
+
<div class="stb-decide-wrap"></div>
|
|
240
|
+
</div>
|
|
241
|
+
|
|
242
|
+
<!-- Hobbies -->
|
|
243
|
+
<div class="stb-variant" data-clone=".hb-form-input / -textarea / -select / -label / -hint" data-sites="~14">
|
|
244
|
+
<div class="stb-variant-head"><span class="stb-vname">Hobbies · <code>.hb-form-*</code></span><span class="stb-tag">~14 sites</span></div>
|
|
245
|
+
<div class="stb-specimens stb-specimens-col">
|
|
246
|
+
<div class="hb-form-group">
|
|
247
|
+
<label class="hb-form-label">Label</label>
|
|
248
|
+
<input class="hb-form-input" type="text" placeholder="text input" />
|
|
249
|
+
<div class="hb-form-hint">helper hint text</div>
|
|
250
|
+
</div>
|
|
251
|
+
<textarea class="hb-form-textarea" rows="2" placeholder="textarea"></textarea>
|
|
252
|
+
<select class="hb-form-select"><option>select option</option></select>
|
|
253
|
+
</div>
|
|
254
|
+
<p class="stb-diff">token-driven (theme-flips) · 1px border · NO focus ring · sentence-case label · has a hint class</p>
|
|
255
|
+
<div class="stb-decide-wrap"></div>
|
|
256
|
+
</div>
|
|
257
|
+
|
|
258
|
+
<!-- pf-input orphan bug -->
|
|
259
|
+
<div class="stb-variant stb-dead" data-clone=".pf-input (email-tab — orphan, no CSS)" data-sites="2" data-dead="1">
|
|
260
|
+
<div class="stb-variant-head"><span class="stb-vname">Profile email · <code>.pf-input</code></span><span class="stb-tag stb-dead-tag">ORPHAN · no rule</span></div>
|
|
261
|
+
<div class="stb-specimens stb-specimens-col pf stb-scope">
|
|
262
|
+
<input class="pf-input" type="email" placeholder="you@example.com (unstyled!)" />
|
|
263
|
+
</div>
|
|
264
|
+
<p class="stb-diff">latent bug: email-tab emits class="pf-input" but NO such rule exists → renders unstyled. Fix → input-field.</p>
|
|
265
|
+
<div class="stb-decide-wrap"></div>
|
|
266
|
+
</div>
|
|
267
|
+
|
|
268
|
+
<!-- Admin reference -->
|
|
269
|
+
<div class="stb-variant stb-admin" data-clone=".adm-input (admin — own system)" data-sites="43" data-admin="1">
|
|
270
|
+
<div class="stb-variant-head"><span class="stb-vname">Admin · <code>.adm-input</code></span><span class="stb-tag stb-admin-tag">admin — separate</span></div>
|
|
271
|
+
<div class="stb-specimens stb-specimens-col adm stb-scope">
|
|
272
|
+
<input class="adm-input adm-input-full" type="text" placeholder="text input" />
|
|
273
|
+
</div>
|
|
274
|
+
<p class="stb-diff">8×12 · 6px radius · indigo focus ring rgba(99,102,241,.15) (different hue, won't theme-flip). Stays admin; consolidate within admin only.</p>
|
|
275
|
+
<div class="stb-decide-wrap"></div>
|
|
276
|
+
</div>
|
|
277
|
+
</div>
|
|
278
|
+
|
|
279
|
+
<label class="stb-note-wrap">Family note: <input class="stb-note" data-note="Inputs" type="text" placeholder="e.g. unify on canonical size but keep sentence-case labels" /></label>
|
|
280
|
+
</section>
|
|
281
|
+
|
|
282
|
+
<!-- ════════════════════════ STAT CARDS ════════════════════════ -->
|
|
283
|
+
<section class="stb-family" data-family="Stat cards">
|
|
284
|
+
<h2 class="stb-fam-title">Stat cards (metric tiles)</h2>
|
|
285
|
+
<p class="stb-fam-desc">
|
|
286
|
+
Canonical <code>.stat-card</code> = centered, neutral bold value over an UPPERCASE muted label.
|
|
287
|
+
9 live clones diverge on size, value color (several tint the number with the accent), label casing,
|
|
288
|
+
and even value/label order (admin + portal render label-first).
|
|
289
|
+
</p>
|
|
290
|
+
|
|
291
|
+
<div class="stb-variant-row stb-variant-row-stats">
|
|
292
|
+
<!-- Canonical -->
|
|
293
|
+
<div class="stb-variant stb-canonical">
|
|
294
|
+
<div class="stb-variant-head"><span class="stb-vname">Canonical · <code>.stat-card</code></span><span class="stb-tag stb-ref">reference</span></div>
|
|
295
|
+
<div class="stb-specimens">
|
|
296
|
+
<div class="stat-card"><div class="stat-card-value">1,284</div><div class="stat-card-label">Members</div></div>
|
|
297
|
+
</div>
|
|
298
|
+
<p class="stb-diff">value-first · 1.35rem/800 neutral · .66rem UPPERCASE label · var(--radius-sm)</p>
|
|
299
|
+
</div>
|
|
300
|
+
|
|
301
|
+
<!-- Marketplace -->
|
|
302
|
+
<div class="stb-variant" data-clone=".mk-stat-card" data-sites="2">
|
|
303
|
+
<div class="stb-variant-head"><span class="stb-vname">Marketplace · <code>.mk-stat-*</code></span><span class="stb-tag">2 sites</span></div>
|
|
304
|
+
<div class="stb-specimens">
|
|
305
|
+
<div class="mk-stat-card"><div class="mk-stat-value">1,284</div><div class="mk-stat-label">Members</div></div>
|
|
306
|
+
</div>
|
|
307
|
+
<p class="stb-diff">value tinted var(--accent) · 1.5rem/700 · 10px radius · sentence-case label · label fallback #6b6b8a</p>
|
|
308
|
+
<p class="stb-map">the accent-tinted value is a variant canonical lacks → "Add / merge into canonical" would add an optional <code>.stat-card-value.accent</code> tone everyone could use.</p>
|
|
309
|
+
<div class="stb-decide-wrap"></div>
|
|
310
|
+
</div>
|
|
311
|
+
|
|
312
|
+
<!-- Hobbies -->
|
|
313
|
+
<div class="stb-variant" data-clone=".hb-stat-card" data-sites="3">
|
|
314
|
+
<div class="stb-variant-head"><span class="stb-vname">Hobbies · <code>.hb-stat-*</code></span><span class="stb-tag">3 sites</span></div>
|
|
315
|
+
<div class="stb-specimens">
|
|
316
|
+
<div class="hb-stat-card"><div class="hb-stat-value">1,284</div><div class="hb-stat-label">Members</div></div>
|
|
317
|
+
</div>
|
|
318
|
+
<p class="stb-diff">near-twin of mk-stat · accent-tinted value · token-driven (theme-flips)</p>
|
|
319
|
+
<div class="stb-decide-wrap"></div>
|
|
320
|
+
</div>
|
|
321
|
+
|
|
322
|
+
<!-- Dev portal -->
|
|
323
|
+
<div class="stb-variant" data-clone=".dv-stat" data-sites="4">
|
|
324
|
+
<div class="stb-variant-head"><span class="stb-vname">Dev portal · <code>.dv-stat</code></span><span class="stb-tag">4 sites</span></div>
|
|
325
|
+
<div class="stb-specimens">
|
|
326
|
+
<div class="dv-stat"><div class="dv-num">1,284</div><div class="dv-label">Members</div></div>
|
|
327
|
+
</div>
|
|
328
|
+
<p class="stb-diff">value var(--love1) brand accent · 1.5rem/700 · flex sizing · 12px radius</p>
|
|
329
|
+
<div class="stb-decide-wrap"></div>
|
|
330
|
+
</div>
|
|
331
|
+
|
|
332
|
+
<!-- Profile node-stats -->
|
|
333
|
+
<div class="stb-variant" data-clone=".pf .card.stat-card + .stat-value/.stat-label" data-sites="~6">
|
|
334
|
+
<div class="stb-variant-head"><span class="stb-vname">Profile node-stats · <code>.stat-value/.stat-label</code></span><span class="stb-tag">~6 sites</span></div>
|
|
335
|
+
<div class="stb-specimens pf stb-scope">
|
|
336
|
+
<div class="card stat-card"><div class="stat-value">1,284</div><div class="stat-label">Members</div></div>
|
|
337
|
+
</div>
|
|
338
|
+
<p class="stb-diff">reuses .stat-card box but reinvents children · value color via INLINE style (theme-bypass)</p>
|
|
339
|
+
<div class="stb-decide-wrap"></div>
|
|
340
|
+
</div>
|
|
341
|
+
|
|
342
|
+
<!-- Profile wallet -->
|
|
343
|
+
<div class="stb-variant" data-clone=".pf .wl-stat + .wl-val/.wl-label" data-sites="4">
|
|
344
|
+
<div class="stb-variant-head"><span class="stb-vname">Profile wallet · <code>.wl-stat</code></span><span class="stb-tag">4 sites</span></div>
|
|
345
|
+
<div class="stb-specimens pf stb-scope">
|
|
346
|
+
<div class="wl-stat"><div class="wl-val wl-val-success">1,284</div><div class="wl-label">Earned</div></div>
|
|
347
|
+
</div>
|
|
348
|
+
<p class="stb-diff">monospace value (numeric alignment) · success/danger tints · label fallback #6B7280</p>
|
|
349
|
+
<p class="stb-map">monospace value + success/danger tints are variants canonical lacks → "Add / merge into canonical" would add <code>.stat-card-value.mono</code> / <code>.success</code> / <code>.danger</code> modifiers.</p>
|
|
350
|
+
<div class="stb-decide-wrap"></div>
|
|
351
|
+
</div>
|
|
352
|
+
|
|
353
|
+
<!-- Agent detail -->
|
|
354
|
+
<div class="stb-variant" data-clone=".pf-agd-stat-card / .agd-stat-card" data-sites="~10">
|
|
355
|
+
<div class="stb-variant-head"><span class="stb-vname">Agent detail · <code>.pf-agd-stat-card</code></span><span class="stb-tag">~10 sites</span></div>
|
|
356
|
+
<div class="stb-specimens pf stb-scope">
|
|
357
|
+
<div class="pf-agd-stat-card"><div class="pf-agd-stat-value">1,284</div><div class="pf-agd-stat-label">Tasks</div></div>
|
|
358
|
+
</div>
|
|
359
|
+
<p class="stb-diff">two aliased prefixes (.agd-/.pf-agd-) · 1.5rem/600 · light-only fallbacks #FFFFFF/#E5E7EB/#1A1A2E</p>
|
|
360
|
+
<div class="stb-decide-wrap"></div>
|
|
361
|
+
</div>
|
|
362
|
+
|
|
363
|
+
<!-- Portal user-world -->
|
|
364
|
+
<div class="stb-variant" data-clone=".user-stat (portal)" data-sites="1">
|
|
365
|
+
<div class="stb-variant-head"><span class="stb-vname">Portal user-world · <code>.user-stat</code></span><span class="stb-tag">1 site</span></div>
|
|
366
|
+
<div class="stb-specimens">
|
|
367
|
+
<div class="user-stat"><div class="user-stat-label">Members</div><div class="user-stat-value">1,284</div></div>
|
|
368
|
+
</div>
|
|
369
|
+
<p class="stb-diff">LABEL-FIRST order · closest to canonical tokens · 1.05rem/700 smaller value</p>
|
|
370
|
+
<div class="stb-decide-wrap"></div>
|
|
371
|
+
</div>
|
|
372
|
+
|
|
373
|
+
<!-- Admin StatsGrid reference -->
|
|
374
|
+
<div class="stb-variant stb-admin" data-clone=".adm-card+.adm-stat (admin StatsGrid)" data-sites="~20 tabs" data-admin="1">
|
|
375
|
+
<div class="stb-variant-head"><span class="stb-vname">Admin StatsGrid · <code>.adm-card/.adm-stat</code></span><span class="stb-tag stb-admin-tag">admin — separate</span></div>
|
|
376
|
+
<div class="stb-specimens adm stb-scope">
|
|
377
|
+
<div class="adm-card"><h2>Members</h2><div class="adm-stat indigo">1,284</div><div class="adm-stat-label">last 24h</div></div>
|
|
378
|
+
</div>
|
|
379
|
+
<p class="stb-diff">LABEL-FIRST · rich 8-tone color system · the de-facto shared component (~20 tabs). Stays admin; consolidate within admin.</p>
|
|
380
|
+
<div class="stb-decide-wrap"></div>
|
|
381
|
+
</div>
|
|
382
|
+
|
|
383
|
+
<!-- Admin agent-integration reference -->
|
|
384
|
+
<div class="stb-variant stb-admin" data-clone=".adm-agi-stat-card (admin AgentIntegration)" data-sites="~6" data-admin="1">
|
|
385
|
+
<div class="stb-variant-head"><span class="stb-vname">Admin AgentIntegration · <code>.adm-agi-stat-*</code></span><span class="stb-tag stb-admin-tag">admin — separate</span></div>
|
|
386
|
+
<div class="stb-specimens adm stb-scope">
|
|
387
|
+
<div class="adm-agi-stat-card"><div class="adm-agi-stat-value adm-agi-stat-value--success">1,284</div><div class="adm-agi-stat-label">Completed</div></div>
|
|
388
|
+
</div>
|
|
389
|
+
<p class="stb-diff">a SECOND admin stat tile (didn't reuse StatsGrid) — fold into the one admin stat component during admin consolidation</p>
|
|
390
|
+
<div class="stb-decide-wrap"></div>
|
|
391
|
+
</div>
|
|
392
|
+
|
|
393
|
+
<!-- Dead profile hero -->
|
|
394
|
+
<div class="stb-variant stb-dead" data-clone=".pf .stat-card .num/.label (profile hero)" data-sites="0" data-dead="1">
|
|
395
|
+
<div class="stb-variant-head"><span class="stb-vname">Profile hero · <code>.stat-card .num/.label</code></span><span class="stb-tag stb-dead-tag">DEAD · 0 sites</span></div>
|
|
396
|
+
<div class="stb-specimens pf stb-scope">
|
|
397
|
+
<div class="stat-card"><div class="num heart">1,284</div><div class="label">Hearts</div></div>
|
|
398
|
+
</div>
|
|
399
|
+
<p class="stb-diff">orphaned hero-strip CSS (heart/blue/purple/mint) — all hardcoded hex, nothing renders it. Safe to delete.</p>
|
|
400
|
+
<div class="stb-decide-wrap"></div>
|
|
401
|
+
</div>
|
|
402
|
+
</div>
|
|
403
|
+
|
|
404
|
+
<label class="stb-note-wrap">Family note: <input class="stb-note" data-note="Stat cards" type="text" placeholder="e.g. one shared component, value-first, neutral value with optional tone+mono modifiers" /></label>
|
|
405
|
+
</section>
|
|
406
|
+
|
|
407
|
+
</main>
|
|
408
|
+
|
|
409
|
+
<!-- ════════════════════════ OUTPUT ════════════════════════ -->
|
|
410
|
+
<footer class="stb-output-bar">
|
|
411
|
+
<div class="stb-output-head">
|
|
412
|
+
<span class="stb-output-title">Your decisions <span class="stb-output-count" id="stb-count"></span></span>
|
|
413
|
+
<button class="stb-copy-btn" id="stb-copy" type="button">Copy to clipboard</button>
|
|
414
|
+
</div>
|
|
415
|
+
<textarea class="stb-output" id="stb-output" readonly rows="10"></textarea>
|
|
416
|
+
</footer>
|
|
417
|
+
|
|
418
|
+
<script src="/js/style-testbed.js"></script>
|
|
419
|
+
</body>
|
|
420
|
+
</html>
|