数据可视化-echarts入门、常见图表案例、超详细配置解析及项目案例

35 篇文章 476 订阅
17 篇文章 19 订阅

文章目录

数据可视化-echarts入门、常见图表案例及项目案例

一、简介

一、数据可视化简介

什么是数据可视化?

在这里插入图片描述

数据可视化是将数据库中每一个数据项作为单个图元元素表示,大量的数据集构成数据图像,同时将数据的各个属性值以多维数据的形式表示,可以从不同的维度观察数据,从而对数据进行更深入的观察和分析;主要是借助于图形化手段,清晰有效地传达与沟通信息

二、echarts简介

ECharts,缩写来自Enterprise Charts,商业级数据图表,一个纯Javascript的图表库,可以流畅的运行在PC和移动设备上,兼容当前绝大部分浏览器(IE6/7/8/9 /10/11,chrome,firefox,Safari等),底层依赖轻量级的Canvas类库ZRender,提供直观,生动,可交互,可高度个性化定制的数据可视化图表。创新的拖拽重计算、数据视图、值域漫游等特性大大增强了用户体验,赋予了用户对数据进行挖掘、整合的能力。

支持折线图(区域图)、柱状图(条状图)、散点图(气泡图)、K线图、饼图(环形图)、雷达图(填充雷达 图)、和弦图、力导向布局图、地图、仪表盘、漏斗图、事件河流图等12类图表,同时提供标题,详情气泡、图例、值域、数据区域、时间轴、工具箱等7个可交 互组件,支持多图表、组件的联动和混搭展现。

在这里插入图片描述

三、echarts特点

1.可视化类型丰富,并且提供了吸引眼球的特效

2.多渲染方案,能够跨平台使用,支持以 Canvas、SVG(4.0+)、VML 的形式渲染图表。

3.多维数据的支持以及丰富的视觉编码手段,例如 对于传统的散点图等,传入的数据也可以是多个维度的。

4.多种数据格式无需转换直接使用,内置的 dataset 属性(4.0+)支持直接传入包括二维表,key-value 等多种格式的数据源,此外还支持输入 TypedArray 格式的数据。

5.无障碍访问(4.0+),能够支持自动根据图表配置项智能生成描述,使得盲人可以在朗读设备的帮助下了解图表内容,让图表可以被更多人群访问!

丰富的图表类型
ECharts 提供了常规的折线图、柱状图、散点图、饼图、k线图,用于统计的盒形图,用于地理数据可视化的地图、热力图、线图,用于数据关系可视化的关系图,treemap,多维数据可视化的平行坐标,还有用于BI的漏斗图,仪表盘,并且支持图与图之间的混搭

动态数据
ECharts由数据驱动,数据的改变驱动图表展现的改变。因此动态数据的实现也变得异常简单,只需获取数据,填入数据,ECharts会找到两组数据之间的差异然后通过合适的动画去表现数据的变化。

移动端的优化
流量珍贵的移动端需要图表库的体积尽量小。ECharts和ZRender代码的重构,带来了核心部分体积的减小。ECharts和ZRender代码的重构带来了核心部分体积的缩小。ECharts提供按需打包的能力,因为ECharts的组件众多,并且会持续增加。

多维数据支持以及丰富的视觉编码手段
ECharts 3开始加强了对多维数据的支持。除了加入平行坐标等常见的多维数据可视化工具外,对于传统的散点图,传入的数据也可以是多个维度的。配合视觉映射组件visualMap 提供丰富的视觉编码,能够将不同维度的数据映射到颜色,大小,透明度,明暗度等不同的视觉通道。

四、ZRender介绍
ECharts 底层依赖着轻量级的Canvas类库ZRender。
ZRender(Zlevel Render)是一个轻量级的Canvas类库,MVC封装,数据驱动,提供类DOM事件模型。

MVC核心封装实现图形仓库、视图渲染和交互控制:

  • Stroage(M) : shape数据CURD管理
  • Painter(V) : canvas元素生命周期管理,视图渲染,绘画,更新控制
  • Handler© : 事件交互处理,实现完整dom事件模拟封装
  • shape : 图形实体,分而治之的图形策略,可定义扩展
  • tool : 绘画扩展相关实用方法,工具及脚手架

在这里插入图片描述
特色:
1、数据驱动
利用zrender绘图,你只需做的是定义图形数据,剩下的事情就交给zrender.
2、完整的事件封装
用DOM事件模型去操作canvas里的图形元素。不仅可以响应zrender全局事件,甚至可以为特定的shape添加特定的事件。
3、高效的分层刷新
如css中的z-index一样,你可以定义把不同的shape放在不同的层中,这不仅实现了视觉上的上下覆盖,更重要的是图形元素发生变化后的refresh将局限在发生了变化的图形层中。
4、强大的动画支持
提供promise式的动画接口和常用缓动函数,轻松实现各种动画需求
5、易于扩展
分而治之的图形定义策略允许你扩展自己独有的图形元素,你既可以完整实现三个接口方法(brush,drift,isCover),也可以通过base派生后仅实现需要关心的图形细节。

二、Echarts的基本使用

一、安装

1.下载地址

https://echarts.apache.org/zh/download.html
在这里插入图片描述
2.使用npm安装

npm install echarts
二、ECharts的快速上手

ECharts 的入门使用特别简单, 5分钟就能够上手. 他大体分为这几个步骤

  • 步骤1:引入 echarts.js 文件

    echarts是一个 js 的库,当然得先引入这个库文件

    <script src="js/echarts.min.js"></script>
    
  • 步骤2:准备一个呈现图表的盒子

    这个盒子通常来说就是我们熟悉的 div ,这个 div 决定了图表显示在哪里

    <div id="main" style="width: 600px;height:400px;"></div>
    
  • 步骤3:初始化 echarts 实例对象

    在这个步骤中, 需要指明图表最终显示在哪里的DOM元素

    var myChart = echarts.init(document.getElementById('main'))
    
  • 步骤4:准备配置项

    这步很关键,我们最终的效果,到底是显示饼图还是折线图,基本上都是由配置项决定的

    var option = {
      xAxis: {
        type: 'category',
        data: ['小明', '小红', '小王']
      },
      yAxis: {
        type: 'value'
      },
      series: [{
        name: '语文',
        type: 'bar',
        data: [70, 92, 87],
      }]
    }
    
  • 步骤5:将配置项设置给 echarts 实例对象

    myChart.setOption(option)
    

通过简单的5个步骤, 就能够把一个简单的柱状图给显示在网页中了.这几个步骤中, 步骤4最重要,一个图表最终呈现什么样子,完全取决于这个配置项.所以对于不同的图表, 除了配置项会发生改变之外,其他的代码 都是固定不变的.

三、简单实例
<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <title>测试 ECharts</title>
    <!-- 引入 echarts.js -->
    <script src="https://cdn.staticfile.org/echarts/4.3.0/echarts.min.js"></script>
</head>
<body>
    <!-- 为ECharts准备一个具备大小(宽高)的Dom -->
    <div id="main" style="width: 600px;height:400px;"></div>
    <script type="text/javascript">
        // 基于准备好的dom,初始化echarts实例
        var myChart = echarts.init(document.getElementById('main'));
 
        // 指定图表的配置项和数据
        var option = {
            title: {
                text: '测试 ECharts'
            },
            tooltip: {},
            legend: {
                data:['销量']
            },
            xAxis: {
                data: ["衬衫","短袖","皮鞋","裤子","高跟鞋","袜子"]
            },
            yAxis: {},
            series: [{
                name: '销量',
                type: 'line',
                data: [9, 10, 36, 19, 14, 20]
            }]
        };
 
        // 使用刚指定的配置项和数据显示图表。
        myChart.setOption(option);
    </script>
</body>
</html>

在这里插入图片描述

四、Echarts-基础配置

这是要求大家知道以下配置每个模块的主要作用干什么的就可以了

需要了解的主要配置:series xAxis yAxis grid tooltip title legend color

  • series

    • 系列列表。每个系列通过 type 决定自己的图表类型
    • 大白话:图标数据,指定什么类型的图标,可以多个图表重叠。
  • xAxis:直角坐标系 grid 中的 x 轴

    • boundaryGap: 坐标轴两边留白策略 true,这时候刻度只是作为分隔线,标签和数据点都会在两个刻度之间的带(band)中间。
  • yAxis:直角坐标系 grid 中的 y 轴

  • grid:直角坐标系内绘图网格。

  • title:标题组件

  • tooltip:提示框组件

  • legend:图例组件

  • color:调色盘颜色列表

    数据堆叠,同个类目轴上系列配置相同的stack值后 后一个系列的值会在前一个系列的值上相加。

option = {
    // color设置我们线条的颜色 注意后面是个数组
    color: ['pink', 'red', 'green', 'skyblue'],
    // 设置图表的标题
    title: {
        text: '折线图堆叠123'
    },
    // 图表的提示框组件 
    tooltip: {
        // 触发方式
        trigger: 'axis'
    },
    // 图例组件
    legend: {
       // series里面有了 name值则 legend里面的data可以删掉
    },
    // 网格配置  grid可以控制线形图 柱状图 图表大小
    grid: {
        left: '3%',
        right: '4%',
        bottom: '3%',
        // 是否显示刻度标签 如果是true 就显示 否则反之
        containLabel: true
    },
    // 工具箱组件  可以另存为图片等功能
    toolbox: {
        feature: {
            saveAsImage: {}
        }
    },
    // 设置x轴的相关配置
    xAxis: {
        type: 'category',
        // 是否让我们的线条和坐标轴有缝隙
        boundaryGap: false,
        data: ['星期一', '周二', '周三', '周四', '周五', '周六', '周日']
    },
     // 设置y轴的相关配置
    yAxis: {
        type: 'value'
    },
    // 系列图表配置 它决定着显示那种类型的图表
    series: [
        {
            name: '邮件营销',
            type: 'line',
           
            data: [120, 132, 101, 134, 90, 230, 210]
        },
        {
            name: '联盟广告',
            type: 'line',

            data: [220, 182, 191, 234, 290, 330, 310]
        },
        {
            name: '视频广告',
            type: 'line',
          
            data: [150, 232, 201, 154, 190, 330, 410]
        },
        {
            name: '直接访问',
            type: 'line',
          
            data: [320, 332, 301, 334, 390, 330, 320]
        }
    ]
};

