Skip to content

Commit 8993120

Browse files
authored
Use color-mix for text selection highlights (#94)
* Use color-mix for text selection highlights - Make selection background use `color-mix()` - Keep selection foreground aligned with the default text color * Add selection highlight accessibility fixes - Replace invalid hsl(var(--...)) color usage with color-mix-friendly values - Add reduced-motion, forced-colors, and high-contrast selection styles - Cover selection and scrollbar styling with regression tests
1 parent 26fe284 commit 8993120

4 files changed

Lines changed: 534 additions & 10 deletions

File tree

apps/web/src/components/ui/button.tsx

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,9 +9,9 @@ const buttonVariants = cva(
99
variants: {
1010
variant: {
1111
default:
12-
"bg-linear-to-b from-primary to-[hsl(223_82%_62%)] text-primary-foreground shadow-[0_18px_45px_-20px_hsl(var(--primary)/0.85)] hover:brightness-110 hover:shadow-[0_22px_55px_-22px_hsl(var(--primary)/0.95)]",
12+
"bg-linear-to-b from-primary to-[hsl(223_82%_62%)] text-primary-foreground shadow-[0_18px_45px_-20px_color-mix(in_srgb,var(--primary)_85%,transparent)] hover:brightness-110 hover:shadow-[0_22px_55px_-22px_color-mix(in_srgb,var(--primary)_95%,transparent)]",
1313
destructive:
14-
"bg-linear-to-b from-destructive to-[hsl(352_72%_52%)] text-destructive-foreground shadow-[0_18px_45px_-20px_hsl(var(--destructive)/0.7)] hover:brightness-105 hover:shadow-[0_22px_55px_-22px_hsl(var(--destructive)/0.8)]",
14+
"bg-linear-to-b from-destructive to-[hsl(352_72%_52%)] text-destructive-foreground shadow-[0_18px_45px_-20px_color-mix(in_srgb,var(--destructive)_70%,transparent)] hover:brightness-105 hover:shadow-[0_22px_55px_-22px_color-mix(in_srgb,var(--destructive)_80%,transparent)]",
1515
"destructive-outline":
1616
"border border-destructive/35 bg-destructive/6 text-destructive shadow-[inset_0_1px_0_hsl(0_0%_100%/0.04)] hover:border-destructive/45 hover:bg-destructive/10 hover:text-destructive",
1717
outline:

apps/web/src/components/ui/sidebar.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -814,7 +814,7 @@ const sidebarMenuButtonVariants = cva(
814814
variant: {
815815
default: "hover:bg-sidebar-accent hover:text-sidebar-accent-foreground",
816816
outline:
817-
"bg-background shadow-[0_0_0_1px_hsl(var(--sidebar-border))] hover:bg-sidebar-accent hover:text-sidebar-accent-foreground hover:shadow-[0_0_0_1px_hsl(var(--sidebar-accent))]",
817+
"bg-background shadow-[0_0_0_1px_var(--color-sidebar-border,var(--border))] hover:bg-sidebar-accent hover:text-sidebar-accent-foreground hover:shadow-[0_0_0_1px_var(--color-sidebar-accent,var(--accent))]",
818818
},
819819
},
820820
},

apps/web/src/index.css

Lines changed: 40 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -598,18 +598,17 @@ label:has(> select#reasoning-effort) select {
598598
body {
599599
background:
600600
radial-gradient(circle at top, hsl(217 96% 71% / 0.08), transparent 28%),
601-
radial-gradient(circle at 80% 0%, hsl(228 88% 68% / 0.06), transparent 24%),
602-
hsl(var(--background));
601+
radial-gradient(circle at 80% 0%, hsl(228 88% 68% / 0.06), transparent 24%), var(--background);
603602
background-attachment: fixed;
604603
}
605604

606605
::selection {
607-
background: hsl(var(--primary) / 0.55);
608-
color: hsl(var(--foreground));
606+
background: color-mix(in srgb, var(--primary) 55%, transparent);
607+
color: var(--foreground);
609608
}
610609

611610
* {
612-
scrollbar-color: hsl(var(--primary) / 0.42) transparent;
611+
scrollbar-color: color-mix(in srgb, var(--primary) 42%, transparent) transparent;
613612
}
614613

615614
*::-webkit-scrollbar {
@@ -623,14 +622,48 @@ label:has(> select#reasoning-effort) select {
623622

624623
*::-webkit-scrollbar-thumb {
625624
border-radius: 999px;
626-
background: hsl(var(--primary) / 0.25);
625+
background: color-mix(in srgb, var(--primary) 25%, transparent);
627626
border: 2px solid transparent;
628627
background-clip: padding-box;
629628
}
630629

631630
*::-webkit-scrollbar-thumb:hover {
632-
background: hsl(var(--primary) / 0.38);
631+
background: color-mix(in srgb, var(--primary) 38%, transparent);
633632
border: 2px solid transparent;
634633
background-clip: padding-box;
635634
}
636635
}
636+
637+
/* ─── Accessibility ─── */
638+
639+
@media (prefers-reduced-motion: reduce) {
640+
*,
641+
*::before,
642+
*::after {
643+
animation-duration: 0.01ms !important;
644+
animation-iteration-count: 1 !important;
645+
transition-duration: 0.01ms !important;
646+
scroll-behavior: auto !important;
647+
}
648+
}
649+
650+
@media (forced-colors: active) {
651+
::selection {
652+
background: Highlight;
653+
color: HighlightText;
654+
}
655+
656+
*::-webkit-scrollbar-thumb {
657+
background: ButtonText;
658+
}
659+
660+
*::-webkit-scrollbar-track {
661+
background: Canvas;
662+
}
663+
}
664+
665+
@media (prefers-contrast: more) {
666+
::selection {
667+
background: color-mix(in srgb, var(--primary) 88%, transparent);
668+
}
669+
}

0 commit comments

Comments
 (0)