list-bar-chart2.vue 8.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326
  1. <template>
  2. <div>
  3. <div class="chart" v-for="index of list.length" :key="index" :id="id + index"></div>
  4. </div>
  5. </template>
  6. <script>
  7. import util from "@/helper/util.js";
  8. import partten from "@/helper/partten.js";
  9. import * as echarts from "echarts";
  10. export default {
  11. name: "percent-pie",
  12. componentName: "percent-pie",
  13. props: {
  14. width: {
  15. type: String,
  16. default: "100%",
  17. },
  18. height: {
  19. type: String,
  20. default: "18.519vh",
  21. },
  22. // 传入数据
  23. list: {
  24. type: Array,
  25. default: () => [
  26. {
  27. name: "当日预测电量",
  28. value: 103.62,
  29. total: 200,
  30. },
  31. {
  32. name: "实际发电量",
  33. value: 98.62,
  34. total: 100,
  35. },
  36. {
  37. name: "当月预测电量",
  38. value: 113.27,
  39. total: 100,
  40. },
  41. {
  42. name: "实际发电量",
  43. value: 136.72,
  44. total: 100,
  45. },
  46. ],
  47. },
  48. total: {
  49. type: Number,
  50. default: 150,
  51. },
  52. colors: {
  53. type: Array,
  54. default: () => ["green", "purple"],
  55. },
  56. },
  57. data() {
  58. return {
  59. id: "",
  60. chart: null,
  61. firstAnimation: true,
  62. };
  63. },
  64. computed: {
  65. datas() {
  66. return this.list.map((t) => {
  67. return t.value;
  68. });
  69. },
  70. },
  71. methods: {
  72. resize() {},
  73. initChart(value, index) {
  74. var currColor = this.colors[index % 2];
  75. var $dom = document.getElementById(this.id + (index + 1));
  76. $dom.style.width = this.width;
  77. $dom.style.height = `calc(${this.height} / ${this.list.length} - 4px)`;
  78. let chart = echarts.init($dom);
  79. let option = {
  80. xAxis: {
  81. max: value.total,
  82. splitLine: {
  83. show: false,
  84. },
  85. axisLine: {
  86. show: false,
  87. },
  88. axisLabel: {
  89. show: false,
  90. },
  91. axisTick: {
  92. show: false,
  93. },
  94. },
  95. grid: {
  96. left: 16,
  97. top: 16, // 设置条形图的边s距
  98. right: 110,
  99. bottom: 0,
  100. containLabel: true,
  101. },
  102. yAxis: [
  103. {
  104. type: "category",
  105. inverse: true,
  106. data: [value],
  107. axisLine: {
  108. show: false,
  109. },
  110. axisTick: {
  111. show: false,
  112. },
  113. axisLabel: {
  114. show: false,
  115. },
  116. },
  117. ],
  118. series: [
  119. // 内
  120. {
  121. type: "bar",
  122. barWidth: 6,
  123. animation: this.firstAnimation,
  124. // legendHoverLink: false,
  125. // silent: true,
  126. itemStyle: {
  127. normal: {
  128. color: function(params) {
  129. return {
  130. type: "linear",
  131. x: 0,
  132. y: 0,
  133. x2: 1,
  134. y2: 0,
  135. colorStops: [
  136. {
  137. offset: 0,
  138. color: partten.getColor(currColor), // 0% 处的颜色
  139. },
  140. {
  141. offset: 1,
  142. color: partten.getColor(currColor), // 100% 处的颜色
  143. },
  144. ],
  145. };
  146. },
  147. shadowBlur: 10,
  148. shadowColor: "rgba(255, 255, 255, 0.30)",
  149. },
  150. },
  151. label: {
  152. normal: {
  153. show: true,
  154. position: [0, util.vh("-20")],
  155. formatter: function(param) {
  156. return param.data.name;
  157. },
  158. textStyle: {
  159. color: "#7a8385",
  160. fontSize: 12,
  161. },
  162. },
  163. },
  164. data: [value],
  165. z: 1,
  166. animationEasing: "elasticOut",
  167. },
  168. // 三角
  169. {
  170. type: "pictorialBar",
  171. symbolPosition: "end",
  172. animation: this.firstAnimation,
  173. data: [value],
  174. symbol: "triangle",
  175. symbolOffset: [0, -10],
  176. symbolSize: [5, 5],
  177. symbolRotate: 180,
  178. itemStyle: {
  179. normal: {
  180. borderWidth: 0,
  181. color: function(params) {
  182. return partten.getColor(currColor);
  183. },
  184. // shadowBlur: 2,
  185. // shadowColor: "rgba(255, 255, 255, 0.80)",
  186. },
  187. },
  188. },
  189. // 分隔
  190. {
  191. type: "pictorialBar",
  192. itemStyle: {
  193. normal: {
  194. color: "#20314f",
  195. },
  196. },
  197. animation: this.firstAnimation,
  198. symbolRepeat: "fixed",
  199. symbolMargin: 4,
  200. symbol: "rect",
  201. symbolClip: true,
  202. symbolSize: [1, 8],
  203. symbolPosition: "start",
  204. symbolOffset: [8, -1],
  205. symbolBoundingData: value.total,
  206. symbolRotate: -15,
  207. data: [value],
  208. z: 2,
  209. animationEasing: "elasticOut",
  210. },
  211. // 外边框
  212. {
  213. type: "pictorialBar",
  214. animation: this.firstAnimation,
  215. symbol: "rect",
  216. symbolBoundingData: value.total,
  217. itemStyle: {
  218. normal: {
  219. color: "none",
  220. },
  221. },
  222. label: {
  223. normal: {
  224. formatter: (params) => {
  225. return "{gm|}{f| " + params.data + "}";
  226. },
  227. rich: {
  228. f: {
  229. color: "#ffffff",
  230. fontSize: 14,
  231. lineHeight: 20,
  232. fontFamily: "Bicubik",
  233. },
  234. gm: {
  235. backgroundColor: partten.getColor(currColor),
  236. width: 4,
  237. height: 4,
  238. lineHeight: 20,
  239. verticalAlign: "middle",
  240. borderRadius: [50, 50, 50, 50],
  241. },
  242. },
  243. position: "right",
  244. distance: 8, // 向右偏移位置
  245. show: true,
  246. },
  247. },
  248. data: [value.value],
  249. },
  250. // 外框
  251. {
  252. type: "bar",
  253. animation: this.firstAnimation,
  254. name: "外框",
  255. barGap: "-120%", // 设置外框粗细
  256. data: [
  257. {
  258. value: value.total,
  259. itemStyle: {
  260. normal: {
  261. color: "transparent",
  262. borderColor: partten.getColor(currColor), // [, "#333"],
  263. borderWidth: 1, // 边框宽度
  264. // barBorderRadius: 0, //圆角半径
  265. opacity: 0.5,
  266. label: {
  267. // 标签显示位置
  268. show: false,
  269. position: "top", // insideTop 或者横向的 insideLeft
  270. },
  271. },
  272. },
  273. },
  274. ],
  275. barWidth: 9,
  276. },
  277. ],
  278. };
  279. chart.clear();
  280. chart.setOption(option);
  281. this.resize = function() {
  282. chart.resize();
  283. };
  284. window.removeEventListener("resize", this.resize);
  285. window.addEventListener("resize", this.resize);
  286. },
  287. },
  288. created() {
  289. this.id = "pie-chart-" + util.newGUID();
  290. },
  291. mounted() {
  292. this.$nextTick(() => {
  293. this.$el.style.width = this.width;
  294. this.$el.style.height = this.height;
  295. this.list.forEach((value, index) => {
  296. this.initChart(value, index);
  297. });
  298. this.firstAnimation = false;
  299. });
  300. },
  301. updated() {
  302. this.$nextTick(() => {
  303. this.list.forEach((value, index) => {
  304. this.initChart(value, index);
  305. });
  306. });
  307. },
  308. unmounted() {
  309. window.removeEventListener("resize", this.resize);
  310. },
  311. };
  312. </script>
  313. <style lang="less">
  314. .chart {
  315. width: 100%;
  316. height: 100%;
  317. display: inline-block;
  318. }
  319. </style>