yuwenjun1997 пре 2 година
родитељ
комит
ce20d374e3

+ 12 - 13
src/components/IconList/index.vue

@@ -10,7 +10,7 @@
               </div>
               <div class="icon-item">
                 <svg-icon :icon-class="item" class-name="disabled" />
-                <span>{{ item }}</span>
+                <!-- <span>{{ item }}</span> -->
               </div>
             </el-tooltip>
           </div>
@@ -25,7 +25,7 @@
               </div>
               <div class="icon-item">
                 <i :class="'el-icon-' + item" />
-                <span>{{ item }}</span>
+                <!-- <span>{{ item }}</span> -->
               </div>
             </el-tooltip>
           </div>
@@ -40,7 +40,7 @@
               </div>
               <div class="icon-item">
                 <i :class="'iconfont ' + item" />
-                <span>{{ item }}</span>
+                <!-- <span>{{ item }}</span> -->
               </div>
             </el-tooltip>
           </div>
@@ -73,27 +73,26 @@ export default {
 
 <style lang="scss" scoped>
 .icons-container {
-  margin: 10px 20px 0;
   overflow: hidden;
 
   .el-tab-pane{
-    max-height: 500px;
+    max-height: 400px;
     overflow-y: auto;
   }
 
   .grid {
     position: relative;
     display: grid;
-    grid-template-columns: repeat(auto-fill, minmax(120px, 1fr));
+    grid-template-columns: repeat(auto-fill, minmax(40px, 1fr));
   }
   .icon-item {
-    padding-top: 8px;
-    margin: 16px;
-    height: 80px;
+    padding-top: 4px;
+    margin: 8px;
+    height: 30px;
+    width: 30px;
     text-align: center;
-    width: 100px;
     float: left;
-    font-size: 28px;
+    font-size: 16px;
     color: #24292e;
     cursor: pointer;
     &:hover{
@@ -102,8 +101,8 @@ export default {
   }
   span {
     display: block;
-    font-size: 16px;
-    margin-top: 10px;
+    font-size: 12px;
+    margin-top: 8px;
   }
   .disabled {
     pointer-events: none;

+ 349 - 0
src/views/admin/settings/menus/components/edit-page.vue

@@ -0,0 +1,349 @@
+<template>
+  <el-drawer :title="title" :visible.sync="visible" size="40%" :before-close="onBeforeClose">
+    <div class="menus-edit">
+      <div class="menus-edit-form">
+        <el-form ref="menuFrom" label-width="100px" :model="menuData" :rules="rules">
+          <el-form-item v-if="parentMenuData" label="上级菜单:">
+            <el-input v-model="parentMenuData.title" placeholder="上级菜单" readonly />
+          </el-form-item>
+          <el-form-item label="菜单名称:" prop="title">
+            <el-input v-model="menuData.title" placeholder="菜单名称" />
+          </el-form-item>
+          <el-form-item label="路由名称:" prop="name">
+            <el-input v-model="menuData.name" placeholder="路由名称" />
+          </el-form-item>
+          <el-form-item label="显示隐藏:">
+            <el-radio-group v-model="menuData.hidden">
+              <el-radio :label="0">显示</el-radio>
+              <el-radio :label="1">隐藏</el-radio>
+            </el-radio-group>
+          </el-form-item>
+          <el-form-item label="前端图标:">
+            <el-popover v-model="showIcons" placement="bottom" width="400" trigger="click">
+              <icon-list @click="onChooseIcon" />
+              <div slot="reference">
+                <el-input v-model="menuData.icon" style="width: 80%" placeholder="选择图标" clearable>
+                  <template><el-button slot="append" icon="el-icon-edit" /></template>
+                </el-input>
+                <template>
+                  <i v-if="isElementIcon(menuData.icon)" :class="menuData.icon" class="preview-icon" />
+                  <i v-if="isOurIcon(menuData.icon)" :class="menuData.icon" class="preview-icon" />
+                  <svg-icon v-else-if="menuData.icon" :icon-class="menuData.icon" class="preview-icon" />
+                </template>
+              </div>
+            </el-popover>
+          </el-form-item>
+          <template v-if="!parentMenuData && menuType !== 1">
+            <el-form-item label="功能类型:" prop="baseFlag">
+              <el-radio-group v-model="menuData.baseFlag">
+                <el-radio :label="1">基础功能</el-radio>
+                <el-radio :label="0">会员特定</el-radio>
+              </el-radio-group>
+            </el-form-item>
+            <el-form-item label="功能切换:" prop="moveFlag">
+              <el-radio-group v-model="menuData.moveFlag">
+                <el-radio :label="1">允许</el-radio>
+                <el-radio :label="0">禁止</el-radio>
+              </el-radio-group>
+            </el-form-item>
+          </template>
+          <el-form-item label="状态:">
+            <el-radio-group v-model="menuData.status">
+              <el-radio :label="0">启用</el-radio>
+              <el-radio :label="1">停用</el-radio>
+            </el-radio-group>
+          </el-form-item>
+          <el-form-item label="排序:">
+            <el-input v-model="menuData.sort" />
+          </el-form-item>
+          <el-form-item label="按钮权限:">
+            <template>
+              <el-input v-show="false" v-model="menuData.permissionJson" />
+              <el-table border :data="permissions">
+                <el-table-column label="按钮名称" align="center">
+                  <template slot-scope="{ row }">
+                    <el-input v-model="row.title" size="mini" />
+                  </template>
+                </el-table-column>
+                <el-table-column label="权限标识" align="center">
+                  <template slot-scope="{ row }">
+                    <el-input v-model="row.name" size="mini" />
+                  </template>
+                </el-table-column>
+                <el-table-column label="操作" align="center">
+                  <template slot-scope="{ row }">
+                    <el-button type="danger" size="mini" @click="removeOne(row.uuid)">删除按钮</el-button>
+                  </template>
+                </el-table-column>
+              </el-table>
+              <div style="text-align: center; margin-top: 24px">
+                <el-button type="primary" size="mini" @click="insertOne">添加按钮</el-button>
+              </div>
+            </template>
+          </el-form-item>
+        </el-form>
+      </div>
+      <!-- 确认 取消 -->
+      <div class="control-box">
+        <el-button type="warning" @click="cancel">取消</el-button>
+        <el-button type="primary" @click="submit">保存</el-button>
+      </div>
+    </div>
+  </el-drawer>
+</template>
+
+<script>
+import { createMenu, getMenu, updateMenu } from '@/api/system'
+import IconList from '@/components/IconList'
+let uuid = 0
+const menuData = () => ({
+  id: '',
+  title: '',
+  name: '',
+  icon: '',
+  hidden: 0,
+  status: 0,
+  sort: 0,
+  childCount: 0,
+  permissionJson: '',
+  parentId: 0,
+  baseFlag: 1,
+  moveFlag: 1,
+  menuType: 1
+})
+
+export default {
+  name: 'EditPage',
+  components: {
+    IconList
+  },
+  props: {
+    show: {
+      type: Boolean,
+      default: false
+    },
+    title: {
+      type: String,
+      default: 'add'
+    },
+    // 编辑类型
+    editType: {
+      type: String,
+      default: 'add'
+    },
+    // 菜单类型
+    menuType: {
+      type: Number,
+      default: 1
+    },
+    // 菜单id
+    menuId: {
+      type: Number,
+      default: 0
+    }
+  },
+  data() {
+    return {
+      visible: false,
+      showIcons: false,
+      // 上级菜单信息
+      parentMenuData: null,
+      // 表单参数
+      menuData: menuData(),
+      // 按钮权限列表
+      permissions: [],
+      // 验证规则
+      rules: {
+        title: [{ required: true, message: '菜单名称不能为空', trigger: 'blur' }],
+        name: [{ required: true, message: '路由名称不能为空', trigger: 'blur' }]
+      }
+    }
+  },
+  watch: {
+    show(nval) {
+      if (nval) {
+        this.visible = nval
+        this.init()
+      }
+    },
+    visible(nval) {
+      if (!nval) this.$emit('close')
+    }
+  },
+  methods: {
+    onChooseIcon(item) {
+      this.showIcons = false
+      this.menuData.icon = item
+    },
+    // 选择图标
+    handleChooseIcon() {
+      this.showIcons = true
+    },
+
+    // 初始化
+    init() {
+      this.menuData = menuData()
+      this.parentMenuData = null
+      this.permissions = []
+      console.log('editType', this.editType)
+      console.log('menuType', this.menuType)
+      console.log('menuId', this.menuId)
+
+      this.menuData.menuType = this.menuType
+      // 编辑修改菜单
+      if (this.editType === 'edit') {
+        this.menuData.id = this.menuId
+        this.fetchMenuInfo()
+      } else if (this.editType === 'child') {
+        this.menuData.parentId = this.menuId
+        this.fetchParentMenuInfo()
+      }
+    },
+    // 获取父菜单信息
+    fetchParentMenuInfo() {
+      getMenu(this.menuData.parentId).then((res) => {
+        this.parentMenuData = res.data
+        this.menuData.baseFlag = res.data.baseFlag
+      })
+    },
+    // 获取菜单数据
+    fetchMenuInfo() {
+      getMenu(this.menuData.id).then((res) => {
+        console.log(res)
+        this.setMenuData(res.data)
+      })
+    },
+    // 设置菜单数据
+    setMenuData(data) {
+      for (const key in this.menuData) {
+        if (Object.hasOwnProperty.call(data, key)) {
+          this.menuData[key] = data[key]
+        }
+      }
+      // 按钮权限列表
+      if (this.permissionJson) {
+        this.permissions = JSON.parse(this.permissionJson)
+      }
+      // 父级菜单信息
+      if (this.menuData.parentId > 0) {
+        this.fetchParentMenuInfo()
+      }
+    },
+    // 判断图标类型
+    isElementIcon(value) {
+      return value && value.substr(0, 7) === 'el-icon'
+    },
+    // 判断自定义图标
+    isOurIcon(value) {
+      return value && value.startsWith('iconfont')
+    },
+    // 提交
+    submit() {
+      console.log(this.menuData)
+      this.menuData.permissionJson = JSON.stringify(this.permissions)
+      this.$refs.menuFrom.validate((valide) => {
+        if (!valide) return
+        if (this.editType === 'add') {
+          this.createMenu()
+        } else {
+          this.updateMenu()
+        }
+      })
+    },
+    // 修改菜单
+    updateMenu() {
+      updateMenu(this.menuData.id, this.menuData)
+        .then(() => {
+          this.$message.success('修改菜单成功')
+          this.$emit('success')
+        })
+        .catch(() => {
+          this.$emit('error')
+        })
+    },
+    // 添加菜单
+    createMenu() {
+      console.log(this.menuData)
+      // return
+      createMenu(this.menuData)
+        .then(() => {
+          this.$message.success('添加菜单成功')
+          this.$emit('success')
+        })
+        .catch(() => {
+          this.$emit('error')
+        })
+    },
+
+    cancel() {
+      this.visible = false
+    },
+
+    // 添加按钮权限
+    insertOne() {
+      this.permissions.push({
+        uuid: ++uuid,
+        name: '',
+        title: ''
+      })
+    },
+    // 移除一条按钮权限
+    removeOne(uuid) {
+      const index = this.permissions.findIndex((item) => item.uuid === uuid)
+      this.permissions.splice(index, 1)
+    },
+
+    onBeforeClose(done) {
+      this.$confirm('您有数据未保存, 是否继续?', '提示', {
+        confirmButtonText: '确定',
+        cancelButtonText: '取消',
+        type: 'warning'
+      })
+        .then(() => {
+          this.$refs.menuFrom.clearValidate()
+          done()
+        })
+        .catch(() => {
+          this.$message({
+            type: 'info',
+            message: '已取消关闭'
+          })
+        })
+    }
+  }
+}
+</script>
+
+<style scoped lang="scss">
+.menus-edit {
+  position: relative;
+  height: calc(100vh - 45px);
+
+  .menus-edit-form {
+    overflow-y: auto;
+    height: 100%;
+    box-sizing: border-box;
+    padding: 24px 12px 60px;
+  }
+
+  .preview-icon {
+    font-size: 24px;
+    margin-left: 8px;
+  }
+}
+.control-box {
+  position: absolute;
+  bottom: 0;
+  left: 0;
+  width: 100%;
+  text-align: center;
+  background: #fff;
+  border-top: 1px solid #ebebeb;
+  padding: 12px 0;
+  z-index: 9;
+  .el-button {
+    width: 120px;
+    margin: 0 8px;
+  }
+}
+</style>

+ 52 - 0
src/views/admin/settings/menus/index-t.vue

@@ -0,0 +1,52 @@
+<template>
+  <div class="app-container">
+    <el-tabs v-model="activeName" @tab-click="handleClick">
+      <el-tab-pane v-for="item in menusCategory" :key="item.menuType" :label="item.title" :name="item.name" :lazy="true">
+        <table-list :key="item.menuType" :menu-type="item.menuType" />
+      </el-tab-pane>
+      <!-- <el-tab-pane label="供应商" name="second">配置管理</el-tab-pane> -->
+    </el-tabs>
+  </div>
+</template>
+
+<script>
+import TableList from './components/table-list.vue'
+export default {
+  name: 'SettingsMenus',
+  components: {
+    TableList
+  },
+  data() {
+    return {
+      activeName: 'manager',
+      menusCategory: [
+        {
+          id: 1,
+          title: '管理员菜单管理',
+          name: 'manager',
+          menuType: 1
+        },
+        {
+          id: 2,
+          title: '供应商管理',
+          name: 'supplier',
+          menuType: 2
+        }
+      ]
+    }
+  },
+  created() {
+    this.activeName = this.$route.query.activeName || 'manager'
+  },
+  methods: {
+    handleClick() {}
+  }
+}
+</script>
+
+<style scoped>
+.page-title {
+  font-size: 18px;
+  color: #404040;
+}
+</style>

+ 198 - 31
src/views/admin/settings/menus/index.vue

@@ -1,52 +1,219 @@
 <template>
-  <div class="app-container">
-    <el-tabs v-model="activeName" @tab-click="handleClick">
-      <el-tab-pane v-for="item in menusCategory" :key="item.menuType" :label="item.title" :name="item.name" :lazy="true">
-        <table-list :key="item.menuType" :menu-type="item.menuType" />
-      </el-tab-pane>
-      <!-- <el-tab-pane label="供应商" name="second">配置管理</el-tab-pane> -->
-    </el-tabs>
+  <div class="table-list">
+    <div class="app-container">
+      <div class="filter-container">
+        <div class="filter-control">
+          <span>菜单状态:</span>
+          <el-select
+            v-model="listQuery.status"
+            placeholder="启用状态"
+            clearable
+            style="width: 200px"
+            class="filter-item"
+            @change="getList"
+          >
+            <el-option label="全部" value="" />
+            <el-option label="已启用" :value="0" />
+            <el-option label="未启用" :value="1" />
+          </el-select>
+        </div>
+        <div class="filter-control">
+          <el-button type="primary" @click="onEditMenu(null, 'add')">添加菜单</el-button>
+        </div>
+      </div>
+      <!-- 搜索区域END -->
+      <el-table
+        v-loading="listLoading"
+        header-row-class-name="tableHeader"
+        class="table-cell"
+        row-key="id"
+        border
+        fit
+        lazy
+        :indent="24"
+        :data="list"
+        :load="load"
+        :tree-props="{ hasChildren: 'hasChildren' }"
+      >
+        <el-table-column :index="indexMethod" label="序号" type="index" width="80" align="center" />
+        <el-table-column label="菜单名称" prop="title" align="center" class-name="text-left" />
+        <el-table-column prop="name" label="路由名称" align="center" />
+        <el-table-column label="菜单级别" width="120px" align="center">
+          <template slot-scope="{ row }">
+            {{ row.level | levelName }}
+          </template>
+        </el-table-column>
+        <el-table-column prop="childCount" label="子菜单数量" align="center" width="100px" />
+        <el-table-column label="展示图标" align="center" width="100">
+          <template slot-scope="{ row }">
+            <i v-if="row.icon" :class="row.icon" />
+            <span v-else>无</span>
+          </template>
+        </el-table-column>
+        <el-table-column v-if="listQuery.menuType === 2" prop="name" label="会员功能" align="center">
+          <template slot-scope="{ row }">
+            <span v-if="row.baseFlag === 1">基础功能</span>
+            <span v-else>订制功能</span>
+          </template>
+        </el-table-column>
+        <el-table-column label="启用状态" align="center" width="100">
+          <template slot-scope="{ row }">
+            <el-switch v-model="row.status" :active-value="0" :inactive-value="1" />
+          </template>
+        </el-table-column>
+        <el-table-column prop="sort" label="排序" align="center" width="100">
+          <template slot-scope="{ row }">
+            <el-input v-model="row.sort" />
+          </template>
+        </el-table-column>
+        <el-table-column label="创建时间" align="center" width="180px">
+          <template slot-scope="{ row }">
+            <span>{{ row.createTime | formatTime }}</span>
+          </template>
+        </el-table-column>
+        <el-table-column label="操作" align="center" width="300">
+          <template slot-scope="{ row }">
+            <el-button type="primary" size="mini" @click="onEditMenu(row, 'edit')">编辑</el-button>
+            <el-button type="primary" size="mini" @click="onEditMenu(row, 'child')">添加子菜单</el-button>
+            <el-button type="danger" size="mini">删除</el-button>
+          </template>
+        </el-table-column>
+      </el-table>
+      <!-- 页码 -->
+      <pagination
+        :total="total"
+        :page.sync="listQuery.pageNum"
+        :limit.sync="listQuery.pageSize"
+        @pagination="getList"
+      />
+      <edit-page
+        :title="editTitle"
+        :show="editDrawer"
+        :menu-type="menuType"
+        :edit-type="editType"
+        :menu-id="currentMenuId"
+        @close="editDrawer = false"
+      />
+    </div>
   </div>
 </template>
 
 <script>
-import TableList from './components/table-list.vue'
+import { fetchMenuList } from '@/api/system'
+import Pagination from '@/components/Pagination' // secondary package based on el-pagination
+import EditPage from './components/edit-page.vue'
 export default {
-  name: 'SettingsMenus',
+  name: 'TableList',
   components: {
-    TableList
+    Pagination,
+    EditPage
+  },
+  filters: {
+    levelName(level) {
+      return '一二三四五六七八九十'.split('')[level - 1] + '级菜单'
+    }
+  },
+  props: {
+    menuType: {
+      type: Number,
+      default: 1
+    }
   },
   data() {
     return {
-      activeName: 'manager',
-      menusCategory: [
-        {
-          id: 1,
-          title: '管理员菜单管理',
-          name: 'manager',
-          menuType: 1
-        },
-        {
-          id: 2,
-          title: '供应商管理',
-          name: 'supplier',
-          menuType: 2
-        }
-      ]
+      listLoading: false,
+      editDrawer: false,
+      editTitle: '',
+      // 查询参数
+      listQuery: {
+        parentId: '',
+        menuType: '', // 1:管理员 2:供应商
+        status: '',
+        pageSize: 10,
+        pageNum: 1
+      },
+      total: 0,
+      // 菜单列表
+      list: [],
+      currentMenuId: 0,
+      editType: 'add'
     }
   },
   created() {
-    this.activeName = this.$route.query.activeName || 'manager'
+    this.getList()
   },
   methods: {
-    handleClick() {}
+    // 编辑菜单
+    onEditMenu(row, type) {
+      this.editType = type
+      const titles = {
+        edit: '修改菜单信息',
+        add: '添加菜单',
+        child: '添加子菜单'
+      }
+      this.editTitle = titles[type]
+      if (type === 'edit') {
+        this.currentMenuId = row.id
+      } else if (type === 'child') {
+        this.currentMenuId = row.id
+      } else {
+        this.currentMenuId = 0
+      }
+      this.editDrawer = true
+    },
+
+    // 加载子菜单
+    async load(tree, treeNode, resolve) {
+      try {
+        const res = await fetchMenuList({
+          parentId: tree.id,
+          menuType: this.menuType,
+          status: '',
+          pageSize: 1000,
+          pageNum: 1
+        })
+        const list = res.data.list.map((item) => {
+          item.hasChildren = item.childCount > 0
+          item.level = tree.level + 1
+          return item
+        })
+        resolve(list)
+      } catch (error) {
+        console.log(error)
+      }
+    },
+
+    // 获取列表
+    async getList() {
+      this.listQuery.menuType = this.menuType
+      this.listQuery.pageNum = 1
+      try {
+        const res = await fetchMenuList(this.listQuery)
+        this.list = res.data.list.map((item) => {
+          item.hasChildren = item.childCount > 0
+          item.level = 1
+          return item
+        })
+        this.total = res.data.total
+      } catch (error) {
+        console.log(error)
+      }
+    },
+
+    // 表格索引
+    indexMethod(index) {
+      return index + this.listQuery.pageSize * (this.listQuery.pageNum - 1) + 1
+    }
   }
 }
 </script>
 
-<style scoped>
-.page-title {
-  font-size: 18px;
-  color: #404040;
+<style>
+.table-list .text-left {
+  text-align: left !important;
+}
+
+.table-list .text-left.is-leaf {
+  text-align: center !important;
 }
 </style>

+ 2 - 18
src/views/admin/supplier/index.vue

@@ -5,7 +5,6 @@
         <span>供应商名称:</span>
         <el-input v-model="listQuery.shopName" placeholder="供应商名称" @keyup.enter.native="handleFilter" />
       </div>
-
       <div class="filter-control">
         <span>供应商类型:</span>
         <el-select
@@ -25,21 +24,6 @@
         <span>登录账号:</span>
         <el-input v-model="listQuery.loginAccount" placeholder="登录账号" @keyup.enter.native="handleFilter" />
       </div>
-      <!-- <div class="filter-control">
-        <span>所属品牌:</span>
-        <el-select
-          v-model="listQuery.brandId"
-          placeholder="所属品牌"
-          clearable
-          class="filter-item"
-          style="width: 200px"
-          filterable
-          @change="getList()"
-        >
-          <el-option label="所有品牌" value="" />
-          <el-option v-for="item in brandList" :key="item.id" :label="item.name" :value="item.id" />
-        </el-select>
-      </div> -->
       <div class="filter-control">
         <span>手机号:</span>
         <el-input
@@ -62,8 +46,8 @@
       </div>
 
       <div class="filter-control">
-        <el-button type="primary" @click="getList(listQuery)">查询</el-button>
-        <el-button type="primary" @click="$_navigationTo('supplier-add')">添加供应商</el-button>
+        <el-button size="mini" type="primary" @click="getList(listQuery)">查询</el-button>
+        <el-button size="mini" type="primary" @click="$_navigationTo('supplier-add')">添加供应商</el-button>
       </div>
     </div>
     <!-- 表格区域 -->