Merge remote-tracking branch 'origin/feat/uploads-85' into feat/medicine-form-167

This commit is contained in:
hasyim_kai
2025-11-17 09:18:47 +07:00
23 changed files with 1071 additions and 21 deletions
@@ -0,0 +1,71 @@
<script setup lang="ts">
import type { FormErrors } from '~/types/error'
import Combobox from '~/components/pub/my-ui/combobox/combobox.vue'
import { cn, mapToComboboxOptList } from '~/lib/utils'
import { docTypeCode, supportingDocOpt, type docTypeCodeKey } from '~/lib/constants'
import { getValueLabelList as getDoctorLabelList } from '~/services/doctor.service'
import { getValueLabelList as getUnitLabelList } from '~/services/unit.service'
import * as DE from '~/components/pub/my-ui/doc-entry'
import type { Item } from '~/components/pub/my-ui/combobox'
const props = defineProps<{
fieldName?: string
label?: string
placeholder?: string
errors?: FormErrors
class?: string
selectClass?: string
fieldGroupClass?: string
labelClass?: string
isRequired?: boolean
}>()
const {
fieldName = 'job',
label = 'Pekerjaan',
placeholder = 'Pilih pekerjaan',
errors,
class: containerClass,
fieldGroupClass,
labelClass,
} = props
</script>
<template>
<DE.Cell :class="cn('select-field-group', fieldGroupClass, containerClass)">
<DE.Label
:label-for="fieldName"
:class="cn('select-field-label', labelClass)"
:is-required="isRequired"
>
{{ label }}
</DE.Label>
<DE.Field
:id="fieldName"
:errors="errors"
:class="cn('select-field-wrapper')"
>
<FormField
v-slot="{ componentField }"
:name="fieldName"
>
<FormItem>
<FormControl>
<Combobox
class="focus:ring-0 focus:ring-offset-0"
:id="fieldName"
v-bind="componentField"
:items="supportingDocOpt"
:placeholder="placeholder"
search-placeholder="Cari..."
empty-message="Data tidak ditemukan"
/>
</FormControl>
<FormMessage />
</FormItem>
</FormField>
</DE.Field>
</DE.Cell>
</template>
@@ -0,0 +1,73 @@
<script setup lang="ts">
import type { FormErrors } from '~/types/error'
import { toTypedSchema } from '@vee-validate/zod'
import { Form } from '~/components/pub/ui/form'
import InputBase from '~/components/pub/my-ui/form/input-base.vue'
import * as DE from '~/components/pub/my-ui/doc-entry'
import FileField from '~/components/pub/my-ui/form/file-field.vue'
import SelectDocType from './_common/select-doc-type.vue'
import Separator from '~/components/pub/ui/separator/Separator.vue'
const props = defineProps<{
schema: any
initialValues?: any
errors?: FormErrors
}>()
const formSchema = toTypedSchema(props.schema)
const formRef = ref()
defineExpose({
validate: () => formRef.value?.validate(),
resetForm: () => formRef.value?.resetForm(),
setValues: (values: any, shouldValidate = true) => formRef.value?.setValues(values, shouldValidate),
values: computed(() => formRef.value?.values),
})
</script>
<template>
<Form
ref="formRef"
v-slot="{ values }"
as=""
keep-values
:validation-schema="formSchema"
:validate-on-mount="false"
validation-mode="onSubmit"
:initial-values="initialValues ? initialValues : {}"
>
<DE.Block :col-count="2" :cell-flex="false">
<InputBase
field-name="officer"
label="Petugas Upload"
placeholder="Masukkan Petugas Upload"
:is-disabled="true"
/>
<DE.Cell :col-span="2">
<Separator class="w-full my-4"/>
<DE.Block :col-count="3" :cell-flex="false">
<InputBase
field-name="name"
label="Nama Dokumen"
placeholder="Maukkan Nama Dokumen"
/>
<SelectDocType
field-name="type_code"
label="Tipe Dokumen"
placeholder="Pilih Jenis Dokumen"
:errors="errors"
is-required
/>
<FileField
field-name="content"
label="Upload Dokumen"
placeholder="Unggah dokumen"
:errors="errors"
:accept="['pdf', 'jpg', 'png']"
:max-size-mb="1"
/>
</DE.Block>
</DE.Cell>
</DE.Block>
</Form>
</template>
@@ -0,0 +1,43 @@
import type { Config } from '~/components/pub/my-ui/data-table'
import { defineAsyncComponent } from 'vue'
import { docTypeCode, docTypeLabel, type docTypeCodeKey } from '~/lib/constants'
const action = defineAsyncComponent(() => import('~/components/pub/my-ui/data/dropdown-action-dd.vue'))
export const config: Config = {
cols: [{}, {}, {}, {width: 50},],
headers: [
[
{ label: 'Nama Dokumen' },
{ label: 'Tipe Dokumen' },
{ label: 'Petugas Upload' },
{ label: 'Action' },
],
],
keys: ['fileName', 'type_code', 'employee.name', 'action'],
delKeyNames: [
],
parses: {
type_code: (v: unknown) => {
return docTypeLabel[v?.type_code as docTypeCodeKey]
},
},
components: {
action(rec, idx) {
return {
idx,
rec: rec as object,
component: action,
}
},
},
htmls: {
},
}
@@ -0,0 +1,31 @@
<script setup lang="ts">
import type { PaginationMeta } from '~/components/pub/my-ui/pagination/pagination.type'
import PaginationView from '~/components/pub/my-ui/pagination/pagination-view.vue'
import { config } from './list.cfg'
interface Props {
data: any[]
paginationMeta: PaginationMeta
}
defineProps<Props>()
const emit = defineEmits<{
pageChange: [page: number]
}>()
function handlePageChange(page: number) {
emit('pageChange', page)
}
</script>
<template>
<div class="space-y-4">
<PubMyUiDataTable
v-bind="config"
:rows="data"
:skeleton-size="paginationMeta?.pageSize"
/>
<PaginationView :pagination-meta="paginationMeta" @page-change="handlePageChange" />
</div>
</template>