+ {homePageData.isLoading ? (
+
) : (
<>
- Главная страница
+ Главная страница
- {/* Быстрые действия */}
-
-
+
+
}
- onClick={handleCreateAppointment}
- style={buttonStyle}
+ icon={}
+ onClick={homePageData.handleCreateAppointment}
+ style={homePageUI.buttonStyle}
>
Новый прием
}
- onClick={handleCreateScheduledAppointment}
- style={buttonStyle}
+ icon={}
+ onClick={homePageData.handleCreateScheduledAppointment}
+ style={homePageUI.buttonStyle}
>
Запланировать
}
- onClick={handleCreatePatient}
- style={buttonStyle}
+ icon={}
+ onClick={homePageData.handleCreatePatient}
+ style={homePageUI.buttonStyle}
>
Добавить пациента
- {/* Статистика */}
-
-
-
-
+
+
+
+
-
-
+
+
dayjs(a.appointment_datetime).isSame(dayjs(), "month")).length
+ homePageData.appointments.filter((a) => dayjs(a.appointment_datetime).isSame(dayjs(), "month")).length
}
/>
-
-
-
+
+
+
- {/* События на сегодня */}
(
handleEventClick(item)}
- style={listItemStyle}
+ onClick={() => homePageData.handleEventClick(item)}
+ style={homePageUI.listItemStyle}
>
@@ -168,43 +130,22 @@ const HomePage = () => {
)}
/>
- {todayEvents.length === 0 && (
+ {homePageUI.todayEvents.length === 0 && (
Нет событий на сегодня
)}
- {/* Уведомления */}
-
-
- {upcomingBirthdays.map((p) => (
-
- ))}
- {upcomingBirthdays.length === 0 && (
- Нет уведомлений
- )}
-
-
-
- {/* График */}
-
-
-
+
+
+
- {/* Модальные окна */}
-
-
-
-
+
+
+
+
+
>
)}
diff --git a/web-app/src/Components/Pages/HomePage/useHomePage.js b/web-app/src/Components/Pages/HomePage/useHomePage.js
index d03593b..f92b6c8 100644
--- a/web-app/src/Components/Pages/HomePage/useHomePage.js
+++ b/web-app/src/Components/Pages/HomePage/useHomePage.js
@@ -1,16 +1,18 @@
-import { useGetAppointmentsQuery } from "../../../Api/appointmentsApi.js";
-import { useGetScheduledAppointmentsQuery } from "../../../Api/scheduledAppointmentsApi.js";
-import { useGetPatientsQuery } from "../../../Api/patientsApi.js";
-import { notification } from "antd";
-import { useEffect } from "react";
-import { useDispatch } from "react-redux";
+import {useGetAppointmentsQuery} from "../../../Api/appointmentsApi.js";
+import {useGetScheduledAppointmentsQuery} from "../../../Api/scheduledAppointmentsApi.js";
+import {useGetPatientsQuery} from "../../../Api/patientsApi.js";
+import {notification} from "antd";
+import {useEffect} from "react";
+import {useDispatch} from "react-redux";
import {
setSelectedAppointment,
setSelectedScheduledAppointment,
- openModal,
+ openModal as openAppointmentsListModal,
openScheduledModal,
- closeModal,
} from "../../../Redux/Slices/appointmentsSlice.js";
+import {
+ openModal as openPatientModal,
+} from "../../../Redux/Slices/patientsSlice.js";
import dayjs from "dayjs";
import isBetween from "dayjs/plugin/isBetween";
import {useGetAppointmentTypesQuery} from "../../../Api/appointmentTypesApi.js"; // Import isBetween plugin
@@ -92,7 +94,7 @@ const useHomePage = () => {
};
const handleCreateAppointment = () => {
- dispatch(openModal());
+ dispatch(openAppointmentsListModal());
};
const handleCreateScheduledAppointment = () => {
@@ -100,15 +102,7 @@ const useHomePage = () => {
};
const handleCreatePatient = () => {
- notification.info({
- message: "В разработке",
- description: "Функция добавления пациента будет доступна в будущем.",
- placement: "topRight",
- });
- };
-
- const handleCancelModal = () => {
- dispatch(closeModal());
+ dispatch(openPatientModal());
};
return {
@@ -130,7 +124,6 @@ const useHomePage = () => {
handleCreateAppointment,
handleCreateScheduledAppointment,
handleCreatePatient,
- handleCancelModal,
};
};
diff --git a/web-app/src/Components/Pages/HomePage/useHomePageUI.js b/web-app/src/Components/Pages/HomePage/useHomePageUI.js
index 1d0118a..d4767df 100644
--- a/web-app/src/Components/Pages/HomePage/useHomePageUI.js
+++ b/web-app/src/Components/Pages/HomePage/useHomePageUI.js
@@ -1,7 +1,8 @@
import { Grid } from "antd";
import { useMemo } from "react";
import dayjs from "dayjs";
-import isBetween from "dayjs/plugin/isBetween"; // Import isBetween plugin
+import isBetween from "dayjs/plugin/isBetween";
+import {useSelector} from "react-redux"; // Import isBetween plugin
dayjs.extend(isBetween); // Extend dayjs with isBetween
@@ -42,6 +43,52 @@ const useHomePageUI = (appointments, scheduledAppointments, patients) => {
return data;
}, [appointments]);
+ const scheduledAppointmentsByDay = useMemo(() => {
+ const data = Array(7).fill(0);
+ scheduledAppointments
+ .filter((app) =>
+ dayjs(app.scheduled_datetime).isBetween(dayjs().startOf("week"), dayjs().endOf("week"), "day", "[]")
+ )
+ .forEach((app) => {
+ const dayIndex = dayjs(app.scheduled_datetime).day();
+ data[dayIndex === 0 ? 6 : dayIndex - 1]++;
+ });
+ return data;
+ }, [scheduledAppointments]);
+
+ const chartOptions = {
+ responsive: true,
+ maintainAspectRatio: false,
+ scales: {
+ y: { beginAtZero: true, title: { display: true, text: "Количество приемов" } },
+ x: { title: { display: true, text: "День недели" } },
+ },
+ plugins: {
+ legend: { display: false },
+ title: { display: true, text: "Приемы за неделю" },
+ },
+ };
+
+ const chartData = {
+ labels: ["Пн", "Вт", "Ср", "Чт", "Пт", "Сб", "Вс"],
+ datasets: [
+ {
+ label: "Приемы",
+ data: appointmentsByDay,
+ backgroundColor: "#1890ff",
+ borderColor: "#096dd9",
+ borderWidth: 1,
+ },
+ {
+ label: "Запланированные приемы",
+ data: scheduledAppointmentsByDay,
+ backgroundColor: "#ff4d4f",
+ borderColor: "#ff4d4f",
+ borderWidth: 1,
+ },
+ ],
+ };
+
return {
containerStyle,
sectionStyle,
@@ -53,6 +100,8 @@ const useHomePageUI = (appointments, scheduledAppointments, patients) => {
todayEvents,
upcomingBirthdays,
appointmentsByDay,
+ chartData,
+ chartOptions,
};
};
diff --git a/web-app/src/Components/Pages/AppointmentsPage/Components/AppointmentViewModal/AppointmentViewModal.jsx b/web-app/src/Components/Widgets/AppointmentViewModal/AppointmentViewModal.jsx
similarity index 84%
rename from web-app/src/Components/Pages/AppointmentsPage/Components/AppointmentViewModal/AppointmentViewModal.jsx
rename to web-app/src/Components/Widgets/AppointmentViewModal/AppointmentViewModal.jsx
index 3499bc9..99f1130 100644
--- a/web-app/src/Components/Pages/AppointmentsPage/Components/AppointmentViewModal/AppointmentViewModal.jsx
+++ b/web-app/src/Components/Widgets/AppointmentViewModal/AppointmentViewModal.jsx
@@ -1,11 +1,10 @@
import {Button, Modal, Row, Typography} from "antd";
import useAppointmentViewUI from "./useAppointmentViewUI.js";
-import PropTypes from "prop-types";
import dayjs from "dayjs";
-const AppointmentViewModal = ({visible, onCancel}) => {
- const appointmentViewModalUI = useAppointmentViewUI(visible, onCancel);
+const AppointmentViewModal = () => {
+ const appointmentViewModalUI = useAppointmentViewUI();
if (!appointmentViewModalUI.selectedAppointment) {
return null;
@@ -15,8 +14,8 @@ const AppointmentViewModal = ({visible, onCancel}) => {
<>
@@ -52,10 +51,11 @@ const AppointmentViewModal = ({visible, onCancel}) => {
Результаты приема:
-
+
-
@@ -64,9 +64,5 @@ const AppointmentViewModal = ({visible, onCancel}) => {
);
};
-AppointmentViewModal.propTypes = {
- visible: PropTypes.bool.isRequired,
- onCancel: PropTypes.func.isRequired,
-};
export default AppointmentViewModal;
\ No newline at end of file
diff --git a/web-app/src/Components/Pages/AppointmentsPage/Components/AppointmentViewModal/useAppointmentViewUI.js b/web-app/src/Components/Widgets/AppointmentViewModal/useAppointmentViewUI.js
similarity index 73%
rename from web-app/src/Components/Pages/AppointmentsPage/Components/AppointmentViewModal/useAppointmentViewUI.js
rename to web-app/src/Components/Widgets/AppointmentViewModal/useAppointmentViewUI.js
index 542570f..c461e22 100644
--- a/web-app/src/Components/Pages/AppointmentsPage/Components/AppointmentViewModal/useAppointmentViewUI.js
+++ b/web-app/src/Components/Widgets/AppointmentViewModal/useAppointmentViewUI.js
@@ -1,4 +1,7 @@
import {useDispatch, useSelector} from "react-redux";
+import {
+ setSelectedAppointment
+} from "../../../Redux/Slices/appointmentsSlice.js";
const useAppointmentViewUI = () => {
const dispatch = useDispatch();
@@ -10,7 +13,11 @@ const useAppointmentViewUI = () => {
const blockStyle = {marginBottom: 16};
const footerRowStyle = {marginTop: 16};
const footerButtonStyle = {marginRight: 8};
+ const visible = !!selectedAppointment;
+ const onCancel = () => {
+ dispatch(setSelectedAppointment(null));
+ };
const getDateString = (date) => {
return new Date(date).toLocaleDateString('ru-RU');
@@ -22,7 +29,9 @@ const useAppointmentViewUI = () => {
footerRowStyle,
footerButtonStyle,
selectedAppointment,
+ visible,
getDateString,
+ onCancel,
};
};
diff --git a/web-app/src/Components/Pages/AppointmentsPage/Components/ScheduledAppointmentsViewModal/ScheduledAppointmentsViewModal.jsx b/web-app/src/Components/Widgets/ScheduledAppointmentsViewModal/ScheduledAppointmentsViewModal.jsx
similarity index 97%
rename from web-app/src/Components/Pages/AppointmentsPage/Components/ScheduledAppointmentsViewModal/ScheduledAppointmentsViewModal.jsx
rename to web-app/src/Components/Widgets/ScheduledAppointmentsViewModal/ScheduledAppointmentsViewModal.jsx
index 2441c4f..6fa6f74 100644
--- a/web-app/src/Components/Pages/AppointmentsPage/Components/ScheduledAppointmentsViewModal/ScheduledAppointmentsViewModal.jsx
+++ b/web-app/src/Components/Widgets/ScheduledAppointmentsViewModal/ScheduledAppointmentsViewModal.jsx
@@ -3,7 +3,7 @@ import dayjs from "dayjs";
import useScheduledAppointmentsViewModal from "./useScheduledAppointmentsViewModal.js";
import useScheduledAppointmentsViewModalUI from "./useScheduledAppointmentsViewModalUI.js";
import { useDispatch } from "react-redux";
-import {openModalWithScheduledData} from "../../../../../Redux/Slices/appointmentsSlice.js";
+import {openModalWithScheduledData} from "../../../Redux/Slices/appointmentsSlice.js";
const ScheduledAppointmentsViewModal = () => {
const dispatch = useDispatch();
diff --git a/web-app/src/Components/Pages/AppointmentsPage/Components/ScheduledAppointmentsViewModal/useScheduledAppointmentsViewModal.js b/web-app/src/Components/Widgets/ScheduledAppointmentsViewModal/useScheduledAppointmentsViewModal.js
similarity index 67%
rename from web-app/src/Components/Pages/AppointmentsPage/Components/ScheduledAppointmentsViewModal/useScheduledAppointmentsViewModal.js
rename to web-app/src/Components/Widgets/ScheduledAppointmentsViewModal/useScheduledAppointmentsViewModal.js
index 45904b3..b0ab3e1 100644
--- a/web-app/src/Components/Pages/AppointmentsPage/Components/ScheduledAppointmentsViewModal/useScheduledAppointmentsViewModal.js
+++ b/web-app/src/Components/Widgets/ScheduledAppointmentsViewModal/useScheduledAppointmentsViewModal.js
@@ -1,4 +1,4 @@
-import {useCancelScheduledAppointmentMutation} from "../../../../../Api/scheduledAppointmentsApi.js";
+import {useCancelScheduledAppointmentMutation} from "../../../Api/scheduledAppointmentsApi.js";
const useScheduledAppointmentsViewModal = () => {
diff --git a/web-app/src/Components/Pages/AppointmentsPage/Components/ScheduledAppointmentsViewModal/useScheduledAppointmentsViewModalUI.js b/web-app/src/Components/Widgets/ScheduledAppointmentsViewModal/useScheduledAppointmentsViewModalUI.js
similarity index 93%
rename from web-app/src/Components/Pages/AppointmentsPage/Components/ScheduledAppointmentsViewModal/useScheduledAppointmentsViewModalUI.js
rename to web-app/src/Components/Widgets/ScheduledAppointmentsViewModal/useScheduledAppointmentsViewModalUI.js
index 93602fa..d2a5730 100644
--- a/web-app/src/Components/Pages/AppointmentsPage/Components/ScheduledAppointmentsViewModal/useScheduledAppointmentsViewModalUI.js
+++ b/web-app/src/Components/Widgets/ScheduledAppointmentsViewModal/useScheduledAppointmentsViewModalUI.js
@@ -1,6 +1,6 @@
import {useDispatch, useSelector} from "react-redux";
import dayjs from "dayjs";
-import {setSelectedScheduledAppointment} from "../../../../../Redux/Slices/appointmentsSlice.js";
+import {setSelectedScheduledAppointment} from "../../../Redux/Slices/appointmentsSlice.js";
import {notification} from "antd";