处理 AutoForm 的提交事件、自动与手动 loading、校验错误以及编程式提交。
loadingAuto
@submit 返回 Promise 时,提交按钮的 loading 由 AutoForm 自动管理(loadingAuto 默认开启):
<script setup lang="ts">
import type { z } from 'zod'
const { afz } = useAutoForm()
const toast = useToast()
const schema = afz.object({
name: afz.string().min(2).meta({ label: '姓名' })
})
const state = reactive<Partial<z.output<typeof schema>>>({})
async function onSubmit() {
await new Promise(r => setTimeout(r, 1500))
toast.add({ title: '提交成功', description: 'loadingAuto 自动维护按钮 loading', color: 'success' })
}
</script>
<template>
<MAutoForm :schema="schema" :state="state" @submit="onSubmit" />
</template>
手动 loading 控制
关闭 loading-auto,由 submit-button-props.loading 接管按钮状态:
<script setup lang="ts">
import type { z } from 'zod'
const { afz } = useAutoForm()
const toast = useToast()
const schema = afz.object({
name: afz.string().min(2).meta({ label: '姓名' })
})
const state = reactive<Partial<z.output<typeof schema>>>({})
const loading = ref(false)
async function onSubmit() {
loading.value = true
try {
await new Promise(r => setTimeout(r, 1500))
toast.add({ title: '提交成功(手动 loading)', color: 'success' })
}
finally {
loading.value = false
}
}
</script>
<template>
<MAutoForm
:schema="schema"
:state="state"
:loading-auto="false"
:submit-button-props="{ loading, label: loading ? '提交中…' : '提交' }"
@submit="onSubmit"
/>
</template>
异常与校验事件
@submit 中处理异步异常;@error 接收字段校验失败:
<script setup lang="ts">
import type { z } from 'zod'
const { afz } = useAutoForm()
const toast = useToast()
const schema = afz.object({
name: afz.string().min(2).meta({ label: '姓名(最少 2 个字符)' })
})
const state = reactive<Partial<z.output<typeof schema>>>({})
async function onSubmit() {
try {
await new Promise((_, reject) => setTimeout(() => reject(new Error('API 返回 500')), 1000))
}
catch (e: unknown) {
const msg = e instanceof Error ? e.message : '未知错误'
toast.add({ title: '提交失败', description: msg, color: 'error' })
}
}
function onError() {
toast.add({ title: '校验未通过', description: '请检查字段输入', color: 'warning' })
}
</script>
<template>
<MAutoForm :schema="schema" :state="state" @submit="onSubmit" @error="onError" />
</template>
编程式提交
通过 useTemplateRef 拿到表单实例后,可在外部触发 formRef.submit()、reset()、clear()(配合 :submit="false" 隐藏内置按钮):
<script setup lang="ts">
import type { z } from 'zod'
const { afz } = useAutoForm()
const toast = useToast()
const schema = afz.object({
name: afz.string().min(2).meta({ label: '姓名' }).default('默认值'),
age: afz.number().min(0).meta({ label: '年龄' })
})
const state = reactive<Partial<z.output<typeof schema>>>({})
const apiForm = useTemplateRef('apiForm')
async function onSubmit() {
await new Promise(r => setTimeout(r, 600))
toast.add({ title: '通过暴露 API 提交成功', color: 'success' })
}
</script>
<template>
<div class="flex flex-col gap-3">
<div class="flex flex-wrap gap-2">
<UButton size="sm" label="submit()" @click="apiForm?.formRef?.submit()" />
<UButton size="sm" variant="soft" label="reset()" @click="apiForm?.reset()" />
<UButton size="sm" variant="soft" color="neutral" label="clear()" @click="apiForm?.clear()" />
</div>
<MAutoForm ref="apiForm" :schema="schema" :state="state" :submit="false" @submit="onSubmit" />
</div>
</template>