看這標題,可能會有一些人不太明白,那麼直接上圖,就是柱圖展現形式以下圖(兼容IE8)html
要想實現這樣展現效果。咱們想用echarts直接實現不行的,即便是紋理填充也不可行的,可是咱們能夠藉助echarts柱圖展現來進行二次操做來現實。那麼如何實現呢?性能優化
下面咱們開始講解:app
1.思路:echarts
從設計圖中,咱們要知道藍色部分隨着值的變化而變化,而灰色部分高度是不變的。性能
咱們能夠經過把柱圖的透明度設爲0,而後獲取每根柱圖的高度,每根柱圖的位置,而後建立一個元素,把獲取到每根柱圖的高度和位置賦給這個元素,經過設置元素背景圖片填充樣式來實現優化
2.根據上面的思路,那就開始着手了,直接上代碼url
先把樣式設置好:spa
<style> *{margin: 0;padding: 0;} .bar-p,.bar-g{ position: absolute; z-index: 9999; width:22px ;/*柱圖的寬度*/ } .bar-p>span,.bar-g>span{ position: absolute; left: 50%; width: 80px; text-align: center; margin-left: -40px; margin-top: -18px; } .bar-g>span{ color: #808182; } .bar-p>span{ color: #0b7cd1; } .bar-p{background: url("../img/bar.png") repeat-y 50% 100%;} /*灰色的在這裏高度是固定的,無論多大值*/ .bar-g{background: url("../img/bar1.png") no-repeat 50% 100%;height: 5px!important;} </style>
html和js代碼:設計
<div id="main" style="width: 60%; height: 500px;margin:10px auto;"></div> <script> /* * @echarts3版本:v3.2.2 * */ var option=null,xAxisData=[],numData=[],numData1=[]; for(var i=1;i<9;i++){ xAxisData.push('幣種'+i); if(i>=6) numData[i-1]=-10; else numData[i-1]=i*20; numData1[i-1]=Math.abs(numData[i-1]); } option = { color: ['#3398DB'], tooltip : { trigger: 'item', formatter:'{b}:{c}', axisPointer : { // 座標軸指示器,座標軸觸發有效 type : 'shadow' // 默認爲直線,可選爲:'line' | 'shadow' } }, grid: { left: '3%', right: '4%', bottom: '3%', containLabel: true }, xAxis : [ { type : 'category', data : xAxisData, axisLine:{ lineStyle:{ color:'#ccc' } }, axisTick:false // 座標軸刻度不顯示的話直接這樣 } ], yAxis : [ { type : 'value', axisLabel:{ show:false }, splitLine:{ lineStyle:{ color:'#ddd' } }, axisLine:{ show:false }, axisTick:false // 座標軸刻度不顯示的話直接這樣 } ], series : [ { type:'bar', barWidth: 22, data:numData1, itemStyle:{ normal:{ opacity:0 } } } ] }; var myChart = echarts.init(document.getElementById('main')); // 使用剛指定的配置項和數據顯示圖表。 myChart.setOption(option); /* * getModel() echarts模型的獲取 * getSeriesByIndex(i) 這個i表示series的下標,如今的series只有一個 因此直接是0 * */ var model=myChart.getModel(), layer=model.getSeriesByIndex(0), layouts=layer._data._itemLayouts;// 獲取每根柱圖的位置和高度和寬度 var div=document.getElementById('main').getElementsByTagName('div')[0]; // 得到div var elem,height=document.getElementById('main').offsetHeight,bottom=height-layouts[0]['y']; for(var i= 0,len=layouts.length;i<len;i++){ elem=document.createElement('div'); if(numData[i]<0) elem.className='bar-g'; else elem.className='bar-p'; elem.style.bottom=bottom+'px'; elem.style.left=layouts[i]['x']+'px'; elem.style.height=Math.abs(layouts[i]['height'])+'px'; elem.innerHTML='<span>'+numData[i]+'</span>'; div.appendChild(elem); } </script>
運行結果以下:code
其實上面的js代碼是實現了這個效果,可是有一個問題,就是for循環輸出div的,每次循環都是從document中建立一個div,其實這樣是不可取的,並且每次都要設置樣式!
因此咱們應該經過從innerHTML來輸出會更好,由於咱們的代碼就是要簡潔、性能優化得最好、條理清晰,更少的代碼作更多的事情等!
因此咱們要改爲下面這樣的:
<script> /* * @echarts3版本:v3.2.2 * */ var option=null,xAxisData=[],numData=[],numData1=[]; for(var i=1;i<9;i++){ xAxisData.push('幣種'+i); if(i>=6) numData[i-1]=-10; else numData[i-1]=i*20; numData1[i-1]=Math.abs(numData[i-1]); } option = { color: ['#3398DB'], tooltip : { trigger: 'item', formatter:'{b}:{c}', axisPointer : { // 座標軸指示器,座標軸觸發有效 type : 'shadow' // 默認爲直線,可選爲:'line' | 'shadow' } }, grid: { left: '3%', right: '4%', bottom: '3%', containLabel: true }, xAxis : [ { type : 'category', data : xAxisData, axisLine:{ lineStyle:{ color:'#ccc' } }, axisTick:false // 座標軸刻度不顯示的話直接這樣 } ], yAxis : [ { type : 'value', axisLabel:{ show:false }, splitLine:{ lineStyle:{ color:'#ddd' } }, axisLine:{ show:false }, axisTick:false // 座標軸刻度不顯示的話直接這樣 } ], series : [ { type:'bar', barWidth: 22, data:numData1, itemStyle:{ normal:{ opacity:0 } } } ] }; var myChart = echarts.init(document.getElementById('main')); // 使用剛指定的配置項和數據顯示圖表。 myChart.setOption(option); /* * getModel() echarts模型的獲取 * getSeriesByIndex(i) 這個i表示series的下標,如今的series只有一個 因此直接是0 * */ var model=myChart.getModel(), layer=model.getSeriesByIndex(0), layouts=layer._data._itemLayouts;// 獲取每根柱圖的位置和高度和寬度 var div=document.getElementById('main').getElementsByTagName('div')[0]; // 得到div var elem="",height=document.getElementById('main').offsetHeight,bottom=height-layouts[0]['y']; for(var i= 0,len=layouts.length;i<len;i++){ elem+='<div class="'+(numData[i]<0?'bar-g':'bar-p')+ '"style="bottom:'+bottom+'px;left:'+layouts[i]['x']+'px;height:'+Math.abs(layouts[i]['height'])+'px;">'+ '<span>'+numData[i]+'</span>'+ '</div>'; } div.appendChild(document.createElement('div')); div.getElementsByTagName('div')[0].innerHTML=elem; </script>
運行結果以下: