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
18 changes: 7 additions & 11 deletions packages/web/app/help/help.module.css
Original file line number Diff line number Diff line change
@@ -1,16 +1,12 @@
/*
* Color values match themeTokens from theme-config.ts
* CSS modules cannot import JS, so hex values are used directly
* (same pattern as about.module.css)
*/
/* Uses CSS custom properties from index.css (derived from theme-config.ts) */

.pageLayout {
min-height: 100vh;
background: #f9fafb;
background: var(--semantic-background);
}

.header {
background: #ffffff;
background: var(--semantic-surface);
padding: 0 16px;
display: flex;
align-items: center;
Expand Down Expand Up @@ -43,7 +39,7 @@

.heroIcon {
font-size: 48px;
color: #06b6d4;
color: var(--color-primary);
margin-bottom: 16px;
}

Expand All @@ -68,15 +64,15 @@

.sectionIcon {
margin-right: 8px;
color: #06b6d4;
color: var(--color-primary);
}

.mainCollapse {
background: transparent;
}

.nestedCollapse {
background: #f9fafb;
background: var(--neutral-50);
}

.answerContent {
Expand Down Expand Up @@ -110,7 +106,7 @@
max-width: 100%;
border-radius: 8px;
margin-bottom: 16px;
border: 1px solid #e5e7eb;
border: 1px solid var(--neutral-200);
}

@media (max-width: 576px) {
Expand Down
66 changes: 43 additions & 23 deletions packages/web/e2e/help-screenshots.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -34,9 +34,12 @@ test.describe('Help Page Screenshots', () => {
// Click Start Climbing button
await page.getByRole('button', { name: 'Start Climbing' }).click();

// Wait for the board page to load
// Wait for the board page to load - wait for climb list or board to render
await page.waitForURL(/\/kilter\//);
await page.waitForTimeout(2000); // Allow time for content to render
await page.waitForSelector('[data-testid="board-renderer"], .ant-list-items', { timeout: 10000 }).catch(() => {
// Fallback: wait for any main content to appear
return page.waitForSelector('.ant-layout-content', { state: 'visible' });
});
});

test('main interface', async ({ page }) => {
Expand All @@ -45,23 +48,26 @@ test.describe('Help Page Screenshots', () => {

test('search filters', async ({ page }) => {
await page.getByRole('tab', { name: 'Search', exact: true }).click();
await page.waitForTimeout(500);
// Wait for search form content to be visible
await page.waitForSelector('.ant-collapse, .ant-form', { state: 'visible' });
await page.screenshot({ path: `${SCREENSHOT_DIR}/search-filters.png` });
});

test('search by hold', async ({ page }) => {
await page.getByRole('tab', { name: 'Search by Hold' }).click();
await page.waitForTimeout(500);
// Wait for the hold search tab content
await page.waitForSelector('button:has-text("Show Heatmap"), button:has-text("Hide Heatmap")', { state: 'visible' });
await page.screenshot({ path: `${SCREENSHOT_DIR}/search-by-hold.png` });
});

test('heatmap', async ({ page }) => {
await page.getByRole('tab', { name: 'Search by Hold' }).click();
await page.getByRole('button', { name: 'Show Heatmap' }).click();

// Wait for heatmap to load
// Wait for heatmap loading to complete
await page.waitForSelector('text=Loading heatmap...', { state: 'hidden', timeout: 10000 }).catch(() => {});
await page.waitForTimeout(1000);
// Wait for heatmap controls or canvas to be visible
await page.waitForSelector('button:has-text("Hide Heatmap")', { state: 'visible' });

await page.screenshot({ path: `${SCREENSHOT_DIR}/heatmap.png` });
});
Expand All @@ -70,21 +76,25 @@ test.describe('Help Page Screenshots', () => {
// Click on the first climb's info button
await page.getByRole('link', { name: 'info-circle' }).first().click();
await page.waitForURL(/\/view\//);
await page.waitForTimeout(1000);
// Wait for climb details to load
await page.waitForSelector('.ant-descriptions, .ant-card-body', { state: 'visible' });

await page.screenshot({ path: `${SCREENSHOT_DIR}/climb-detail.png` });
});

test('party mode modal', async ({ page }) => {
await page.getByRole('button', { name: 'team' }).click();
await page.waitForTimeout(500);
// Wait for drawer content to be visible
await page.waitForSelector('.ant-drawer-body', { state: 'visible' });

await page.screenshot({ path: `${SCREENSHOT_DIR}/party-mode.png` });
});

test('login modal', async ({ page }) => {
await page.getByRole('button', { name: 'Login' }).click();
await page.waitForTimeout(500);
// Wait for modal with login form to be visible
await page.waitForSelector('.ant-modal-content', { state: 'visible' });
await page.waitForSelector('input#login_email', { state: 'visible' });

await page.screenshot({ path: `${SCREENSHOT_DIR}/login-modal.png` });
});
Expand All @@ -105,29 +115,34 @@ test.describe('Help Page Screenshots - Authenticated', () => {
await page.getByRole('option', { name: 'Kilter' }).click();
await page.getByRole('button', { name: 'Start Climbing' }).click();
await page.waitForURL(/\/kilter\//);
await page.waitForTimeout(2000);
await page.waitForSelector('[data-testid="board-renderer"], .ant-list-items', { timeout: 10000 }).catch(() => {
return page.waitForSelector('.ant-layout-content', { state: 'visible' });
});

// Login via auth modal
await page.getByRole('button', { name: 'Login' }).click();
await page.waitForTimeout(500);
await page.waitForSelector('input#login_email', { state: 'visible' });

// Fill login form
await page.locator('input#login_email').fill(testEmail!);
await page.locator('input#login_password').fill(testPassword!);
await page.locator('button[type="submit"]').filter({ hasText: 'Login' }).click();

// Wait for login to complete
await page.waitForTimeout(2000);
// Wait for login to complete - modal should close and user button should appear
await page.waitForSelector('.ant-modal-content', { state: 'hidden', timeout: 10000 });
await page.waitForSelector('button:has(.anticon-user)', { state: 'visible', timeout: 5000 }).catch(() => {
// Alternative: wait for any indication of logged-in state
return page.waitForSelector('text=Logout', { state: 'attached' });
});
});

test('personal progress filters', async ({ page }) => {
// Open search tab to show personal progress filters
await page.getByRole('tab', { name: 'Search', exact: true }).click();
await page.waitForTimeout(500);
await page.waitForSelector('.ant-collapse, .ant-form', { state: 'visible' });

// Scroll to Personal Progress section
await page.evaluate(() => {
const element = document.querySelector('.ant-collapse-header-text');
const headers = document.querySelectorAll('.ant-collapse-header-text');
for (const header of headers) {
if (header.textContent?.includes('Personal Progress')) {
Expand All @@ -136,19 +151,20 @@ test.describe('Help Page Screenshots - Authenticated', () => {
}
}
});
await page.waitForTimeout(500);

await page.screenshot({ path: `${SCREENSHOT_DIR}/personal-progress.png` });
});

test('party mode active session', async ({ page }) => {
// Open party mode drawer
await page.getByRole('button', { name: 'team' }).click();
await page.waitForTimeout(500);
await page.waitForSelector('.ant-drawer-body', { state: 'visible' });

// Start a party session
await page.getByRole('button', { name: 'Start Party Mode' }).click();
await page.waitForTimeout(3000); // Wait for session to connect

// Wait for session to be active - look for Leave button or session ID indicator
await page.waitForSelector('button:has-text("Leave")', { state: 'visible', timeout: 10000 });

await page.screenshot({ path: `${SCREENSHOT_DIR}/party-mode-active.png` });

Expand All @@ -158,18 +174,23 @@ test.describe('Help Page Screenshots - Authenticated', () => {

test('hold classification wizard', async ({ page }) => {
// Open user menu and click Classify Holds
await page.locator('button').filter({ hasText: /Marco|User/ }).first().click();
await page.waitForTimeout(300);
await page.locator('button:has(.anticon-user)').first().click();
await page.waitForSelector('.ant-dropdown', { state: 'visible' });
await page.getByText('Classify Holds').click();
await page.waitForTimeout(1000); // Wait for wizard to load

// Wait for wizard drawer to open and content to load
await page.waitForSelector('.ant-drawer-body', { state: 'visible' });
// Wait for hold content or progress indicator
await page.waitForSelector('.ant-rate, .ant-progress', { state: 'visible', timeout: 10000 });

await page.screenshot({ path: `${SCREENSHOT_DIR}/hold-classification.png` });
});

test('settings aurora sync', async ({ page }) => {
// Navigate to settings page
await page.goto('/settings');
await page.waitForTimeout(1000);
// Wait for settings page content to load
await page.waitForSelector('.ant-card', { state: 'visible' });

// Scroll to Board Accounts section
await page.evaluate(() => {
Expand All @@ -179,7 +200,6 @@ test.describe('Help Page Screenshots - Authenticated', () => {
heading.scrollIntoView({ behavior: 'instant', block: 'start' });
}
});
await page.waitForTimeout(500);

await page.screenshot({ path: `${SCREENSHOT_DIR}/settings-aurora.png` });
});
Expand Down
Loading