antd table列选中效果实现

news2024/12/26 23:35:16

前言

开发中有一个需要呈现不同时间点各个气象要素的值需求,我觉得一个table可以实现这类数据的展示,只是因为时间点时关注的重点,所以需要列选中效果,清晰的展示时间点下的要素数据。我选择的是antd的table组件,这个组件没有列选中的效果,所以还是需要自己动手丰衣足食,改造一下。

分析

这个功能的难点在于列选中效果,我们需要给他一个背景加上边框,虽然antd的table没有列选中效果,但是它提供了customCell,customHeaderCell,我们可以根据这些回调函数的特点灵活使用实现列选中效果。

参数说明类型用途
customCell设置单元格属性Function(record, rowIndex)根据activeColIndex参数,为选中列包含的单元格添加class,并且为最后一个单元格加上“lastCol”的class,因为最后一个需要加上下边框
customHeaderCell设置头部单元格属性Function(column)主要为选中列的第一个单元格加上class,因为表头单元格需要加上上边框

源代码

/**
* CustomTable.vue
* @Author ZhangJun
* @Date  2024/5/28 11:39
**/
<template>
  <a-spin :spinning="loading">
    <template v-if="dataSource&&dataSource.length>0">
      <a-table :pagination="false"
               :columns="getColumns"
               :dataSource="dataSource"
               rowKey="itemCode"
               :scroll="{y:dataSource.length>9?'280px':false}"></a-table>
    </template>

    <custom-empty v-else
                  desc="暂无机场高影响数据"
                  sub-title="NO DATA IS AVAILABLE"
                  style="margin: 8% auto;"></custom-empty>
  </a-spin>
</template>

<script>
import CustomEmpty from "@/components/CustomEmpty.vue";
import moment from "moment";
import {HighImpactWeatherApi} from "@/api/HighImpactWeatherApi";
import WizStyleHelper from "@/utils/leaflet/WizStyleHelper";
import BigNumber from "bignumber.js";

