| ¶Ô±ÈÐÂÎļþ |
| | |
| | | <template> |
| | | <div class="app-container"> |
| | | <!-- æç´¢è¡¨å --> |
| | | <div class="search_form"> |
| | | <div class="search-row"> |
| | | <div class="search-left"> |
| | | <div class="search-item"> |
| | | <span class="search_title">çç»åç§°ï¼</span> |
| | | <el-input v-model="searchForm.teamName" |
| | | style="width: 240px" |
| | | placeholder="请è¾å
¥" |
| | | @change="handleQuery" |
| | | clearable |
| | | prefix-icon="Search" /> |
| | | </div> |
| | | <div class="search-item"> |
| | | <el-button type="primary" |
| | | @click="handleQuery">æç´¢</el-button> |
| | | </div> |
| | | </div> |
| | | <div class="search-right"> |
| | | <el-button type="primary" |
| | | @click="handleAdd">æ°å¢</el-button> |
| | | <el-button type="danger" |
| | | plain |
| | | :disabled="!selectedIds.length" |
| | | @click="handleBatchDelete">å é¤</el-button> |
| | | </div> |
| | | </div> |
| | | </div> |
| | | |
| | | <!-- è¡¨æ ¼æ°æ® --> |
| | | <div class="table_list"> |
| | | <PIMTable rowKey="id" |
| | | :column="tableColumn" |
| | | :tableData="tableData" |
| | | :page="page" |
| | | :tableLoading="tableLoading" |
| | | @pagination="pagination" |
| | | :isSelection="true" |
| | | @selection-change="handleSelectionChange"> |
| | | <template #members="{ row }"> |
| | | <el-tag |
| | | v-for="member in getNonLeaderMembers(row)" |
| | | :key="member.userId" |
| | | type="info" |
| | | size="small" |
| | | style="margin-right: 4px" |
| | | >{{ member.nickName }}</el-tag> |
| | | <span v-if="!getNonLeaderMembers(row).length" class="text-gray">ææ æå</span> |
| | | </template> |
| | | </PIMTable> |
| | | </div> |
| | | |
| | | <!-- æ·»å æä¿®æ¹çç»å¯¹è¯æ¡ --> |
| | | <el-dialog :title="title" v-model="open" width="500px" append-to-body> |
| | | <el-form ref="teamRef" :model="form" :rules="rules" label-width="100px"> |
| | | <el-form-item label="çç»åç§°" prop="teamName"> |
| | | <el-input v-model="form.teamName" placeholder="请è¾å
¥çç»åç§°" /> |
| | | </el-form-item> |
| | | <el-form-item label="çç»é¿" prop="leaderId"> |
| | | <el-select |
| | | v-model="form.leaderId" |
| | | placeholder="è¯·éæ©çç»é¿" |
| | | style="width: 100%" |
| | | clearable |
| | | filterable |
| | | > |
| | | <el-option |
| | | v-for="user in userList" |
| | | :key="user.userId" |
| | | :label="user.nickName" |
| | | :value="user.userId" |
| | | /> |
| | | </el-select> |
| | | </el-form-item> |
| | | <el-form-item label="çç»æå" prop="memberIds"> |
| | | <el-select |
| | | v-model="form.memberIds" |
| | | placeholder="è¯·éæ©çç»æåï¼ä¸å
å«çç»é¿ï¼" |
| | | style="width: 100%" |
| | | multiple |
| | | clearable |
| | | filterable |
| | | > |
| | | <el-option |
| | | v-for="user in availableMembers" |
| | | :key="user.userId" |
| | | :label="user.nickName" |
| | | :value="user.userId" |
| | | /> |
| | | </el-select> |
| | | </el-form-item> |
| | | <el-form-item label="夿³¨"> |
| | | <el-input v-model="form.remark" type="textarea" placeholder="请è¾å
¥å¤æ³¨"></el-input> |
| | | </el-form-item> |
| | | </el-form> |
| | | <template #footer> |
| | | <div class="dialog-footer"> |
| | | <el-button type="primary" @click="submitForm">ç¡® å®</el-button> |
| | | <el-button @click="cancel">å æ¶</el-button> |
| | | </div> |
| | | </template> |
| | | </el-dialog> |
| | | </div> |
| | | </template> |
| | | |
| | | <script setup name="ProductionTeam"> |
| | | import { ref, reactive, toRefs, onMounted, computed, watch } from "vue"; |
| | | import { |
| | | createTeam, |
| | | updateTeam, |
| | | deleteTeam, |
| | | getTeamDetail, |
| | | getTeamListPage, |
| | | } from "@/api/productionManagement/productionTeam.js"; |
| | | import { userListNoPageByTenantId } from "@/api/system/user.js"; |
| | | |
| | | const { proxy } = getCurrentInstance(); |
| | | |
| | | const tableColumn = ref([ |
| | | { |
| | | label: "çç»åç§°", |
| | | prop: "teamName", |
| | | width: "150", |
| | | }, |
| | | { |
| | | label: "çç»é¿", |
| | | prop: "leaderName", |
| | | width: "120", |
| | | }, |
| | | { |
| | | label: "çç»æå", |
| | | dataType: "slot", |
| | | slot: "members", |
| | | }, |
| | | { |
| | | label: "åå»ºæ¥æ", |
| | | prop: "createTime", |
| | | width: "180", |
| | | }, |
| | | { |
| | | label: "夿³¨", |
| | | prop: "remark", |
| | | }, |
| | | { |
| | | label: "æä½", |
| | | width: "180", |
| | | align: "center", |
| | | dataType: "action", |
| | | fixed: "right", |
| | | operation: [ |
| | | { |
| | | name: "ç¼è¾", |
| | | clickFun: (row) => { |
| | | handleUpdate(row); |
| | | }, |
| | | }, |
| | | { |
| | | name: "å é¤", |
| | | clickFun: (row) => { |
| | | handleDelete(row); |
| | | }, |
| | | }, |
| | | ], |
| | | }, |
| | | ]); |
| | | |
| | | const tableData = ref([]); |
| | | const tableLoading = ref(false); |
| | | const open = ref(false); |
| | | const title = ref(""); |
| | | const userList = ref([]); |
| | | const selectedIds = ref([]); |
| | | |
| | | // å¯éæ©çæååè¡¨ï¼æé¤çç»é¿ï¼ |
| | | const availableMembers = computed(() => { |
| | | if (!form.value.leaderId) { |
| | | return userList.value; |
| | | } |
| | | return userList.value.filter(user => user.userId !== form.value.leaderId); |
| | | }); |
| | | |
| | | const page = reactive({ |
| | | current: 1, |
| | | size: 10, |
| | | total: 0, |
| | | }); |
| | | |
| | | const data = reactive({ |
| | | form: {}, |
| | | searchForm: { |
| | | teamName: "", |
| | | }, |
| | | rules: { |
| | | teamName: [{ required: true, message: "çç»åç§°ä¸è½ä¸ºç©º", trigger: "blur" }], |
| | | leaderId: [{ required: true, message: "è¯·éæ©çç»é¿", trigger: "blur" }], |
| | | }, |
| | | }); |
| | | |
| | | const { searchForm, form, rules } = toRefs(data); |
| | | |
| | | /** æ¥è¯¢çç»å表 */ |
| | | function getList() { |
| | | tableLoading.value = true; |
| | | const params = { ...searchForm.value, ...page }; |
| | | getTeamListPage(params).then((response) => { |
| | | tableData.value = response.data?.records || response.data || []; |
| | | page.total = response.data?.total || (response.data?.length || 0); |
| | | tableLoading.value = false; |
| | | }).catch(() => { |
| | | tableLoading.value = false; |
| | | }); |
| | | } |
| | | |
| | | /** æç´¢æé®æä½ */ |
| | | function handleQuery() { |
| | | page.current = 1; |
| | | getList(); |
| | | } |
| | | |
| | | /** å页æä½ */ |
| | | function pagination(obj) { |
| | | page.current = obj.page; |
| | | page.size = obj.limit; |
| | | getList(); |
| | | } |
| | | |
| | | /** å é¤æé®æä½ */ |
| | | function handleDelete(row) { |
| | | proxy.$modal.confirm(`æ¯å¦ç¡®è®¤å é¤çç»"${row.teamName}"?`).then(function () { |
| | | return deleteTeam(row.id); |
| | | }).then(() => { |
| | | getList(); |
| | | proxy.$modal.msgSuccess("å 餿å"); |
| | | }).catch(() => {}); |
| | | } |
| | | |
| | | /** æ¹éå é¤ */ |
| | | function handleBatchDelete() { |
| | | if (!selectedIds.value.length) { |
| | | proxy.$modal.msgWarning("è¯·éæ©è¦å é¤ççç»"); |
| | | return; |
| | | } |
| | | proxy.$modal.confirm(`æ¯å¦ç¡®è®¤å é¤éä¸ç${selectedIds.value.length}个çç»?`).then(function () { |
| | | // æ¹éå é¤ï¼ä¾æ¬¡å 餿¯ä¸ªID |
| | | const deletePromises = selectedIds.value.map(id => deleteTeam(id)); |
| | | return Promise.all(deletePromises); |
| | | }).then(() => { |
| | | getList(); |
| | | selectedIds.value = []; |
| | | proxy.$modal.msgSuccess("å 餿å"); |
| | | }).catch(() => {}); |
| | | } |
| | | |
| | | /** å¤éæ¡é䏿°æ® */ |
| | | function handleSelectionChange(selection) { |
| | | selectedIds.value = selection.map((item) => item.id); |
| | | } |
| | | |
| | | /** è·åéçç»é¿çæåå表 */ |
| | | function getNonLeaderMembers(row) { |
| | | if (!row.members || !row.leaderId) { |
| | | return row.members || []; |
| | | } |
| | | return row.members.filter(m => m.userId !== row.leaderId); |
| | | } |
| | | |
| | | /** è·åç¨æ·å表 */ |
| | | function getUserList() { |
| | | userListNoPageByTenantId().then((response) => { |
| | | if (response.code === 200) { |
| | | userList.value = response.data || []; |
| | | } |
| | | }); |
| | | } |
| | | |
| | | /** é置表å */ |
| | | function reset() { |
| | | form.value = { |
| | | id: undefined, |
| | | teamName: undefined, |
| | | leaderId: undefined, |
| | | memberIds: [], |
| | | remark: undefined, |
| | | }; |
| | | proxy.resetForm("teamRef"); |
| | | } |
| | | |
| | | /** æ·»å çç» */ |
| | | function handleAdd() { |
| | | reset(); |
| | | open.value = true; |
| | | title.value = "æ·»å çç»"; |
| | | } |
| | | |
| | | /** ä¿®æ¹çç» */ |
| | | function handleUpdate(row) { |
| | | reset(); |
| | | getTeamDetail(row.id).then((response) => { |
| | | form.value = response.data; |
| | | // è¿æ»¤æçç»é¿ï¼åªä¿çæ®éæå |
| | | form.value.memberIds = response.data.members |
| | | .filter(m => m.userId !== response.data.leaderId) |
| | | .map((m) => m.userId); |
| | | open.value = true; |
| | | }); |
| | | title.value = "ä¿®æ¹çç»"; |
| | | } |
| | | |
| | | // çå¬çç»é¿ååï¼èªå¨ä»æåå表ä¸ç§»é¤çç»é¿ |
| | | watch(() => form.value.leaderId, (newLeaderId, oldLeaderId) => { |
| | | if (newLeaderId && form.value.memberIds) { |
| | | form.value.memberIds = form.value.memberIds.filter(id => id !== newLeaderId); |
| | | } |
| | | }); |
| | | |
| | | /** æäº¤æé® */ |
| | | function submitForm() { |
| | | proxy.$refs["teamRef"].validate((valid) => { |
| | | if (valid) { |
| | | const submitData = { |
| | | id: form.value.id, |
| | | teamName: form.value.teamName, |
| | | leaderId: form.value.leaderId, |
| | | memberIds: form.value.memberIds || [], |
| | | remark: form.value.remark, |
| | | }; |
| | | if (form.value.id != undefined) { |
| | | updateTeam(submitData).then((response) => { |
| | | proxy.$modal.msgSuccess("ä¿®æ¹æå"); |
| | | open.value = false; |
| | | getList(); |
| | | }); |
| | | } else { |
| | | createTeam(submitData).then((response) => { |
| | | proxy.$modal.msgSuccess("æ°å¢æå"); |
| | | open.value = false; |
| | | getList(); |
| | | }); |
| | | } |
| | | } |
| | | }); |
| | | } |
| | | |
| | | /** åæ¶æé® */ |
| | | function cancel() { |
| | | open.value = false; |
| | | reset(); |
| | | } |
| | | |
| | | onMounted(() => { |
| | | getList(); |
| | | getUserList(); |
| | | }); |
| | | </script> |
| | | |
| | | <style scoped lang="scss"> |
| | | .search_form { |
| | | margin-bottom: 20px; |
| | | .search-row { |
| | | display: flex; |
| | | justify-content: space-between; |
| | | align-items: center; |
| | | width: 100%; |
| | | } |
| | | .search-left { |
| | | display: flex; |
| | | gap: 20px; |
| | | align-items: center; |
| | | .search-item { |
| | | display: flex; |
| | | align-items: center; |
| | | gap: 10px; |
| | | } |
| | | } |
| | | .search-right { |
| | | display: flex; |
| | | gap: 10px; |
| | | } |
| | | } |
| | | </style> |