五、名词解析
基本名词
名词描述
chart是指一个完整的图表,如折线图,饼图等“基本”图表类型或由基本图表组合而成的“混搭”图表,可能包括坐标轴、图例等
axis直角坐标系中的一个坐标轴,坐标轴可分为类目型、数值型或时间型
xAxis直角坐标系中的横轴,通常并默认为类目型
yAxis直角坐标系中的纵轴,通常并默认为数值型
grid直角坐标系中除坐标轴外的绘图网格,用于定义直角系整体布局
legend图例,表述数据和图形的关联
dataRange值域选择,常用于展现地域数据时选择值域范围
dataZoom数据区域缩放,常用于展现大量数据时选择可视范围
roamController缩放漫游组件,搭配地图使用
toolbox辅助工具箱,辅助功能,如添加标线,框选缩放等
tooltip气泡提示框,常用于展现更详细的数据
timeline时间轴,常用于展现同一系列数据在时间维度上的多份数据
series数据系列,一个图表可能包含多个系列,每一个系列可能包含多个数据
图表名词
名词描述
line折线图,堆积折线图,区域图,堆积区域图。
bar柱形图(纵向),堆积柱形图,条形图(横向),堆积条形图。
scatter散点图,气泡图。散点图至少需要横纵两个数据,更高维度数据加入时可以映射为颜色或大小,当映射到大小时则为气泡图
kK线图,蜡烛图。常用于展现股票交易数据。
pie饼图,圆环图。饼图支持两种(半径、面积)南丁格尔玫瑰图模式。
radar雷达图,填充雷达图。高维度数据展现的常用图表。
chord和弦图。常用于展现关系数据,外层为圆环图,可体现数据占比关系,内层为各个扇形间相互连接的弦,可体现关系数据
force力导布局图。常用于展现复杂关系网络聚类布局。
map地图。内置世界地图、中国及中国34个省市自治区地图数据、可通过标准GeoJson扩展地图类型。支持svg扩展类地图应用,如室内地图、运动场、物件构造等。
heatmap热力图。用于展现密度分布信息,支持与地图、百度地图插件联合使用。
gauge仪表盘。用于展现关键指标数据,常见于BI类系统。
funnel漏斗图。用于展现数据经过筛选、过滤等流程处理后发生的数据变化,常见于BI类系统。
evnetRiver事件河流图。常用于展示具有时间属性的多个事件,以及事件随时间的演化。
treemap矩形式树状结构图,简称:矩形树图。用于展示树形数据结构,优势是能最大限度展示节点的尺寸特征。
venn韦恩图。用于展示集合以及它们的交集。
tree树图。用于展示树形数据结构各节点的层级关系
wordCloud词云。词云是关键词的视觉化描述,用于汇总用户生成的标签或一个网站的文字内容

三、ECharts常用图表

1、图表1 柱状图
1.柱状图的实现步骤
  • 步骤1 ECharts 最基本的代码结构
<!DOCTYPE html>
  <html lang="en">

  <head>
    <script src="js/echarts.min.js"></script>
  </head>

  <body>
    <div style="width: 600px;height:400px"></div>
    <script>
      var mCharts = echarts.init(document.querySelector("div")) var option = {}
      mCharts.setOption(option)
    </script>
  </body>

</html>

此时 option 是一个空空如也的对象

  • 步骤2 准备x轴的数据
var xDataArr = ['张三', '李四', '王五', '闰土', '小明', '茅台', '二妞', '大强']
  • 步骤3 准备 y 轴的数据
var yDataArr = [88, 92, 63, 77, 94, 80, 72, 86]
  • 步骤4 准备 option , 将 series 中的 type 的值设置为: bar
var option = {
  xAxis: {
    type: 'category',
    data: xDataArr
  },
  yAxis: {
    type: 'value'
  },
  series: [{
    type: 'bar',
    data: yDataArr
  }]
}

注意: 坐标轴 xAxis 或者 yAxis 中的配置, type 的值主要有两种: category 和 value , 如果 type属性的值为 category ,那么需要配置 data 数据, 代表在 x 轴的呈现. 如果 type 属性配置为 value ,那么无需配置 data , 此时 y 轴会自动去 series 下找数据进行图表的绘制

最终的效果如下图:

在这里插入图片描述

2.柱状图的常见效果

标记:

  • 最大值\最小值 markPoint
series: [{
  ......
  markPoint: {
    data: [{
      type: 'max',
      name: '最大值'
    }, {
      type: 'min',
      name: '最小值'
    }]
  }
}]

在这里插入图片描述

  • 平均值 markLine
series: [{
  ......markLine: {
    data: [{
      type: 'average',
      name: '平均值'
    }]
  }
}]

在这里插入图片描述
显示

  • 数值显示 label
series: [{
  ......
  label: {
    show: true, // 是否可见 
    rotate: 60 // 旋转角度 
  } 
} ]

在这里插入图片描述

  • 柱宽度 barWidth
series: [{
  ......
  barWidth: '30%' // 柱的宽度 
}]

在这里插入图片描述

  • 横向柱状图

    所谓的横向柱状图, 只需要让x轴的角色和y轴的角色互换一下即可. 既 xAxis 的 type 设置为value , yAxis 的 type 设置为 category , 并且设置 data 即可

var option = {
  xAxis: {
    type: 'value'
  },
  yAxis: {
    type: 'category',
    data: xDataArr
  },
  series: [{
    type: 'bar',
    data: yDataArr
  }]
}

在这里插入图片描述

3.柱状图特点

柱状图描述的是分类数据,呈现的是每一个分类中『有多少?』, 图表所表达出来的含义在于不同类别数据的排名\对比情况

4.通用配置

使用 ECharts 绘制出来的图表, 都天生就自带一些功能, 这些功能是每一个图表都具备的, 我们可以通过配置, 对这些功能进行设置.

  • 标题: title
var option = {
  title: {
    text: "成绩", // 标题文字 
    textStyle: {
      color: 'red' // 文字颜色 
    },
    borderWidth: 5, // 标题边框 
    borderColor: 'green', // 标题边框颜色 
    borderRadius: 5, // 标题边框圆角 
    left: 20, // 标题的位置 
    top: 20 // 标题的位置 
  }
}

在这里插入图片描述
提示框: tooltip

tooltip 指的是当鼠标移入到图表或者点击图表时, 展示出的提示框

  • 触发类型: trigger

    可选值有item\axis
    
  • 触发时机: triggerOn

    可选值有 mouseOver\click
    
  • 格式化显示: formatter

    • 字符串模板
    var option = {
      tooltip: {
        trigger: 'item',
        triggerOn: 'click',
        formatter: '{b}:{c}'
      }
    }
    这个{b}{c} 所代表的含义不需要去记, 在官方文档中有详细的描述
    

在这里插入图片描述

  • 回调函数
var option = {
  tooltip: {
    trigger: 'item',
    triggerOn: 'click',
    formatter: function (arg) {
      return arg.name + ':' + arg.data
    }
  }
}

在这里插入图片描述
工具按钮: toolbox

toolbox 是 ECharts 提供的工具栏, 内置有 导出图片,数据视图, 重置, 数据区域缩放, 动态类型切换五个工具

工具栏的按钮是配置在 feature 的节点之下

var option = {
  toolbox: {
    feature: {
      saveAsImage: {}, // 将图表保存为图片 
      dataView: {}, // 是否显示出原始数据 
      restore: {}, // 还原图表 
      dataZoom: {}, // 数据缩放 
      magicType: { // 将图表在不同类型之间切换,图表的转换需要数据的支持 
        type: ['bar', 'line']
      }
    }
  }
}

在这里插入图片描述
图例: legend

legend 是图例,用于筛选类别,需要和 series 配合使用

  • legend 中的 data 是一个数组
  • legend 中的 data 的值需要和 series 数组中某组数据的 name 值一致
var option = {
  legend: {
    data: ['语文', '数学']
  },
  xAxis: {
    type: 'category',
    data: ['张三', '李四', '王五', '闰土', '小明', '茅台', '二妞', '大强']
  },
  yAxis: {
    type: 'value'
  },
  series: [{
    name: '语文',
    type: 'bar',
    data: [88, 92, 63, 77, 94, 80, 72, 86]
  }, {
    name: '数学',
    type: 'bar',
    data: [93, 60, 61, 82, 95, 70, 71, 86]
  }]
}

在这里插入图片描述

2、图表2 折线图
1.折线图的实现步骤
  • 步骤1 ECharts 最基本的代码结构
<!DOCTYPE html>
  <html lang="en">

  <head>
    <script src="js/echarts.min.js"></script>
  </head>

  <body>
    <div style="width: 600px;height:400px"></div>
    <script>
      var mCharts = echarts.init(document.querySelector("div")) var option = {}
      mCharts.setOption(option)
    </script>
  </body>

</html>

此时 option 是一个空空如也的对象

  • 步骤2 准备x轴的数据
var xDataArr = ['1月', '2月', '3月', '4月', '5月', '6月', '7月', '8月', '9月', '10月', '11月', '12月']
  • 步骤3 准备 y 轴的数据
var yDataArr = [3000, 2800, 900, 1000, 800, 700, 1400, 1300, 900, 1000, 800, 600]
  • 步骤4 准备 option , 将 series 中的 type 的值设置为: line
var option = {
  xAxis: {
    type: 'category',
    data: xDataArr
  },
  yAxis: {
    type: 'value'
  },
  series: [{
    type: 'line',
    data: yDataArr
  }]
}

最终的效果如下:
在这里插入图片描述

2.柱状图的常见效果

标记:

  • 最大值\最小值 markPoint
series: [{
  ......
  markPoint: {
    data: [{
      type: 'max',
      name: '最大值'
    }, {
      type: 'min',
      name: '最小值'
    }]
  }
}]

在这里插入图片描述

  • 平均值 markLine
series: [{
  ......markLine: {
    data: [{
      type: 'average',
      name: '平均值'
    }]
  }
}]

在这里插入图片描述
显示

  • 数值显示 label
series: [{
  ......
  label: {
    show: true, // 是否可见 
    rotate: 60 // 旋转角度 
  } 
} ]

在这里插入图片描述

  • 标注区间 markArea
var option = {
  series: [{
    ......
    markArea: {
      data: [
        [{
          xAxis: '1月'
        }, {
          xAxis: '2月'
        }],
        [{
          xAxis: '7月'
        }, {
          xAxis: '8月'
        }]
      ]
    }
  }]
}

在这里插入图片描述
线条控制

  • 平滑线条 smooth
var option = {
  series: [{
    ......
    smooth: true
  }]
}

在这里插入图片描述

  • 线条样式 lineStyle
var option = {
  series: [{
    ......
    smooth: true,
    lineStyle: {
      color: 'green',
      type: 'dashed' // 可选值还有 dotted solid 
    }
  }]
}

在这里插入图片描述

  • 填充风格 areaStyle
var option = {
  series: [{
    type: 'line',
    data: yDataArr,
    areaStyle: {
      color: 'pink'
    }
  }]
}

在这里插入图片描述

  • 紧挨边缘 boundaryGap

boundaryGap 是设置给 x 轴的, 让起点从 x 轴的0坐标开始

var option = {
  xAxis: {
    type: 'category',
    data: xDataArr,
    boundaryGap: false
  }
}

在这里插入图片描述
缩放, 脱离0值比例

  • 如果每一组数据之间相差较少, 且都比0大很多, 那么有可能会出现这种情况
var yDataArr = [3005, 3003, 3001, 3002, 3009, 3007, 3003, 3001, 3005, 3004, 3001, 3009] // 此时y轴的数据都在3000附近, 每个数之间相差不多 
var option = {
  xAxis: {
    type: 'category',
    data: xDataArr
  },
  yAxis: {
    type: 'value'
  },
  series: [{
    type: 'line',
    data: yDataArr
  }]
}

效果如下图:
在这里插入图片描述
这显然不是我们想要的效果, 因此可以配置上 scale , 让其摆脱0值比例

  • scale 配置

    scale 应该配置给 y 轴

var option = {
  yAxis: {
    type: 'value',
    scale: true
  }
}

在这里插入图片描述
堆叠图

堆叠图指的是, 同个类目轴上系列配置相同的 stack 值后,后一个系列的值会在前一个系列的值上相加

如果在一个图表中有两个或者多个折线图, 在没有使用堆叠配置的时候, 效果如下:

var mCharts = echarts.init(document.querySelector("div")) var xDataArr = ['周一', '周二', '周三', '周四', '周五', '周六', '周日']
var yDataArr1 = [120, 132, 101, 134, 90, 230, 210]
var yDataArr2 = [20, 82, 191, 94, 290, 330, 310]
var option = {
  xAxis: {
    type: 'category',
    data: xDataArr
  },
  yAxis: {
    type: 'value',
    scale: true
  },
  series: [{
    type: 'line',
    data: yDataArr1
  }, {
    type: 'line',
    data: yDataArr2
  }]
}
mCharts.setOption(option)

在这里插入图片描述
使用了堆叠图之后:

var option = {
  series: [{
    type: 'line',
    data: yDataArr1,
    stack: 'all' // series中的每一个对象配置相同的stack值, 这个all可以任 意写 
  }, {
    type: 'line',
    data: yDataArr2,
    stack: 'all' // series中的每一个对象配置相同的stack值, 这个all可以任意 写 
  }]
}

在这里插入图片描述

  • 蓝色这条线的y轴起点, 不再是y轴, 而是红色这条线对应的点. 所以相当于蓝色是在红色这条线的基础之上进行绘制. 基于前一个图表进行堆叠
3.折线图的特点

折线图更多的使用来呈现数据随时间的**『变化趋势』**

3、图表3 散点图
1.散点图的实现步骤
  • 步骤1 ECharts 最基本的代码结构
<!DOCTYPE html>
  <html lang="en">

  <head>
    <script src="js/echarts.min.js"></script>
  </head>

  <body>
    <div style="width: 600px;height:400px"></div>
    <script>
      var mCharts = echarts.init(document.querySelector("div")) var option = {}
      mCharts.setOption(option)
    </script>
  </body>

</html>

此时 option 是一个空空如也的对象

  • 步骤2 准备 x 轴和 y 轴的数据
var data = [{ "gender": "female", "height": 161.2, "weight": 51.6 }, { "gender": "female", "height": 167.5, "weight": 59 }, { "gender": "female", "height": 159.5, "weight": 49.2 }, { "gender": "female", "height": 157, "weight": 63 }, { "gender": "female", "height": 155.8, "weight": 53.6 }, { "gender": "female", "height": 170, "weight": 59 }, { "gender": "female", "height": 159.1, "weight": 47.6 }, { "gender": "female", "height": 166, "weight": 69.8 }, { "gender": "female", "height": 176.2, "weight": 66.8 }, { "gender": "female", "height": 160.2, "weight": 75.2 }, { "gender": "female", "height": 172.5, "weight": 55.2 }, { "gender": "female", "height": 170.9, "weight": 54.2 }, { "gender": "female", "height": 172.9, "weight": 62.5 }, { "gender": "female", "height": 153.4, "weight": 42 }, { "gender": "female", "height": 160, "weight": 50 }, { "gender": "female", "height": 147.2, "weight": 49.8 },...此处省略...]

假设这个数据是从服务器获取到的, 数组中的每一个元素都包含3个维度的数据: 性别,身高,体重, 而散点图需要的数据是一个二维数组, 所以我们需要将从服务器获取到的这部分数据,通过代码生成散点图需要的数据

var axisData = []
for (var i = 0; i < data.length; i++) {
  var height = data[i].height
  var weight = data[i].weight
  var itemArr = [height, weight] axisData.push(itemArr)
}

axisData 就是一个二维数组, 数组中的每一个元素还是一个数组, 最内层数组中有两个元素, 一个代表身高, 一个代表体重

  • 步骤3 准备配置项
    • xAxis 和 yAxis 的 type 都要设置为 value
    • 在 series 下设置 type:scatter
var option = {
  xAxis: {
    type: 'value'
  },
  yAxis: {
    type: 'value'
  },
  series: [{
    type: 'scatter',
    data: axisData
  }]
}
  • 步骤4 调整配置项, 脱离0值比例

    给 xAxis 和 yAxis 配置 scale 的值为 true

    var option = {
      xAxis: {
        type: 'value',
        scale: true
      },
      yAxis: {
        type: 'value',
        scale: true
      },
      series: [{
        type: 'scatter',
        data: axisData,
      }]
    }
    

最终的效果如下:
在这里插入图片描述

2.散点图的常见效果
  • 气泡图效果

    要能够达到气泡图的效果, 其实就是让每一个散点的大小不同, 让每一个散点的颜色不同

    • symbolSize 控制散点的大小
    • itemStyle.color 控制散点的颜色

    这两个配置项都支持固定值的写法, 也支持回调函数的写法

    固定值的写法如下:

    var option = {
      series: [{
        type: 'scatter',
        data: axisData,
        symbolSize: 25,
        itemStyle: {
          color: 'green',
        }
      }]
    }
    

在这里插入图片描述

var option = {
  series: [{
    type: 'scatter',
    data: axisData,
    symbolSize: function (arg) {
      var weight = arg[1]
      var height = arg[0] / 100 
      // BMI > 28 则代表肥胖, 肥胖的人用大的散点标识, 正常的人用小散点标识 
      // BMI: 体重/ 身高*身高 kg m
      var bmi = weight / (height * height) if (bmi > 28) {
        return 20
      }
      return 5
    },
    itemStyle: {
      color: function (arg) {
        var weight = arg.data[1]
        var height = arg.data[0] / 100
        var bmi = weight / (height * height) if (bmi > 28) {
          return 'red'
        }
        return 'green'
      }
    }
  }]
}

在这里插入图片描述
涟漪动画效果

  • type:effectScatter

    将 type 的值从 scatter 设置为 effectScatter 就能够产生涟漪动画的效果

  • rippleEffect

    rippleEffect 可以配置涟漪动画的大小

var option = {
  series: [{
    type: 'effectScatter',
    rippleEffect: {
      scale: 3
    }
  }]
}

在这里插入图片描述

  • showEffectOn

showEffectOn 可以控制涟漪动画在什么时候产生, 它的可选值有两个: render 和 emphasis

render 代表界面渲染完成就开始涟漪动画

emphasis 代表鼠标移过某个散点的时候, 该散点开始涟漪动画

var option = {
  series: [{
    type: 'effectScatter',
    showEffectOn: 'emphasis',
    rippleEffect: {
      scale: 3
    }
  }]
}

在这里插入图片描述

  • 结合地图

    散点图也经常结合地图来进行地图区域的标注, 这个效果将在讲解地图时实现

3.散点图的特点

散点图可以帮助我们推断出不同维度数据之间的相关性, 比如上述例子中,看得出身高和体重是正相关, 身高越高, 体重越重

散点图也经常用在地图的标注上

4.直角坐标系的常见配置

直角坐标系的图表指的是带有x轴和y轴的图表, 常见的直角坐标系的图表有: 柱状图 折线图 散点图

针对于直角坐标系的图表, 有一些通用的配置

  • 配置1: 网格 grid

    grid是用来控制直角坐标系的布局和大小, x轴和y轴就是在grid的基础上进行绘制的

    • 显示 grid

      show: true

    • grid 的边框

      borderWidth : 10

    • grid 的位置和大小

      left top right bottom width height

    var option = {
      grid: {
        show: true, // 显示grid 
        borderWidth: 10, // grid的边框宽度 
        borderColor: 'red', // grid的边框颜色 
        left: 100, // grid的位置 
        top: 100,
        width: 300, // grid的大小
        height: 150
      }
    }
    
  • 配置2: 坐标轴 axis

    坐标轴分为x轴和y轴, 一个 grid 中最多有两种位置的 x 轴和 y 轴

    • 坐标轴类型 type

      value : 数值轴, 自动会从目标数据中读取数据

      category : 类目轴, 该类型必须通过 data 设置类目数据

    • 坐标轴位置

      xAxis : 可取值为 top 或者 bottom

      yAxis : 可取值为 left 或者 right

    var option = {
      xAxis: {
        type: 'category',
        data: xDataArr,
        position: 'top'
      },
      yAxis: {
        type: 'value',
        position: 'right'
      }
    }
    
  • 配置3: 区域缩放 dataZoom

    dataZoom 用于区域缩放, 对数据范围过滤, x轴和y轴都可以拥有, dataZoom 是一个数组, 意味着可以配置多个区域缩放器

    • 区域缩放类型 type

      slider : 滑块

      inside : 内置, 依靠鼠标滚轮或者双指缩放

    • 产生作用的轴

      xAxisIndex :设置缩放组件控制的是哪个 x 轴, 一般写0即可

      yAxisIndex :设置缩放组件控制的是哪个 y 轴, 一般写0即可

    • 指明初始状态的缩放情况

      start : 数据窗口范围的起始百分比

      end : 数据窗口范围的结束百分比

    var option = {
      xAxis: {
        type: 'category',
        data: xDataArr
      },
      yAxis: {
        type: 'value'
      },
      dataZoom: [{
        type: 'slider',
        xAxisIndex: 0
      }, {
        type: 'slider',
        yAxisIndex: 0,
        start: 0,
        end: 80
      }]
    }
    

在这里插入图片描述
需要注意的是, 针对于非直角坐标系图表, 比如饼图 地图 等, 以上三个配置可能就不会生效了

4、图表4 饼图
1.饼图的实现步骤
  • 步骤1 ECharts 最基本的代码结构
<!DOCTYPE html>
  <html lang="en">

  <head>
    <script src="js/echarts.min.js"></script>
  </head>

  <body>
    <div style="width: 600px;height:400px"></div>
    <script>
      var mCharts = echarts.init(document.querySelector("div")) var option = {}
      mCharts.setOption(option)
    </script>
  </body>

</html>

此时 option 是一个空空如也的对象

  • 步骤2 准备数据
var pieData = [{
  value: 11231,
  name: "淘宝",
}, {
  value: 22673,
  name: "京东"
}, {
  value: 6123,
  name: "唯品会"
}, {
  value: 8989,
  name: "1号店"
}, {
  value: 6700,
  name: "聚美优品"
}]
  • 步骤3 准备配置项 在 series 下设置 type:pie
var option = {
  series: [{
    type: 'pie',
    data: pieData
  }]
}

在这里插入图片描述
注意:

  • 饼图的数据是由 name 和 value 组成的字典所形成的数组

  • 饼图无须配置 xAxis 和 yAxis

2.饼图的常见效果
  • 显示数值
    • label.show : 显示文字
    • label.formatter : 格式化文字
var option = {
  series: [{
    type: 'pie',
    data: pieData,
    label: {
      show: true,
      formatter: function (arg) {
        return arg.data.name + '平台' + arg.data.value + '元\n' + arg.percent + '%'
      }
    }
  }]
}
  • 南丁格尔图

    南丁格尔图指的是每一个扇形的半径随着数据的大小而不同, 数值占比越大, 扇形的半径也就越大

    • roseType:‘radius’
var option = {
  series: [{
    type: 'pie',
    data: pieData,
    label: {
      show: true,
      formatter: function (arg) {
        return arg.data.name + '平台' + arg.data.value + '元\n' + arg.percent + '%'
      }
    },
    roseType: 'radius'
  }]
}

在这里插入图片描述

  • 选中效果

    • selectedMode: ‘multiple’

    选中模式,表示是否支持多个选中,默认关闭,支持布尔值和字符串,字符串取值可选 ‘single’ , ‘multiple’ ,分别表示单选还是多选

    • selectedOffset: 30

    选中扇区的偏移距离

var option = {
  series: [{
    type: 'pie',
    data: pieData,
    selectedMode: 'multiple', // 
    selectedOffset: 30
  }]
}

在这里插入图片描述

  • 圆环
    • radius

饼图的半径。可以为如下类型:

number :直接指定外半径值。 string :例如, ‘20%’ ,表示外半径为可视区尺寸(容器高宽中较小一项)的 20% 长度。 Array. :数组的第一项是内半径,第二项是外半径, 通过 Array , 可以将饼图设置为圆环图

var option = {
  series: [{
    type: 'pie',
    data: pieData,
    radius: ['50%', '70%']
  }]
}

在这里插入图片描述

3.饼图的特点

饼图可以很好地帮助用户快速了解不同分类的数据的占比情况

5、图表5 地图
1.地图图表的使用方式

百度地图API : 使用百度地图的 api , 它能够在线联网展示地图, 百度地图需要申请 ak

矢量地图 : 可以离线展示地图, 需要开发者准备矢量地图数据

接下来的实现是通过矢量图的方式来实现的

2.矢量地图的实现步骤
  • 步骤1 ECharts 最基本的代码结构
<!DOCTYPE html>
  <html lang="en">

  <head>
    <script src="js/echarts.min.js"></script>
  </head>

  <body>
    <div style="width: 600px;height:400px"></div>
    <script>
      var mCharts = echarts.init(document.querySelector("div")) var option = {}
      mCharts.setOption(option)
    </script>
  </body>

</html>

此时 option 是一个空空如也的对象

  • 步骤2 准备中国的矢量 json 文件, 放到 json/map/ 目录之下

在这里插入图片描述

  • 步骤3 使用 Ajax 获取 china.json
$.get('json/map/china.json', function (chinaJson) {})
  • 步骤4 在Ajax的回调函数中, 往 echarts 全局对象注册地图的 json 数据
echarts.registerMap('chinaMap', chinaJson) 
$.get('json/map/china.json', function (chinaJson) {
  echarts.registerMap('chinaMap', chinaJson)
})
  • 步骤5 获取完数据之后, 需要配置 geo 节点, 再次的 setOption

    type : ‘map’

    map : ‘chinaMap’

var mCharts = echarts.init(document.querySelector("div")) $.get('json/map/china.json', function (chinaJson) {
  echarts.registerMap('chinaMap', chinaJson) 
  var option = {
    geo: {
      type: 'map', // map是一个固定的值 
      map: 'chinaMap', //chinaMap需要和registerMap中的第一个参数保持一致 
    }
  };
  mCharts.setOption(option)
})

(地图不给放,大家自行尝试)

注意: 需要注意的是, 由于在代码中使用了 Ajax , 所以, 关于此文件的打开, 不能以 file 的协议打开, 应该将其置于 HTTP 的服务之下方可正常展示地图

3.地图的常见配置
  • 缩放拖动: roam
var option = {
  geo: {
    type: 'map', // map是一个固定的值 
    map: 'chinaMap', //chinaMap需要和registerMap中的第一个参数保持一致, 
    roam: true, // 运行使用鼠标进行拖动和缩放
  }
}
  • 名称显示: label
var option = {
  geo: {
    type: 'map', // map是一个固定的值
    map: 'chinaMap', //chinaMap需要和registerMap中的第一个参数保持一致,
    roam: true,
    label: {
      show: true
    }
  }
}

(地图不给放,大家自行尝试)

  • 初始缩放比例: zoom

  • 地图中心点: center

var option = {
  geo: {
    type: 'map', // map是一个固定的值 
    map: 'chinaMap', //chinaMap需要和registerMap中的第一个参数保持一致, 
    roam: true,
    label: {
      show: true
    },
    zoom: 0.8, // 地图的缩放比例, 大于1代表放大, 小于1代表缩小 
    center: [87.617733, 43.792818] // 当前视角的中心点,用经纬度表示 
  }
}

(地图不给放,大家自行尝试)

4.地图的常见效果
  • 显示某个区域

    • 准备安徽省的矢量地图数据
      在这里插入图片描述

    • 加载安徽省地图的矢量数据

    $.get('json/map/anhui.json', function (anhuiJson) { })
    
    • 在Ajax的回调函数中注册地图矢量数据

      echarts.registerMap(‘anhui’, anhuiJson)

    • 配置 geo 的 type:‘map’ , map:‘anhui’

    • 通过 zoom 调整缩放比例

    • 通过 center 调整中心点

<script>
  var mCharts = echarts.init(document.querySelector("div")) $.get('json/map/anhui.json', function (anhuiJson) {
    console.log(anhuiJson) echarts.registerMap('anhui', anhuiJson) var option = {
      geo: {
        type: 'map',
        map: 'anhui',
        label: {
          show: true
        },
        zoom: 1.2,
        center: [116.507676, 31.752889]
      }
    };
    mCharts.setOption(option)
  })
</script>

在这里插入图片描述

  • 不同城市颜色不同

    • 1.显示基本的中国地图
    <body>
      <div style="width: 600px;height:400px;border:1px solid red"></div>
      <script>
        var mCharts = echarts.init(document.querySelector("div")) $.get('json/map/china.json', function (chinaJson) {
          echarts.registerMap('chinaMap', chinaJson) var option = {
            geo: {
              type: 'map',
              map: 'chinaMap',
              roam: true,
              label: {
                show: true
              }
            }
          }
          mCharts.setOption(option)
        })
      </script>
    </body>
    
    • 2.准备好城市空气质量的数据, 并且将数据设置给 series
    var airData = [{
        name: '北京',
        value: 39.92
      }, {
        name: '天津',
        value: 39.13
      }, {
        name: '上海',
        value: 31.22
      }, {
        name: '重庆',
        value: 66
      }, {
        name: '河北',
        value: 147
      }, {
        name: '河南',
        value: 113
      }, {
        name: '云南',
        value: 25.04
      }, {
        name: '辽宁',
        value: 50
      }, {
        name: '黑龙江',
        value: 114
      }, {
        name: '湖南',
        value: 175
      }, {
        name: '安徽',
        value: 117
      }, {
        name: '山 东',
        value: 92
      }, {
        name: '新疆',
        value: 84
      }, {
        name: '江苏',
        value: 67
      }, {
        name: '浙江',
        value: 84
      }, {
        name: '江西',
        value: 96
      }, {
        name: '湖北',
        value: 273
      }, {
        name: '广西',
        value: 59
      }, {
        name: '甘肃',
        value: 99
      }, {
        name: '山西',
        value: 39
      }, {
        name: '内蒙古',
        value: 58
      }, {
        name: '陕西',
        value: 61
      }, {
        name: '吉林',
        value: 51
      }, {
        name: '福建',
        value: 29
      }, {
        name: '贵州',
        value: 71
      }, {
        name: '广东',
        value: 38
      }, {
        name: '青海',
        value: 57
      }, {
        name: '西藏',
        value: 24
      }, {
        name: '四川',
        value: 58
      }, {
        name: '宁夏',
        value: 52
      }, {
        name: '海南',
        value: 54
      }, {
        name: '台湾',
        value: 88
      }, {
        name: '香港',
        value: 66
      }, {
        name: '澳门',
        value: 77
      }, {
        name: '南海诸岛',
        value: 55
      }]......
      var option = {
        ......
        series: [{
          data: airData
        }]
      }
    
  • 3.将 series 下的数据和 geo 关联起来

    geoIndex: 0

    type: ‘map’

    var option = {
      series: [{
        data: airData,
        geoIndex: 0,
        type: 'map'
      }]
    }
    
  • 4.结合 visualMap 配合使用

    visualMap 是视觉映射组件, 和之前区域缩放 dataZoom 很类似, 可以做数据的过滤. 只不过dataZoom 主要使用在直角坐标系的图表, 而 visualMap 主要使用在地图或者饼图中

    var option = {
      geo: {
        type: 'map',
        map: 'chinaMap',
        roam: true,
        label: {
          show: true
        }
      },
      series: [{
        data: airData,
        geoIndex: 0,
        type: 'map'
      }],
      visualMap: {
        min: 0, // 最小值 
        max: 300, // 最大值 
        inRange: {
          color: ['white', 'red'] // 颜色的范围
        },
        calculable: true // 是否显示拖拽用的手柄(手柄能拖拽调整选中范围)
      }
    }
    

(地图不给放,大家自行尝试)

地图和散点图结合

  • 1.给 series 这个数组下增加新的对象
  • 2.准备好散点数据,设置给新对象的 data
var scatterData = [{
  value: [117.283042, 31.86119] // 散点的坐标, 使用的是经纬度
}]
  • 3.配置新对象的 type

    type:effectScatter

  • 让散点图使用地图坐标系统

    coordinateSystem: ‘geo’

  • 让涟漪的效果更加明显

    rippleEffect: { scale: 10 }

var option = {
  series: [{
    data: airData,
    geoIndex: 0,
    type: 'map'
  }, {
    data: scatterData,
    type: 'effectScatter',
    coordinateSystem: 'geo',
    rippleEffect: {
      scale: 10
    }
  }]
}

(地图不给放,大家自行尝试)

5.地图的特点

地图主要可以帮助我们从宏观的角度快速看出不同地理位置上数据的差异

6、图表6 雷达图
1.雷达图的实现步骤
  • 步骤1 ECharts 最基本的代码结构
<!DOCTYPE html>
  <html lang="en">

  <head>
    <script src="js/echarts.min.js"></script>
  </head>

  <body>
    <div style="width: 600px;height:400px"></div>
    <script>
      var mCharts = echarts.init(document.querySelector("div")) var option = {}
      mCharts.setOption(option)
    </script>
  </body>

</html>

此时 option 是一个空空如也的对象

  • 步骤2 定义各个维度的最大值
var dataMax = [{
  name: '易用性',
  max: 100
}, {
  name: '功能',
  max: 100
}, {
  name: '拍照',
  max: 100
}, {
  name: '跑分',
  max: 100
}, {
  name: '续航',
  max: 100
}]
  • 步骤3 准备具体产品的数据
var hwScore = [80, 90, 80, 82, 90] 
var zxScore = [70, 82, 75, 70, 78]
  • 步骤4 在 series 下设置 type:radar
var option = {
  radar: {
    indicator: dataMax
  },
  series: [{
    type: 'radar',
    data: [{
      name: '华为手机1',
      value: hwScore
    }, {
      name: '中兴手机1',
      value: zxScore
    }]
  }]
}

在这里插入图片描述

2.雷达图的常见效果
  • 显示数值 label

    var option = {
      series: [{
        type: 'radar',
        label: {
          show: true
        },
        data: [{
          name: '华为手机1',
          value: hwScore
        }, {
          name: '中兴手机1',
          value: zxScore
        }]
      }]
    }
    

在这里插入图片描述
区域面积 areaStyle

var option = {
  series: [{
    type: 'radar',
    label: {
      show: true
    },
    areaStyle: {},
    data: [{
      name: '华为手机1',
      value: hwScore
    }, {
      name: '中兴手机1',
      value: zxScore
    }]
  }]
}

在这里插入图片描述

  • 绘制类型 shape

    雷达图绘制类型,支持 ‘polygon’ 和 ‘circle’

    ‘polygon’ : 多边形

    ‘circle’ 圆形

var option = {
  radar: {
    indicator: dataMax,
    shape: 'circle'
  },
  series: [{
    type: 'radar',
    label: {
      show: true
    },
    data: [{
      name: '华为手机1',
      value: hwScore
    }, {
      name: '中兴手机1',
      value: zxScore
    }]
  }]
}