export default {
  name: "CustomTable",
  components: {CustomEmpty},
  props: {
    currentDateTime: {type: String},
    //选择的可显示的要素
    visibleItemsConfig: {type: Array, default: () => ([])},
    airportId: {type: String}
  },
  data() {
    return {
      loading: false,
      itemDefaultConfig: {
        visibility: {unit: 'm', name: '能见度'},
        wins: {unit: 'm/s', name: '风'},
        rain: {unit: 'mm', name: '雨'},
        lowTemperature: {unit: '℃', name: '低温'},
      },
      itemColors: {},//要素配色缓存
      dataSource: [],
      activeColIndex: -1,//现在选中的列
    }
  },
  computed: {
    /**
     * 动态获取表格的columns
     * @returns {*[]}
     */
    getColumns() {
      //获取各种要素的颜色
      let colors = this.visibleItemsConfig?.map(({styleCode}) => {
        return [styleCode, this.getItemColor(styleCode)];
      }) || [];
      this.itemColors = Object.fromEntries(colors);

      //要素名称列自定义
      let itemCodeCustomRender = (text) => {
        let {styleCode, pCode, name} = this.visibleItemsConfig?.find(({code}) => code === text);
        let unit = this.itemDefaultConfig?.[pCode]?.unit || '';
        let color = this.itemColors?.[styleCode];
        return <div class="flex justify-end" style="width:80px;">
          {name}
          <div style={{padding: '0 4px', color}}>{unit}</div>
        </div>
      };

      let dayDate = moment(this.currentDateTime, 'YYYYMMDDHHmmss');
      let columns_temp = [];
      for (let i = 0; i < 24; i++) {
        let dataIndex = dayDate.clone().add(i, 'hour');
        columns_temp = [...columns_temp, {
          align: 'center',
          title: dataIndex.format('HH:mm'),
          dataIndex: dataIndex.format('YYYYMMDDHH'),
          key: dataIndex.format('YYYYMMDDHH'),
          className: 'customCell',
          //为了实现列选中高亮效果
          customCell: (record, rowIndex) => {
            return {
              class: {
                activeCol: i === this.activeColIndex,//如果该cell所以选中的那一列中,就在上这个样式
                lastCol: rowIndex === this.dataSource.length - 1//如果该cell属于选中列的最后一个cell,就加上这个样式,因为要在这个cell加上下边框
              },
              on: {
                mouseenter: (e) => {
                  //赋值当前cell所在的列索引,为高亮列做准备
                  this.activeColIndex = i;
                },
                mouseleave: (event) => {
                  //清空
                  this.activeColIndex = -1;
                }
              }
            }
          },
          //头部需要加上上边框
          customHeaderCell: (column) => {//自定义表头
            return {
              class: {
                activeCol: i === this.activeColIndex,//该表头为选中列的表头,加上这个样式,因为列头需要加上边框
                headerCell: true
              },
            }
          },
          customRender: (text, record) => {
            text = Number(text);
            if (text >= 1000) {
              text = new BigNumber(text).toFixed(0);
            } else if (text < 1000 && text >= 100) {
              text = new BigNumber(text).toFixed(0);
            } else if (text < 100 && text >= 10) {
              text = new BigNumber(text).toFixed(1);
            } else if (text < 10 && text > 0) {
              text = new BigNumber(text).toFixed(2);
            }

            let {itemCode} = record;
            let {styleCode, legendImage, name, pCode} = this.visibleItemsConfig?.find(({code}) => code === itemCode);
            let unit = this.itemDefaultConfig?.[pCode]?.unit || '';
            //如果有图标就显示图标
            if (legendImage) {
              if (text > 0) {
                return <img height="15" title={`${name}${text} ${unit}`} src={legendImage} alt={name}/>;
              }
              return <div style={{
                padding: '4px 0',
                overflow: 'hidden',
                width: '28px',
                textAlign: 'center',
                cursor: 'default',
              }} title={`${name}${text} ${unit}`}>
                -
              </div>
            }

            let color = this.itemColors?.[styleCode];
            return <div style={{
              background: text > 0 ? color : '',
              padding: '4px 0',
              overflow: 'hidden',
              width: '28px',
              textAlign: 'center',
              cursor: 'default',
            }} title={`${name}${text} ${unit}`}>
              {text}
            </div>;
          }
        }];
      }

      return [{
        title: '',
        dataIndex: 'itemCode',
        key: 'itemCode',
        className: 'customCell',
        align: 'right',
        width: 80,
        customRender: itemCodeCustomRender,
      }, ...columns_temp];
    },
  },
  methods: {
    /**
     * 获取数据
     */
    fetchData() {
      if (this.currentDateTime && this.visibleItemsConfig?.length > 0 && this.airportId) {
        let startTime = moment(this.currentDateTime, 'YYYYMMDDHH').format('YYYYMMDDHH');
        let endTime = moment(this.currentDateTime, 'YYYYMMDDHH').add(23, 'hour').format('YYYYMMDDHH');
        let itemCodes = this.visibleItemsConfig?.map(({code}) => code).join(',');
        this.loading = true;
        HighImpactWeatherApi.getHighImpactSingleAirportFutureImpactInfo({
          startTime,// 2024051102,
          endTime,
          itemCodes,
          airportId: this.airportId
        }).then((res = {}) => {
          let {data} = res;
          if (data) {
            this.dataSource = itemCodes.split(',').map(itemCode => {
              return {itemCode, ...data[itemCode]};
            });
          }
        }, () => {
          this.dataSource = [];
        }).finally(() => {
          this.loading = false;
        });
      }
    },
    /**
     * 获取站点图例颜色
     * @param styleCode 配色code
     */
    getItemColor(styleCode) {
      if (styleCode) {
        const wizStyleHelper = new WizStyleHelper();
        const colorConfig = wizStyleHelper.getStyleImpl(styleCode);
        let {colors: [, color]} = colorHelper.getColorImpl(colorConfig.shaded.color).colorPalettes;
        return `rgba(${color.join(',')})`;
      }
      return undefined
    },
  },
  mounted() {
    this.fetchData();
    this.$watch(() => [this.currentDateTime, this.airportId, this.visibleItemsConfig], ([params1, params2, params3]) => {
      this.fetchData();
    });
  }
}
</script>

<style scoped lang="less">
/deep/ .customCell {
  background: transparent;
  padding: 4px 0 !important;
  border-color: transparent;
  border-width: 0 1px 0 1px;

  * {
    font-family: D-DIN, sans-serif;
    font-size: 12px;
    font-weight: normal;
    line-height: 12px;
    text-align: center;
    letter-spacing: 0;
    color: rgba(255, 255, 255, 0.6);
    white-space: nowrap;
  }
}


/deep/ .customRow {
  > td {
    font-family: D-DIN, sans-serif;
    font-size: 12px;
    font-weight: normal;
    line-height: normal;
    text-align: center;
    letter-spacing: 0;

    color: white;
  }
}

/deep/ .ant-table-header {
  background: transparent;

  &.ant-table-hide-scrollbar {
    margin-right: -0.69rem;
  }
}

