2023-11-15 10:04:45 +08:00

310 lines
9.4 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import { useEffect, useState } from "react";
import { ImageUploader, Skeleton, Toast, Mask, Image } from "antd-mobile";
import { useNavigate } from "react-router-dom";
import { user as member } from "../../api/index";
import { getDepName, studyTimeFormat } from "../../utils/index";
import { loginAction, logoutAction } from "../../store/user/loginUserSlice";
import { ImageUploadItem } from "antd-mobile/es/components/image-uploader";
import styles from "./index.module.scss";
import { useDispatch, useSelector } from "react-redux";
import moreIcon from "../../assets/images/commen/icon-more.png";
const MemberPage = () => {
const dispatch = useDispatch();
const navigate = useNavigate();
const [loading, setLoading] = useState(false);
const [currentDepartment, setCurrentDepartment] = useState("");
const [visible, setVisible] = useState(false);
const [init, setInit] = useState(false);
const [stats, setStats] = useState<any>({});
const [fileList, setFileList] = useState<ImageUploadItem[]>([
{
url: "",
},
]);
const [learnTodayHour, setLearnTodayHour] = useState(0);
const [learnTodayMin, setLearnTodayMin] = useState(0);
const [learnTotalHour, setLearnTotalHour] = useState(0);
const [learnTotalMin, setLearnTotalMin] = useState(0);
const user = useSelector((state: any) => state.loginUser.value.user);
const departments = useSelector(
(state: any) => state.loginUser.value.departments
);
const currentDepId = useSelector(
(state: any) => state.loginUser.value.currentDepId
);
useEffect(() => {
document.title = "我的";
getUser();
}, []);
useEffect(() => {
if (departments.length > 0) {
setCurrentDepartment(getDepName() || departments[0].name);
}
}, [departments]);
useEffect(() => {
if (currentDepId === 0) {
return;
}
getData();
}, [currentDepId, user]);
const getData = () => {
setLoading(true);
member.courses(currentDepId, 0).then((res: any) => {
setStats(res.data.stats);
let todayData = studyTimeFormat(res.data.stats.today_learn_duration);
if (todayData) {
setLearnTodayHour(todayData[0]);
setLearnTodayMin(todayData[1]);
if (todayData[1] === 0 && todayData[2] > 0) {
setLearnTodayMin(1);
}
}
let totalData = studyTimeFormat(res.data.stats.learn_duration);
if (totalData) {
setLearnTotalHour(totalData[0]);
setLearnTotalMin(totalData[1]);
if (totalData[1] === 0 && totalData[2] > 0) {
setLearnTodayMin(1);
}
}
setLoading(false);
});
};
const setClick = () => {
setVisible(true);
};
const getTotal = (num1: number, num2: number) => {
let value = 0;
if (num1) {
value = value + num1;
}
if (num2 && num2 > 0) {
value = value + num2;
}
return value;
};
// const beforeUpload = (file: File) => {
// if (file.size > 2 * 1024 * 1024) {
// Toast.show("超过2M限制不允许上传");
// return null;
// }
// return file;
// };
const mockUpload = async (file: File) => {
setVisible(false);
const data = new FormData();
data.append("file", file);
try {
let res = await member.avatar(data);
if (res) {
Toast.show("头像更换成功");
await getUser(); //获取登录用户的信息并写入store
}
} catch (e) {
console.error("上传失败", e);
}
return {
url: URL.createObjectURL(file),
};
};
const getUser = async () => {
let res: any = await member.detail();
if (res) {
dispatch(loginAction(res.data));
setFileList([]);
setInit(true);
}
};
return (
<div className={styles["main-body"]}>
<div className={styles["content-box"]}>
<div className={styles["top-content"]}>
<div className={styles["user-info"]}>
{!init && (
<>
<Skeleton
animated
style={{
width: 100,
height: 100,
borderRadius: "50%",
marginRight: 20,
}}
/>
<div className={styles["other-cont"]}>
<Skeleton
animated
style={{ width: "100%", height: 20, marginTop: 15 }}
/>
<Skeleton
animated
style={{ width: "100%", height: 24, marginTop: 20 }}
/>
</div>
</>
)}
{init && (
<>
<Image
width={100}
height={100}
style={{
borderRadius: "50%",
marginRight: 20,
}}
fit="cover"
src={user?.avatar}
/>
<div className={styles["other-cont"]}>
<div className={styles["name"]}>{user?.name}</div>
<div className={styles["departments"]}>
<div className={styles["department-name"]}>
{currentDepartment}
</div>
</div>
</div>
</>
)}
</div>
<Image
className={styles["more-button"]}
onClick={() => setClick()}
src={moreIcon}
/>
</div>
<div className={styles["stats-content"]}>
<div className={styles["stat-item"]}>
<span className={styles["time"]}>
<strong> {learnTodayHour} </strong>
<strong> {learnTodayMin} </strong>
</span>
<span className={styles["tit"]}></span>
</div>
<div className={styles["stat-item"]}>
<span className={styles["time"]}>
<strong> {learnTotalHour} </strong>
<strong> {learnTotalMin} </strong>
</span>
<span className={styles["tit"]}></span>
</div>
</div>
<div className={styles["records-content"]}>
<div className={styles["record-item"]}>
<div className={styles["name"]}></div>
<div className={styles["value"]}>{currentDepartment}</div>
</div>
<div className={styles["record-item"]}>
<div className={styles["name"]}></div>
<div className={styles["value"]}>
<strong>
{getTotal(
stats.required_finished_hour_count,
stats.nun_required_finished_hour_count
)}{" "}
</strong>
/{" "}
{getTotal(
stats.required_hour_count,
stats.nun_required_hour_count
)}
</div>
</div>
<div className={styles["record-item"]}>
<div className={styles["name"]}></div>
<div className={styles["value"]}>
{" "}
<strong>{stats.required_finished_course_count || 0} </strong>/{" "}
{stats.required_course_count || 0}
</div>
</div>
<div className={styles["record-item"]}>
<div className={styles["name"]}></div>
{stats.nun_required_course_count > 0 ? (
<div className={styles["value"]}>
{" "}
<strong>
{stats.nun_required_finished_course_count || 0}{" "}
</strong>
/ {stats.nun_required_course_count || 0}
</div>
) : (
<div className={styles["value"]}>
<strong>0 </strong>/ 0
</div>
)}
</div>
</div>
</div>
<Mask
visible={visible}
onMaskClick={() => {
setVisible(false);
}}
>
<div className={styles["dialog-body"]}>
<div className={styles["dialog-box"]}>
<div
className={styles["button-item"]}
onClick={() => {
setVisible(false);
if (departments.length === 1) {
Toast.show({
content: "暂无可切换部门",
});
return;
}
navigate("/change-department");
}}
>
</div>
<ImageUploader
value={fileList}
onChange={setFileList}
upload={mockUpload}
preview={false}
showFailed={false}
>
<div className={styles["button-item"]}></div>
</ImageUploader>
<div
className={styles["button-item"]}
onClick={() => {
setVisible(false);
navigate("/change-password");
}}
>
</div>
</div>
<div
className={styles["dialog-button"]}
onClick={() => {
setVisible(false);
dispatch(logoutAction());
window.location.href = "/login";
}}
>
退
</div>
</div>
</Mask>
</div>
);
};
export default MemberPage;