React+CSS 实现绘制横向柱状图

前言:

页面一共分为两个结构

文字 + 渐变柱形图为一个部分,下面的标注为一个结构。

我们先看文字 + 渐变柱形图部分。

总体使用 flex 布局,左边文字部分占总体的 50%,右边的占剩余的空间部分。右侧渐变柱形部分的宽度是动态变化的。宽度是根据传入的 value,进行计算的。

<section className="graphs" style={style}>
  <div className="chart-1">
    {listData.map((item, index) => {
      return (
        <div className="chart-2" key={index}>
          <div className="chart-3">
            <span>{item.name}</span>
          </div>
          <div className="chart-4">
            <div style={{ width: `${item.percent}%`, height: 24 }} />
          </div>
        </div>
      )
    })}
  </div>
</section>
.graphs {
  width: 100%;
  position: relative;
  .chart-1 {
    .chart-2 {
      display: flex;
      .chart-3 {
        flex: 0 0 auto;
        width: 50%;
      }
      .chart-4 {
        flex: 1 1 auto;
      }
    }
  }
}

下方的标注部分,使用绝对定位,width = 50%,占父元素整体的一半,left = 50%,让其定位在右侧。这样就实现了,标注和渐变柱形部分的重叠。

这部分将 li 标签的 width = 1px,height = 100%,间隔通过 left 来动态实现。

<div className="bar-10">
  <ul className="chart-11">
    {scaleArray.map((item, itemIndex) => {
      return (
        <li
          className="chart-12"
          style={{ left: `${(100 / scaleNum) * itemIndex}%` }}
          key={itemIndex}
        >
          <span>{item}</span>
        </li>
      )
    })}
  </ul>
</div>
.bar-10 {
  position: absolute;
  top: 0px;
  height: 100%;
  width: 50%;
  left: 50%;
  box-sizing: border-box;
  .chart-11 {
    height: 100%;
    position: relative;
    width: 100%;
    .chart-12 {
      position: absolute;
      top: -3px;
      width: 1px;
      height: 89%;
      border-right: 1px solid #d7dbe0;
    }
  }
}

关于数值的计算,这里笔者是找到这一组数据里面的最大值

let maxValue = 0;
data.forEach((dataItem) => {
  if (dataItem.value > maxValue) maxValue = dataItem.value;
});

获取最大值最近的100整数

let maxScaleNum = Math.ceil(maxValue / 100) * 100

求取最小公倍数

let lcm = getLcm(maxScaleNum, scaleNum)

计算每一个数据的 value,占最小公倍数的百分比。

percent: (dataItem.value / lcm) * 100

标注的left,使用 for 循环生成。

const newArray = new Array();
for (let i = 0; i <= lcm; i += lcm / scaleNum) {
  newArray.push(i);
}

 整体代码:

import React, { useState, useEffect } from 'react';
import ReactDom from 'react-dom';
function getGcd(a, b) {
  let max = Math.max(a, b);
  let min = Math.min(a, b);
  if (max % min === 0) {
      return min;
  } else {
      return getGcd(max % min, min);
  }
}
function getLcm(a, b) {
  return a * b / getGcd(a, b);
}
const Test = ({ data, style, scaleNum = 5 }) => {
  const [listData, setListData] = useState([])
  const [scaleArray, setScaleArray] = useState([])

  useEffect(() => {
    if (scaleNum <= 0) {
      return
    }
    let maxValue = 0
    data.forEach((dataItem) => {
      if (dataItem.value > maxValue) maxValue = dataItem.value
    })
    let maxScaleNum = Math.ceil(maxValue / 100) * 100
    let lcm = getLcm(maxScaleNum, scaleNum)

    if (maxValue <= 0) {
      const newArray = [0]
      let number = 0
      for (let i = 0; i < scaleNum; i++) {
        newArray.push((number += 20))
      }
      setScaleArray(newArray)
      setListData(
        data.map((dataItem) => {
          return {
            name: dataItem.name,
            percent: 0,
            value: dataItem.value
          }
        })
      )
      return
    }
    setListData(
      data.map((dataItem) => {
        return {
          name: dataItem.name,
          percent: (dataItem.value / lcm) * 100,
          value: dataItem.value
        }
      })
    )
    const newArray = new Array()
    for (let i = 0; i <= lcm; i += (lcm / scaleNum)) {
      newArray.push(i)
    }
    setScaleArray(newArray)
  }, [data, scaleNum])

  return (
    <section className="graphs" style={style}>
      <div className="chart-1">
        {listData.map((item, index) => {
          return (
            <div className="chart-2" key={index}>
              <div className="chart-3">
                <span>{item.name}</span>
              </div>
              <div className="chart-4">
                <div style={{ width: `${item.percent}%`, height: 24 }} />
              </div>
            </div>
          )
        })}
      </div>
      <div className="bar-5">
        <ul className="chart-6">
          {scaleArray.map((item, itemIndex) => {
            return (
              <li
                className="chart-7"
                style={{ left: `${(100 / scaleNum) * itemIndex}%` }}
                key={itemIndex}
              >
                <span>{item}</span>
              </li>
            )
          })}
        </ul>
      </div>
    </section>
  )
}
ReactDom.render(<Test style={{ width: 440 }}
          scaleNum={6}
          data={[
            {
              name: '西瓜',
              value: 40
            },
            {
              name: '菠萝',
              value: 56
            },
            {
              name: '香蕉',
              value: 47
            }
          ]} />, document.getElementById('app'));
      

