yanghao 3 روز پیش
والد
کامیت
35b18a5cab
2فایلهای تغییر یافته به همراه146 افزوده شده و 5 حذف شده
  1. 120 0
      src/components/DeptSelectForm/qhseDept.vue
  2. 26 5
      src/views/pms/qhse/monthlyReport/MonthlyReportAdd.vue

+ 120 - 0
src/components/DeptSelectForm/qhseDept.vue

@@ -0,0 +1,120 @@
+<template>
+  <Dialog v-model="dialogVisible" title="部门选择" width="600">
+    <el-row v-loading="formLoading">
+      <el-col :span="24">
+        <ContentWrap class="h-1/1">
+          <el-tree-select
+            ref="treeRef"
+            :data="deptTree"
+            :props="defaultProps"
+            show-checkbox
+            :check-strictly="true"
+            :multiple="false"
+            check-on-click-node
+            highlight-current
+            node-key="id"
+            @check="handleCheck" />
+        </ContentWrap>
+      </el-col>
+    </el-row>
+    <template #footer>
+      <el-button
+        :disabled="formLoading || !selectedDeptIds?.length"
+        type="primary"
+        @click="submitForm">
+        确 定
+      </el-button>
+      <el-button @click="dialogVisible = false">取 消</el-button>
+    </template>
+  </Dialog>
+</template>
+
+<script lang="ts" setup>
+import { defaultProps, handleTree } from '@/utils/tree'
+import * as DeptApi from '@/api/system/dept'
+
+defineOptions({ name: 'DeptSelectForm' })
+
+const emit = defineEmits<{
+  confirm: [deptList: any[]]
+}>()
+
+const { t } = useI18n() // 国际化
+const message = useMessage() // 消息弹窗
+
+const props = defineProps({
+  // 是否严格的遵循父子不互相关联
+  checkStrictly: {
+    type: Boolean,
+    default: false
+  },
+  // 是否支持多选
+  multiple: {
+    type: Boolean,
+    default: false
+  }
+})
+
+const treeRef = ref()
+const deptTree = ref<Tree[]>([]) // 部门树形结构
+const selectedDeptIds = ref<number[]>([]) // 选中的部门 ID 列表
+const dialogVisible = ref(false) // 弹窗的是否展示
+const formLoading = ref(false) // 表单的加载中
+
+/** 打开弹窗 */
+const open = async (selectedList?: DeptApi.DeptVO[]) => {
+  resetForm()
+  formLoading.value = true
+  try {
+    // 加载部门列表
+    const deptData = await DeptApi.getSimpleDeptList()
+    deptTree.value = handleTree(deptData)
+  } finally {
+    formLoading.value = false
+  }
+  dialogVisible.value = true
+  // 设置已选择的部门
+  if (selectedList?.length) {
+    await nextTick()
+    const selectedIds = selectedList
+      .map((dept) => dept.id)
+      .filter((id): id is number => id !== undefined)
+    selectedDeptIds.value = selectedIds
+    treeRef.value?.setCheckedKeys(selectedIds)
+  }
+}
+
+/** 处理选中状态变化 */
+const handleCheck = (data: any, checked: any) => {
+  selectedDeptIds.value = treeRef.value.getCheckedKeys()
+  if (!props.multiple && selectedDeptIds.value.length > 1) {
+    // 单选模式下,只保留最后选择的节点
+    const lastSelectedId = selectedDeptIds.value[selectedDeptIds.value.length - 1]
+    selectedDeptIds.value = [lastSelectedId]
+    treeRef.value.setCheckedKeys([lastSelectedId])
+  }
+}
+
+/** 提交选择 */
+const submitForm = async () => {
+  try {
+    // 获取选中的完整部门数据
+    const checkedNodes = treeRef.value.getCheckedNodes()
+    message.success(t('common.updateSuccess'))
+    dialogVisible.value = false
+    emit('confirm', checkedNodes)
+  } finally {
+  }
+}
+
+/** 重置表单 */
+const resetForm = () => {
+  deptTree.value = []
+  selectedDeptIds.value = []
+  if (treeRef.value) {
+    treeRef.value.setCheckedKeys([])
+  }
+}
+
+defineExpose({ open }) // 提供 open 方法,用于打开弹窗
+</script>

+ 26 - 5
src/views/pms/qhse/monthlyReport/MonthlyReportAdd.vue

@@ -17,7 +17,7 @@
         <el-row :gutter="20">
           <el-col :span="12">
             <el-form-item label="部门名称" prop="deptId">
-              <el-input
+              <!-- <el-input
                 v-model="deptName"
                 placeholder="请选择部门"
                 readonly
@@ -25,7 +25,17 @@
                 <template #suffix>
                   <Icon icon="ep:search" class="cursor-pointer" />
                 </template>
-              </el-input>
+              </el-input> -->
+
+              <el-tree-select
+                clearable
+                v-model="formData.deptId"
+                :data="deptList2"
+                :props="defaultProps"
+                :check-strictly="false"
+                node-key="id"
+                filterable
+                placeholder="请选择所属队伍" />
             </el-form-item>
           </el-col>
           <el-col :span="12">
@@ -449,10 +459,14 @@
     </el-form>
 
     <!-- 部门选择弹窗 -->
-    <DeptSelectForm ref="deptSelectFormRef" :multiple="false" @confirm="handleDeptConfirm" />
+    <!-- <DeptSelectForm
+      ref="deptSelectFormRef"
+      :checkStrictly="true"
+      :multiple="false"
+      @confirm="handleDeptConfirm" /> -->
 
     <!-- 用户选择弹窗 -->
-    <UserSelectForm ref="userSelectFormRef" @confirm="handleUserConfirm" />
+    <UserSelectForm ref="userSelectFormRef" :multiple="false" @confirm="handleUserConfirm" />
   </div>
 </template>
 
@@ -461,8 +475,11 @@ import { reactive, ref } from 'vue'
 import { useRouter } from 'vue-router'
 import { FormInstance, FormRules } from 'element-plus'
 import { QhseMonthReportApi } from '@/api/pms/qhse'
-import DeptSelectForm from '@/components/DeptSelectForm/index.vue'
+// import DeptSelectForm from '@/components/DeptSelectForm/qhseDept.vue'
 import UserSelectForm from '@/components/UserSelectForm/index.vue'
+import { handleTree, defaultProps } from '@/utils/tree'
+import * as DeptApi from '@/api/system/dept'
+const deptList2 = ref<Tree[]>([]) // 树形结构
 
 defineOptions({ name: 'MonthlyReportAdd' })
 
@@ -585,6 +602,10 @@ const handleSubmit = async () => {
 const handleCancel = () => {
   router.back()
 }
+
+onMounted(async () => {
+  deptList2.value = handleTree(await DeptApi.getSimpleDeptList())
+})
 </script>
 
 <style scoped lang="scss">