| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344 |
- <script setup lang="ts">
- import { useRole } from "./utils/hook";
- import { ref, computed, nextTick, onMounted } from "vue";
- import { PureTableBar } from "@/components/RePureTableBar";
- import { useRenderIcon } from "@/components/ReIcon/src/hooks";
- import {
- delay,
- subBefore,
- deviceDetection,
- useResizeObserver
- } from "@pureadmin/utils";
- // import Database from "~icons/ri/database-2-line";
- // import More from "~icons/ep/more-filled";
- import Delete from "~icons/ep/delete";
- import EditPen from "~icons/ep/edit-pen";
- import Refresh from "~icons/ep/refresh";
- import Menu from "~icons/ep/menu";
- import AddFill from "~icons/ri/add-circle-line";
- import Close from "~icons/ep/close";
- import Check from "~icons/ep/check";
- defineOptions({
- name: "SystemRole"
- });
- const iconClass = computed(() => {
- return [
- "w-[22px]",
- "h-[22px]",
- "flex",
- "justify-center",
- "items-center",
- "outline-hidden",
- "rounded-[4px]",
- "cursor-pointer",
- "transition-colors",
- "hover:bg-[#0000000f]",
- "dark:hover:bg-[#ffffff1f]",
- "dark:hover:text-[#ffffffd9]"
- ];
- });
- const treeRef = ref();
- const formRef = ref();
- const tableRef = ref();
- const contentRef = ref();
- const treeHeight = ref();
- const {
- form,
- isShow,
- curRow,
- loading,
- columns,
- rowStyle,
- dataList,
- treeData,
- treeProps,
- isLinkage,
- pagination,
- isExpandAll,
- isSelectAll,
- treeSearchValue,
- // buttonClass,
- onSearch,
- resetForm,
- openDialog,
- handleMenu,
- handleSave,
- handleDelete,
- filterMethod,
- transformI18n,
- onQueryChanged,
- // handleDatabase,
- handleSizeChange,
- handleCurrentChange,
- handleSelectionChange
- } = useRole(treeRef);
- onMounted(() => {
- useResizeObserver(contentRef, async () => {
- await nextTick();
- delay(60).then(() => {
- treeHeight.value = parseFloat(
- subBefore(tableRef.value.getTableDoms().tableWrapper.style.height, "px")
- );
- });
- });
- });
- </script>
- <template>
- <div class="main">
- <el-form
- ref="formRef"
- :inline="true"
- :model="form"
- class="search-form bg-bg_color w-full pl-8 pt-[12px] overflow-auto"
- >
- <el-form-item label="角色名称:" prop="name">
- <el-input
- v-model="form.name"
- placeholder="请输入角色名称"
- clearable
- class="w-[180px]!"
- />
- </el-form-item>
- <el-form-item label="角色标识:" prop="code">
- <el-input
- v-model="form.code"
- placeholder="请输入角色标识"
- clearable
- class="w-[180px]!"
- />
- </el-form-item>
- <el-form-item label="状态:" prop="status">
- <el-select
- v-model="form.status"
- placeholder="请选择状态"
- clearable
- class="w-[180px]!"
- >
- <el-option label="已启用" value="1" />
- <el-option label="已停用" value="0" />
- </el-select>
- </el-form-item>
- <el-form-item>
- <el-button
- type="primary"
- :icon="useRenderIcon('ri/search-line')"
- :loading="loading"
- @click="onSearch"
- >
- 搜索
- </el-button>
- <el-button :icon="useRenderIcon(Refresh)" @click="resetForm(formRef)">
- 重置
- </el-button>
- </el-form-item>
- </el-form>
- <div
- ref="contentRef"
- :class="['flex', deviceDetection() ? 'flex-wrap' : '']"
- >
- <PureTableBar
- :class="[isShow && !deviceDetection() ? 'w-[60vw]!' : 'w-full']"
- style="transition: width 220ms cubic-bezier(0.4, 0, 0.2, 1)"
- title="角色管理(仅演示,操作后不生效)"
- :columns="columns"
- @refresh="onSearch"
- >
- <template #buttons>
- <el-button
- type="primary"
- :icon="useRenderIcon(AddFill)"
- @click="openDialog()"
- >
- 新增角色
- </el-button>
- </template>
- <template v-slot="{ size, dynamicColumns }">
- <pure-table
- ref="tableRef"
- align-whole="center"
- showOverflowTooltip
- table-layout="auto"
- :loading="loading"
- :size="size"
- adaptive
- :row-style="rowStyle"
- :adaptiveConfig="{ offsetBottom: 108 }"
- :data="dataList"
- :columns="dynamicColumns"
- :pagination="{ ...pagination, size }"
- :header-cell-style="{
- background: 'var(--el-fill-color-light)',
- color: 'var(--el-text-color-primary)'
- }"
- @selection-change="handleSelectionChange"
- @page-size-change="handleSizeChange"
- @page-current-change="handleCurrentChange"
- >
- <template #operation="{ row }">
- <el-button
- class="reset-margin"
- link
- type="primary"
- :size="size"
- :icon="useRenderIcon(EditPen)"
- @click="openDialog('修改', row)"
- >
- 修改
- </el-button>
- <el-popconfirm
- :title="`是否确认删除角色名称为${row.name}的这条数据`"
- @confirm="handleDelete(row)"
- >
- <template #reference>
- <el-button
- class="reset-margin"
- link
- type="primary"
- :size="size"
- :icon="useRenderIcon(Delete)"
- >
- 删除
- </el-button>
- </template>
- </el-popconfirm>
- <el-button
- class="reset-margin"
- link
- type="primary"
- :size="size"
- :icon="useRenderIcon(Menu)"
- @click="handleMenu(row)"
- >
- 权限
- </el-button>
- <!-- <el-dropdown>
- <el-button
- class="ml-3 mt-[2px]"
- link
- type="primary"
- :size="size"
- :icon="useRenderIcon(More)"
- />
- <template #dropdown>
- <el-dropdown-menu>
- <el-dropdown-item>
- <el-button
- :class="buttonClass"
- link
- type="primary"
- :size="size"
- :icon="useRenderIcon(Menu)"
- @click="handleMenu"
- >
- 菜单权限
- </el-button>
- </el-dropdown-item>
- <el-dropdown-item>
- <el-button
- :class="buttonClass"
- link
- type="primary"
- :size="size"
- :icon="useRenderIcon(Database)"
- @click="handleDatabase"
- >
- 数据权限
- </el-button>
- </el-dropdown-item>
- </el-dropdown-menu>
- </template>
- </el-dropdown> -->
- </template>
- </pure-table>
- </template>
- </PureTableBar>
- <div
- v-if="isShow"
- class="min-w-[calc(100vw-60vw-268px)]! w-full mt-2 px-2 pb-2 bg-bg_color ml-2 overflow-auto"
- >
- <div class="flex justify-between w-full px-3 pt-5 pb-4">
- <div class="flex">
- <span :class="iconClass">
- <IconifyIconOffline
- v-tippy="{
- content: '关闭'
- }"
- class="dark:text-white"
- width="18px"
- height="18px"
- :icon="Close"
- @click="handleMenu"
- />
- </span>
- <span :class="[iconClass, 'ml-2']">
- <IconifyIconOffline
- v-tippy="{
- content: '保存菜单权限'
- }"
- class="dark:text-white"
- width="18px"
- height="18px"
- :icon="Check"
- @click="handleSave"
- />
- </span>
- </div>
- <p class="font-bold truncate">
- 菜单权限
- {{ `${curRow?.name ? `(${curRow.name})` : ""}` }}
- </p>
- </div>
- <el-input
- v-model="treeSearchValue"
- placeholder="请输入菜单进行搜索"
- class="mb-1"
- clearable
- @input="onQueryChanged"
- />
- <div class="flex flex-wrap">
- <el-checkbox v-model="isExpandAll" label="展开/折叠" />
- <el-checkbox v-model="isSelectAll" label="全选/全不选" />
- <el-checkbox v-model="isLinkage" label="父子联动" />
- </div>
- <el-tree-v2
- ref="treeRef"
- show-checkbox
- :data="treeData"
- :props="treeProps"
- :height="treeHeight"
- :check-strictly="!isLinkage"
- :filter-method="filterMethod"
- >
- <template #default="{ node }">
- <span>{{ transformI18n(node.label) }}</span>
- </template>
- </el-tree-v2>
- </div>
- </div>
- </div>
- </template>
- <style lang="scss" scoped>
- :deep(.el-dropdown-menu__item i) {
- margin: 0;
- }
- .main-content {
- margin: 24px 24px 0 !important;
- }
- .search-form {
- :deep(.el-form-item) {
- margin-bottom: 12px;
- }
- }
- </style>
|