FN-6604: increase task chat send icon size

Increase the Task Detail chat send glyph so it is visibly larger on mobile without changing the touch target.

- Switch the task chat send button icon token from space-lg to space-xl for desktop and mobile rules.
- Add CSS token resolution coverage so the task chat send glyph must exceed the default medium icon size.
- Keep desktop and mobile send button touch target sizing unchanged.

Files changed:
 packages/dashboard/app/components/TaskChatTab.css  |  7 ++--
 .../app/components/__tests__/TaskChatTab.test.tsx  | 37 +++++++++++++++++++---
 2 files changed, 38 insertions(+), 6 deletions(-)

Fusion-Task-Id: FN-6604

Fusion-Task-Lineage: d1708d43-fe1b-4eb2-ab6a-c5954ff00a87
This commit is contained in:
gsxdsm
2026-06-17 18:18:56 -07:00
parent 1d76e9d02c
commit 076ab9fed0
2 changed files with 37 additions and 5 deletions

View File

@@ -371,9 +371,12 @@ FN-6425 requires the chat expand control to stay inside the chat view as an icon
/*
FNXC:TaskDetailChat 2026-06-16-19:45:
FN-6507 requires the Task Detail chat send glyph to scale with the larger square touch target on desktop and mobile. Override only this button's global .btn-icon size so Send and Loader2 stay visually proportional without changing the tap box or sibling chat send buttons.
FNXC:TaskDetailChat 2026-06-17-18:05:
FN-6604 corrects the FN-6507 no-op where var(--space-lg) resolved to the same 16px value as the global --icon-size-md default. Use var(--space-xl) so the glyph resolves to 24px and fills the 40px desktop and mobile send button proportionally while preserving the tap box.
*/
.task-chat-send {
--btn-icon-size: var(--space-lg);
--btn-icon-size: var(--space-xl);
flex: 0 0 auto;
display: inline-flex;
align-items: center;
@@ -474,7 +477,7 @@ FN-6507 requires the Task Detail chat send glyph to scale with the larger square
}
.task-chat-send {
--btn-icon-size: var(--space-lg);
--btn-icon-size: var(--space-xl);
inline-size: calc(var(--space-2xl) + var(--space-sm));
min-inline-size: calc(var(--space-2xl) + var(--space-sm));
}

View File

@@ -97,6 +97,28 @@ function getCssAfter(css: string, marker: string): string {
return markerIndex >= 0 ? css.slice(markerIndex) : "";
}
function getCssDeclaration(rule: string, propertyName: string): string {
const declarationMatch = new RegExp(`${propertyName}\\s*:\\s*([^;]+);`).exec(rule);
return declarationMatch?.[1]?.trim() ?? "";
}
function getRootTokenPxValues(css: string): Record<string, number> {
const rootRule = getCssRuleBlock(css, ":root");
const tokenValues: Record<string, number> = {};
for (const match of rootRule.matchAll(/(--(?:space|icon-size)-[\w-]+)\s*:\s*(\d+)px;/g)) {
tokenValues[match[1]] = Number(match[2]);
}
return tokenValues;
}
function resolveCssPxToken(value: string, tokenValues: Record<string, number>): number {
const tokenName = /^var\((--[\w-]+)\)$/.exec(value.trim())?.[1];
if (!tokenName || tokenValues[tokenName] === undefined) {
throw new Error(`Unable to resolve CSS token value: ${value}`);
}
return tokenValues[tokenName];
}
function mockLogs(
entries: AgentLogEntry[] = [],
loading = false,
@@ -2037,17 +2059,22 @@ describe("TaskChatTab", () => {
it("scales the task chat send glyph without shrinking the desktop or mobile touch target", () => {
const css = readFileSync(resolve(__dirname, "../TaskChatTab.css"), "utf8");
const sharedStyles = readFileSync(resolve(__dirname, "../../styles.css"), "utf8");
const sendRule = getCssRuleBlock(css, ".task-chat-send");
const mobileCss = getCssAfter(css, "@media (max-width: 768px)");
const mobileSendRule = getCssRuleBlock(mobileCss, ".task-chat-send");
const tokenValues = getRootTokenPxValues(sharedStyles);
const defaultIconSizePx = tokenValues["--icon-size-md"];
const desktopIconSizePx = resolveCssPxToken(getCssDeclaration(sendRule, "--btn-icon-size"), tokenValues);
const mobileIconSizePx = resolveCssPxToken(getCssDeclaration(mobileSendRule, "--btn-icon-size"), tokenValues);
expect(sendRule).toContain("--btn-icon-size: var(--space-lg)");
expect(sendRule).not.toContain("--btn-icon-size: var(--icon-size-md)");
expect(defaultIconSizePx).toBe(16);
expect(desktopIconSizePx).toBeGreaterThan(defaultIconSizePx);
expect(mobileIconSizePx).toBeGreaterThan(defaultIconSizePx);
expect(sendRule).toContain("inline-size: calc(var(--space-2xl) + var(--space-sm))");
expect(sendRule).toContain("min-inline-size: calc(var(--space-2xl) + var(--space-sm))");
expect(sendRule).toContain("block-size: calc(var(--space-2xl) + var(--space-sm))");
expect(sendRule).toContain("min-block-size: calc(var(--space-2xl) + var(--space-sm))");
expect(mobileSendRule).toContain("--btn-icon-size: var(--space-lg)");
expect(mobileSendRule).toContain("inline-size: calc(var(--space-2xl) + var(--space-sm))");
expect(mobileSendRule).toContain("min-inline-size: calc(var(--space-2xl) + var(--space-sm))");
});
@@ -2085,12 +2112,14 @@ describe("TaskChatTab", () => {
expect(css).toContain(".task-chat-transcript");
expect(css).toContain(".task-chat-jump-to-bottom");
expect(css).toContain(".task-chat-composer-row");
expect(sendRule).toContain("--btn-icon-size: var(--space-xl)");
expect(sendRule).toContain("inline-size: calc(var(--space-2xl) + var(--space-sm))");
expect(sendRule).toContain("block-size: calc(var(--space-2xl) + var(--space-sm))");
expect(sendRule).not.toContain("gap");
expect(mobileComposerRule).toContain("align-items: flex-end");
expect(mobileComposerRule).not.toContain("flex-direction: column");
expect(mobileComposerRule).not.toContain("align-items: stretch");
expect(mobileSendRule).toContain("--btn-icon-size: var(--space-xl)");
expect(mobileSendRule).toContain("inline-size: calc(var(--space-2xl) + var(--space-sm))");
expect(css).toContain(".task-chat-tool-group-summary");
expect(css).toContain(".task-chat-tool-group-names");