Merge commit '11ced9f05a' into develop
This commit is contained in:
commit
95ac852446
30 changed files with 5978 additions and 357 deletions
11
src/api/scholarship/api.scholarship.ts
Normal file
11
src/api/scholarship/api.scholarship.ts
Normal file
|
|
@ -0,0 +1,11 @@
|
|||
import env from "../index";
|
||||
|
||||
const development = `${env.API_URI}/development`;
|
||||
const developmentScholarshipReport = `${env.API_URI}/development/report/scholarship`;
|
||||
const developmentSalaryFile = `${env.API_URI}/salary/file`;
|
||||
|
||||
export default {
|
||||
developmentScholarshipReport,
|
||||
developmentScholarship: `${development}/scholarship`,
|
||||
developmentSalaryFile: (name: string, group: string, id: string) => `${developmentSalaryFile}/${name}/${group}/${id}`,
|
||||
};
|
||||
|
|
@ -9,6 +9,7 @@ import message from "./api/api.message";
|
|||
import evaluate from "./api/evaluate/api.evaluate";
|
||||
import support from "./api/support/api.support";
|
||||
import org from "./api/org/api.org";
|
||||
import scholarship from "./api/scholarship/api.scholarship";
|
||||
|
||||
const API = {
|
||||
...testtest,
|
||||
|
|
@ -19,6 +20,7 @@ const API = {
|
|||
...appeal,
|
||||
...support,
|
||||
...org,
|
||||
...scholarship,
|
||||
};
|
||||
|
||||
export default {
|
||||
|
|
|
|||
|
|
@ -81,6 +81,30 @@ const items = ref<any>([
|
|||
path: "/appeal-complain",
|
||||
active: false,
|
||||
},
|
||||
{
|
||||
icon: "mdi-account-box-outline",
|
||||
title: "ขอรับการประเมิน (KPI)",
|
||||
sub: "ประเมินผลการปฏิบัติหน้าที่ราชการ",
|
||||
color: "red-2",
|
||||
path: "/KPI",
|
||||
active: false,
|
||||
},
|
||||
{
|
||||
icon: "mdi-elevator",
|
||||
title: "ทำการประเมิน (KPI)",
|
||||
sub: "ประเมินผลการปฏิบัติหน้าที่ราชการ",
|
||||
color: "red-2",
|
||||
path: "/KPI-evaluator",
|
||||
active: false,
|
||||
},
|
||||
{
|
||||
icon: "mdi-school",
|
||||
title: "ทุนการศึกษา/ฝึกอบรม",
|
||||
sub: "รายการทุนการศึกษา/ฝึกอบรม",
|
||||
color: "teal-2",
|
||||
path: "/scholarship",
|
||||
active: false,
|
||||
},
|
||||
]);
|
||||
onMounted(async () => {
|
||||
await fetchlistInbox(1);
|
||||
|
|
|
|||
|
|
@ -1,425 +1,584 @@
|
|||
<script setup lang="ts">
|
||||
import { ref, onMounted } from "vue"
|
||||
import { useQuasar } from "quasar"
|
||||
import { useRouter, useRoute } from "vue-router"
|
||||
import { useCounterMixin } from "@/stores/mixin"
|
||||
import http from "@/plugins/http"
|
||||
import config from "@/app.config"
|
||||
import type { QForm } from "quasar"
|
||||
import Dialog from '@/modules/03_retire/views/DialogRetire.vue'
|
||||
import { ref, onMounted } from "vue";
|
||||
import { useQuasar } from "quasar";
|
||||
import { useRouter, useRoute } from "vue-router";
|
||||
import { useCounterMixin } from "@/stores/mixin";
|
||||
import http from "@/plugins/http";
|
||||
import config from "@/app.config";
|
||||
import type { QForm } from "quasar";
|
||||
import Dialog from "@/modules/03_retire/views/DialogRetire.vue";
|
||||
|
||||
const mixin = useCounterMixin()
|
||||
const { date2Thai, dateToISO, success, messageError, showLoader, hideLoader, fails } = mixin
|
||||
const router = useRouter()
|
||||
const route = useRoute()
|
||||
const $q = useQuasar()
|
||||
const routeName = router.currentRoute.value.name
|
||||
const mixin = useCounterMixin();
|
||||
const {
|
||||
date2Thai,
|
||||
dateToISO,
|
||||
success,
|
||||
messageError,
|
||||
showLoader,
|
||||
hideLoader,
|
||||
fails,
|
||||
} = mixin;
|
||||
const router = useRouter();
|
||||
const route = useRoute();
|
||||
const $q = useQuasar();
|
||||
const routeName = router.currentRoute.value.name;
|
||||
|
||||
/**
|
||||
* ตัวแปรที่ใช้งาน
|
||||
*/
|
||||
const id = ref<string>("")
|
||||
const myform = ref<QForm | null>(null)
|
||||
const tranferOrg = ref("")
|
||||
const dateCommand = ref<Date>(new Date())
|
||||
const dateLeave = ref<Date>(new Date())
|
||||
const noteReason = ref("")
|
||||
const modal = ref<boolean>(false)
|
||||
const id = ref<string>("");
|
||||
const myform = ref<QForm | null>(null);
|
||||
const tranferOrg = ref("");
|
||||
const dateCommand = ref<Date>(new Date());
|
||||
const dateLeave = ref<Date>(new Date());
|
||||
const noteReason = ref("");
|
||||
const modal = ref<boolean>(false);
|
||||
/** ข้อมูล v-model ของฟอร์ม */
|
||||
const dataDetail = ref<any>({
|
||||
datetext: "",
|
||||
activeDate: new Date(),
|
||||
createdAt: new Date(),
|
||||
firstName: "",
|
||||
id: "",
|
||||
isActive: true,
|
||||
lastName: "",
|
||||
location: "",
|
||||
organizationPositionOld: "",
|
||||
positionLevelOld: "",
|
||||
positionNumberOld: "",
|
||||
positionTypeOld: "",
|
||||
prefix: "",
|
||||
profileId: "",
|
||||
reason: "",
|
||||
salary: 0,
|
||||
sendDate: new Date(),
|
||||
status: "",
|
||||
statustext: "",
|
||||
fullname: "",
|
||||
})
|
||||
datetext: "",
|
||||
activeDate: new Date(),
|
||||
createdAt: new Date(),
|
||||
firstName: "",
|
||||
id: "",
|
||||
isActive: true,
|
||||
lastName: "",
|
||||
location: "",
|
||||
organizationPositionOld: "",
|
||||
positionLevelOld: "",
|
||||
positionNumberOld: "",
|
||||
positionTypeOld: "",
|
||||
prefix: "",
|
||||
profileId: "",
|
||||
reason: "",
|
||||
salary: 0,
|
||||
sendDate: new Date(),
|
||||
status: "",
|
||||
statustext: "",
|
||||
fullname: "",
|
||||
});
|
||||
|
||||
/**
|
||||
* ฟังก์ชั่นย้อนกลับไปยังหน้ารายการลาออก
|
||||
*/
|
||||
const clickBack = () => {
|
||||
router.push(`/retire`)
|
||||
}
|
||||
router.push(`/retire`);
|
||||
};
|
||||
|
||||
/**
|
||||
* ฟังก์ชั่นเปลี่ยนเป็น string ของ status
|
||||
* @param val value ของ status true/false
|
||||
*/
|
||||
const statusOrder = (val: boolean) => {
|
||||
switch (val) {
|
||||
case true:
|
||||
return "ยับยั้งการลาออก"
|
||||
case false:
|
||||
return "อนุมัติการลาออก"
|
||||
}
|
||||
}
|
||||
switch (val) {
|
||||
case true:
|
||||
return "ยับยั้งการลาออก";
|
||||
case false:
|
||||
return "อนุมัติการลาออก";
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* เรียกฟังก์ชันทั้งหมดตอนเรียกใช้ไฟล์นี้
|
||||
*/
|
||||
onMounted(() => {
|
||||
if (route.params.id !== undefined) {
|
||||
id.value = route.params.id.toString()
|
||||
fectDataresign(id.value)
|
||||
}
|
||||
})
|
||||
if (route.params.id !== undefined) {
|
||||
id.value = route.params.id.toString();
|
||||
fectDataresign(id.value);
|
||||
}
|
||||
});
|
||||
|
||||
/**
|
||||
* บันทึกข้อมูลการลาออก
|
||||
*/
|
||||
const saveData = async () => {
|
||||
if (myform.value != null) {
|
||||
await myform.value.validate().then(async (saveDataTest: Boolean) => {
|
||||
if (saveDataTest) {
|
||||
saveResing()
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
if (myform.value != null) {
|
||||
await myform.value.validate().then(async (saveDataTest: Boolean) => {
|
||||
if (saveDataTest) {
|
||||
saveResing();
|
||||
}
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* ฟังก์ชั่นดาว์โหลดอัพโหลดไฟล์
|
||||
*/
|
||||
const filesNull = () => {
|
||||
files.value = null
|
||||
}
|
||||
const nameFile = ref<string>("")
|
||||
const fileDocDataUpload = ref<File[]>([])
|
||||
const files = ref<any>()
|
||||
files.value = null;
|
||||
};
|
||||
const nameFile = ref<string>("");
|
||||
const fileDocDataUpload = ref<File[]>([]);
|
||||
const files = ref<any>();
|
||||
//อัพโหลดไฟล์
|
||||
const fileUploadDoc = async (file: any) => {
|
||||
fileDocDataUpload.value.push(file)
|
||||
nameFile.value = file[0].name
|
||||
files.value = file
|
||||
}
|
||||
fileDocDataUpload.value.push(file);
|
||||
nameFile.value = file[0].name;
|
||||
files.value = file;
|
||||
};
|
||||
|
||||
/**
|
||||
* ฟังก์ชั่นเซฟข้อมูลลาออกเเล้วเรียกใช้งานApi
|
||||
*/
|
||||
const saveResing = () => {
|
||||
$q.dialog({
|
||||
title: "ยืนยันการยื่นข้อมูลลาออก",
|
||||
message: "ต้องการยื่นข้อมูลลาออกนี้ใช่หรือไม่?",
|
||||
cancel: {
|
||||
flat: true,
|
||||
color: "negative",
|
||||
},
|
||||
persistent: true,
|
||||
})
|
||||
.onOk(() => {
|
||||
createFormresign()
|
||||
})
|
||||
.onCancel(() => {})
|
||||
.onDismiss(() => {})
|
||||
}
|
||||
$q.dialog({
|
||||
title: "ยืนยันการยื่นข้อมูลลาออก",
|
||||
message: "ต้องการยื่นข้อมูลลาออกนี้ใช่หรือไม่?",
|
||||
cancel: {
|
||||
flat: true,
|
||||
color: "negative",
|
||||
},
|
||||
persistent: true,
|
||||
})
|
||||
.onOk(() => {
|
||||
createFormresign();
|
||||
})
|
||||
.onCancel(() => {})
|
||||
.onDismiss(() => {});
|
||||
};
|
||||
|
||||
//ยกเลิกการลาออก
|
||||
const cancelResing = () => {
|
||||
modal.value = true
|
||||
}
|
||||
modal.value = true;
|
||||
};
|
||||
|
||||
/**
|
||||
* ฟังก์ชั่นลบ
|
||||
* @param id ไอดีของข้อมูลการลาออก
|
||||
*/
|
||||
const deleteResting = async (id: string) => {
|
||||
showLoader()
|
||||
await http
|
||||
.delete(config.API.resingByid(id))
|
||||
.then(() => {
|
||||
success($q, "ยกเลิกการลาออกขอสำเร็จ")
|
||||
})
|
||||
.catch(e => {
|
||||
messageError($q, e)
|
||||
})
|
||||
.finally(() => {
|
||||
hideLoader()
|
||||
clickBack()
|
||||
})
|
||||
}
|
||||
showLoader();
|
||||
await http
|
||||
.delete(config.API.resingByid(id))
|
||||
.then(() => {
|
||||
success($q, "ยกเลิกการลาออกขอสำเร็จ");
|
||||
})
|
||||
.catch((e) => {
|
||||
messageError($q, e);
|
||||
})
|
||||
.finally(() => {
|
||||
hideLoader();
|
||||
clickBack();
|
||||
});
|
||||
};
|
||||
|
||||
//บันทึกข้อมูล
|
||||
const createFormresign = async () => {
|
||||
const formData = new FormData()
|
||||
if (files.value > 0) {
|
||||
const blob = files.value.slice(0, files.value[0].size)
|
||||
const newFile = new File(blob, nameFile.value, {
|
||||
type: files.value[0].type,
|
||||
})
|
||||
formData.append("file", newFile)
|
||||
}
|
||||
const formData = new FormData();
|
||||
if (files.value.length > 0) {
|
||||
const blob = files.value.slice(0, files.value[0].size);
|
||||
const newFile = new File(blob, nameFile.value, {
|
||||
type: files.value[0].type,
|
||||
});
|
||||
formData.append("file", newFile);
|
||||
}
|
||||
|
||||
formData.append("Location", tranferOrg.value)
|
||||
formData.append("SendDate", dateToISO(dateCommand.value))
|
||||
formData.append("ActiveDate", dateToISO(dateLeave.value))
|
||||
formData.append("Reason", noteReason.value)
|
||||
formData.append("Location", tranferOrg.value);
|
||||
formData.append("SendDate", dateToISO(dateCommand.value));
|
||||
formData.append("ActiveDate", dateToISO(dateLeave.value));
|
||||
formData.append("Reason", noteReason.value);
|
||||
|
||||
await http
|
||||
.post(config.API.listResign(), formData)
|
||||
.then((res: any) => {
|
||||
let data = res.data.result.id
|
||||
success($q, "บันทึกข้อมูลสำเร็จ")
|
||||
router.push(`/retire/result/${data}`)
|
||||
})
|
||||
.catch((e: any) => {
|
||||
messageError($q, e)
|
||||
})
|
||||
}
|
||||
await http
|
||||
.post(config.API.listResign(), formData)
|
||||
.then((res: any) => {
|
||||
let data = res.data.result.id;
|
||||
success($q, "บันทึกข้อมูลสำเร็จ");
|
||||
router.push(`/retire/result/${data}`);
|
||||
})
|
||||
.catch((e: any) => {
|
||||
messageError($q, e);
|
||||
});
|
||||
};
|
||||
|
||||
/**
|
||||
* ฟังก์ชั่นเรียกข้อมูลจาก Api
|
||||
* @param id ไอดีของข้อมูล
|
||||
*/
|
||||
const fectDataresign = async (id: string) => {
|
||||
showLoader()
|
||||
await http
|
||||
.get(config.API.resingByid(id))
|
||||
.then((res: any) => {
|
||||
let data = res.data.result
|
||||
;(tranferOrg.value = data.location),
|
||||
(dateCommand.value = data.sendDate),
|
||||
(dateLeave.value = data.activeDate),
|
||||
(noteReason.value = data.reason),
|
||||
(files.value = data.docs),
|
||||
(dataDetail.value = data)
|
||||
})
|
||||
.catch((e: any) => {
|
||||
messageError($q, e)
|
||||
})
|
||||
.finally(() => {
|
||||
hideLoader()
|
||||
})
|
||||
showLoader();
|
||||
await http
|
||||
.get(config.API.resingByid(id))
|
||||
.then((res: any) => {
|
||||
let data = res.data.result;
|
||||
(tranferOrg.value = data.location),
|
||||
(dateCommand.value = data.sendDate),
|
||||
(dateLeave.value = data.activeDate),
|
||||
(noteReason.value = data.reason),
|
||||
(files.value = data.docs),
|
||||
(dataDetail.value = data);
|
||||
})
|
||||
.catch((e: any) => {
|
||||
messageError($q, e);
|
||||
})
|
||||
.finally(() => {
|
||||
hideLoader();
|
||||
});
|
||||
};
|
||||
|
||||
function downloadFile(data: string) {
|
||||
window.open(data, "_blank");
|
||||
}
|
||||
</script>
|
||||
<template>
|
||||
<div class="col-12 row justify-center">
|
||||
<div class="col-xs-12 col-sm-12 col-md-11">
|
||||
<div class="toptitle text-white col-12 row items-center">
|
||||
<q-btn icon="mdi-arrow-left" unelevated round dense flat color="primary" class="q-mr-sm" @click="router.go(-1)" />
|
||||
<div v-if="routeName == 'AddRetire'">เพิ่มเรื่องลาออก</div>
|
||||
<div v-else>รายละเอียดเรื่องลาออก</div>
|
||||
</div>
|
||||
<q-form ref="myform" class="col-12">
|
||||
<q-card bordered>
|
||||
<div class="col-12 row q-col-gutter-md q-pa-md">
|
||||
<div class="col-xs-12 col-sm-12">
|
||||
<div class="col-12 row q-pa-sm q-col-gutter-sm">
|
||||
<q-input
|
||||
class="col-8"
|
||||
dense
|
||||
outlined
|
||||
v-model="tranferOrg"
|
||||
label="สถานที่ยื่นขอลาออกจากราชการ"
|
||||
:readonly="routeName != 'AddRetire'"
|
||||
:rules="[(val:string) => !!val || `${'กรุณากรอกสถานที่ยื่นขอลาออกจากราชการ'}`]"
|
||||
/>
|
||||
<datepicker class="col-2" menu-class-name="modalfix" v-model="dateCommand" :locale="'th'" autoApply readonly borderless :enableTimePicker="false" week-start="0">
|
||||
<template #year="{ year }">
|
||||
{{ year + 543 }}
|
||||
</template>
|
||||
<template #year-overlay-value="{ value }">
|
||||
{{ parseInt(value + 543) }}
|
||||
</template>
|
||||
<template #trigger>
|
||||
<q-input
|
||||
outlined
|
||||
readonly
|
||||
dense
|
||||
hide-bottom-space
|
||||
class="full-width datepicker"
|
||||
:model-value="dateCommand != null ? date2Thai(dateCommand) : null"
|
||||
:label="`${'วันที่ยื่นขอลาออกจากราชการ'}`"
|
||||
:rules="[val => !!val || `${'กรุณาเลือกวันที่ยื่นขอลาออกจากราชการ'}`]"
|
||||
>
|
||||
<template v-slot:prepend>
|
||||
<q-icon name="event" class="cursor-pointer" style="color: var(--q-primary)"> </q-icon>
|
||||
</template>
|
||||
</q-input>
|
||||
</template>
|
||||
</datepicker>
|
||||
<datepicker
|
||||
class="col-2"
|
||||
menu-class-name="modalfix"
|
||||
v-model="dateLeave"
|
||||
:locale="'th'"
|
||||
autoApply
|
||||
borderless
|
||||
:enableTimePicker="false"
|
||||
week-start="0"
|
||||
:readonly="routeName != 'AddRetire'"
|
||||
>
|
||||
<template #year="{ year }">
|
||||
{{ year + 543 }}
|
||||
</template>
|
||||
<template #year-overlay-value="{ value }">
|
||||
{{ parseInt(value + 543) }}
|
||||
</template>
|
||||
<template #trigger>
|
||||
<q-input
|
||||
outlined
|
||||
dense
|
||||
hide-bottom-space
|
||||
:readonly="routeName != 'AddRetire'"
|
||||
class="full-width datepicker"
|
||||
:model-value="dateLeave != null ? date2Thai(dateLeave) : null"
|
||||
:label="`${'วันที่ขอลาออกจากราชการ'}`"
|
||||
:rules="[val => !!val || `${'กรุณาเลือกวันที่ขอลาออกจากราชการ'}`]"
|
||||
>
|
||||
<template v-slot:prepend>
|
||||
<q-icon name="event" class="cursor-pointer" style="color: var(--q-primary)"> </q-icon>
|
||||
</template>
|
||||
</q-input>
|
||||
</template>
|
||||
</datepicker>
|
||||
<q-input
|
||||
class="col-12"
|
||||
dense
|
||||
outlined
|
||||
v-model="noteReason"
|
||||
label="เหตุผลที่ลาออกจากราชการ"
|
||||
type="textarea"
|
||||
:readonly="routeName != 'AddRetire'"
|
||||
:rules="[val => !!val || `${'กรุณากรอกเหตุผลที่ลาออกจากราชการ'}`]"
|
||||
/>
|
||||
<div class="col-12 row justify-center">
|
||||
<div class="col-xs-12 col-sm-12 col-md-11">
|
||||
<div class="toptitle text-white col-12 row items-center">
|
||||
<q-btn
|
||||
icon="mdi-arrow-left"
|
||||
unelevated
|
||||
round
|
||||
dense
|
||||
flat
|
||||
color="primary"
|
||||
class="q-mr-sm"
|
||||
@click="router.go(-1)"
|
||||
/>
|
||||
<div v-if="routeName == 'AddRetire'">เพิ่มเรื่องลาออก</div>
|
||||
<div v-else>รายละเอียดเรื่องลาออก</div>
|
||||
</div>
|
||||
<q-form ref="myform" class="col-12">
|
||||
<q-card bordered>
|
||||
<div class="col-12 row q-col-gutter-sm q-pa-md">
|
||||
<div class="col-xs-12 col-sm-12">
|
||||
<div class="col-12 row q-pa-sm q-col-gutter-sm">
|
||||
<q-input
|
||||
class="col-8"
|
||||
dense
|
||||
outlined
|
||||
v-model="tranferOrg"
|
||||
hide-bottom-space
|
||||
label="สถานที่ยื่นขอลาออกจากราชการ"
|
||||
:readonly="routeName != 'AddRetire'"
|
||||
:rules="[(val:string) => !!val || `${'กรุณากรอกสถานที่ยื่นขอลาออกจากราชการ'}`]"
|
||||
/>
|
||||
<datepicker
|
||||
class="col-2"
|
||||
menu-class-name="modalfix"
|
||||
v-model="dateCommand"
|
||||
:locale="'th'"
|
||||
autoApply
|
||||
readonly
|
||||
borderless
|
||||
:enableTimePicker="false"
|
||||
week-start="0"
|
||||
>
|
||||
<template #year="{ year }">
|
||||
{{ year + 543 }}
|
||||
</template>
|
||||
<template #year-overlay-value="{ value }">
|
||||
{{ parseInt(value + 543) }}
|
||||
</template>
|
||||
<template #trigger>
|
||||
<q-input
|
||||
outlined
|
||||
readonly
|
||||
dense
|
||||
hide-bottom-space
|
||||
class="full-width datepicker"
|
||||
:model-value="
|
||||
dateCommand != null ? date2Thai(dateCommand) : null
|
||||
"
|
||||
:label="`${'วันที่ยื่นขอลาออกจากราชการ'}`"
|
||||
:rules="[
|
||||
(val) =>
|
||||
!!val || `${'กรุณาเลือกวันที่ยื่นขอลาออกจากราชการ'}`,
|
||||
]"
|
||||
>
|
||||
<template v-slot:prepend>
|
||||
<q-icon
|
||||
name="event"
|
||||
class="cursor-pointer"
|
||||
style="color: var(--q-primary)"
|
||||
>
|
||||
</q-icon>
|
||||
</template>
|
||||
</q-input>
|
||||
</template>
|
||||
</datepicker>
|
||||
<datepicker
|
||||
class="col-2"
|
||||
menu-class-name="modalfix"
|
||||
v-model="dateLeave"
|
||||
:locale="'th'"
|
||||
autoApply
|
||||
borderless
|
||||
:enableTimePicker="false"
|
||||
week-start="0"
|
||||
:readonly="routeName != 'AddRetire'"
|
||||
>
|
||||
<template #year="{ year }">
|
||||
{{ year + 543 }}
|
||||
</template>
|
||||
<template #year-overlay-value="{ value }">
|
||||
{{ parseInt(value + 543) }}
|
||||
</template>
|
||||
<template #trigger>
|
||||
<q-input
|
||||
outlined
|
||||
dense
|
||||
hide-bottom-space
|
||||
:readonly="routeName != 'AddRetire'"
|
||||
class="full-width datepicker"
|
||||
:model-value="
|
||||
dateLeave != null ? date2Thai(dateLeave) : null
|
||||
"
|
||||
:label="`${'วันที่ขอลาออกจากราชการ'}`"
|
||||
:rules="[
|
||||
(val) =>
|
||||
!!val || `${'กรุณาเลือกวันที่ขอลาออกจากราชการ'}`,
|
||||
]"
|
||||
>
|
||||
<template v-slot:prepend>
|
||||
<q-icon
|
||||
name="event"
|
||||
class="cursor-pointer"
|
||||
style="color: var(--q-primary)"
|
||||
>
|
||||
</q-icon>
|
||||
</template>
|
||||
</q-input>
|
||||
</template>
|
||||
</datepicker>
|
||||
<q-input
|
||||
class="col-12"
|
||||
dense
|
||||
outlined
|
||||
v-model="noteReason"
|
||||
label="เหตุผลที่ลาออกจากราชการ"
|
||||
type="textarea"
|
||||
hide-bottom-space
|
||||
:readonly="routeName != 'AddRetire'"
|
||||
:rules="[
|
||||
(val) => !!val || `${'กรุณากรอกเหตุผลที่ลาออกจากราชการ'}`,
|
||||
]"
|
||||
/>
|
||||
|
||||
<div class="col-12 row" v-if="routeName == 'AddRetire'">
|
||||
<q-uploader
|
||||
flat
|
||||
bordered
|
||||
class="col-xs-12 col-sm-12"
|
||||
accept=".jpg,.png,.pdf,.csv,.doc"
|
||||
url="http://localhost:4444/upload"
|
||||
label="เอกสารเพิ่มเติม"
|
||||
type="file"
|
||||
@added="fileUploadDoc"
|
||||
@removed="filesNull"
|
||||
style="max-width: px"
|
||||
/>
|
||||
</div>
|
||||
<div class="col-12 row" v-if="routeName != 'AddRetire'">
|
||||
<div class="bg-grey-1 q-pa-sm col-12 row items-center text-primary">
|
||||
<div class="q-pl-sm text-weight-bold text-dark">เอกสารเพิ่มเติม</div>
|
||||
</div>
|
||||
<q-card bordered flat class="full-width">
|
||||
<q-list separator>
|
||||
<q-item v-for="file in files" :key="file.key" class="q-my-xs">
|
||||
<q-item-section>
|
||||
<q-item-label class="full-width ellipsis">
|
||||
{{ file.fileName }}
|
||||
</q-item-label>
|
||||
<div class="col-12 row" v-if="routeName == 'AddRetire'">
|
||||
<q-uploader
|
||||
flat
|
||||
bordered
|
||||
class="col-xs-12 col-sm-12"
|
||||
accept=".jpg,.png,.pdf,.csv,.doc"
|
||||
url="http://localhost:4444/upload"
|
||||
label="เอกสารเพิ่มเติม"
|
||||
type="file"
|
||||
@added="fileUploadDoc"
|
||||
@removed="filesNull"
|
||||
style="max-width: px"
|
||||
/>
|
||||
</div>
|
||||
<div class="col-12 row">
|
||||
<q-card
|
||||
bordered
|
||||
flat
|
||||
class="row col-12 text-dark q-mt-sm"
|
||||
v-if="routeName != 'AddRetire'"
|
||||
>
|
||||
<div
|
||||
class="bg-grey-1 q-pa-sm col-12 row items-center text-primary"
|
||||
>
|
||||
<div class="q-pl-sm text-weight-bold text-dark">
|
||||
เอกสารเพิ่มเติม
|
||||
</div>
|
||||
</div>
|
||||
<q-list class="col-12">
|
||||
<q-item
|
||||
v-for="file in files"
|
||||
:key="file.key"
|
||||
class="q-my-xs"
|
||||
>
|
||||
<q-item-section>
|
||||
<q-item-label class="full-width ellipsis">
|
||||
{{ file.fileName }}
|
||||
</q-item-label>
|
||||
|
||||
<q-item-label caption> </q-item-label>
|
||||
</q-item-section>
|
||||
</q-item>
|
||||
</q-list>
|
||||
</q-card>
|
||||
</div>
|
||||
</div>
|
||||
<q-card bordered class="row col-12 text-dark q-mt-sm" v-if="routeName != 'AddRetire'">
|
||||
<div class="bg-grey-1 q-pa-sm col-12 row items-center text-primary">
|
||||
<div class="q-pl-sm text-weight-bold text-dark">ผลการพิจารณาของผู้บังคับบัญชา</div>
|
||||
</div>
|
||||
<q-separator />
|
||||
<div class="row col-12 q-pa-md">
|
||||
<div class="col-12 row bg-white q-col-gutter-md">
|
||||
<div class="col-xs-6 row items-start">
|
||||
<div class="col-12 text-top">สถานะ</div>
|
||||
<div class="col-12 text-detail">
|
||||
{{ dataDetail.commanderReject !== null ? statusOrder(dataDetail.commanderReject) : "-" }}
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-xs-6 row items-start">
|
||||
<div class="col-12 text-top">วันสุดท้ายที่ยับยั้ง</div>
|
||||
<div class="col-12 text-detail">
|
||||
{{ dataDetail.commanderRejectDate !== null ? date2Thai(dataDetail.commanderRejectDate) : "-" }}
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-xs-12 row items-start">
|
||||
<div class="col-12 text-top">ความคิดเห็นและเหตุผล</div>
|
||||
<div class="col-12 text-detail" v-if="dataDetail.commanderReject === false">
|
||||
{{ dataDetail.commanderApproveReason !== null ? dataDetail.commanderApproveReason : "-" }}
|
||||
</div>
|
||||
<div class="col-12 text-detail" v-if="dataDetail.commanderReject === true">
|
||||
{{ dataDetail.commanderRejectReason !== null ? dataDetail.commanderRejectReason : "-" }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</q-card>
|
||||
<q-item-label caption> </q-item-label>
|
||||
</q-item-section>
|
||||
<q-space />
|
||||
|
||||
<q-card bordered class="row col-12 text-dark q-mt-sm" v-if="routeName != 'AddRetire'">
|
||||
<div class="bg-grey-1 q-pa-sm col-12 row items-center text-primary">
|
||||
<div class="q-pl-sm text-weight-bold text-dark">ผลการพิจารณาของผู้มีอำนาจ</div>
|
||||
</div>
|
||||
<q-separator />
|
||||
<div class="row col-12 q-pa-md">
|
||||
<div class="col-12 row bg-white q-col-gutter-md">
|
||||
<div class="col-xs-6 row items-start">
|
||||
<div class="col-12 text-top">สถานะ</div>
|
||||
<div class="col-12 text-detail">
|
||||
{{ dataDetail.oligarchReject !== null ? statusOrder(dataDetail.oligarchReject) : "-" }}
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-xs-6 row items-start">
|
||||
<div class="col-12 text-top">วันสุดท้ายที่ยับยั้ง</div>
|
||||
<div class="col-12 text-detail">
|
||||
{{ dataDetail.oligarchRejectDate !== null ? date2Thai(dataDetail.oligarchRejectDate) : "-" }}
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-xs-12 row items-start">
|
||||
<div class="col-12 text-top">ความคิดเห็นและเหตุผล</div>
|
||||
<div class="col-12 text-detail" v-if="dataDetail.oligarchReject == false">
|
||||
{{ dataDetail.oligarchApproveReason !== null ? dataDetail.oligarchApproveReason : "-" }}
|
||||
</div>
|
||||
<div class="col-12 text-detail" v-else-if="dataDetail.oligarchReject == true">
|
||||
{{ dataDetail.oligarchRejectReason !== null ? dataDetail.oligarchRejectReason : "-" }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</q-card>
|
||||
</div>
|
||||
<q-btn
|
||||
size="12px"
|
||||
flat
|
||||
round
|
||||
dense
|
||||
color="blue"
|
||||
icon="mdi-download"
|
||||
@click="downloadFile(file.pathName)"
|
||||
><q-tooltip>ดาวน์โหลดไฟล์</q-tooltip></q-btn
|
||||
>
|
||||
</q-item>
|
||||
</q-list>
|
||||
</q-card>
|
||||
</div>
|
||||
<div class="col-12 row">
|
||||
<q-card
|
||||
bordered
|
||||
class="row col-12 text-dark q-mt-sm"
|
||||
v-if="routeName != 'AddRetire'"
|
||||
>
|
||||
<div
|
||||
class="bg-grey-1 q-pa-sm col-12 row items-center text-primary"
|
||||
>
|
||||
<div class="q-pl-sm text-weight-bold text-dark">
|
||||
ผลการพิจารณาของผู้บังคับบัญชา
|
||||
</div>
|
||||
</div>
|
||||
<q-separator />
|
||||
<div class="row col-12 q-pa-md">
|
||||
<div class="col-12 row bg-white q-col-gutter-md">
|
||||
<div class="col-xs-6 row items-start">
|
||||
<div class="col-12 text-top">สถานะ</div>
|
||||
<div class="col-12 text-detail">
|
||||
{{
|
||||
dataDetail.commanderReject !== null
|
||||
? statusOrder(dataDetail.commanderReject)
|
||||
: "-"
|
||||
}}
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-xs-6 row items-start">
|
||||
<div class="col-12 text-top">
|
||||
วันสุดท้ายที่ยับยั้ง
|
||||
</div>
|
||||
<div class="col-12 text-detail">
|
||||
{{
|
||||
dataDetail.commanderRejectDate !== null
|
||||
? date2Thai(dataDetail.commanderRejectDate)
|
||||
: "-"
|
||||
}}
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-xs-12 row items-start">
|
||||
<div class="col-12 text-top">
|
||||
ความคิดเห็นและเหตุผล
|
||||
</div>
|
||||
<div
|
||||
class="col-12 text-detail"
|
||||
v-if="dataDetail.commanderReject === false"
|
||||
>
|
||||
{{
|
||||
dataDetail.commanderApproveReason !== null
|
||||
? dataDetail.commanderApproveReason
|
||||
: "-"
|
||||
}}
|
||||
</div>
|
||||
<div
|
||||
class="col-12 text-detail"
|
||||
v-if="dataDetail.commanderReject === true"
|
||||
>
|
||||
{{
|
||||
dataDetail.commanderRejectReason !== null
|
||||
? dataDetail.commanderRejectReason
|
||||
: "-"
|
||||
}}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</q-card>
|
||||
</div>
|
||||
<div class="col-12 row">
|
||||
<q-card
|
||||
bordered
|
||||
class="row col-12 text-dark q-mt-sm"
|
||||
v-if="routeName != 'AddRetire'"
|
||||
>
|
||||
<div
|
||||
class="bg-grey-1 q-pa-sm col-12 row items-center text-primary"
|
||||
>
|
||||
<div class="q-pl-sm text-weight-bold text-dark">
|
||||
ผลการพิจารณาของผู้มีอำนาจ
|
||||
</div>
|
||||
</div>
|
||||
<q-separator />
|
||||
<div class="row col-12 q-pa-md">
|
||||
<div class="col-12 row bg-white q-col-gutter-md">
|
||||
<div class="col-xs-6 row items-start">
|
||||
<div class="col-12 text-top">สถานะ</div>
|
||||
<div class="col-12 text-detail">
|
||||
{{
|
||||
dataDetail.oligarchReject !== null
|
||||
? statusOrder(dataDetail.oligarchReject)
|
||||
: "-"
|
||||
}}
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-xs-6 row items-start">
|
||||
<div class="col-12 text-top">
|
||||
วันสุดท้ายที่ยับยั้ง
|
||||
</div>
|
||||
<div class="col-12 text-detail">
|
||||
{{
|
||||
dataDetail.oligarchRejectDate !== null
|
||||
? date2Thai(dataDetail.oligarchRejectDate)
|
||||
: "-"
|
||||
}}
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-xs-12 row items-start">
|
||||
<div class="col-12 text-top">
|
||||
ความคิดเห็นและเหตุผล
|
||||
</div>
|
||||
<div
|
||||
class="col-12 text-detail"
|
||||
v-if="dataDetail.oligarchReject == false"
|
||||
>
|
||||
{{
|
||||
dataDetail.oligarchApproveReason !== null
|
||||
? dataDetail.oligarchApproveReason
|
||||
: "-"
|
||||
}}
|
||||
</div>
|
||||
<div
|
||||
class="col-12 text-detail"
|
||||
v-else-if="dataDetail.oligarchReject == true"
|
||||
>
|
||||
{{
|
||||
dataDetail.oligarchRejectReason !== null
|
||||
? dataDetail.oligarchRejectReason
|
||||
: "-"
|
||||
}}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</q-card>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="row col-12 q-pa-md" v-if="routeName != 'AddRetire'">
|
||||
<q-space />
|
||||
<q-btn
|
||||
v-if="dataDetail.status !== 'DELETE' && dataDetail.status !== 'DONE'"
|
||||
unelevated
|
||||
dense
|
||||
class="q-px-md items-center"
|
||||
color="orange"
|
||||
label="ยกเลิกการลาออก"
|
||||
@click="cancelResing"
|
||||
:disable="tranferOrg == '' && noteReason == ''"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<q-separator v-if="routeName == 'AddRetire'" />
|
||||
<div class="row col-12 q-pa-md" v-if="routeName == 'AddRetire'">
|
||||
<q-space />
|
||||
<q-btn unelevated dense class="q-px-md items-center" color="primary" label="ยื่นเรื่องขอลาออก" @click="saveData" :disable="tranferOrg == '' && noteReason == ''" />
|
||||
</div>
|
||||
</q-card>
|
||||
</q-form>
|
||||
</div>
|
||||
</div>
|
||||
<div class="row col-12 q-pa-md" v-if="routeName != 'AddRetire'">
|
||||
<q-space />
|
||||
<q-btn
|
||||
v-if="
|
||||
dataDetail.status !== 'DELETE' && dataDetail.status !== 'DONE'
|
||||
"
|
||||
unelevated
|
||||
dense
|
||||
class="q-px-md items-center"
|
||||
color="orange"
|
||||
label="ยกเลิกการลาออก"
|
||||
@click="cancelResing"
|
||||
:disable="tranferOrg == '' && noteReason == ''"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<q-separator v-if="routeName == 'AddRetire'" />
|
||||
<div class="row col-12 q-pa-md" v-if="routeName == 'AddRetire'">
|
||||
<q-space />
|
||||
<q-btn
|
||||
unelevated
|
||||
dense
|
||||
class="q-px-md items-center"
|
||||
color="primary"
|
||||
label="ยื่นเรื่องขอลาออก"
|
||||
@click="saveData"
|
||||
:disable="tranferOrg == '' && noteReason == ''"
|
||||
/>
|
||||
</div>
|
||||
</q-card>
|
||||
</q-form>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<Dialog
|
||||
v-model:modal="modal"
|
||||
/>
|
||||
<Dialog v-model:modal="modal" />
|
||||
</template>
|
||||
|
|
|
|||
84
src/modules/08_KPI/components/Tab/01_Assessment.vue
Normal file
84
src/modules/08_KPI/components/Tab/01_Assessment.vue
Normal file
|
|
@ -0,0 +1,84 @@
|
|||
<script setup lang="ts">
|
||||
import { useQuasar, type QTableProps } from "quasar";
|
||||
import { ref, onMounted } from "vue";
|
||||
|
||||
import Work from "@/modules/08_KPI/components/Tab/Topic/01_Template.vue";
|
||||
import Capacity from "@/modules/08_KPI/components/Tab/Topic/02_Template.vue";
|
||||
|
||||
const rows_01 = ref<any[]>();
|
||||
const rows_02 = ref<any[]>();
|
||||
const rows_03 = ref<any[]>();
|
||||
|
||||
const rows_04 = ref<any[]>();
|
||||
const rows_05 = ref<any[]>();
|
||||
|
||||
const total = ref<number>(0);
|
||||
const resultWork = ref<number>(0);
|
||||
const resultEvaluation = ref<number>(0);
|
||||
|
||||
function getList() {
|
||||
const data = [
|
||||
{
|
||||
indicators: "ตัวชี้วัด 1",
|
||||
target: null,
|
||||
scoreLevel: "4",
|
||||
weight: "50",
|
||||
workResult: "ระดับ 5",
|
||||
evaluationResults: "50",
|
||||
},
|
||||
];
|
||||
|
||||
rows_01.value = data;
|
||||
}
|
||||
|
||||
onMounted(() => {
|
||||
getList();
|
||||
});
|
||||
</script>
|
||||
<template>
|
||||
<q-scroll-area style="height: 56vh" class="bg-white row col-12 text-dark q-pa-md">
|
||||
<div class="text-weight-bold text-body2">
|
||||
<span class="txt-under text-blue-6">องค์ประกอบที่ 1</span>
|
||||
<span class="q-ml-sm"> ผลสัมฤทธิ์ของงาน</span>
|
||||
</div>
|
||||
|
||||
<div class="q-gutter-md q-mt-sm">
|
||||
<!-- องค์ประกอบที่ 1 -->
|
||||
<Work v-model:data="rows_01" :title="`1. งานตามแผนปฏิบัติราชการประจำปี`" :page="1" />
|
||||
<Work v-model:data="rows_02" :title="`2. งานตามหน้าที่ความรับผิดชอบหลัก`" :page="2" />
|
||||
<Work v-model:data="rows_03" :title="`3. งานที่ได้รับมอบหมาย`" :page="3" />
|
||||
<div class="row text-body2 text-weight-bold">
|
||||
<div class="col-6 text-center row justify-center">
|
||||
<span>รวมผลการประเมิน (ร้อยละ) 100</span>
|
||||
<div class="text-primary q-pl-md">{{ total }}</div>
|
||||
</div>
|
||||
|
||||
<div class="col-6 text-center row justify-center">
|
||||
<span>สรุปผลการประเมินผลสัมฤทธิ์ของงาน (คะแนนเต็ม 70 คะแนน)</span>
|
||||
<div class="text-primary q-pl-md">{{ resultWork }}</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<q-separator size="3px" class="q-my-lg" />
|
||||
|
||||
<!-- องค์ประกอบที่ 2 -->
|
||||
<div class="text-weight-bold text-body2 q-mb-sm">
|
||||
<span class="txt-under text-blue-6">องค์ประกอบที่ 2</span>
|
||||
<span class="q-ml-sm"> พฤติกรรมการปฎิบัติราชการ (สมรรถนะ)</span>
|
||||
</div>
|
||||
|
||||
<Capacity v-model:data="rows_04" :title="`1. สมรรถนะหลัก`" :page="1" />
|
||||
<Capacity v-model:data="rows_05" :title="`2. สมรรถนะประจำกลุ่ม`" :page="2" />
|
||||
|
||||
<div class="row text-body2 text-weight-bold justify-center">
|
||||
<span>ผลการประเมินสมรรถนะ (20 คะแนน)</span>
|
||||
<div class="text-primary q-pl-md">{{ resultEvaluation }}</div>
|
||||
</div>
|
||||
</div>
|
||||
</q-scroll-area>
|
||||
</template>
|
||||
<style scoped>
|
||||
.txt-under {
|
||||
text-decoration: underline;
|
||||
}
|
||||
</style>
|
||||
3
src/modules/08_KPI/components/Tab/02_CommanderAbove.vue
Normal file
3
src/modules/08_KPI/components/Tab/02_CommanderAbove.vue
Normal file
|
|
@ -0,0 +1,3 @@
|
|||
<template>
|
||||
<div class="q-pa-md">2</div>
|
||||
</template>
|
||||
|
|
@ -0,0 +1,3 @@
|
|||
<template>
|
||||
<div class="q-pa-md">3</div>
|
||||
</template>
|
||||
3
src/modules/08_KPI/components/Tab/04_File.vue
Normal file
3
src/modules/08_KPI/components/Tab/04_File.vue
Normal file
|
|
@ -0,0 +1,3 @@
|
|||
<template>
|
||||
<div class="q-pa-md">4</div>
|
||||
</template>
|
||||
288
src/modules/08_KPI/components/Tab/Dialog/01_Dialog.vue
Normal file
288
src/modules/08_KPI/components/Tab/Dialog/01_Dialog.vue
Normal file
|
|
@ -0,0 +1,288 @@
|
|||
<script setup lang="ts">
|
||||
import { ref, reactive } from "vue";
|
||||
import DialogHeader from "@/components/DialogHeader.vue";
|
||||
|
||||
const modal = defineModel<boolean>("modal", { required: true });
|
||||
const numpage = defineModel<number>("numpage", { required: true });
|
||||
const splitterModel = ref<number>(25);
|
||||
const search = ref<string>("");
|
||||
|
||||
const define = ref<string>("");
|
||||
const formula = ref<string>("");
|
||||
|
||||
const listCheck = ref<number | null>();
|
||||
const listTarget = ref<any>([
|
||||
{
|
||||
id: "ID1",
|
||||
metricCode: "1กก",
|
||||
indicatorName: "ตัวชี้วัด 1",
|
||||
},
|
||||
{
|
||||
id: "ID2",
|
||||
metricCode: "2กก",
|
||||
indicatorName: "ตัวชี้วัด 2",
|
||||
},
|
||||
]);
|
||||
|
||||
const formDetail = reactive<any>({
|
||||
oc: `สำนักงานคณะกรรมการข้าราชการกรุงเทพมหานคร/กองบริหารทั่วไป/กลุ่มงานช่วยนักบริหาร`,
|
||||
indicators: "1",
|
||||
code: "1กก",
|
||||
name: "ตัวชี้วัด 1",
|
||||
target: "",
|
||||
unit: "",
|
||||
weight: "100",
|
||||
});
|
||||
const formScore = reactive<any>({
|
||||
score5: "5",
|
||||
score4: "4",
|
||||
score3: "3",
|
||||
score2: "2",
|
||||
score1: "1",
|
||||
});
|
||||
|
||||
const fieldDetailLabels = {
|
||||
oc: "หน่วยงาน/ส่วนราชการ",
|
||||
indicators: "ลำดับตัวชี้วัด",
|
||||
code: "รหัสตัวชี้วัด",
|
||||
name: "ชื่อตัวชี้วัด",
|
||||
target: "ค่าเป้าหมาย",
|
||||
unit: "หน่วยนับ",
|
||||
weight: "น้ำหนัก (ร้อยละ)",
|
||||
};
|
||||
|
||||
const fieldLabels = {
|
||||
score5: "5",
|
||||
score4: "4",
|
||||
score3: "3",
|
||||
score2: "2",
|
||||
score1: "1",
|
||||
};
|
||||
|
||||
function clickList(index: number, data: any) {
|
||||
listCheck.value = index;
|
||||
// dataList.value = data.map((i: any) => ({
|
||||
// commandNo: i.commandNo,
|
||||
// duty: i.duty,
|
||||
// prefix: i.prefix,
|
||||
// firstName: i.firstName,
|
||||
// lastName: i.lastName,
|
||||
// fullName:`${i.prefix}${i.firstName} ${i.lastName}`
|
||||
// }));
|
||||
}
|
||||
|
||||
/** ปิด dialog */
|
||||
function closeDialog() {
|
||||
modal.value = false;
|
||||
search.value = ''
|
||||
define.value = ''
|
||||
formula.value = ''
|
||||
}
|
||||
|
||||
/** เรียกใช้ class */
|
||||
function getclass() {
|
||||
return "inputgreen";
|
||||
}
|
||||
|
||||
function onSubmit() {}
|
||||
</script>
|
||||
<template>
|
||||
<q-dialog v-model="modal" persistent>
|
||||
<q-card class="col-12" style="width: 85%">
|
||||
<q-form greedy @submit.prevent @validation-success="onSubmit">
|
||||
<DialogHeader
|
||||
:tittle="
|
||||
numpage == 1
|
||||
? 'เพิ่มตัวชี้วัดตามแผนปฏิบัติราชการประจําปี'
|
||||
: 'เพิ่มตัวชี้วัดตามหน้าที่ความรับผิดชอบ'
|
||||
"
|
||||
:close="closeDialog"
|
||||
/>
|
||||
<q-separator />
|
||||
|
||||
<q-card-section class="q-pa-none scroll" style="max-height: 80vh">
|
||||
<div class="col-12 row">
|
||||
<div class="bg-grey-1 q-pa-md col-xs-12 col-sm-4 col-md-3 row lineRight">
|
||||
<div class="col-12 fit">
|
||||
<div class="col-12 ">
|
||||
<q-input
|
||||
v-model="search"
|
||||
outlined
|
||||
dense
|
||||
label="ค้นหา"
|
||||
:class="getclass()"
|
||||
>
|
||||
<template v-slot:append>
|
||||
<q-icon v-if="search == ''" name="search" />
|
||||
<q-icon
|
||||
v-if="search !== ''"
|
||||
name="clear"
|
||||
class="cursor-pointer"
|
||||
@click="search = ''"
|
||||
/>
|
||||
</template>
|
||||
</q-input>
|
||||
</div>
|
||||
<q-card bordered flat class="q-mt-sm no-shadow bg-white col-12">
|
||||
<div class="row q-px-md q-py-sm items-center bg-grey-1">
|
||||
<div class="col-4">
|
||||
<span>รหัสตัวชี้วัด</span>
|
||||
</div>
|
||||
<div class="col-4">
|
||||
<span>ชื่อตัวชี้วัด</span>
|
||||
</div>
|
||||
</div>
|
||||
<q-separator/>
|
||||
|
||||
<q-card-section class="q-pa-none">
|
||||
<q-list
|
||||
separator
|
||||
dense
|
||||
>
|
||||
<q-item
|
||||
v-for="(item, index) in listTarget"
|
||||
:key="index"
|
||||
clickable
|
||||
v-ripple
|
||||
:active="listCheck === index"
|
||||
active-class="my-menu-link"
|
||||
@click="clickList(index, item.id)"
|
||||
>
|
||||
<q-item-section class="q-pa-none">
|
||||
<div class="row items-center" style="height: 20px">
|
||||
<div class="col-4">
|
||||
<span>{{ item.metricCode }}</span>
|
||||
</div>
|
||||
<div class="col-4">
|
||||
<span>{{ item.indicatorName }}</span>
|
||||
</div>
|
||||
</div>
|
||||
</q-item-section>
|
||||
</q-item>
|
||||
</q-list>
|
||||
</q-card-section>
|
||||
</q-card>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="col-xs-12 col-sm-8 col-md-9 row">
|
||||
<div class="row q-pa-md q-col-gutter-sm">
|
||||
<div class="col-12">
|
||||
<span class="text-body2 text-weight-medium"
|
||||
>รายละเอียดตัวชี้วัด</span
|
||||
>
|
||||
</div>
|
||||
<div class="col-8">
|
||||
<q-card bordered class="full-height q-pa-sm">
|
||||
<div
|
||||
v-for="(field, index) in Object.keys(fieldDetailLabels)"
|
||||
:key="index + 1"
|
||||
>
|
||||
<div class="row q-pa-sm q-col-gutter-lg col-12">
|
||||
<div class="col-4 text-grey-6">
|
||||
{{
|
||||
fieldDetailLabels[
|
||||
field as keyof typeof fieldDetailLabels
|
||||
]
|
||||
}}
|
||||
</div>
|
||||
<div class="col-8">
|
||||
<span>{{
|
||||
formDetail[field] ? formDetail[field] : "-"
|
||||
}}</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</q-card>
|
||||
</div>
|
||||
<div class="col-4 row ">
|
||||
<div class="row col-12 card-box">
|
||||
<div class="col-12 bg-grey-2 row items-center text-weight-medium">
|
||||
<div class="col-6 text-center">ระดับคะแนน</div>
|
||||
<div class="col-6 text-center">ผลสำเร็จของงาน</div>
|
||||
</div>
|
||||
|
||||
<div
|
||||
v-for="(field, index) in Object.keys(fieldLabels)"
|
||||
:key="index + 1"
|
||||
class="row col-12 items-center lineTop"
|
||||
>
|
||||
<div
|
||||
class="col-6 text-center text-body2"
|
||||
>
|
||||
{{ fieldLabels[field as keyof typeof fieldLabels] }}
|
||||
</div>
|
||||
<div class="col-6 text-center text-primary">
|
||||
<span>{{
|
||||
formScore[field] ? formScore[field] : "-"
|
||||
}}</span>
|
||||
</div>
|
||||
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-12">
|
||||
<q-input
|
||||
v-model="define"
|
||||
label="นิยามหรือความหมายของตัวชี้วัด"
|
||||
type="textarea"
|
||||
outlined
|
||||
autogrow
|
||||
dense
|
||||
:rules="[(val:string) => !!val || `${'กรุณากรอกตัวชี้วัด'}`,]"
|
||||
hide-bottom-space
|
||||
:class="getclass()"
|
||||
/>
|
||||
</div>
|
||||
<div class="col-12">
|
||||
<q-input
|
||||
v-model="formula"
|
||||
label="สูตรคำนวณ"
|
||||
type="textarea"
|
||||
outlined
|
||||
autogrow
|
||||
dense
|
||||
:rules="[(val:string) => !!val || `${'กรุณากรอกตัวชี้วัด'}`,]"
|
||||
hide-bottom-space
|
||||
:class="getclass()"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</q-card-section>
|
||||
<q-separator />
|
||||
|
||||
<q-card-actions align="right" class="bg-white text-teal">
|
||||
<q-btn
|
||||
label="บันทึก"
|
||||
color="secondary"
|
||||
type="submit"
|
||||
><q-tooltip>บันทึกข้อมูล</q-tooltip></q-btn
|
||||
>
|
||||
</q-card-actions>
|
||||
</q-form>
|
||||
</q-card>
|
||||
</q-dialog>
|
||||
</template>
|
||||
|
||||
<style scoped>
|
||||
.my-menu-link {
|
||||
background: #ebf9f7 !important;
|
||||
color: #1bb19ab8 !important;
|
||||
}
|
||||
.no-shadow{
|
||||
box-shadow:none !important;
|
||||
}
|
||||
.lineRight{
|
||||
border-right: 1px solid #EDEDED !important;
|
||||
}
|
||||
.lineTop{
|
||||
border-top: 1px solid #EDEDED !important;
|
||||
}
|
||||
.card-box{
|
||||
border: 1px solid #EDEDED !important;
|
||||
border-radius: 8px;
|
||||
}
|
||||
</style>
|
||||
122
src/modules/08_KPI/components/Tab/Dialog/03_Dialog.vue
Normal file
122
src/modules/08_KPI/components/Tab/Dialog/03_Dialog.vue
Normal file
|
|
@ -0,0 +1,122 @@
|
|||
<script setup lang="ts">
|
||||
import { ref, reactive } from "vue";
|
||||
import DialogHeader from "@/components/DialogHeader.vue";
|
||||
import type { FormDataAssigned } from '@/modules/08_KPI/interface/request/index'
|
||||
|
||||
const modal = defineModel<boolean>("modal", { required: true });
|
||||
|
||||
const formData = reactive<FormDataAssigned>({
|
||||
indicator:'',//ชื่อตัวชี้วัด
|
||||
target:'',//ค่าเป้าหมาย
|
||||
unit:'',//หน่วยนับ
|
||||
weigth:'',//น้ำหนัก (ร้อยละ)
|
||||
definition:'',//นิยามหรือความหมายของตัวชี้วัด
|
||||
})
|
||||
/** ปิด dialog */
|
||||
function closeDialog() {
|
||||
modal.value = false;
|
||||
formData.indicator = ''
|
||||
formData.target = ''
|
||||
formData.unit = ''
|
||||
formData.weigth = ''
|
||||
formData.definition = ''
|
||||
}
|
||||
|
||||
/** เรียกใช้ class */
|
||||
function getclass() {
|
||||
return "inputgreen";
|
||||
}
|
||||
|
||||
function onSubmit() {}
|
||||
</script>
|
||||
<template>
|
||||
<q-dialog v-model="modal" persistent>
|
||||
<q-card class="col-12" style="width: 50%">
|
||||
<q-form greedy @submit.prevent @validation-success="onSubmit">
|
||||
<DialogHeader
|
||||
:tittle="`เพิ่มตัวชี้วัดที่ได้รับมอบหมาย`"
|
||||
:close="closeDialog"
|
||||
/>
|
||||
<q-separator />
|
||||
|
||||
<q-card-section >
|
||||
<div class="row q-col-gutter-sm">
|
||||
<div class="col-12">
|
||||
<q-input
|
||||
v-model="formData.indicator"
|
||||
label="ชื่อตัวชี้วัด"
|
||||
outlined
|
||||
dense
|
||||
:rules="[(val:string) => !!val || `${'กรุณากรอกชื่อตัวชี้วัด'}`,]"
|
||||
hide-bottom-space
|
||||
:class="getclass()"
|
||||
/>
|
||||
</div>
|
||||
<div class="col-4">
|
||||
<q-input
|
||||
v-model="formData.target"
|
||||
label="ค่าเป้าหมาย"
|
||||
outlined
|
||||
dense
|
||||
:rules="[(val:string) => !!val || `${'กรุณากรอกค่าเป้าหมาย'}`,]"
|
||||
hide-bottom-space
|
||||
:class="getclass()"
|
||||
/>
|
||||
</div>
|
||||
<div class="col-4">
|
||||
<q-input
|
||||
v-model="formData.unit"
|
||||
label="หน่วยนับ"
|
||||
outlined
|
||||
dense
|
||||
:rules="[(val:string) => !!val || `${'กรุณากรอกหน่วยนับ'}`,]"
|
||||
hide-bottom-space
|
||||
:class="getclass()"
|
||||
/>
|
||||
</div>
|
||||
<div class="col-4">
|
||||
<q-input
|
||||
v-model="formData.weigth"
|
||||
label="น้ำหนัก (ร้อยละ)"
|
||||
outlined
|
||||
dense
|
||||
:rules="[(val:string) => !!val || `${'กรุณากรอกน้ำหนัก (ร้อยละ)'}`,]"
|
||||
hide-bottom-space
|
||||
:class="getclass()"
|
||||
/>
|
||||
</div>
|
||||
<div class="col-12">
|
||||
<q-input
|
||||
v-model="formData.definition"
|
||||
label="นิยามหรือความหมายของตัวชี้วัด"
|
||||
outlined
|
||||
dense
|
||||
type="textarea"
|
||||
:rules="[(val:string) => !!val || `${'กรุณากรอกนิยามหรือความหมายของตัวชี้วัด'}`,]"
|
||||
hide-bottom-space
|
||||
:class="getclass()"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</q-card-section>
|
||||
<q-separator />
|
||||
|
||||
<q-card-actions align="right" class="bg-white text-teal">
|
||||
<q-btn
|
||||
label="บันทึก"
|
||||
color="secondary"
|
||||
type="submit"
|
||||
><q-tooltip>บันทึกข้อมูล</q-tooltip></q-btn
|
||||
>
|
||||
</q-card-actions>
|
||||
</q-form>
|
||||
</q-card>
|
||||
</q-dialog>
|
||||
</template>
|
||||
|
||||
<style scoped>
|
||||
.my-menu-link {
|
||||
background: #ebf9f7 !important;
|
||||
color: #1bb19ab8 !important;
|
||||
}
|
||||
</style>
|
||||
297
src/modules/08_KPI/components/Tab/Dialog/04_Dialog.vue
Normal file
297
src/modules/08_KPI/components/Tab/Dialog/04_Dialog.vue
Normal file
|
|
@ -0,0 +1,297 @@
|
|||
<script setup lang="ts">
|
||||
import { ref, reactive } from "vue";
|
||||
import DialogHeader from "@/components/DialogHeader.vue";
|
||||
import type { DataOptions } from "@/modules/08_KPI/interface/index/Main";
|
||||
|
||||
const modal = defineModel<boolean>("modal", { required: true });
|
||||
const numpage = defineModel<number>("numpage", { required: true });
|
||||
const splitterModel = ref<number>(30);
|
||||
const search = ref<string>("");
|
||||
|
||||
const define = ref<string>("");
|
||||
const formula = ref<string>("");
|
||||
const type = ref<string>("");
|
||||
|
||||
const listCheck = ref<number | null>();
|
||||
const listTarget = ref<any>([
|
||||
{
|
||||
id: "ID1",
|
||||
metricCode: "1กก",
|
||||
indicatorName: "ตัวชี้วัด 1",
|
||||
},
|
||||
{
|
||||
id: "ID2",
|
||||
metricCode: "2กก",
|
||||
indicatorName: "ตัวชี้วัด 2",
|
||||
},
|
||||
]);
|
||||
|
||||
const formDetail = reactive<any>({
|
||||
type: "สมรรถนะหลัก",
|
||||
name: "สมรรถนะ 1",
|
||||
definition: "",
|
||||
criteria: "",
|
||||
});
|
||||
const formScore = reactive<any>({
|
||||
score1: "1",
|
||||
score2: "2",
|
||||
score3: "3",
|
||||
score4: "",
|
||||
score5: "5",
|
||||
});
|
||||
|
||||
const fieldDetailLabels = {
|
||||
type: "ประเภทสมรรถนะ",
|
||||
name: "ชื่อสมรรถนะ",
|
||||
definition: "คำจำกัดความ",
|
||||
criteria: "กำหนดเกณฑ์การประเมิน",
|
||||
};
|
||||
|
||||
const fieldLabels = {
|
||||
score1: "1",
|
||||
score2: "2",
|
||||
score3: "3",
|
||||
score4: "4",
|
||||
score5: "5",
|
||||
};
|
||||
|
||||
const competencyTypeOp = ref<DataOptions[]>([
|
||||
{
|
||||
id: "ID1",
|
||||
name: "สมรรถนะหลัก",
|
||||
},
|
||||
{
|
||||
id: "ID2",
|
||||
name: "สมรรถนะประจำกลุ่มงาน",
|
||||
},
|
||||
{
|
||||
id: "ID3",
|
||||
name: "สมรรถนะประจำกลุ่มงาน",
|
||||
},
|
||||
{
|
||||
id: "ID4",
|
||||
name: "สมรรถนะประจำผู้บริหารกรุงเทพมหานคร",
|
||||
},
|
||||
{
|
||||
id: "ID5",
|
||||
name: "สมรรถนะเฉพาะสำหรับตำแหน่ง ผอ.เขต ผช.ผอ.เขต และหัวหน้าฝ่ายในสังกัด สนง.เขต",
|
||||
},
|
||||
{
|
||||
id: "ID6",
|
||||
name: "สมรรถนะเฉพาะสำหรับตำแหน่งผู้ตรวจราชการ กทม. และผู้ตรวจราชการ",
|
||||
},
|
||||
]);
|
||||
|
||||
function clickList(index: number, data: any) {
|
||||
listCheck.value = index;
|
||||
// dataList.value = data.map((i: any) => ({
|
||||
// commandNo: i.commandNo,
|
||||
// duty: i.duty,
|
||||
// prefix: i.prefix,
|
||||
// firstName: i.firstName,
|
||||
// lastName: i.lastName,
|
||||
// fullName:`${i.prefix}${i.firstName} ${i.lastName}`
|
||||
// }));
|
||||
}
|
||||
|
||||
/** ปิด dialog */
|
||||
function closeDialog() {
|
||||
modal.value = false;
|
||||
type.value = ''
|
||||
search.value = ''
|
||||
}
|
||||
|
||||
/** เรียกใช้ class */
|
||||
function getclass() {
|
||||
return "inputgreen";
|
||||
}
|
||||
|
||||
function onSubmit() {}
|
||||
</script>
|
||||
<template>
|
||||
<q-dialog v-model="modal" persistent>
|
||||
<q-card class="col-12" style="width: 85%">
|
||||
<q-form greedy @submit.prevent @validation-success="onSubmit">
|
||||
<DialogHeader :tittle="`เพิ่มสมรรถนะ`" :close="closeDialog" />
|
||||
<q-separator />
|
||||
|
||||
<q-card-section class="q-pa-none scroll" style="max-height: 80vh">
|
||||
<div class="col-12 row">
|
||||
<div class="bg-grey-1 q-pa-md col-xs-12 col-sm-4 col-md-3 row lineRight">
|
||||
<div class="col-12 q-col-gutter-sm fit">
|
||||
<div class="col-12 ">
|
||||
<q-select
|
||||
v-model="type"
|
||||
outlined
|
||||
label="ประเภทสมรรถนะ"
|
||||
dense
|
||||
bg-color="white"
|
||||
option-label="name"
|
||||
option-value="id"
|
||||
:options="competencyTypeOp"
|
||||
emit-value
|
||||
:class="getclass()"
|
||||
map-options
|
||||
/>
|
||||
</div>
|
||||
<div class="col-12 ">
|
||||
<q-input
|
||||
v-model="search"
|
||||
outlined
|
||||
dense
|
||||
label="ค้นหา"
|
||||
bg-color="white"
|
||||
:class="getclass()"
|
||||
>
|
||||
<template v-slot:append>
|
||||
<q-icon v-if="search == ''" name="search" />
|
||||
<q-icon
|
||||
v-if="search !== ''"
|
||||
name="clear"
|
||||
class="cursor-pointer"
|
||||
@click="search = ''"
|
||||
/>
|
||||
</template>
|
||||
</q-input>
|
||||
</div>
|
||||
<div class="col-12 ">
|
||||
<q-card bordered flat class="no-shadow bg-white col-12">
|
||||
<div class="row q-px-md q-py-sm items-center bg-grey-1">
|
||||
<div class="col-4">
|
||||
<span>รหัสตัวชี้วัด</span>
|
||||
</div>
|
||||
<div class="col-4">
|
||||
<span>ชื่อตัวชี้วัด</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<q-separator />
|
||||
<q-card-section class="q-pa-none">
|
||||
<q-list
|
||||
separator
|
||||
dense
|
||||
>
|
||||
<q-item
|
||||
v-for="(item, index) in listTarget"
|
||||
:key="index"
|
||||
clickable
|
||||
v-ripple
|
||||
:active="listCheck === index"
|
||||
active-class="my-menu-link"
|
||||
@click="clickList(index, item.id)"
|
||||
>
|
||||
<q-item-section class="q-pa-none">
|
||||
<div class="row items-center" style="height: 20px">
|
||||
<div class="col-4">
|
||||
<span>{{ item.metricCode }}</span>
|
||||
</div>
|
||||
<div class="col-4">
|
||||
<span>{{ item.indicatorName }}</span>
|
||||
</div>
|
||||
</div>
|
||||
</q-item-section>
|
||||
</q-item>
|
||||
</q-list>
|
||||
</q-card-section>
|
||||
</q-card>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="col-xs-12 col-sm-8 col-md-9 row">
|
||||
<div class="row col-12 q-pa-md q-col-gutter-sm">
|
||||
<div class="col-12">
|
||||
<span class="text-body2 text-weight-medium"
|
||||
>รายละเอียดตัวชี้วัด</span
|
||||
>
|
||||
</div>
|
||||
<div class="col-8 row">
|
||||
<q-card bordered class="fit q-pa-sm no-shadow">
|
||||
<div
|
||||
v-for="(field, index) in Object.keys(fieldDetailLabels)"
|
||||
:key="index + 1"
|
||||
>
|
||||
<div class="row q-pa-sm q-col-gutter-lg col-12">
|
||||
<div class="col-4 text-grey-6">
|
||||
{{
|
||||
fieldDetailLabels[
|
||||
field as keyof typeof fieldDetailLabels
|
||||
]
|
||||
}}
|
||||
</div>
|
||||
<div class="col-8">
|
||||
<span>{{
|
||||
formDetail[field] ? formDetail[field] : "-"
|
||||
}}</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</q-card>
|
||||
</div>
|
||||
<div class="col-4 row ">
|
||||
<q-card bordered class="col-12 row no-shadow">
|
||||
<div class="bg-grey-2 row q-py-sm text-weight-bold col-12">
|
||||
<div class="col-6 text-center">ระดับคะแนน</div>
|
||||
<div class="col-6 text-center">ผลสำเร็จของงาน</div>
|
||||
</div>
|
||||
<div
|
||||
v-for="(field, index) in Object.keys(fieldLabels)"
|
||||
:key="index + 1"
|
||||
class="col-12"
|
||||
>
|
||||
<div class="row col-12 q-py-sm">
|
||||
<div
|
||||
class="col-6 text-center text-body2"
|
||||
>
|
||||
{{ fieldLabels[field as keyof typeof fieldLabels] }}
|
||||
</div>
|
||||
<div class="col-6 text-center">
|
||||
<span>{{
|
||||
formScore[field] ? formScore[field] : "-"
|
||||
}}</span>
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="col-12"
|
||||
v-if="index !== Object.keys(fieldLabels).length - 1"
|
||||
>
|
||||
<q-separator />
|
||||
</div>
|
||||
</div>
|
||||
</q-card>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</q-card-section>
|
||||
<q-separator />
|
||||
|
||||
<q-card-actions align="right" class="bg-white text-teal">
|
||||
<q-btn label="บันทึก" color="secondary" type="submit"
|
||||
><q-tooltip>บันทึกข้อมูล</q-tooltip></q-btn
|
||||
>
|
||||
</q-card-actions>
|
||||
</q-form>
|
||||
</q-card>
|
||||
</q-dialog>
|
||||
</template>
|
||||
|
||||
<style scoped>
|
||||
.my-menu-link {
|
||||
background: #ebf9f7 !important;
|
||||
color: #1bb19ab8 !important;
|
||||
}
|
||||
.no-shadow{
|
||||
box-shadow:none !important;
|
||||
}
|
||||
.lineRight{
|
||||
border-right: 1px solid #EDEDED !important;
|
||||
}
|
||||
.lineTop{
|
||||
border-top: 1px solid #EDEDED !important;
|
||||
}
|
||||
.card-box{
|
||||
border: 1px solid #EDEDED !important;
|
||||
border-radius: 8px;
|
||||
}
|
||||
</style>
|
||||
206
src/modules/08_KPI/components/Tab/Topic/01_Template.vue
Normal file
206
src/modules/08_KPI/components/Tab/Topic/01_Template.vue
Normal file
|
|
@ -0,0 +1,206 @@
|
|||
<script setup lang="ts">
|
||||
import { ref } from "vue";
|
||||
import Dialog from "@/modules/08_KPI/components/Tab/Dialog/01_Dialog.vue";
|
||||
import Dialog03 from "@/modules/08_KPI/components/Tab/Dialog/03_Dialog.vue";
|
||||
import type { QTableProps } from "quasar";
|
||||
import { useCounterMixin } from "@/stores/mixin";
|
||||
|
||||
const title = defineModel<string>('title',{required:true})
|
||||
const rows = defineModel<any>('data',{required:true})
|
||||
const numpage = defineModel<number>('page',{required:true})
|
||||
|
||||
const mixin = useCounterMixin();
|
||||
const { date2Thai } = mixin;
|
||||
const filterKeyword = ref<string>("");
|
||||
const modal = ref<boolean>(false);
|
||||
const modalAssigned = ref<boolean>(false);
|
||||
|
||||
const visibleColumns = ref<string[]>([
|
||||
"indicators",
|
||||
"target",
|
||||
"scoreLevel",
|
||||
"weight",
|
||||
"workResult",
|
||||
"evaluationResults",
|
||||
]);
|
||||
|
||||
const columns = ref<QTableProps["columns"]>([
|
||||
{
|
||||
name: "indicators",
|
||||
align: "left",
|
||||
label: "ตัวชี้วัด",
|
||||
sortable: true,
|
||||
field: "indicators",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
{
|
||||
name: "target",
|
||||
align: "left",
|
||||
label: "ค่าเป้าหมาย",
|
||||
sortable: true,
|
||||
field: "target",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
{
|
||||
name: "scoreLevel",
|
||||
align: "left",
|
||||
label: "ระดับคะแนนตามเกณฑ์การประเมิน",
|
||||
sortable: true,
|
||||
field: "scoreLevel",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
{
|
||||
name: "weight",
|
||||
align: "left",
|
||||
label: "น้ำหนัก (ร้อยละ)",
|
||||
sortable: true,
|
||||
field: "weight",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
{
|
||||
name: "workResult",
|
||||
align: "left",
|
||||
label: "ผลสำเร็จของงาน",
|
||||
sortable: true,
|
||||
field: "workResult",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
{
|
||||
name: "evaluationResults",
|
||||
align: "left",
|
||||
label: "ผลการประเมิน",
|
||||
sortable: true,
|
||||
field: "evaluationResults",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
]);
|
||||
|
||||
function onAdd() {
|
||||
if(numpage.value !== 3){
|
||||
modal.value = true;
|
||||
}else if(numpage.value == 3){
|
||||
modalAssigned.value = true
|
||||
}
|
||||
}
|
||||
</script>
|
||||
<template>
|
||||
<q-card bordered style="border-radius: 5px" class="no-shadow">
|
||||
<q-card-section class="bg-grey-2 q-py-sm">
|
||||
<span class="text-weight-medium">{{ title }}</span>
|
||||
<q-btn
|
||||
class="q-ml-xs"
|
||||
flat
|
||||
round
|
||||
icon="mdi-plus"
|
||||
color="primary"
|
||||
size="12px"
|
||||
dense
|
||||
@click="onAdd"
|
||||
>
|
||||
<q-tooltip>เพิ่มข้อมูล</q-tooltip>
|
||||
</q-btn>
|
||||
</q-card-section>
|
||||
<q-separator/>
|
||||
<q-card-section class="q-pa-sm">
|
||||
<q-table
|
||||
ref="table"
|
||||
:columns="columns"
|
||||
:rows="rows"
|
||||
:filter="filterKeyword"
|
||||
row-key="id"
|
||||
flat
|
||||
bordered
|
||||
:paging="true"
|
||||
dense
|
||||
hide-pagination
|
||||
class="custom-table2"
|
||||
:visible-columns="visibleColumns"
|
||||
no-data-label="ยังไม่มีข้อมูลแสดงในตารางนี้"
|
||||
>
|
||||
<template v-slot:header="props">
|
||||
<q-tr :props="props">
|
||||
<q-th v-for="col in props.cols" :key="col.name" :props="props">
|
||||
<span class="text-weight-medium">{{ col.label }}</span>
|
||||
</q-th>
|
||||
<q-th auto-width />
|
||||
</q-tr>
|
||||
</template>
|
||||
<template v-slot:body="props">
|
||||
<q-tr :props="props" class="cursor-pointer">
|
||||
<q-td v-for="col in props.cols" :key="col.id">
|
||||
<div v-if="col.name == 'createDate'">
|
||||
{{ col.value ? date2Thai(col.value) : "-" }}
|
||||
</div>
|
||||
<div v-else>
|
||||
{{ col.value ? col.value : "-" }}
|
||||
</div>
|
||||
</q-td>
|
||||
</q-tr>
|
||||
</template>
|
||||
</q-table>
|
||||
</q-card-section>
|
||||
</q-card>
|
||||
|
||||
<Dialog v-model:modal="modal" :numpage="numpage"/>
|
||||
<Dialog03 v-model:modal="modalAssigned" :numpage="numpage"/>
|
||||
</template>
|
||||
<style scoped>
|
||||
.custom-table2 {
|
||||
max-height: 64vh;
|
||||
|
||||
.q-table tr:nth-child(odd) td {
|
||||
background: white;
|
||||
}
|
||||
|
||||
.q-table tr:nth-child(even) td {
|
||||
background: #f8f8f8;
|
||||
}
|
||||
|
||||
.q-table thead tr {
|
||||
background: #ecebeb;
|
||||
}
|
||||
|
||||
.q-table thead tr th {
|
||||
position: sticky;
|
||||
}
|
||||
|
||||
.q-table td:nth-of-type(2) {
|
||||
z-index: 3 !important;
|
||||
}
|
||||
|
||||
.q-table th:nth-of-type(2),
|
||||
.q-table td:nth-of-type(2) {
|
||||
position: sticky;
|
||||
left: 0;
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
/* this will be the loading indicator */
|
||||
.q-table thead tr:last-child th {
|
||||
/* height of all previous header rows */
|
||||
top: 48px;
|
||||
}
|
||||
|
||||
.q-table thead tr:first-child th {
|
||||
top: 0;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
188
src/modules/08_KPI/components/Tab/Topic/02_Template.vue
Normal file
188
src/modules/08_KPI/components/Tab/Topic/02_Template.vue
Normal file
|
|
@ -0,0 +1,188 @@
|
|||
<script setup lang="ts">
|
||||
import { ref } from "vue";
|
||||
import Dialog from "@/modules/08_KPI/components/Tab/Dialog/04_Dialog.vue";
|
||||
|
||||
import type { QTableProps } from "quasar";
|
||||
import { useCounterMixin } from "@/stores/mixin";
|
||||
|
||||
const title = defineModel<string>('title',{required:true})
|
||||
const rows = defineModel<any>('data',{required:true})
|
||||
const numpage = defineModel<number>('page',{required:true})
|
||||
|
||||
const mixin = useCounterMixin();
|
||||
const { date2Thai } = mixin;
|
||||
const filterKeyword = ref<string>("");
|
||||
const modal = ref<boolean>(false);
|
||||
const modalAssigned = ref<boolean>(false);
|
||||
|
||||
const visibleColumns = ref<string[]>([
|
||||
"capacity",
|
||||
"level",
|
||||
"scoreLevel",
|
||||
"weight",
|
||||
"evaluationResults",
|
||||
]);
|
||||
|
||||
const columns = ref<QTableProps["columns"]>([
|
||||
{
|
||||
name: "capacity",
|
||||
align: "left",
|
||||
label: "รายการสมรรถนะ",
|
||||
sortable: true,
|
||||
field: "capacity",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
{
|
||||
name: "level",
|
||||
align: "left",
|
||||
label: "ระดับที่คาดหวัง",
|
||||
sortable: true,
|
||||
field: "level",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
{
|
||||
name: "scoreLevel",
|
||||
align: "left",
|
||||
label: "ระดับคะแนนตามเกณฑ์การประเมิน",
|
||||
sortable: true,
|
||||
field: "scoreLevel",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
{
|
||||
name: "weight",
|
||||
align: "left",
|
||||
label: "น้ำหนัก (ร้อยละ)",
|
||||
sortable: true,
|
||||
field: "weight",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
{
|
||||
name: "evaluationResults",
|
||||
align: "left",
|
||||
label: "ผลการประเมิน",
|
||||
sortable: true,
|
||||
field: "evaluationResults",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
]);
|
||||
|
||||
function onAdd() {
|
||||
modal.value = true;
|
||||
}
|
||||
</script>
|
||||
<template>
|
||||
<q-card bordered style="border-radius: 5px" class="no-shadow">
|
||||
<q-card-section class="bg-grey-3 q-py-sm">
|
||||
<span class="text-weight-medium">{{ title }}</span>
|
||||
<q-btn
|
||||
class="q-ml-xs"
|
||||
flat
|
||||
round
|
||||
icon="mdi-plus"
|
||||
color="primary"
|
||||
size="12px"
|
||||
dense
|
||||
@click="onAdd"
|
||||
>
|
||||
<q-tooltip>เพิ่มข้อมูล</q-tooltip>
|
||||
</q-btn>
|
||||
</q-card-section>
|
||||
<q-card-section class="q-pa-sm">
|
||||
<q-table
|
||||
ref="table"
|
||||
:columns="columns"
|
||||
:rows="rows"
|
||||
:filter="filterKeyword"
|
||||
row-key="id"
|
||||
flat
|
||||
bordered
|
||||
:paging="true"
|
||||
dense
|
||||
hide-pagination
|
||||
class="custom-table2"
|
||||
:visible-columns="visibleColumns"
|
||||
no-data-label="ยังไม่มีข้อมูลแสดงในตารางนี้"
|
||||
>
|
||||
<template v-slot:header="props">
|
||||
<q-tr :props="props">
|
||||
<q-th v-for="col in props.cols" :key="col.name" :props="props">
|
||||
<span class="text-weight-medium">{{ col.label }}</span>
|
||||
</q-th>
|
||||
<q-th auto-width />
|
||||
</q-tr>
|
||||
</template>
|
||||
<template v-slot:body="props">
|
||||
<q-tr :props="props" class="cursor-pointer">
|
||||
<q-td v-for="col in props.cols" :key="col.id">
|
||||
<div v-if="col.name == 'createDate'">
|
||||
{{ col.value ? date2Thai(col.value) : "-" }}
|
||||
</div>
|
||||
<div v-else>
|
||||
{{ col.value ? col.value : "-" }}
|
||||
</div>
|
||||
</q-td>
|
||||
</q-tr>
|
||||
</template>
|
||||
</q-table>
|
||||
</q-card-section>
|
||||
</q-card>
|
||||
|
||||
<Dialog v-model:modal="modal" :numpage="numpage"/>
|
||||
</template>
|
||||
<style scoped>
|
||||
.custom-table2 {
|
||||
max-height: 64vh;
|
||||
|
||||
.q-table tr:nth-child(odd) td {
|
||||
background: white;
|
||||
}
|
||||
|
||||
.q-table tr:nth-child(even) td {
|
||||
background: #f8f8f8;
|
||||
}
|
||||
|
||||
.q-table thead tr {
|
||||
background: #ecebeb;
|
||||
}
|
||||
|
||||
.q-table thead tr th {
|
||||
position: sticky;
|
||||
}
|
||||
|
||||
.q-table td:nth-of-type(2) {
|
||||
z-index: 3 !important;
|
||||
}
|
||||
|
||||
.q-table th:nth-of-type(2),
|
||||
.q-table td:nth-of-type(2) {
|
||||
position: sticky;
|
||||
left: 0;
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
/* this will be the loading indicator */
|
||||
.q-table thead tr:last-child th {
|
||||
/* height of all previous header rows */
|
||||
top: 48px;
|
||||
}
|
||||
|
||||
.q-table thead tr:first-child th {
|
||||
top: 0;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
8
src/modules/08_KPI/interface/index/Main.ts
Normal file
8
src/modules/08_KPI/interface/index/Main.ts
Normal file
|
|
@ -0,0 +1,8 @@
|
|||
interface DataOptions {
|
||||
id:string
|
||||
name:string
|
||||
}
|
||||
|
||||
export type {
|
||||
DataOptions
|
||||
}
|
||||
22
src/modules/08_KPI/interface/request/index.ts
Normal file
22
src/modules/08_KPI/interface/request/index.ts
Normal file
|
|
@ -0,0 +1,22 @@
|
|||
interface FormProfile {
|
||||
fullName: string;
|
||||
prefix: string;
|
||||
firstName: string;
|
||||
lastName: string;
|
||||
position: string;
|
||||
type: string;
|
||||
level: string;
|
||||
status: string;
|
||||
score: string;
|
||||
|
||||
avartar:string
|
||||
}
|
||||
|
||||
interface FormDataAssigned{
|
||||
indicator:string
|
||||
target:string
|
||||
unit:string
|
||||
weigth:string
|
||||
definition:string
|
||||
}
|
||||
export type { FormProfile ,FormDataAssigned};
|
||||
55
src/modules/08_KPI/router.ts
Normal file
55
src/modules/08_KPI/router.ts
Normal file
|
|
@ -0,0 +1,55 @@
|
|||
/**
|
||||
* Router ขอโอน
|
||||
*/
|
||||
|
||||
const KPIPage = () => import("@/modules/08_KPI/views/main.vue");
|
||||
const FormPage = () => import("@/modules/08_KPI/views/form.vue");
|
||||
const KPIMainEvaluator = () => import("@/modules/08_KPI/views/mainEvaluator.vue");
|
||||
|
||||
export default [
|
||||
{
|
||||
path: "/KPI",
|
||||
name: "KPIMain",
|
||||
component: KPIPage,
|
||||
meta: {
|
||||
Auth: true,
|
||||
Key: [8],
|
||||
},
|
||||
},
|
||||
{
|
||||
path: "/KPI/add",
|
||||
name: "KPIAdd",
|
||||
component: FormPage,
|
||||
meta: {
|
||||
Auth: true,
|
||||
Key: [8.1],
|
||||
},
|
||||
},
|
||||
{
|
||||
path: "/KPI/:id",
|
||||
name: "KPIEdit",
|
||||
component: FormPage,
|
||||
meta: {
|
||||
Auth: true,
|
||||
Key: [8.2],
|
||||
},
|
||||
},
|
||||
{
|
||||
path: "/KPI-evaluator",
|
||||
name: "KPIMainEvaluator",
|
||||
component: KPIMainEvaluator,
|
||||
meta: {
|
||||
Auth: true,
|
||||
Key: [8.3],
|
||||
},
|
||||
},
|
||||
{
|
||||
path: "/KPI-evaluator/:id",
|
||||
name: "KPIEditEvaluator",
|
||||
component: FormPage,
|
||||
meta: {
|
||||
Auth: true,
|
||||
Key: [8.4],
|
||||
},
|
||||
},
|
||||
];
|
||||
7
src/modules/08_KPI/store.ts
Normal file
7
src/modules/08_KPI/store.ts
Normal file
|
|
@ -0,0 +1,7 @@
|
|||
import { defineStore } from "pinia";
|
||||
import { ref } from "vue";
|
||||
|
||||
export const useKpiDataStore = defineStore("KPIDate", () => {
|
||||
const tabMain = ref<string>("1");
|
||||
return {tabMain};
|
||||
});
|
||||
86
src/modules/08_KPI/views/TabMain.vue
Normal file
86
src/modules/08_KPI/views/TabMain.vue
Normal file
|
|
@ -0,0 +1,86 @@
|
|||
<script setup lang="ts">
|
||||
import { ref } from "vue";
|
||||
import { useKpiDataStore } from '@/modules/08_KPI/store'
|
||||
|
||||
import Assessment from '@/modules/08_KPI/components/Tab/01_Assessment.vue'
|
||||
import CommanderAbove from '@/modules/08_KPI/components/Tab/02_CommanderAbove.vue'
|
||||
import CommanderAboveOneStep from '@/modules/08_KPI/components/Tab/03_CommanderAboveOneStep.vue'
|
||||
import File from '@/modules/08_KPI/components/Tab/04_File.vue'
|
||||
|
||||
const store = useKpiDataStore()
|
||||
|
||||
const itemsTab = ref<any>([
|
||||
{
|
||||
name: "1",
|
||||
label: "ผู้ขอรับการประเมิน",
|
||||
},
|
||||
{
|
||||
name: "2",
|
||||
label: "ผู้บังคับบัญชาเหนือขึ้นไป",
|
||||
},
|
||||
{
|
||||
name: "3",
|
||||
label: "ผู้บังคับบัญชาเหนือขึ้นไปอีกหนึ่งขั้น",
|
||||
},
|
||||
{
|
||||
name: "4",
|
||||
label: "ไฟล์เอกสาร",
|
||||
},
|
||||
]);
|
||||
|
||||
const splitterModel = ref<number>(12);
|
||||
</script>
|
||||
<template>
|
||||
<q-splitter v-model="splitterModel" disable>
|
||||
<template v-slot:before>
|
||||
<q-tabs v-model="store.tabMain" vertical class="text-grey-7 text-weight-light" active-class="bg-blue-1 text-blue-8 text-weight-bold">
|
||||
<!-- <q-tab
|
||||
class="hover-tab"
|
||||
v-for="(tab, index) in itemsTab"
|
||||
:key="index"
|
||||
:name="tab.name"
|
||||
:icon="tab.icon"
|
||||
:label="tab.label"
|
||||
/> -->
|
||||
<q-tab name="1" label="ผู้ขอรับการประเมิน" />
|
||||
<q-tab name="2" label="ผู้บังคับบัญชา">
|
||||
<div class="text-caption">เหนือขึ้นไป</div>
|
||||
</q-tab>
|
||||
<q-tab name="3" label="ผู้บังคับบัญชา">
|
||||
<div class="text-caption">เหนือขึ้นไปอีกหนึ่งขั้น</div>
|
||||
</q-tab>
|
||||
<q-tab name="4" label="ไฟล์เอกสาร" />
|
||||
</q-tabs>
|
||||
</template>
|
||||
|
||||
<template v-slot:after>
|
||||
<q-tab-panels
|
||||
v-model="store.tabMain"
|
||||
animated
|
||||
swipeable
|
||||
vertical
|
||||
transition-prev="jump-up"
|
||||
transition-next="jump-up"
|
||||
>
|
||||
<q-tab-panel
|
||||
v-for="(tab, index) in itemsTab"
|
||||
:key="index"
|
||||
:name="tab.name"
|
||||
class="q-pa-none"
|
||||
>
|
||||
<Assessment v-if="store.tabMain === '1'" />
|
||||
<CommanderAbove v-if="store.tabMain === '2'" />
|
||||
<CommanderAboveOneStep v-if="store.tabMain === '3'" />
|
||||
<File v-if="store.tabMain === '4'" />
|
||||
</q-tab-panel>
|
||||
</q-tab-panels>
|
||||
</template>
|
||||
</q-splitter>
|
||||
</template>
|
||||
<style scoped>
|
||||
.hover-tab:hover {
|
||||
background-color: #0793f1;
|
||||
color: white !important;
|
||||
opacity: 1 !important;
|
||||
}
|
||||
</style>
|
||||
185
src/modules/08_KPI/views/form.vue
Normal file
185
src/modules/08_KPI/views/form.vue
Normal file
|
|
@ -0,0 +1,185 @@
|
|||
<script setup lang="ts">
|
||||
import { ref, onMounted, reactive } from "vue";
|
||||
import { useRoute, useRouter } from "vue-router";
|
||||
import TabMain from "@/modules/08_KPI/views/TabMain.vue";
|
||||
import http from "@/plugins/http";
|
||||
import config from "@/app.config";
|
||||
|
||||
import { useCounterMixin } from "@/stores/mixin";
|
||||
import { useQuasar } from "quasar";
|
||||
|
||||
import type { FormProfile } from "@/modules/08_KPI/interface/request/index";
|
||||
|
||||
const route = useRoute();
|
||||
const id = route.params.id as string;
|
||||
|
||||
const $q = useQuasar();
|
||||
const mixin = useCounterMixin();
|
||||
const { showLoader, hideLoader, messageError } = mixin;
|
||||
|
||||
const formProfile = reactive<FormProfile>({
|
||||
fullName: "นางสาวกัณฐิมา กาฬสินธุ์",
|
||||
prefix: "นางสาว",
|
||||
firstName: "กัณฐิมา",
|
||||
lastName: "กาฬสินธุ์",
|
||||
position: "หัวหน้าสำนักงาน",
|
||||
type: "บริหาร",
|
||||
level: "ชำนาญการพิเศษ",
|
||||
status: "จัดเตรียมข้อมูล",
|
||||
score: "100",
|
||||
avartar:
|
||||
"https://cdn.quasar.dev/img/boy-avatar.png",
|
||||
});
|
||||
|
||||
const router = useRouter();
|
||||
|
||||
function getProfile() {
|
||||
showLoader();
|
||||
http
|
||||
.get(config.API.profileBykeycloak())
|
||||
.then((res) => {
|
||||
const data = res.data.result;
|
||||
})
|
||||
.catch((e) => {
|
||||
messageError($q, e);
|
||||
})
|
||||
.finally(() => {
|
||||
hideLoader();
|
||||
});
|
||||
}
|
||||
|
||||
/** save */
|
||||
function onSave() {}
|
||||
|
||||
onMounted(() => {
|
||||
getProfile();
|
||||
});
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div class="col-12 row justify-center">
|
||||
<div class="col-xs-12 col-sm-12 col-md-11">
|
||||
<div class="toptitle text-white col-12 row items-center">
|
||||
<q-btn
|
||||
icon="mdi-arrow-left"
|
||||
unelevated
|
||||
round
|
||||
dense
|
||||
flat
|
||||
color="primary"
|
||||
class="q-mr-sm"
|
||||
@click="router.push(`/KPI`)"
|
||||
/>
|
||||
{{ id ? `แก้ไขแบบประเมิน` : `เพิ่มแบบประเมิน` }}
|
||||
<q-space />
|
||||
<q-btn label="บันทึก" color="secondary" unelevated @click="onSave"
|
||||
><q-tooltip>บันทึก</q-tooltip></q-btn
|
||||
>
|
||||
</div>
|
||||
<div class="col-12">
|
||||
<q-card bordered flat class="relative-position">
|
||||
<div
|
||||
class="absolute"
|
||||
style="left: 2%; top: 50%; transform: translateY(-50%)"
|
||||
>
|
||||
<q-avatar size="95px">
|
||||
<q-img :src="formProfile.avartar" />
|
||||
</q-avatar>
|
||||
</div>
|
||||
<div class="row col-12">
|
||||
<div class="row items-center col-12 q-pa-sm">
|
||||
<div class="col-12" style="padding-left: 12%;">
|
||||
<div class="row col-12 items-center">
|
||||
<span class="text-h6 text-weight-medium text-primary">{{
|
||||
formProfile.fullName ? formProfile.fullName : "-"
|
||||
}}</span>
|
||||
<q-space />
|
||||
<div class="q-gutter-x-sm">
|
||||
<q-btn
|
||||
unelevated
|
||||
round
|
||||
icon="mdi-file-eye-outline"
|
||||
color="grey-2"
|
||||
text-color="primary"
|
||||
size="md"
|
||||
>
|
||||
<q-tooltip>ดูข้อมูลการช่วยราชการ</q-tooltip>
|
||||
</q-btn>
|
||||
<q-btn
|
||||
unelevated
|
||||
round
|
||||
color="grey-2"
|
||||
text-color="blue-5"
|
||||
icon="mdi-file-eye-outline"
|
||||
size="md"
|
||||
>
|
||||
<q-tooltip>ดูข้อมูลการทดลองงาน</q-tooltip>
|
||||
</q-btn>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
||||
<div class="row items-center bg-toolbar col-12 q-pa-sm">
|
||||
<div class="col-12 q-py-xs" style="padding-left: 12%;">
|
||||
<div class="row no-wrap">
|
||||
<div class="col-2">
|
||||
<div class="column">
|
||||
<span class="text-grey-6">ตำแหน่งในสายงาน</span>
|
||||
<span class="text-weight-medium text-dark">{{
|
||||
formProfile.position
|
||||
}}</span>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-2">
|
||||
<div class="column">
|
||||
<span class="text-grey-6">ประเภท</span>
|
||||
<span class="text-weight-medium text-dark">{{
|
||||
formProfile.type
|
||||
}}</span>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-2">
|
||||
<div class="column">
|
||||
<span class="text-grey-6">ระดับชั้นงาน</span>
|
||||
<span class="text-weight-medium text-dark">{{
|
||||
formProfile.level
|
||||
}}</span>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-2">
|
||||
<div class="column">
|
||||
<span class="text-grey-6">สถานะการประเมิน</span>
|
||||
<span class="text-weight-medium text-dark">{{
|
||||
formProfile.status
|
||||
}}</span>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-2">
|
||||
<div class="column">
|
||||
<span class="text-grey-6">คะแนนประเมิน</span>
|
||||
<span class="text-weight-medium text-primary">{{
|
||||
formProfile.score
|
||||
}}</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</q-card>
|
||||
|
||||
<q-card class="q-mt-md rounded">
|
||||
<TabMain />
|
||||
</q-card>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
<style>
|
||||
.bg-toolbar{
|
||||
background-color: #F2FBFA;
|
||||
}
|
||||
|
||||
</style>
|
||||
245
src/modules/08_KPI/views/main.vue
Normal file
245
src/modules/08_KPI/views/main.vue
Normal file
|
|
@ -0,0 +1,245 @@
|
|||
<script setup lang="ts">
|
||||
import { ref, onMounted } from "vue";
|
||||
import { useRouter } from "vue-router";
|
||||
|
||||
import type { DataOptions } from "@/modules/08_KPI/interface/index/Main";
|
||||
import type { QTableProps } from "quasar";
|
||||
|
||||
import { useCounterMixin } from "@/stores/mixin";
|
||||
|
||||
const mixin = useCounterMixin()
|
||||
const { date2Thai } = mixin
|
||||
const router = useRouter();
|
||||
|
||||
const filterKeyword = ref<string>("");
|
||||
|
||||
const rows = ref<any>();
|
||||
|
||||
const round = ref<string>("ID1");
|
||||
const roundOp = ref<DataOptions[]>([
|
||||
{
|
||||
id: "ID1",
|
||||
name: "รอบเมษา",
|
||||
},
|
||||
]);
|
||||
|
||||
const visibleColumns = ref<string[]>(["createDate", "status", "result"]);
|
||||
|
||||
const columns = ref<QTableProps["columns"]>([
|
||||
{
|
||||
name: "createDate",
|
||||
align: "left",
|
||||
label: "วันที่สร้างแบบประเมิน",
|
||||
sortable: true,
|
||||
field: "createDate",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
{
|
||||
name: "status",
|
||||
align: "left",
|
||||
label: "สถานะการประเมิน",
|
||||
sortable: true,
|
||||
field: "status",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
{
|
||||
name: "result",
|
||||
align: "left",
|
||||
label: "ผลการประเมิน",
|
||||
sortable: true,
|
||||
field: "result",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
]);
|
||||
|
||||
/** ดึงข้อมูล */
|
||||
function getData() {
|
||||
const data = [
|
||||
{
|
||||
id: "ID1",
|
||||
createDate: '2024-02-16T06:01:00.000Z',
|
||||
status: "รอดำเนินการ",
|
||||
result: "ผ่านเกณฑ์การประเมิน",
|
||||
},
|
||||
{
|
||||
id: "ID1",
|
||||
createDate: '2024-02-16T06:01:00.000Z',
|
||||
status: "รอดำเนินการ",
|
||||
result: "ผ่านเกณฑ์การประเมิน",
|
||||
},
|
||||
];
|
||||
rows.value = data;
|
||||
// showLoader();
|
||||
// await http
|
||||
// .get(config.API.orgPrefix)
|
||||
// .then(async (res) => {
|
||||
// })
|
||||
// .catch((err) => {
|
||||
// messageError($q, err);
|
||||
// })
|
||||
// .finally(() => {
|
||||
// hideLoader();
|
||||
// });
|
||||
}
|
||||
|
||||
function onEdit(id:string){
|
||||
router.push(`/KPI/${id}`)
|
||||
}
|
||||
onMounted(async () => {
|
||||
getData();
|
||||
});
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div class="col-12 row justify-center">
|
||||
<div class="col-xs-12 col-sm-12 col-md-11">
|
||||
<div class="toptitle text-white col-12 row items-center">
|
||||
<q-btn
|
||||
icon="mdi-arrow-left"
|
||||
unelevated
|
||||
round
|
||||
dense
|
||||
flat
|
||||
color="primary"
|
||||
class="q-mr-sm"
|
||||
@click="router.push(`/`)"
|
||||
/>
|
||||
รายการขอรับประเมินผลการปฏิบัติราชการระดับบุคคล
|
||||
</div>
|
||||
<div class="col-12">
|
||||
<q-card bordered class="q-pa-md">
|
||||
<q-toolbar style="padding: 0">
|
||||
<q-select
|
||||
v-model="round"
|
||||
outlined
|
||||
label="รอบการประเมิน"
|
||||
dense
|
||||
option-label="name"
|
||||
option-value="id"
|
||||
:options="roundOp"
|
||||
style="min-width: 200px"
|
||||
emit-value
|
||||
map-options
|
||||
/>
|
||||
<q-btn class="q-ml-sm" flat round color="primary" icon="add" @click="router.push(`/KPI/add`)">
|
||||
<q-tooltip> เพิ่มข้อมูล </q-tooltip>
|
||||
</q-btn>
|
||||
<q-space />
|
||||
<div class="row q-gutter-sm">
|
||||
<q-input
|
||||
outlined
|
||||
dense
|
||||
v-model="filterKeyword"
|
||||
label="ค้นหา"
|
||||
></q-input>
|
||||
<q-select
|
||||
v-model="visibleColumns"
|
||||
multiple
|
||||
outlined
|
||||
dense
|
||||
options-dense
|
||||
:display-value="$q.lang.table.columns"
|
||||
emit-value
|
||||
map-options
|
||||
:options="columns"
|
||||
option-value="name"
|
||||
options-cover
|
||||
style="min-width: 150px"
|
||||
/>
|
||||
</div>
|
||||
</q-toolbar>
|
||||
|
||||
<q-table
|
||||
ref="table"
|
||||
:columns="columns"
|
||||
:rows="rows"
|
||||
:filter="filterKeyword"
|
||||
row-key="id"
|
||||
flat
|
||||
bordered
|
||||
:paging="true"
|
||||
dense
|
||||
class="custom-table2"
|
||||
:visible-columns="visibleColumns"
|
||||
>
|
||||
<template v-slot:header="props">
|
||||
<q-tr :props="props">
|
||||
<q-th v-for="col in props.cols" :key="col.name" :props="props" >
|
||||
<span class="text-weight-medium">{{ col.label }}</span>
|
||||
</q-th>
|
||||
<q-th auto-width />
|
||||
</q-tr>
|
||||
</template>
|
||||
<template v-slot:body="props">
|
||||
<q-tr :props="props" class="cursor-pointer">
|
||||
<q-td v-for="col in props.cols" :key="col.id" @click="onEdit(props.row.id)">
|
||||
<div v-if="col.name == 'createDate'">
|
||||
{{ col.value ? date2Thai(col.value):'-' }}
|
||||
</div>
|
||||
<div v-else>
|
||||
{{ col.value }}
|
||||
</div>
|
||||
</q-td>
|
||||
</q-tr>
|
||||
</template>
|
||||
</q-table>
|
||||
</q-card>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
<style scoped lang="scss">
|
||||
.icon-color {
|
||||
color: #4154b3;
|
||||
}
|
||||
|
||||
.custom-table2 {
|
||||
max-height: 64vh;
|
||||
|
||||
.q-table tr:nth-child(odd) td {
|
||||
background: white;
|
||||
}
|
||||
|
||||
.q-table tr:nth-child(even) td {
|
||||
background: #f8f8f8;
|
||||
}
|
||||
|
||||
.q-table thead tr {
|
||||
background: #ecebeb;
|
||||
}
|
||||
|
||||
.q-table thead tr th {
|
||||
position: sticky;
|
||||
}
|
||||
|
||||
.q-table td:nth-of-type(2) {
|
||||
z-index: 3 !important;
|
||||
}
|
||||
|
||||
.q-table th:nth-of-type(2),
|
||||
.q-table td:nth-of-type(2) {
|
||||
position: sticky;
|
||||
left: 0;
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
/* this will be the loading indicator */
|
||||
.q-table thead tr:last-child th {
|
||||
/* height of all previous header rows */
|
||||
top: 48px;
|
||||
}
|
||||
|
||||
.q-table thead tr:first-child th {
|
||||
top: 0;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
255
src/modules/08_KPI/views/mainEvaluator.vue
Normal file
255
src/modules/08_KPI/views/mainEvaluator.vue
Normal file
|
|
@ -0,0 +1,255 @@
|
|||
<script setup lang="ts">
|
||||
import { ref, onMounted } from "vue";
|
||||
import { useRouter } from "vue-router";
|
||||
|
||||
import type { DataOptions } from "@/modules/08_KPI/interface/index/Main";
|
||||
import type { QTableProps } from "quasar";
|
||||
|
||||
import { useCounterMixin } from "@/stores/mixin";
|
||||
|
||||
const mixin = useCounterMixin()
|
||||
const { date2Thai } = mixin
|
||||
const router = useRouter();
|
||||
|
||||
const filterKeyword = ref<string>("");
|
||||
|
||||
const rows = ref<any>();
|
||||
|
||||
const round = ref<string>("ID1");
|
||||
const roundOp = ref<DataOptions[]>([
|
||||
{
|
||||
id: "ID1",
|
||||
name: "รอบเมษา",
|
||||
},
|
||||
]);
|
||||
|
||||
const visibleColumns = ref<string[]>(["name", "createDate", "status", "result"]);
|
||||
|
||||
const columns = ref<QTableProps["columns"]>([
|
||||
{
|
||||
name: "name",
|
||||
align: "left",
|
||||
label: "ผู้ขอรับการประเมิน",
|
||||
sortable: true,
|
||||
field: "name",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
{
|
||||
name: "createDate",
|
||||
align: "left",
|
||||
label: "วันที่สร้างแบบประเมิน",
|
||||
sortable: true,
|
||||
field: "createDate",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
{
|
||||
name: "status",
|
||||
align: "left",
|
||||
label: "สถานะการประเมิน",
|
||||
sortable: true,
|
||||
field: "status",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
{
|
||||
name: "result",
|
||||
align: "left",
|
||||
label: "ผลการประเมิน",
|
||||
sortable: true,
|
||||
field: "result",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
sort: (a: string, b: string) =>
|
||||
a.localeCompare(b, undefined, { numeric: true, sensitivity: "base" }),
|
||||
},
|
||||
]);
|
||||
|
||||
/** ดึงข้อมูล */
|
||||
function getData() {
|
||||
const data = [
|
||||
{
|
||||
id: "ID1",
|
||||
name: "สมศรี ใจดี",
|
||||
createDate: '2024-02-16T06:01:00.000Z',
|
||||
status: "รอดำเนินการ",
|
||||
result: "ผ่านเกณฑ์การประเมิน",
|
||||
},
|
||||
{
|
||||
id: "ID1",
|
||||
name: "สมจิตร ใจดี",
|
||||
createDate: '2024-02-16T06:01:00.000Z',
|
||||
status: "รอดำเนินการ",
|
||||
result: "ผ่านเกณฑ์การประเมิน",
|
||||
},
|
||||
];
|
||||
rows.value = data;
|
||||
// showLoader();
|
||||
// await http
|
||||
// .get(config.API.orgPrefix)
|
||||
// .then(async (res) => {
|
||||
// })
|
||||
// .catch((err) => {
|
||||
// messageError($q, err);
|
||||
// })
|
||||
// .finally(() => {
|
||||
// hideLoader();
|
||||
// });
|
||||
}
|
||||
|
||||
function onEdit(id:string){
|
||||
router.push(`/KPI-evaluator/${id}`)
|
||||
}
|
||||
onMounted(async () => {
|
||||
getData();
|
||||
});
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div class="col-12 row justify-center">
|
||||
<div class="col-xs-12 col-sm-12 col-md-11">
|
||||
<div class="toptitle text-white col-12 row items-center">
|
||||
<q-btn
|
||||
icon="mdi-arrow-left"
|
||||
unelevated
|
||||
round
|
||||
dense
|
||||
flat
|
||||
color="primary"
|
||||
class="q-mr-sm"
|
||||
@click="router.push(`/`)"
|
||||
/>
|
||||
รายการการประเมินผลการปฏิบัติราชการระดับบุคคล
|
||||
</div>
|
||||
<div class="col-12">
|
||||
<q-card bordered class="q-pa-md">
|
||||
<q-toolbar style="padding: 0">
|
||||
<q-select
|
||||
v-model="round"
|
||||
outlined
|
||||
label="รอบการประเมิน"
|
||||
dense
|
||||
option-label="name"
|
||||
option-value="id"
|
||||
:options="roundOp"
|
||||
style="min-width: 200px"
|
||||
emit-value
|
||||
map-options
|
||||
/>
|
||||
<q-space />
|
||||
<div class="row q-gutter-sm">
|
||||
<q-input
|
||||
outlined
|
||||
dense
|
||||
v-model="filterKeyword"
|
||||
label="ค้นหา"
|
||||
></q-input>
|
||||
<q-select
|
||||
v-model="visibleColumns"
|
||||
multiple
|
||||
outlined
|
||||
dense
|
||||
options-dense
|
||||
:display-value="$q.lang.table.columns"
|
||||
emit-value
|
||||
map-options
|
||||
:options="columns"
|
||||
option-value="name"
|
||||
options-cover
|
||||
style="min-width: 150px"
|
||||
/>
|
||||
</div>
|
||||
</q-toolbar>
|
||||
|
||||
<q-table
|
||||
ref="table"
|
||||
:columns="columns"
|
||||
:rows="rows"
|
||||
:filter="filterKeyword"
|
||||
row-key="id"
|
||||
flat
|
||||
bordered
|
||||
:paging="true"
|
||||
dense
|
||||
class="custom-table2"
|
||||
:visible-columns="visibleColumns"
|
||||
>
|
||||
<template v-slot:header="props">
|
||||
<q-tr :props="props">
|
||||
<q-th v-for="col in props.cols" :key="col.name" :props="props" >
|
||||
<span class="text-weight-medium">{{ col.label }}</span>
|
||||
</q-th>
|
||||
<q-th auto-width />
|
||||
</q-tr>
|
||||
</template>
|
||||
<template v-slot:body="props">
|
||||
<q-tr :props="props" class="cursor-pointer">
|
||||
<q-td v-for="col in props.cols" :key="col.id" @click="onEdit(props.row.id)">
|
||||
<div v-if="col.name == 'createDate'">
|
||||
{{ col.value ? date2Thai(col.value):'-' }}
|
||||
</div>
|
||||
<div v-else>
|
||||
{{ col.value }}
|
||||
</div>
|
||||
</q-td>
|
||||
</q-tr>
|
||||
</template>
|
||||
</q-table>
|
||||
</q-card>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
<style scoped lang="scss">
|
||||
.icon-color {
|
||||
color: #4154b3;
|
||||
}
|
||||
|
||||
.custom-table2 {
|
||||
max-height: 64vh;
|
||||
|
||||
.q-table tr:nth-child(odd) td {
|
||||
background: white;
|
||||
}
|
||||
|
||||
.q-table tr:nth-child(even) td {
|
||||
background: #f8f8f8;
|
||||
}
|
||||
|
||||
.q-table thead tr {
|
||||
background: #ecebeb;
|
||||
}
|
||||
|
||||
.q-table thead tr th {
|
||||
position: sticky;
|
||||
}
|
||||
|
||||
.q-table td:nth-of-type(2) {
|
||||
z-index: 3 !important;
|
||||
}
|
||||
|
||||
.q-table th:nth-of-type(2),
|
||||
.q-table td:nth-of-type(2) {
|
||||
position: sticky;
|
||||
left: 0;
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
/* this will be the loading indicator */
|
||||
.q-table thead tr:last-child th {
|
||||
/* height of all previous header rows */
|
||||
top: 48px;
|
||||
}
|
||||
|
||||
.q-table thead tr:first-child th {
|
||||
top: 0;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
327
src/modules/09_scholarship/components/Dialog/DialogReturn.vue
Normal file
327
src/modules/09_scholarship/components/Dialog/DialogReturn.vue
Normal file
|
|
@ -0,0 +1,327 @@
|
|||
<script setup lang="ts">
|
||||
import { ref, watch } from "vue";
|
||||
import DialogHeader from "@/components/DialogHeader.vue";
|
||||
|
||||
import { useCounterMixin } from "@/stores/mixin";
|
||||
import { useQuasar } from "quasar";
|
||||
import http from "@/plugins/http";
|
||||
import config from "@/app.config";
|
||||
import { useRoute } from "vue-router";
|
||||
|
||||
const route = useRoute();
|
||||
const id = ref<string>(route.params.id.toLocaleString());
|
||||
const $q = useQuasar();
|
||||
const mixin = useCounterMixin();
|
||||
const {
|
||||
date2Thai,
|
||||
dialogMessageNotify,
|
||||
showLoader,
|
||||
hideLoader,
|
||||
messageError,
|
||||
dialogConfirm,
|
||||
success,
|
||||
} = mixin;
|
||||
const modal = defineModel<boolean>("modal", { required: true });
|
||||
|
||||
const governmentDate = ref<any>(null);
|
||||
const graduatedDate = ref<any>(null);
|
||||
const isGraduated = ref<any>(null);
|
||||
const graduatedReason = ref<string>("");
|
||||
|
||||
const bookNumber = ref<string>("");
|
||||
const bookDate = ref<any>(null);
|
||||
const governmentEndDate = ref<any>(null);
|
||||
|
||||
function close() {
|
||||
modal.value = false;
|
||||
|
||||
bookNumber.value = "";
|
||||
bookDate.value = null;
|
||||
governmentDate.value = null;
|
||||
governmentEndDate.value = null;
|
||||
|
||||
isGraduated.value = null;
|
||||
graduatedDate.value = null;
|
||||
graduatedReason.value = "";
|
||||
}
|
||||
|
||||
function onSubmit() {
|
||||
if (isGraduated.value == null) {
|
||||
dialogMessageNotify($q, "กรุณาเลือกสำเร็จการศึกษาตามที่หลักสูตรกำหนด");
|
||||
} else {
|
||||
dialogConfirm($q, () => {
|
||||
showLoader();
|
||||
http
|
||||
.put(config.API.developmentScholarship + `/user/detail/${id.value}`, {
|
||||
bookNumber: bookNumber.value,
|
||||
bookDate: bookDate.value,
|
||||
governmentDate: governmentDate.value,
|
||||
governmentEndDate: governmentEndDate.value,
|
||||
isGraduated: isGraduated.value,
|
||||
graduatedDate: isGraduated.value == 'true' ? graduatedDate.value : null,
|
||||
graduatedReason: isGraduated.value == 'false' ? graduatedReason.value : null,
|
||||
})
|
||||
.then((res) => {
|
||||
success($q, "บันทึกสำเร็จ");
|
||||
close();
|
||||
})
|
||||
.catch((e) => {
|
||||
messageError($q, e);
|
||||
})
|
||||
.finally(() => {
|
||||
hideLoader();
|
||||
});
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
watch(
|
||||
() => modal.value,
|
||||
() => {
|
||||
if (modal.value == true) {
|
||||
showLoader();
|
||||
http
|
||||
.get(config.API.developmentScholarship + `/user/detail/${id.value}`)
|
||||
.then((res) => {
|
||||
const data = res.data.result;
|
||||
bookNumber.value = data.bookNumber;
|
||||
bookDate.value = data.bookDate;
|
||||
governmentDate.value = data.governmentDate;
|
||||
governmentEndDate.value = data.governmentEndDate;
|
||||
isGraduated.value = data.isGraduated.toLocaleString();
|
||||
graduatedDate.value = data.graduatedDate;
|
||||
graduatedReason.value = data.graduatedReason;
|
||||
})
|
||||
.catch((e) => {
|
||||
messageError($q, e);
|
||||
})
|
||||
.finally(() => {
|
||||
hideLoader();
|
||||
});
|
||||
}
|
||||
}
|
||||
);
|
||||
</script>
|
||||
<template>
|
||||
<q-dialog v-model="modal">
|
||||
<q-card flat style="min-width: 30vw">
|
||||
<q-form greedy @submit.prevent @validation-success="onSubmit">
|
||||
<DialogHeader tittle="รายงานตัวกลับเข้ารับราชการ" :close="close" />
|
||||
<q-separator />
|
||||
<q-card-section>
|
||||
<div class="row q-col-gutter-sm">
|
||||
<div class="col-6">
|
||||
<q-input
|
||||
label="เลขที่หนังสือรายงานตัวกลับเข้าปฏิบัติราชการ"
|
||||
v-model="bookNumber"
|
||||
outlined
|
||||
lazy-rules
|
||||
dense
|
||||
hide-bottom-space
|
||||
:rules="[
|
||||
(val:string) =>
|
||||
!!val || `${'กรุณากรอกเลขที่หนังสือรายงานตัวกลับเข้าปฏิบัติราชการ'}`,
|
||||
]"
|
||||
class="inputgreen"
|
||||
/>
|
||||
</div>
|
||||
<div class="col-6">
|
||||
<datepicker
|
||||
menu-class-name="modalfix"
|
||||
v-model="bookDate"
|
||||
:locale="'th'"
|
||||
autoApply
|
||||
:enableTimePicker="false"
|
||||
week-start="0"
|
||||
>
|
||||
<template #year="{ year }">{{ year + 543 }}</template>
|
||||
<template #year-overlay-value="{ value }">{{
|
||||
parseInt(value + 543)
|
||||
}}</template>
|
||||
<template #trigger>
|
||||
<q-input
|
||||
dense
|
||||
outlined
|
||||
:model-value="bookDate ? date2Thai(bookDate) : null"
|
||||
:label="`${'หนังสือรายงานตัวกลับเข้าปฏิบัติราชการลงวันที่'}`"
|
||||
hide-bottom-space
|
||||
class="inputgreen"
|
||||
:rules="[
|
||||
(val:string) =>
|
||||
!!val || `${'กรุณากรอกหนังสือรายงานตัวกลับเข้าปฏิบัติราชการลงวันที่'}`,
|
||||
]"
|
||||
>
|
||||
<template v-slot:prepend>
|
||||
<q-icon
|
||||
name="event"
|
||||
class="cursor-pointer"
|
||||
style="color: var(--q-primary)"
|
||||
>
|
||||
</q-icon>
|
||||
</template>
|
||||
</q-input>
|
||||
</template>
|
||||
</datepicker>
|
||||
</div>
|
||||
<div class="col-6">
|
||||
<datepicker
|
||||
menu-class-name="modalfix"
|
||||
v-model="governmentDate"
|
||||
:locale="'th'"
|
||||
autoApply
|
||||
:enableTimePicker="false"
|
||||
week-start="0"
|
||||
>
|
||||
<template #year="{ year }">{{ year + 543 }}</template>
|
||||
<template #year-overlay-value="{ value }">{{
|
||||
parseInt(value + 543)
|
||||
}}</template>
|
||||
<template #trigger>
|
||||
<q-input
|
||||
dense
|
||||
outlined
|
||||
:model-value="
|
||||
governmentDate ? date2Thai(governmentDate) : null
|
||||
"
|
||||
:label="`${'วันที่กลับเข้าปฏิบัติราชการ'}`"
|
||||
hide-bottom-space
|
||||
class="inputgreen"
|
||||
:rules="[
|
||||
(val:string) =>
|
||||
!!val || `${'กรุณากรอกวันที่กลับเข้าปฏิบัติราชการ'}`,
|
||||
]"
|
||||
>
|
||||
<template v-slot:prepend>
|
||||
<q-icon
|
||||
name="event"
|
||||
class="cursor-pointer"
|
||||
style="color: var(--q-primary)"
|
||||
>
|
||||
</q-icon>
|
||||
</template>
|
||||
</q-input>
|
||||
</template>
|
||||
</datepicker>
|
||||
</div>
|
||||
<div class="col-6">
|
||||
<datepicker
|
||||
menu-class-name="modalfix"
|
||||
v-model="governmentEndDate"
|
||||
:locale="'th'"
|
||||
autoApply
|
||||
:enableTimePicker="false"
|
||||
week-start="0"
|
||||
>
|
||||
<template #year="{ year }">{{ year + 543 }}</template>
|
||||
<template #year-overlay-value="{ value }">{{
|
||||
parseInt(value + 543)
|
||||
}}</template>
|
||||
<template #trigger>
|
||||
<q-input
|
||||
dense
|
||||
outlined
|
||||
:model-value="
|
||||
governmentEndDate ? date2Thai(governmentEndDate) : null
|
||||
"
|
||||
:label="`${' วันสิ้นสุดภาระผูกพัน'}`"
|
||||
hide-bottom-space
|
||||
class="inputgreen"
|
||||
:rules="[
|
||||
(val:string) =>
|
||||
!!val || `${'กรุณากรอก วันสิ้นสุดภาระผูกพัน'}`,
|
||||
]"
|
||||
>
|
||||
<template v-slot:prepend>
|
||||
<q-icon
|
||||
name="event"
|
||||
class="cursor-pointer"
|
||||
style="color: var(--q-primary)"
|
||||
>
|
||||
</q-icon>
|
||||
</template>
|
||||
</q-input>
|
||||
</template>
|
||||
</datepicker>
|
||||
</div>
|
||||
<q-radio
|
||||
v-model="isGraduated"
|
||||
checked-icon="task_alt"
|
||||
unchecked-icon="panorama_fish_eye"
|
||||
val="true"
|
||||
label="สำเร็จการศึกษาตามที่หลักสูตรกำหนด"
|
||||
/>
|
||||
|
||||
<q-radio
|
||||
v-model="isGraduated"
|
||||
checked-icon="task_alt"
|
||||
unchecked-icon="panorama_fish_eye"
|
||||
val="false"
|
||||
label="เสร็จสิ้นการศึกษาตามที่หลักสูตรกำหนดแล้วแต่ยังไม่สำเร็จการศึกษา"
|
||||
/>
|
||||
<div v-if="isGraduated == 'true'" class="col-12">
|
||||
<datepicker
|
||||
menu-class-name="modalfix"
|
||||
v-model="graduatedDate"
|
||||
:locale="'th'"
|
||||
autoApply
|
||||
:enableTimePicker="false"
|
||||
week-start="0"
|
||||
>
|
||||
<template #year="{ year }">{{ year + 543 }}</template>
|
||||
<template #year-overlay-value="{ value }">{{
|
||||
parseInt(value + 543)
|
||||
}}</template>
|
||||
<template #trigger>
|
||||
<q-input
|
||||
dense
|
||||
outlined
|
||||
:model-value="
|
||||
graduatedDate ? date2Thai(graduatedDate) : null
|
||||
"
|
||||
:label="`${'ตั้งแต่ (วันที่)'}`"
|
||||
hide-bottom-space
|
||||
class="inputgreen"
|
||||
:rules="[
|
||||
(val:string) =>
|
||||
!!val || `${'กรุณากรอกตั้งแต่ (วันที่)'}`,
|
||||
]"
|
||||
>
|
||||
<template v-slot:prepend>
|
||||
<q-icon
|
||||
name="event"
|
||||
class="cursor-pointer"
|
||||
style="color: var(--q-primary)"
|
||||
>
|
||||
</q-icon>
|
||||
</template>
|
||||
</q-input>
|
||||
</template>
|
||||
</datepicker>
|
||||
</div>
|
||||
<div v-if="isGraduated == 'false'" class="col-12">
|
||||
<q-input
|
||||
v-model="graduatedReason"
|
||||
type="textarea"
|
||||
dense
|
||||
outlined
|
||||
hide-bottom-space
|
||||
class="inputgreen"
|
||||
:rules="[
|
||||
(val:string) =>
|
||||
!!val || `${'กรุณากรอก เนื่องจาก'}`,
|
||||
]"
|
||||
label="เนื่องจาก"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</q-card-section>
|
||||
<q-separator />
|
||||
<q-card-actions align="right">
|
||||
<q-btn label="บันทึก" color="secondary" type="submit"
|
||||
><q-tooltip>บันทึกข้อมูล</q-tooltip></q-btn
|
||||
>
|
||||
</q-card-actions>
|
||||
</q-form>
|
||||
</q-card>
|
||||
</q-dialog>
|
||||
</template>
|
||||
8
src/modules/09_scholarship/interface/index/Main.ts
Normal file
8
src/modules/09_scholarship/interface/index/Main.ts
Normal file
|
|
@ -0,0 +1,8 @@
|
|||
interface DataOptions {
|
||||
id:string
|
||||
name:string
|
||||
}
|
||||
|
||||
export type {
|
||||
DataOptions
|
||||
}
|
||||
132
src/modules/09_scholarship/interface/request/index.ts
Normal file
132
src/modules/09_scholarship/interface/request/index.ts
Normal file
|
|
@ -0,0 +1,132 @@
|
|||
interface FormsSholarship {
|
||||
profileId: string;
|
||||
rank: string; //ยศ
|
||||
prefix: string; //คำนำหน้าชื่อ
|
||||
firstName: string; //ชื่อ
|
||||
lastName: string; //นามสกุล
|
||||
citizenId: string; //เลขประจำตัวประชาชน
|
||||
position: string; //ตำแหน่ง
|
||||
posExecutive: string; //ชื่อตำแหน่งทางการบริหาร
|
||||
posLevelId: string | null; //ไอดีระดับตำแหน่ง
|
||||
posTypeId: string | null; //ไอดีประเภทตำแหน่ง
|
||||
org: string;
|
||||
rootId: string | null;
|
||||
root: string;
|
||||
orgRootShortName: string;
|
||||
orgRevisionId: string | null;
|
||||
guarantorRank: string; //ยศ(ผู้ค้ำ)
|
||||
guarantorPrefix: string; //คำนำหน้าชื่อ(ผู้ค้ำ)
|
||||
guarantorFirstName: string; //ชื่อ(ผู้ค้ำ)
|
||||
guarantorLastName: string; //นามสกุล(ผู้ค้ำ)
|
||||
guarantorCitizenId: string; //เลขประจำตัวประชาชน(ผู้ค้ำ)
|
||||
guarantorPosition: string; //ตำแหน่ง(ผู้ค้ำ)
|
||||
guarantorPosExecutive: string; //ชื่อตำแหน่งทางการบริหาร(ผู้ค้ำ)
|
||||
guarantorOrg: string;
|
||||
guarantorRootId: string | null;
|
||||
guarantorRoot: string;
|
||||
guarantorOrgRootShortName: string;
|
||||
guarantorOrgRevisionId: string | null;
|
||||
posLevelguarantorId: string | null; //ไอดีระดับตำแหน่ง(ผู้ค้ำ)
|
||||
posTypeguarantorId: string | null; //ไอดีประเภทตำแหน่ง(ผู้ค้ำ)
|
||||
scholarshipYear: number | null; //ปีงบประมาณที่ได้รับทุน
|
||||
budgetSource: string; //แหล่งงบประมาณ
|
||||
budgetApprove: number | string | null; //งบประมาณที่ได้รับอนุมัติตลอดหลักสูตร
|
||||
bookNo: string; //เลขที่หนังสืออนุมัติ
|
||||
bookNoDate: Date | null; //ลงวันที่(หนังสือ)
|
||||
bookApproveDate: Date | null; //หนังสืออนุมัติเมื่อวันที่
|
||||
useOfficialTime: boolean; //ใช้เวลาราชการ
|
||||
changeDetail: string; //เปลี่ยนแปลงรายละเอียด
|
||||
scholarshipType: string; //เลือกประเภททุน
|
||||
fundType: string; //ประเภททุน
|
||||
contractNo: string; //เลขที่สัญญา
|
||||
contractDate: Date | null; //ลงวันที่(เลขที่สัญญา)
|
||||
reportBackNo: string; //เลขที่หนังสือรายงานตัวกลับ
|
||||
reportBackNoDate: Date | null; //ลงวันที่(เลขที่หนังสือรายงานตัวกลับ)
|
||||
reportBackDate: Date | null; //รายงานตัวกลับวันที่
|
||||
degreeLevel: string; //ระดับปริญญา
|
||||
course: string; //หลักสูตรการศึกษา/หลักสูตรการฝึกอบรม
|
||||
field: string; //สาขาวิชา/สาขา
|
||||
faculty: string; //คณะ
|
||||
educationalInstitution: string; //สถาบันการศึกษา/สถาบันการศึกษา_หน่วยงานผู้จัดการฝึกอบรม/สถานที่ไปศึกษาดูงานในประเทศ
|
||||
startDate: Date | null; //วันเริ่มต้นการศึกษา/วันเริ่มต้นการฝึกอบรม/วันเริ่มต้นการศึกษาดูงานในประเทศ
|
||||
endDate: Date | null; //วันสิ้นสุดการศึกษา/วันสิ้นสุดการฝึกอบรม/วันสิ้นสุดการศึกษาดูงานในประเทศ
|
||||
studyPlace: string; //สถานที่ไปศึกษาดูงาน
|
||||
studyTopic: string; //หัวข้อการไปศึกษาดูงาน/หัวข้อการไปศึกษาดูงานในประเทศ
|
||||
studyStartDate: Date | null; //วันเริ่มต้นการศึกษาดูงาน
|
||||
studyEndDate: Date | null; //วันสิ้นสุดการศึกษาดูงาน
|
||||
studyCountry: string; //ประเทศที่เดินทางไปศึกษาดูงาน
|
||||
studyAbroadTopic: string; //หัวข้อการไปศึกษาดูงานต่างประเทศ
|
||||
studyAbroadStartDate: Date | null; //วันเริ่มต้นการศึกษาดูงานต่างประเทศ
|
||||
studyAbroadEndDate: Date | null; //วันสิ้นสุดการศึกษาดูงานต่างประเทศ
|
||||
totalPeriod: string; //รวมระยะเวลาในการศึกษา/รวมระยะเวลาในการฝึกอบรม
|
||||
planType: string; // INPLAN ในแผนฯ, OUTPLAN นอกแผนฯ
|
||||
isNoUseBudget: boolean; //
|
||||
}
|
||||
|
||||
interface DataSholarship {
|
||||
rank: string; //ยศ
|
||||
prefix: string; //คำนำหน้าชื่อ
|
||||
firstName: string; //ชื่อ
|
||||
lastName: string; //นามสกุล
|
||||
citizenId: string; //เลขประจำตัวประชาชน
|
||||
position: string; //ตำแหน่ง
|
||||
posExecutive: string; //ชื่อตำแหน่งทางการบริหาร
|
||||
posLevelId: string; //ไอดีระดับตำแหน่ง
|
||||
posTypeId: string; //ไอดีประเภทตำแหน่ง
|
||||
posTypeName: string; //ไอดีระดับตำแหน่ง
|
||||
posLevelName: string; //ไอดีประเภทตำแหน่ง
|
||||
org: string;
|
||||
guarantorRank: string; //ยศ(ผู้ค้ำ)
|
||||
guarantorPrefix: string; //คำนำหน้าชื่อ(ผู้ค้ำ)
|
||||
guarantorFirstName: string; //ชื่อ(ผู้ค้ำ)
|
||||
guarantorLastName: string; //นามสกุล(ผู้ค้ำ)
|
||||
guarantorCitizenId: string; //เลขประจำตัวประชาชน(ผู้ค้ำ)
|
||||
guarantorPosition: string; //ตำแหน่ง(ผู้ค้ำ)
|
||||
guarantorPosExecutive: string; //ชื่อตำแหน่งทางการบริหาร(ผู้ค้ำ)
|
||||
guarantorOrg: string;
|
||||
guarantorRootId: string | null;
|
||||
guarantorRoot: string;
|
||||
guarantorOrgRootShortName: string;
|
||||
guarantorOrgRevisionId: string | null;
|
||||
posLevelguarantorId: string; //ไอดีระดับตำแหน่ง(ผู้ค้ำ)
|
||||
posTypeguarantorId: string; //ไอดีประเภทตำแหน่ง(ผู้ค้ำ)
|
||||
posTypeguarantorName: string; //ไอดีระดับตำแหน่ง(ผู้ค้ำ)
|
||||
posLevelguarantorName: string; //ไอดีประเภทตำแหน่ง(ผู้ค้ำ)
|
||||
scholarshipYear: number | null; //ปีงบประมาณที่ได้รับทุน
|
||||
budgetSource: string; //แหล่งงบประมาณ
|
||||
budgetApprove: number | null; //งบประมาณที่ได้รับอนุมัติตลอดหลักสูตร
|
||||
bookNo: string; //เลขที่หนังสืออนุมัติ
|
||||
bookNoDate: Date | null; //ลงวันที่(หนังสือ)
|
||||
bookApproveDate: Date | null; //หนังสืออนุมัติเมื่อวันที่
|
||||
useOfficialTime: boolean; //ใช้เวลาราชการ
|
||||
changeDetail: string; //เปลี่ยนแปลงรายละเอียด
|
||||
scholarshipType: string; //เลือกประเภททุน
|
||||
fundType: string; //ประเภททุน
|
||||
contractNo: string; //เลขที่สัญญา
|
||||
contractDate: Date | null; //ลงวันที่(เลขที่สัญญา)
|
||||
reportBackNo: string; //เลขที่หนังสือรายงานตัวกลับ
|
||||
reportBackNoDate: Date | null; //ลงวันที่(เลขที่หนังสือรายงานตัวกลับ)
|
||||
reportBackDate: Date | null; //รายงานตัวกลับวันที่
|
||||
degreeLevel: string; //ระดับปริญญา
|
||||
course: string; //หลักสูตรการศึกษา/หลักสูตรการฝึกอบรม
|
||||
field: string; //สาขาวิชา/สาขา
|
||||
faculty: string; //คณะ
|
||||
educationalInstitution: string; //สถาบันการศึกษา/สถาบันการศึกษา_หน่วยงานผู้จัดการฝึกอบรม/สถานที่ไปศึกษาดูงานในประเทศ
|
||||
startDate: Date | null; //วันเริ่มต้นการศึกษา/วันเริ่มต้นการฝึกอบรม/วันเริ่มต้นการศึกษาดูงานในประเทศ
|
||||
endDate: Date | null; //วันสิ้นสุดการศึกษา/วันสิ้นสุดการฝึกอบรม/วันสิ้นสุดการศึกษาดูงานในประเทศ
|
||||
studyPlace: string; //สถานที่ไปศึกษาดูงาน
|
||||
studyTopic: string; //หัวข้อการไปศึกษาดูงาน/หัวข้อการไปศึกษาดูงานในประเทศ
|
||||
studyStartDate: Date | null; //วันเริ่มต้นการศึกษาดูงาน
|
||||
studyEndDate: Date | null; //วันสิ้นสุดการศึกษาดูงาน
|
||||
studyCountry: string; //ประเทศที่เดินทางไปศึกษาดูงาน
|
||||
studyAbroadTopic: string; //หัวข้อการไปศึกษาดูงานต่างประเทศ
|
||||
studyAbroadStartDate: Date | null; //วันเริ่มต้นการศึกษาดูงานต่างประเทศ
|
||||
studyAbroadEndDate: Date | null; //วันสิ้นสุดการศึกษาดูงานต่างประเทศ
|
||||
totalPeriod: string; //รวมระยะเวลาในการศึกษา/รวมระยะเวลาในการฝึกอบรม
|
||||
status: string;
|
||||
planType: string; // INPLAN ในแผนฯ, OUTPLAN นอกแผนฯ
|
||||
isNoUseBudget: boolean; // ไม่ใช้งบประมาณ
|
||||
}
|
||||
|
||||
export type { FormsSholarship,DataSholarship };
|
||||
|
||||
26
src/modules/09_scholarship/router.ts
Normal file
26
src/modules/09_scholarship/router.ts
Normal file
|
|
@ -0,0 +1,26 @@
|
|||
/**
|
||||
* Router ขอโอน
|
||||
*/
|
||||
|
||||
const scholarshipPage = () => import("@/modules/09_scholarship/views/main.vue");
|
||||
const scholarshipDetail = () => import('@/modules/09_scholarship/views/detail.vue')
|
||||
export default [
|
||||
{
|
||||
path: "/scholarship",
|
||||
name: "scholarshipMain",
|
||||
component: scholarshipPage,
|
||||
meta: {
|
||||
Auth: true,
|
||||
Key: [9],
|
||||
},
|
||||
},
|
||||
{
|
||||
path: "/scholarship/:id",
|
||||
name: "scholarshipDetail",
|
||||
component: scholarshipDetail,
|
||||
meta: {
|
||||
Auth: true,
|
||||
Key: [9],
|
||||
},
|
||||
},
|
||||
];
|
||||
2508
src/modules/09_scholarship/views/detail.vue
Normal file
2508
src/modules/09_scholarship/views/detail.vue
Normal file
File diff suppressed because it is too large
Load diff
363
src/modules/09_scholarship/views/main.vue
Normal file
363
src/modules/09_scholarship/views/main.vue
Normal file
|
|
@ -0,0 +1,363 @@
|
|||
<script setup lang="ts">
|
||||
import { ref, onMounted, watch } from "vue";
|
||||
import { useRouter } from "vue-router";
|
||||
import { useQuasar, type QTableProps } from "quasar";
|
||||
|
||||
import { useCounterMixin } from "@/stores/mixin";
|
||||
|
||||
import type { DataOptions } from "@/modules/09_scholarship/interface/index/Main";
|
||||
|
||||
import http from "@/plugins/http";
|
||||
import config from "@/app.config";
|
||||
const mixin = useCounterMixin();
|
||||
const { date2Thai, showLoader, hideLoader, messageError } = mixin;
|
||||
const router = useRouter();
|
||||
|
||||
const $q = useQuasar();
|
||||
const filterKeyword = ref<string>("");
|
||||
|
||||
const profilId = ref<string>("");
|
||||
const currentPage = ref<number>(1);
|
||||
const maxPage = ref<number>(1);
|
||||
const page = ref<number>(1);
|
||||
const rowsPerPage = ref<number>(10);
|
||||
|
||||
const rows = ref<any>();
|
||||
const year = ref<number>(0);
|
||||
const type = ref<string>("DOMESTICE");
|
||||
const scholarshipTypeOp = ref<DataOptions[]>([
|
||||
{ id: "DOMESTICE", name: "การศึกษาในประเทศ" },
|
||||
{
|
||||
id: "NOABROAD",
|
||||
name: "ฝึกอบรมในประเทศที่ส่งไปพัฒนากับหน่วยงานภายนอก (หลักสูตรที่ไม่มีการไปต่างประเทศ)",
|
||||
},
|
||||
{
|
||||
id: "ABROAD",
|
||||
name: "ฝึกอบรมในประเทศที่ส่งไปพัฒนากับหน่วยงานภายนอก (หลักสูตรที่มีการไปต่างประเทศ)",
|
||||
},
|
||||
{
|
||||
id: "EXECUTIVE",
|
||||
name: " ฝึกอบรมในประเทศที่ส่งไปพัฒนากับหน่วยงานภายนอก (หลักสูตรประเภทนักบริหาร)",
|
||||
},
|
||||
{
|
||||
id: "RESEARCH",
|
||||
name: "ศึกษา ฝึกอบรม ประชุม ดูงาน และปฏิบัติการวิจัย ณ ต่างประเทศ",
|
||||
},
|
||||
]);
|
||||
|
||||
/**
|
||||
* ตั้งค่า pagination
|
||||
*/
|
||||
const pagination = ref({
|
||||
sortBy: "lastUpdatedAt",
|
||||
descending: true,
|
||||
page: page.value,
|
||||
rowsPerPage: rowsPerPage.value,
|
||||
});
|
||||
|
||||
const columns = ref<QTableProps["columns"]>([
|
||||
{
|
||||
name: "scholarshipYear",
|
||||
align: "left",
|
||||
label: "ปีงบประมาณที่ได้รับทุน ",
|
||||
sortable: true,
|
||||
field: "scholarshipYear",
|
||||
headerStyle: "font-size: 14px ;width:20%",
|
||||
style: "font-size: 14px",
|
||||
},
|
||||
{
|
||||
name: "scholarshipType",
|
||||
align: "left",
|
||||
label: "ประเภททุน",
|
||||
sortable: true,
|
||||
field: "scholarshipType",
|
||||
headerStyle: "font-size: 14px",
|
||||
style: "font-size: 14px",
|
||||
},
|
||||
]);
|
||||
const visibleColumns = ref<string[]>(["scholarshipYear", "scholarshipType"]);
|
||||
|
||||
/** ดึงข้อมูล */
|
||||
function getData() {
|
||||
http
|
||||
.get(config.API.developmentScholarship + `/user/${profilId.value}?year=${year.value}&type=${type.value}`)
|
||||
.then((res) => {
|
||||
rows.value = res.data.result;
|
||||
})
|
||||
.catch((e) => {
|
||||
messageError($q, e);
|
||||
})
|
||||
.finally(() => {});
|
||||
}
|
||||
|
||||
function onEdit(id: string) {
|
||||
router.push(`/scholarship/${id}`);
|
||||
}
|
||||
|
||||
watch(
|
||||
() => currentPage.value,
|
||||
() => {
|
||||
rowsPerPage.value = pagination.value.rowsPerPage;
|
||||
getData();
|
||||
}
|
||||
);
|
||||
|
||||
watch(
|
||||
() => pagination.value.rowsPerPage,
|
||||
() => {
|
||||
rowsPerPage.value = pagination.value.rowsPerPage;
|
||||
currentPage.value = 1;
|
||||
getData();
|
||||
}
|
||||
);
|
||||
|
||||
function getProfileId() {
|
||||
showLoader();
|
||||
http
|
||||
.get(config.API.profilePosition())
|
||||
.then((res) => {
|
||||
profilId.value = res.data.result.profileId;
|
||||
getData();
|
||||
})
|
||||
.catch((e) => {
|
||||
messageError($q, e);
|
||||
})
|
||||
.finally(() => {
|
||||
hideLoader();
|
||||
});
|
||||
}
|
||||
|
||||
function convertType(val: string) {
|
||||
switch (val) {
|
||||
case "DOMESTICE":
|
||||
return "การศึกษาในประเทศ";
|
||||
case "NOABROAD":
|
||||
return "ฝึกอบรมในประเทศที่ส่งไปพัฒนากับหน่วยวงานภายนอก (หลักสูตรที่ไม่มีการไปต่างประเทศ)";
|
||||
case "ABROAD":
|
||||
return "ฝึกอบรมในประเทศที่ส่งไปพัฒนากับหน่วยวงานภายนอก (หลักสูตรที่มีการไปต่างประเทศ)";
|
||||
case "EXECUTIVE":
|
||||
return "ฝึกอบรมในประเทศที่ส่งไปพัฒนากับหน่วยวงานภายนอก (หลักสูตรประเภทนักบริหาร)";
|
||||
case "RESEARCH":
|
||||
return "ศึกษา ฝึกอบรม ประชุม ดูงาน และปฏิบัติการวิจัย ณ ต่างประเทศ";
|
||||
}
|
||||
}
|
||||
|
||||
onMounted(async () => {
|
||||
getProfileId();
|
||||
});
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div class="col-12 row justify-center">
|
||||
<div class="col-xs-12 col-sm-12 col-md-11">
|
||||
<div class="toptitle text-white col-12 row items-center">
|
||||
<q-btn
|
||||
icon="mdi-arrow-left"
|
||||
unelevated
|
||||
round
|
||||
dense
|
||||
flat
|
||||
color="primary"
|
||||
class="q-mr-sm"
|
||||
@click="router.push(`/`)"
|
||||
/>
|
||||
รายการทุนการศึกษา/ฝึกอบรม
|
||||
</div>
|
||||
<div class="col-12">
|
||||
<q-card bordered class="q-pa-md">
|
||||
<q-toolbar style="padding: 0">
|
||||
<div class="row q-gutter-sm">
|
||||
<datepicker
|
||||
style="width: 150px"
|
||||
menu-class-name="modalfix"
|
||||
v-model="year"
|
||||
:locale="'th'"
|
||||
autoApply
|
||||
year-picker
|
||||
:enableTimePicker="false"
|
||||
@update:model-value="getData()"
|
||||
>
|
||||
<template #year="{ year }">{{ year + 543 }}</template>
|
||||
<template #year-overlay-value="{ value }">{{
|
||||
parseInt(value + 543)
|
||||
}}</template>
|
||||
<template #trigger>
|
||||
<q-input
|
||||
dense
|
||||
lazy-rules
|
||||
outlined
|
||||
:model-value="year === 0 ? 'ทั้งหมด' : Number(year) + 543"
|
||||
:label="`${'ปีงบประมาณ'}`"
|
||||
>
|
||||
<template v-if="year" v-slot:append>
|
||||
<q-icon
|
||||
name="cancel"
|
||||
@click.stop.prevent="(year = 0), getData()"
|
||||
class="cursor-pointer"
|
||||
/>
|
||||
</template>
|
||||
<template v-slot:prepend>
|
||||
<q-icon
|
||||
name="event"
|
||||
class="cursor-pointer"
|
||||
style="color: var(--q-primary)"
|
||||
>
|
||||
</q-icon>
|
||||
</template>
|
||||
</q-input>
|
||||
</template>
|
||||
</datepicker>
|
||||
<q-select
|
||||
dense
|
||||
outlined
|
||||
v-model="type"
|
||||
:options="scholarshipTypeOp"
|
||||
emit-value
|
||||
map-options
|
||||
option-value="id"
|
||||
option-label="name"
|
||||
label="เลือกประเภททุน"
|
||||
@update:model-value="getData()"
|
||||
style="width: 350px"
|
||||
/>
|
||||
<!-- <q-btn
|
||||
flat
|
||||
round
|
||||
color="primary"
|
||||
icon="add"
|
||||
@click="router.push(`/KPI/add`)"
|
||||
>
|
||||
<q-tooltip> เพิ่มข้อมูล </q-tooltip>
|
||||
</q-btn> -->
|
||||
</div>
|
||||
|
||||
<q-space />
|
||||
<div class="row q-gutter-sm">
|
||||
<q-input
|
||||
outlined
|
||||
dense
|
||||
v-model="filterKeyword"
|
||||
label="ค้นหา"
|
||||
></q-input>
|
||||
<q-select
|
||||
v-model="visibleColumns"
|
||||
multiple
|
||||
outlined
|
||||
dense
|
||||
options-dense
|
||||
:display-value="$q.lang.table.columns"
|
||||
emit-value
|
||||
map-options
|
||||
:options="columns"
|
||||
option-value="name"
|
||||
options-cover
|
||||
style="min-width: 150px"
|
||||
/>
|
||||
</div>
|
||||
</q-toolbar>
|
||||
|
||||
<q-table
|
||||
ref="table"
|
||||
:columns="columns"
|
||||
:rows="rows"
|
||||
:filter="filterKeyword"
|
||||
row-key="id"
|
||||
flat
|
||||
bordered
|
||||
:paging="true"
|
||||
dense
|
||||
hide-pagination
|
||||
class="custom-table2"
|
||||
:visible-columns="visibleColumns"
|
||||
v-model:pagination="pagination"
|
||||
:rows-per-page-options="[10, 25, 50, 100]"
|
||||
>
|
||||
<template v-slot:pagination="scope">
|
||||
<q-pagination
|
||||
v-model="currentPage"
|
||||
active-color="primary"
|
||||
color="dark"
|
||||
:max="Number(maxPage)"
|
||||
size="sm"
|
||||
boundary-links
|
||||
direction-links
|
||||
></q-pagination>
|
||||
</template>
|
||||
<template v-slot:header="props">
|
||||
<q-tr :props="props">
|
||||
<q-th v-for="col in props.cols" :key="col.name" :props="props">
|
||||
<span class="text-weight-medium">{{ col.label }}</span>
|
||||
</q-th>
|
||||
</q-tr>
|
||||
</template>
|
||||
<template v-slot:body="props">
|
||||
<q-tr :props="props" class="cursor-pointer">
|
||||
<q-td
|
||||
v-for="col in props.cols"
|
||||
:key="col.id"
|
||||
@click="onEdit(props.row.id)"
|
||||
>
|
||||
<div v-if="col.name == 'scholarshipYear'">
|
||||
{{ col.value ? col.value + 543 : "-" }}
|
||||
</div>
|
||||
<div v-else-if="col.name == 'scholarshipType'">
|
||||
{{ col.value ? convertType(col.value) : "-" }}
|
||||
</div>
|
||||
<div v-else>
|
||||
{{ col.value ? col.value : "-" }}
|
||||
</div>
|
||||
</q-td>
|
||||
</q-tr>
|
||||
</template>
|
||||
</q-table>
|
||||
</q-card>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
<style scoped lang="scss">
|
||||
.icon-color {
|
||||
color: #4154b3;
|
||||
}
|
||||
|
||||
.custom-table2 {
|
||||
max-height: 64vh;
|
||||
|
||||
.q-table tr:nth-child(odd) td {
|
||||
background: white;
|
||||
}
|
||||
|
||||
.q-table tr:nth-child(even) td {
|
||||
background: #f8f8f8;
|
||||
}
|
||||
|
||||
.q-table thead tr {
|
||||
background: #ecebeb;
|
||||
}
|
||||
|
||||
.q-table thead tr th {
|
||||
position: sticky;
|
||||
}
|
||||
|
||||
.q-table td:nth-of-type(2) {
|
||||
z-index: 3 !important;
|
||||
}
|
||||
|
||||
.q-table th:nth-of-type(2),
|
||||
.q-table td:nth-of-type(2) {
|
||||
position: sticky;
|
||||
left: 0;
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
/* this will be the loading indicator */
|
||||
.q-table thead tr:last-child th {
|
||||
/* height of all previous header rows */
|
||||
top: 48px;
|
||||
}
|
||||
|
||||
.q-table thead tr:first-child th {
|
||||
top: 0;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
|
@ -11,6 +11,8 @@ import ModuleLeave from "@/modules/05_leave/router";
|
|||
import ModuEvaluate from "@/modules/06_evaluate/router";
|
||||
import ModuAppealComplain from "@/modules/07_appealComplain/router";
|
||||
import ModuleSupport from "@/modules/00_support/router";
|
||||
import ModuleKPI from "@/modules/08_KPI/router";
|
||||
import ModuleScholarship from "@/modules/09_scholarship/router";
|
||||
// TODO: ใช้หรือไม่?
|
||||
import keycloak from "@/plugins/keycloak";
|
||||
|
||||
|
|
@ -47,6 +49,8 @@ const router = createRouter({
|
|||
...ModuEvaluate,
|
||||
...ModuAppealComplain,
|
||||
...ModuleSupport,
|
||||
...ModuleKPI,
|
||||
...ModuleScholarship,
|
||||
],
|
||||
},
|
||||
],
|
||||
|
|
|
|||
|
|
@ -988,7 +988,7 @@ export const useCounterMixin = defineStore("mixin", () => {
|
|||
* @param endDate วันสิ้นสุด format MM-DD-YYYY"
|
||||
* @returns ผลการคำนวน ปี เดือน วัน ในรูปแบบ 1 ปี 10 เดือน 5 วัน
|
||||
*/
|
||||
function calculateDurationYmd(startDate: string, endDate: string) {
|
||||
function calculateDurationYmd(startDate: any, endDate: any) {
|
||||
if (startDate && endDate) {
|
||||
const start = new Date(startDate);
|
||||
const end = new Date(endDate);
|
||||
|
|
|
|||
|
|
@ -90,7 +90,7 @@ const fetchlistNotification = async (index: number, type: string) => {
|
|||
const doLogout = () => {
|
||||
$q.dialog({
|
||||
title: "ยืนยันการออกจากระบบ",
|
||||
message: `ต้องการออกจากระบบใช้หรือไม่?`,
|
||||
message: `ต้องการออกจากระบบใช่หรือไม่?`,
|
||||
cancel: "ยกเลิก",
|
||||
ok: "ยืนยัน",
|
||||
persistent: true,
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue