47 4 months ago
parent
commit
6eaba741c9

+ 1 - 1
src/api/system/user/index.ts

@@ -59,7 +59,7 @@ export const updateStudentImg = (employeeNo: string, photoUrl: string) => {
 
 // 用户自己上传(考勤信息也可上传照片)
 export const importUserData = (photoUrl: string) => {
-  return request.post({ url: '/md/acs/import-selfData', photoUrl })
+  return request.post({ url: `/md/acs/import-selfData?photoUrl=${photoUrl}`})
 }
 
 // 查询所有用户列表

+ 1 - 0
src/api/system/user/profile.ts

@@ -35,6 +35,7 @@ export interface ProfileVO {
   supervisor: string
   masterType: string
   userType: string
+  photoUrl: string
 }
 
 export interface UserProfileUpdateReqVO {

+ 4 - 1
src/views/Profile/Index.vue

@@ -22,8 +22,11 @@
           <el-tab-pane :label="t('profile.info.resetPwd')" name="resetPwd">
             <ResetPwd />
           </el-tab-pane>
-          <el-tab-pane label='成果提交' name="achievement" v-if="userType === 1">
+          <!-- <el-tab-pane label='成果提交' name="achievement" v-if="userType === 1">
             <Achievement />
+          </el-tab-pane> -->
+          <el-tab-pane label='人脸信息' name="faceInfo" v-if="userType === 1">
+            <FaceInfo />
           </el-tab-pane>
           <!-- <el-tab-pane :label="t('profile.info.userSocial')" name="userSocial">
             <UserSocial v-model:activeName="activeName" />

+ 169 - 26
src/views/Profile/components/FaceInfo.vue

@@ -1,42 +1,185 @@
 <template>
   <ContentWrap>
-    <el-image
-      v-if="photourl"
-      class="h-80px w-80px"
-      :src="photourl"
-      fit="cover"
-    />
-    <p v-else>加载中...</p>
+    <el-form ref="formRef" :model="formData" label-width="100px">
+      <el-form-item label="人脸信息" prop="photoUrl">
+        <UploadImg v-model="formData.photoUrl">
+          <template #default>
+            <el-image
+              v-if="formData.photoUrl"
+              class="image"
+              :src="formData.photoUrl"
+              fit="cover"
+              style="margin-bottom: 12px;" 
+            />
+          </template>
+        </UploadImg>
+      </el-form-item>
+
+      <el-form-item>
+        <el-button type="primary" @click="submitForm">确定上传</el-button>
+      </el-form-item>
+    </el-form>
   </ContentWrap>
 </template>
 
 <script setup lang="ts">
-import { ref, onMounted } from 'vue'
-import { getUserProfile, ProfileVO } from '@/api/system/user/profile'
+import { reactive, onMounted } from 'vue';
+import { getUserProfile, ProfileVO } from '@/api/system/user/profile';
+import { importUserData } from '@/api/system/user';
+import { useMessage } from '@/hooks/web/useMessage';
+
+const message = useMessage(); // 消息弹窗
+const formData = reactive({
+  photoUrl: '',
+});
 
-const userInfo = ref({} as ProfileVO)
+// 加载用户信息
 const getUserInfo = async () => {
-  const users = await getUserProfile()
-  console.log(users)
-  userInfo.value = users
+  const users = await getUserProfile();
+  console.log(users);
+  formData.photoUrl = users.photoUrl; // 将用户头像填充到 formData 中
+};
+
+const submitForm = async () => {
+  try {
+    console.log('准备提交的头像 URL:', formData.photoUrl);
+    const data = formData as unknown as ProfileVO;
+    const res = await importUserData(data.photoUrl);
+    console.log('API 响应:', res);
+    if (res && res.data) {
+      message.success('照片上传成功');
+      // 在这里处理成功上传后的逻辑,例如更新用户信息
+    } else {
+      message.error('照片上传失败');
+    }
+  } catch (error) {
+    console.error(error);
+    message.error('提交失败,请稍后重试');
+  }
+};
+
+
+// 组件挂载时获取用户信息
+onMounted(async () => {
+  await getUserInfo();
+});
+</script>
+
+<style scoped>
+.image {
+  width: 160px; /* 设置图片宽度 */
+  height: 160px; /* 设置图片高度 */
 }
+</style>
+
+
+
 
-const photourl = ref('')
 
-// 获取图片的函数
-const fetchImage = async () => {
+<!-- <template>
+  <ContentWrap>
+    <div class="image-container">
+      <el-image
+        v-if="userInfo.photoUrl"
+        class="image"
+        :src="userInfo.photoUrl"
+        fit="cover"
+      />
+      <el-button type="primary" @click="photoChange" class="edit-button">编辑</el-button>
+    </div>
+    <el-dialog 
+      v-model:visible="dialogVisible"
+      title="编辑图片" 
+      @open="open"
+      @close="handle"
+      >
+      <div>
+        <el-form ref="formRef">
+          <el-form-item label="图片材料" prop="photoUrl">
+            <UploadImg v-model="formData.photoUrl" />
+          </el-form-item>
+        </el-form>
+      </div>
+      <template #footer>
+        <el-button @click="dialogVisible = false">取消</el-button>
+        <el-button type="primary" @click="submitForm">确定上传</el-button>
+      </template>
+    </el-dialog>
+  </ContentWrap>
+</template>
+
+<script setup lang="ts">
+import { ref, reactive, onMounted } from 'vue';
+import { getUserProfile, ProfileVO } from '@/api/system/user/profile';
+import { importUserData } from '@/api/system/user';
+import { useMessage } from '@/hooks/web/useMessage';
+
+const message = useMessage(); // 消息弹窗
+const dialogVisible = ref(false); // 弹窗的是否展示
+const formLoading = ref(false); // 表单的加载中
+const formData = reactive({
+  photoUrl: '',
+});
+const userInfo = ref({} as ProfileVO);
+
+const getUserInfo = async () => {
+  const users = await getUserProfile();
+  console.log(users);
+  userInfo.value = users;
+};
+
+const photoChange = () => {
+  dialogVisible.value = true;
+  formData.photoUrl = userInfo.value.photoUrl;
+};
+
+const open = () => {
+  dialogVisible.value = true;
+  formData.photoUrl = userInfo.value.photoUrl;
+};
+
+const handle = () => {
+  dialogVisible.value = false;
+};
+
+const submitForm = async () => {
+  formLoading.value = true;
   try {
-    const response = await getUserProfile() // 替换为实际获取图片的API方法
-    console.log(response,'12');
-    photourl.value = response.photoUrl // 根据实际API的返回结构调整
+    const res = await importUserData(formData.photoUrl);
+    if (res && res.data) {
+      userInfo.value.photoUrl = res.data; // 更新用户信息中的头像链接
+      message.success('照片上传成功');
+      dialogVisible.value = false;
+    } else {
+      message.error('照片上传失败');
+    }
   } catch (error) {
-    console.error('获取图片失败:', error)
+    console.error(error);
+    message.error('提交失败,请稍后重试');
+  } finally {
+    formLoading.value = false;
   }
+};
+
+onMounted(async () => {
+  await getUserInfo();
+});
+</script>
+
+<style scoped>
+.image-container {
+  display: flex;
+  flex-direction: column;
+  align-items: center; /* 垂直居中 */
+  justify-content: center; /* 水平居中 */
 }
 
-// 组件挂载后获取图片
-onMounted(() => {
-  fetchImage()
-  getUserInfo()
-})
-</script>
+.image {
+  width: 160px; /* 将图片宽度设置为原来的两倍 */
+  height: 160px; /* 将图片高度设置为原来的两倍 */
+}
+
+.edit-button {
+  margin-top: 16px; /* 设置按钮与图片之间的间距 */
+}
+</style> -->

+ 2 - 2
src/views/system/workroomCollege/deptInfo/index.vue

@@ -223,8 +223,8 @@ const toggleEditMode = () => {
 
  // 创建一个 computed 属性来处理并去掉 <p> 标签
   const cleanedDescription = computed(() => {
-      return userInfo.value.description ? userInfo.value.description.replace(/<\/?p[^>]*>/g, '') : '';
-    });
+  return userInfo.value.description ? userInfo.value.description.replace(/<\/?[^>]+(>|$)/g, '') : '';
+});
 
     // 表单提交
     const submit = async () => {

+ 73 - 180
src/views/system/workroomTeacher/dept/DeptForm.vue

@@ -7,234 +7,127 @@
       :rules="formRules"
       label-width="100px"
     >
-      <!-- <el-form-item label="上级部门" prop="parentId">
-        <el-tree-select
-          v-model="formData.parentId"
-          :data="deptTree"
-          :props="defaultProps"
-          check-strictly
-          default-expand-all
-          placeholder="请选择上级部门"
-          value-key="deptId"
-        />
-      </el-form-item> -->
       <el-form-item label="工作间名称" prop="name">
         <el-input v-model="formData.name" placeholder="请输入工作间名称" />
       </el-form-item>
-      <!-- <el-form-item label="显示排序" prop="sort">
-        <el-input-number v-model="formData.sort" :min="0" controls-position="right" />
-      </el-form-item> -->
-      <!-- <el-form-item label="负责人" prop="leaderUserId">
-        <el-select
-          v-model="formData.leaderUserId"
-          @change="handleSupervisorChange"
-          placeholder="请选择负责人"
-          clearable
-          filterable
-          multiple
-          class="!w-240px"
-        >
-          <el-option
-            v-for="user in users"
-            :key="user.id"
-            :label="user.nickname"
-            :value="user.id"
-          />
-        </el-select>
-      </el-form-item> -->
-      <el-form-item label="联系电话" prop="phone" >
+      <el-form-item label="联系电话" prop="phone">
         <el-input v-model="formData.phone" maxlength="11" placeholder="请输入联系电话" />
       </el-form-item>
-      <el-form-item label="邮箱" prop="email" >
+      <el-form-item label="邮箱" prop="email">
         <el-input v-model="formData.email" maxlength="50" placeholder="请输入邮箱" />
       </el-form-item>
-      <!-- <el-form-item label="状态" prop="status">
-        <el-select v-model="formData.status" clearable placeholder="请选择状态">
-          <el-option
-            v-for="dict in getIntDictOptions(DICT_TYPE.COMMON_STATUS)"
-            :key="dict.value"
-            :label="dict.label"
-            :value="dict.value"
-          />
-        </el-select>
-      </el-form-item> -->
       <el-form-item label="工作间地址" prop="address">
-          <el-input v-model="formData.address" placeholder="请输入工作间地址" />
-        </el-form-item>
-      <!-- <el-form-item label="创建时间" prop="createTime">
-        <el-date-picker
-          v-model="formData.createTime"
-          type="datetime"
-          value-format="x"
-          placeholder="选择打卡时间"
-        />
-      </el-form-item> -->
-      <!-- <el-form-item label="简介" prop="description">
-        <el-input type="textarea" v-model="formData.description" placeholder="请输入简介" />
-      </el-form-item> -->
+        <el-input v-model="formData.address" placeholder="请输入工作间地址" />
+      </el-form-item>
       <el-form-item label="简介" prop="description">
-          <Editor v-model="formData.description" ref="editorRef"/>
+        <Editor v-model="formData.description" ref="editorRef"/>
       </el-form-item>
     </el-form>
     <template #footer>
       <el-button type="primary" @click="submitForm">确 定</el-button>
-      <el-button @click="dialogVisible = false">取 消</el-button>
+      <el-button @click="handleClose">取 消</el-button>
     </template>
   </Dialog>
 </template>
+
 <script lang="ts" setup>
-// import { DICT_TYPE, getIntDictOptions } from '@/utils/dict'
-import { defaultProps, handleTree } from '@/utils/tree'
-import * as DeptApi from '@/api/system/dept'
-import * as UserApi from '@/api/system/user'
-import { CommonStatusEnum } from '@/utils/constants'
-import { FormRules } from 'element-plus'
+import { ref, reactive, watch } from 'vue';
+import { useI18n } from 'vue-i18n';
+import { useMessage } from '@/hooks/web/useMessage';
+import * as DeptApi from '@/api/system/dept';
+import * as UserApi from '@/api/system/user';
+import { FormRules } from 'element-plus';
 
-defineOptions({ name: 'SystemDeptForm' })
+const { t } = useI18n();
+const message = useMessage();
 
-const { t } = useI18n() // 国际化
-const message = useMessage() // 消息弹窗
+// Props and Emits
+const props = defineProps(['visible']);
+const emit = defineEmits(['update:visible', 'success']);
 
-const dialogVisible = ref(false) // 弹窗的是否展示
-const dialogTitle = ref('') // 弹窗的标题
-const formLoading = ref(false) // 表单的加载中:1)修改时的数据加载;2)提交的按钮禁用
-const formType = ref('') // 表单的类型:create - 新增;update - 修改
+const dialogVisible = ref(props.visible);
+const dialogTitle = ref('修改工作间信息');
+const formLoading = ref(false);
 const formData = ref({
   id: undefined,
-  title: '',
-  parentId: 0,
-  name: undefined,
-  // sort: undefined,
-  leaderUserId: [],
-  phone: undefined,
-  email: undefined,
-  status: CommonStatusEnum.ENABLE,
-  // createTime: undefined,
-  address: undefined,
+  name: '',
+  phone: '',
+  email: '',
+  address: '',
   description: '',
-})
+});
+
 const formRules = reactive<FormRules>({
-  parentId: [{ required: true, message: '上级部门不能为空', trigger: 'blur' }],
   name: [{ required: true, message: '工作间名称不能为空', trigger: 'blur' }],
-  // sort: [{ required: true, message: '显示排序不能为空', trigger: 'blur' }],
-  leaderUserId: [{ required: true, message: '负责人不能为空', trigger: 'change' }],
-  email: [{ type: 'email', message: '请输入正确的邮箱地址', trigger: ['blur', 'change'] }],
   phone: [
+    { required: true, message: '联系电话不能为空', trigger: 'blur' },
     { pattern: /^1[3|4|5|6|7|8|9][0-9]\d{8}$/, message: '请输入正确的手机号码', trigger: 'blur' }
   ],
-  status: [{ required: true, message: '状态不能为空', trigger: 'blur' }]
-})
-const formRef = ref() // 表单 Ref
-const deptTree = ref() // 树形结构
-const userList = ref<UserApi.UserVO[]>([]) // 用户列表
+  email: [{ required: true, message: '邮箱不能为空', trigger: 'blur' }, { type: 'email', message: '请输入正确的邮箱地址', trigger: ['blur', 'change'] }],
+  address: [{ required: true, message: '工作间地址不能为空', trigger: 'blur' }],
+  description: [{ required: false, message: '简介不能为空', trigger: 'blur' }],
+});
+
+
 
