add Form component with feedback and loading state handling

This commit is contained in:
axolotle 2023-11-25 16:24:46 +01:00
parent c9caa7db76
commit f8b33f803e
4 changed files with 51 additions and 1 deletions

View file

@ -28,7 +28,7 @@ const classVariant = computed(() => {
<div
:aria-live="assertive ? 'assertive' : 'polite'"
aria-atomic="true"
:class="'mt-10 alert ' + classVariant"
:class="'mt-8 alert ' + classVariant"
>
<YIcon v-if="icon" :name="icon" size="2em" aria-hidden="true" />
<slot name="default">

41
components/YForm.vue Normal file
View file

@ -0,0 +1,41 @@
<script setup lang="ts">
import type { Feedback } from '@/composables/form'
withDefaults(
defineProps<{
loading: boolean | null
feedback?: Feedback
submitVariant?: 'success' | 'warning' | 'error'
}>(),
{
feedback: null,
submitVariant: 'success',
},
)
</script>
<template>
<form class="flex flex-col h-full" novalidate v-bind="$attrs">
<slot name="default" />
<!-- Success + generic error announcement -->
<BaseAlert v-show="feedback" v-bind="feedback" class="mb-8" />
<!-- SR "loading" announcement -->
<BaseAlert
:message="loading ? $t('api.processing') : ''"
class="sr-only"
assertive
/>
<div class="mt-auto flex">
<slot name="actions">
<SubmitButton
:loading="loading"
:variant="submitVariant"
class="ms-auto mt-3"
/>
</slot>
</div>
</form>
</template>

View file

@ -1,3 +1,9 @@
export type Feedback = {
variant: 'success' | 'warning' | 'error'
icon: string
message: string
} | null
export const formGroupExtras = Symbol('form-group-extras') as InjectionKey<{
invalid: Ref<boolean>
describedBy: Ref<string | undefined>

View file

@ -7,6 +7,9 @@
},
"add_forward": "Add an e-mail forwarding address",
"add_mail": "Add an e-mail alias",
"api": {
"processing": "Processing…"
},
"app_list": "App list",
"back_to_apps": "Go back to app list",
"cancel": "Cancel",