feat(web): card hover-reveal + drop year + accent rule on section headers
test-web / test (push) Failing after 33s
test-web / test (push) Failing after 33s
First wave of Home visual polish (UI tasks 78/79/81/85): - CardActionCluster like/queue/menu cluster is now opacity-0 and fades in on group-hover or focus-within. The group class moves from the inner anchor to the outer card wrapper so the cluster (positioned outside the anchor) participates in the same hover scope. PlaylistCard refresh kebab gets the same treatment. - AlbumCard drops the year line. Title plus artist is enough on Home tiles; the album detail page still shows the year. - HorizontalScrollRow h2 picks up a flex-baseline layout with a trailing 12-wide accent rule (after:bg-accent/60), so section headers read as chapter breaks instead of identical plain text. - AlbumCard art-wrap is shadow-sm by default and lifts to shadow-lg plus ring-accent/40 on hover. Pairs with the existing group-hover:scale-1.03 for a clean lift-on-mouseover feel.
This commit is contained in:
@@ -28,12 +28,16 @@
|
||||
}
|
||||
</script>
|
||||
|
||||
<div class="card relative">
|
||||
<div class="card group relative">
|
||||
<a
|
||||
href={`/albums/${album.id}`}
|
||||
class="group block rounded focus-visible:ring-2 focus-visible:ring-accent"
|
||||
class="block rounded focus-visible:ring-2 focus-visible:ring-accent"
|
||||
>
|
||||
<div class="art-wrap relative aspect-square w-full overflow-hidden rounded-md">
|
||||
<div
|
||||
class="art-wrap relative aspect-square w-full overflow-hidden rounded-md
|
||||
shadow-sm transition-all duration-150
|
||||
group-hover:shadow-lg group-hover:ring-1 group-hover:ring-accent/40"
|
||||
>
|
||||
<img
|
||||
src={album.cover_url}
|
||||
alt=""
|
||||
@@ -54,9 +58,6 @@
|
||||
{#if album.artist_name}
|
||||
<div class="truncate text-xs text-text-secondary">{album.artist_name}</div>
|
||||
{/if}
|
||||
{#if album.year}
|
||||
<div class="text-xs text-text-secondary">{album.year}</div>
|
||||
{/if}
|
||||
</a>
|
||||
<CardActionCluster
|
||||
likeEntityType="album"
|
||||
|
||||
@@ -42,10 +42,10 @@
|
||||
}
|
||||
</script>
|
||||
|
||||
<div class="card relative">
|
||||
<div class="card group relative">
|
||||
<a
|
||||
href={`/artists/${artist.id}`}
|
||||
class="group block rounded focus-visible:ring-2 focus-visible:ring-accent"
|
||||
class="block rounded focus-visible:ring-2 focus-visible:ring-accent"
|
||||
>
|
||||
<div class="art-wrap relative mx-auto aspect-square w-full overflow-hidden rounded-full bg-surface-hover">
|
||||
{#if artist.cover_url}
|
||||
|
||||
@@ -34,9 +34,17 @@
|
||||
} = $props();
|
||||
</script>
|
||||
|
||||
<!-- Like + Add to queue + Menu cluster. Hover-revealed so the
|
||||
default tile state is just the cover artwork — controls fade in
|
||||
when the user hovers the card or focuses any of the buttons
|
||||
(focus-within keeps it visible during keyboard navigation). -->
|
||||
<!-- svelte-ignore a11y_click_events_have_key_events -->
|
||||
<!-- svelte-ignore a11y_no_static_element_interactions -->
|
||||
<div class="absolute right-2 top-2 z-10 flex gap-1" onclick={(e) => e.stopPropagation()}>
|
||||
<div
|
||||
class="absolute right-2 top-2 z-10 flex gap-1 opacity-0 transition-opacity duration-150
|
||||
group-hover:opacity-100 focus-within:opacity-100"
|
||||
onclick={(e) => e.stopPropagation()}
|
||||
>
|
||||
<LikeButton entityType={likeEntityType} entityId={likeEntityId} />
|
||||
<button
|
||||
type="button"
|
||||
@@ -50,6 +58,10 @@
|
||||
</div>
|
||||
<!-- svelte-ignore a11y_click_events_have_key_events -->
|
||||
<!-- svelte-ignore a11y_no_static_element_interactions -->
|
||||
<div class="absolute right-2 bottom-2 z-10" onclick={(e) => e.stopPropagation()}>
|
||||
<div
|
||||
class="absolute right-2 bottom-2 z-10 opacity-0 transition-opacity duration-150
|
||||
group-hover:opacity-100 focus-within:opacity-100"
|
||||
onclick={(e) => e.stopPropagation()}
|
||||
>
|
||||
{@render menu()}
|
||||
</div>
|
||||
|
||||
@@ -62,7 +62,14 @@
|
||||
<div class="section" aria-label={ariaLabel}>
|
||||
<header class="section-header">
|
||||
{#if title}
|
||||
<h2 class="font-display text-2xl font-medium text-text-primary">{title}</h2>
|
||||
<!-- Section header: Fraunces (font-display) at 24px with an
|
||||
inline accent rule that bleeds out from the title — gives
|
||||
each shelf a clear chapter break without adding chrome. -->
|
||||
<h2
|
||||
class="font-display text-2xl font-medium text-text-primary
|
||||
flex items-baseline gap-3 after:h-[2px] after:w-12 after:flex-shrink-0
|
||||
after:rounded-full after:bg-accent/60 after:content-['']"
|
||||
>{title}</h2>
|
||||
{:else}
|
||||
<span></span>
|
||||
{/if}
|
||||
|
||||
@@ -104,9 +104,14 @@
|
||||
|
||||
<svelte:window onclick={() => { menuOpen = false; }} />
|
||||
|
||||
<div class="card relative">
|
||||
<div class="card group relative">
|
||||
{#if refreshable}
|
||||
<div class="kebab-wrap absolute right-1 top-1 z-10">
|
||||
<!-- Kebab is hover/focus-revealed so the default tile state is
|
||||
just the cover. Same pattern as CardActionCluster. -->
|
||||
<div
|
||||
class="kebab-wrap absolute right-1 top-1 z-10 transition-opacity duration-150
|
||||
{menuOpen ? 'opacity-100' : 'opacity-0 group-hover:opacity-100 focus-within:opacity-100'}"
|
||||
>
|
||||
<button
|
||||
type="button"
|
||||
aria-label="Playlist actions"
|
||||
|
||||
Reference in New Issue
Block a user