/deep/ .ant-table-body {
  background: transparent !important;

  &::-webkit-scrollbar {
    /* 对应纵向滚动条的宽度 */
    width: 0.425rem;
    /* 对应横向滚动条的宽度 */
    height: 0.425rem;
  }

  &::-webkit-scrollbar-thumb {
    background: #198CF8;
    border-radius: 32px;
  }

  &::-webkit-scrollbar-track {
    background: rgba(7, 28, 65, 0.5);
    border-radius: 32px;
  }

  .ant-table-tbody {
    > tr:hover:not(.ant-table-expanded-row):not(.ant-table-row-selected) > td {
      background: unset;
    }
  }
}

/deep/ .headerCell {
  border-width: 1px 1px 0;
  border-style: solid;
  border-color: transparent;
}

/deep/ .lastCol {
  border-width: 0 1px 1px;
  border-style: solid;
  border-color: transparent;
}

/deep/ .activeCol {
  background: rgba(77, 136, 255, 0.19) !important;
  //border-width: 0 1px 0 1px;
  border-style: solid;
  border-color: #5FACFF;

  &.headerCell {
    border-radius: 2px 2px 0 0;
  }

  &.lastCol {
    border-radius: 0 0 2px 2px;
  }
}
</style>

效果

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1715349.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

每日复盘-20240529

20240529 六日涨幅最大: ------1--------300956--------- 英力股份 五日涨幅最大: ------1--------301361--------- 众智科技 四日涨幅最大: ------1--------301361--------- 众智科技 三日涨幅最大: ------1--------300637--------- 扬帆新材 二日涨幅最大: ------1--------30…

【busybox记录】【shell指令】rmdir

目录 内容来源&#xff1a; 【GUN】【rmdir】指令介绍 【busybox】【rmdir】指令介绍 【linux】【rmdir】指令介绍 使用示例&#xff1a; 删除空目录 - 默认 删除dirname下的所有空目录&#xff0c;包括因删除其他目录而变为空的目录 常用组合指令&#xff1a; 指令不…

数据结构(七)查找

2024年5月26日一稿&#xff08;王道P291&#xff09; 7.1 查找的基本概念 7.2 顺序查找和折半查找 7.2.1 顺序查找 7.2.2 折半查找 7.2.3 分块查找 7.3 树形查找 7.3.1 二叉排序树(BST) 7.3.2 平衡二叉树 7.4 B树和B树 7.4.1 B树及其基本操作 7.4.2 B树的基本概念 7.5 散列&…

UVa11604 General Sultan

UVa11604 General Sultan 题目链接题意分析AC 代码 题目链接 UVA - 11604 General Sultan 题意 给出一些0和1组成的模式串&#xff0c;问是否存在一个串使得有多种方案将这个串分解成模式串。    给一个包含n&#xff08;n≤100&#xff09;个符号的二进制编码方式&#xff…

HTTP Digest Access Authentication Schema

HTTP Digest Access Authentication Schema 背景介绍ChallengeResponse摘要计算流程总结参考 背景 本文内容大多基于网上其他参考文章及资料整理后所得&#xff0c;并非原创&#xff0c;目的是为了需要时方便查看。 介绍 HTTP Digest Access Authentication Schema&#xff…

Spring创建对象的多种方式

一、对象分类 简单对象&#xff1a;使用new Obj()方式创建的对象 复杂对象&#xff1a;无法使用new Obj()方式创建的对象。例如&#xff1a; 1. AOP创建代理对象。ProxyFactoryBean; 2. Mybatis中的SqlSessionFactoryBean; 3. Hibernate中的SessionFactoryBean。二、创建对象方…

MFC工控项目实例一主菜单制作

1、本项目用在WIN10下安装的vc6.0兼容版实现。创建项目名为SEAL_PRESSURE的MFC对话框。在项目res文件下添加相关256色ico格式图片。 2、项目名称&#xff1a;密封压力试验机 主菜单名称&#xff1a; 系统参数 SYS_DATA 系统测试 SYS_TEST 选择型号 TYP_CHOICE 开始试验 TES_STA…

内存函数<C语言>

前言 前面两篇文章介绍了字符串函数&#xff0c;不过它们都只能用来处理字符串&#xff0c;C语言中也内置了一些内存函数来对不同类型的数据进行处理&#xff0c;本文将介绍&#xff1a;memcpy()使用以及模拟实现&#xff0c;memmove()使用以及模拟实现&#xff0c;memset()使用…

越来越多的连锁企业选择开源连锁收银系统