运行结果:

到此这篇关于React+CSS 实现绘制横向柱状图的文章就介绍到这了,更多相关React+CSS 柱状图内容请搜索我们以前的文章或继续浏览下面的相关文章希望大家以后多多支持我们!

(0)

相关推荐

  • React中编写CSS实例详解

    目录 正文 内联样式 普通的CSS css modules css in js 样式组件 引入外部变量 默认值 引入全局样式 provider 样式继承 动态添加class 正文 目前,前端最流行的开发方式是组件化,而CSS的设计本身就不是为组件化而生的,所以在目前组件化的框架中都在需要一种合适的CSS解决方案 在组件化开发环境下的CSS,应该满足如下需求: 可以编写局部css: css具备自己的具备作用域,不会随意污染其他组件内的元素 可以编写动态的css: 可以获取当前组件的一些状态,根据状

  • react项目引入scss的方法

    首先下载依赖 yarn add sass-loader node-sass 然后在项目路径 node_modules/react-scripts/config/webpack.config.js 打开文件 找到 加入红线内的代码 { test:/\.scss$/, loaders: ['style-loader', 'css-loader', 'sass-loader'] }, 就可以使用scss了 知识点扩展: React pwa的配置 在到webpack配置文件中添加插件 const Wor

  • 详解react的两种动态改变css样式的方法

    第一种:动态添加class,以点击按钮让文字显示隐藏为demo import React, { Component, Fragment } from 'react'; import './style.css'; class Demo extends Component{ constructor(props) { super(props); this.state = { display: true } this.handleshow = this.handleshow.bind(this) thi

  • React+CSS 实现绘制竖状柱状图

    前言: 页面结构分为两个部分,柱状图 + 文字为一部分,标注为为一部分. 先来看柱状图 + 文字这一部分. 宽度定为 width: 55, height 高度使用百分比进行动态变化.整个部分使用 flex 布局.通过 justify-content: space-around; 属性,对里面的项目进行排列.项目 item 同样使用 flex 布局,这个是对 柱状图 + 文字 进行整体的排列. <div className="crosswise_diagram_top"> {

  • 如何用react优雅的书写CSS

    1.内联样式 优点:这种方式较为简单,一目了然,给标签添加style属性. 缺点: 这种方式可以造成项目结构较为臃肿,造成css命名冲突. import React, { Component } from 'react' import PropTypes from 'prop-types' export default class index extends Component { static propTypes = { title: PropTypes.string } render() {

  • React css-in-js基础介绍与应用

    目录 1. 介绍 2. 使用 1. 介绍 CSS-in-JS 是一种技术,而不是一个具体的库实现.简单来说 CSS-in-JS 就是将应用的CSS样式写在 JavaScript 文件里面,而不是独立为一些 css,scss 或 less 之类的文件,这样你就可以在 CSS 中使用一些属于JS的诸如模块声明,变量定义,函数调用和条件判断等语言特性来提供灵活的可扩展的样式定义.CSS-in-JS 在 React 社区的热度是最高的,这是因为 React 本身不会管用户怎么去为组件定义样式的问题,而

  • ReactJs设置css样式的方法

    前段时间看了React Native,但是感觉在安卓反面的开发并不成熟.有较多功能有待完善,而且自己在实际运用的过程中在一些模块上遇到了不晓得阻力,又苦于网上没有找到那么多资源.于是打算先放一段时间,还是回过头来看ReactJs吧. React颠覆了html的传统思维,代码基本都写在<script  type="text/babel"></script>标签里面.我开发的时候采用的是IDEA,当然也可以使用atom或者webstor.使用IDEA时,需要在set

  • react使用CSS实现react动画功能示例

    本文实例讲述了react使用CSS实现react动画功能.分享给大家供大家参考,具体如下: react动画: import React, { Component } from 'react'; class Boss extends Component { constructor(props) { super(props); this.state = { isShow:true } this.toTogger=this.toTogger.bind(this) } render() { return

  • React+CSS 实现绘制横向柱状图

    前言: 页面一共分为两个结构 文字 + 渐变柱形图为一个部分,下面的标注为一个结构. 我们先看文字 + 渐变柱形图部分. 总体使用 flex 布局,左边文字部分占总体的 50%,右边的占剩余的空间部分.右侧渐变柱形部分的宽度是动态变化的.宽度是根据传入的 value,进行计算的. <section className="graphs" style={style}> <div className="chart-1"> {listData.map

  • python绘制横向水平柱状条形图

    python绘制横向水平柱状条形图Bar,供大家参考,具体内容如下 import matplotlib import random import matplotlib.pyplot as plt   # 中文乱码和坐标轴负号处理. matplotlib.rc('font', family='SimHei', weight='bold') plt.rcParams['axes.unicode_minus'] = False   #城市数据. city_name = ['北京', '上海', '广州

  • jQuery插件FusionCharts绘制2D柱状图和折线图的组合图效果示例【附demo源码】

    本文实例讲述了jQuery插件FusionCharts绘制2D柱状图和折线图的组合图效果.分享给大家供大家参考,具体如下: 1.设计思路 (1)了解组合图的特性以及用法,选用图的类型: (2)设计出两根柱子和两根折线,分开展示. 2.设计步骤 (1)设计页面 index.html: <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loos

  • jQuery插件HighCharts绘制2D柱状图、折线图的组合双轴图效果示例【附demo源码下载】

    本文实例讲述了jQuery插件HighCharts绘制2D柱状图.折线图的组合双轴图效果.分享给大家供大家参考,具体如下: 1.实例代码: <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>HighCharts 2D柱状图.折线图的组合双轴图</title> <script type="text/javascript"

  • jQuery插件HighCharts绘制2D柱状图、折线图和饼图的组合图效果示例【附demo源码下载】

    本文实例讲述了jQuery插件HighCharts绘制2D柱状图.折线图和饼图的组合图效果.分享给大家供大家参考,具体如下: 1.实例代码: <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>HighCharts 2D柱状图.折线图和饼图的组合图</title> <script type="text/javascript"

  • Python绘制堆叠柱状图的实例

    有个朋友要求帮忙绘制堆叠柱状图,查阅了一些文档之后也算是完成了,只是一个小demo,下面我就记录一下. 1.什么是堆叠柱状图 与并排显示分类的分组柱状图不同,堆叠柱状图将每个柱子进行分割以显示相同类型下各个数据的大小情况.它可以形象的展示一个大分类包含的每个小分类的数据,以及各个小分类的占比,显示的是单个项目与整体之间的关系.效果图如下: 2.数据展示 这里展示了部分数据,主要是treatment就是对应的上图分类一,分类二:species就是对应的分组:ra就是对应的各个分组的比例. 3.Py

  • Python实现绘制双柱状图并显示数值功能示例

    本文实例讲述了Python实现绘制双柱状图并显示数值功能.分享给大家供大家参考,具体如下: # -*- coding:utf-8 -*- #! python3 import matplotlib.pyplot as plt import mpl_toolkits.mplot3d #定义函数来显示柱状上的数值 def autolabel(rects): for rect in rects: height = rect.get_height() plt.text(rect.get_x()+rect.

  • 如何在CSS中绘制曲线图形及展示动画

    理解 box-shadow 首先,回顾一下box-shadow这个属性.基本属性用法就是给元素创造一层阴影. 再简单提一下,本文会用到的关于阴影的第一个技巧: 使用阴影复制图像/投影图像 当 box-shadow 的第三.第四个参数模糊半径和扩张半径都为 0 的时候,我们可以得到一个和元素大小一样的阴影: div { width: 80px; height: 80px; border: 1px solid #333; box-sizing: border-box; box-shadow: 80p

  • Echarts Bar横向柱状图实例代码

    目录 横向柱状图 动态更新数据和样式 解决 echarts 宽高自适应问题 纵向柱状图 纵向柱状图实现 坐标指示器背景渐变色 柱体设置不同颜色 柱状图上方显示数值 tooltip 提示框自定义 总体实现 总结 接上一篇# Echart Bar柱状图样式详解续写,可以先看看上一篇,不看的话,影响也不是特别大. 横向柱状图 动态更新数据和样式 实现数据按月统计和按日统计的动态切换.按月统计时,每个月数据都会展示,x 轴显示 12 个标签:按日统计时,x 轴不完全显示所有标签,间隔显示,而且柱状体的宽

随机推荐