Skip to content
Component installs need the registry setup
VegaStack Design

Agent Question Form

An agent asks one to five questions at once — options with their descriptions in view, the first recommended, own words and a note, previews and a review.

Status
stable
Since
0.59.0
Accessibility pattern
named steps, keyed choices, focus follows the step

Last updated

How should the task page be laid out?
PreviewSidebar
┌──────────────┬───────────────────────────┐
│ Sidebar      │ Task list                 │
│ ▸ Inbox      │ ☐ Order 3000 K samples    │
│ ▸ Projects   │ ☐ Update the datasheet    │
└──────────────┴───────────────────────────┘

Install

Configure registry credentials first using the Quickstart. Before copying this item or any transitive registry dependency, verify the signed manifest and save the exact bytes for Agent Question Form before installation. Retain the digest printed by this command.

pnpm exec vegastack-design verify agent-question-form

Install with the pinned shadcn CLI. Bare shadcn does not verify VegaStack signature or integrity.

pnpm dlx shadcn@4.21.0 add @vegastack/agent-question-form

Run the exact offline --post-write command printed by the preflight, using its saved item path and independently retained --expected-integrity digest. Use the saved preflight for every transitive registry dependency too; stop on any mismatch before using the components.

The same command installs the registry items it composes: @vegastack/badge, @vegastack/button, @vegastack/questionnaire, @vegastack/textarea.

Usage

import {
  AgentQuestionAnswers,
  AgentQuestionForm,
} from "@/components/ui/agent-question-form";

<AgentQuestionForm
  questions={questions}
  onSubmit={async (answers) => {
    const sent = await answerAgent(answers);
    return sent ? null : "Couldn't send your answers. Try again.";
  }}
/>;

onSubmit gets one answer per question, in order: { selected, other?, notes? }, where selected holds the chosen options' labels. Resolve with an error to show it under the form, which stays editable; resolve with null once sent, and the form stays disabled. Afterwards, show what was answered with AgentQuestionAnswers.

How should the task page be laid out?
PreviewSidebar
┌──────────────┬───────────────────────────┐
│ Sidebar      │ Task list                 │
│ ▸ Inbox      │ ☐ Order 3000 K samples    │
│ ▸ Projects   │ ☐ Update the datasheet    │
└──────────────┴───────────────────────────┘

Scope

  • The first option is the recommended one and carries the badge. Order the options so it is.
  • Every option shows its description in full. Nothing hides behind a tooltip.
  • The person can always answer in their own words (Other), and add a note to any question.
  • Every word is a prop in labels, with an English default.

Anatomy

AgentQuestionForm
AgentQuestionAnswers — data-slot="agent-question-answer" | "agent-question-answers"

Examples

Compact

One single-choice question with no previews is compact: the options are cards, and picking one sends it at once. Other opens a box for the person's own words with a Send button.

Colour

Which colour temperature should the IP65 range use?

Narrow

In a side panel the preview drops below the choices and scrolls sideways inside its own box; from a 42rem container it sits beside them. This one fails on submit, to show the error.

How should the task page be laid out?
PreviewSidebar
┌──────────────┬───────────────────────────┐
│ Sidebar      │ Task list                 │
│ ▸ Inbox      │ ☐ Order 3000 K samples    │
│ ▸ Projects   │ ☐ Update the datasheet    │
└──────────────┴───────────────────────────┘

Answers

AgentQuestionAnswers lists each header with the chosen options, own words and note, wrapped in full.

Layout
Sidebar
Notify
Assignee, Channel
Note: Only the channel for tasks due this week.
Due date
Other: Two working days, skipping weekends.

API Reference

PropTypeDefaultDescription
onSubmit*(answers: AgentQuestionFormAnswer[]) => Promise<string | null>—Sends the answers, one per question in order. Resolve with an error to show (the form stays editable), or null once sent (the form then stays disabled). A rejection shows its message.
questions*AgentQuestionFormQuestion[]—One to five questions, asked together and answered together.
classNamestring—Classes on the root.
disabledbooleanfalseNothing can be changed or sent: answered elsewhere, or the question expired.
labelsPartial<AgentQuestionFormLabels>{}The words, each with an English default.
limits{ other?: number; notes?: number; }{ other: 4000, notes: 1000 }Character limits for the person's own words and notes.

AgentQuestionFormQuestion

PropTypeDefaultDescription
header*string—A short chip naming the question: "Colour".
options*AgentQuestionFormOption[]—Two to four options; the first is the recommended one.
question*string—The question itself.
multiSelectbooleanfalseCheckboxes instead of radios: any number of options may be chosen.

AgentQuestionFormOption

PropTypeDefaultDescription
label*string—What the person picks, and what the answer reports: "Use 4000 K".
descriptionstring—One sentence on what picking it means. Always shown, never a tooltip.
previewstring—Monospace text shown while the option is focused, hovered or chosen: an ASCII layout, a code snippet, a draft. Kept whole, scrolled sideways when wide.

AgentQuestionAnswers

PropTypeDefaultDescription
answers*AgentQuestionFormAnswer[]—The answers, one per question in order.
questions*AgentQuestionFormQuestion[]—The questions that were asked.
classNamestring—Classes on the list.
labelsPartial<Pick<AgentQuestionFormLabels, "noAnswer" | "notes" | "other">>{}The words: other, notes and noAnswer.

Data attributes and CSS variables on AgentQuestionAnswers

AttributeValues
data-slot"agent-question-answer" | "agent-question-answers"

Accessibility

  • The compact form is a group named by its question; each option is a button whose name includes its description.
  • The full form is a Questionnaire: each question is a fieldset named by its text, its options are radios or checkboxes, and a multi-select question says "Choose any". The step chips are a navigation list, the current one marked aria-current="step".
  • Focus moves to the question when the step changes. A failed submit shows its message as an alert.
  • The preview is a focusable box, so it can be scrolled from the keyboard.
KeyAction
1–5Pick an option (the last number is Other)
↑ / ↓Move between options
EnterNext, once the question is answered
← / →Previous or next question
ContractStates tested
Behaviourcompact, full, single-select, multi-select, other, notes, preview, review, submitting, error, sent, disabled
Accessibilitylabelled-group, step-navigation-aria-current, number-key-shortcuts, focus-on-step-change, alert-on-error, aria-busy, browser-accessibility-test
Visualcompact, full, preview-below, preview-beside, review

Do / Don't

Do
Put the option you recommend first and say in one sentence what each one means.
Don't
Ask a yes/no question about one action — that is an ApprovalCard.

On this page