import Input from "@moduletrace/twui/form/Input"; import Radios from "@moduletrace/twui/form/Radios"; import Span from "@moduletrace/twui/layout/Span"; import Stack from "@moduletrace/twui/layout/Stack"; import { AppData } from "@/src/data/app-data"; import type { BotQuestionAnswer, BotQuestionItem } from "@/src/types"; import type { BotQuestionDraft } from "../(utils)/bot-question-draft-answer"; import BotQuestionOption from "./bot-question-option"; import MessageDetailsHeading from "./message-details-heading"; type Props = { question_id: number; index: number; item: BotQuestionItem; draft: BotQuestionDraft; /** * What the user answered, once they did. */ answer: BotQuestionAnswer | null; /** * Whether it still takes answers. */ open: boolean; onChange: (draft: BotQuestionDraft) => void; }; /** * Value of the "Other" radio, beside the options' indexes. */ const OtherValue = "other"; /** * One of a bot's questions in its card: the question, then its options as * radios (one pick) or checkboxes (several), with "Other" and a field to * type into when the bot allows it. Once answered, what the user picked. */ export default function BotQuestionField({ question_id, index, item, draft, answer, open, onChange }: Props) { const single = item.kind == "single"; const picked = answer ? [...answer.choices.map((choice) => item.options[choice]), answer.other ? `Other: ${answer.other}` : ""].filter(Boolean) : []; return ( {`${index + 1}. ${single ? "Pick one" : "Pick any"}`} {item.question} {open ? ( {single ? ( ({ value: String(choice), title: option })), ...(item.allow_other ? [{ value: OtherValue, title: "Other" }] : []), ]} wrapperProps={{ className: "w-full flex-col items-start gap-2!" }} labelProps={{ className: "text-[13px] leading-5 text-ink break-words cursor-pointer" }} changeHandler={(value) => onChange( value == OtherValue ? { ...draft, choices: [], other_on: true } : { ...draft, choices: [Number(value)], other_on: false }, ) } /> ) : ( {item.options.map((option, choice) => ( onChange({ ...draft, choices: checked ? [...new Set([...draft.choices, choice])] : draft.choices.filter((c) => c != choice), }) } /> ))} {item.allow_other ? ( onChange({ ...draft, other_on: checked })} /> ) : null} )} {draft.other_on ? ( onChange({ ...draft, other: e.target.value })} /> ) : null} ) : answer ? ( {picked.join("; ")} ) : null} ); }