-/** 打开弹窗 */
-const open = async (type: string, id?: number) => {
+const formRef = ref();
+
+const open = async () => {
   dialogVisible.value = true
-  dialogTitle.value = t('action.' + type)
-  formType.value = type
-  resetForm()
-  // 修改时,设置数据
-  if (id) {
-    formLoading.value = true
+  formLoading.value = true
     try {
-      // formData.value = await DeptApi.getDept(id)
-      const response = await DeptApi.getDept(id);
+      const response = await DeptApi.getUserDept();
       formData.value = {
         id: response.id,
-        title: response.title,
-        parentId: response.parentId,
         name: response.name,
-        leaderUserId: response.leaderUserId,
         phone: response.phone,
         email: response.email,
-        status: response.status,
         address: response.address,
         description: response.description || '' // 确保为字符串
       }
     } finally {
       formLoading.value = false
-    }
   }
-  // 获得用户列表
-  userList.value = await UserApi.getSimpleUserList()
-  // 获得部门树
-  await getTree()
-}
-defineExpose({ open }) // 提供 open 方法,用于打开弹窗
+};
+defineExpose({ open });
 
-//获取所有导师
-const users = ref()
-const getSupervisor= async () => {
-  try {
-    const response = await UserApi.getSupervisor()
-    users.value = response
-    console.log(response)
-  } catch (error) {
-    console.error('Error fetching user data:', error)
-  }
-}
-//传supervisorId给formData.leaderUserId
-const handleSupervisorChange = (values) => {
-  formData.value.leaderUserId = values;  // values 是选择的用户ID数组
-  // 如有需要,可以进行其他相关的处理
-}
-
-/** 提交表单 */
-const emit = defineEmits(['success']) // 定义 success 事件,用于操作成功后的回调
 const submitForm = async () => {
-  // 校验表单
-  if (!formRef) return
-  const valid = await formRef.value.validate()
-  if (!valid) return
-  // 提交请求
-  formLoading.value = true
+  if (!formRef.value) return;
+  const valid = await formRef.value.validate();
+  if (!valid) return;
+  formLoading.value = true;
   try {
-    const data = formData.value as unknown as DeptApi.DeptVO
-    if (formType.value === 'create') {
-      await DeptApi.createDept(data)
-      message.success(t('common.createSuccess'))
-    } else {
-      await DeptApi.updateDept(data)
-      message.success(t('common.updateSuccess'))
-    }
-    dialogVisible.value = false
-    // 发送操作成功的事件
-    emit('success')
+    const data = formData.value as unknown as DeptApi.DeptVO;
+    await DeptApi.updateDept(data);
+    message.success(t('common.updateSuccess'));
+    dialogVisible.value = false;
+    emit('success');
   } finally {
-    formLoading.value = false
+    formLoading.value = false;
   }
-}
+};
 
