当前位置: 首页 > Web前端 > HTML

Echarts扩展问题解决(二)——直方图框选择的随机缩放

时间:2023-03-28 18:30:26 HTML

echarts本身不支持直方图。在官方示例文档中,直方图是使用自定义图表实现的,之前在项目中使用的实现也是直接使用了官方示例的代码。今年三四月份,疫情隔离,我们在家办公的时候,我们的产品经理说,我们的直方图的缩放只能在x轴上放大,不能在y轴上放大。打开!结果,人都傻了。看官方例子的缩放效果,好像只能自己动手了。首先我们要明白直方图的renderItem属性是如何渲染直方图的,也就是整体series//普通直方图seriesconsttempseries={type:'custom',renderItem:function(params:any,api:any){让yValue=api.value(2);//console.log(yValue,'yValue');让start=api.coord([api.value(0),yValue]);letsize=api.size([(api.value(1)asnumber)-(api.value(0)asnumber),yValue])asnumber[];//console.log(开始,'开始');//console.log(size,'size');conststyle=api.style();return{type:'rect',shape:{x:start[0],y:start[1],width:size[0],height:size[1],},样式,};},label:{show:false,position:'top',},dimensions:['from','to','count'],编码:{x:[0,1],y:2,tooltip:[0,1,2],itemName:3,},markLine:{symbol:'none',silent:false,precision:100,label:{position:'insideEndTop',silent:true,},tooltip:{formatter:'{c}',},data:marklineData,},name:key,yAxisIndex:0,data:histogramData.map((item:any,index:number)=>{返回{值:[item[1],item[2],histogramDisplayLog?Math.log10(item[3]):item[3],item[0]],//itemStyle:{//颜色:colorList[index],//},};}),};series.push(tempseries);首先,看数据中的数据。这里的histogramLog是因为项目中有传输日志的需求。如果正常,用三元表达式histogramDisplayLog?数学。log10(item[3]):将item[3]替换为item[3]data:histogramData.map((item:any,index:number)=>{返回{值:[item[1],item[2],直方图显示日志?Math.log10(item[3]):item[3],item[0]],//itemStyle:{//color:colorList[index],//},};}),是一个对象数组,里面有一个字段value,value是一个长度为4的数组,再看data数组和renderItem的对应关系:renderItem:function(params:any,api:any){让yValue=api.value(2);让start=api.coord([api.value(0),yValue]);letsize=api.size([(api.value(1)asnumber)-(api.value(0)asnumber),yValue])asnumber[];conststyle=api.style();return{type:'rect',shape:{x:start[0],y:start[1],width:size[0],height:size[1],},样式,};},维度:['from','to','count'],编码:{x:[0,1],y:2,tooltip:[0,1,2],itemName:3,},可以看出按照官方例子的格式,我们直方图各列数据的value数组可以理解为[x轴的起始位置坐标,结束位置x轴的坐标,y轴的值,columnname]其中shape下的x,y,width,height分别对应每一列PS:(更详细的在文档中。。。)知道了所有的绘制方法,就可以开始重写缩放了整个系列首先获取缩放范围信息if(typeofparams.batch[0].startValue==='number'){conststartX=params.batch[0].startValue;constendX=params.batch[0].endValue;conststartY=params.batch[1].startValue;constendY=params.batch[1].endValue;改写的两个要点:1.数据x轴级别只取列的scalex范围。即只有x的起始位置坐标大于startX且x的结束位置坐标小于startX的列才能被选入我们的data数据:histogramData.map((item:any,index:number)=>{if((histogramDisplayLog?Math.log10(item[3]):item[3])>startY&&item[1]>startX&&item[2]endY?endY:api.value(2);x为letstart=api.coord([api.value(0),yValue])之前每一列x的起始位置坐标那么列的高度和宽度①宽度保持不变或者x的结束位置坐标减去x的起始位置坐标②高度应该是列的y值(yValue)减去缩放后的y起始位置(startY)让size=api.size([(api.value(1)asnumber)-(api.value(0)asnumber),bignumberFc.subtract(yValue,startY),])asnumber[];集成的renderItem应该是renderItem:function(params:any,api:any){letyValue=api.value(2)>endY?endY:api.value(2);让start=api.coord([api.value(0),yValue]);letsize=api.size([(api.value(1)asnumber)-(api.value(0)asnumber),bignumberFc.subtract(yValue,startY),])asnumber[];conststyle=api.style();返回{类型:'rect',形状:{x:开始[0],y:st艺术[1],宽度:尺寸[0],高度:尺寸[1],},风格,};},最后贴上整体datazoom响应部分的函数(如果是返回初始状态,需要额外判断处理,echarts缩放坑)myChart.on('datazoom',(params:any)=>{//回到初始状态时if(params.batch[0].start===0){myChart.setOption({series:[...series],},{replaceMerge:['series'],//替换合并系列,默认正常合并},);}//当有startValue值时(常规缩放)elseif(typeofparams.batch[0].startValue==='number'){conststartX=params.batch[0].startValue;constendX=params.batch[0].endValue;conststartY=params.batch[1].startValue;constendY=params.batch[1].endValue;constnewSeries:any[]=[];if(data&&Object.keys(data).length>0){for(letkeyindata){consthistogramData=data[键]['数据'];consttempseries={type:'custom',renderItem:function(params:any,api:any){letyValue=api.value(2)>endY?endY:api.value(2);让start=api.coord([api.value(0),yValue]);letsize=api.size([(api.value(1)asnumber)-(api.value(0)asnumber),bignumberFc.subtract(yValue,startY),])asnumber[];conststyle=api.style();return{type:'rect',shape:{x:start[0],y:start[1],width:size[0],height:size[1],},样式,};},标签:{show:false,position:'top',},dimensions:['from','to','count'],编码:{x:[0,1],y:2,工具提示:[0,1,2],itemName:3,},name:key,data:histogramData.map((item:any,index:number)=>{if((histogramDisplayLog?Math.log10(item[3]):item[3])>startY&&item[1]>startX&&item[2]