2021/12/23 基于 vue element ui 封装的 X轴标题 Y轴标题 自定义表格

效果图

子组件

<template>
  <div id="tableXY1">
    <el-button
      type="text"
      icon="el-icon-back"
      @click="goBack"
      style="margin-left: 20px"
      >{{ $t("button.back") }}</el-button
    >
    <!-- 筛选 start -->
    <el-form :inline="true" class="demo-form-inline" style="text-align: center">
      <!-- 状态查询 -->
      <el-form-item :label="$t('list.status')">
        <el-select
          v-model="status"
          placeholder="请选择"
          @change="statusChange()"
        >
          <el-option
            v-for="item in statusarr"
            :key="item.value"
            :label="item.label"
            :value="item.value"
          >
          </el-option>
        </el-select>
      </el-form-item>
    </el-form>
    <!-- 筛选 end -->
    <div class="stars" ref="starsRef">
      <div class="star" v-for="(item, index) in starsCount" :key="index"></div>
    </div>
    <table style="width: 100%" class="myTable">
      <tr v-for="(item, index) in column" :key="index">
        <td
          class="column"
          style="
            display: inline-block;
            width: 200px;
            background: rgba(248, 248, 255, 0.5);
            font-weight: 700;
          "
        >
          <span :style="{ color: item.colorText ? item.colorText : '#000' }">
            {{ item.title }}
          </span>
        </td>
        <td
          class="column"
          v-for="(itemData, indexData) in tableData"
          :key="indexData"
        >
          <div v-if="item.value === 'action'">
            <el-button
              :type="itemAction.showType"
              @click="handClick(itemAction.clickMethods, itemData)"
              v-for="(itemAction, indexAction) in item.action"
              :key="indexAction"
              >{{ itemAction.clickName }}</el-button
            >
          </div>
          <div v-else>
            <div style="width: 200px">
              {{ itemData[item.value] }}
              <!-- {{ item.value }} -->
              <!-- <el-progress :text-inside="true" :stroke-width="26" :percentage="70"></el-progress> -->
              <div class="edit-datasBody-td-progress">
                <div
                v-if="item.value=='progress'"
                  class="edit-datasBody-td-progress-bg"
                  :style="{
                    background:
                      itemData[item.value] >= 0.7
                        ? '#33e35d'
                        : 0.7 > itemData[item.value] >= 0.5
                        ? '#fcdb3d'
                        : 0.5 > itemData[item.value] >= 0.2
                        ? '#fba81f'
                        : '#f87169',
                    height: itemData[item.value] * 35 + 'px',
                  }"
                ></div>
              </div>
            </div>
          </div>
        </td>
      </tr>
    </table>
    <el-pagination
      @size-change="handleSizeChange"
      @current-change="handleCurrentChange"
      :current-page="currentPage4"
      :page-sizes="[10, 20, 30, 40]"
      :page-size="100"
      layout="total, sizes, prev, pager, next, jumper"
      :total="total"
    >
    </el-pagination>
  </div>
</template>

<script>
export default {
  name: "TableXY",
  props: {
    column: {
      type: Array,
      default: function () {
        return [];
      },
    },
    tableData: {
      type: Array,
      default: function () {
        return [];
      },
    },
  },
  data() {
    return {
      pageNum: 1,
      pageSize: 10,
      currentPage4: 1,
      total: 7,
      statusarr: [
        {
          value: "选项1",
          label: "黄金糕",
        },
        {
          value: "选项2",
          label: "双皮奶",
        },
        {
          value: "选项3",
          label: "蚵仔煎",
        },
        {
          value: "选项4",
          label: "龙须面",
        },
        {
          value: "选项5",
          label: "北京烤鸭",
        },
      ],
      status: "",
      starsCount: 800, //星星数量
      distance: 900, //间距
    };
  },
  mounted() {
    this.tableData.forEach((ele, index) => {
      if (ele.progress != undefined) {
        console.log(ele.progress, index, "进度");
        console.log(ele.progress > 50 && ele.progress < 70, "50-70?");
      }
    });
    console.log(this.$refs.starsRef.children);
    let starNodes = Array.from(this.$refs.starsRef.children);
    starNodes.forEach((item) => {
      let speed = 0.2 + Math.random() * 1;
      let thisDistance = this.distance + Math.random() * 300;
      item.style.transformOrigin = `0 0 ${thisDistance}px`;
      item.style.transform = `
		        translate3d(0,0,-${thisDistance}px)
		        rotateY(${Math.random() * 360}deg)
		        rotateX(${Math.random() * -50}deg)
		        scale(${speed},${speed})`;
    });
  },
  methods: {
    handClick(methods, row) {
      this.$emit("handClick", methods, row);
    },
    handleSizeChange(val) {
      this.pageSize = val;
      console.log(`每页 ${val} 条`);
    },
    handleCurrentChange(val) {
      this.pageNum = val;
      console.log(`当前页: ${val}`);
    },
    statusChange() {
      console.log(this.status, "zzz");
    },
    goBack() {
      this.$router.push({
        path: "/Task/MyTask",
      });
    },
  },
};
</script>

