91 lines
2.3 KiB
Vue
91 lines
2.3 KiB
Vue
<script setup lang="ts">
|
|
import { ref } from "vue";
|
|
|
|
import FormClient from "~/components/formClient.vue";
|
|
|
|
type optionalMap<Optional, type> = Optional extends true ? undefined | type : type;
|
|
|
|
type typeMap = {
|
|
"text": string,
|
|
"password": string,
|
|
"number": number,
|
|
"boolean": boolean,
|
|
"none": undefined,
|
|
"client": `${bigint}`
|
|
};
|
|
|
|
export type fieldDefinition<Optional extends boolean = boolean, type extends keyof typeMap = keyof typeMap> = {
|
|
key: string,
|
|
label?: string,
|
|
type: type,
|
|
optional?: Optional,
|
|
value?: optionalMap<Optional, typeMap[type]>,
|
|
}
|
|
|
|
const props = defineProps<{
|
|
fields: Array<fieldDefinition>,
|
|
}>();
|
|
|
|
// eslint-disable-next-line func-call-spacing
|
|
const emit = defineEmits<{
|
|
(e: "update:modelValue", value: any): void,
|
|
(e: "updateSubModelValue", key: fieldDefinition["key"], value: fieldDefinition["value"]): void,
|
|
}>();
|
|
|
|
const modelValue = ref<{[key: string]: string | number | boolean | undefined}>({});
|
|
|
|
for (const i of props.fields) {
|
|
modelValue.value[i.key] = i.value;
|
|
emit("updateSubModelValue", i.key, i.value);
|
|
}
|
|
|
|
function updateModel(key: string, v: any) {
|
|
modelValue.value[key] = v;
|
|
emit("update:modelValue", modelValue.value);
|
|
emit("updateSubModelValue", key, v);
|
|
}
|
|
|
|
emit("update:modelValue", modelValue.value);
|
|
</script>
|
|
|
|
<template>
|
|
<div v-for="i of fields" :key="i.key">
|
|
<VTextField
|
|
v-if="i.type == 'text'"
|
|
:model-value="modelValue[i.key]"
|
|
:label="i.label"
|
|
type="text"
|
|
@update:model-value="v => updateModel(i.key, v)"
|
|
/>
|
|
<VTextField
|
|
v-if="i.type == 'password'"
|
|
:model-value="modelValue[i.key]"
|
|
:label="i.label"
|
|
type="password"
|
|
@update:model-value="v => updateModel(i.key, v)"
|
|
/>
|
|
<VTextField
|
|
v-if="i.type == 'number'"
|
|
:model-value="modelValue[i.key]"
|
|
:label="i.label"
|
|
type="number"
|
|
@update:model-value="v => updateModel(i.key, Number(v))"
|
|
/>
|
|
<v-checkbox
|
|
v-if="i.type == 'boolean'"
|
|
:label="i.label"
|
|
:model-value="modelValue[i.key]"
|
|
@update:model-value="v => updateModel(i.key, Boolean(v))"
|
|
/>
|
|
<p v-if="i.type == 'none'">
|
|
{{ i.label }}
|
|
</p>
|
|
<FormClient
|
|
v-if="i.type == 'client'"
|
|
:model-value="modelValue[i.key] as `${bigint}`"
|
|
:label="i.label"
|
|
:optional="i.optional"
|
|
@update:model-value="v => updateModel(i.key, v)"
|
|
/>
|
|
</div>
|
|
</template>
|