FN-6967: widen tablet agent chat bubbles
Improve tablet Chat readability by widening agent-side response bubbles without expanding user or Quick Chat bubbles. - Add a ChatView container query that widens assistant, streaming, and failure bubbles on tablet-width containers. - Cover the targeted bubble classes and CSS width contract in ChatView tests. - Document the tablet behavior and add a structured patch changeset for the published CLI bundle. Files changed: .changeset/fn-6967-tablet-chat-bubble-width.md | 7 +++ docs/dashboard-guide.md | 3 +- packages/dashboard/app/components/ChatView.css | 12 +++++ .../app/components/__tests__/ChatView.test.tsx | 56 ++++++++++++++++++++++ 4 files changed, 77 insertions(+), 1 deletion(-) Fusion-Task-Id: FN-6967 Fusion-Task-Lineage: 74195885-4ec0-4fc9-b628-0b0510129026
This commit is contained in:
7
.changeset/fn-6967-tablet-chat-bubble-width.md
Normal file
7
.changeset/fn-6967-tablet-chat-bubble-width.md
Normal file
@@ -0,0 +1,7 @@
|
||||
---
|
||||
"@runfusion/fusion": patch
|
||||
---
|
||||
|
||||
summary: Widen tablet Chat View agent response bubbles for easier reading.
|
||||
category: fix
|
||||
dev: Uses ChatView container queries to target assistant, streaming, and failure bubbles without widening user or Quick Chat bubbles.
|
||||
@@ -333,7 +333,8 @@ Chat view provides project-scoped conversations with agents.
|
||||
- On mobile direct-chat threads, entering a thread and restoring Chat after tab/page visibility returns re-anchors to the newest message (`scrollTop = scrollHeight`) so the view always opens at the live tail.
|
||||
- On mobile direct-chat threads, tapping the active title/identity in the thread header opens a lightweight conversation dropdown so you can switch to another direct session without backing out to the sidebar list first; long conversation titles now stay readable in the dropdown via wrapped option text and taller touch-friendly rows.
|
||||
- Direct chat sessions can be renamed from the desktop conversation context menu and from the mobile session switcher; blank rename submissions clear the custom title so the default session label is shown again.
|
||||
- On mobile (`max-width: 768px`), chat bubbles are slightly wider in full Chat for improved readability while preserving header/composer gutters.
|
||||
<!-- FNXC:ChatViewDocs 2026-06-23-11:48: Chat responsive docs need to distinguish the mobile all-bubble readability cap from the tablet main Chat assistant-only widening; Quick Chat remains governed by its narrow container so floating desktop hosts do not inherit the tablet measure. -->
|
||||
- On mobile (`max-width: 768px`), chat bubbles are slightly wider in full Chat for improved readability while preserving header/composer gutters. On tablet-width main Chat containers, assistant/agent, streaming, and failure bubbles use a wider reading measure for long responses while user bubbles and narrow floating Quick Chat hosts stay bounded.
|
||||
- Full Chat tool-call summaries now use a denser mobile layout: grouped and single-call collapsed rows keep icon + label + status on one line (Quick Chat-style scanability) while expanded details remain unchanged.
|
||||
<!-- FNXC:ChatAskQuestion 2026-06-17-16:35: Dashboard chat agents have a Fusion-native `fn_ask_question` tool, so the documented question-card behavior must cover both provider-native question tools and Fusion's first-party tool. -->
|
||||
- Assistant question tool calls now render as a shared in-chat response card instead of a generic tool-call disclosure. The card recognizes provider-native question tools and Fusion's `fn_ask_question`, supports select, multi-select, text, and yes/no prompts, sends the formatted answer back into the same direct or room thread, and renders historical answered questions read-only.
|
||||
|
||||
@@ -973,6 +973,18 @@ In the narrow/mobile chat layout there is no room for an expand/maximize afforda
|
||||
border: var(--btn-border-width) solid var(--status-error-bg-deep);
|
||||
}
|
||||
|
||||
/*
|
||||
FNXC:ChatView 2026-06-23-11:40:
|
||||
Tablet Chat View has enough message-pane width for assistant prose, markdown, tool output, failure details, and attachments, so agent-side bubbles need a wider reading measure than the shared desktop/user cap. Use the ChatView container width instead of the viewport so floating Quick Chat and other narrow hosts keep their bounded bubble layout.
|
||||
*/
|
||||
@container chat-view (min-width: 48.0625rem) and (max-width: 64rem) {
|
||||
.chat-message--assistant,
|
||||
.chat-message--streaming,
|
||||
.chat-message--failure {
|
||||
max-width: 88%;
|
||||
}
|
||||
}
|
||||
|
||||
.chat-message-avatar {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
|
||||
@@ -1378,6 +1378,41 @@ describe("ChatView", () => {
|
||||
expect(within(messageBubble).getByText("run-42")).toBeInTheDocument();
|
||||
});
|
||||
|
||||
it("renders assistant, user, streaming, and failure bubbles with the width-targeting classes", async () => {
|
||||
setupMockChat({
|
||||
activeSession: activeSessionFixture,
|
||||
messages: [
|
||||
{ id: "msg-user", sessionId: "session-001", role: "user", content: "Question", createdAt: "2026-04-08T00:00:00.000Z" },
|
||||
{ id: "msg-assistant", sessionId: "session-001", role: "assistant", content: "Answer", createdAt: "2026-04-08T00:00:01.000Z" },
|
||||
{
|
||||
id: "msg-failure",
|
||||
sessionId: "session-001",
|
||||
role: "assistant",
|
||||
content: "Failed answer",
|
||||
failureInfo: { summary: "Failed answer", detail: "Provider failed" },
|
||||
createdAt: "2026-04-08T00:00:02.000Z",
|
||||
},
|
||||
],
|
||||
isStreaming: true,
|
||||
streamingText: "Live answer",
|
||||
});
|
||||
|
||||
await renderWithAct(<ChatView projectId="proj-123" addToast={vi.fn()} />);
|
||||
|
||||
expect(screen.getByTestId("chat-message-msg-user")).toHaveClass("chat-message", "chat-message--user");
|
||||
expect(screen.getByTestId("chat-message-msg-assistant")).toHaveClass("chat-message", "chat-message--assistant");
|
||||
expect(screen.getByTestId("chat-message-msg-failure")).toHaveClass(
|
||||
"chat-message",
|
||||
"chat-message--assistant",
|
||||
"chat-message--failure",
|
||||
);
|
||||
expect(document.querySelector(".chat-message--streaming")).toHaveClass(
|
||||
"chat-message",
|
||||
"chat-message--assistant",
|
||||
"chat-message--streaming",
|
||||
);
|
||||
});
|
||||
|
||||
it("shows streaming copy action for provider chats", async () => {
|
||||
setupMockChat({
|
||||
activeSession: {
|
||||
@@ -3194,6 +3229,27 @@ describe("ChatView CSS — failure bubble contracts", () => {
|
||||
});
|
||||
});
|
||||
|
||||
describe("ChatView CSS — tablet assistant bubble width", () => {
|
||||
const css = loadAllAppCss();
|
||||
|
||||
it("widens assistant, streaming, and failure bubbles on tablet containers while preserving user and mobile caps", async () => {
|
||||
const baseMessageRule = css.match(/\.chat-message\s*\{([^}]*)\}/);
|
||||
const userRule = css.match(/\.chat-message--user\s*\{([^}]*)\}/);
|
||||
const tabletRule = css.match(
|
||||
/@container\s+chat-view\s+\(min-width:\s*48\.0625rem\)\s+and\s+\(max-width:\s*64rem\)\s*\{([\s\S]*?)\n\}/,
|
||||
);
|
||||
|
||||
expect(baseMessageRule?.[1]).toContain("max-width: 75%");
|
||||
expect(userRule?.[1]).toContain("align-self: flex-end");
|
||||
expect(userRule?.[1]).not.toContain("max-width");
|
||||
expect(tabletRule?.[1]).toMatch(
|
||||
/\.chat-message--assistant,\s*\.chat-message--streaming,\s*\.chat-message--failure\s*\{[^}]*max-width:\s*88%/,
|
||||
);
|
||||
expect(tabletRule?.[1]).not.toMatch(/\.chat-message--user\s*\{[^}]*max-width/);
|
||||
expect(css).toMatch(/@media\s*\(max-width:\s*768px\)[\s\S]*?\.chat-message\s*\{[^}]*max-width:\s*90%/);
|
||||
});
|
||||
});
|
||||
|
||||
describe("ChatView CSS — active state edge highlights", () => {
|
||||
const css = loadAllAppCss();
|
||||
|
||||
|
||||
Reference in New Issue
Block a user