首页 > 代码库 > CSDN开源夏令营 百度数据可视化实践 ECharts(6) 期中总结

CSDN开源夏令营 百度数据可视化实践 ECharts(6) 期中总结

期中总结

(1)首先感谢林峰老师的辛勤指导!!
    通过半个多月的培训,林峰老师讲解了ECharts总体框架和其中各个部分:图类、组件、接口、基础库的具有应用方法和应该把握的细节,并通过实际的例子熟悉和掌握各个控件。只有打牢基础才能正正的为下步的工作做好准备,熟练的属性代码的编程技巧,才能做出更好的专题。
   
(2)第一次任务重点总结:
   要求:了解ECharts特性中列举的每一项特性,并能找到实例中的例子,并且在实例中操作。
   重点问题:
  1)ECharts一种支持多少种图表?有多少个组件?列举出中英文名称。

  共11类图表:折线图(line)、柱状图(bar)、散点图(scatter)、k线图(k)、饼图(pie)、雷达图      (radar)、和炫图(chord)、力导向布局      图(force)、地图(map)、仪表盘(gauge)、漏斗图(funnel)。
 

  7种组件:标题(title)、详情气泡(tooltip)、图例(legend)、值域(dataRange)、数据区域(datazoom)、时间轴(timeline)、工具箱(toolbox)。
  更加具体组件:Axis(坐标轴)、Grid(网格)、Polar(极坐标)、Title(标题)、Tooltip(提示)、        Legend(图例)、DataZoom(数据区域缩放)、DataRange(值域漫游)、Toolbox(工具箱)、Timeline(时间轴)。


  官网上如下图所示:
  

  详细划分后如下图:
    


  2)哪些特性可以让用户修改图表中的数据?哪些特性帮助用户进行信息筛选(专注)?哪些特性帮助实现了用不同的方式解读同样的数据?
  答:

 改图表中的数据:拖拽重计算、数据视图

  信息筛选:图例开关、数据区域缩放功能、值域漫游
  帮助了解不同的方式:动态类型切换、多图联动、多维度堆积、混搭

 3) 怎么引入ECharts?有几种方式?有什么不同?这里重点讲述其中的不同

    
第一种方法是packet引入,这是开发时最好的做法,不管是开发echarts还是用echarts都是,因为文件未被合并压 缩,所有 的错误能立马定位到出错的地方从而让你快速知道可能问题会出在哪。但这并不适合直接上线,原因就是上面说的,这样上网会被骂死的,因为传送将会花费大量的时间,用户肯定忍受不了。

 

//  from echarts example
 require.config({
 packages:[
 {
 name:’echarts’,
 location:’../../src’,
 main:’echarts’
 },
 {
 name:’zrender’,
 location:’../../../zrender/src’,//zrender与echarts在同一级目录
 main:’zrender’
 }
 ]
 });

第二种方法是模块化单文件引入,真正上线时如果你是模块化的项目,应该用连接压缩好的单文件,也就是第二种。

但问题可能就来了,如果我只用到一个图表,如果直接用第二种方式上线可是把所有图表都打包在一起啊,就会造成资源的严重浪费,那么最真实做法是项目打包,用到什么就打包什么,这种方法效率好。

<span style="font-family:SimSun;">//from echarts example
require.config({
	path:{
	‘echarts’:’./js/echarts’,
	‘echarts/chart/bar’:’./js/echarts’,//把所需图表指向单文件
	‘echarts/chart/line’:’./js/echarts’
}});
配置好后可以通过动态加载使用echarts
function(ec){
	var mychart=ec.init(domMain);
	var option={...}
	myChart.setOption(option);
});</span>


  第三种方法就是标签式单文件引入,其实还是因为使用方的环境和水平差异较大所来的。其实这个单文件的构建只是我们用一个大闭包把模块加载器和echarts打包在一起,通过一个全局的命名空间echarts/zrender对外暴露出去而已。内部还是模块化的,只是使用方就当命名空间来用就行,这可以免去很多不熟悉模块化的开发人员在管理各种调用时序、声明、回调之类的麻烦。