-/** 重置表单 */
-const resetForm = () => {
-  formData.value = {
-    id: undefined,
-    title: '',
-    parentId: 0,
-    name: undefined,
-    // sort: undefined,
-    leaderUserId: [],
-    phone: undefined,
-    email: undefined,
-    status: CommonStatusEnum.ENABLE,
-    address: undefined,
-    // createTime: undefined,
-    description: ''
-  }
-  formRef.value?.resetFields()
-}
+const handleClose = () => {
+  emit('update:visible', false);
+  dialogVisible.value = false;
+};
 
-/** 获得部门树 */
-const getTree = async () => {
-  deptTree.value = []
-  const data = await DeptApi.getSimpleDeptList()
-  let dept: Tree = { id: 0, name: '测绘学院', children: [] }
-  dept.children = handleTree(data)
-  deptTree.value.push(dept)
-}
+watch(() => props.visible, (newVal) => {
+  dialogVisible.value = newVal;
+});
+
+// 获取用户列表
+const users = ref([]);
+const getSupervisor = async () => {
+  try {
+    const response = await UserApi.getSupervisor();
+    users.value = response;
+  } catch (error) {
+    console.error('Error fetching user data:', error);
+  }
+};
 
 onMounted(() => {
-  getSupervisor()
-})
-</script>
+  getSupervisor();
+});
+</script>

+ 66 - 36
src/views/system/workroomTeacher/dept/index.vue

@@ -66,9 +66,18 @@
           <div class="div-label" style="margin-left: 20px;">简介:</div>
           <div class="description-content">{{ cleanedDescription }}</div>
         </div>
-        <!-- <el-button type="primary" @click="openDialog">修改</el-button> -->
+        <div class="button-container">
+          <el-button type="primary" @click="openDialog">修改</el-button>
+        </div>
       </el-card>
-       <!-- <DeptForm ref="formRef" @success="getList" /> -->
+      <DeptForm
+        ref="formRef"
+        :visible="dialogVisible"
+        :form="form"
+        :rules="rules"
+        @update:visible="dialogVisible = $event"
+        @success="handleSuccess"
+      />
     <!-- <el-card class="workspace-info ml-3 w-2/3">
       <template #header>
         <div class="card-header">
@@ -141,11 +150,16 @@ import { useI18n } from 'vue-i18n';
 import { useMessage } from '@/hooks/web/useMessage';
 import { updateDept, DeptVO, getUserDept } from '@/api/system/dept/index';
 import * as UserApi from '@/api/system/user'
+import DeptForm from './DeptForm.vue';
 
 export default defineComponent({
+  components: {
+    DeptForm
+  },
   setup() {
     const { t } = useI18n();
     const message = useMessage();
+    const dialogVisible = ref(false);
     const formRef = ref();
 
     const form = reactive({
@@ -202,37 +216,46 @@ export default defineComponent({
       };
     };
 
-  //获取所有导师
-const users = ref()
-const getSupervisor= async () => {
-  try {
-    const response = await UserApi.getSupervisor()
-    users.value = response
-  } catch (error) {
-    console.error('Error fetching user data:', error)
-  }
-}
-
-//传supervisorId给form.leaderUserId
-const handleSupervisorChange = (values) => {
-  form.leaderUserId = values;  // values 是选择的用户ID数组
-}
-
-const isEditMode = ref(false);
+//   //获取所有导师
+// const users = ref()
+// const getSupervisor= async () => {
+//   try {
+//     const response = await UserApi.getSupervisor()
+//     users.value = response
+//   } catch (error) {
+//     console.error('Error fetching user data:', error)
+//   }
+// }
+
+// //传supervisorId给form.leaderUserId
+// const handleSupervisorChange = (values) => {
+//   form.leaderUserId = values;  // values 是选择的用户ID数组
+// }
+
+// const isEditMode = ref(false);
+
+// // 切换编辑模式
+// const toggleEditMode = () => {
+//   if (isEditMode.value) {
+//     // 在“保存”状态下执行保存操作
+//     submit();
+//   }
+//   isEditMode.value = !isEditMode.value;
+// };
+
+const openDialog = () => {
+  dialogVisible.value = true;
+  formRef.value.open(); // 打开弹窗
+};
 
-// 切换编辑模式
-const toggleEditMode = () => {
-  if (isEditMode.value) {
-    // 在“保存”状态下执行保存操作
-    submit();
-  }
-  isEditMode.value = !isEditMode.value;
+const handleSuccess = () => {
+      dialogVisible.value = false;
 };
 
 // 创建一个 computed 属性来处理并去掉 <p> 标签
   const cleanedDescription = computed(() => {
-     return userInfo.value.description ? userInfo.value.description.replace(/<\/?p[^>]*>/g, '') : '';
-  });
+  return userInfo.value.description ? userInfo.value.description.replace(/<\/?[^>]+(>|$)/g, '') : '';
+});
 
 
     // 表单提交
@@ -269,7 +292,7 @@ const toggleEditMode = () => {
     onMounted(async () => {
       await init();
       await fetchUserInfo();
-      getSupervisor();
+      // getSupervisor();
 
     });
 
@@ -277,16 +300,19 @@ const toggleEditMode = () => {
       t,
       form,
       userInfo,
-      isEditMode,
-      toggleEditMode,
+      // isEditMode,
+      // toggleEditMode,
       submit,
       init,
       rules,
       formRef,
-      users,
-      handleSupervisorChange,
-      getSupervisor,
-      cleanedDescription
+      // users,
+      // handleSupervisorChange,
+      // getSupervisor,
+      cleanedDescription,
+      dialogVisible,
+      openDialog,
+      handleSuccess,
     };
   }
 });
@@ -387,5 +413,9 @@ const toggleEditMode = () => {
   margin-top: 20px;
 }
 
-
+.button-container {
+  display: flex;
+  justify-content: center; /* 水平居中 */
+  margin-top: 30px; /* 上间距 */
+}
 </style>

+ 11 - 4
src/views/system/workroomTeacher/user/UserForm.vue

@@ -6,6 +6,7 @@
       :model="formData"
       :rules="formRules"
       label-width="80px"
+      
     >
       <el-row>
         <el-col :span="12">
@@ -157,7 +158,7 @@
     </el-form>
     <template #footer>
       <el-button :disabled="formLoading" type="primary" @click="submitForm">确 定</el-button>
-      <el-button @click="dialogVisible = false">取 消</el-button>
+      <el-button  @click="handleClose">取 消</el-button>
     </template>
   </Dialog>
 </template>
@@ -254,14 +255,14 @@ const handleSupervisorChange = (value: number) => {
 
 /** 打开弹窗 */
 const open = async (type: string, id?: number) => {
-  dialogVisible.value = true
+  dialogVisible.value = true;
   if (type === 'create-S' || type === 'create-T') {
     dialogTitle.value = '新增'
   } else if (type === 'update-T' || type === 'update-S') {
     dialogTitle.value = '编辑'
   }
-  formType.value = type
-  resetForm()
+  formType.value = type;
+  resetForm();
   // 修改时,设置数据
   if (id) {
     formLoading.value = true
@@ -304,6 +305,12 @@ const submitForm = async () => {
   }
 }
 
+const handleClose = () => {
+  // console.log('Closing dialog. Current dialogVisible:', dialogVisible.value);
+  resetForm();
+  dialogVisible.value = false; 
+};
+
 /** 重置表单 */
 const resetForm = () => {
   formData.value = {