Prechádzať zdrojové kódy

build: 教师管理

chaooo 2 rokov pred
rodič
commit
8b1a530281

+ 43 - 1
src/api/school/index.ts

@@ -1,6 +1,13 @@
 import request from "@/utils/request";
 import { AxiosPromise } from "axios";
-import { SchoolList, GradeList, GradeItem, StudentList } from "./types";
+import {
+  SchoolList,
+  GradeList,
+  GradeItem,
+  StudentList,
+  TeacherList,
+  TeacherEquipment,
+} from "./types";
 
 /**
  * 获取学校列表
@@ -45,3 +52,38 @@ export function getGradeStudents(id: number): AxiosPromise<StudentList[]> {
     params: { grade_id: id },
   });
 }
+/**
+ * 获取教师列表
+ */
+export function getTeacherList(
+  id: number,
+  keyword: string
+): AxiosPromise<TeacherList[]> {
+  return request({
+    url: "/board/v1/teacher",
+    method: "get",
+    params: { school_id: id, search: keyword },
+  });
+}
+/**
+ * 获取教师设备
+ */
+export function getTeacherEquipment(
+  id: number
+): AxiosPromise<TeacherEquipment> {
+  return request({
+    url: "/board/v1/teacher-equipment",
+    method: "get",
+    params: { teacher_id: id },
+  });
+}
+/**
+ * 获取教师班级
+ */
+export function getTeacherGrade(id: number): AxiosPromise<GradeList[]> {
+  return request({
+    url: "/board/v1/teacher-class",
+    method: "get",
+    params: { teacher_id: id },
+  });
+}

+ 61 - 1
src/api/school/types.ts

@@ -37,7 +37,7 @@ export interface GradeItem {
   // 结课时间
   grade_time: string;
   // 折叠面板使用
-  active: number;
+  active: number[];
   // 学生列表
   students: StudentList[];
 }
@@ -54,3 +54,63 @@ export interface StudentList {
   // 训练次数
   count: number;
 }
+/**
+ * 教师列表
+ */
+export interface TeacherList {
+  lists: TeacherItem[];
+  // 数量
+  count: number;
+}
+export interface TeacherItem {
+  // 学生id
+  id: number;
+  // 学生名称
+  name: string;
+  // 注册时间
+  create_time: string;
+  // 折叠面板使用
+  active: number[];
+  // 教师的设备
+  equipment: EquipmentShown[];
+  // 负责班级
+  grades: GradeList[];
+  // 表格行数
+  lines: number;
+}
+export interface TeacherEquipment {
+  // 脑机
+  AI: Equipment[];
+  // 水舞
+  SW: Equipment[];
+  // 恐龙
+  KL: Equipment[];
+  // 碰碰车
+  PP: Equipment[];
+  // SUV
+  SU: Equipment[];
+  // 赛车
+  SC: Equipment[];
+  // UFO
+  UF: Equipment[];
+  // 积木
+  JM: Equipment[];
+}
+export interface Equipment {
+  // 设备号
+  sn: string;
+}
+
+/**
+ * 设备页面展示排列
+ */
+export interface EquipmentShown {
+  AI: string;
+  SW: string;
+  KL: string;
+  PP: string;
+  SU: string;
+  SC: string;
+  UF: string;
+  JM: string;
+}

+ 5 - 5
src/views/grade/index.vue

@@ -5,11 +5,11 @@ import { useUserStore } from "@/store/modules/user";
 import { CaretBottom } from "@element-plus/icons-vue";
 import { getGradeList, getGradeStudents } from "@/api/school";
 
+const userStore = useUserStore();
 defineOptions({
   name: "ClassIndex",
   inheritAttrs: false,
 });
-const userStore = useUserStore();
 /**
  * 班级数据
  */
@@ -40,7 +40,7 @@ function changeStatus() {
   getGradeItems(userStore.schoolId, gradeStatus.value);
 }
 // 打开班级请求学生
