fix(client): keep reading activity text inside card

Preserve the card's intrinsic minimum height when the detail column needs to scroll so empty-state copy remains within its border.

Fixes #1262
This commit is contained in:
neon
2026-09-05 09:30:20 +00:00
parent f5bb88f996
commit e63c4b3685
3 changed files with 13 additions and 2 deletions
@@ -95,7 +95,7 @@ function formatBadgeStyle(format: string) {
</script>
<template>
<section class="flex min-h-0 flex-col rounded-xl border border-border bg-card px-3.5 py-3" :aria-label="t('book.detail.details.yourReading')">
<section class="flex flex-col rounded-xl border border-border bg-card px-3.5 py-3" :aria-label="t('book.detail.details.yourReading')">
<div class="flex items-baseline gap-2">
<h3 class="text-[10px] font-semibold uppercase tracking-wider text-muted-foreground">
{{ t('book.detail.details.yourReading') }}
@@ -1869,7 +1869,7 @@ watch(
</section>
<BookReadingActivityCard
class="@min-[46rem]/book-detail:min-h-0 @min-[46rem]/book-detail:flex-1"
class="@min-[46rem]/book-detail:flex-1"
:stats="readingStats"
:sessions="readingSessions"
:loading="readingLogLoading"
@@ -3,6 +3,7 @@ import { flushPromises, shallowMount } from '@vue/test-utils'
import { defineComponent } from 'vue'
import type { BookDetail } from '@bookorbit/types'
import DetailsTab from '../DetailsTab.vue'
import BookReadingActivityCard from '../../details/BookReadingActivityCard.vue'
import { useDisplaySettings } from '@/composables/useDisplaySettings'
const mocks = vi.hoisted(() => ({
@@ -116,6 +117,7 @@ function mountDetails(book: BookDetail) {
stubs: {
BookCoverArtwork: false,
BookCoverSurface: false,
BookReadingActivityCard: false,
RouterLink: RouterLinkStub,
Popover: { template: '<div><slot /><slot name="content" /></div>' },
PopoverTrigger: { template: '<div><slot /></div>' },
@@ -335,6 +337,15 @@ describe('DetailsTab cover surface', () => {
expect(toggle!.attributes('aria-expanded')).toBe('false')
})
it('keeps the reading activity card tall enough for its content', async () => {
const wrapper = mountDetails(makeBook())
await flushPromises()
const activityCard = wrapper.getComponent(BookReadingActivityCard)
expect(activityCard.classes()).toContain('@min-[46rem]/book-detail:flex-1')
expect(activityCard.classes().some((className) => className.includes('min-h-0'))).toBe(false)
})
it('summarizes pending Kobo sync state for each affected device', async () => {
mocks.api.mockImplementation(async (input) => {
const url = String(input)