对于模块化问题大家可以多去看看CMD规范、AMD规范。


4)如何初始化出一个ECharts实例?
  在回调函数种使用init方法初始化。

<span style="font-family:SimSun;"> var myEChart = ec.init(docuemt.getElementBy(“main”));
 myEChart.setOption({})…</span>

 图标库为多实例,同一个页面可在多个dom init多个图表,同一个dom 再次init将释放已有实例。

3)第二次任务重点总结:
    
   将ECharts引入项目共有三种方式,将其全部实现,并将line1的Option应用上。
   具体的实现参考博文:
    CSDN开源夏令营 百度数据可视化实践 ECharts(2) 

(4)第三次任务重点总结:
  
   4.1)  ec大多数组件都能支持称为“九宫格自由布局”的方式,怎么理解?那些组件支持?
    

   这就是九宫格自由布局,x支持left、center和right,y 支持right、center和bottom

   

   这样x,y就能把页面划分为9个区域,可以任意定位在一处。x/y除了支持语义文本,还能更加特殊的传入数值做绝对定位比如:{x:100, y:100}。甚至有个别组件还能支持百分比:x:‘10%’代表横向定位在总宽度*10%的位置
注意js数据类型没有‘10%’百分比这一说,设置时是字符串,内部逻辑会处理为百分比。
   
 (5)Formatter是万金油,可以实现高度个性化的需求,那些地方支持formatter?

   首先大家要认识到Formatter是做文本格式化用的。因为不可能内置文本显示能满足所有需求,所以在做个性化定制是formatter显得尤为重要和灵活,不仅是满足格式要求,甚至可用于满足图形化的需求,功能很是强大。
   最常见的是tooltip、axisLabel、itemStyle.*.label.formatter
   
   
   异步回调方式填充tooltip
   

  这就是一个异步回调的模拟,可以把setTimeout理解为一个ajax的回调。当网络请求回来内容时callback调用填充tooltip内容就是一个异步回调填充tooltip的过程。保证了交互的准确性,总之功能很强大大家慢慢挖掘。
  

   重点提示:永远别忘了数据在你自己的手里,option是你传个ec的,如果任何地方的回调变量或数据不能满足你的需求,直接从你自己的option里找。

  (6)如何利用dataZoom实现按需加载特定区间数据?比如显示一个全年的趋势作为dataZoom,仅加载当前选定的区间数据?dataZoom交互发生区间变化后按需请求特定区间数据并加载?
   首先先上代码:
    

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="utf-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta name="description" content="ECharts">
    <meta name="author" content="linzhifeng@baidu.com">
    <title>ECharts · Example</title>

    <link rel="shortcut icon" href="../asset/ico/favicon.png">

    <link href="http://maxcdn.bootstrapcdn.com/font-awesome/4.1.0/css/font-awesome.min.css" rel="stylesheet">
    <link href="../asset/css/bootstrap.css" rel="stylesheet">
    <link href="../asset/css/carousel.css" rel="stylesheet">
    <link href="../asset/css/echartsHome.css" rel="stylesheet">
    <!-- HTML5 shim and Respond.js IE8 support of HTML5 elements and media queries -->
    <!--[if lt IE 9]>
      <script src="https://oss.maxcdn.com/html5shiv/3.7.2/html5shiv.min.js"></script>
      <script src="https://oss.maxcdn.com/respond/1.4.2/respond.min.js"></script>
    <![endif]-->

    <script src="../asset/js/esl/esl.js"></script>
    <script src="../asset/js/codemirror.js"></script>
    <script src="../asset/js/javascript.js"></script>

    <link href="../asset/css/codemirror.css" rel="stylesheet">
    <link href="../asset/css/monokai.css" rel="stylesheet">
</head>

