From 1fa6ac40e2ce16e1174cec9ca538d45eeb660fdc Mon Sep 17 00:00:00 2001
From: xiangpei <xiangpei@timesnew.cn>
Date: 星期四, 05 六月 2025 18:17:56 +0800
Subject: [PATCH] 工作台

---
 src/views/workbench.vue |  596 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 596 insertions(+), 0 deletions(-)

diff --git a/src/views/workbench.vue b/src/views/workbench.vue
new file mode 100644
index 0000000..ce8c638
--- /dev/null
+++ b/src/views/workbench.vue
@@ -0,0 +1,596 @@
+<template>
+  <div class="dashboard-container">
+    <!-- 椤堕儴瀵艰埅鏍� -->
+    <div class="top-navbar">
+      <div class="welcome-message">
+        <h2>鏃╁畨锛寋{ this.$store.state.user.name }}锛�</h2>
+        <p>浠婂ぉ鏄瘂{ currentDate }}锛岀鎮ㄥ伐浣滄剦蹇紒</p>
+      </div>
+      <div class="quick-stats">
+        <div class="stat-item">
+          <span class="stat-number">{{ todayTasks }}</span>
+          <span class="stat-label">浠婃棩寰呭姙</span>
+        </div>
+        <div class="stat-item">
+          <span class="stat-number">{{ todaySchedules }}</span>
+          <span class="stat-label">浠婃棩鏃ョ▼</span>
+        </div>
+        <div class="stat-item">
+          <span class="stat-number">{{ unreadMessages }}</span>
+          <span class="stat-label">鏈娑堟伅</span>
+        </div>
+      </div>
+      <div class="user-profile">
+<!--        <el-dropdown>-->
+<!--          <div class="user-avatar">-->
+<!--            <img :src="userInfo.avatar" alt="鐢ㄦ埛澶村儚">-->
+<!--            <span>{{ userInfo.name }}</span>-->
+<!--          </div>-->
+<!--          <el-dropdown-menu slot="dropdown">-->
+<!--            <el-dropdown-item>涓汉涓績</el-dropdown-item>-->
+<!--            <el-dropdown-item>璁剧疆</el-dropdown-item>-->
+<!--            <el-dropdown-item divided>閫�鍑虹櫥褰�</el-dropdown-item>-->
+<!--          </el-dropdown-menu>-->
+<!--        </el-dropdown>-->
+      </div>
+    </div>
+
+    <!-- 涓诲唴瀹瑰尯 -->
+    <div class="main-content">
+      <!-- 宸︿晶椤圭洰鍒楄〃 -->
+      <div class="left-sidebar">
+        <div class="project-list">
+          <h3>椤圭洰鍒楄〃</h3>
+          <el-menu
+            :default-active="activeProject"
+            class="project-menu"
+            @select="handleProjectSelect">
+            <el-menu-item index="all">
+              <i class="el-icon-menu"></i>
+              <span slot="title">鍏ㄩ儴椤圭洰</span>
+            </el-menu-item>
+            <el-menu-item
+              v-for="project in projects"
+              :key="project.id"
+              :index="project.id">
+              <i class="el-icon-folder"></i>
+              <span slot="title" class="project-name" :title="project.name">
+                {{ project.name }}
+              </span>
+            </el-menu-item>
+          </el-menu>
+          <div class="project-actions">
+            <el-button type="primary" icon="el-icon-plus" size="small">鏂板缓椤圭洰</el-button>
+          </div>
+        </div>
+      </div>
+
+      <!-- 涓棿鍐呭鍖� -->
+      <div class="center-content">
+        <!-- 寰呭姙浠诲姟 -->
+        <div class="task-section">
+          <div class="section-header">
+            <h3>寰呭姙浠诲姟</h3>
+            <el-button type="text" icon="el-icon-refresh">鍒锋柊</el-button>
+          </div>
+          <el-table
+            :data="tasks"
+            border
+            style="width: 100%"
+            >
+            <el-table-column
+              prop="name"
+              label="浠诲姟鍚嶇О"
+              width="240">
+            </el-table-column>
+            <el-table-column
+              prop="project"
+              label="鎵�灞為」鐩�"
+              show-overflow-tooltip
+              width="300">
+            </el-table-column>
+            <el-table-column
+              prop="startTime"
+              label="寮�濮嬫椂闂�"
+              align="center"
+              width="160">
+            </el-table-column>
+            <el-table-column
+              prop="deadline"
+              label="鎴鏃堕棿"
+              align="center"
+              width="160">
+            </el-table-column>
+            <el-table-column
+              prop="status"
+              label="鐘舵��"
+              align="center"
+              width="100">
+              <template slot-scope="scope">
+                <el-tag :type="scope.row.status === '寰呭畬鎴�' ? 'success' : 'warning'" size="small">
+                  {{ scope.row.status }}
+                </el-tag>
+              </template>
+            </el-table-column>
+            <el-table-column
+              label="鎿嶄綔"
+              fixed="right"
+              width="120">
+              <template slot-scope="scope">
+                <el-button size="mini" @click="handleTaskEdit(scope.row)">鍔炵悊</el-button>
+              </template>
+            </el-table-column>
+          </el-table>
+        </div>
+
+        <!-- 椤圭洰鍔炵悊鏃ュ織 -->
+        <div class="log-section">
+          <div class="section-header">
+            <h3>椤圭洰鍔炵悊鏃ュ織</h3>
+            <el-button type="text" icon="el-icon-refresh">鍒锋柊</el-button>
+          </div>
+          <div class="log-list">
+            <div v-for="log in logs" :key="log.id" class="log-item">
+              <div class="log-time">{{ log.time }}</div>
+              <div class="log-content">
+                <span class="log-project">{{ log.project }}</span>
+                <span class="log-action">{{ log.action }}</span>
+                <span class="log-detail">{{ log.detail }}</span>
+              </div>
+            </div>
+          </div>
+        </div>
+      </div>
+
+      <!-- 鍙充晶杈规爮 -->
+      <div class="right-sidebar">
+        <!-- 涓汉鎴愬氨 -->
+        <div class="achievement-section">
+          <h3>涓汉鎴愬氨</h3>
+          <div class="achievement-stats">
+            <div class="stat-item">
+              <div class="stat-number">{{ achievements.completedTasks }}</div>
+              <div class="stat-label">瀹屾垚浠诲姟</div>
+            </div>
+            <div class="stat-item">
+              <div class="stat-number">{{ achievements.avgDuration }}澶�</div>
+              <div class="stat-label">骞冲潎鐢ㄦ椂</div>
+            </div>
+            <div class="stat-item">
+              <div class="stat-number">{{ achievements.totalSchedules }}</div>
+              <div class="stat-label">瀹夋帓鏃ョ▼</div>
+            </div>
+            <div class="stat-item">
+              <div class="stat-number">{{ achievements.completedSchedules }}</div>
+              <div class="stat-label">瀹屾垚鏃ョ▼</div>
+            </div>
+          </div>
+        </div>
+
+        <!-- 鏃ュ巻 -->
+        <div class="calendar-section">
+          <el-calendar v-model="calendarDate">
+            <template
+              slot="dateCell"
+              slot-scope="{date, data}">
+              <div class="calendar-day">
+                {{ data.day.split('-').slice(2).join('-') }}
+                <div v-if="getScheduleCount(date) > 0" class="schedule-count">
+                  {{ getScheduleCount(date) }}涓棩绋�
+                </div>
+              </div>
+            </template>
+          </el-calendar>
+        </div>
+
+        <!-- 鏃ョ▼鍒楄〃 -->
+        <div class="schedule-list-section">
+          <div class="section-header">
+            <h3>鏃ョ▼鍒楄〃</h3>
+            <div>
+              <el-button type="text" icon="el-icon-plus" @click="handleAddSchedule">鏂板</el-button>
+              <el-button type="text" icon="el-icon-refresh">鍒锋柊</el-button>
+            </div>
+          </div>
+          <div class="schedule-list">
+            <el-table
+              :data="filteredSchedules"
+              style="width: 100%"
+              height="250">
+              <el-table-column
+                prop="time"
+                label="鏃堕棿"
+                width="100">
+              </el-table-column>
+              <el-table-column
+                prop="title"
+                label="浜嬮」"
+                width="120">
+              </el-table-column>
+              <el-table-column
+                label="鎿嶄綔"
+                width="120">
+                <template slot-scope="scope">
+                  <el-button size="mini" @click="handleEditSchedule(scope.row)">缂栬緫</el-button>
+                  <el-button size="mini" type="danger" @click="handleDeleteSchedule(scope.row)">鍒犻櫎</el-button>
+                </template>
+              </el-table-column>
+            </el-table>
+          </div>
+        </div>
+      </div>
+    </div>
+  </div>
+</template>
+
+<script>
+export default {
+  data() {
+    return {
+      userInfo: {
+        name: '寮犲伐绋嬪笀',
+        avatar: 'https://cube.elemecdn.com/0/88/03b0d39583f48206768a7534e55bcpng.png',
+        department: '椤圭洰閮�'
+      },
+      currentDate: this.formatDate(new Date()),
+      todayTasks: 5,
+      todaySchedules: 3,
+      unreadMessages: 2,
+      activeProject: 'all',
+      projects: [
+        { id: '1', name: '灏勬椽甯傛脖鐗岄晣缁煎悎姘村埄璁炬柦寤鸿椤圭洰' },
+        { id: '2', name: '灏勬椽甯傚浗瀹跺偍澶囨灄寤鸿椤圭洰锛堜竴鏈燂級' },
+        { id: '3', name: '灏勬椽甯傜櫧缇借倝楦′骇涓氬缓璁鹃」鐩�' },
+        { id: '4', name: '閬傚畞甯傚皠娲�2024鈥�2027骞村害涓滃寳鐗囧尯楂樻爣鍑嗗啘鐢板缓璁鹃」鐩�' },
+        { id: '5', name: '灏勬椽甯傜幇浠g涓氱ず鑼冨熀鍦板缓璁鹃」鐩�' },
+      ],
+      tasks: [
+        { id: 1, name: '瀹℃牳鏂藉伐鍥剧焊', project: '灏勬椽甯傚浗瀹跺偍澶囨灄寤鸿椤圭洰锛堜竴鏈燂級', startTime: '2025-05-05', deadline: '2025-06-15', status: '寰呭畬鎴�' },
+        { id: 2, name: '閲囪喘鏉愭枡娓呭崟', project: '灏勬椽甯傜櫧缇借倝楦′骇涓氬缓璁鹃」鐩�', startTime: '2025-05-14', deadline: '2025-06-18', status: '寰呭畬鎴�' },
+        { id: 3, name: '鐜板満瀹夊叏妫�鏌�', project: '閬傚畞甯傚皠娲�2024鈥�2027骞村害涓滃寳鐗囧尯楂樻爣鍑嗗啘鐢板缓璁鹃」鐩�', startTime: '2025-05-10', deadline: '2025-06-12', status: '瀹圭己涓�' },
+        { id: 4, name: '椤圭洰杩涘害鎶ュ憡', project: '灏勬椽甯傜幇浠g涓氱ず鑼冨熀鍦板缓璁鹃」鐩�', startTime: '2025-05-23', deadline: '2025-06-20', status: '寰呭畬鎴�' },
+        { id: 5, name: '渚涘簲鍟嗕細璁�', project: '灏勬椽甯傛脖鐗岄晣缁煎悎姘村埄璁炬柦寤鸿椤圭洰', startTime: '2025-05-14', deadline: '2025-06-14', status: '瀹圭己涓�' }
+      ],
+      logs: [
+        { id: 1, time: '09:30', project: '灏勬椽甯傚浗瀹跺偍澶囨灄寤鸿椤圭洰锛堜竴鏈燂級', action: '鎻愪氦', detail: '鎻愪氦浜嗘柦宸ュ浘绾稿鏍哥敵璇�' },
+        { id: 2, time: '10:15', project: '灏勬椽甯傜櫧缇借倝楦′骇涓氬缓璁鹃」鐩�', action: '鏇存柊', detail: '鏇存柊浜嗘潗鏂欓噰璐竻鍗�' },
+        { id: 3, time: '11:00', project: '閬傚畞甯傚皠娲�2024鈥�2027骞村害涓滃寳鐗囧尯楂樻爣鍑嗗啘鐢板缓璁鹃」鐩�', action: '瀹屾垚', detail: '瀹屾垚浜嗙數鍔涜澶囨祴璇�' },
+        { id: 4, time: '14:30', project: '灏勬椽甯傜幇浠g涓氱ず鑼冨熀鍦板缓璁鹃」鐩�', action: '鍒涘缓', detail: '鍒涘缓浜嗘柊鐨勫畨瑁呰鍒�' },
+        { id: 5, time: '16:45', project: '灏勬椽甯傛脖鐗岄晣缁煎悎姘村埄璁炬柦寤鸿椤圭洰', action: '瀹℃壒', detail: '瀹℃壒閫氳繃浜嗗畨鍏ㄦ柟妗�' }
+      ],
+      achievements: {
+        completedTasks: 128,
+        avgDuration: 3.5,
+        totalSchedules: 89,
+        completedSchedules: 76
+      },
+      calendarDate: new Date(),
+      schedules: [
+        { id: 1, date: '2025-05-10', time: '09:00', title: '椤圭洰鍚姩浼氳', project: '灏勬椽甯傚浗瀹跺偍澶囨灄寤鸿椤圭洰锛堜竴鏈燂級' },
+        { id: 2, date: '2025-05-10', time: '14:00', title: '渚涘簲鍟嗘唇璋�', project: '灏勬椽甯傜櫧缇借倝楦′骇涓氬缓璁鹃」鐩�' },
+        { id: 3, date: '2025-05-11', time: '10:30', title: '鐜板満鍕樺療', project: '閬傚畞甯傚皠娲�2024鈥�2027骞村害涓滃寳鐗囧尯楂樻爣鍑嗗啘鐢板缓璁鹃」鐩�' },
+        { id: 4, date: '2025-05-12', time: '09:00', title: '瀹夊叏鍩硅', project: '灏勬椽甯傜幇浠g涓氱ず鑼冨熀鍦板缓璁鹃」鐩�' },
+        { id: 5, date: '2025-05-12', time: '15:00', title: '杩涘害姹囨姤', project: '灏勬椽甯傛脖鐗岄晣缁煎悎姘村埄璁炬柦寤鸿椤圭洰' },
+        { id: 6, date: '2025-05-15', time: '13:00', title: '璁惧楠屾敹', project: '灏勬椽甯傜櫧缇借倝楦′骇涓氬缓璁鹃」鐩�' }
+      ]
+    }
+  },
+  computed: {
+    filteredSchedules() {
+      const selectedDate = this.formatCalendarDate(this.calendarDate);
+      return this.schedules.filter(schedule => schedule.date === selectedDate);
+    }
+  },
+  methods: {
+    // 鎴柇杩囬暱鐨勯」鐩悕绉�
+    truncateProjectName(name) {
+      const maxLength = 10; // 鏈�澶ф樉绀洪暱搴�
+      return name.length > maxLength ? `${name.substring(0, maxLength)}...` : name;
+    },
+    // 鍒ゆ柇椤圭洰鍚嶆槸鍚﹁繃闀�
+    isProjectNameTooLong(name) {
+      return name.length > 10;
+    },
+    formatDate(date) {
+      const year = date.getFullYear();
+      const month = date.getMonth() + 1;
+      const day = date.getDate();
+      return `${year}骞�${month}鏈�${day}鏃;
+    },
+    formatCalendarDate(date) {
+      const year = date.getFullYear();
+      const month = (date.getMonth() + 1).toString().padStart(2, '0');
+      const day = date.getDate().toString().padStart(2, '0');
+      return `${year}-${month}-${day}`;
+    },
+    handleProjectSelect(index) {
+      this.activeProject = index;
+      // 杩欓噷鍙互娣诲姞椤圭洰绛涢�夐�昏緫
+    },
+    getPriorityType(priority) {
+      switch (priority) {
+        case '楂�': return 'danger';
+        case '涓�': return 'warning';
+        case '浣�': return 'success';
+        default: return 'info';
+      }
+    },
+    handleTaskEdit(task) {
+      console.log('缂栬緫浠诲姟:', task);
+      this.$message.info(`寮�濮嬪鐞嗕换鍔�: ${task.name}`);
+    },
+    getScheduleCount(date) {
+      const dateStr = this.formatCalendarDate(date);
+      return this.schedules.filter(s => s.date === dateStr).length;
+    },
+    handleAddSchedule() {
+      this.$message.info('鏂板鏃ョ▼');
+    },
+    handleEditSchedule(schedule) {
+      this.$message.info(`缂栬緫鏃ョ▼: ${schedule.title}`);
+    },
+    handleDeleteSchedule(schedule) {
+      this.$confirm('纭畾鍒犻櫎璇ユ棩绋嬪悧?', '鎻愮ず', {
+        confirmButtonText: '纭畾',
+        cancelButtonText: '鍙栨秷',
+        type: 'warning'
+      }).then(() => {
+        this.$message.success('鍒犻櫎鎴愬姛');
+      }).catch(() => {
+        this.$message.info('宸插彇娑堝垹闄�');
+      });
+    }
+  }
+}
+</script>
+
+<style scoped>
+.dashboard-container {
+  font-family: 'Helvetica Neue', Helvetica, 'PingFang SC', 'Hiragino Sans GB', 'Microsoft YaHei', Arial, sans-serif;
+  height: 100vh;
+  display: flex;
+  flex-direction: column;
+  background-color: #f5f7fa;
+}
+
+/* 椤堕儴瀵艰埅鏍忔牱寮� */
+.top-navbar {
+  background-color: #1e88e5;
+  color: white;
+  padding: 15px 20px;
+  display: flex;
+  justify-content: space-between;
+  align-items: center;
+  box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);
+}
+
+.welcome-message h2 {
+  margin: 0;
+  font-size: 20px;
+}
+
+.welcome-message p {
+  margin: 5px 0 0;
+  font-size: 14px;
+  opacity: 0.9;
+}
+
+.quick-stats {
+  display: flex;
+  gap: 30px;
+}
+
+.stat-item {
+  display: flex;
+  flex-direction: column;
+  align-items: center;
+}
+
+.stat-number {
+  font-size: 24px;
+  font-weight: bold;
+}
+
+.stat-label {
+  font-size: 14px;
+  opacity: 0.9;
+}
+
+.user-profile {
+  display: flex;
+  align-items: center;
+}
+
+.user-avatar {
+  display: flex;
+  align-items: center;
+  cursor: pointer;
+}
+
+.user-avatar img {
+  width: 40px;
+  height: 40px;
+  border-radius: 50%;
+  margin-right: 10px;
+}
+
+/* 涓诲唴瀹瑰尯鏍峰紡 */
+.main-content {
+  display: flex;
+  flex: 1;
+  overflow: hidden;
+}
+
+.left-sidebar {
+  width: 220px;
+  background-color: white;
+  border-right: 1px solid #e6e6e6;
+  padding: 15px;
+  margin-top: 10px;
+  overflow-y: auto;
+}
+.project-name {
+  display: inline-block;
+  max-width: 150px;
+  white-space: nowrap;
+  overflow: hidden;
+  text-overflow: ellipsis;
+}
+.project-list h3 {
+  margin-top: 0;
+  color: #333;
+  padding-bottom: 10px;
+  border-bottom: 1px solid #eee;
+}
+
+.project-menu {
+  border-right: none;
+}
+
+.project-actions {
+  margin-top: 15px;
+  text-align: center;
+}
+
+.center-content {
+  flex: 1;
+  padding: 15px;
+  overflow-y: auto;
+  background-color: white;
+  margin: 10px 10px 0px;
+  border-radius: 4px;
+  box-shadow: 0 1px 3px rgba(0, 0, 0, 0.1);
+}
+
+.section-header {
+  display: flex;
+  justify-content: space-between;
+  align-items: center;
+  margin-bottom: 15px;
+}
+
+.section-header h3 {
+  margin: 0;
+  color: #333;
+}
+
+.task-section {
+  margin-bottom: 20px;
+  height: 350px;
+}
+
+.log-list {
+  border: 1px solid #ebeef5;
+  border-radius: 4px;
+  padding: 10px;
+}
+
+.log-item {
+  display: flex;
+  padding: 8px 0;
+  border-bottom: 1px dashed #eee;
+}
+
+.log-item:last-child {
+  border-bottom: none;
+}
+
+.log-time {
+  width: 60px;
+  color: #666;
+  font-size: 14px;
+}
+
+.log-content {
+  flex: 1;
+}
+
+.log-project {
+  color: #1e88e5;
+  margin-right: 10px;
+  font-weight: bold;
+}
+
+.log-action {
+  color: #ff9800;
+  margin-right: 10px;
+}
+
+.right-sidebar {
+  width: 320px;
+  background-color: white;
+  border-left: 1px solid #e6e6e6;
+  padding: 15px;
+  margin-top: 10px;
+  overflow-y: auto;
+}
+
+.achievement-section h3 {
+  margin-top: 0;
+  color: #333;
+  padding-bottom: 10px;
+  border-bottom: 1px solid #eee;
+}
+
+.achievement-stats {
+  display: grid;
+  grid-template-columns: 1fr 1fr;
+  gap: 15px;
+  margin-bottom: 20px;
+}
+
+.achievement-stats .stat-item {
+  background-color: #f5f7fa;
+  padding: 15px;
+  border-radius: 4px;
+  text-align: center;
+}
+
+.achievement-stats .stat-number {
+  font-size: 24px;
+  color: #1e88e5;
+  font-weight: bold;
+  margin-bottom: 5px;
+}
+
+.achievement-stats .stat-label {
+  font-size: 14px;
+  color: #666;
+}
+
+.calendar-section {
+  margin-bottom: 20px;
+}
+
+.calendar-day {
+  height: 45px;
+  padding: 5px;
+  box-sizing: border-box;
+}
+
+.schedule-count {
+  font-size: 12px;
+  color: #1e88e5;
+  margin-top: 2px;
+}
+
+.schedule-list-section h3 {
+  margin-top: 0;
+  color: #333;
+  padding-bottom: 10px;
+  border-bottom: 1px solid #eee;
+}
+
+.calendar-section >>> .el-calendar-table .el-calendar-day {
+  height: 40px !important; /* 璁剧疆姣忔棩鍗曞厓鏍奸珮搴� */
+  padding: 0 !important;
+}
+.calendar-section >>> .el-calendar__header {
+  padding: 0 !important;
+  border: none !important;
+}
+.calendar-section >>> .el-calendar__body {
+  padding: 0 !important;
+  border: none !important;
+}
+</style>

--
Gitblit v1.8.0