fix(web): clear prompt when removing Home example chip (#2989) (#3045)

Removing the selected example prompt chip now also clears the composer
input so chip state stays in sync with the inserted example text.
This commit is contained in:
吴杨帆 2026-05-27 14:21:35 +08:00 committed by GitHub
parent a72d66d243
commit 26ef90ffd9
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
2 changed files with 49 additions and 1 deletions

View file

@ -538,6 +538,13 @@ export const HomeHero = forwardRef<HTMLTextAreaElement, Props>(function HomeHero
onAddFiles(files);
}
function clearSelectedPromptExample() {
if (selectedPromptExample) {
onPromptChange('');
}
setSelectedPromptExample(null);
}
function usePromptExample(example: string) {
setSelectedPromptExample({
label: promptExampleChipLabel(example),
@ -748,7 +755,7 @@ export const HomeHero = forwardRef<HTMLTextAreaElement, Props>(function HomeHero
<button
type="button"
className="home-hero__active-clear"
onClick={() => setSelectedPromptExample(null)}
onClick={clearSelectedPromptExample}
aria-label={t('common.close')}
title={t('common.close')}
>

View file

@ -10,6 +10,7 @@
import { cleanup, fireEvent, render, screen } from '@testing-library/react';
import { afterEach, describe, expect, it, vi } from 'vitest';
import { useState } from 'react';
import type { InstalledPluginRecord } from '@open-design/contracts';
import { HomeHero } from '../../src/components/HomeHero';
@ -187,6 +188,46 @@ describe('HomeHero intent rail', () => {
expect(screen.getByTestId('home-hero-active-example').textContent).toContain('...');
});
it('clears the prompt input when the selected example chip is removed', () => {
function StatefulHero() {
const [prompt, setPrompt] = useState('');
return (
<HomeHero
prompt={prompt}
onPromptChange={setPrompt}
onSubmit={() => undefined}
activePluginTitle={null}
activeChipId="deck"
onClearActivePlugin={() => undefined}
pluginOptions={[]}
pluginsLoading={false}
pendingPluginId={null}
pendingChipId={null}
onPickPlugin={() => undefined}
onPickExamplePlugin={() => undefined}
onPickChip={() => undefined}
onClearActiveChip={() => undefined}
contextItemCount={0}
error={null}
/>
);
}
render(<StatefulHero />);
const examples = screen.getAllByTestId('home-hero-prompt-example');
fireEvent.click(examples[0]!);
const input = screen.getByTestId('home-hero-input') as HTMLTextAreaElement;
expect(input.value).toContain('Research the market opportunity');
expect(screen.getByTestId('home-hero-active-example')).toBeTruthy();
fireEvent.click(screen.getByTestId('home-hero-active-example').querySelector('.home-hero__active-clear')!);
expect(input.value).toBe('');
expect(screen.queryByTestId('home-hero-active-example')).toBeNull();
});
it('shows matching plugin presets in the example prompt area for the selected tab', () => {
const deckPlugin = makePlugin('example-deck-a', 'deck', 'Investor deck');
const imagePlugin = makePlugin('example-image-a', 'image', 'Product image');