3.雷达图的特点

雷达图可以用来分析多个维度的数据与标准数据的对比情况

7、图表7 仪表盘图
1.仪表盘的实现步骤
  • 步骤1 ECharts 最基本的代码结构
<!DOCTYPE html>
  <html lang="en">

  <head>
    <script src="js/echarts.min.js"></script>
  </head>

  <body>
    <div style="width: 600px;height:400px"></div>
    <script>
      var mCharts = echarts.init(document.querySelector("div")) var option = {}
      mCharts.setOption(option)
    </script>
  </body>

</html>

此时 option 是一个空空如也的对象

  • 步骤2: 准备数据, 设置给 series 下的 data

    data:[97]

  • 步骤3: 在 series 下设置 type:gauge

    var option = {
      series: [{
        type: 'gauge',
        data: [{
          value: 97,
        }]
      }]
    }
    

在这里插入图片描述

2.仪表盘的常见效果
  • 数值范围: max min
  • 多个指针: 增加data中数组的元素
  • 多个指针颜色的差异: itemStyle
var option = {
  series: [{
    type: 'gauge',
    data: [{
      value: 97,
      itemStyle: {
        color: 'pink'
      }
    }, {
      value: 85,
      itemStyle: {
        color: 'green'
      }
    }],
    min: 50
  }]
}

在这里插入图片描述

3.仪表盘的特点

仪表盘可以更直观的表现出某个指标的进度或实际情况

8、小结

各个图表的英文单词

  • bar
  • line
  • scatter/effectScatter
  • pie
  • map
  • radar
  • gauge

在这里插入图片描述
使用场景

  • 柱状图:柱状图描述的是分类数据,呈现的是每一个分类中有多少

  • 折线图:折线图常用来分析数据随时间的变化趋势

  • 散点图:散点图可以帮助我们推断出不同维度数据之间的相关性

  • 饼图:饼图可以很好地帮助用户快速了解不同分类的数据的占比情况

  • 地图:地图主要可以帮助我们从宏观的角度快速看出不同地理位置上数据的差异

  • 雷达图:雷达图可以用来分析多个维度的数据与标准数据的对比情况

  • 仪表盘:仪表盘可以更直观的表现出某个指标的进度或实际情况

四、配置项小结

1、柱状图 bar
series[].typexAxisyAxismarkPointmarkLinelabelbarWidth
图表类型x轴y轴最大值\最小平均值显示文柱宽度
2、折线图 line
series[].typexAxisyAxismarkPointmarkLinelabelbarWidth
图表类型x轴y轴最大值\最小平均值显示文柱宽度
lineStyleareaStyleboundaryGapscale
线条风格风格x轴紧挨边缘脱离0值比例
3、散点图 scatter
series[].typexAxisyAxissymbolSize
图表类型x轴y轴散点大小
lineStyleshowEffectOnrippleEffectscale
线条风格显示时机涟漪效果脱离0值比例
4、饼图 pie
series[].typelabelradiusroseTypeselectedModeselectedOffset
图表类型显示文本半径饼图类型是否多选选中扇区偏移量
5、地图 map
series[].typegeomaproamzoom
图表类型地理坐标系组件指明地图数据开启鼠标拖动和缩放平均值
centerlabelgeoIndexvisualMapcoordinateSystem
图表的中心是否显示地区指明关联的geo组视觉映射组件使用坐标系统
6、雷达图 radar
series[].typeradarindicatorlabelareaStyleshape
图表类型雷达图组件雷达图的指示器文字区域颜色雷达图形状
7、仪表盘 gauge
series[].typemaxminitemStyle
图表类型最大值最小值指针样式
8、直角坐标系配置
  • grid
showborderWidthborderColorlefttopright
是否可见边框宽度边框颜色左边顶部右边
bottomwidthheight
底部宽度高度
  • axis
typedataposition
底部轴类型数据显示位置
  • dataZoom
typexAxisIndexyAxisIndexstartend
缩放块类型x轴索引y轴索引初始值结束值
9、通用配置
  • title
textStyleborderWidthborderColorborderRadius
文字样式边框宽度边框颜色边框圆角
lefttoprightbottom
左边顶部右边底部
  • tooltip
triggertriggerOnformatter
触发类型触发时机内容自定义
  • toolbox.feature
saveAsImagedataViewrestoredataZoommagicType
缩放块类型x轴索引重置缩放图表转换
  • legend
data
图例数据, 需要和series数组中某组数据的name值一致

五、ECharts高级

1、显示相关
1.主题
  • 默认主题

    ECharts 中默认内置了两套主题: light dark

    在初始化对象方法 init 中可以指明

var chart = echarts.init(dom, 'light') 
var chart = echarts.init(dom, 'dark')
  • 自定义主题

    • 1.在主题编辑器中编辑主题

      主题编辑器的地址为: https://echarts.apache.org/zh/theme-builder.html

      在该地址中, 你可以定义一个主题的很多方面的内容:

在这里插入图片描述
2.下载主题, 是一个 js 文件

在线编辑完主题之后, 可以点击下载主题按钮, 下载主题的js文件

在这里插入图片描述

    • 3.引入主题 js 文件

      <script src="js/echarts.min.js"></script> 
      <script src="js/myTheme.js"></script>
      

      其中, cast.js 就是下载下来的主题文件

    • 4.在 init 方法中使用主题

      var mCharts = echarts.init(document.querySelector("div"), 'myTheme')
      

      init方法中的第二个参数myTheme就是主题的名称, 这个名称叫什么我们可以在myTheme.js的代码中

      看出

2.调色盘

它是一组颜色,图形、系列会自动从其中选择颜色, 不断的循环从头取到尾, 再从头取到尾, 如此往复.

  • 主题调色盘

    echarts.registerTheme('myTheme', {
      "color": ["#893448", "#d95850", "#eb8146", "#ffb248", "#f2d643", "#ebdba4"],
      "backgroundColor": "rgba(242,234,191,0.15)",
      ......
    })
    
  • 全局调色盘

    全局调色盘是在 option 下增加一个 color 的数组

    var option = { // 全局调色盘 
      color: ['red', 'green', 'blue'],
      ......
    }
    mCharts.setOption(option)
    
  • 局部调色盘

    局部调色盘就是在 series 下增加一个 color 的数组

    var option = { // 全局调色盘 
      color: ['red', 'green', 'blue'],
      series: [{
        type: 'pie',
        data: pieData, // 局部调色盘 
        color: ['pink', 'yellow', 'black']
      }]
    }
    mCharts.setOption(option)
    

    需要注意一点的是, 如果全局的调色盘和局部的调色盘都设置了, 局部调色盘会产生效果, 这里面遵循的是就近原则

  • 渐变颜色的实现

    在 ECharts 中, 支持线性渐变和径向渐变两种颜色渐变的方式

    • 线性渐变

      线性渐变的类型为 linear , 他需要配置线性的方向, 通过 x, y, x2, y2 即可进行配置

      x , y , x2 , y2 , 范围从 0 - 1,相当于在图形包围盒中的百分比,如果 global 为 true ,则该四个值是绝对的像素位置

      在下述代码中的 0 0 0 1 意味着从上往下进行渐变

    <!DOCTYPE html>
    <html lang="en">
    
    <head>
      <script src="js/echarts.min.js"></script>
    </head>
    
    <body>
      <div style="width: 600px;height:400px"></div>
      <script>
        var mCharts = echarts.init(document.querySelector("div")) 
    	var xDataArr = ['张三', '李四', '王五', '闰土', '小明', '茅台', '二妞',
          '大 强'
        ]
        var yDataArr = [88, 92, 63, 77, 94, 80, 72, 86]
        var option = {
          xAxis: {
            type: 'category',
            data: xDataArr
          },
          yAxis: {
            type: 'value'
          },
          series: [{
            type: 'bar',
            data: yDataArr,
            itemStyle: {
              color: {
                type: 'linear',
                x: 0,
                y: 0,
                x2: 0,
                y2: 1,
                colorStops: [{
                  offset: 0,
                  color: 'red' // 0% 处的颜色
                }, {
                  offset: 1,
                  color: 'blue' // 100% 处的颜色
                }],
                globalCoord: false // 缺省为 false
              }
            }
          }]
        };
        mCharts.setOption(option)
      </script>
    </body>
    
    </html>
    

在这里插入图片描述

  • 径向渐变

线性渐变的类型为 radial , 他需要配置径向的方向, 通过 x , y , r 即可进行配置

前三个参数分别是圆心 x , y 和半径,取值同线性渐变

在下述代码中的 0.5 0.5 0.5 意味着从柱的重点点, 向外径向扩散半径为宽度一半的圆

    series: [{
      itemStyle: {
        color: {
          type: 'radial',
          x: 0.5,
          y: 0.5,
          r: 0.5,
          colorStops: [{
            offset: 0,
            color: 'red' // 0% 处的颜色
          }, {
            offset: 1,
            color: 'blue' // 100% 处的颜色
          }],
          global: false // 缺省为 false 
        }
      }
    }]

在这里插入图片描述

3.样式
  • 直接样式

    • itemStyle
    • textStyle
    • lineStyle
    • areaStyle
    • label
    data: [{
      value: 11231,
      name: "淘宝",
      itemStyle: {
        color: 'black'
      }
    }] 
    title: {
      text: '我是标题',
      textStyle: {
        color: 'red'
      }
    }
    label: {
      color: 'green'
    }
    

    这些样式一般都可以设置颜色或者背景或者字体等样式, 他们会覆盖主题中的样式

  • 高亮样式

    图表中, 其实有很多元素都是有两种状态的, 一种是默认状态, 另外一种就是鼠标滑过或者点击形成的高亮状态. 而高亮样式是针对于元素的高亮状态设定的样式

    那它的使用也非常简单,在 emphasis 中包裹原先的 itemStyle 等等, 我们来试一下

    series: [{
      type: 'pie',
      label: {
        color: 'green'
      },
      emphasis: {
        label: {
          color: 'red'
        },
      },
      data: [{
        value: 11231,
        name: "淘宝",
        itemStyle: {
          color: 'black'
        },
        emphasis: {
          itemStyle: {
            color: 'blue'
          },
        }
      }, ]
    }]
    
4.自适应

步骤1: 监听窗口大小变化事件

步骤2: 在事件处理函数中调用 ECharts 实例对象的 resize 即可

<!DOCTYPE html>
<html lang="en">

<head>
  <script src="js/echarts.min.js"></script>
</head>

<body>
  <div style=" height:400px;border:1px solid red"></div>
  <script>
    var mCharts = echarts.init(document.querySelector("div")) var xDataArr = ['张三', '李四', '王五', '闰土', '小明', '茅台', '二妞',
      '大 强'
    ]
    var yDataArr = [88, 92, 63, 77, 94, 80, 72, 86]
    var option = {
      xAxis: {
        type: 'category',
        data: xDataArr
      },
      yAxis: {
        type: 'value'
      },
      series: [{
        type: 'bar',
        data: yDataArr
      }]
    };

    mCharts.setOption(option) // 监听window大小变化的事件 
    window.onresize = function () { // 调用echarts示例对象的resize方法 
      mCharts.resize()
    } // window.onresize = mCharts.resize 
  </script>
</body>

</html>
2、动画的使用
1.加载动画

ECharts 已经内置好了加载数据的动画, 我们只需要在合适的时机显示或者隐藏即可

  • 显示加载动画
