index.vue 5.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170
  1. <script lang="ts" setup>
  2. import { RadioGroup, Radio, Divider, TypographyTitle, RadioButton } from 'ant-design-vue';
  3. import FullCalendar from '@fullcalendar/vue3';
  4. import dayGridPlugin from '@fullcalendar/daygrid';
  5. import { CalendarOptions } from '@fullcalendar/core';
  6. import interactionPlugin from '@fullcalendar/interaction';
  7. import { useMessage } from '/@/hooks/web/useMessage';
  8. import { getQueryByTenantId, editDay } from './teachorNoteach.api';
  9. import { useUserStore } from '/@/store/modules/user';
  10. import { h, ref } from 'vue';
  11. import dayjs from 'dayjs';
  12. import { storeToRefs } from 'pinia';
  13. const { userInfo } = storeToRefs(useUserStore());
  14. const { createWarningModal, createMessage } = useMessage();
  15. const isChangeDay = ref(0);
  16. const changeDay = ref(1);
  17. const today = new Date();
  18. const nonTeachingDays = ref<Date[]>([]);
  19. const fullCalendarRef = ref();
  20. const TeachingData = ref<{ day: string; id: string; isTeaching: number; orgCode: string }[]>([]);
  21. const calendarOptions = ref<CalendarOptions>({
  22. plugins: [dayGridPlugin, interactionPlugin],
  23. initialView: 'dayGridMonth',
  24. events: [{ title: '今天', start: new Date() }],
  25. selectable: true,
  26. selectMirror: true,
  27. headerToolbar: {
  28. left: '',
  29. right: '',
  30. },
  31. locale: 'zh-cn',
  32. dayCellClassNames: (arg) => {
  33. const { date } = arg;
  34. const day = date.getDay();
  35. if ((day === 0 || day === 6) && isNonTeachingDay(date)) {
  36. return ['weekend-cell'];
  37. }
  38. // const isPast = date < today && !dayjs(date).isSame(dayjs(today), 'day');
  39. if (isPast(date)) {
  40. return ['past-day'];
  41. }
  42. // 判断是否为非教学日
  43. // const isNonTeachingDay = nonTeachingDays.value.some((d) => dayjs(d).isSame(dayjs(date), 'day'));
  44. if (isNonTeachingDay(date)) {
  45. return ['non-teaching-day'];
  46. }
  47. return [];
  48. },
  49. select: handleClick,
  50. });
  51. function handleClick(selectInfo) {
  52. const clickedDate = selectInfo.start;
  53. // const day = dayjs(clickedDate).day();
  54. if (isPast(clickedDate)) {
  55. //今天之前的日期不允许点击//或者是周末也不允许点击
  56. return;
  57. }
  58. createWarningModal({
  59. title: '日期类型修改',
  60. okText: '确认',
  61. cancelText: '取消',
  62. content() {
  63. const arr = [h(Radio, { value: 0 }, () => '教学日'), h(Radio, { value: 1 }, () => '非教学日')];
  64. return h(
  65. RadioGroup,
  66. {
  67. value: isChangeDay.value,
  68. onChange(e) {
  69. isChangeDay.value = e.target.value;
  70. },
  71. },
  72. () => arr
  73. );
  74. },
  75. okCancel: true,
  76. onOk: async () => {
  77. const findData = TeachingData.value.find((it) => dayjs(it.day).valueOf() == dayjs(clickedDate).valueOf());
  78. if (!findData) return createMessage.error('添加失败,请重新选择');
  79. await editDay({ isTeaching: isChangeDay.value, id: findData.id });
  80. getTimeDay();
  81. fullCalendarRef.value.getApi().render();
  82. if (isChangeDay.value == 2) {
  83. nonTeachingDays.value.push(clickedDate);
  84. } else {
  85. const index = findNonTeachingDayIndex(clickedDate);
  86. if (index > -1) {
  87. nonTeachingDays.value.splice(index, 1);
  88. }
  89. }
  90. },
  91. onCancel: () => {},
  92. });
  93. }
  94. function isNonTeachingDay(date: Date): boolean {
  95. // 判断日期是否为非教学日
  96. return nonTeachingDays.value.some((d) => dayjs(d).isSame(dayjs(date), 'day'));
  97. }
  98. function findNonTeachingDayIndex(clickedDate: Date): number {
  99. // 找到非教学日在数组中的索引
  100. return nonTeachingDays.value.findIndex((d) => dayjs(d).isSame(dayjs(clickedDate), 'day'));
  101. }
  102. function isPast(date) {
  103. return date < today && !dayjs(date).isSame(dayjs(today), 'day');
  104. }
  105. function handleChangeDay() {
  106. if (changeDay.value == 1) {
  107. fullCalendarRef.value.getApi().today();
  108. } else {
  109. fullCalendarRef.value.getApi().next();
  110. }
  111. }
  112. async function getTimeDay() {
  113. const res = await getQueryByTenantId({
  114. orgCode: userInfo.value?.orgCode,
  115. });
  116. TeachingData.value = res;
  117. nonTeachingDays.value = TeachingData.value.filter((it) => it.isTeaching).map((it) => new Date(it.day));
  118. fullCalendarRef.value.getApi().render();
  119. }
  120. getTimeDay();
  121. </script>
  122. <template>
  123. <div class="px-15 py-3 bg-white">
  124. <div class="flex items-center justify-between">
  125. <TypographyTitle :level="3"> {{ changeDay == 1 ? dayjs().format('YYYY-MM') : dayjs().add(1, 'month').format('YYYY-MM') }} </TypographyTitle>
  126. <RadioGroup v-model:value="changeDay" @change="handleChangeDay">
  127. <RadioButton :value="1">今天 </RadioButton>
  128. <RadioButton :value="2">下一个月 </RadioButton>
  129. </RadioGroup>
  130. </div>
  131. <Divider></Divider>
  132. <div class="flex items-center justify-center customer">
  133. <div class="w-70%">
  134. <FullCalendar :options="calendarOptions" ref="fullCalendarRef"> </FullCalendar>
  135. </div>
  136. </div>
  137. <div class="mt-5 w-full text-right"> 红色数字为非教学日,蓝色数字为教学日。 </div>
  138. </div>
  139. </template>
  140. <style lang="less" scoped>
  141. .customer {
  142. :deep(.weekend-cell) {
  143. .fc-daygrid-day-number {
  144. color: red !important;
  145. }
  146. }
  147. :deep(.past-day) {
  148. .fc-daygrid-day-number {
  149. color: #ccc;
  150. }
  151. }
  152. :deep(.non-teaching-day) {
  153. .fc-daygrid-day-number {
  154. color: red !important;
  155. }
  156. }
  157. :deep(.fc-col-header) {
  158. .fc-day-sat,
  159. .fc-day-sun {
  160. .fc-col-header-cell-cushion {
  161. color: red !important;
  162. }
  163. }
  164. }
  165. }
  166. </style>