Merge remote-tracking branch 'origin/developer' into developer

This commit is contained in:
吴红兵
2026-02-24 17:21:29 +08:00
5 changed files with 86 additions and 110 deletions

View File

@@ -1,56 +1,79 @@
<template>
<el-dialog
v-model="visible"
title="角色切换"
:title="dialogTitle"
width="50%"
:show-close="false"
:close-on-click-modal="false"
:close-on-press-escape="false"
:before-close="handleBeforeClose"
center
>
<el-form>
<!-- <el-form-item label="学校">-->
<!-- <el-tag>{{schoolName}}</el-tag>-->
<!-- </el-form-item>-->
<el-form-item label="角色" class="role-form-item">
<el-form-item class="role-form-item">
<el-radio-group v-model="radio" class="role-radio-group" @change="handleChangeRole">
<el-radio-button
v-for="item in allRole"
:key="item.roleCode"
:label="item.roleCode"
>
{{ item.roleName }}
</el-radio-button>
<template v-for="(roles, groupName) in allRoleGroups" :key="groupName">
<div class="role-group">
<el-divider>{{ groupName }}</el-divider>
<el-radio-button
v-for="item in roles"
:key="item.roleCode"
:label="item.roleCode"
>
{{ item.roleName }}
</el-radio-button>
</div>
</template>
</el-radio-group>
</el-form-item>
</el-form>
<template #footer>
<!-- <el-button type="primary" @click="handleChangeRole">切换</el-button>-->
<template v-if="!requireSelectToClose" #footer>
<el-button @click="handleFooterClose"> </el-button>
</template>
</el-dialog>
</template>
<script setup lang="ts">
import { ref, computed, toRef } from 'vue'
import { listAllRole } from '/@/api/admin/role'
import { Local } from '/@/utils/storage'
import { useMessage } from '/@/hooks/message'
/** 弹框标题,如「角色切换」「登录角色选择」 */
const props = withDefaults(
defineProps<{ title?: string; requireSelectToClose?: boolean }>(),
{ title: '角色切换', requireSelectToClose: false }
)
const dialogTitle = computed(() => props.title)
const visible = ref(false)
const radio = ref('')
const allRole = reactive<any[]>([])
/** 按分组名分组的角色列表:{ "未分组": [{ roleId, roleName, roleCode, ... }], ... } */
const allRoleGroups = ref<Record<string, any[]>>({})
const requireSelectToClose = toRef(props, 'requireSelectToClose')
const open = () => {
if (visible.value) return
visible.value = true
listAllRole().then((res) => {
Object.assign(allRole, res.data)
allRoleGroups.value = res.data && typeof res.data === 'object' && !Array.isArray(res.data)
? res.data
: { '未分组': Array.isArray(res.data) ? res.data : [] }
radio.value = Local.get('roleCode')
visible.value = true
})
}
/** 根据 roleCode 从分组数据中查找角色 */
const findRoleByCode = (code: string) => {
for (const roles of Object.values(allRoleGroups.value)) {
if (!Array.isArray(roles)) continue
const found = roles.find((r: any) => r.roleCode === code)
if (found) return found
}
return null
}
const canClose = () => {
if (!radio.value) {
useMessage().warning('请选择一个角色')
@@ -60,6 +83,10 @@ const canClose = () => {
}
const handleBeforeClose = (done: () => void) => {
if (requireSelectToClose.value) {
useMessage().warning('请先选择登录角色')
return
}
if (!canClose()) return
done()
}
@@ -70,7 +97,7 @@ const handleFooterClose = () => {
}
const handleChangeRole = (label: string) => {
const obj = allRole.find((v: any) => v.roleCode === label)
const obj = findRoleByCode(label)
if (!obj) return
Local.set('roleCode', obj.roleCode)
Local.set('roleName', obj.roleName)
@@ -94,6 +121,18 @@ defineExpose({
flex-wrap: wrap;
}
}
.role-group {
margin-bottom: 12px;
&:last-child {
margin-bottom: 0;
}
}
.group-name {
font-size: 13px;
color: var(--el-text-color-secondary);
margin-bottom: 6px;
}
.role-radio-group {
display: flex;
flex-wrap: wrap;

View File

@@ -1,64 +0,0 @@
<template>
<el-dialog v-model="visible" width="50%" :close-on-click-modal="false" :close-on-press-escape="false" :show-close="false" center>
<template #title>
<div style="margin: 0 auto;width:100%;text-align:center;font-size:18px;font-weight:bold;">
登录角色选择
</div>
</template>
<div style="margin: 0 auto;width:100%;text-align:center;font-size:18px;font-weight:bold;">
<el-radio-group v-model="radio">
<el-radio-button v-for="(item,index) in allRole" :key="index" :label="item.roleCode" @click.native="handleChangeRole(item.roleCode)">{{item.roleName}}</el-radio-button>
</el-radio-group>
</div>
</el-dialog>
</template>
<script setup lang="ts">
import {listAllRole} from '/@/api/admin/role'
import {Local, Session} from '/@/utils/storage';
import {useMessage} from "/@/hooks/message";
// import {querySchoolName} from "/@/api/admin/tenant"
const visible=ref(false)
const radio=ref('')
const allRole = reactive<any[]>([])
const schoolName=ref('')
const open = () => {
listAllRole().then(res => {
Object.assign(allRole, res.data)
radio.value = Local.get('roleCode')
visible.value = true
})
}
// 必须选择角色后才能关闭,禁止点击遮罩/ESC 关闭(不调用 done 即不关闭)
const handleBeforeClose = (_done: () => void) => {
useMessage().warning('请先选择登录角色')
}
const handleChangeRole = (label: any) => {
let obj:any=allRole.find((v:any) => v.roleCode == label)
Local.set("roleCode",obj.roleCode)
Local.set("roleName",obj.roleName)
Local.set("roleId",obj.roleId)
useMessage().success("操作成功")
setTimeout(()=>{
window.location.reload()
},500)
}
// const handleQuerySchoolName=()=>{
// querySchoolName({id:Session.get("tenantId")}).then((res:any)=>{
// schoolName.value=res.data
// })
// }
defineExpose({
open
})
</script>
<style scoped>
</style>