mCharts.showLoading() 
一般, 我们会在获取图表数据之前 显示加载动画

在这里插入图片描述

  • 隐藏加载动画
mCharts.hideLoading() 
一般, 我们会在获取图表数据之后 隐藏加载动画, 显示图表
2.增量动画

所有数据的更新都通过 setOption 实现, 我们不用考虑数据到底产生了那些变化, ECharts 会找到两组

数据之间的差异然后通过合适的动画去表现数据的变化。

<!DOCTYPE html>
<html lang="en">

<head>
  <script src="js/echarts.min.js"></script>
</head>

<body>
  <div style="width: 600px;height:400px"></div>
  <button>修改数据</button> <button id="btnAdd">增加数据</button>
  <script>
    var mCharts = echarts.init(document.querySelector("div")) 
    var xDataArr = ['张三', '李四', '王五', '闰土', '小明', '茅台', '二妞',
      '大强'
    ]
    var yDataArr = [88, 92, 63, 77, 94, 80, 72, 86]
    var option = {
      xAxis: {
        type: 'category',
        data: xDataArr
      },
      yAxis: {
        type: 'value'
      },
      series: [{
        type: 'bar',
        data: yDataArr
      }]
    };
    mCharts.setOption(option) 
    var btn = document.querySelector('button');
    btn.onclick = function () {
      var newArr = [68, 62, 93, 67, 64, 90, 52,
        36
      ]
      // setOption的方法可以被调用多次 
      // 新的option 和旧的option配置 
      // 新旧option配置项他们之间不是替换的关系,是相互整合的关系 
      // 我们在设置新的option的时候,只需要考虑到将变化的配置项配置就可以了
      var option = {
        series: [{
          data: newArr,
        }]
      };
      mCharts.setOption(option)
    }
    var btnAdd = document.querySelector('#btnAdd') 
    btnAdd.onclick = function () {
      setInterval(
        function () { //增加数据 
          xDataArr.push('小明') 
          yDataArr.push(parseInt(50 + Math.random() * 10)) 
          var option = {
            xAxis: {
              data: xDataArr
            },
            series: [{
              data: yDataArr
            }]
          }
          mCharts.setOption(option)
        }, 1000)
    }
  </script>
</body>

</html>
3.动画的配置
  • 开启动画

    animation: true

  • 动画时长

    animationDuration: 5000

  • 缓动动画

    animationEasing : ‘bounceOut’

    linear ,线性变化, 这样动画效果会很均匀

    bounceOut ,这样动画效果会有一个回弹效果

    缓动动画的可选值如下图:
    在这里插入图片描述

  • 动画阈值

    animationThreshold: 8

    单种形式的元素数量大于这个阈值时会关闭动画

3、交互API
1.全局echarts 对象

全局 echarts 对象是引入 echarts.js 文件之后就可以直接使用的

  • echarts.init

    初始化ECharts实例对象 
    使用主题
    
  • echarts.registerTheme

    注册主题 
    只有注册过的主题,才能在init方法中使用该主题
    
  • echarts.registerMap

    注册地图数据 
    $.get('json/map/china.json', function (chinaJson) {
      echarts.registerMap('china', chinaJson);
    });
    geo组件使用地图数据
      var option = {
      geo: {
        type: 'map',
        map: 'china',
      },
    })
    
  • echarts.connect

    • 一个页面中可以有多个独立的图表
  • 每一个图表对应一个 ECharts 实例对象

    • connect 可以实现多图关联,传入联动目标为 EChart 实例,支持数组
    • 保存图片的自动拼接
      • 刷新按钮
    • 重置按钮
      • 提示框联动、图例选择、数据范围修改等。。。
    <!DOCTYPE html>
    <html lang="en">
    
    <head>
      <script src="js/echarts.min.js"></script>
      <script src="js/jquery.min.js"></script>
    </head>
    
    <body>
      <div style="width: 600px;height:400px;border:1px solid red"></div>
      <div style="width: 600px;height:400px;border:1px solid green" id="div1"> </div>
      <script>
        var mCharts = echarts.init(document.querySelector("div"), 'itcast') 
        var xDataArr = ['张三', '李四', '王五', '闰土', '小明',
          '茅台', '二妞', '大 强'
        ]
        var yDataArr = [88, 92, 63, 77, 94, 80, 72, 86]
        var option = {
          xAxis: {
            type: 'category',
            data: xDataArr
          },
          toolbox: {
            feature: {
              saveAsImage: {}
            }
          },
          yAxis: {
            type: 'value'
          },
          series: [{
            type: 'bar',
            data: yDataArr
          }]
        };
        mCharts.setOption(option) $.get('json/map/china.json', function (chinaJson) {
          echarts.registerMap('china', chinaJson) 
          var mCharts2 = echarts.init(document.querySelector('#div1'));
          var option2 = {
            geo: {
              type: 'map',
              map: 'china'
            }
          }
          mCharts2.setOption(option2) 
          echarts.connect([mCharts, mCharts2])
        })
      </script>
    </body>
    </html>
    

    这样, 由于我们打开了toolbox中的saveAsImage, 所以会出现下载图片的按钮. 而通过echarts.connect([mCharts, mCharts2]) , 此时点击下载图片按钮, 保存下来的图片就是两个图表的图片了

2. echartsInstance 对象

eChartsInstance 对象是通过 echarts.init 方法调用之后得到的

  • echartsInstance.setOption

    设置或修改图表实例的配置项以及数据 
    多次调用setOption方法 
    合并新的配置和旧的配置 
    增量动画
    
  • echartsInstance.resize

    重新计算和绘制图表 
    一般和window对象的resize事件结合使用 
    window.onresize = function(){ 
    	myChart.resize(); 
    }
    
  • echartsInstance.on echartsInstance.offff

    绑定或者解绑事件处理函数
    
    • 鼠标事件

      常见事件: 'click''dblclick''mousedown''mousemove''mouseup'等 
      事件参数 arg: 和事件相关的数据信息 
      mCharts.on('click', function (arg) { 
        // console.log(arg) 
        console.log('饼图被点击了')
      }) 
      解绑事件: 
      mCharts.off('click')
      
    • ECharts 事件

      常见事件: legendselectchanged、'datazoom''pieselectchanged''mapselectchanged' 等
      事件参数 arg: 和事件相关的数据信息 
      mCharts.on('legendselectchanged', function (arg) { 
      	console.log(arg) 
      	console.log('图例选择发生了改变...') 
      })
      
  • echartsInstance.dispatchAction

    主动触发某些行为, 使用代码模拟用户的行为

    // 触发高亮的行为 
    mCharts.dispatchAction({
      type: "highlight",
      seriesIndex: 0,
      dataIndex: 1
    }) // 触发显示提示框的行为 
    mCharts.dispatchAction({
      type: "showTip",
      seriesIndex: 0,
      dataIndex: 3
    })
    
  • echartsInstance.clear

    清空当前实例,会移除实例中所有的组件和图表

    清空之后可以再次 setOption

  • echartsInstance.dispose

    销毁实例

    销毁后实例无法再被使用

3.echart 渐变内置生成器echarts.graphic.LinearGradient

在使用echarts绘制图表时, 如果需要使用渐变色, 则应使用echarts内置的渐变色生成器echarts.graphic.LinearGradient

itemStyle: {
	normal: {
		color: '#00E2FF',
		lineStyle: {
			// 系列级个性化折线样式
			width: 5,
			type: 'solid',
			// 颜色渐变函数 前四个参数分别表示四个位置依次为
            // 右下左上
			color: new echarts.graphic.LinearGradient(1, 0, 0, 0, [
				{
					offset: 0,
					color: '#00E2FF'
				},
				{
					offset: 1,
					color: '#0063BF'
				}
			]) // 线条渐变色
		}
	},
	emphasis: {
		color: '#0063BF',
		lineStyle: {
			// 系列级个性化折线样式
			width: 5,
			type: 'dotted',
			color: '#4fd6d2' // 折线的颜色
		}
	}
}, // 线条样式
areaStyle: {
	normal: {
		color: new this.$echarts.graphic.LinearGradient(0, 0, 0, 1, [
			{
				// 折线图颜色渐变
				offset: 0,
				color: 'rgba(0, 226, 255, 0.5)'
			},
			{
				offset: 1,
				color: 'rgba(0, 99, 191, 0)'
			}
		])
	}
},

入了5个参数:

前4个参数用于配置渐变色的起止位置, 这4个参数依次对应右/下/左/上四个方位. 而0 0 0 1则代表渐变色从正上方开始.
第5个参数则是一个数组, 用于配置颜色的渐变过程. 包含offset和color两个参数. offset的范围是0 ~ 1, 用于表示位置, color表示颜色

六、案例地址

https://gitee.com/wu_yuxin/echarts-learning.git

分为三部分代码

  • 原生(jQuery)编写的一个小项目

  • echarts基础

  • echarts-online实例

七、案例内后端部分-KOA2的使用

1、KOA2的介绍
  • 基于 Node.js 平台的Web服务器框架

  • 由 Express 原班人马打造

    Express Koa , Koa2 都是 Web 服务器的框架,他们之间的差别和关系可以通过下面这个表格表示出

框架名作用异步处理
Expressweb 框架回调函数
Koaweb 框架Generator+yield
Koa2web 框架async/await
  • 环境依赖 Node v7.6.0 及以上

    由于 Koa2 它是支持 async 和 await ,所以它对 Node 的版本是有要求的,它要求 Node 的版本至少是在7.6级以上,因为语法糖 async和await 是在 Node7.6 版本之后出现才支持

  • 洋葱模型的中间件

    如下图所示, 对于服务器而言,它其实就是来处理一个又一个的请求, Web 服务器接收由浏览器发过来的一个又一个请求之后,它形成一个又一个的响应返回给浏览器. 而请求到达我们的服务器是需要经过程序处理的,程序处理完之后才会形成响应,返回给浏览器,我们服务器处理请求的这一块程序,在 Koa2 的世界当中就把它称之为中间件

在这里插入图片描述

  • 这种中间件可能还不仅仅只有一个,可能会存在多个,比如上图所示, 它就存在三层中间件,这三层中间件在处理请求的过程以及它调用的顺序为:

    • 当一个请求到达咱们的服务器,最先最先处理这个请求的是第一层中间件
    • 第一层的中间件在处理这个请求之后,它会把这个请求给第二层的中间件
    • 第二层的中间件在处理这个请求之后,它会把这个请求给第三层的中间件
    • 第三层中间件内部并没有中间件了, 所以第三层中间件在处理完所有的代码之后,这个请求又会到了第二层的中间件,所以第二层中间件对这个请求经过了两次的处理
    • 第二层的中间件在处理完这个请求之后,又到了第一层的中间件, 所以第一层的中间件也对这个请求经过了两次的处理

这个调用顺序就是洋葱模型, 中间件对请求的处理有一种先进后出的感觉,请求最先到达第一层中间件,而最后也是第一层中间件对请求再次处理了一下

2、KOA2的快速上手

