From 57fb99af635687c459b2298e89f4826185d356f1 Mon Sep 17 00:00:00 2001 From: Thomas Hallock Date: Tue, 11 Nov 2025 18:21:24 -0600 Subject: [PATCH] feat: improve worksheet preview placeholder with cartoonish grid layout MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Enhanced PagePlaceholder component to show a visual preview of the actual worksheet layout: Layout Matching: - Calculate rows per page correctly (problemsPerPage / cols) - Match exact page dimensions (816×1056 portrait, 1056×816 landscape) - Display cartoonish grid with correct rows × cols matching worksheet Visual Design: - Header bars mimicking name/date fields - Problem cells with mini bars representing: - Problem number (top-left) - Two operands (right-aligned) - Answer line separator - Semi-transparent grid overlay with centered info badge Unified Loading States: - Single component handles both idle and loading states - Idle: "Scroll to load" with slower pulse - Loading: Spinning hourglass with "Loading page X..." - Both show same grid layout for consistency 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude --- .../worksheets/components/PagePlaceholder.tsx | 211 ++++++++++++++++-- .../components/WorksheetPreview.tsx | 39 +--- 2 files changed, 197 insertions(+), 53 deletions(-) diff --git a/apps/web/src/app/create/worksheets/components/PagePlaceholder.tsx b/apps/web/src/app/create/worksheets/components/PagePlaceholder.tsx index 902553d4..e5b732f3 100644 --- a/apps/web/src/app/create/worksheets/components/PagePlaceholder.tsx +++ b/apps/web/src/app/create/worksheets/components/PagePlaceholder.tsx @@ -6,60 +6,229 @@ import { useTheme } from '@/contexts/ThemeContext' interface PagePlaceholderProps { pageNumber: number orientation?: 'portrait' | 'landscape' + rows?: number + cols?: number + loading?: boolean } -export function PagePlaceholder({ pageNumber, orientation = 'portrait' }: PagePlaceholderProps) { +export function PagePlaceholder({ + pageNumber, + orientation = 'portrait', + rows = 5, + cols = 4, + loading = false, +}: PagePlaceholderProps) { const { resolvedTheme } = useTheme() const isDark = resolvedTheme === 'dark' - // Match the aspect ratio of actual worksheet pages - // Portrait: 8.5" × 11" (aspect ratio 1:1.294) - // Landscape: 11" × 8.5" (aspect ratio 1.294:1) - const aspectRatio = orientation === 'portrait' ? 11 / 8.5 : 8.5 / 11 + // Calculate exact pixel dimensions based on page size + // Portrait: 8.5" × 11" at 96 DPI = 816px × 1056px + // Landscape: 11" × 8.5" at 96 DPI = 1056px × 816px + // Scale down to fit typical viewport (maxWidth: 100%) + const width = orientation === 'portrait' ? 816 : 1056 + const height = orientation === 'portrait' ? 1056 : 816 return (
+ {/* Header area (mimics worksheet header with name/date) */}
- 📄 +
+
+ + {/* Problem grid - cartoonish representation */}
- Page {pageNumber} + {Array.from({ length: rows }).map((_, rowIndex) => ( +
+ {Array.from({ length: cols }).map((_, colIndex) => ( +
+ {/* Problem number */} +
+ {/* Top operand */} +
+ {/* Bottom operand */} +
+ {/* Answer line */} +
+
+ ))} +
+ ))}
+ + {/* Page info overlay */}
- Loading... + {loading ? ( + <> +
+ ⏳ +
+
+ Loading page {pageNumber}... +
+ + ) : ( + <> +
+ 📄 +
+
+ Page {pageNumber} +
+
+ Scroll to load +
+ + )}
) diff --git a/apps/web/src/app/create/worksheets/components/WorksheetPreview.tsx b/apps/web/src/app/create/worksheets/components/WorksheetPreview.tsx index 3e6ce456..9e3d4522 100644 --- a/apps/web/src/app/create/worksheets/components/WorksheetPreview.tsx +++ b/apps/web/src/app/create/worksheets/components/WorksheetPreview.tsx @@ -436,39 +436,14 @@ function PreviewContent({ formState, initialData, isScrolling = false }: Workshe })} dangerouslySetInnerHTML={{ __html: page }} /> - ) : isFetching ? ( -
-
- ⏳ -
-

- Loading page {index + 1}... -

-
) : ( - + )}
)