董国庆
2025-04-21 e62f2e0a1a97ba272125508d0eafba03bf8afc49
选择组件的共用组件
1个文件已修改
5个文件已添加
228 ■■■■■ 已修改文件
src/assets/public/modalImg1.png 补丁 | 查看 | 原始文档 | blame | 历史
src/assets/public/modalImg2.png 补丁 | 查看 | 原始文档 | blame | 历史
src/assets/public/modalImg3.png 补丁 | 查看 | 原始文档 | blame | 历史
src/assets/public/modalImg4.png 补丁 | 查看 | 原始文档 | blame | 历史
src/components/AddComponentDialog/index.vue 210 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/dataManagement/testResultReport/detail.vue 18 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/assets/public/modalImg1.png
src/assets/public/modalImg2.png
src/assets/public/modalImg3.png
src/assets/public/modalImg4.png
src/components/AddComponentDialog/index.vue
New file
@@ -0,0 +1,210 @@
<template>
  <el-dialog
    title="新增组件"
    :visible.sync="visible"
    width="70%"
    :close-on-click-modal="false"
    custom-class="add-component-dialog"
    @close="handleClose"
  >
    <div class="component-cards">
      <div
        v-for="(item, index) in componentTypes"
        :key="index"
        class="component-card"
        :class="{ active: selectedType === item.type }"
        :data-type="item.type"
        @click="handleSelect(item)"
      >
        <div class="card-icon">
          <img :src="item.icon" :alt="item.title" />
        </div>
        <div class="card-content">
          <div class="card-title">{{ item.title }}</div>
          <div class="card-desc">{{ item.description }}</div>
        </div>
      </div>
    </div>
    <div slot="footer" class="dialog-footer select-member-footer">
      <el-button @click="handleClose">取消</el-button>
      <el-button type="primary" @click="handleConfirm">保存</el-button>
    </div>
  </el-dialog>
