feat(timeline): regroup /zeitstrahl by Ereignis or Thema (#827) #847

Closed
marcel wants to merge 25 commits from feat/issue-827-zeitstrahl-grouping into main
2 changed files with 58 additions and 35 deletions
Showing only changes of commit e100213760 - Show all commits

View File

@@ -57,16 +57,20 @@ let revealed = $state(bucket.kind !== 'fallback');
</script>
<section
class="my-3 border-l-2 pl-3"
class="my-3 overflow-hidden rounded-md border border-l-2 border-line bg-surface shadow-sm"
class:border-l-brand-mint={isEventCluster}
class:border-line={!railColor && !isEventCluster}
class:border-dashed={isDrawer}
style={railStyle}
data-testid="letter-bucket"
data-bucket-kind={bucket.kind}
>
{#if !nested}
<header class="mb-2 flex items-center gap-2">
<header
class="flex items-center gap-2 px-3 py-2"
class:bg-canvas={isEventCluster}
class:border-b={!isDrawer}
class:border-line={!isDrawer}
>
{#if mode === 'thema' && bucket.kind === 'tag'}
<BucketHeaderChip name={bucket.title ?? ''} color={bucket.color} />
{:else if mode === 'event' && bucket.kind === 'event'}
@@ -81,42 +85,44 @@ let revealed = $state(bucket.kind !== 'fallback');
</header>
{/if}
{#if !revealed}
<button
type="button"
data-testid="bucket-reveal"
onclick={() => (revealed = true)}
style="display: inline-flex; align-items: center; min-height: 44px"
class="px-1 font-sans text-xs font-semibold text-brand-navy hover:underline focus:outline-none focus-visible:ring-2 focus-visible:ring-brand-navy"
>
{m.timeline_bucket_show_more({ count: bucket.letters.length })}
</button>
{:else}
<ul class="space-y-1.5">
{#each visible as letter (entryKey(letter))}
<li>
<LetterCard
entry={letter}
variant={cardVariant}
suppressTagChip={mode === 'thema'}
compact={true}
/>
</li>
{/each}
</ul>
{#if hiddenCount > 0}
<div class="px-3 py-2">
{#if !revealed}
<button
type="button"
data-testid="bucket-show-more"
aria-expanded={expanded}
onclick={() => (expanded = !expanded)}
data-testid="bucket-reveal"
onclick={() => (revealed = true)}
style="display: inline-flex; align-items: center; min-height: 44px"
class="mt-1 px-1 font-sans text-xs font-semibold text-brand-navy hover:underline focus:outline-none focus-visible:ring-2 focus-visible:ring-brand-navy"
class="px-1 font-sans text-xs font-semibold text-brand-navy hover:underline focus:outline-none focus-visible:ring-2 focus-visible:ring-brand-navy"
>
{expanded
? m.timeline_bucket_show_less()
: m.timeline_bucket_show_more({ count: hiddenCount })}
{m.timeline_bucket_show_more({ count: bucket.letters.length })}
</button>
{:else}
<ul class="space-y-1.5">
{#each visible as letter (entryKey(letter))}
<li>
<LetterCard
entry={letter}
variant={cardVariant}
suppressTagChip={mode === 'thema'}
compact={true}
/>
</li>
{/each}
</ul>
{#if hiddenCount > 0}
<button
type="button"
data-testid="bucket-show-more"
aria-expanded={expanded}
onclick={() => (expanded = !expanded)}
style="display: inline-flex; align-items: center; min-height: 44px"
class="mt-1 px-1 font-sans text-xs font-semibold text-brand-navy hover:underline focus:outline-none focus-visible:ring-2 focus-visible:ring-brand-navy"
>
{expanded
? m.timeline_bucket_show_less()
: m.timeline_bucket_show_more({ count: hiddenCount })}
</button>
{/if}
{/if}
{/if}
</div>
</section>

View File

@@ -161,3 +161,20 @@ describe('LetterBucket — leftover drawer (#827 redesign)', () => {
expect(document.querySelector('[data-testid="bucket-show-more"]')).not.toBeNull();
});
});
describe('LetterBucket — card chrome (#827 redesign)', () => {
it('renders the cluster as a contained card (bordered, rounded, surface)', () => {
const bucket: Bucket = {
key: 'tag:t1',
kind: 'tag',
title: 'Krieg',
color: 'sienna',
letters: [makeEntry({ documentId: 'a' })]
};
render(LetterBucket, { bucket, mode: 'thema', year: 1916 });
const card = document.querySelector('[data-testid="letter-bucket"]') as HTMLElement;
expect(card.className).toMatch(/\brounded\b|rounded-/);
expect(card.className).toContain('border');
expect(card.className).toContain('bg-surface');
});
});