Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
17 changes: 13 additions & 4 deletions resources/js/components/ui/button.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,11 +12,14 @@ type Size = 'sm' | 'md' | 'lg';
* buttons ended up hand-written at four different padding scales instead.
*
* `secondary` takes `border-rule` so it moves with the two-weight rule system
* rather than declaring its own black/white alphas.
* rather than declaring its own black/white alphas. Its hover steps up to
* `border-rule-strong` over a `bg-muted` fill. It had no hover state at all
* until the consent bar rendered it as a `<button>`: every earlier use was a
* link, and the link's pointer cursor had been the only feedback it gave.
*/
const variants: Record<Variant, string> = {
primary: 'bg-primary text-primary-foreground hover:opacity-90',
secondary: 'border border-rule text-foreground',
secondary: 'border border-rule text-foreground hover:border-rule-strong hover:bg-muted',
ghost: 'text-muted-foreground hover:text-foreground',
};

Expand All @@ -39,8 +42,14 @@ const sizes: Record<Size, string> = {
*/
export function buttonClasses(variant: Variant = 'primary', size: Size = 'md', className?: string): string {
return cn(
'inline-flex items-center justify-center gap-2 rounded-full font-semibold',
'transition-opacity duration-(--dur-tap) ease-(--ease-feedback)',
/*
* `cursor-pointer` because Tailwind v4's preflight leaves `<button>` on
* the default arrow. A link gets the pointer from the browser, so
* without this the same pill read as clickable or not depending on
* which element it rendered as.
*/
'inline-flex cursor-pointer items-center justify-center gap-2 rounded-full font-semibold',
'transition-[opacity,background-color,border-color] duration-(--dur-tap) ease-(--ease-feedback)',
variants[variant],
sizes[size],
className,
Expand Down
15 changes: 15 additions & 0 deletions tests/Feature/Landing/AnalyticsConsentTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -130,6 +130,21 @@
Assert::assertSame($props[0], $props[1], 'Allow and Decline must be styled identically');
});

/*
* The bar's buttons were the first secondary `Button`s to render as `<button>`
* rather than `<a>`, and they showed an arrow cursor and no hover: Tailwind v4
* leaves buttons on the default cursor, and the variant had no hover because
* a link's pointer had always stood in for one.
*/
it('makes the Allow and Decline buttons look clickable', function () use ($readSource): void {
$button = $readSource('resources/js/components/ui/button.tsx');

preg_match("/secondary: '([^']+)'/", $button, $secondary);

expect($button)->toMatch("/'inline-flex cursor-pointer /");
expect($secondary[1] ?? '')->toContain('hover:');
});

it('tells readers which cookies analytics sets and how to take consent back', function () use ($readSource): void {
$privacy = $readSource('resources/js/pages/Privacy.tsx');

Expand Down
Loading