react-os-shell 2.7.0 → 2.8.1
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/{Browser-YEOBTPST.js → Browser-RNO4KYSE.js} +4 -4
- package/dist/{Browser-YEOBTPST.js.map → Browser-RNO4KYSE.js.map} +1 -1
- package/dist/{Documents-D7UN7W6P.js → Documents-L7CTOPIN.js} +3 -3
- package/dist/{Documents-D7UN7W6P.js.map → Documents-L7CTOPIN.js.map} +1 -1
- package/dist/{Files-VXHZY7NY.js → Files-FJL2BZDI.js} +7 -7
- package/dist/{Files-VXHZY7NY.js.map → Files-FJL2BZDI.js.map} +1 -1
- package/dist/{Notepad-THWCG35G.js → Notepad-2OJ53Q7M.js} +3 -3
- package/dist/{Notepad-THWCG35G.js.map → Notepad-2OJ53Q7M.js.map} +1 -1
- package/dist/Preview-65VPPGWD.js +9 -0
- package/dist/{Preview-5SOLJFFK.js.map → Preview-65VPPGWD.js.map} +1 -1
- package/dist/{Sidebar-BW7SYNBA.js → Sidebar-PY762ANK.js} +3 -3
- package/dist/Sidebar-PY762ANK.js.map +1 -0
- package/dist/{Spreadsheet-UVBEPLQB.js → Spreadsheet-VIYNZ6KJ.js} +4 -4
- package/dist/{Spreadsheet-UVBEPLQB.js.map → Spreadsheet-VIYNZ6KJ.js.map} +1 -1
- package/dist/apps/index.js +12 -12
- package/dist/{chunk-FX77XLQZ.js → chunk-5HXHD62G.js} +4 -4
- package/dist/{chunk-FX77XLQZ.js.map → chunk-5HXHD62G.js.map} +1 -1
- package/dist/{chunk-MJIMKMSJ.js → chunk-IXW6775F.js} +3 -3
- package/dist/{chunk-MJIMKMSJ.js.map → chunk-IXW6775F.js.map} +1 -1
- package/dist/{chunk-AAKIF7SW.js → chunk-V6N2NXHQ.js} +3 -3
- package/dist/{chunk-AAKIF7SW.js.map → chunk-V6N2NXHQ.js.map} +1 -1
- package/dist/{chunk-UATWDGLV.js → chunk-WG3PMYDQ.js} +3 -3
- package/dist/{chunk-UATWDGLV.js.map → chunk-WG3PMYDQ.js.map} +1 -1
- package/dist/{chunk-LD2JBHD3.js → chunk-YQWFKXWH.js} +3 -3
- package/dist/{chunk-LD2JBHD3.js.map → chunk-YQWFKXWH.js.map} +1 -1
- package/dist/{chunk-YZEQWMO5.js → chunk-ZEMXT6BR.js} +4 -4
- package/dist/{chunk-YZEQWMO5.js.map → chunk-ZEMXT6BR.js.map} +1 -1
- package/dist/index.js +99 -64
- package/dist/index.js.map +1 -1
- package/dist/styles.css +187 -2
- package/dist/themes.css +244 -0
- package/package.json +4 -3
- package/dist/Preview-5SOLJFFK.js +0 -9
- package/dist/Sidebar-BW7SYNBA.js.map +0 -1
package/dist/styles.css
CHANGED
|
@@ -18,11 +18,15 @@
|
|
|
18
18
|
* - Status-badge tone-downs (matches the 8 semantic groups in StatusBadge)
|
|
19
19
|
* - Scrollbar styling for editable grids and dark-mode containers
|
|
20
20
|
*
|
|
21
|
-
* Per-theme variants (pink / green / grey / blue
|
|
22
|
-
*
|
|
21
|
+
* Per-theme accent variants (pink / green / grey / blue + custom accent)
|
|
22
|
+
* live in themes.css, imported below so every consumer gets the full set —
|
|
23
|
+
* useTheme() offers all of them in every portal, so the remaps must exist
|
|
24
|
+
* wherever styles.css is loaded. themes.css is also exported standalone
|
|
25
|
+
* ("react-os-shell/themes.css") for consumers that import granularly.
|
|
23
26
|
*/
|
|
24
27
|
|
|
25
28
|
@import "tailwindcss";
|
|
29
|
+
@import "./themes.css";
|
|
26
30
|
|
|
27
31
|
/* Tailwind v4 doesn't scan node_modules by default — tell it to scan this
|
|
28
32
|
package's compiled JS so utility classes used in shell components get
|
|
@@ -212,6 +216,7 @@
|
|
|
212
216
|
[data-theme="dark"] [data-sticky-id] .text-black\/70 { color: rgba(230, 233, 245, 0.92) !important; }
|
|
213
217
|
[data-theme="dark"] [data-sticky-id] .text-black\/30 { color: rgba(230, 233, 245, 0.45) !important; }
|
|
214
218
|
[data-theme="dark"] [data-sticky-id] .text-black\/20 { color: rgba(230, 233, 245, 0.42) !important; }
|
|
219
|
+
[data-theme="dark"] [data-sticky-id] .text-black\/15 { color: rgba(230, 233, 245, 0.35) !important; }
|
|
215
220
|
[data-theme="dark"] [data-sticky-id] .hover\:text-black\/50:hover { color: rgba(230, 233, 245, 0.70) !important; }
|
|
216
221
|
[data-theme="dark"] [data-sticky-id] .placeholder\:text-black\/30::placeholder { color: rgba(230, 233, 245, 0.45) !important; }
|
|
217
222
|
[data-theme="dark"] [data-sticky-id] .bg-black\/10 { background-color: rgba(230, 233, 245, 0.16) !important; }
|
|
@@ -262,6 +267,186 @@
|
|
|
262
267
|
[data-theme="dark"] .bg-orange-100.text-orange-800 { background-color: rgba(249, 115, 22, 0.18) !important; color: #fdba74 !important; }
|
|
263
268
|
[data-theme="dark"] .bg-red-100.text-red-800 { background-color: rgba(239, 68, 68, 0.18) !important; color: #fca5a5 !important; }
|
|
264
269
|
|
|
270
|
+
/* ── Extended dark-mode tint families ────────────────────────────────
|
|
271
|
+
Upstreamed 2026-06-13 from the admin portal's 2026-06-10 audit so all
|
|
272
|
+
consumers share one source of truth. Every hue used by chips/badges
|
|
273
|
+
(tag colors, group colors, status accents, deal stages), notice
|
|
274
|
+
banners, verdict panels, row tints and danger buttons gets the same
|
|
275
|
+
scale as the families above: -50 → 10% tint, -100 → 18%, -200 → ~30%,
|
|
276
|
+
borders -200 → 32% / -300 → 45%, and dark inks flip to the
|
|
277
|
+
-400/-300/-200 light end of their scale.
|
|
278
|
+
Deliberately NOT remapped: game surfaces that read as intentionally
|
|
279
|
+
light (Calculator LCD bg-slate-200/text-slate-600/800, 2048/Chess
|
|
280
|
+
tiles, weather gradients), the Customization theme-preview swatches
|
|
281
|
+
(bg-pink-50/90, bg-green-50/90, bg-blue-50/90, bg-gray-200/90,
|
|
282
|
+
bg-pink-200, bg-green-200 — they must show each theme's real colors),
|
|
283
|
+
and low white/black alphas used as glass highlights on wallpaper. */
|
|
284
|
+
|
|
285
|
+
/* Red */
|
|
286
|
+
[data-theme="dark"] .bg-red-50 { background-color: rgba(239, 68, 68, 0.10) !important; }
|
|
287
|
+
[data-theme="dark"] .hover\:bg-red-50:hover { background-color: rgba(239, 68, 68, 0.16) !important; }
|
|
288
|
+
[data-theme="dark"] .active\:bg-red-50:active { background-color: rgba(239, 68, 68, 0.16) !important; }
|
|
289
|
+
[data-theme="dark"] .bg-red-50\/30 { background-color: rgba(239, 68, 68, 0.06) !important; }
|
|
290
|
+
[data-theme="dark"] .bg-red-50\/50 { background-color: rgba(239, 68, 68, 0.08) !important; }
|
|
291
|
+
[data-theme="dark"] .hover\:bg-red-100:hover { background-color: rgba(239, 68, 68, 0.22) !important; }
|
|
292
|
+
[data-theme="dark"] .border-red-200 { border-color: rgba(239, 68, 68, 0.35) !important; }
|
|
293
|
+
[data-theme="dark"] .border-red-300,
|
|
294
|
+
[data-theme="dark"] .hover\:border-red-300:hover { border-color: rgba(239, 68, 68, 0.45) !important; }
|
|
295
|
+
[data-theme="dark"] .text-red-600,
|
|
296
|
+
[data-theme="dark"] .hover\:text-red-600:hover { color: #f87171 !important; }
|
|
297
|
+
[data-theme="dark"] .hover\:text-red-700:hover { color: #fca5a5 !important; }
|
|
298
|
+
[data-theme="dark"] .text-red-800,
|
|
299
|
+
[data-theme="dark"] .hover\:text-red-800:hover { color: #fecaca !important; }
|
|
300
|
+
[data-theme="dark"] .text-red-900 { color: #fecaca !important; }
|
|
301
|
+
|
|
302
|
+
/* Amber */
|
|
303
|
+
[data-theme="dark"] .bg-amber-50 { background-color: rgba(245, 158, 11, 0.10) !important; }
|
|
304
|
+
[data-theme="dark"] .hover\:bg-amber-50:hover { background-color: rgba(245, 158, 11, 0.14) !important; }
|
|
305
|
+
[data-theme="dark"] .bg-amber-50\/30 { background-color: rgba(245, 158, 11, 0.06) !important; }
|
|
306
|
+
[data-theme="dark"] .bg-amber-50\/40 { background-color: rgba(245, 158, 11, 0.07) !important; }
|
|
307
|
+
[data-theme="dark"] .bg-amber-50\/50 { background-color: rgba(245, 158, 11, 0.08) !important; }
|
|
308
|
+
[data-theme="dark"] .hover\:bg-amber-100:hover { background-color: rgba(245, 158, 11, 0.24) !important; }
|
|
309
|
+
[data-theme="dark"] .bg-amber-200 { background-color: rgba(245, 158, 11, 0.28) !important; }
|
|
310
|
+
[data-theme="dark"] .border-amber-200 { border-color: rgba(245, 158, 11, 0.35) !important; }
|
|
311
|
+
[data-theme="dark"] .border-amber-300,
|
|
312
|
+
[data-theme="dark"] .hover\:border-amber-300:hover { border-color: rgba(245, 158, 11, 0.45) !important; }
|
|
313
|
+
[data-theme="dark"] .text-amber-600,
|
|
314
|
+
[data-theme="dark"] .hover\:text-amber-600:hover { color: #fbbf24 !important; }
|
|
315
|
+
[data-theme="dark"] .text-amber-800 { color: #fde68a !important; }
|
|
316
|
+
[data-theme="dark"] .text-amber-900 { color: #fde68a !important; }
|
|
317
|
+
|
|
318
|
+
/* Yellow */
|
|
319
|
+
[data-theme="dark"] .bg-yellow-50 { background-color: rgba(234, 179, 8, 0.10) !important; }
|
|
320
|
+
[data-theme="dark"] .bg-yellow-50\/50 { background-color: rgba(234, 179, 8, 0.08) !important; }
|
|
321
|
+
[data-theme="dark"] .border-yellow-200 { border-color: rgba(234, 179, 8, 0.35) !important; }
|
|
322
|
+
[data-theme="dark"] .border-yellow-300 { border-color: rgba(234, 179, 8, 0.45) !important; }
|
|
323
|
+
[data-theme="dark"] .text-yellow-600,
|
|
324
|
+
[data-theme="dark"] .hover\:text-yellow-600:hover { color: #facc15 !important; }
|
|
325
|
+
[data-theme="dark"] .text-yellow-900 { color: #fef08a !important; }
|
|
326
|
+
|
|
327
|
+
/* Green / emerald */
|
|
328
|
+
[data-theme="dark"] .bg-green-50 { background-color: rgba(34, 197, 94, 0.10) !important; }
|
|
329
|
+
[data-theme="dark"] .hover\:bg-green-50:hover { background-color: rgba(34, 197, 94, 0.14) !important; }
|
|
330
|
+
[data-theme="dark"] .bg-green-50\/40 { background-color: rgba(34, 197, 94, 0.06) !important; }
|
|
331
|
+
[data-theme="dark"] .border-green-200 { border-color: rgba(34, 197, 94, 0.32) !important; }
|
|
332
|
+
[data-theme="dark"] .border-green-300,
|
|
333
|
+
[data-theme="dark"] .hover\:border-green-300:hover { border-color: rgba(34, 197, 94, 0.45) !important; }
|
|
334
|
+
[data-theme="dark"] .text-green-600,
|
|
335
|
+
[data-theme="dark"] .hover\:text-green-600:hover { color: #4ade80 !important; }
|
|
336
|
+
[data-theme="dark"] .text-green-900,
|
|
337
|
+
[data-theme="dark"] .hover\:text-green-800:hover { color: #bbf7d0 !important; }
|
|
338
|
+
[data-theme="dark"] .bg-emerald-50 { background-color: rgba(16, 185, 129, 0.10) !important; }
|
|
339
|
+
[data-theme="dark"] .hover\:bg-emerald-100:hover { background-color: rgba(16, 185, 129, 0.24) !important; }
|
|
340
|
+
[data-theme="dark"] .border-emerald-200 { border-color: rgba(16, 185, 129, 0.32) !important; }
|
|
341
|
+
[data-theme="dark"] .border-emerald-300 { border-color: rgba(16, 185, 129, 0.45) !important; }
|
|
342
|
+
[data-theme="dark"] .text-emerald-600 { color: #34d399 !important; }
|
|
343
|
+
[data-theme="dark"] .text-emerald-800 { color: #a7f3d0 !important; }
|
|
344
|
+
|
|
345
|
+
/* Orange */
|
|
346
|
+
[data-theme="dark"] .bg-orange-50 { background-color: rgba(249, 115, 22, 0.10) !important; }
|
|
347
|
+
[data-theme="dark"] .hover\:bg-orange-50:hover { background-color: rgba(249, 115, 22, 0.14) !important; }
|
|
348
|
+
[data-theme="dark"] .hover\:bg-orange-200:hover { background-color: rgba(249, 115, 22, 0.30) !important; }
|
|
349
|
+
[data-theme="dark"] .border-orange-200 { border-color: rgba(249, 115, 22, 0.32) !important; }
|
|
350
|
+
[data-theme="dark"] .border-orange-300,
|
|
351
|
+
[data-theme="dark"] .hover\:border-orange-300:hover { border-color: rgba(249, 115, 22, 0.45) !important; }
|
|
352
|
+
[data-theme="dark"] .text-orange-600 { color: #fb923c !important; }
|
|
353
|
+
[data-theme="dark"] .text-orange-900 { color: #fed7aa !important; }
|
|
354
|
+
|
|
355
|
+
/* Sky / teal / cyan */
|
|
356
|
+
[data-theme="dark"] .bg-sky-50 { background-color: rgba(14, 165, 233, 0.10) !important; }
|
|
357
|
+
[data-theme="dark"] .border-sky-300 { border-color: rgba(14, 165, 233, 0.45) !important; }
|
|
358
|
+
[data-theme="dark"] .bg-teal-50 { background-color: rgba(20, 184, 166, 0.10) !important; }
|
|
359
|
+
[data-theme="dark"] .bg-teal-100 { background-color: rgba(20, 184, 166, 0.18) !important; }
|
|
360
|
+
[data-theme="dark"] .text-teal-600 { color: #2dd4bf !important; }
|
|
361
|
+
[data-theme="dark"] .text-teal-700 { color: #5eead4 !important; }
|
|
362
|
+
[data-theme="dark"] .text-teal-800 { color: #99f6e4 !important; }
|
|
363
|
+
[data-theme="dark"] .text-cyan-600 { color: #22d3ee !important; }
|
|
364
|
+
|
|
365
|
+
/* Purple / violet */
|
|
366
|
+
[data-theme="dark"] .bg-purple-50 { background-color: rgba(168, 85, 247, 0.10) !important; }
|
|
367
|
+
[data-theme="dark"] .hover\:bg-purple-50:hover { background-color: rgba(168, 85, 247, 0.14) !important; }
|
|
368
|
+
[data-theme="dark"] .border-purple-200 { border-color: rgba(168, 85, 247, 0.32) !important; }
|
|
369
|
+
[data-theme="dark"] .border-purple-300,
|
|
370
|
+
[data-theme="dark"] .hover\:border-purple-300:hover { border-color: rgba(168, 85, 247, 0.45) !important; }
|
|
371
|
+
[data-theme="dark"] .text-purple-600 { color: #c084fc !important; }
|
|
372
|
+
[data-theme="dark"] .text-purple-800,
|
|
373
|
+
[data-theme="dark"] .text-purple-900 { color: #e9d5ff !important; }
|
|
374
|
+
[data-theme="dark"] .bg-violet-100 { background-color: rgba(139, 92, 246, 0.18) !important; }
|
|
375
|
+
[data-theme="dark"] .border-violet-300 { border-color: rgba(139, 92, 246, 0.45) !important; }
|
|
376
|
+
[data-theme="dark"] .text-violet-800 { color: #ddd6fe !important; }
|
|
377
|
+
|
|
378
|
+
/* Pink / rose */
|
|
379
|
+
[data-theme="dark"] .bg-pink-100 { background-color: rgba(236, 72, 153, 0.18) !important; }
|
|
380
|
+
[data-theme="dark"] .border-pink-200 { border-color: rgba(236, 72, 153, 0.32) !important; }
|
|
381
|
+
[data-theme="dark"] .border-pink-300 { border-color: rgba(236, 72, 153, 0.45) !important; }
|
|
382
|
+
[data-theme="dark"] .text-pink-600 { color: #f472b6 !important; }
|
|
383
|
+
[data-theme="dark"] .text-pink-800,
|
|
384
|
+
[data-theme="dark"] .text-pink-900 { color: #fbcfe8 !important; }
|
|
385
|
+
[data-theme="dark"] .bg-rose-100 { background-color: rgba(244, 63, 94, 0.18) !important; }
|
|
386
|
+
[data-theme="dark"] .text-rose-700 { color: #fda4af !important; }
|
|
387
|
+
[data-theme="dark"] .text-rose-800 { color: #fecdd3 !important; }
|
|
388
|
+
|
|
389
|
+
/* Indigo / slate */
|
|
390
|
+
[data-theme="dark"] .bg-indigo-50 { background-color: rgba(99, 102, 241, 0.15) !important; }
|
|
391
|
+
[data-theme="dark"] .hover\:bg-indigo-100:hover { background-color: rgba(99, 102, 241, 0.25) !important; }
|
|
392
|
+
[data-theme="dark"] .text-indigo-600 { color: #a5b4fc !important; }
|
|
393
|
+
[data-theme="dark"] .border-indigo-300 { border-color: rgba(99, 102, 241, 0.45) !important; }
|
|
394
|
+
[data-theme="dark"] .text-slate-700 { color: #cbd5e1 !important; } /* slate-600/800 left for the Calculator LCD */
|
|
395
|
+
[data-theme="dark"] .border-slate-300 { border-color: rgba(148, 163, 184, 0.35) !important; }
|
|
396
|
+
|
|
397
|
+
/* Blue — gaps beyond the accent remaps above. Hover/active steps sit one
|
|
398
|
+
ladder step above their resting tint (base .26 → active .30; the /30../50
|
|
399
|
+
alpha ladder steps 0.10/0.12/0.15 → hovers 0.12/0.15/0.18). */
|
|
400
|
+
[data-theme="dark"] .bg-blue-200 { background-color: rgba(59, 130, 246, 0.35) !important; }
|
|
401
|
+
[data-theme="dark"] .active\:bg-blue-200:active { background-color: rgba(59, 130, 246, 0.40) !important; }
|
|
402
|
+
[data-theme="dark"] .bg-blue-200\/60 { background-color: rgba(59, 130, 246, 0.20) !important; }
|
|
403
|
+
[data-theme="dark"] .hover\:bg-blue-100:hover { background-color: rgba(59, 130, 246, 0.26) !important; }
|
|
404
|
+
[data-theme="dark"] .active\:bg-blue-50:active { background-color: rgba(59, 130, 246, 0.30) !important; }
|
|
405
|
+
[data-theme="dark"] .hover\:bg-blue-50\/30:hover { background-color: rgba(59, 130, 246, 0.12) !important; }
|
|
406
|
+
[data-theme="dark"] .hover\:bg-blue-50\/40:hover { background-color: rgba(59, 130, 246, 0.15) !important; }
|
|
407
|
+
[data-theme="dark"] .hover\:bg-blue-50\/50:hover { background-color: rgba(59, 130, 246, 0.18) !important; }
|
|
408
|
+
[data-theme="dark"] .border-blue-100 { border-color: rgba(59, 130, 246, 0.22) !important; }
|
|
409
|
+
[data-theme="dark"] .border-blue-200,
|
|
410
|
+
[data-theme="dark"] .hover\:border-blue-200:hover { border-color: rgba(59, 130, 246, 0.32) !important; }
|
|
411
|
+
[data-theme="dark"] .border-blue-300,
|
|
412
|
+
[data-theme="dark"] .hover\:border-blue-300:hover { border-color: rgba(59, 130, 246, 0.45) !important; }
|
|
413
|
+
[data-theme="dark"] .border-blue-300\/50 { border-color: rgba(59, 130, 246, 0.25) !important; }
|
|
414
|
+
[data-theme="dark"] .text-blue-900 { color: #bfdbfe !important; }
|
|
415
|
+
[data-theme="dark"] .hover\:text-blue-600:hover { color: #93c5fd !important; }
|
|
416
|
+
[data-theme="dark"] .hover\:text-blue-800:hover { color: #bfdbfe !important; }
|
|
417
|
+
/* File-input buttons (file: compiles to ::file-selector-button) */
|
|
418
|
+
[data-theme="dark"] .file\:bg-blue-50::file-selector-button { background-color: rgba(59, 130, 246, 0.26) !important; }
|
|
419
|
+
[data-theme="dark"] .file\:text-blue-700::file-selector-button { color: #bfdbfe !important; }
|
|
420
|
+
[data-theme="dark"] .hover\:file\:bg-blue-100:hover::file-selector-button { background-color: rgba(59, 130, 246, 0.26) !important; }
|
|
421
|
+
|
|
422
|
+
/* Gray interaction-state variants (separate class names from the bare remaps) */
|
|
423
|
+
[data-theme="dark"] .hover\:text-gray-600:hover,
|
|
424
|
+
[data-theme="dark"] .hover\:text-gray-700:hover { color: #a6adc8 !important; }
|
|
425
|
+
[data-theme="dark"] .hover\:text-gray-800:hover { color: #bac2de !important; }
|
|
426
|
+
[data-theme="dark"] .hover\:text-gray-900:hover,
|
|
427
|
+
[data-theme="dark"] .active\:text-gray-900:active { color: #cdd6f4 !important; }
|
|
428
|
+
[data-theme="dark"] .active\:bg-gray-100:active { background-color: #313244 !important; }
|
|
429
|
+
[data-theme="dark"] .active\:bg-gray-200:active { background-color: #45475a !important; }
|
|
430
|
+
[data-theme="dark"] .active\:bg-gray-300:active,
|
|
431
|
+
[data-theme="dark"] .hover\:bg-gray-300:hover { background-color: #585b70 !important; }
|
|
432
|
+
[data-theme="dark"] .disabled\:bg-gray-100:disabled { background-color: #1e1e2e !important; }
|
|
433
|
+
[data-theme="dark"] .disabled\:bg-gray-200:disabled { background-color: #313244 !important; }
|
|
434
|
+
[data-theme="dark"] .hover\:bg-gray-200\/50:hover { background-color: rgba(69, 71, 90, 0.5) !important; }
|
|
435
|
+
[data-theme="dark"] .even\:bg-gray-50\/50:nth-child(even) { background-color: rgba(24, 24, 37, 0.5) !important; }
|
|
436
|
+
[data-theme="dark"] .border-gray-50,
|
|
437
|
+
[data-theme="dark"] .divide-gray-50 > :not(:last-child) { border-color: #2a2a3c !important; }
|
|
438
|
+
[data-theme="dark"] .border-gray-200\/50 { border-color: rgba(49, 50, 68, 0.6) !important; }
|
|
439
|
+
[data-theme="dark"] .hover\:border-gray-200:hover { border-color: #313244 !important; }
|
|
440
|
+
[data-theme="dark"] .hover\:border-gray-300:hover { border-color: #45475a !important; }
|
|
441
|
+
|
|
442
|
+
/* White panel surfaces / solid black ink. hover-to-white means "emphasize",
|
|
443
|
+
which on dark glass means a solid panel tint; hover-to-black ink flips to
|
|
444
|
+
brighter, not darker (e.g. the taskbar bell). */
|
|
445
|
+
[data-theme="dark"] .bg-white\/85 { background-color: rgba(30, 30, 46, 0.85) !important; }
|
|
446
|
+
[data-theme="dark"] .hover\:bg-white:hover { background-color: #1e1e2e !important; }
|
|
447
|
+
[data-theme="dark"] .text-black { color: #cdd6f4 !important; }
|
|
448
|
+
[data-theme="dark"] .hover\:text-black:hover { color: #ffffff !important; }
|
|
449
|
+
|
|
265
450
|
/* Scrollbar */
|
|
266
451
|
/* Force visible scrollbars on editable grids (macOS hides them by default) */
|
|
267
452
|
.grid-scroll::-webkit-scrollbar { width: 10px; height: 10px; }
|
package/dist/themes.css
ADDED
|
@@ -0,0 +1,244 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* react-os-shell theme variants — accent + surface-tint remaps for the
|
|
3
|
+
* pink / green / grey / blue themes and the user-picked custom accent.
|
|
4
|
+
*
|
|
5
|
+
* useTheme() stamps `data-theme="<name>"` on <html> and, when the user
|
|
6
|
+
* picks a custom accent color, `data-custom-accent` plus the --accent-*
|
|
7
|
+
* shade scale. This file turns those attributes into looks by remapping
|
|
8
|
+
* the blue accent utilities (bg-blue-600 buttons, text-blue-700 links,
|
|
9
|
+
* focus rings, checkbox accents) and tinting the neutral gray surfaces.
|
|
10
|
+
*
|
|
11
|
+
* styles.css imports this file, so plain `import 'react-os-shell/styles.css'`
|
|
12
|
+
* already includes it. It is exported standalone ("react-os-shell/themes.css")
|
|
13
|
+
* only for consumers that build their CSS granularly.
|
|
14
|
+
*
|
|
15
|
+
* Dark-theme remaps are NOT here — they live in styles.css, because dark
|
|
16
|
+
* is a readability baseline rather than an accent variant.
|
|
17
|
+
*
|
|
18
|
+
* Upstreamed 2026-06-13 from the admin portal's index.css so all three
|
|
19
|
+
* EFFICIENT portals + the demo share one source of truth.
|
|
20
|
+
*/
|
|
21
|
+
|
|
22
|
+
/* ═══════════════════════════════════════════════════
|
|
23
|
+
Theme: Pink
|
|
24
|
+
Swaps the blue accent to pink/rose throughout
|
|
25
|
+
═══════════════════════════════════════════════════ */
|
|
26
|
+
|
|
27
|
+
/* Accent backgrounds */
|
|
28
|
+
[data-theme="pink"] .bg-blue-600 { background-color: #db2777 !important; }
|
|
29
|
+
[data-theme="pink"] .bg-blue-700 { background-color: #be185d !important; }
|
|
30
|
+
[data-theme="pink"] .bg-blue-500 { background-color: #ec4899 !important; }
|
|
31
|
+
[data-theme="pink"] .bg-blue-100 { background-color: #fce7f3 !important; }
|
|
32
|
+
[data-theme="pink"] .bg-blue-50 { background-color: #fdf2f8 !important; }
|
|
33
|
+
|
|
34
|
+
/* Accent text */
|
|
35
|
+
[data-theme="pink"] .text-blue-600 { color: #db2777 !important; }
|
|
36
|
+
[data-theme="pink"] .text-blue-700 { color: #be185d !important; }
|
|
37
|
+
[data-theme="pink"] .text-blue-800 { color: #9d174d !important; }
|
|
38
|
+
[data-theme="pink"] .text-blue-500 { color: #ec4899 !important; }
|
|
39
|
+
|
|
40
|
+
/* Accent borders */
|
|
41
|
+
[data-theme="pink"] .border-blue-600 { border-color: #db2777 !important; }
|
|
42
|
+
[data-theme="pink"] .border-blue-500 { border-color: #ec4899 !important; }
|
|
43
|
+
[data-theme="pink"] .border-blue-400 { border-color: #f472b6 !important; }
|
|
44
|
+
[data-theme="pink"] .border-blue-300 { border-color: #f9a8d4 !important; }
|
|
45
|
+
[data-theme="pink"] .border-blue-200 { border-color: #fbcfe8 !important; }
|
|
46
|
+
|
|
47
|
+
/* Accent hover */
|
|
48
|
+
[data-theme="pink"] .hover\:bg-blue-700:hover { background-color: #be185d !important; }
|
|
49
|
+
[data-theme="pink"] .hover\:bg-blue-100:hover { background-color: #fce7f3 !important; }
|
|
50
|
+
[data-theme="pink"] .hover\:bg-blue-50:hover { background-color: #fdf2f8 !important; }
|
|
51
|
+
[data-theme="pink"] .hover\:text-blue-800:hover { color: #9d174d !important; }
|
|
52
|
+
[data-theme="pink"] .hover\:border-blue-300:hover { border-color: #f9a8d4 !important; }
|
|
53
|
+
|
|
54
|
+
/* Focus rings */
|
|
55
|
+
[data-theme="pink"] .focus\:border-blue-500:focus { border-color: #ec4899 !important; }
|
|
56
|
+
[data-theme="pink"] .focus\:ring-blue-500:focus { --tw-ring-color: #ec4899 !important; }
|
|
57
|
+
|
|
58
|
+
/* Checkbox accent */
|
|
59
|
+
[data-theme="pink"] input[type="checkbox"].text-blue-600 { accent-color: #db2777; }
|
|
60
|
+
[data-theme="pink"] input[type="range"].accent-blue-600 { accent-color: #db2777; }
|
|
61
|
+
|
|
62
|
+
/* Ring colors */
|
|
63
|
+
[data-theme="pink"] .ring-blue-300 { --tw-ring-color: #f9a8d4 !important; }
|
|
64
|
+
|
|
65
|
+
/* Pink tint on backgrounds */
|
|
66
|
+
[data-theme="pink"] .bg-white { background-color: #fff5f9 !important; }
|
|
67
|
+
[data-theme="pink"] .bg-gray-100 { background-color: #fce7f3 !important; }
|
|
68
|
+
[data-theme="pink"] .bg-gray-50 { background-color: #fdf2f8 !important; }
|
|
69
|
+
[data-theme="pink"] .bg-gray-200 { background-color: #fbcfe8 !important; }
|
|
70
|
+
|
|
71
|
+
/* Pink tint on borders — kept light to distinguish from accent */
|
|
72
|
+
[data-theme="pink"] .border-gray-200 { border-color: #fce7f3 !important; }
|
|
73
|
+
[data-theme="pink"] .border-gray-300 { border-color: #fbcfe8 !important; }
|
|
74
|
+
[data-theme="pink"] .border-gray-100 { border-color: #fdf2f8 !important; }
|
|
75
|
+
[data-theme="pink"] .divide-gray-200 > :not(:last-child) { border-color: #fce7f3 !important; }
|
|
76
|
+
[data-theme="pink"] .divide-gray-100 > :not(:last-child) { border-color: #fdf2f8 !important; }
|
|
77
|
+
|
|
78
|
+
/* Pink hover states */
|
|
79
|
+
[data-theme="pink"] .hover\:bg-gray-50:hover { background-color: #fdf2f8 !important; }
|
|
80
|
+
[data-theme="pink"] .hover\:bg-gray-100:hover { background-color: #fce7f3 !important; }
|
|
81
|
+
[data-theme="pink"] .hover\:bg-gray-200:hover { background-color: #fbcfe8 !important; }
|
|
82
|
+
|
|
83
|
+
|
|
84
|
+
/* ═══════════════════════════════════════════════════
|
|
85
|
+
Theme: Green
|
|
86
|
+
Swaps the blue accent to green/emerald throughout
|
|
87
|
+
═══════════════════════════════════════════════════ */
|
|
88
|
+
|
|
89
|
+
/* Accent backgrounds */
|
|
90
|
+
[data-theme="green"] .bg-blue-600 { background-color: #059669 !important; }
|
|
91
|
+
[data-theme="green"] .bg-blue-700 { background-color: #047857 !important; }
|
|
92
|
+
[data-theme="green"] .bg-blue-500 { background-color: #10b981 !important; }
|
|
93
|
+
[data-theme="green"] .bg-blue-100 { background-color: #d1fae5 !important; }
|
|
94
|
+
[data-theme="green"] .bg-blue-50 { background-color: #ecfdf5 !important; }
|
|
95
|
+
|
|
96
|
+
/* Accent text */
|
|
97
|
+
[data-theme="green"] .text-blue-600 { color: #059669 !important; }
|
|
98
|
+
[data-theme="green"] .text-blue-700 { color: #047857 !important; }
|
|
99
|
+
[data-theme="green"] .text-blue-800 { color: #065f46 !important; }
|
|
100
|
+
[data-theme="green"] .text-blue-500 { color: #10b981 !important; }
|
|
101
|
+
|
|
102
|
+
/* Accent borders */
|
|
103
|
+
[data-theme="green"] .border-blue-600 { border-color: #059669 !important; }
|
|
104
|
+
[data-theme="green"] .border-blue-500 { border-color: #10b981 !important; }
|
|
105
|
+
[data-theme="green"] .border-blue-400 { border-color: #34d399 !important; }
|
|
106
|
+
[data-theme="green"] .border-blue-300 { border-color: #6ee7b7 !important; }
|
|
107
|
+
[data-theme="green"] .border-blue-200 { border-color: #a7f3d0 !important; }
|
|
108
|
+
|
|
109
|
+
/* Accent hover */
|
|
110
|
+
[data-theme="green"] .hover\:bg-blue-700:hover { background-color: #047857 !important; }
|
|
111
|
+
[data-theme="green"] .hover\:bg-blue-100:hover { background-color: #d1fae5 !important; }
|
|
112
|
+
[data-theme="green"] .hover\:bg-blue-50:hover { background-color: #ecfdf5 !important; }
|
|
113
|
+
[data-theme="green"] .hover\:text-blue-800:hover { color: #065f46 !important; }
|
|
114
|
+
[data-theme="green"] .hover\:border-blue-300:hover { border-color: #6ee7b7 !important; }
|
|
115
|
+
|
|
116
|
+
/* Focus rings */
|
|
117
|
+
[data-theme="green"] .focus\:border-blue-500:focus { border-color: #10b981 !important; }
|
|
118
|
+
[data-theme="green"] .focus\:ring-blue-500:focus { --tw-ring-color: #10b981 !important; }
|
|
119
|
+
|
|
120
|
+
/* Checkbox accent */
|
|
121
|
+
[data-theme="green"] input[type="checkbox"].text-blue-600 { accent-color: #059669; }
|
|
122
|
+
[data-theme="green"] input[type="range"].accent-blue-600 { accent-color: #059669; }
|
|
123
|
+
|
|
124
|
+
/* Ring colors */
|
|
125
|
+
[data-theme="green"] .ring-blue-300 { --tw-ring-color: #6ee7b7 !important; }
|
|
126
|
+
|
|
127
|
+
/* Green tint on backgrounds */
|
|
128
|
+
[data-theme="green"] .bg-white { background-color: #f5fef7 !important; }
|
|
129
|
+
[data-theme="green"] .bg-gray-100 { background-color: #dcfce7 !important; }
|
|
130
|
+
[data-theme="green"] .bg-gray-50 { background-color: #ecfdf5 !important; }
|
|
131
|
+
[data-theme="green"] .bg-gray-200 { background-color: #bbf7d0 !important; }
|
|
132
|
+
|
|
133
|
+
/* Green tint on borders — kept light to distinguish from accent */
|
|
134
|
+
[data-theme="green"] .border-gray-200 { border-color: #dcfce7 !important; }
|
|
135
|
+
[data-theme="green"] .border-gray-300 { border-color: #bbf7d0 !important; }
|
|
136
|
+
[data-theme="green"] .border-gray-100 { border-color: #ecfdf5 !important; }
|
|
137
|
+
[data-theme="green"] .divide-gray-200 > :not(:last-child) { border-color: #dcfce7 !important; }
|
|
138
|
+
[data-theme="green"] .divide-gray-100 > :not(:last-child) { border-color: #ecfdf5 !important; }
|
|
139
|
+
|
|
140
|
+
/* Green hover states */
|
|
141
|
+
[data-theme="green"] .hover\:bg-gray-50:hover { background-color: #ecfdf5 !important; }
|
|
142
|
+
[data-theme="green"] .hover\:bg-gray-100:hover { background-color: #dcfce7 !important; }
|
|
143
|
+
[data-theme="green"] .hover\:bg-gray-200:hover { background-color: #bbf7d0 !important; }
|
|
144
|
+
|
|
145
|
+
|
|
146
|
+
/* ═══════════════════════════════════════════════════
|
|
147
|
+
Theme: Grey
|
|
148
|
+
A darker, more contrasty neutral theme
|
|
149
|
+
═══════════════════════════════════════════════════ */
|
|
150
|
+
|
|
151
|
+
/* Grey tint on backgrounds */
|
|
152
|
+
[data-theme="grey"] .bg-white { background-color: #f3f4f6 !important; }
|
|
153
|
+
[data-theme="grey"] .bg-gray-100 { background-color: #e5e7eb !important; }
|
|
154
|
+
[data-theme="grey"] .bg-gray-50 { background-color: #f3f4f6 !important; }
|
|
155
|
+
[data-theme="grey"] .bg-gray-200 { background-color: #d1d5db !important; }
|
|
156
|
+
|
|
157
|
+
/* Grey tint on borders */
|
|
158
|
+
[data-theme="grey"] .border-gray-200 { border-color: #d1d5db !important; }
|
|
159
|
+
[data-theme="grey"] .border-gray-300 { border-color: #9ca3af !important; }
|
|
160
|
+
[data-theme="grey"] .border-gray-100 { border-color: #e5e7eb !important; }
|
|
161
|
+
[data-theme="grey"] .divide-gray-200 > :not(:last-child) { border-color: #d1d5db !important; }
|
|
162
|
+
[data-theme="grey"] .divide-gray-100 > :not(:last-child) { border-color: #e5e7eb !important; }
|
|
163
|
+
|
|
164
|
+
/* Grey hover states */
|
|
165
|
+
[data-theme="grey"] .hover\:bg-gray-50:hover { background-color: #e5e7eb !important; }
|
|
166
|
+
[data-theme="grey"] .hover\:bg-gray-100:hover { background-color: #d1d5db !important; }
|
|
167
|
+
[data-theme="grey"] .hover\:bg-gray-200:hover { background-color: #9ca3af !important; }
|
|
168
|
+
|
|
169
|
+
/* Grey accent — dark gray buttons */
|
|
170
|
+
[data-theme="grey"] .bg-blue-600 { background-color: #374151 !important; }
|
|
171
|
+
[data-theme="grey"] .bg-blue-700 { background-color: #1f2937 !important; }
|
|
172
|
+
[data-theme="grey"] .bg-blue-500 { background-color: #4b5563 !important; }
|
|
173
|
+
[data-theme="grey"] .bg-blue-100 { background-color: #e5e7eb !important; }
|
|
174
|
+
[data-theme="grey"] .bg-blue-50 { background-color: #f3f4f6 !important; }
|
|
175
|
+
[data-theme="grey"] .text-blue-600 { color: #374151 !important; }
|
|
176
|
+
[data-theme="grey"] .text-blue-700 { color: #1f2937 !important; }
|
|
177
|
+
[data-theme="grey"] .text-blue-800 { color: #111827 !important; }
|
|
178
|
+
[data-theme="grey"] .text-blue-500 { color: #4b5563 !important; }
|
|
179
|
+
[data-theme="grey"] .border-blue-600 { border-color: #374151 !important; }
|
|
180
|
+
[data-theme="grey"] .border-blue-500 { border-color: #4b5563 !important; }
|
|
181
|
+
[data-theme="grey"] .border-blue-400 { border-color: #6b7280 !important; }
|
|
182
|
+
[data-theme="grey"] .border-blue-300 { border-color: #9ca3af !important; }
|
|
183
|
+
[data-theme="grey"] .border-blue-200 { border-color: #d1d5db !important; }
|
|
184
|
+
[data-theme="grey"] .hover\:bg-blue-700:hover { background-color: #1f2937 !important; }
|
|
185
|
+
[data-theme="grey"] .hover\:bg-blue-100:hover { background-color: #e5e7eb !important; }
|
|
186
|
+
[data-theme="grey"] .hover\:bg-blue-50:hover { background-color: #f3f4f6 !important; }
|
|
187
|
+
[data-theme="grey"] .focus\:border-blue-500:focus { border-color: #4b5563 !important; }
|
|
188
|
+
[data-theme="grey"] .focus\:ring-blue-500:focus { --tw-ring-color: #4b5563 !important; }
|
|
189
|
+
[data-theme="grey"] input[type="checkbox"].text-blue-600 { accent-color: #374151; }
|
|
190
|
+
[data-theme="grey"] input[type="range"].accent-blue-600 { accent-color: #374151; }
|
|
191
|
+
[data-theme="grey"] .ring-blue-300 { --tw-ring-color: #9ca3af !important; }
|
|
192
|
+
|
|
193
|
+
|
|
194
|
+
/* ═══════════════════════════════════════════════════
|
|
195
|
+
Theme: Blue
|
|
196
|
+
Swaps the blue accent to a deeper blue, tints UI blue
|
|
197
|
+
═══════════════════════════════════════════════════ */
|
|
198
|
+
|
|
199
|
+
/* Blue tint on backgrounds */
|
|
200
|
+
[data-theme="blue"] .bg-white { background-color: #f0f6ff !important; }
|
|
201
|
+
[data-theme="blue"] .bg-gray-100 { background-color: #dbeafe !important; }
|
|
202
|
+
[data-theme="blue"] .bg-gray-50 { background-color: #eff6ff !important; }
|
|
203
|
+
[data-theme="blue"] .bg-gray-200 { background-color: #bfdbfe !important; }
|
|
204
|
+
|
|
205
|
+
/* Blue tint on borders — kept light to distinguish from accent */
|
|
206
|
+
[data-theme="blue"] .border-gray-200 { border-color: #dbeafe !important; }
|
|
207
|
+
[data-theme="blue"] .border-gray-300 { border-color: #bfdbfe !important; }
|
|
208
|
+
[data-theme="blue"] .border-gray-100 { border-color: #eff6ff !important; }
|
|
209
|
+
[data-theme="blue"] .divide-gray-200 > :not(:last-child) { border-color: #dbeafe !important; }
|
|
210
|
+
[data-theme="blue"] .divide-gray-100 > :not(:last-child) { border-color: #eff6ff !important; }
|
|
211
|
+
|
|
212
|
+
/* Blue hover states */
|
|
213
|
+
[data-theme="blue"] .hover\:bg-gray-50:hover { background-color: #eff6ff !important; }
|
|
214
|
+
[data-theme="blue"] .hover\:bg-gray-100:hover { background-color: #dbeafe !important; }
|
|
215
|
+
[data-theme="blue"] .hover\:bg-gray-200:hover { background-color: #bfdbfe !important; }
|
|
216
|
+
|
|
217
|
+
|
|
218
|
+
/* ═══════════════════════════════════════════════════
|
|
219
|
+
Custom Accent Color
|
|
220
|
+
Overrides the blue accent when user picks a custom color.
|
|
221
|
+
useTheme() sets data-custom-accent + the --accent-* scale.
|
|
222
|
+
═══════════════════════════════════════════════════ */
|
|
223
|
+
[data-custom-accent] .bg-blue-600 { background-color: var(--accent-600) !important; }
|
|
224
|
+
[data-custom-accent] .bg-blue-700 { background-color: var(--accent-700) !important; }
|
|
225
|
+
[data-custom-accent] .bg-blue-500 { background-color: var(--accent-500) !important; }
|
|
226
|
+
[data-custom-accent] .bg-blue-100 { background-color: var(--accent-100) !important; }
|
|
227
|
+
[data-custom-accent] .bg-blue-50 { background-color: var(--accent-50) !important; }
|
|
228
|
+
[data-custom-accent] .text-blue-600 { color: var(--accent-600) !important; }
|
|
229
|
+
[data-custom-accent] .text-blue-700 { color: var(--accent-700) !important; }
|
|
230
|
+
[data-custom-accent] .text-blue-800 { color: var(--accent-700) !important; }
|
|
231
|
+
[data-custom-accent] .text-blue-500 { color: var(--accent-500) !important; }
|
|
232
|
+
[data-custom-accent] .border-blue-600 { border-color: var(--accent-600) !important; }
|
|
233
|
+
[data-custom-accent] .border-blue-500 { border-color: var(--accent-500) !important; }
|
|
234
|
+
[data-custom-accent] .border-blue-400 { border-color: var(--accent-400) !important; }
|
|
235
|
+
[data-custom-accent] .border-blue-300 { border-color: var(--accent-300) !important; }
|
|
236
|
+
[data-custom-accent] .border-blue-200 { border-color: var(--accent-200) !important; }
|
|
237
|
+
[data-custom-accent] .hover\:bg-blue-700:hover { background-color: var(--accent-700) !important; }
|
|
238
|
+
[data-custom-accent] .hover\:bg-blue-100:hover { background-color: var(--accent-100) !important; }
|
|
239
|
+
[data-custom-accent] .hover\:bg-blue-50:hover { background-color: var(--accent-50) !important; }
|
|
240
|
+
[data-custom-accent] .focus\:border-blue-500:focus { border-color: var(--accent-500) !important; }
|
|
241
|
+
[data-custom-accent] .focus\:ring-blue-500:focus { --tw-ring-color: var(--accent-500) !important; }
|
|
242
|
+
[data-custom-accent] input[type="checkbox"].text-blue-600 { accent-color: var(--accent-600); }
|
|
243
|
+
[data-custom-accent] input[type="range"].accent-blue-600 { accent-color: var(--accent-600); }
|
|
244
|
+
[data-custom-accent] .ring-blue-300 { --tw-ring-color: var(--accent-300) !important; }
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "react-os-shell",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.8.1",
|
|
4
4
|
"description": "Desktop-style React UI shell — windows, taskbar, start menu, sticky notes, frosted glass theming, and bundled apps.",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"author": "Victor Y. Mau",
|
|
@@ -28,7 +28,8 @@
|
|
|
28
28
|
"types": "./dist/apps/index.d.ts",
|
|
29
29
|
"import": "./dist/apps/index.js"
|
|
30
30
|
},
|
|
31
|
-
"./styles.css": "./dist/styles.css"
|
|
31
|
+
"./styles.css": "./dist/styles.css",
|
|
32
|
+
"./themes.css": "./dist/themes.css"
|
|
32
33
|
},
|
|
33
34
|
"files": [
|
|
34
35
|
"dist"
|
|
@@ -65,7 +66,7 @@
|
|
|
65
66
|
"xlsx": "^0.18.5"
|
|
66
67
|
},
|
|
67
68
|
"scripts": {
|
|
68
|
-
"build": "tsup && cp src/styles.css
|
|
69
|
+
"build": "tsup && cp src/styles.css src/themes.css dist/",
|
|
69
70
|
"dev": "tsup --watch",
|
|
70
71
|
"typecheck": "tsc --noEmit",
|
|
71
72
|
"screenshot": "node scripts/screenshot.mjs",
|
package/dist/Preview-5SOLJFFK.js
DELETED
|
@@ -1,9 +0,0 @@
|
|
|
1
|
-
export { Preview as default, setPdfPreview } from './chunk-UATWDGLV.js';
|
|
2
|
-
import './chunk-KUIPWCTJ.js';
|
|
3
|
-
import './chunk-WIJ45SYD.js';
|
|
4
|
-
import './chunk-MJIMKMSJ.js';
|
|
5
|
-
import './chunk-JNF5VRPB.js';
|
|
6
|
-
import './chunk-UBN4IUDE.js';
|
|
7
|
-
import './chunk-ZF6AYO4G.js';
|
|
8
|
-
//# sourceMappingURL=Preview-5SOLJFFK.js.map
|
|
9
|
-
//# sourceMappingURL=Preview-5SOLJFFK.js.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/shell/Sidebar.tsx"],"names":["navSections","navIcons","sectionIcons"],"mappings":"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","file":"Sidebar-BW7SYNBA.js","sourcesContent":["/**\n * Sidebar — persistent left strip used when `prefs.layout_mode === 'sidebar'`.\n *\n * Same configuration surface as <StartMenu> (navSections, navIcons,\n * sectionIcons, categories) but rendered inline:\n * - No flyouts. Sections expand/collapse accordion-style below their\n * header, indented one step.\n * - No taskbar-anchored positioning — fixed full-height left strip,\n * width pulled from `--sidebar-width`.\n * - Right edge `rounded-r-2xl` so it matches windowed cards on the\n * right (which use `rounded-2xl`).\n *\n * Designed for small-screen layouts where flyouts would clip and where\n * keeping the menu always-visible saves a tap to switch apps.\n */\n\nimport { useEffect, useMemo, useRef, useState, isValidElement, cloneElement, type ReactElement, type ReactNode } from 'react';\nimport {\n navSections as defaultNavSections,\n navIcons as defaultNavIcons,\n sectionIcons as defaultSectionIcons,\n startMenuCategories as defaultCategories,\n isSection,\n type NavSection,\n type NavItem,\n type StartMenuCategories,\n type VirtualSection,\n} from '../shell-config/nav';\nimport { useAuth } from '../contexts/AuthContext';\nimport { glassStyle, GLASS_INPUT_BG } from '../utils/glass';\n\ninterface SidebarProps {\n width: number;\n openPage: (path: string) => void;\n profile: any;\n user: any;\n onLogout: () => void;\n onNavigate: (path: string) => void;\n navSections?: (NavSection | NavItem)[];\n navIcons?: Record<string, ReactNode>;\n sectionIcons?: Record<string, ReactNode>;\n categories?: StartMenuCategories;\n productName?: string;\n productIcon?: string;\n}\n\nexport default function Sidebar({\n width,\n openPage,\n profile,\n user,\n onLogout,\n onNavigate,\n navSections = defaultNavSections,\n navIcons = defaultNavIcons,\n sectionIcons = defaultSectionIcons,\n categories = defaultCategories,\n productName,\n productIcon,\n}: SidebarProps) {\n const { hasAnyPerm } = useAuth();\n const erpLabels = new Set(categories.erp);\n const systemLabels = new Set(categories.system);\n const footerLabels = new Set(categories.footer ?? []);\n // Flat rows pinned to the footer (next to the profile) — rendered inline,\n // not as an accordion section. Mirrors StartMenu's `footerItems`.\n const footerItems = (categories.footerItems ?? []).filter(it => !it.perms || hasAnyPerm(it.perms));\n const virtualSections = categories.virtual ?? [];\n\n const [search, setSearch] = useState('');\n const [expanded, setExpanded] = useState<Set<string>>(new Set());\n const searchRef = useRef<HTMLInputElement>(null);\n\n const toggleExpanded = (label: string) => {\n setExpanded(prev => {\n const next = new Set(prev);\n if (next.has(label)) next.delete(label);\n else next.add(label);\n return next;\n });\n };\n\n // Top-level items vs sections, mirroring StartMenu's split.\n const topItems = navSections.filter(item => !isSection(item)) as NavItem[];\n const erpSections = navSections.filter(item => isSection(item) && erpLabels.has((item as NavSection).label)) as NavSection[];\n const systemSections = navSections.filter(item => isSection(item) && systemLabels.has((item as NavSection).label)) as NavSection[];\n const footerSections = navSections.filter(item => isSection(item) && footerLabels.has((item as NavSection).label)) as NavSection[];\n\n const getVisibleItems = (section: { items: NavItem[]; perms?: string[] }) => {\n if (section.perms && !hasAnyPerm(section.perms)) return [];\n return section.items.filter(it => !it.perms || hasAnyPerm(it.perms));\n };\n\n // Search across all items + sections (same flat list StartMenu uses).\n // Walks 3rd-level children too so nested entries are still discoverable.\n const matchTree = (it: NavItem, q: string): NavItem[] => {\n if (it.perms && !hasAnyPerm(it.perms)) return [];\n const hits: NavItem[] = [];\n if (it.label.toLowerCase().includes(q)) hits.push(it);\n if (it.children) {\n for (const c of it.children) hits.push(...matchTree(c, q));\n }\n return hits;\n };\n const searchResults = useMemo(() => {\n if (search.length < 2) return [] as NavItem[];\n const q = search.toLowerCase();\n return [\n ...navSections.flatMap((entry) => {\n if (isSection(entry)) {\n return getVisibleItems(entry).flatMap(it => matchTree(it, q));\n }\n return matchTree(entry as NavItem, q);\n }),\n ...footerItems.flatMap(it => matchTree(it, q)),\n ];\n }, [search, navSections, footerItems, hasAnyPerm]);\n\n // Esc collapses any expanded section + clears search; '/' focuses search.\n useEffect(() => {\n const onKey = (e: KeyboardEvent) => {\n if (e.key === 'Escape') {\n setExpanded(new Set());\n setSearch('');\n } else if (e.key === '/' && document.activeElement?.tagName !== 'INPUT' && document.activeElement?.tagName !== 'TEXTAREA') {\n e.preventDefault();\n searchRef.current?.focus();\n }\n };\n window.addEventListener('keydown', onKey);\n return () => window.removeEventListener('keydown', onKey);\n }, []);\n\n const handleClick = (path: string) => {\n onNavigate(path);\n onPageOpenedReset();\n };\n\n // Reset search after navigating so the next visit starts clean.\n const onPageOpenedReset = () => {\n setSearch('');\n };\n\n const itemCls = 'w-full flex items-center gap-2 rounded-lg px-3 py-2 text-sm';\n const menuGlass = glassStyle();\n\n // Helper that returns the (possibly recolored) per-route icon.\n const iconEl = (to: string) => {\n const icon = navIcons[to];\n if (icon && isValidElement(icon)) {\n return cloneElement(icon as ReactElement<{ className?: string }>, {\n className: 'h-4 w-4 shrink-0 text-gray-500',\n });\n }\n return <span className=\"h-4 w-4 shrink-0\" />;\n };\n\n const secIcon = (label: string) => {\n const icon = sectionIcons[label];\n if (icon && isValidElement(icon)) {\n return cloneElement(icon as ReactElement<{ className?: string }>, {\n className: 'h-4 w-4 shrink-0 text-gray-500',\n });\n }\n return <span className=\"h-4 w-4 shrink-0\" />;\n };\n\n const renderItem = (item: NavItem) => (\n <div key={item.to}>\n <button\n onClick={() => handleClick(item.to)}\n className={`${itemCls} text-gray-700 hover:bg-blue-50 hover:text-blue-700 transition-colors`}\n >\n {iconEl(item.to)}\n <span className=\"truncate\">{item.label}</span>\n </button>\n {item.dividerAfter && <div className=\"border-t border-white/20 my-1.5 mx-2\" />}\n </div>\n );\n\n // 3rd-level: when a NavItem inside an accordion has children, render the\n // parent as its own mini-accordion (further indented). Expansion key is\n // `child:<to>` so it doesn't clash with the section labels in `expanded`.\n const renderNestedItem = (item: NavItem) => {\n const kids = (item.children ?? []).filter(c => !c.perms || hasAnyPerm(c.perms));\n if (kids.length === 0) return renderItem(item);\n const key = `child:${item.to}`;\n const isOpen = expanded.has(key);\n return (\n <div key={item.to}>\n <button\n onClick={() => toggleExpanded(key)}\n aria-expanded={isOpen}\n className={`${itemCls} text-gray-700 hover:bg-blue-50 hover:text-blue-700 transition-colors`}\n >\n {iconEl(item.to)}\n <span className=\"truncate\">{item.label}</span>\n <svg\n className={`h-3.5 w-3.5 ml-auto text-gray-500 transition-transform ${isOpen ? 'rotate-90' : ''}`}\n fill=\"none\" viewBox=\"0 0 24 24\" stroke=\"currentColor\" strokeWidth={2}>\n <path strokeLinecap=\"round\" strokeLinejoin=\"round\" d=\"M8.25 4.5l7.5 7.5-7.5 7.5\" />\n </svg>\n </button>\n {isOpen && (\n <div className=\"pl-4 mt-0.5 mb-1 space-y-0.5\">\n {kids.map(c => (\n <button\n key={c.to}\n onClick={() => handleClick(c.to)}\n className={`${itemCls} text-gray-700 hover:bg-blue-50 hover:text-blue-700 transition-colors`}\n >\n {iconEl(c.to)}\n <span className=\"truncate\">{c.label}</span>\n </button>\n ))}\n </div>\n )}\n {item.dividerAfter && <div className=\"border-t border-white/20 my-1.5 mx-2\" />}\n </div>\n );\n };\n\n const renderSectionAccordion = (section: NavSection | VirtualSection, isErp: boolean) => {\n const items = 'perms' in section\n ? getVisibleItems(section as NavSection)\n : (section as VirtualSection).items;\n if (items.length === 0) return null;\n const isOpen = expanded.has(section.label);\n return (\n <div key={section.label}>\n <button\n onClick={() => toggleExpanded(section.label)}\n aria-expanded={isOpen}\n className={`${itemCls} text-gray-700 hover:bg-blue-50 hover:text-blue-700 transition-colors`}\n >\n {'icon' in section && section.icon\n ? section.icon\n : secIcon(section.label)}\n <span className={`truncate ${isErp ? 'font-medium' : ''}`}>{section.label}</span>\n <svg\n className={`h-3.5 w-3.5 ml-auto text-gray-500 transition-transform ${isOpen ? 'rotate-90' : ''}`}\n fill=\"none\" viewBox=\"0 0 24 24\" stroke=\"currentColor\" strokeWidth={2}>\n <path strokeLinecap=\"round\" strokeLinejoin=\"round\" d=\"M8.25 4.5l7.5 7.5-7.5 7.5\" />\n </svg>\n </button>\n {isOpen && (\n <div className=\"pl-4 mt-0.5 mb-1 space-y-0.5\">\n {items.map(it => renderNestedItem(it))}\n </div>\n )}\n </div>\n );\n };\n\n return (\n <div\n className=\"fixed top-0 left-0 bottom-0 z-[260] flex flex-col rounded-r-2xl overflow-hidden\"\n style={{ width, ...menuGlass }}\n >\n {/* Brand */}\n <div className=\"flex items-center gap-2 px-4 py-3 border-b border-white/15 shrink-0\">\n {productIcon && <img src={productIcon} alt=\"\" className=\"h-5 w-5 shrink-0 opacity-80\" />}\n <span className=\"text-sm font-semibold text-gray-800 truncate\">{productName ?? 'Apps'}</span>\n </div>\n\n {/* Search */}\n <div className=\"px-3 pt-3 pb-2 shrink-0\">\n <div className={`flex items-center gap-2 ${GLASS_INPUT_BG} rounded-lg px-2.5 py-1.5`}>\n <svg className=\"h-3.5 w-3.5 text-gray-400 shrink-0\" fill=\"none\" viewBox=\"0 0 24 24\" stroke=\"currentColor\" strokeWidth={2}>\n <path strokeLinecap=\"round\" strokeLinejoin=\"round\" d=\"M21 21l-5.197-5.197m0 0A7.5 7.5 0 105.196 5.196a7.5 7.5 0 0010.607 10.607z\" />\n </svg>\n <input\n ref={searchRef}\n value={search}\n onChange={e => setSearch(e.target.value)}\n placeholder=\"Search...\"\n className=\"flex-1 bg-transparent text-xs outline-none placeholder-gray-400\"\n />\n {search && (\n <button onClick={() => setSearch('')} className=\"text-gray-400 hover:text-gray-600 text-xs\">×</button>\n )}\n </div>\n </div>\n\n {/* Body */}\n <div className=\"flex-1 overflow-y-auto px-1 pb-1\">\n {search.length >= 2 ? (\n // Search results take over the body.\n <div>\n {searchResults.length === 0 ? (\n <div className=\"px-3 py-6 text-center text-xs text-gray-400\">No matches</div>\n ) : (\n searchResults.map(r => (\n <button\n key={r.to}\n onClick={() => handleClick(r.to)}\n className={`${itemCls} text-gray-700 hover:bg-blue-50 hover:text-blue-700 transition-colors`}\n >\n {iconEl(r.to)}\n <span className=\"truncate\">{r.label}</span>\n </button>\n ))\n )}\n </div>\n ) : (\n <>\n {/* Top-level apps */}\n {topItems.map(renderItem)}\n\n <div className=\"border-t border-white/15 my-1.5 mx-2\" />\n\n {/* ERP sections then system sections — same order as StartMenu's vertical layout. */}\n {erpSections.map(s => renderSectionAccordion(s, true))}\n {systemSections.map(s => renderSectionAccordion(s, false))}\n {virtualSections.map(v => renderSectionAccordion(v, false))}\n {/* Footer items + sections: pinned just above the profile, divided from the rest. */}\n {(footerSections.length > 0 || footerItems.length > 0) && <div className=\"border-t border-white/15 my-1.5 mx-2\" />}\n {footerSections.map(s => renderSectionAccordion(s, false))}\n {footerItems.map(renderItem)}\n </>\n )}\n </div>\n\n {/* Profile + Sign out at the bottom — mirrors StartMenu's user row. */}\n <div className=\"border-t border-white/15 p-1 shrink-0\">\n <div\n onClick={() => handleClick('/profile')}\n className=\"rounded-lg px-2 py-1.5 flex items-center gap-2.5 hover:bg-blue-50 hover:text-blue-700 transition-colors cursor-pointer\"\n >\n {profile?.avatar_url ? (\n <img src={profile.avatar_url} alt=\"\" className=\"h-8 w-8 rounded-full object-cover border border-white/20 shrink-0\" />\n ) : (\n <div className=\"h-8 w-8 rounded-full bg-blue-100 flex items-center justify-center text-sm font-bold text-blue-700 shrink-0\">\n {(profile?.first_name?.charAt(0) || user?.email?.charAt(0) || '?').toUpperCase()}\n </div>\n )}\n <p className=\"flex-1 min-w-0 text-sm font-medium text-gray-900 truncate\">\n {profile?.first_name ? `${profile.first_name} ${profile.last_name || ''}`.trim() : user?.email}\n </p>\n <button\n onClick={e => { e.stopPropagation(); onLogout(); }}\n title=\"Sign Out\"\n className=\"shrink-0 p-1.5 rounded-md text-gray-500 hover:text-red-600 hover:bg-red-50 transition-colors\"\n >\n <svg className=\"h-5 w-5\" fill=\"none\" viewBox=\"0 0 24 24\" stroke=\"currentColor\" strokeWidth={1.5}>\n <path strokeLinecap=\"round\" strokeLinejoin=\"round\" d=\"M15.75 9V5.25A2.25 2.25 0 0013.5 3h-6a2.25 2.25 0 00-2.25 2.25v13.5A2.25 2.25 0 007.5 21h6a2.25 2.25 0 002.25-2.25V15m3 0l3-3m0 0l-3-3m3 3H9\" />\n </svg>\n </button>\n </div>\n </div>\n </div>\n );\n}\n"]}
|