<style lang="less">
#tableXY1 {
  margin-bottom: 15px;
  position: absolute;
  width: 100%;
  height: 100%;
  margin: 0;
  padding: 0;
  background: radial-gradient(
    200% 100% at bottom center,
    #f7f7b6,
    #e96f92,
    #1b2947
  );
  background: radial-gradient(
    200% 105% at top center,
    #1b2947 10%,
    #75517d 60%,
    #c8699e 75%,
    #fcc5e4
  );
  background-attachment: fixed;
  overflow: hidden;
  .stars {
    transform: perspective(500px);
    transform-style: preserve-3d;
    position: absolute;
    perspective-origin: 50% 100%;
    left: 45%;
    animation: rotate 90s infinite linear;
    bottom: 0;
  }
  .star {
    width: 2px;
    height: 2px;
    background: #f7f7b6;
    position: absolute;
    left: 0;
    top: 0;
    backface-visibility: hidden;
  }
  .el-form--inline .el-form-item__label {
    color: #fff;
  }
  .myTable {
    width: 1850px !important;
    margin: 0 auto;
    height: 830px;
    overflow: scroll;
    display: block;
    color: #fff;
    // background-color: rgb(213, 221, 248);
    border-collapse: collapse;
    text-align: center;
    tr:nth-child(1) {
      // background-color: #ebeef5;
      background-color: rgba(248, 248, 255, 0.5);
      color: #000 !important;
      font-weight: 700;
    }
  }
  /*定义滚动条高宽及背景 高宽分别对应横竖滚动条的尺寸*/
  ::-webkit-scrollbar {
    width: 14px;
    height: 14px;
    background-color: #f5f5f5;
  }

  /*定义滚动条轨道 内阴影+圆角*/
  ::-webkit-scrollbar-track {
    -webkit-box-shadow: inset 0 0 5px rgba(0, 0, 0, 0.3);
    border-radius: 10px;
    background-color: #f5f5f5;
  }

  /*定义滑块 内阴影+圆角*/
  ::-webkit-scrollbar-thumb {
    border-radius: 8px;
    background: linear-gradient(-90deg, #ced9db 0%, #141414 100%);
    // background: #fda34b;
  }

  .myTable td,
  .myTable th {
    border: 1px solid #fff;
    // color: #fff;
    height: 60px;
    line-height: 60px;
  }
  .slotMain {
    padding: 0 4px;
  }
  // 进度条
  .edit-datasBody-td-progress {
    display: inline-block;
  }
  .edit-datasBody-td-progress-bg {
    width: 20px;
  }
}
.el-pagination {
  float: none;
  text-align: center;
}
@keyframes rotate {
  0% {
    transform: perspective(400px) rotateZ(20deg) rotateX(-40deg) rotateY(0);
  }

  100% {
    transform: perspective(400px) rotateZ(20deg) rotateX(-40deg)
      rotateY(-360deg);
  }
}
</style>

父组件

<template>
  <tableXY :column="column" :table-data="tableData1" @handClick="handClick" />