如何对 Koa2 进行快速的上手呢?需要有如下几个步骤

  • 检查 Node 的版本

    • node -v 的命令可以帮助我们检查 Node 的版本, Koa2 的使用要求 Node 版本在7.6及以上
  • 安装 Koa2

    • npm init -y

      这个命令可以快速的创建出 package.json 的文件, 这个文件可以维护项目中第三方包的信息

    • npm install koa

      这个命令可以在线的联网下载最新版本 koa 到当前项目中, 由于线上最新版本的 koa 就是koa2 , 所以我们并不需要执行 npm install koa2

      如果下载特别慢的话, 需要将 npm 的下载源换成国内的下载源, 命令如下

      npm set registry https://registry.npm.taobao.org/
      
  • 编写入口文件 app.js

    • 创建 Koa 的实例对象

      // 1.创建koa对象 
      const Koa = require('koa') // 导入构造方法 
      const app = new Koa() // 通过构造方法, 创建实例对象
      
    • 编写响应函数(中间件)

      响应函数是通过use的方式才能产生效果, 这个函数有两个参数, 一个是 ctx ,一个是 next

      • ctx :

      上下文, 指的是请求所处于的Web容器,我们可以通过 ctx.request 拿到请求对象, 也可以通过 ctx.response 拿到响应对象

      • next :

        内层中间件执行的入口

      // 2.编写响应函数(中间件) 
      app.use((ctx, next) => { 
      	console.log(ctx.request.url) 
      	ctx.response.body = 'hello world' 
      })
      
    • 指明端口号

      通过 app.listen 就可以指明一个端口号

      // 3.绑定端口号 3000 
      app.listen(3000)
      
  • 启动服务器

    通过 node app.js 就可以启动服务器了

随即打开浏览器, 在浏览器中输入 127.0.0.1:3000/ 你将会看到浏览器中出现 hello world 的字符串, 并且在服务器的终端中, 也能看到请求的 url

3、KOA2中间件的特点
  • Koa2 的实例对象通过 use 方法加入一个中间件
  • 一个中间件就是一个函数,这个函数具备两个参数,分别是 ctx 和 next
  • 中间件的执行符合洋葱模型
  • 内层中间件能否执行取决于外层中间件的 next 函数是否调用
  • 调用 next 函数得到的是 Promise 对象, 如果想得到 Promise 所包装的数据, 可以结合 await 和 async
4、后台项目的开发
1.后台项目的目标

我们已经学习完了 KOA2 的快速上手, 并且对 KOA2 当中的中间件的特点页进行了讲解. 接下来就是利用KOA2 的知识来进行后台项目的开发,后台项目需要达到这以下几个目标:

  • 1.计算服务器处理请求的总耗时

    计算出服务器对于这个请求它的所有中间件总耗时时长究竟是,我们需要计算一下

  • 2.在响应头上加上响应内容的 mime 类型

    加入mime类型, 可以让浏览器更好的来处理由服务器返回的数据.

    如果响应给前端浏览器是 json 格式的数据,这时候就需要在咱们的响应头当中增加 Content- Type 它的值就是 application/json , application/json 就是 json 数据类型的 mime 类型

  • 3.根据URL读取指定目录下的文件内容

    为了简化后台服务器的代码,前端图表所要的数据, 并没有存在数据库当中,而是将存在文件当中的,这种操作只是为了简化咱们后台的代码. 所以咱们是需要去读取某一个目录下面的文件内容的。

每一个目标就是一个中间件需要实现的功能, 所以后台项目中需要有三个中间件

2.后台项目的开发步骤

创建一个新的文件夹, 叫做 koa_server , 这个文件夹就是后台项目的文件夹

  • 1.项目准备

    • 1.安装包

      • npm init -y
      • npm install koa
    • 2.创建文件和目录结构
      在这里插入图片描述

    • app.js 是后台服务器的入口文件

      data 目录是用来存放所有模块的 json 文件数据

      middleware 是用来存放所有的中间件代码

      koa_response_data.js 是业务逻辑中间件

      koa_response_duration.js 是计算服务器处理时长的中间件

      koa_response_header.js 是用来专门设置响应头的中间件

    接着将各个模块的 json 数据文件复制到 data 的目录之下, 接着在 app.js 文件中写上代码如下:

    // 服务器的入口文件 
    // 1.创建KOA的实例对象 
    const Koa = require('koa') 
    const app = new Koa() 
    // 2.绑定中间件 
    // 绑定第一层中间件 
    // 绑定第二层中间件 
    // 绑定第三层中间件 
    // 3.绑定端口号 8888 
    app.listen(8888)
    
  • 2.总耗时中间件

    • 1.第1层中间件

      总耗时中间件的功能就是计算出服务器所有中间件的总耗时,应该位于第一层,因为第一层的中间件是最先处理请求的中间件,同时也是最后处理请求的中间件

    • 2.计算执行时间
      第一次进入咱们中间件的时候,就记录一个开始的时间

      当其他所有中间件都执行完之后,再记录下结束时间以后

      将两者相减就得出总耗时

    • 3.设置响应头

      将计算出来的结果,设置到响应头的 X-Response-Time 中, 单位是毫秒 ms

    具体代码如下:

    app.js

    // 绑定第一层中间件 
    const respDurationMiddleware = require('./middleware/koa_response_duration') 
    app.use(respDurationMiddleware)
    

    koa_response_duration.js

    // 计算服务器消耗时长的中间件 
    module.exports = async (ctx, next) => {
      // 记录开始时间
      const start = Date.now() 
      // 让内层中间件得到执行 
      await next() 
      // 记录结束的时间 
      const end = Date.now() 
      // 设置响应头 X-Response-Time 
      const duration = end - start 
      // ctx.set 设置响应头 
      ctx.set('X-Response-Time', duration + 'ms') 
    }
    
  • 3.响应头中间件

    • 1.第2层中间件

      这个第2层中间件没有特定的要求

    • 2.获取 mime 类型

      由于咱们所响应给前端浏览器当中的数据都是 json 格式的字符串,所以 mime 类型可以统一的给它写成 application/json , 当然这一块也是简化的处理了,因为 mime 类型有几十几百种,我们我们没有必要在我们的项目当中考虑那么多,所以这里简化处理一下

    • 3.设置响应头

      响应头的key是 Content-Type ,它的值是 application/json , 顺便加上 charset=utf-8

      告诉浏览器,我这部分响应的数据,它的类型是 application/json ,同时它的编码是 utf- 8

    具体代码如下:

    app.js

    // 绑定第二层中间件 
    const respHeaderMiddleware = require('./middleware/koa_response_header') 
    app.use(respHeaderMiddleware)
    

    koa_response_header.js

    // 设置响应头的中间件 
    module.exports = async (ctx, next) => { 
    	const contentType = 'application/json; charset=utf-8' 
    	ctx.set('Content-Type', contentType) 
    	await next() 
    }
    
  • 4.业务逻辑中间件

    • 1.第3层中间件

      这个第3层中间件没有特定的要求

    • 2.读取文件内容

      • 获取 URL 请求路径

        const url = ctx.request.url
        
      • 根据URL请求路径,拼接出文件的绝对路径

        let filePath = url.replace('/api', '') 
        filePath = '../data' + filePath + '.json'
        filePath = path.join(__dirname, filePath)
        

        这个 filePath 就是需要读取文件的绝对路径

      • 读取这个文件的内容

        使用 fs 模块中的 readFile 方法进行实现

    • 3.设置响应体

      ctx.response.body

    具体代码如下:

    app.js

    // 绑定第三层中间件 
    const respDataMiddleware = require('./middleware/koa_response_data') 
    app.use(respDataMiddleware)
    

    koa_response_data.js

    // 处理业务逻辑的中间件,读取某个json文件的数据 
    const path = require('path') 
    const fileUtils = require('../utils/file_utils') 
    module.exports = async (ctx, next) => { 
    	// 根据url 
    	const url = ctx.request.url // /api/seller ../data/seller.json 
    	let filePath = url.replace('/api', '') // /seller 
    	filePath = '../data' + filePath + '.json' // ../data/seller.json 
    	filePath = path.join(__dirname, filePath) 
    	try { 
    		const ret = await fileUtils.getFileJsonData(filePath) 
    		ctx.response.body = ret
    	} catch (error) { 
    		const errorMsg = { 
    			message: '读取文件内容失败, 文件资源不存在', 
    			status: 404 
            }
            ctx.response.body = JSON.stringify(errorMsg) 
        }
        console.log(filePath) 
        await next() 
    }
    

    file_utils.js

    // 读取文件的工具方法 
    const fs = require('fs') 
    module.exports.getFileJsonData = (filePath) => { 
    	// 根据文件的路径, 读取文件的内容 
    	return new Promise((resolve, reject) => { 
    		fs.readFile(filePath, 'utf-8', (error, data) => { 
    			if(error) { 
    				// 读取文件失败 
    				reject(error) 
    			} else { 
    				// 读取文件成功 
    				resolve(data) 
    			} 
    		}) 
    	}) 
    }
    
  • 5.允许跨域

    • 设置响应头
    app.use(async (ctx, next) => { 
    	ctx.set("Access-Control-Allow-Origin", "*") 
    	ctx.set("Access-Control-Allow-Methods", "OPTIONS, GET, PUT, POST, DELETE") 
    	await next(); 
    })
    

八、js中WebSocket

1、WebSocket是什么?

​ WebSocket是一种网络通信协议, 一种由HTML5 开始提供的、在单个 TCP 连接上进行全双工通讯的协议。它和HTTP协议的最大区别在于:HTTP 协议是一种无状态的、无连接的、单向的应用层协议当客户端想要知道服务端的变化时,HTTP协议必须使用“轮询”的方式,效率很低;而WebSocket只需一次连接,便可以让服务端直接向客户端推送信息,从而告别轮询。

其实只要记住几点:

  1. WebSocket可以在浏览器里使用
  2. 支持双向通信
  3. 使用很简单

2、WebSocket的优点

很多网站为了实现数据推送,所用的技术都是ajax轮询。轮询是在特定的时间间隔,由浏览器主动发起请求,将服务器的数据拉回来。轮询需要不断的向服务器发送请求,会占用很多带宽和服务器资源。WebSocket建立TCP连接后,服务器可以主动给客户端传递数据,能够更好的节省服务器资源和带宽,实现更实时的数据通讯。

概括地说就是:支持双向通信,更灵活,更高效,可扩展性更好。

  1. 支持双向通信,实时性更强。
  2. 更好的二进制支持。
  3. 较少的控制开销。连接创建后,ws客户端、服务端进行数据交换时,协议控制的数据包头部较小。在不包含头部的情况下,服务端到客户端的包头只有2~10字节(取决于数据包长度),客户端到服务端的的话,需要加上额外的4字节的掩码。而HTTP协议每次通信都需要携带完整的头部。
  4. 支持扩展。ws协议定义了扩展,用户可以扩展协议,或者实现自定义的子协议。(比如支持自定义压缩算法等)

在这里插入图片描述
3、WebSocke的属性

属性描述
Socket.readyState只读属性 readyState 表示连接状态,可以是以下值:0 - 表示连接尚未建立。1 - 表示连接已建立,可以进行通信。2 - 表示连接正在进行关闭。3 - 表示连接已经关闭或者连接不能打开。
Socket.bufferedAmount只读属性 bufferedAmount 已被 send() 放入正在队列中等待传输,但是还没有发出的 UTF-8 文本字节数。

4、WebSocket 事件

事件事件处理程序描述
openSocket.onopen连接建立时触发
messageSocket.onmessage客户端接收服务端数据时触发
errorSocket.onerror通信发生错误时触发
closeSocket.onclose连接关闭时触发

我们可以看出所有的操作都是采用消息的方式触发的,这样就不会阻塞UI,使得UI有更快的响应时间,得到更好的用户体验。

