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
10 changes: 9 additions & 1 deletion webviews/src/agent-session/acpmux/conversation/conversation.css
Original file line number Diff line number Diff line change
Expand Up @@ -494,7 +494,7 @@
pane's right edge, its own width (data-enter, ui/presence.ts). */
.acpmux-artifact {
--ui-enter-distance: 100%;
flex: 0 0 clamp(320px, 46%, 760px);
flex: 0 0 var(--acpmux-artifact-width, clamp(320px, 46vw, 760px));
min-width: 0;
display: flex;
flex-direction: column;
Expand All @@ -509,13 +509,21 @@
margin-top: var(--acpmux-tab-row-height);
max-height: calc(100% - var(--acpmux-tab-row-height));
}
/* The header lives in the chat column while Preview is a shell sibling. Keep its tools at the
pane edge, across the Preview column, just as the inline Summary does. */
.acpmux-shell[data-tab-row]:has(> .acpmux-artifact) .acpmux-header[data-tab-row] {
width: calc(100% + var(--acpmux-artifact-width, clamp(320px, 46vw, 760px)));
}
@media (max-width: 720px) {
.acpmux-artifact {
position: absolute;
inset: 0;
z-index: var(--layer-overlay);
box-shadow: none;
}
.acpmux-shell[data-tab-row]:has(> .acpmux-artifact) .acpmux-header[data-tab-row] {
width: 100%;
}
}
.acpmux-artifact-bar {
flex: 0 0 44px;
Expand Down
82 changes: 57 additions & 25 deletions webviews/test/summary-header-surface.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,10 @@ await requireBrowserLane("summary-header-surface.test.ts", async () => {
});
await server.listen();
browser = await chromium.launch({ headless: true });
await warmGalleryFrame(server, "agent-pane.summary-card", { browser, params: { variant: "shared-tab-row" } });
await warmGalleryFrame(server, "agent-pane.summary-card", {
browser,
params: { variant: "shared-tab-row" },
});
});
afterAll(async () => {
await browser?.close();
Expand All @@ -28,7 +31,9 @@ await requireBrowserLane("summary-header-surface.test.ts", async () => {
for (const height of [28, 40]) {
for (const theme of ["Apple System Colors", "Apple System Colors Light"]) {
test(`inline Summary leaves the ${height}px native tools row clear (${theme})`, async () => {
const page = await browser.newPage({ viewport: { width: 720, height: 560 } });
const page = await browser.newPage({
viewport: { width: 720, height: 560 },
});
try {
const port = (server.httpServer!.address() as { port: number }).port;
await page.goto(
Expand All @@ -39,7 +44,9 @@ await requireBrowserLane("summary-header-surface.test.ts", async () => {
(node as HTMLElement).style.setProperty("--acpmux-tab-row-height", `${pixels}px`);
}, height);
if (process.env.CMUX_SUMMARY_CAPTURE_DIR) {
await mkdir(process.env.CMUX_SUMMARY_CAPTURE_DIR, { recursive: true });
await mkdir(process.env.CMUX_SUMMARY_CAPTURE_DIR, {
recursive: true,
});
await page.screenshot({
path: path.join(
process.env.CMUX_SUMMARY_CAPTURE_DIR,
Expand Down Expand Up @@ -100,29 +107,54 @@ await requireBrowserLane("summary-header-surface.test.ts", async () => {
}
for (const width of [640, 1000]) {
for (const height of [28, 40]) {
test(`Preview leaves the ${height}px native row clear at ${width}px`, async () => {
const page = await browser.newPage({ viewport: { width, height: 560 }, reducedMotion: "reduce" });
try {
const port = (server.httpServer!.address() as { port: number }).port;
await page.goto(
`http://127.0.0.1:${port}${galleryFrame("agent-pane.summary-card", { variant: "preview-tab-row" })}`,
);
await page.waitForFunction(() => document.documentElement.dataset.galleryReady === "1");
await page.locator(".acpmux-shell").evaluate((node, pixels) => {
(node as HTMLElement).style.setProperty("--acpmux-tab-row-height", `${pixels}px`);
}, height);
await page.locator(".acpmux-artifact").waitFor();
const actual = await page.evaluate(() => {
const shell = document.querySelector(".acpmux-shell")!.getBoundingClientRect();
const panel = document.querySelector(".acpmux-artifact")!.getBoundingClientRect();
return { top: panel.top - shell.top, bottom: panel.bottom - shell.bottom };
for (const theme of ["Apple System Colors", "Apple System Colors Light"]) {
test(`Preview leaves the ${height}px native row clear at ${width}px (${theme})`, async () => {
const page = await browser.newPage({
viewport: { width, height: 560 },
reducedMotion: "reduce",
});
expect(actual.top).toBe(height);
expect(actual.bottom).toBeLessThanOrEqual(0);
} finally {
await page.close();
}
});
try {
const port = (server.httpServer!.address() as { port: number }).port;
await page.goto(
`http://127.0.0.1:${port}${galleryFrame("agent-pane.summary-card", { variant: "preview-tab-row", theme })}`,
);
await page.waitForFunction(() => document.documentElement.dataset.galleryReady === "1");
await page.locator(".acpmux-shell").evaluate((node, pixels) => {
(node as HTMLElement).style.setProperty("--acpmux-tab-row-height", `${pixels}px`);
}, height);
await page.locator(".acpmux-artifact").waitFor();
if (process.env.CMUX_SUMMARY_CAPTURE_DIR) {
await mkdir(process.env.CMUX_SUMMARY_CAPTURE_DIR, {
recursive: true,
});
await page.screenshot({
path: path.join(
process.env.CMUX_SUMMARY_CAPTURE_DIR,
`preview-${height}-${width}-${theme.endsWith("Light") ? "light" : "dark"}.png`,
),
});
}
const actual = await page.evaluate(() => {
const shell = document.querySelector(".acpmux-shell")!.getBoundingClientRect();
const panel = document.querySelector(".acpmux-artifact")!.getBoundingClientRect();
const tools = document.querySelector<HTMLElement>(".acpmux-header-tools")!.getBoundingClientRect();
return {
top: panel.top - shell.top,
bottom: panel.bottom - shell.bottom,
toolsWidth: tools.width,
toolsRight: tools.right,
shellRight: shell.right,
};
});
expect(actual.top).toBe(height);
expect(actual.bottom).toBeLessThanOrEqual(0);
expect(actual.toolsWidth).toBeGreaterThan(0);
expect(actual.toolsRight).toBe(actual.shellRight);
} finally {
await page.close();
}
});
}
}
}
});
Loading