</template>
<script>
import tableXY from "./table.vue";
export default {
  components: { tableXY },
  name: "Index",
  data() {
    return {
      column: [
        {
          title: "#", // 第一个单元格展示的 title
          colorBJ: "#fff",
          value: "nameX", //   第一个对象固定 横轴 标题
        },
        {
          title: "左侧1", // 必传  左侧标题
          value: "aaaa", // 必传   左侧标题  对应的value
          // colorText: "#ffffff", // 非必传  左侧标题当前单元格  字体颜色
          colorBJ: "", // 非必传  左侧标题当前单元格 背景颜色
          slot: [
            // 自定义必须传数组 暂时只支持 button   非必传
            {
              type: "button", // 自定义模板类型
              showType: "", // 按钮显示类型  以element  按钮类型 为准
              clickName: "复制", // 按钮展示汉字
              clickMethods: "copyMethods", // 按钮回调 方法名
            },
          ],
        },
        {
          title: "左侧2",
          colorBJ: "",
          value: "cccc",
        },

        {
          title: "左侧3",
          value: "eeee",
        },
        {
          title: "进度",
          value: "progress",
        },
        {
          title: "操作", // 操作列  单写  按以下格式  暂时只支持button
          value: "action", // 必传
          action: [
            {
              type: "button",
              showType: "",
              clickName: "删除",
              clickMethods: "delMethods",
            },
          ],
        },
      ],
      tableData1: [
        // {
        //   nameX: "11111",
        //   aaaa: "值b1",
        //   cccc: "值c",
        //   eeee: "值e",
        //   // progress:"0.75"
        // },

        {
          nameX: "进度",
          aaaa: "值11",
          cccc: "值cc",
          eeee: "值ee",
          progress:"0.2"
        },
        {
          nameX: "阿巴1",
          aaaa: "值11",
          cccc: "值cc",
          eeee: "值ee",
          progress:"0.4"
        },
        {
          nameX: "阿巴2",
          aaaa: "值11",
          cccc: "0.2",
          eeee: "值ee",
          progress:"0.8"

        },
        {
          nameX: "阿巴3",
          aaaa: "值11",
          cccc: "值cc",
          eeee: "值ee",
        },
        {
          nameX: "阿巴4",
          aaaa: "40",
          cccc: "值cc",
          eeee: "值ee",
          progress:"0.1"
        },
        {
          nameX: "阿巴5",
          aaaa: "值11",
          cccc: "值cc",
          eeee: "值ee",
        },
        {
          nameX: "阿巴6",
          aaaa: "值11",
          cccc: "值cc",
          eeee: "值ee",
        },
      ],
    };
  },
  methods: {
    handClick(methods, row) {
      console.log(methods, row);
    },
  },
};
</script>
遇到的问题
自定义表格分页
固定表头内容滚动
引入插件 显示进度条

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Vue基于Element UI Table的二次封装可以通过创建一个自定义的组件来实现。以下是一个简单的示例,演示了如何封装一个基于Element UI Table的组件: ```vue <template> <el-table :data="tableData" :row-key="rowKey" :height="height"> <!-- 渲染表头 --> <el-table-column v-for="column in columns" :key="column.prop" :prop="column.prop" :label="column.label"> <!-- 自定义插槽 --> <template slot-scope="scope"> <slot :column="column" :scope="scope"></slot> </template> </el-table-column> </el-table> </template> <script> export default { name: 'CustomTable', props: { tableData: { type: Array, required: true }, columns: { type: Array, required: true }, rowKey: { type: String, required: true }, height: { type: String, default: 'auto' } } } </script> ``` 在这个示例,我们创建了一个名为`CustomTable`的组件。它接受`tableData`、`columns`、`rowKey`和`height`作为props,分别表示表格数据、表格列配置、行数据的唯一标识以及表格的高度。 在模板,我们使用`el-table`和`el-table-column`来渲染Element UI表格。我们使用了`v-for`指令来循环渲染表格列,并通过`slot-scope`来传递数据给插槽。插槽可以在父组件定义,并在插槽使用自定义的组件来渲染表格单元格内容。 通过这种方式,我们可以在父组件使用这个封装自定义表格组件,并通过插槽来定制表格的内容和样式。 希望这个简单的示例能帮助到你进行Vue基于Element UI Table的二次封装。如果有任何问题,请随时提问。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值