(1)当Browser和WebSocketServer连接成功后,会触发onopen消息;

websocket.onopen = function(evt) {};

(2)如果连接失败,发送、接收数据失败或者处理数据出现错误,browser会触发onerror消息;

websocket.onerror = function(evt) { };

(3)当Browser接收到WebSocketServer发送过来的数据时,就会触发onmessage消息,参数evt中包含server传输过来的数据;

websocket.onmessage = function(evt) { };

(4)当Browser接收到WebSocketServer端发送的关闭连接请求时,就会触发onclose消息。

websocket.onclose = function(evt) { };

5、WebSocket 方法

以下是 WebSocket 对象的相关方法。假定我们使用了以上代码创建了 Socket 对象:

方法描述
Socket.send()使用连接发送数据
Socket.close()关闭连接

6、通信协议

WebSocket与TCP、HTTP的关系WebSocket与http协议一样都是基于TCP的,所以他们都是可靠的协议,Web开发者调用的WebSocket的send函数在browser的实现中最终都是通过TCP的系统接口进行传输的。

WebSocket和Http协议一样都属于应用层的协议,那么他们之间有没有什么关系呢?答案是肯定的,WebSocket在建立握手连接时,数据是通过http协议传输的,但是在建立连接之后,真正的数据传输阶段是不需要http协议参与的。
在这里插入图片描述
7、WebSocket通讯解读:

从下图可以明显的看到,分三个阶段:

  1. 打开握手
  2. 数据传递
  3. 关闭握手
    在这里插入图片描述
    下图显示了WebSocket主要的三步 浏览器和 服务器端分别做了那些事情。

在这里插入图片描述
8、建立连接的握手

当Web应用程序调用new WebSocket(url)接口时,Browser就开始了与地址为url的WebServer建立握手连接的过程。

  1. Browser与WebSocket服务器通过TCP三次握手建立连接,如果这个建立连接失败,那么后面的过程就不会执行,Web应用程序将收到错误消息通知。

  2. 在TCP建立连接成功后,Browser/UA通过http协议传送WebSocket支持的版本号,协议的字版本号,原始地址,主机地址等等一些列字段给服务器端。

  3. WebSocket服务器收到Browser/UA发送来的握手请求后,如果数据包数据和格式正确,客户端和服务器端的协议版本号匹配等等,就接受本次握手连接,并给出相应的数据回复,同样回复的数据包也是采用http协议传输。

  4. Browser收到服务器回复的数据包后,如果数据包内容、格式都没有问题的话,就表示本次连接成功,触发onopen消息,此时Web开发者就可以在此时通过send接口想服务器发送数据。否则,握手连接失败,Web应用程序会收到onerror消息,并且能知道连接失败的原因。

这个握手很像HTTP,但是实际上却不是,它允许服务器以HTTP的方式解释一部分handshake的请求,然后切换为websocket

9、数据传输

WebScoket协议中,数据以帧序列的形式传输。

考虑到数据安全性,客户端向服务器传输的数据帧必须进行掩码处理。服务器若接收到未经过掩码处理的数据帧,则必须主动关闭连接。

服务器向客户端传输的数据帧一定不能进行掩码处理。客户端若接收到经过掩码处理的数据帧,则必须主动关闭连接。

针对上情况,发现错误的一方可向对方发送close帧(状态码是1002,表示协议错误),以关闭连接。

关闭WebSocket(握手)

在这里插入图片描述

九、知识拓展

1、详解a标签中href="javascript:"的几种用法

一、js 伪协议的几种调用方法(参考总结的)

1、<a href="javascript:js_method();></a>"`

​ 这是常用的方法,但是这种方法在传递this等参数的时候很容易出问题,而且javascript:协议作为a的href属性的时候不仅会导致不必要的触发window.onbeforeunload事件,在IE里面更会使gif动画图片停止播放。W3C标准不推荐在href里面执行javascript语句

​ 2、 <a href="javascript:void(0);" onclick="js_method()></a>"`

​ 这种方法是很多网站最常用的方法,也是最周全的方法,onclick方法负责执行js函数,而void是一个操作符,void(0)返回undefined,地址不发生跳转。而且这种方法不会像第一种方法一样直接将js方法暴露在浏览器的状态栏。

​ 3、<a href="javascript:;" onclick="js_method()></a>"`

​ 这种方法跟跟2种类似,区别只是执行了一条空的js代码。

4、<a href="#" onclick="js_method()></a>"`

​ 这种方法也是网上很常见的代码,#是标签内置的一个方法,代表top的作用。所以用这种方法点击后网页后返回到页面的最顶端。

5、<a href="#" onclick="js_method();return false;></a>"`

​ 这种方法点击执行了js函数后return false,页面不发生跳转,执行后还是在页面的当前位置。

6、<a href='javascript:todoFun(void)'>删除</a>

这种方法在点击 a 标签时,执行一个 js 另外自定义函数 todoFun(void) 。并传参 void。

综合上述,在a中调用js函数最适当的方法推荐使用:

<a href="javascript:void(0);" onclick="js_method()"></a> 
<a href="javascript:;" onclick="js_method()"></a> 
<a href="#" onclick="js_method();return false;"></a>

二、href="#"的作用

​ a中href="#"表示回到最顶部。如果当前页面中需要滚动的话,那么用这种方式就可以直接回到顶部。比如有些网站会在右下角制作一个图标按钮,回到顶部,那么此时可以考虑用这种最简单的方式实现。

<span style="font-size:14px;"><a href="#">回到最顶端</a></span> 

三、href="URL"的作用

1、URL为绝对URL

此时指向另一个站点,比如href=“http://write.blog.csdn.NET”,那么点击时就会直接跳转到这个链接的页面。

2、URL为相对URL

此时指向站点内的某个文件,比如href="/test.doc",那么点击时就会直接下载文件。

3、锚 URL

​ 此时指向页面中的锚,比如href="#top",那么点击时就会到当前页面中id="top"的这个锚点,实现当前页面的所谓跳转。用的最多就是在可滚动页面中,添加菜单,可以直接回到页面中的某个部分的内容。

即所有的三种代码样例:

<a href="http://baidu.com">超链接</a> 
<a href="#">回到最顶端</a> 
<a href="css/css1.css">文件链接</a>
2、Uncaught TypeError: Object(…) is not a function at resetStoreState

在这里插入图片描述
在Vue2中使用Vuex4.0以上版本会报这个错误

在这里插入图片描述
引起这个错误的原因是因为Vuex4.0以上版本依赖于Vue3中的一些属性方法

解决方案

npm uninstall vuex
npm install vuex@3.4.0
// 将版本转换为3.4.0即可完美解决这个问题
3、window.location获取url各项参数详解

1.href ----- 整个URL字符串.

2.protocol ----- 含有URL第一部分的字符串,如https.

3.host ----- 主机名.

4.port ----- 端口号.

5.pathname ----- 路径.

6.search ----- “?” 之后的字符串.

7.hash ----- “#” 之后的字符串.

下面举个例子,有这样一个URL

https://www.djhero.com:80/dj/post/0805/dongjing.html?ver=1.0&id=1#happy

1.window.location.href

整个URl字符串(浏览器完整的地址栏)

返回值:

https://www.djhero.com:80/dj/post/0805/dongjing.html?ver=1.0&id=6#happy

2.window.location.protocol

URL的协议部分

返回值:

https:

3.window.location.host & window.location.hostname

URL的主机部分

返回值:

www.djhero.com

4.window.location.port

URL的端口部分

返回值:" "

Note: If the port number is default (80 for http and 443 for https), most browsers will display 0 or nothing.

5.window.location.pathname

URL的路径部分

返回值:

/dj/post/0805/dongjing.html

6.window.location.search

查询部分

返回值:

?ver=1.0&id=1

7.window.location.hash

锚点

返回值:

#happy
4、javascript中sort方法的完整解析

说起对数组的排序,大家能想到的应该是冒泡排序,快速排序,sort排序,以及希尔排序吧,但是可能对sort排序只停留再数组层面(每个元素均是数字或者字符串),事实上,它还可以对对象进行排序。

原理是:不管元素是什么类型,sort排序始终是根据元素的unicode编码进行的

下面来分别看下各种情况:

元素为数字或者字符串:

先从简单的开始,大家都知道sort()函数比较的是ASCII码的大小,而且而且而且:Array的sort()方法默认把所有元素先转换为String再排序,所以就有以下问题。

 var arr1 = [10,1,5,2,3];
 arr1.sort();
 console.log(arr1);

在这里插入图片描述
结果转换成字符串比较,'10’排在了’2’的前面,因为字符’1’比字符’2’的ASCII码小

[语法]:
arr.sort()

arr.sort(compareFunction)

[参数]:

compareFunction可选。用来指定按某种顺序进行排列的函数。如果省略,元素按照转换为的字符串的诸个字符的Unicode位点进行排序。
[返回值]:

返回排序后的数组。原数组已经被排序后的数组代替。

[描述]:

如果没有指明 compareFunction ,那么元素会按照转换为的字符串的诸个字符的Unicode位点进行排序。例如 “Banana” 会被排列到 “cherry” 之前。数字比大小时,2 出现在 10 之前,但这里比较时数字会先被转换为字符串,所以 “10” 比 “2” 要靠前。

如果指明了 compareFunction ,那么数组会按照调用该函数的返回值排序。即 a 和 b 是两个将要被比较的元素:

如果 compareFunction(a, b) 小于 0 ,那么 a 会被排列到 b 之前;
如果 compareFunction(a, b) 等于 0 , a 和 b 的相对位置不变。备注: ECMAScript 标准并不保证这一行为,而且也不是所有浏览器都会遵守(例如 Mozilla 在 2003 年之前的版本);
如果 compareFunction(a, b) 大于 0 , b 会被排列到 a 之前。
compareFunction(a, b) 必须总是对相同的输入返回相同的比较结果,否则排序的结果将是不确定的。

所以,比较函数格式如下:

function compare(a, b) {
  if (a < b) {           // 按某种排序标准进行比较, a 小于 b
    return -1;
  }
  if (a > b) {
    return 1;
  }
  // a must be equal to b
  return 0;
}

要比较数字而非字符串,比较函数可以简单的以 a 减 b,如下的函数将会将数组升序排列

function compareNumbers(a, b) {
  return a - b;
}
5、javascript中set与get方法详解

其中get与set的使用方法:

1、get与set是方法,因为是方法,所以可以进行判断。

2、get是得到 一般是要返回的 set 是设置 不用返回

3、如果调用对象内部的属性约定的命名方式是_age

然后就是几个例子来简单说明一下:

var person ={ 
	_name : "chen",
    age:21,
    set name(name) {
    	this._name = name;
    },
    get name() {
    	return this._name;
    }
}
console.log(person.name)
输出”chen“
person.name="lunc";
输出"lunc"
person.name
输出"lunc"

例子2:

var p = {
    name:"chen",
    work:function() {
        console.log("wording...");
    },
    _age:18,
    get age(){
        return this._age;
    },
    set age(val) {
        if (val<0 || val> 100) {//如果年龄大于100就抛出错误
            throw new Error("invalid value")
        }else{
            this._age = val;
        }
    }
};
console.log(p.name);//输出chen
浏览器的直接调试结果:
    p.age
    "18"
    p.age=23
    "23"
    p.age=200
    Uncaught Error: invalid value
  • 9
    点赞
  • 98
    收藏
    觉得还不错? 一键收藏
  • 3
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值