Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
31 changes: 26 additions & 5 deletions packages/design/src/Form/Form.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,16 @@ export default function Form({

const formMethods = useForm<Record<string, string>>({});

// Reset React Hook Form when route changes (e.g., page navigation in FormPreview)
// This prevents field values from bleeding across pages
// Only reset when we have an onSubmit handler (FormPreview mode), not in FormEdit mode
const hasOnSubmit = !!onSubmit;
useEffect(() => {
if (isPreview && hasOnSubmit) {
formMethods.reset({});
}
}, [session.route?.params.page, isPreview, hasOnSubmit]);

return (
<FormProvider {...formMethods}>
<div className="preview grid-container">
Expand Down Expand Up @@ -114,6 +124,19 @@ export default function Form({
>
<FormContents context={context} prompt={prompt} />
</form>
) : onSubmit ? (
<form
className="usa-form margin-bottom-3 maxw-full formContentWrapper"
encType="multipart/form-data"
onSubmit={formMethods.handleSubmit(async (data, event) => {
event?.preventDefault();
onSubmit(data);
})}
method="POST"
aria-label={session.form.summary.title || 'Form'}
>
<FormContents context={context} prompt={prompt} />
</form>
) : (
<div className="formContentWrapper">
<FormContents context={context} prompt={prompt} />
Expand All @@ -134,10 +157,8 @@ const FormContents = ({
prompt: Prompt;
}) => {
return (
<>
<fieldset className="usa-fieldset width-full">
{renderPromptComponents(context, prompt.components)}
</fieldset>
</>
<fieldset className="usa-fieldset width-full">
{renderPromptComponents(context, prompt.components)}
</fieldset>
);
};
40 changes: 37 additions & 3 deletions packages/design/src/FormManager/FormPreview/FormPreview.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import React, { useEffect } from 'react';
import { useNavigate } from 'react-router-dom';

import { mergeSession } from '@flexion/forms-core';
import { applyPromptResponse, mergeSession } from '@flexion/forms-core';

import Form from '../../Form/Form.js';
import { useRouteParams } from '../hooks.js';
Expand All @@ -12,7 +13,8 @@ export const FormPreview = () => {
setSession: state.setSession,
}));
const session = useFormManagerStore(state => state.session);
const { routeParams } = useRouteParams();
const { routeParams, pathname } = useRouteParams();
const navigate = useNavigate();

useEffect(() => {
if (routeParams.page !== session.route?.params.page) {
Expand All @@ -27,5 +29,37 @@ export const FormPreview = () => {
}
}, [routeParams.page]);

return <Form isPreview={true} context={context} session={session} />;
const handleSubmit = (data: Record<string, string>) => {
// Validate and update session with form data
const result = applyPromptResponse(context.config, session, {
action: 'submit',
data,
});

if (!result.success) {
console.warn('Error applying prompt response in preview...', result.error);
return;
}

// Update session with validated data
setSession(result.data);

// Navigate to next page
const currentPage = Number(routeParams.page) || 0;
const nextPage = currentPage + 1;
const newParams = new URLSearchParams({
...routeParams,
page: nextPage.toString(),
});
navigate(`${pathname}?${newParams.toString()}`);
};

return (
<Form
isPreview={true}
context={context}
session={session}
onSubmit={handleSubmit}
/>
);
};