连锁企业的收银系统作为其信息化的基础&#xff0c;随着运营的复杂化&#xff0c;越来越多的连锁企业选择开源连锁收银系统来满足其日常经营需要。商淘云为大家分享连锁企业选择开源连锁收银系统的三大原因&#xff0c;大家点赞收藏。 首先是灵活性和定制性强&#xff0c;连锁企…

k210数字识别 笔记2 (串口通信)

这个模型识别的还可以&#xff0c;离近点 识别率高达0.9 资源&#xff1a; 链接&#xff1a;https://pan.baidu.com/s/1D4ubJGMptqop1x_Nf8KqfQ?pwd1234 提取码&#xff1a;1234 一&#xff1a;报错解决 报错的意思应该是模型文件错误 原程序可以在sd卡运行&#xff0c;但…

stm32学习-CubeIDE使用技巧

1.hex文件生成 右键工程 2.仿真调试 3.常用快捷键 作用快捷键代码提示alt/代码注释/反注释ctrl/ 4.项目复制 复制项目&#xff0c;将ioc文件名改为项目名即可图形化编辑

刷爆leetcode第六期

题目一 用队列实现栈 请你仅使用两个队列实现一个后入先出&#xff08;LIFO&#xff09;的栈&#xff0c;并支持普通栈的全部四种操作&#xff08;push、top、pop 和 empty&#xff09;。 实现 MyStack 类&#xff1a; void push(int x) 将元素 x 压入栈顶。 int pop() 移除…

华为昇腾310 ATC模型转换工具安装

参考: https://bbs.huaweicloud.com/blogs/393282?utm_source=zhihu&utm_medium=bbs-ex&utm_campaign=other&utm_content=content https://www.hiascend.com/document/detail/zh/canncommercial/601/inferapplicationdev/atctool/atctool_0004.html 1、基本工具…

idm软件是做什么的 IDM是啥软件 idm软件怎么下载 idm软件怎么下载

一、IDM是啥软件 IDM 是由美国 Tonec 公司开发的 Windows 软件&#xff0c;该软件最初于 2005 年发布。IDM全称Internet Download Manager&#xff0c;是一款Windows平台老牌而功能强大的下载加速器&#xff0c;专注于互联网数据下载。这款软件是一款不错的轻量级下载工具&…

【EI会议】第二届计算机、物联网与智慧城市国际会议

第二届计算机、物联网与智慧城市国际会议 快速通道 投稿链接&#xff1a;loading 截稿时间&#xff1a;9月15日 检索&#xff1a;EI检索 一、会议信息 大会官网&#xff1a;www.ciotsc.org 会议地点&#xff1a;湖南株洲 会议时间&#xff1a;2023年11月15日-17日 二、征稿主…

Strust2 远程代码执行漏洞[s2-005]

漏洞复现环境搭建请参考 http://t.csdnimg.cn/rZ34p kali切换jdk版本请参考 Kali安装JAVA8和切换JDK版本的详细过程_kali安装jdk8-CSDN博客 漏洞原理 Strust2会将http的每个参数名解析成为OGNL语句执行&#xff0c;OGNL表达式通过#来访问Struts的对象&#xff0c;并且通过过…

光耦的工作原理

一、光电耦合器简介 光电耦合器主要是一种围绕光作为媒介的光电转换元器件&#xff0c;能够实现光到电、电到光之间的自由转换。我们又可以称之为光电隔离器&#xff0c;之所以这么称呼&#xff0c;主要是因为光电耦合器能够很好的对电路中的电信号起到隔离的作用。有效的保护…

C语言 指针——指针变量做函数参数

目录 指针变量的解引用 为什么要用指针变量做函数参数&#xff1f; 演示Call by value 指针变量的解引用 为什么要用指针变量做函数参数&#xff1f; 演示Call by value

民国漫画杂志《时代漫画》第32期.PDF

时代漫画32.PDF: https://url03.ctfile.com/f/1779803-1248635561-0ae98a?p9586 (访问密码: 9586) 《时代漫画》的杂志在1934年诞生了&#xff0c;截止1937年6月战争来临被迫停刊共发行了39期。 ps: 资源来源网络!

【传知代码】BERT论文解读及情感分类实战-论文复现

文章目录 概述原理介绍BERT模型架构任务1 Masked LM&#xff08;MLM&#xff09;任务2 Next Sentence Prediction (NSP)模型输入下游任务微调GLUE数据集SQuAD v1.1 和 v2.0NER 情感分类实战IMDB影评情感数据集数据集构建模型构建 核心代码超参数设置训练结果注意事项 小结 本文…