fix(web): disable the enlarge button along with its field
Copilot review round 2 on #2109. A disabled form (a tool call in flight) left the enlarge button live, and activating it swapped in a text area that mounts disabled — so the focus hand-off targeted an unfocusable element and keyboard focus was dropped to the document. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01JTHVxSu8AUgHRLvo1ntZ8H Signed-off-by: cliffhall <cliff@futurescale.com>
This commit is contained in:
parent
925ff4de2f
commit
7db596b5e6
4 changed files with 42 additions and 2 deletions
|
|
@ -33,4 +33,14 @@ describe("EnlargeButton", () => {
|
|||
screen.getByRole("button", { name: "Enlarge Query" }),
|
||||
).toBeInTheDocument();
|
||||
});
|
||||
|
||||
it("is inert when the field it belongs to is disabled", async () => {
|
||||
const user = userEvent.setup();
|
||||
const onClick = vi.fn();
|
||||
renderWithMantine(<EnlargeButton onClick={onClick} disabled />);
|
||||
const button = screen.getByRole("button", { name: "Enlarge" });
|
||||
expect(button).toBeDisabled();
|
||||
await user.click(button);
|
||||
expect(onClick).not.toHaveBeenCalled();
|
||||
});
|
||||
});
|
||||
|
|
|
|||
|
|
@ -11,6 +11,12 @@ export interface EnlargeButtonProps {
|
|||
* tell them apart; the visible tooltip stays the plain verb.
|
||||
*/
|
||||
ariaLabel?: string;
|
||||
/**
|
||||
* Mirrors the disabled state of the input this sits in. A live button on a
|
||||
* disabled field would still swap in the text area — which mounts disabled and
|
||||
* cannot take focus, dropping keyboard focus to the document.
|
||||
*/
|
||||
disabled?: boolean;
|
||||
}
|
||||
|
||||
const EnlargeActionIcon = ActionIcon.withProps({
|
||||
|
|
@ -34,10 +40,18 @@ const EnlargeActionIcon = ActionIcon.withProps({
|
|||
* of the tab order without cost; entering multiline mode has none, so removing
|
||||
* this one would put the feature out of reach of keyboard users entirely.
|
||||
*/
|
||||
export function EnlargeButton({ onClick, ariaLabel }: EnlargeButtonProps) {
|
||||
export function EnlargeButton({
|
||||
onClick,
|
||||
ariaLabel,
|
||||
disabled,
|
||||
}: EnlargeButtonProps) {
|
||||
return (
|
||||
<Tooltip label="Enlarge">
|
||||
<EnlargeActionIcon aria-label={ariaLabel ?? "Enlarge"} onClick={onClick}>
|
||||
<EnlargeActionIcon
|
||||
aria-label={ariaLabel ?? "Enlarge"}
|
||||
disabled={disabled}
|
||||
onClick={onClick}
|
||||
>
|
||||
<ImEnlarge2 size={12} />
|
||||
</EnlargeActionIcon>
|
||||
</Tooltip>
|
||||
|
|
|
|||
|
|
@ -1954,4 +1954,19 @@ describe("SchemaForm multiline strings (#2042)", () => {
|
|||
await user.keyboard("{Enter}more");
|
||||
expect(textarea.value).toBe("typed\nmore");
|
||||
});
|
||||
|
||||
// A disabled form (a tool call in flight) must be inert as a whole: a live
|
||||
// button there would swap in a text area that mounts disabled, cannot take
|
||||
// focus, and so drops keyboard focus to the document.
|
||||
it("disables the enlarge button along with the field", () => {
|
||||
renderWithMantine(
|
||||
<SchemaForm
|
||||
schema={stringSchema}
|
||||
values={{}}
|
||||
onChange={vi.fn()}
|
||||
disabled
|
||||
/>,
|
||||
);
|
||||
expect(screen.getByRole("button", { name: "Enlarge Note" })).toBeDisabled();
|
||||
});
|
||||
});
|
||||
|
|
|
|||
|
|
@ -713,6 +713,7 @@ export function SchemaForm({
|
|||
<FieldActions>
|
||||
<EnlargeButton
|
||||
ariaLabel={`Enlarge ${label}`}
|
||||
disabled={disabled}
|
||||
onClick={() =>
|
||||
setEnlargedFields(
|
||||
(previous) => new Set([...previous, fieldName]),
|
||||
|
|
|
|||
Loading…
Reference in a new issue