UserForm.vue 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389
  1. <template>
  2. <Dialog v-model="dialogVisible" :title="dialogTitle">
  3. <el-form
  4. ref="formRef"
  5. v-loading="formLoading"
  6. :model="formData"
  7. :rules="formRules"
  8. label-width="80px"
  9. >
  10. <el-row>
  11. <el-col :span="12">
  12. <el-form-item label="姓名" prop="nickname">
  13. <el-input v-model="formData.nickname" placeholder="请输入姓名" />
  14. </el-form-item>
  15. </el-col>
  16. <el-col :span="12">
  17. <el-form-item label="用户性别">
  18. <el-select v-model="formData.sex" placeholder="请选择">
  19. <el-option
  20. v-for="dict in getIntDictOptions(DICT_TYPE.SYSTEM_USER_SEX)"
  21. :key="dict.value"
  22. :label="dict.label"
  23. :value="dict.value"
  24. />
  25. </el-select>
  26. </el-form-item>
  27. </el-col>
  28. </el-row>
  29. <el-row>
  30. <el-col :span="12">
  31. <el-form-item label="年级">
  32. <el-select v-model="formData.grade" placeholder="请选择">
  33. <el-option
  34. v-for="year in gradeOptions"
  35. :key="year"
  36. :label="year"
  37. :value="year"
  38. />
  39. </el-select>
  40. </el-form-item>
  41. </el-col>
  42. <el-col :span="12">
  43. <el-form-item label="学号" prop="userNumber">
  44. <el-input v-model="formData.userNumber" placeholder="请输入学号"/>
  45. </el-form-item>
  46. </el-col>
  47. </el-row>
  48. <el-row>
  49. <el-col :span="12">
  50. <el-form-item label="专业" prop="major">
  51. <!-- <el-input v-model="formData.major" placeholder="请输入专业" /> -->
  52. <el-select v-model="formData.major" placeholder="请选择专业">
  53. <el-option
  54. v-for="option in majorOptions"
  55. :key="option.value"
  56. :label="option.value"
  57. :value="option.value"
  58. />
  59. </el-select>
  60. </el-form-item>
  61. </el-col>
  62. <el-col :span="12">
  63. <el-form-item label="专硕" prop="masterType">
  64. <!-- <el-input v-model="formData.masterType" placeholder="请输入学位类型" /> -->
  65. <el-select v-model="formData.masterType" placeholder="请选择学位类型">
  66. <el-option
  67. v-for="option in masterTypeOptions"
  68. :key="option.value"
  69. :label="option.value"
  70. :value="option.value"
  71. />
  72. </el-select>
  73. </el-form-item>
  74. </el-col>
  75. </el-row>
  76. <el-row>
  77. <el-col :span="12">
  78. <el-form-item label="手机号码" prop="mobile">
  79. <el-input v-model="formData.mobile" maxlength="11" placeholder="请输入手机号码" />
  80. </el-form-item>
  81. </el-col>
  82. <el-col :span="12">
  83. <el-form-item label="邮箱" prop="email">
  84. <el-input v-model="formData.email" maxlength="50" placeholder="请输入邮箱" />
  85. </el-form-item>
  86. </el-col>
  87. </el-row>
  88. <el-row>
  89. <!-- <el-col :span="12">
  90. <el-form-item label="工作间" prop="deptId" v-if="userInfo.userType === '4'">
  91. <el-tree-select
  92. v-model="formData.deptId"
  93. :data="deptList"
  94. :props="defaultProps"
  95. check-strictly
  96. node-key="id"
  97. placeholder="请选择归属工作间"
  98. />
  99. </el-form-item>
  100. </el-col> -->
  101. <el-col :span="12">
  102. <el-form-item label="用户类型" prop="userType">
  103. <!-- <span style="margin-left: 10px;">毕业生</span>
  104. <input v-model="formData.userType" value="2" hidden /> -->
  105. <el-input v-model="userTypeG" value="毕业生" disabled />
  106. </el-form-item>
  107. </el-col>
  108. <el-col :span="12">
  109. <el-form-item label="工作地点" prop="workPlace">
  110. <el-input v-model="formData.workPlace" maxlength="11" placeholder="请输入工作地点" />
  111. </el-form-item>
  112. </el-col>
  113. </el-row>
  114. <el-row>
  115. <!-- <el-col :span="12">
  116. <el-form-item v-if="formData.id === undefined" label="账号" prop="username">
  117. <el-input v-model="formData.username" placeholder="请输入账号" />
  118. </el-form-item>
  119. </el-col> -->
  120. <el-col :span="12">
  121. <el-form-item label="导师名称" prop="supervisorId" v-if="userInfo.userType === '4'">
  122. <el-select
  123. v-model="formData.supervisor"
  124. @change="handleSupervisorChange"
  125. placeholder="请选择导师名称"
  126. clearable
  127. filterable
  128. class="!w-full"
  129. >
  130. <el-option
  131. v-for="user in users"
  132. :key="user.id"
  133. :label="user.nickname"
  134. :value="user.id"
  135. />
  136. </el-select>
  137. </el-form-item>
  138. </el-col>
  139. <!-- <el-col :span="12">
  140. <el-form-item v-if="formData.id === undefined" label="用户密码" prop="password">
  141. <el-input
  142. v-model="formData.password"
  143. placeholder="请输入用户密码"
  144. show-password
  145. type="password"
  146. />
  147. </el-form-item>
  148. </el-col> -->
  149. </el-row>
  150. <!-- <el-row>
  151. <el-col :span="24">
  152. <el-form-item label="导师电话" prop="supervisorMobile" v-if="userInfo.userType === '4'">
  153. <el-input v-model="formData.supervisorMobile" maxlength="11" placeholder="请输入导师电话" />
  154. </el-form-item>
  155. </el-col>
  156. </el-row> -->
  157. <el-row>
  158. <el-col :span="24">
  159. <el-form-item label="备注">
  160. <el-input v-model="formData.remark" placeholder="请输入内容" type="textarea" />
  161. </el-form-item>
  162. </el-col>
  163. </el-row>
  164. </el-form>
  165. <template #footer>
  166. <el-button :disabled="formLoading" type="primary" @click="submitForm">确 定</el-button>
  167. <el-button @click="dialogVisible = false">取 消</el-button>
  168. </template>
  169. </Dialog>
  170. </template>
  171. <script lang="ts" setup>
  172. import { DICT_TYPE, getIntDictOptions } from '@/utils/dict'
  173. import { CommonStatusEnum } from '@/utils/constants'
  174. import { defaultProps, handleTree } from '@/utils/tree'
  175. import * as PostApi from '@/api/system/post'
  176. import * as DeptApi from '@/api/system/dept'
  177. import * as UserApi from '@/api/system/user'
  178. import { FormRules } from 'element-plus'
  179. import { computed } from 'vue';
  180. import { getUserProfile, ProfileVO } from '@/api/system/user/profile'
  181. defineOptions({ name: 'SystemUserForm' })
  182. const { t } = useI18n() // 国际化
  183. const message = useMessage() // 消息弹窗
  184. const userInfo = ref({} as ProfileVO)
  185. const getUserInfo = async () => {
  186. const users = await getUserProfile()
  187. console.log(users)
  188. userInfo.value = users
  189. }
  190. const dialogVisible = ref(false) // 弹窗的是否展示
  191. const dialogTitle = ref('') // 弹窗的标题
  192. const formLoading = ref(false) // 表单的加载中:1)修改时的数据加载;2)提交的按钮禁用
  193. const formType = ref('') // 表单的类型:create - 新增;update - 修改
  194. const formData = ref({
  195. nickname: '',
  196. deptId: '',
  197. grade: '',
  198. userNumber: '',
  199. mobile: '',
  200. email: '',
  201. id: undefined,
  202. username: '',
  203. password: '',
  204. sex: undefined,
  205. postIds: [],
  206. remark: '',
  207. status: CommonStatusEnum.ENABLE,
  208. roleIds: [],
  209. userType: '',
  210. supervisor:'',
  211. supervisorId:'',
  212. supervisorMobile: '',
  213. workPlace:"",
  214. major: "",
  215. masterType: "",
  216. })
  217. const formRules = reactive<FormRules>({
  218. nickname: [{ required: true, message: '姓名不能为空', trigger: 'blur' }],
  219. email: [
  220. { required: true, message: '邮箱不能为空', trigger: 'blur' },
  221. {
  222. type: 'email',
  223. message: '请输入正确的邮箱地址',
  224. trigger: ['blur', 'change']
  225. }
  226. ],
  227. mobile: [
  228. { required: true, message: '手机号码不能为空', trigger: 'blur' },
  229. {
  230. pattern: /^(?:(?:\+|00)86)?1(?:3[\d]|4[5-79]|5[0-35-9]|6[5-7]|7[0-8]|8[\d]|9[189])\d{8}$/,
  231. message: '请输入正确的手机号码',
  232. trigger: 'blur'
  233. }
  234. ],
  235. userNumber: [{ required: true, message: '学号不能为空', trigger: 'blur' }],
  236. userType: [{ required: true, message: '用户类型不能为空', trigger: 'blur' }],
  237. })
  238. const formRef = ref() // 表单 Ref
  239. const deptList = ref<Tree[]>([]) // 树形结构
  240. const postList = ref([] as PostApi.PostVO[]) // 岗位列表
  241. //用户类型
  242. // const userTypes = ref([
  243. // { label: '本校生', value: "1" },
  244. // { label: '毕业生', value: "2" },
  245. // // { label: '导师', value: "3" },
  246. // // { label: '学院', value: "4" }
  247. // ]);
  248. const userTypeG = ref('2')
  249. const currentYear = new Date().getFullYear(); // 获取当前年份
  250. const gradeOptions = computed(() => {
  251. return [
  252. currentYear +'级', // 今年
  253. currentYear - 1 +'级', // 去年
  254. currentYear - 2 +'级', // 前年
  255. currentYear - 3 +'级', // 大前年
  256. currentYear - 4 +'级', // 大大前年
  257. ];
  258. });
  259. // 获取所有专业
  260. const majorOptions = [
  261. { value: '测绘工程' },
  262. { value: '测绘科学与技术' },
  263. { value: '资源与环境' },
  264. ]
  265. // 获取所有学位类型
  266. const masterTypeOptions = [
  267. { value: '学硕' },
  268. { value: '专硕' },
  269. ]
  270. //获取所有导师
  271. const users = ref()
  272. const getSupervisor= async () => {
  273. try {
  274. const response = await UserApi.getSupervisor()
  275. users.value = response
  276. } catch (error) {
  277. console.error('Error fetching user data:', error)
  278. }
  279. }
  280. //传supervisorId给formData.supervisorId
  281. const handleSupervisorChange = (value: number) => {
  282. const selectedUser = users.value.find(user => user.id === value);
  283. if (selectedUser) {
  284. formData.value.supervisorId = selectedUser.id;
  285. formData.value.supervisor = selectedUser.nickname;
  286. }
  287. }
  288. /** 打开弹窗 */
  289. const open = async (type: string, id?: number) => {
  290. dialogVisible.value = true
  291. dialogTitle.value = t('action.' + type)
  292. formType.value = type
  293. resetForm()
  294. // 修改时,设置数据
  295. if (id) {
  296. formLoading.value = true
  297. try {
  298. formData.value = await UserApi.getUser(id)
  299. } finally {
  300. formLoading.value = false
  301. }
  302. }
  303. // 加载部门树
  304. deptList.value = handleTree(await DeptApi.getSimpleDeptList())
  305. // 加载岗位列表
  306. postList.value = await PostApi.getSimplePostList()
  307. }
  308. defineExpose({ open }) // 提供 open 方法,用于打开弹窗
  309. /** 提交表单 */
  310. const emit = defineEmits(['success']) // 定义 success 事件,用于操作成功后的回调
  311. const submitForm = async () => {
  312. formData.value.userType = userTypeG.value
  313. if (formType.value === 'create') {
  314. formData.value.username = 'abc0123'
  315. formData.value.password = 'abc0123'
  316. }
  317. // 校验表单
  318. if (!formRef) return
  319. const valid = await formRef.value.validate()
  320. if (!valid) return
  321. // 提交请求
  322. formLoading.value = true
  323. try {
  324. const data = formData.value as unknown as UserApi.UserVO
  325. if (formType.value === 'create') {
  326. await UserApi.createUser(data)
  327. message.success(t('common.createSuccess'))
  328. } else {
  329. await UserApi.updateUser(data)
  330. message.success(t('common.updateSuccess'))
  331. }
  332. dialogVisible.value = false
  333. // 发送操作成功的事件
  334. emit('success')
  335. } finally {
  336. formLoading.value = false
  337. }
  338. }
  339. /** 重置表单 */
  340. const resetForm = () => {
  341. formData.value = {
  342. nickname: '',
  343. deptId: '',
  344. grade: '',
  345. userNumber: '',
  346. mobile: '',
  347. email: '',
  348. id: undefined,
  349. username: '',
  350. password: '',
  351. sex: undefined,
  352. postIds: [],
  353. remark: '',
  354. status: CommonStatusEnum.ENABLE,
  355. roleIds: [],
  356. userType: '',
  357. supervisor:'',
  358. supervisorId:'',
  359. supervisorMobile: '',
  360. workPlace:"",
  361. major: "",
  362. masterType: "",
  363. }
  364. formRef.value?.resetFields()
  365. }
  366. onMounted(() => {
  367. getSupervisor()
  368. getUserInfo()
  369. })
  370. </script>