useStepLayout
useStepLayout(...) splits a form into successive steps.
Signature
ts
useStepLayout(
[
stepA,
stepB,
stepC,
],
{
errorMessageNotAtLastStep: string,
class?: string,
template?: Templates["step"],
},
);Parameters
formFields: tuple ofFormFieldinstances, one per step.errorMessageNotAtLastStep: message displayed whencheck()is called before the last step.class: CSS class added to thesteptemplate.template: local override of thesteptemplate.
Produced value
Current value
ts
{
currentStep: number;
steps: unknown[];
}Validated value
ts
unknown[]If an error is detected during check(), the layout automatically resets currentStep to the first failing step.
step template contract
Props
ts
{
fieldKey: string;
stepQuantity: number;
isLastStep(): boolean;
getFormFields(): (() => VNode)[];
getCurrentValue(): unknown;
getCurrentStep(): number;
getErrorMessageNotAtLastStep(): null | string;
}Emits
ts
{
nextStep: [];
previousStep: [];
resetStep: [];
}Slots
ts
{
formField(): any;
}Small template example
vue
<script setup lang="ts">
import { type StepTemplateProperties } from "@duplojs/form/vue";
type Props = (
& StepTemplateProperties["props"]
& {
nextLabel?: string;
previousLabel?: string;
resetLabel?: string;
}
);
defineProps<Props>();
defineSlots<StepTemplateProperties["slots"]>();
defineEmits<StepTemplateProperties["emits"]>();
</script>
<template>
<div>
<slot name="formField" />
<div>
<button type="button" @click="$emit('previousStep')">
Back
</button>
<button type="button" @click="$emit('resetStep')">
Reset step
</button>
<button type="button" @click="$emit('nextStep')">
Next
</button>
</div>
</div>
</template>ts
import { createTemplate } from "@duplojs/form/vue";
import MyStepTemplate from "./stepTemplate.vue";
export const useMyStepTemplate = createTemplate(
"step",
MyStepTemplate,
{
props: {
nextLabel: "Next",
previousLabel: "Back",
},
},
);Example
ts
import { useMultiLayout, useStepLayout } from "@duplojs/form/vue";
import { useTextInput } from "@duplojs/form/vueDesignSystem";
export const onboarding = useStepLayout(
[
useMultiLayout({
fullName: useTextInput({ label: "Full name" }),
}),
useMultiLayout({
email: useTextInput({ label: "Email" }),
}),
],
{
errorMessageNotAtLastStep: "Complete all steps before submitting.",
},
);Use cases
- onboarding;
- signup funnel;
- long forms with sequential progression.
