本文講的是如何定制Echarts的tree圖。主要包括下載、全局變量名修改、左鍵菜單添加、右鍵菜單添加、內容縮放、文本過濾高亮等。
一 說明
Echarts中提供了tree圖,但實際項目中,該tree圖並不一定能完全滿足項目需求。例如:需要在鼠標右鍵到節點上添加一個下拉菜單,並且能進行操作。因此,就需要要對該圖表進行定制。
二 代碼下載
實際項目開發中,可能只需要一個tree圖,就沒必要下載全量的Echarts代碼包了,因為完整的Echarts代碼包非常大,10多萬行代碼呢,為提高項目性能,建議只下載用到的圖標和組件。
而Echarts也非常人性化的提供了在線定制構建能力,可以實現按需下載:http://www.echartsjs.com/builder.html
三 全局變量名修改
實際項目中可能已經引入了Echarts,但該Echarts版本存在問題:當前使用的Echarts版本太老了,該版本中還沒有我們將要用到的Tree圖,而要將整個版本升級到最新版本,或者有Tree圖的版本,可能會導致之前圖表出現接口不一致導致的BUG,尤其是已經上線或者即將上線的項目,這種升級風險很大。
一個比較好的解決方案就是:引入兩套Echarts代碼。
但必須解決兩套Echarts圖表代碼沖突的問題,而這個沖突主要是Echarts對外提供的全局變量windows.echarts。只需要將一個Echarts代碼包中的全局變量修改掉,然后使用修改后的全局變量生成圖表即可。
在下載的Echarts包中(uglify混淆后的包),搜echarts,將下邊位置的echarts修改為dlgTreeEcharts:
沒有做uglify混淆壓縮的Echarts包中,修改echarts的位置如下:
定制完后,生成圖表代碼如下:
var myChart = dlgTreeEcharts.init(document.getElementById('main'));
四 hover菜單
Echarts提供了比較多的事件接口,其中click、mouseover等是最基礎的事件。
詳細參考:http://www.echartsjs.com/api.html#events
1 myChart.on('mouseover', function (params) { 2 console.log(params); 3 $('.left-hover-menu').css({ 4 'display': 'block', 5 'left': params.event.offsetX + 15, 6 'top' : params.event.offsetY + 15 7 }); 8 }); 9 myChart.on('mouseout', function (params) { 10 console.log('out'); 11 $('.left-hover-menu').css({ 12 'display': 'none', 13 'left': '-9999px', 14 'top' : '-9999px' 15 }); 16 });
上邊代碼中,mouseover用於顯示絕對定位的菜單,並設置其位置;mouseout用於隱藏菜單。
五 右鍵菜單
Echarts還提供了一個contextmenu事件,用於鼠標右擊時觸發。
詳細見:
http://echarts.baidu.com/tutorial.html#ECharts%20%E4%B8%AD%E7%9A%84%E4%BA%8B%E4%BB%B6%E5%92%8C%E8%A1%8C%E4%B8%BA
http://www.echartsjs.com/api.html#events
注意:在添加右鍵菜單時,首先要給整個樹圖外層容器DOM綁定一個右鍵事件,返回false,避免瀏覽器默認事件觸發,出現默認菜單。
1 $('.tree-container').bind("contextmenu", function () { return false; });//防止默認菜單彈出 2 myChart.on('contextmenu', function (params) { 3 $('.right-click-menu').css({ 4 'display': 'block', 5 'left': params.event.offsetX + 15, 6 'top' : params.event.offsetY + 15 7 }); 8 }); 9 $('.tree-container').click(function () { 10 $('.right-click-menu').css({ 11 'display': 'none', 12 'left': '-9999px', 13 'top' : '-9999px' 14 }); 15 })
六 縮放功能
Echarts中專門提供了用於縮放的組件datazoom,但tree圖並沒用用到該組件。這點令不少人大感惱火,研究嘗試很久,使用datazoom配置到tree圖后就是不生效甚至報錯。最后,無意中看到tree的series中有個配置項是roam,用於控制縮放和平移,不按套路出牌啊,藏得真深。
很簡單,設置roam為true,縮放和平移功能都有了。
roam官方介紹:http://www.echartsjs.com/option.html#series-tree.roam
七 文字過濾高亮
實際項目中,有這樣的需求:由於樹的節點特別多,需要提供搜索功能,例如:輸入‘報表’,需要查找所有節點name中包含‘報表’兩個字的,並將其高亮顯示。
這個可以通過Echarts提供的富文本標簽和Tree組件的series.label.formatter來實現。
http://www.echartsjs.com/tutorial.html#%E5%AF%8C%E6%96%87%E6%9C%AC%E6%A0%87%E7%AD%BE
http://www.echartsjs.com/option.html#series-tree.label.formatter
http://www.echartsjs.com/option.html#series-tree.label.rich
詳細代碼如下:
1 label : { 2 normal: { 3 position: 'left', 4 verticalAlign: 'middle', 5 align: 'right', 6 fontSize: 15, 7 formatter: function (param) { 8 if (param.name.match('Tra')) { 9 return '{a|' + param.name + '}' 10 } else { 11 return param.name; 12 } 13 }, 14 rich: { 15 a: { 16 color: 'red', 17 lineHeight: 10 18 } 19 } 20 } 21 }
代碼說明:上邊代碼中,formatter通過設置為函數,對name進行判斷,看是否有匹配的關鍵字‘Tra’(用戶搜索的關鍵字,Tra只是舉個例子),如果匹配上了,就返回一個匹配富文本的格式;下邊的rich就是富文本樣式設置。
實際效果如下:
八 各級文字位置設置
Echarts對各級文字位置有個自適應設置:該節點展開時,文字自動放到左側;節點收起來時,文字自動放到右側了。
實際項目中,為了達到視覺上整齊效果,需要無論節點是否展開都將文字設置為一個位置。
實現方法:
data接口中,有個label屬性,label屬性中的position用於設置當前節點的文字位置,可以通過這個接口將該級文本設置為固定位置。
注意:不要設置label.align屬性,否則可能位置有偏差。
設置方法如下:
效果如下:
八 完整示例代碼
說明:由於data數據很多,沒有在下邊顯示,可以參考Echarts官網示例數據:http://www.echartsjs.com/examples/editor.html?c=tree-basic
1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4 <meta charset="UTF-8"> 5 <title>Title</title> 6 <script src="echarts.min.js"></script> 7 <script src="jquery.js"></script> 8 <style> 9 .tree-container { 10 border: 1px solid grey; 11 position: relative; 12 } 13 14 .left-hover-menu { 15 position: absolute; 16 border: 1px solid grey; 17 left: -99999px; 18 top: -999999px; 19 } 20 21 .right-click-menu { 22 position: absolute; 23 border: 1px solid blue; 24 left: -99999px; 25 top: -999999px; 26 } 27 </style> 28 </head> 29 <body> 30 <div class="tree-container"> 31 <div id="main" style="width: 1200px;height:1000px;"></div> 32 </div> 33 34 <div class="left-hover-menu"> 35 <div>中文名: 報表</div> 36 <div>英文名:data charts</div> 37 <div>產品域定義:用於記錄各種數據.</div> 38 </div> 39 40 <div class="right-click-menu"> 41 <div>新增業務對象</div> 42 <div>編輯</div> 43 <div>刪除</div> 44 </div> 45 46 <script type="text/javascript"> 47 48 var myChart = dlgTreeEcharts.init(document.getElementById('main')); 49 50 myChart.setOption(option = { 51 tooltip: { 52 show: false 53 }, 54 series: [ 55 { 56 type: 'tree', 57 data: [data], 58 top: '1%', 59 left: '7%', 60 bottom: '1%', 61 right: '20%', 62 symbolSize: 7, 63 label: { 64 normal: { 65 position: 'left', 66 verticalAlign: 'middle', 67 align: 'right', 68 fontSize: 15, 69 formatter: function (param) { 70 if (param.name.match('Tra')) { 71 return '{a|' + param.name + '}' 72 } else { 73 return param.name; 74 } 75 }, 76 rich: { 77 a: { 78 color: 'red', 79 lineHeight: 10 80 } 81 } 82 }, 83 emphasis: { 84 fontSize: 25 85 } 86 }, 87 leaves: { 88 label: { 89 normal: { 90 position: 'right', 91 verticalAlign: 'middle', 92 align: 'left' 93 }, 94 95 } 96 }, 97 expandAndCollapse: true, 98 roam: true, // 縮放 99 animationDuration: 550, 100 animationDurationUpdate: 750 101 } 102 ] 103 }); 104 105 myChart.on('mouseover', function (params) { 106 console.log(params); 107 $('.left-hover-menu').css({ 108 'display': 'block', 109 'left': params.event.offsetX + 15, 110 'top': params.event.offsetY + 15 111 }); 112 }); 113 myChart.on('mouseout', function (params) { 114 console.log('out'); 115 $('.left-hover-menu').css({ 116 'display': 'none', 117 'left': '-9999px', 118 'top': '-9999px' 119 }); 120 }); 121 122 $('.tree-container').bind("contextmenu", function () { 123 return false; 124 });//防止默認菜單彈出 125 myChart.on('contextmenu', function (params) { 126 $('.right-click-menu').css({ 127 'display': 'block', 128 'left': params.event.offsetX + 15, 129 'top': params.event.offsetY + 15 130 }); 131 }); 132 $('.tree-container').click(function () { 133 $('.right-click-menu').css({ 134 'display': 'none', 135 'left': '-9999px', 136 'top': '-9999px' 137 }); 138 }); 139 </script> 140 </body> 141 </html>
參考資料&內容來源:
Echarts官網:http://www.echartsjs.com/option.html#title