背景
业务要求一个图表默认展示堆积柱状图,点击切换折线图按钮后,显示平铺折线图
实现
1. 原理
官方没有对这个配置项做详细介绍,就一句话——option 可选,可传入切换是动态修改的配置,将复写series内的数组项
,不怎么懂,只好研究源码:
toolbox.js 第1150行:
_defaultMagic : function(cType1, cType2) {
if (this._magicType[cType1] || this._magicType[cType2]) {
for (var i = 0, l = this.option.series.length; i < l; i++) {
var chartType = this.option.series[i].type;
if (chartType == cType1 || chartType == cType2) {
this.option.series[i].type = this._magicType[cType1] ? cType1 : cType2;
// 避免不同类型图表类型的样式污染
this.option.series[i].itemStyle = zrUtil.clone(
this.option.series[i].__itemStyle
);
chartType = this.option.series[i].type;
if (this._featureOption[chartType + 'Chart']) {
zrUtil.merge(
this.option.series[i],
this._featureOption[chartType + 'Chart'] || {},
true
);
}
}
}
}
},
zrender的util.js 第110行
/**
* @memberOf module:zrender/core/util
* @param {*} target
* @param {*} source
* @param {boolean} [overwrite=false]
*/
export function merge(target, source, overwrite) {
// We should escapse that source is string
// and enter for ... in ...
if (!isObject(source) || !isObject(target)) {
return overwrite ? clone(source) : target;
}
for (var key in source) {
if (source.hasOwnProperty(key)) {
var targetProp = target[key];
var sourceProp = source[key];
if (isObject(sourceProp)
&& isObject(targetProp)
&& !isArray(sourceProp)
&& !isArray(targetProp)
&& !isDom(sourceProp)
&& !isDom(targetProp)
&& !isBuiltInObject(sourceProp)
&& !isBuiltInObject(targetProp)
&& !isPrimitive(sourceProp)
&& !isPrimitive(targetProp)
) {
// 如果需要递归覆盖,就递归调用merge
merge(targetProp, sourceProp, overwrite);
}
else if (overwrite || !(key in target)) {
// 否则只处理overwrite为true,或者在目标对象中没有此属性的情况
// NOTE,在 target[key] 不存在的时候也是直接覆盖
target[key] = clone(source[key], true);
}
}
}
return target;
}
原来如此,懂了
结论:如果要修改某一个功能按钮,比如切换折线图,那么option.toolbox.feature.magicType.option中增加一个line的对象,line对象里面的属性即替换option.series数组中每个对象的属性。
2. 实现:
/**
* 复写工具栏的折线图切换,由 默认切换折线图 变为 平铺切换折线图
* 适用范围:当默认图表为柱状堆积图时,不调用该方法切换折线图为堆积折线图,调用该方法后切换折线图为平铺折线图
* @param option
*/
static setToolBoxTypeLineTiled (option){
if(option.toolbox && option.toolbox.feature && option.toolbox.feature.magicType){
if(option.series){
option.toolbox.feature.magicType.option = {
line : {
stack : null
}
}
}
}
}
自此 搞定收工