-function changeGrade(grade: GradeItem) {
+function collapseGrade(grade: GradeItem) {
   if (!grade.students || grade.students.length === 0) {
     getStudentList(grade);
   }
@@ -77,8 +77,8 @@ watch(
     </div>
     <!-- 班级折叠面板-->
     <div v-for="grade in gradeData" :key="grade.id" class="list-collapse">
-      <el-collapse v-model="grade.active" @change="changeGrade(grade)">
-        <el-collapse-item name="1">
+      <el-collapse v-model="grade.active" @change="collapseGrade(grade)">
+        <el-collapse-item :name="grade.id">
           <template #title>
             <div class="title">
               <span class="blue mr-10">{{ grade.name }}</span>
@@ -91,7 +91,7 @@ watch(
                 >学生:{{ grade.count }}人
                 <el-icon
                   :class="
-                    grade.active && grade.active.includes('1')
+                    grade.active && grade.active.includes(grade.id)
                       ? 'is-active'
                       : ''
                   "

+ 164 - 44
src/views/teacher/index.vue

@@ -1,37 +1,131 @@
 <script setup lang="ts">
-import { GradeList } from "@/api/school/types";
+import { watch } from "vue";
+import { useUserStore } from "@/store/modules/user";
+import { CaretBottom } from "@element-plus/icons-vue";
+import {
+  EquipmentShown,
+  TeacherEquipment,
+  TeacherItem,
+  TeacherList,
+} from "@/api/school/types";
+import {
+  getTeacherEquipment,
+  getTeacherGrade,
+  getTeacherList,
+} from "@/api/school";
 
+const userStore = useUserStore();
 defineOptions({
   name: "TeacherIndex",
   inheritAttrs: false,
 });
-import { watch } from "vue";
-import { useUserStore } from "@/store/modules/user";
-import { CaretBottom } from "@element-plus/icons-vue";
-const userStore = useUserStore();
+/**
+ * 班级数据
+ */
+const teacherData = ref<TeacherItem[]>();
+// 教师数量
+let teacherCount = ref(0);
+// 用于搜索的教师名称或手机号
+let searchKeyword = ref("");
+// 获取教师
+async function getTeacherData(schoolId: number, keyword: string) {
+  getTeacherList(schoolId, keyword)
+    .then(({ data }) => {
+      const temp: TeacherList = data;
+      teacherData.value = temp.lists;
+      teacherCount.value = temp.count;
+    })
+    .catch((error) => {
+      console.log(error);
+    });
+}
+// 获取教师班级和设备
+async function getGradeAndEquipment(teacher: TeacherItem) {
+  // 获取教师班级
+  getTeacherGrade(teacher.id)
+    .then(({ data }) => {
+      teacher.grades = data;
+      if (teacher.grades && teacher.grades.length > 0) {
+        teacher.lines = teacher.grades.length;
+      }
+      if (!teacher.equipment || Object.keys(teacher.equipment).length == 0) {
+        // 获取教师设备
+        getTeacherEquipment(teacher.id).then(({ data }) => {
+          const temp: TeacherEquipment = data;
+          if (temp.AI && temp.AI.length > teacher.lines) {
+            teacher.lines = temp.AI.length;
+          }
+          if (temp.SW && temp.SW.length > teacher.lines) {
+            teacher.lines = temp.SW.length;
+          }
+          if (temp.KL && temp.KL.length > teacher.lines) {
+            teacher.lines = temp.KL.length;
+          }
+          if (temp.PP && temp.PP.length > teacher.lines) {
+            teacher.lines = temp.PP.length;
+          }
+          if (temp.SU && temp.SU.length > teacher.lines) {
+            teacher.lines = temp.SU.length;
+          }
+          if (temp.SC && temp.SC.length > teacher.lines) {
+            teacher.lines = temp.SC.length;
+          }
+          if (temp.UF && temp.UF.length > teacher.lines) {
+            teacher.lines = temp.UF.length;
+          }
+          if (temp.JM && temp.JM.length > teacher.lines) {
+            teacher.lines = temp.JM.length;
+          }
+          const equipments: EquipmentShown[] = [];
+          for (let i = 0; i < teacher.lines; i++) {
+            let item: EquipmentShown = {
+              AI: temp.AI[i]?.sn || "",
+              SW: temp.SW[i]?.sn || "",
+              KL: temp.KL[i]?.sn || "",
+              PP: temp.PP[i]?.sn || "",
+              SU: temp.SU[i]?.sn || "",
+              SC: temp.SC[i]?.sn || "",
+              UF: temp.UF[i]?.sn || "",
+              JM: temp.JM[i]?.sn || "",
+            };
+            equipments.push(item);
+          }
+          teacher.equipment = equipments;
+        });
+      }
+    })
+    .catch((error) => {
+      console.log(error);
+    });
+}
+// 打开教师面板请求数据
+function collapseTeacher(teacher: TeacherItem) {
+  if (!teacher.grades || teacher.grades.length === 0) {
+    getGradeAndEquipment(teacher);
+  }
+}
+// 搜索
+function teacherSearch() {
+  getTeacherData(userStore.schoolId, searchKeyword.value);
+}
+onMounted(() => {
+  // 获取教师
+  getTeacherData(userStore.schoolId, "");
+});
+watch(
+  () => userStore.schoolId,
+  (newValue) => {
+    searchKeyword.value = "";
+    // 学校切换后重新获取教师
+    getTeacherData(newValue, "");
+  }
+);
 watch(
   () => userStore.schoolId,
   (newValue, oldValue) => {
     console.log(newValue, oldValue);
   }
 );
-
-let teacherInfo = ref("");
-// 折叠面板active
-const activeItem = ref();
-const tableData = ref<any>([
-  {
-    e1: "AI00000000",
-    e2: "AI00000000",
-    e3: "AI00000000",
-    e4: "AI00000000",
-    e5: "AI00000000",
-    e6: "AI00000000",
-    e7: "AI00000000",
-    e8: "AI00000000",
-    cls: "TomTomTom",
-  },
-]);
 </script>
 
 <template>
@@ -39,45 +133,62 @@ const tableData = ref<any>([
     <!-- 教师查找 -->
     <div class="teacher-search">
       <el-input
-        v-model="teacherInfo"
+        v-model="searchKeyword"
         size="large"
         placeholder="请输入教师名称或手机号码"
       />
-      <el-button size="large" type="primary">查找</el-button>
-      <span>共<b>40</b>人</span>
+      <el-button size="large" type="primary" @click="teacherSearch()"
+        >查找</el-button
+      >
+      <span
+        >共<b>{{ teacherCount }}</b
+        >人</span
+      >
     </div>
     <!-- 折叠面板-->
-    <div class="list-collapse">
-      <el-collapse v-model="activeItem">
-        <el-collapse-item name="1">
+    <div v-for="teacher in teacherData" :key="teacher.id" class="list-collapse">
+      <el-collapse v-model="teacher.active" @change="collapseTeacher(teacher)">
+        <el-collapse-item :name="teacher.id">
           <template #title>
             <div class="title">
-              <span class="blue mr-10">松阪老师</span>
-              <span>注册时间:2023-02-23</span>
+              <span class="blue mr-10">{{ teacher.name }}</span>
+              <span>注册时间:{{ teacher.create_time }}</span>
               <span class="blue fr"
                 >负责班级 & 绑定设备
                 <el-icon
                   :class="
-                    activeItem && activeItem.includes('1') ? 'is-active' : ''
+                    teacher.active && teacher.active.includes(teacher.id)
+                      ? 'is-active'
+                      : ''
                   "
                   ><CaretBottom
                 /></el-icon>
               </span>
             </div>
           </template>
-          <div>
-            <el-table :data="tableData" style="width: 100%">
-              <el-table-column prop="e1" label="水母星球脑机" align="center" />
-              <el-table-column prop="e2" label="智脑水舞" align="center" />
-              <el-table-column prop="e3" label="智脑恐龙" align="center" />
-              <el-table-column prop="e4" label="智脑碰碰车" align="center" />
-              <el-table-column prop="e5" label="智脑UFO" align="center" />
-              <el-table-column prop="e6" label="智脑SUV" align="center" />
-              <el-table-column prop="e7" label="智脑赛车" align="center" />
-              <el-table-column prop="e8" label="智脑积木" align="center" />
-              <el-table-column prop="cls" label="负责班级" align="center" />
-            </el-table>
-          </div>
+          <el-row>
+            <el-col :span="19">
+              <el-table :data="teacher.equipment" style="width: 100%">
+                <el-table-column
+                  prop="AI"
+                  label="水母星球脑机"
+                  align="center"
+                />
+                <el-table-column prop="SW" label="智脑水舞" align="center" />
+                <el-table-column prop="KL" label="智脑恐龙" align="center" />
+                <el-table-column prop="PP" label="智脑碰碰车" align="center" />
+                <el-table-column prop="UF" label="智脑UFO" align="center" />
+                <el-table-column prop="SU" label="智脑SUV" align="center" />
+                <el-table-column prop="SC" label="智脑赛车" align="center" />
+                <el-table-column prop="JM" label="智脑积木" align="center" />
+              </el-table>
+            </el-col>
+            <el-col :span="5" class="grade">
+              <el-table :data="teacher.grades" style="width: 100%">
+                <el-table-column prop="name" label="负责班级" align="center" />
+              </el-table>
+            </el-col>
+          </el-row>
         </el-collapse-item>
       </el-collapse>
     </div>
@@ -152,4 +263,13 @@ const tableData = ref<any>([
 :deep(.el-table th.el-table__cell) {
   background: #e9ebee;
 }
+:deep(.el-table .el-table__row) {
+  min-height: 40px;
+}
+.grade {
+  border-left: 1px solid #dddddd;
+}
+:deep(.grade .el-table th.el-table__cell) {
+  background: #dddddd;
+}
 </style>