</template>
<script>
export default {
  name: 'AddComponentDialog',
  props: {
    visible: {
      type: Boolean,
      default: false
    }
  },
  data() {
    return {
      selectedType: '',
      componentTypes: [
        {
          type: 'richText',
          title: '富文本',
          icon: require('@/assets/public/modalImg1.png'),
          description: '富文本组件可以支持文本格式化(如字体、颜色、大小等)、图片插入、链接添加等多种功能。'
        },
        {
          type: 'customTable',
          title: '自定义表格',
          icon: require('@/assets/public/modalImg2.png'),
          description: '自定义表格组件可以支持自定义表头(包括配置表头类型、默认值、权限等)'
        },
        {
          type: 'fileUpload',
          title: '文件上传',
          icon: require('@/assets/public/modalImg3.png'),
          description: '支持上传.docx/.pdf/.xlsx/.txt文件'
        },
        {
          type: 'imageUpload',
          title: '图片上传',
          icon: require('@/assets/public/modalImg4.png'),
          description: '富文本组件可以支持文本格式化(如字体、颜色、大小等)、图片插入、链接添加等多种功能。'
        }
      ]
    }
  },
  methods: {
    handleSelect(item) {
      this.selectedType = item.type
    },
    handleClose() {
      this.$emit('update:visible', false)
      this.selectedType = ''
    },
    handleConfirm() {
      if (!this.selectedType) {
        this.$message.warning('请选择要添加的组件类型')
        return
      }
      this.$emit('confirm', this.selectedType)
      this.handleClose()
    }
  }
}
</script>
<style lang="less" scoped>
.add-component-dialog {
  ::v-deep .el-dialog__header {
    border-bottom: 1px solid #e4e7ed;
    padding: 20px;
    margin: 0;
  }
  ::v-deep .el-dialog__body {
    padding: 30px;
  }
  .component-cards {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(220px, 1fr));
    gap: 20px;
    padding: 10px;
    .component-card {
      display: flex;
      flex-direction: column;
      align-items: center;
      padding: 30px 20px;
      background: #fff;
      border-radius: 10px;
      border: 1px solid #e4e7ed;
      cursor: pointer;
      transition: all 0.3s;
      &[data-type="richText"] {
        background: linear-gradient(180deg, #FFF1DE 0%, rgba(255,249,241,0) 100%);
        border: 1px solid rgba(249,171,20,0.5);
      }
      &[data-type="customTable"] {
        background: linear-gradient(180deg, rgba(5,112,255,0.14) 1%, rgba(234,243,255,0) 100%);
        border: 1px solid rgba(71,145,255,0.5);
      }
      &[data-type="fileUpload"] {
        background: linear-gradient(180deg, #E0FAEA 0%, rgba(224,250,234,0) 100%);
        border: 1px solid rgba(87,180,131,0.5);
      }
      &[data-type="imageUpload"] {
        background: linear-gradient(180deg, #F5EDFF 0%, rgba(234,243,255,0) 100%);
        border: 1px solid rgba(115,83,247,0.5);
      }
      &.active {
        transform: translateY(-4px);
        box-shadow: 0 4px 16px 0 rgba(0, 0, 0, 0.15);
        &[data-type="richText"] {
          border-color: rgba(249,171,20,0.8);
          background: linear-gradient(180deg, #FFF1DE 0%, rgba(255,249,241,0.5) 100%);
        }
        &[data-type="customTable"] {
          border-color: rgba(71,145,255,0.8);
          background: linear-gradient(180deg, rgba(5,112,255,0.2) 1%, rgba(234,243,255,0.5) 100%);
        }
        &[data-type="fileUpload"] {
          border-color: rgba(87,180,131,0.8);
          background: linear-gradient(180deg, #E0FAEA 0%, rgba(224,250,234,0.5) 100%);
        }
        &[data-type="imageUpload"] {
          border-color: rgba(115,83,247,0.8);
          background: linear-gradient(180deg, #F5EDFF 0%, rgba(234,243,255,0.5) 100%);
        }
      }
      .card-icon {
        width: 92px;
        height: 92px;
        margin-bottom: 16px;
        img {
          width: 100%;
          height: 100%;
          object-fit: contain;
        }
      }
      .card-content {
        text-align: center;
        .card-title {
          font-size: 16px;
          font-weight: 500;
          color: #303133;
          margin-bottom: 8px;
        }
        .card-desc {
          font-size: 14px;
          color: #909399;
          line-height: 1.4;
        }
      }
    }
  }
  .dialog-footer {
    text-align: center;
    padding-top: 20px;
    .el-button {
      min-width: 120px;
    }
  }
}
</style>
src/views/dataManagement/testResultReport/detail.vue
@@ -280,6 +280,12 @@
      :visible.sync="checkoutResultVisible"
      :data="currentCheckoutResult"
    />
    <!-- 新增组件弹窗 -->
    <add-component-dialog
      v-if="showNewDialog"
      :visible.sync="showNewDialog"
      @confirm="handleAddComponent"
    />
  </Card>
</template>
@@ -288,16 +294,19 @@
import moment from "moment";
import EvaluationDialog from "./components/evaluation-dialog.vue";
import CheckoutResult from "./components/checkout-result.vue";
import AddComponentDialog from "@/components/AddComponentDialog";
export default {
  name: "AddProject",
  components: {
    ExperimentalScheduling,
    EvaluationDialog,
    CheckoutResult
    CheckoutResult,
    AddComponentDialog
  },
  data() {
    return {
      showNewDialog: true,
      dialogVisible: false,
      schedulingDialogVisible: false,
      isEdit: false,
@@ -605,7 +614,12 @@
    // 更新弹窗显示状态
    updateEvaluationDialogVisible(value) {
      this.evaluationDialogVisible = value;
    }
    },
    // 处理新增组件
    handleAddComponent(type) {
      console.log('选择的组件类型:', type);
      // TODO: 根据type处理不同类型组件的添加逻辑
    },
  },
};
</script>