<body>
    <!-- Fixed navbar -->
    <div class="navbar navbar-default navbar-fixed-top" role="navigation" id="head"></div>


    <div class="container-fluid">
        <div class="row-fluid example">
            <div id="sidebar-code" class="col-md-4">
                <div class="well sidebar-nav">
                    <div class="nav-header"><a href="#" onclick="autoResize()" class="glyphicon glyphicon-resize-full" id ="icon-resize" ></a>option</div>
                    <textarea id="code" name="code">
option = {
    tooltip : {
        trigger: 'axis'
    },
    legend: {
        data:['选定区间数据']
    },
    toolbox: {
        show : true,
        feature : {
            mark : {show: true},
            dataView : {readOnly:false},
            magicType : {show: true, type: ['line', 'bar', 'stack', 'tiled']},
            restore : {show: true},
            saveAsImage : {show: true}
        }
    },
    dataZoom : {
        show : true,
        realtime : false,
        start : 0,
        end : 10,
        xAxisIndex:1
    },
    xAxis : [
        {
            type : 'category',
            boundaryGap : true,
            data : function (){
                var list = [];
                for (var i = 0; i < 10; i++) {
                    list.push(i);
                }
                return list;
            }()
        },
        {
            type : 'category',
            name:'隐藏全局',
            boundaryGap : true,
            data : function (){
                var list = [];
                for (var i = 0; i < 100; i++) {
                    list.push(i);
                }
                return list;
            }(),
            splitLine: {show:false},
            splitArea: {show:false}
        }      
    ],
    yAxis : [
        {
            type : 'value'
        }
    ],
    series : [
        {
            name:'选定区间数据',
            type:'line',
            data:function (){
                var list = [];
                for (var i = 0; i < 10; i++) {
                    list.push(Math.round(Math.random()* 30) + 30);
                }
                return list;
            }()
        },
        {
            name:'全局',
            type:'line',
            symbol:'none',
            itemStyle:{  
              normal:{
                color:'rgba(0,0,0,0)'
              }
            },
            data:function (){
                var list = [];
                for (var i = 0; i < 100; i++) {
                    list.push(Math.round(Math.random()* 10));
                }
                return list;
            }(),
          xAxisIndex:1
        }
    ]
};
var ecConfig = require('echarts/config');
function getData(param) {
  var start = param.zoom.start;
  var end = param.zoom.end;
  var curOption = this.getOption();
  curOption.xAxis[0].data = function (){
    var list = [];
    for (var i = start; i < end; i++) {
      list.push(i);
    }
    return list;
  }();
  curOption.series[0].data = function (){
    var list = [];
    for (var i = start; i < end; i++) {
      list.push(Math.round(Math.random()* 30) + 30);
    }
    return list;
  }();
  myChart.setOption(curOption,true)
}


myChart.on(ecConfig.EVENT.DATA_ZOOM, getData);
                    
                    </textarea>
              </div><!--/.well -->
            </div><!--/span-->
            <div id="graphic" class="col-md-8">
                <div id="main" class="main"></div>
                <div>
                    <button type="button" class="btn btn-sm btn-success" onclick="refresh(true)">刷 新</button>
                    <span class="text-primary">切换主题</span>
                    <select id="theme-select"></select>

                    <span id='wrong-message' style="color:red"></span>
                </div>
            </div><!--/span-->
        </div><!--/row-->
        
        </div><!--/.fluid-container-->

    <footer id="footer"></footer>
    <!-- Le javascript
    ================================================== -->
    <!-- Placed at the end of the document so the pages load faster -->
    <script src="../asset/js/jquery.min.js"></script>
    <script type="text/javascript" src="../asset/js/echartsHome.js"></script>
    <script src="../asset/js/bootstrap.min.js"></script>
    <script src="../asset/js/echartsExample.js"></script>
</body>
</html>
 首先要理解dataZoom的两个关键属性,xAxisIndex、yAxisIndex属性用来指定缩放控制的类目轴,比如湖区全局的抽象数据,用12个月或者365天。并且要注意realtime属性,因为动态请求和交互行为,所有就不能把realtime设置成flase,否则就没法运行了。

 (5)掌握和弦图和力导向图,最近才特别火的图

   5.1)弦图属性列表:
名称默认值描述
{number} padding2每个sector之间的间距(用角度表示)
{string} sort‘none‘数据排序, 可以取none, ascending, descending
{string} sortSub‘none‘数据排序(弦), 可以取none, ascending, descending
{boolean} showScalefalse是否显示刻度
{boolean} showScaleTextfalse是否显示刻度文字
{boolean} clockWisefalse显示是否顺时针
{Array} matrix[[]]关系数据,用二维数组表示,项 [i][j] 的数值表示 i 到 j 的关系数据
 5.2)力导向图

 参数很多,可以调节参数得到很多的效果,具体内容请参考ECharts官网。原来用 force 主要是为了表现网络数据的聚类,力导向图在刚发的 2.0.1 里基本上重写了,跟以前的参数变化很。布局的算法其实挺直白的,就是通过对物理的模拟,任意两个节点之间存在一个斥力,任意一条边会对邻接节点存在一个引力.每次迭代的时候,就会计算一次所有节点的受力,然后算出速度之后更新它的位移,迭代到一定次数之后每个节点的受力会趋向平衡,就会形成一个大致的形状。
 
名称默认值描述
{Array}categories[]力导向图中节点的分类, 对于每一项:
名称默认值描述
{string} name 类目名称
{string} symbolcircle所有该类目的节点的形状, 详见 symbolList
{number} symbolSize 所有该类目的节点的大小
{boolean} draggable 所有该类目的节点是否能被拖拽
itemStyle 详见 itemStyle
 (6)掌握饼图、雷达图、仪表盘、漏斗图
   各种图的基本属性就不说了,具体就讲讲实例
   6.1)实现下面这个仪表盘:(MPH是英里每小时,km/h是公里每小时)下图063572换成当前的MPH值?
   

   具体详细代码请参考博文:
   CSDN开源夏令营 百度数据可视化实践 ECharts(3)

   6.2)如何控制漏斗图的位置和大小?min/max/minSize/maxSize怎么理解?

   通过series.x/y/x2/y2控制漏斗图的位置和大小,也可通过series.width/height来控制大小,minSize/maxSize控制的是漏斗图最大最小值占到总宽度的比例,min/max 控制的是最大最小值。
   
 
   其中min、max好理解就是数值大小。minSize、maxSize默认是0,100%跟上图完全一样的。

(7)熟练掌握地图和dataZoom
   7.1)内置支持多少种地图类型?什么是子区域模式?加上子地图类型一共能支持多少内置地图类型?
   a)地图内置支持world,china及全国34个省市自治区(省市自治区的mapType直接使用简体中文)。
   b)子区域模式是指,通过主地图类型扩展出所包含的子区域地图,格式为’主地图类型|子区域名称‘。

   c)加上子地图类型大概支持780+个地图类型:world+china+34个省市自治区+226个国家子地图+中国34个省市子地图+ +15(安平均15个市区每省市计算)*34个市区子地图~ 780+个,好多啊 !

   

 另外就是function中算法的应用,高效的算法可以处理数据更快,举个例子,二分查找法:
 代码如下:
 

function binary(items,value){
 var startIndex=0,
     stopIndex=items.length-1,
     midlleIndex=(startIndex+stopIndex)>>>1;
     while(items[middleIndex]!=value && startIndex<stopIndex){
       if(items[middleIndex]>value){
          stopIndex=middleIndex-1;
       }else{
          startIndex=middleIndex+1;
       }
       middleIndex=(startIndex+stopIndex)>>>1;
     }
     return items[middleIndex]!=value ? false:true;
}

 本阶段严格按照林峰老师要求,积极完成任务,完成的代码已经上传到code上,还有少量改进的方法还没上传,修改完成后会上传到code上的,谢谢大家!大家可以多玩玩ECharts,只有在多操作多玩中才能发现问题,进而解决问题,最终会取得进步!下一阶段将继续按照林峰老师要求,一步一步完成任务!