Pārlūkot izejas kodu

工作台人员选择组件化

wangziqian 4 gadi atpakaļ
vecāks
revīzija
d96e8a89b1

+ 6 - 1
src/components/dialog/normalDialog.vue

@@ -5,7 +5,7 @@
       :visible.sync="visible"
       :width="width"
       :modal-append-to-body="false"
-      :close-on-click-modal="false"
+      :close-on-click-modal="closeOnClick"
       :top="top"
       @close="cancel()"
     >
@@ -60,6 +60,11 @@ export default {
       type: Boolean,
       default: true,
       required: false
+    },
+    closeOnClick: { // 点击外区域消失
+      type: Boolean,
+      default: false,
+      required: false
     }
   },
   data() {

+ 146 - 0
src/views/workbench/components/createDialog.vue

@@ -0,0 +1,146 @@
+<template>
+  <div class="dialog-main">
+    <el-dialog
+      :title="title"
+      :visible.sync="show"
+      width="20%"
+      :modal-append-to-body="false"
+      :close-on-click-modal="true"
+      :class="{'bizId-dialog':bizSelect}"
+      top="15vh"
+      @close="cancel()"
+    >
+      <article>
+        <div v-show="!bizSelect" class="select-section">
+          <div class="select-schedule" @click="create('schedule')">新建排期</div>
+          <div class="select-calendar" @click="create('calendar')">新建日程</div>
+        </div>
+        <div v-show="bizSelect" class="select-bizId">
+          <i class="el-icon-arrow-left" @click="bizSelect = false;title = '请选择'" />
+          <el-select v-model="bizId" size="medium" placeholder="业务线(必选)" style="width:100%">
+            <el-option v-for="(item,index) in bizList" :key="index" :label="item.name" :value="item.code" />
+          </el-select>
+        </div>
+      </article>
+      <span v-show="bizSelect" slot="footer" class="dialog-footer">
+        <el-button size="small" @click="cancel()">取 消</el-button>
+        <el-button type="primary" size="small" @click="confirm()">确定</el-button>
+      </span>
+    </el-dialog>
+  </div>
+</template>
+<script>
+import {
+  settingGetBizList
+} from '@/api/projectIndex'
+export default {
+  props: {
+    visible: {
+      type: Boolean,
+      default: false,
+      required: true
+    }
+  },
+  data() {
+    return {
+      show: this.visible,
+      title: '请选择',
+      bizSelect: false,
+      bizList: [],
+      bizId: null
+    }
+  },
+  watch: {
+    visible: {
+      handler(newV, old) {
+        this.show = newV
+      },
+      immediate: true
+    }
+  },
+  created() {
+    this.settingGetBizList()
+  },
+  methods: {
+    async settingGetBizList() { // 获取业务线列表
+      const res = await settingGetBizList({})
+      if (res.code === 200) this.bizList = res.data || []
+    },
+    create(type) {
+      if (type === 'calendar') {
+        this.$emit('change')
+      } else if (type === 'schedule') {
+        this.title = '新建排期'
+        this.bizSelect = true
+      }
+    },
+    confirm() {
+      if (!this.bizId) return false
+      this.$emit('change', this.bizId)
+    },
+    cancel() { // 关闭弹框
+      this.show = false
+      this.$emit('update:visible', this.show)
+    }
+  }
+}
+</script>
+<style lang="scss" scoped>
+>>>.el-dialog__header {
+  padding: 20px !important;
+}
+>>>.el-dialog__body {
+  padding: 0 20px 10px 20px;
+}
+>>>.el-dialog__title{
+  padding-left: 10px;
+  position: relative;
+}
+>>>.el-dialog__title::before {
+  content:" ";
+  display: inline-block;
+  position: absolute;
+  top: 2px;
+  left: 0;
+  width: 5px;
+  height: 20px;
+  background-color: rgb(64, 158, 255);
+}
+.bizId-dialog {
+  >>>.el-dialog__title::before {
+    content:"";
+    background-color: #FFFFFF;
+  }
+}
+.el-icon-arrow-left {
+  position: absolute;
+  top: 24px;
+  left: 10px;
+  font-size: 18px;
+}
+.select-section {
+  width: 100%;
+  height: 100px;
+  display: flex;
+  flex-direction: column;
+  justify-content: center;
+  .select-schedule,.select-calendar {
+    cursor: pointer;
+    border-radius: 4px;
+    font-size: 18px;
+    height: 50%;
+    width: 100%;
+    display: flex;
+    justify-content: center;
+    align-items: center;
+  }
+  .select-schedule:hover{
+    color:rgb(64, 158, 255);
+    background-color: rgba(64, 158, 255,0.1);
+  }
+  .select-calendar:hover{
+    color:rgb(64, 158, 255);
+    background-color: rgba(64, 158, 255,0.1);
+  }
+}
+</style>

+ 125 - 0
src/views/workbench/components/searchSection.vue

@@ -0,0 +1,125 @@
+<template>
+  <div class="member-list">
+    <el-checkbox v-model="checkAllMember" :indeterminate="isIndeterminate" style="margin: 0 20px 0 5px" @change="checkAllChange">全选</el-checkbox>
+    <el-checkbox-group v-model="filtrate.checkedMembers" @change="membersChange">
+      <el-checkbox v-for="item in memberList" :key="item.idap" :label="item.idap">
+        <div class="check-point">
+          {{ item.name }}
+          <div class="point" :style="{'background-color': mapMemberColor.get(item.idap).bgColor}" />
+        </div>
+      </el-checkbox>
+    </el-checkbox-group>
+  </div>
+</template>
+<script>
+import { queryTeamMember } from '@/api/workSchedule'
+export default {
+  props: {
+    value: {
+      type: Object,
+      default: () => {},
+      required: true
+    },
+    searchForm: {
+      type: Object,
+      default: () => {},
+      required: true
+    },
+    memberColor: {
+      type: Map,
+      default: () => new Map(),
+      required: false
+    }
+  },
+  data() {
+    return {
+      memberList: [], // 团队成员列表
+      filtrate: {// 筛选项
+        checkedMembers: [] // 被选中的成员列表
+      },
+      checkAllMember: false, // 选择全部成员
+      isIndeterminate: false,
+      colorList: [
+        'rgba(64,127,232,1)', 'rgba(11,160,188,1)', 'rgba(28,188,126,1)', 'rgba(235,172,0,1)', 'rgba(132,100,247,1)',
+        'rgba(73,92,197,1)', 'rgba(193,67,96,1)', 'rgba(211,87,35,1)', 'rgba(40,28,149,1)', 'rgba(85,138,43,1)',
+        'rgba(67,17,59,1)', 'rgba(221,57,222,1)', 'rgba(149,114,109,1)', 'rgba(202,50,31,1)', 'rgba(226,119,141,1)',
+        'rgba(240,164,126,1)', 'rgba(59,64,72,1)', 'rgba(115,159,158,1)', 'rgba(122,209,67,1)', 'rgba(152,40,49,1)'
+      ],
+      mapMemberColor: this.memberColor // 人员对应颜色表
+    }
+  },
+  watch: {
+    value: {
+      handler(newV) {
+        this.filtrate = newV
+      },
+      immediate: true,
+      deep: true
+    }
+  },
+  created() {
+    this.queryTeamMember()
+  },
+  methods: {
+    async queryTeamMember() { // 获取团队人员
+      const params = this.searchForm.teamId ? { teamId: this.searchForm.teamId } : {}
+      const res = await queryTeamMember(params)
+      if (res.code === 200) {
+        this.memberList = this.handleMember(res.data)
+        this.filtrate.checkedMembers = this.memberList.map(item => item.idap)
+        this.checkAllMember = true
+        this.colorHandler(this.memberList)
+        this.$emit('change')
+        this.$emit('update:value', this.filtrate)
+        this.$emit('update:memberColor', this.mapMemberColor)
+      }
+    },
+    colorHandler(arr) { // 成员对应颜色处理
+      this.mapMemberColor.clear()
+      arr.map((item, index) => {
+        this.mapMemberColor.set(item.idap, {
+          color: '#FFFFFF',
+          bgColor: this.colorList[index % 20]
+        })
+      })
+    },
+    handleMember(arr) { // 人员和颜色的映射处理
+      const newMap = new Map()
+      return arr.filter(item => {
+        if (!newMap.has(item.idap)) {
+          newMap.set(item.idap, item)
+          return item
+        }
+      })
+    },
+    checkAllChange(val) { // 成员全部选择
+      this.filtrate.checkedMembers = val ? this.memberList.map(item => item.idap) : []
+      this.isIndeterminate = false
+      this.$emit('change')
+      this.$emit('update:value', this.filtrate)
+    },
+    membersChange(value) { // 成员变动
+      const checkedCount = value.length
+      this.checkAllMember = checkedCount === this.memberList.length
+      this.isIndeterminate = checkedCount > 0 && checkedCount < this.memberList.length
+      this.$emit('change')
+      this.$emit('update:value', this.filtrate)
+    }
+  }
+}
+</script>
+<style lang="scss" scoped>
+.member-list {
+  display: flex;
+}
+.check-point {
+  display: flex;
+  align-items: center;
+  .point {
+    margin-left: 5px;
+    height: 6px;
+    width: 6px;
+    border-radius: 50%;
+  }
+}
+</style>

+ 17 - 1
src/views/workbench/person/index.vue

@@ -136,6 +136,7 @@
             :events="calendarEvents"
             @change="queryWorkListByTime"
             @eventClick="showSchedule"
+            @select="selectDates"
           >
             <el-button type="primary" size="small" @click="dateClick()">添加日程</el-button>
           </MyFullCalendar>
@@ -156,6 +157,9 @@
         />
       </el-container>
       <!-- 日程 -->
+      <!-- 新建操作 -->
+      <create-dialog :visible.sync="createDialog" @change="createSchOrCal" />
+      <!-- 新建操作 -->
       <!-- 日程操作弹框 -->
       <calendar-dialog
         :title="'编辑日程'"
@@ -212,6 +216,7 @@ import needsList from '@/views/workbench/team/components/needsList'
 import taskList from '@/views/workbench/team/components/taskList'
 import bugTableList from '@/views/workbench/bugTableList.vue'
 import statisticsSection from '@/views/workbench/components/statisticsSection'
+import createDialog from '@/views/workbench/components/createDialog'
 import websocket from '@/views/workbench/mixins/websocket'
 
 export default {
@@ -225,7 +230,8 @@ export default {
     projectList,
     needsList,
     taskList,
-    statisticsSection
+    statisticsSection,
+    createDialog
   },
   provide() {
     return {
@@ -250,6 +256,8 @@ export default {
       ],
       activeSchedule: '1', // 日程表和列表切换
       deleteDialogVisible: false,
+      createDialog: false, // 新建弹框
+      selectRangeData: null, // 已选择的范围日期
       createSchedule: { // 新建日程
         visible: false,
         data: null
@@ -338,6 +346,14 @@ export default {
       this.showDetail = true
       this.detailXY = [`${e.jsEvent.clientX - 200}px`, `${e.jsEvent.clientY + 20}px`]
     },
+    selectDates(data) { // 日历中选择日期
+      console.log(data)
+      this.createDialog = true
+    },
+    createSchOrCal(bizId) {
+      this.createDialog = false
+      if (!bizId) this.dateClick(this.selectRangeData)
+    },
     dateClick(arg) { // 新建日程弹框
       this.createSchedule.data = arg
       this.createSchedule.visible = true

+ 15 - 79
src/views/workbench/team/index.vue

@@ -52,17 +52,13 @@
           <el-tab-pane label="甘特图" name="2" />
         </el-tabs>
         <div class="detail-info">
-          <div v-show="activeSchedule === '1'" class="member-list">
-            <el-checkbox v-model="checkAllMember" :indeterminate="isIndeterminate" style="margin: 0 20px 0 5px" @change="checkAllChange">全选</el-checkbox>
-            <el-checkbox-group v-model="checkedMembers" @change="membersChange">
-              <el-checkbox v-for="item in memberList" :key="item.idap" :label="item.idap">
-                <div class="check-point">
-                  {{ item.name }}
-                  <div class="point" :style="{'background-color': mapMemberColor.get(item.idap).bgColor}" />
-                </div>
-              </el-checkbox>
-            </el-checkbox-group>
-          </div>
+          <search-section
+            v-show="activeSchedule === '1'"
+            :value.sync="filtrate"
+            :search-form="searchForm"
+            :member-color.sync="mapMemberColor"
+            @change="queryTeamWorkListByTime(calendarView)"
+          />
           <MyFullCalendar
             v-show="activeSchedule === '1'"
             :events="calendarEvents"
@@ -192,7 +188,6 @@ import {
   queryTeamInfoList,
   queryTeamWorkListByTime,
   deleteSelfSchedule,
-  queryTeamMember,
   getTeamRequireSummary,
   getTeamRequireDisData,
   getTeamTaskSummary,
@@ -212,6 +207,7 @@ import needsList from '@/views/workbench/team/components/needsList'
 import taskList from '@/views/workbench/team/components/taskList'
 import bugTableList from '@/views/workbench/bugTableList.vue'
 import statisticsSection from '@/views/workbench/components/statisticsSection'
+import searchSection from '@/views/workbench/components/searchSection'
 
 export default {
   components: {
@@ -224,7 +220,8 @@ export default {
     projectList,
     needsList,
     taskList,
-    statisticsSection
+    statisticsSection,
+    searchSection
   },
   data() {
     return {
@@ -240,10 +237,10 @@ export default {
       },
       teamName: '团队', // 团队名字
       bizName: '业务线', // 业务线名字
-      memberList: [], // 团队成员列表
-      checkAllMember: false, // 选择全部成员
-      checkedMembers: [], // 被选中的成员列表
-      isIndeterminate: false,
+      filtrate: {// 筛选区域
+        checkedMembers: [] // 被选中的成员列表
+      },
+      mapMemberColor: new Map(), // 人员对应颜色表
       calendarEvents: [// 日程图标数据
         {
           title: 'Event Now',
@@ -267,13 +264,6 @@ export default {
       DialogTitle: '新建排期', // 排期弹框标题
       isDelete: false, // 删除排期操作
       visibleSchedule: false, // 排期任务弹框
-      colorList: [
-        'rgba(64,127,232,1)', 'rgba(11,160,188,1)', 'rgba(28,188,126,1)', 'rgba(235,172,0,1)', 'rgba(132,100,247,1)',
-        'rgba(73,92,197,1)', 'rgba(193,67,96,1)', 'rgba(211,87,35,1)', 'rgba(40,28,149,1)', 'rgba(85,138,43,1)',
-        'rgba(67,17,59,1)', 'rgba(221,57,222,1)', 'rgba(149,114,109,1)', 'rgba(202,50,31,1)', 'rgba(226,119,141,1)',
-        'rgba(240,164,126,1)', 'rgba(59,64,72,1)', 'rgba(115,159,158,1)', 'rgba(122,209,67,1)', 'rgba(152,40,49,1)'
-      ],
-      mapMemberColor: new Map(), // 人员对应颜色表
       tabTips: { // 顶部tab红点提示
         require: false,
         task: false,
@@ -314,7 +304,6 @@ export default {
   mounted() {
     this.settingGetBizList()
     this.queryTeamInfoList()
-    this.queryTeamMember()
     this.teamReminding()
   },
   methods: {
@@ -348,46 +337,6 @@ export default {
         this.searchEnum.teams.unshift({ teamId: null, teamName: '全部' })
       }
     },
-    async queryTeamMember() { // 获取团队人员
-      const params = this.searchForm.teamId ? { teamId: this.searchForm.teamId } : {}
-      const res = await queryTeamMember(params)
-      if (res.code === 200) {
-        this.memberList = this.handleMember(res.data)
-        this.checkedMembers = this.memberList.map(item => item.idap)
-        this.checkAllMember = true
-        this.queryTeamWorkListByTime(this.calendarView)
-        this.colorHandler(this.memberList)
-      }
-    },
-    colorHandler(arr) { // 成员对应颜色处理
-      this.mapMemberColor.clear()
-      arr.map((item, index) => {
-        this.mapMemberColor.set(item.idap, {
-          color: '#FFFFFF',
-          bgColor: this.colorList[index % 20]
-        })
-      })
-    },
-    handleMember(arr) {
-      const newMap = new Map()
-      return arr.filter(item => {
-        if (!newMap.has(item.idap)) {
-          newMap.set(item.idap, item)
-          return item
-        }
-      })
-    },
-    checkAllChange(val) { // 成员全部选择
-      this.checkedMembers = val ? this.memberList.map(item => item.idap) : []
-      this.isIndeterminate = false
-      this.queryTeamWorkListByTime(this.calendarView)
-    },
-    membersChange(value) { // 成员变动
-      const checkedCount = value.length
-      this.checkAllMember = checkedCount === this.memberList.length
-      this.isIndeterminate = checkedCount > 0 && checkedCount < this.memberList.length
-      this.queryTeamWorkListByTime(this.calendarView)
-    },
     handleTeams(e) { // 团队变动
       this.searchForm.teamId = e
       const res = this.searchEnum.teams.find(item => item.teamId === e)
@@ -494,7 +443,7 @@ export default {
         teamSearchInfo: this.searchForm,
         searchScheduleInfo: { origin: this.origin }
       }
-      params.peoples = this.checkedMembers
+      params.peoples = this.filtrate.checkedMembers
       const res = await queryTeamWorkListByTime(params)
       if (res.code === 200) {
         this.calendarEvents = res.data.map((item, index) => {
@@ -608,9 +557,6 @@ export default {
   .detail-info {
     padding: 0 30px 20px 30px;
   }
-  .member-list {
-    display: flex;
-  }
   .tabs-change {
     margin: 10px 35px 0 35px;
   }
@@ -619,16 +565,6 @@ export default {
   color: #333B4A;
   font-weight: 600;
 }
-.check-point {
-  display: flex;
-  align-items: center;
-  .point {
-    margin-left: 5px;
-    height: 6px;
-    width: 6px;
-    border-radius: 50%;
-  }
-}
 >>>.el-dropdown-menu__item {
   max-width: 20vw;
   overflow: scroll;

+ 0 - 1
vue.config.js

@@ -18,7 +18,6 @@ module.exports = {
   productionSourceMap: false,
   devServer: {
     port: port,
-    disableHostCheck: true,
     open: true,
     overlay: {
       warnings: false,