MarkAreaView.js 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367
  1. /*
  2. * Licensed to the Apache Software Foundation (ASF) under one
  3. * or more contributor license agreements. See the NOTICE file
  4. * distributed with this work for additional information
  5. * regarding copyright ownership. The ASF licenses this file
  6. * to you under the Apache License, Version 2.0 (the
  7. * "License"); you may not use this file except in compliance
  8. * with the License. You may obtain a copy of the License at
  9. *
  10. * http://www.apache.org/licenses/LICENSE-2.0
  11. *
  12. * Unless required by applicable law or agreed to in writing,
  13. * software distributed under the License is distributed on an
  14. * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
  15. * KIND, either express or implied. See the License for the
  16. * specific language governing permissions and limitations
  17. * under the License.
  18. */
  19. /**
  20. * AUTO-GENERATED FILE. DO NOT MODIFY.
  21. */
  22. /*
  23. * Licensed to the Apache Software Foundation (ASF) under one
  24. * or more contributor license agreements. See the NOTICE file
  25. * distributed with this work for additional information
  26. * regarding copyright ownership. The ASF licenses this file
  27. * to you under the Apache License, Version 2.0 (the
  28. * "License"); you may not use this file except in compliance
  29. * with the License. You may obtain a copy of the License at
  30. *
  31. * http://www.apache.org/licenses/LICENSE-2.0
  32. *
  33. * Unless required by applicable law or agreed to in writing,
  34. * software distributed under the License is distributed on an
  35. * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
  36. * KIND, either express or implied. See the License for the
  37. * specific language governing permissions and limitations
  38. * under the License.
  39. */
  40. import { __extends } from "tslib"; // TODO Optimize on polar
  41. import * as colorUtil from 'zrender/lib/tool/color';
  42. import SeriesData from '../../data/SeriesData';
  43. import * as numberUtil from '../../util/number';
  44. import * as graphic from '../../util/graphic';
  45. import { enableHoverEmphasis, setStatesStylesFromModel } from '../../util/states';
  46. import * as markerHelper from './markerHelper';
  47. import MarkerView from './MarkerView';
  48. import { retrieve, mergeAll, map, curry, filter, extend } from 'zrender/lib/core/util';
  49. import { isCoordinateSystemType } from '../../coord/CoordinateSystem';
  50. import MarkerModel from './MarkerModel';
  51. import { makeInner } from '../../util/model';
  52. import { getVisualFromData } from '../../visual/helper';
  53. import { setLabelStyle, getLabelStatesModels } from '../../label/labelStyle';
  54. import { getECData } from '../../util/innerStore';
  55. import { parseDataValue } from '../../data/helper/dataValueHelper';
  56. var inner = makeInner();
  57. var markAreaTransform = function (seriesModel, coordSys, maModel, item) {
  58. var lt = markerHelper.dataTransform(seriesModel, item[0]);
  59. var rb = markerHelper.dataTransform(seriesModel, item[1]); // FIXME make sure lt is less than rb
  60. var ltCoord = lt.coord;
  61. var rbCoord = rb.coord;
  62. ltCoord[0] = retrieve(ltCoord[0], -Infinity);
  63. ltCoord[1] = retrieve(ltCoord[1], -Infinity);
  64. rbCoord[0] = retrieve(rbCoord[0], Infinity);
  65. rbCoord[1] = retrieve(rbCoord[1], Infinity); // Merge option into one
  66. var result = mergeAll([{}, lt, rb]);
  67. result.coord = [lt.coord, rb.coord];
  68. result.x0 = lt.x;
  69. result.y0 = lt.y;
  70. result.x1 = rb.x;
  71. result.y1 = rb.y;
  72. return result;
  73. };
  74. function isInifinity(val) {
  75. return !isNaN(val) && !isFinite(val);
  76. } // If a markArea has one dim
  77. function ifMarkAreaHasOnlyDim(dimIndex, fromCoord, toCoord, coordSys) {
  78. var otherDimIndex = 1 - dimIndex;
  79. return isInifinity(fromCoord[otherDimIndex]) && isInifinity(toCoord[otherDimIndex]);
  80. }
  81. function markAreaFilter(coordSys, item) {
  82. var fromCoord = item.coord[0];
  83. var toCoord = item.coord[1];
  84. if (isCoordinateSystemType(coordSys, 'cartesian2d')) {
  85. // In case
  86. // {
  87. // markArea: {
  88. // data: [{ yAxis: 2 }]
  89. // }
  90. // }
  91. if (fromCoord && toCoord && (ifMarkAreaHasOnlyDim(1, fromCoord, toCoord, coordSys) || ifMarkAreaHasOnlyDim(0, fromCoord, toCoord, coordSys))) {
  92. return true;
  93. }
  94. }
  95. return markerHelper.dataFilter(coordSys, {
  96. coord: fromCoord,
  97. x: item.x0,
  98. y: item.y0
  99. }) || markerHelper.dataFilter(coordSys, {
  100. coord: toCoord,
  101. x: item.x1,
  102. y: item.y1
  103. });
  104. } // dims can be ['x0', 'y0'], ['x1', 'y1'], ['x0', 'y1'], ['x1', 'y0']
  105. function getSingleMarkerEndPoint(data, idx, dims, seriesModel, api) {
  106. var coordSys = seriesModel.coordinateSystem;
  107. var itemModel = data.getItemModel(idx);
  108. var point;
  109. var xPx = numberUtil.parsePercent(itemModel.get(dims[0]), api.getWidth());
  110. var yPx = numberUtil.parsePercent(itemModel.get(dims[1]), api.getHeight());
  111. if (!isNaN(xPx) && !isNaN(yPx)) {
  112. point = [xPx, yPx];
  113. } else {
  114. // Chart like bar may have there own marker positioning logic
  115. if (seriesModel.getMarkerPosition) {
  116. // Use the getMarkerPoisition
  117. point = seriesModel.getMarkerPosition(data.getValues(dims, idx));
  118. } else {
  119. var x = data.get(dims[0], idx);
  120. var y = data.get(dims[1], idx);
  121. var pt = [x, y];
  122. coordSys.clampData && coordSys.clampData(pt, pt);
  123. point = coordSys.dataToPoint(pt, true);
  124. }
  125. if (isCoordinateSystemType(coordSys, 'cartesian2d')) {
  126. // TODO: TYPE ts@4.1 may still infer it as Axis instead of Axis2D. Not sure if it's a bug
  127. var xAxis = coordSys.getAxis('x');
  128. var yAxis = coordSys.getAxis('y');
  129. var x = data.get(dims[0], idx);
  130. var y = data.get(dims[1], idx);
  131. if (isInifinity(x)) {
  132. point[0] = xAxis.toGlobalCoord(xAxis.getExtent()[dims[0] === 'x0' ? 0 : 1]);
  133. } else if (isInifinity(y)) {
  134. point[1] = yAxis.toGlobalCoord(yAxis.getExtent()[dims[1] === 'y0' ? 0 : 1]);
  135. }
  136. } // Use x, y if has any
  137. if (!isNaN(xPx)) {
  138. point[0] = xPx;
  139. }
  140. if (!isNaN(yPx)) {
  141. point[1] = yPx;
  142. }
  143. }
  144. return point;
  145. }
  146. var dimPermutations = [['x0', 'y0'], ['x1', 'y0'], ['x1', 'y1'], ['x0', 'y1']];
  147. var MarkAreaView =
  148. /** @class */
  149. function (_super) {
  150. __extends(MarkAreaView, _super);
  151. function MarkAreaView() {
  152. var _this = _super !== null && _super.apply(this, arguments) || this;
  153. _this.type = MarkAreaView.type;
  154. return _this;
  155. }
  156. MarkAreaView.prototype.updateTransform = function (markAreaModel, ecModel, api) {
  157. ecModel.eachSeries(function (seriesModel) {
  158. var maModel = MarkerModel.getMarkerModelFromSeries(seriesModel, 'markArea');
  159. if (maModel) {
  160. var areaData_1 = maModel.getData();
  161. areaData_1.each(function (idx) {
  162. var points = map(dimPermutations, function (dim) {
  163. return getSingleMarkerEndPoint(areaData_1, idx, dim, seriesModel, api);
  164. }); // Layout
  165. areaData_1.setItemLayout(idx, points);
  166. var el = areaData_1.getItemGraphicEl(idx);
  167. el.setShape('points', points);
  168. });
  169. }
  170. }, this);
  171. };
  172. MarkAreaView.prototype.renderSeries = function (seriesModel, maModel, ecModel, api) {
  173. var coordSys = seriesModel.coordinateSystem;
  174. var seriesId = seriesModel.id;
  175. var seriesData = seriesModel.getData();
  176. var areaGroupMap = this.markerGroupMap;
  177. var polygonGroup = areaGroupMap.get(seriesId) || areaGroupMap.set(seriesId, {
  178. group: new graphic.Group()
  179. });
  180. this.group.add(polygonGroup.group);
  181. this.markKeep(polygonGroup);
  182. var areaData = createList(coordSys, seriesModel, maModel); // Line data for tooltip and formatter
  183. maModel.setData(areaData); // Update visual and layout of line
  184. areaData.each(function (idx) {
  185. // Layout
  186. var points = map(dimPermutations, function (dim) {
  187. return getSingleMarkerEndPoint(areaData, idx, dim, seriesModel, api);
  188. });
  189. var xAxisScale = coordSys.getAxis('x').scale;
  190. var yAxisScale = coordSys.getAxis('y').scale;
  191. var xAxisExtent = xAxisScale.getExtent();
  192. var yAxisExtent = yAxisScale.getExtent();
  193. var xPointExtent = [xAxisScale.parse(areaData.get('x0', idx)), xAxisScale.parse(areaData.get('x1', idx))];
  194. var yPointExtent = [yAxisScale.parse(areaData.get('y0', idx)), yAxisScale.parse(areaData.get('y1', idx))];
  195. numberUtil.asc(xPointExtent);
  196. numberUtil.asc(yPointExtent);
  197. var overlapped = !(xAxisExtent[0] > xPointExtent[1] || xAxisExtent[1] < xPointExtent[0] || yAxisExtent[0] > yPointExtent[1] || yAxisExtent[1] < yPointExtent[0]); // If none of the area is inside coordSys, allClipped is set to be true
  198. // in layout so that label will not be displayed. See #12591
  199. var allClipped = !overlapped;
  200. areaData.setItemLayout(idx, {
  201. points: points,
  202. allClipped: allClipped
  203. });
  204. var style = areaData.getItemModel(idx).getModel('itemStyle').getItemStyle();
  205. var color = getVisualFromData(seriesData, 'color');
  206. if (!style.fill) {
  207. style.fill = color;
  208. if (typeof style.fill === 'string') {
  209. style.fill = colorUtil.modifyAlpha(style.fill, 0.4);
  210. }
  211. }
  212. if (!style.stroke) {
  213. style.stroke = color;
  214. } // Visual
  215. areaData.setItemVisual(idx, 'style', style);
  216. });
  217. areaData.diff(inner(polygonGroup).data).add(function (idx) {
  218. var layout = areaData.getItemLayout(idx);
  219. if (!layout.allClipped) {
  220. var polygon = new graphic.Polygon({
  221. shape: {
  222. points: layout.points
  223. }
  224. });
  225. areaData.setItemGraphicEl(idx, polygon);
  226. polygonGroup.group.add(polygon);
  227. }
  228. }).update(function (newIdx, oldIdx) {
  229. var polygon = inner(polygonGroup).data.getItemGraphicEl(oldIdx);
  230. var layout = areaData.getItemLayout(newIdx);
  231. if (!layout.allClipped) {
  232. if (polygon) {
  233. graphic.updateProps(polygon, {
  234. shape: {
  235. points: layout.points
  236. }
  237. }, maModel, newIdx);
  238. } else {
  239. polygon = new graphic.Polygon({
  240. shape: {
  241. points: layout.points
  242. }
  243. });
  244. }
  245. areaData.setItemGraphicEl(newIdx, polygon);
  246. polygonGroup.group.add(polygon);
  247. } else if (polygon) {
  248. polygonGroup.group.remove(polygon);
  249. }
  250. }).remove(function (idx) {
  251. var polygon = inner(polygonGroup).data.getItemGraphicEl(idx);
  252. polygonGroup.group.remove(polygon);
  253. }).execute();
  254. areaData.eachItemGraphicEl(function (polygon, idx) {
  255. var itemModel = areaData.getItemModel(idx);
  256. var style = areaData.getItemVisual(idx, 'style');
  257. polygon.useStyle(areaData.getItemVisual(idx, 'style'));
  258. setLabelStyle(polygon, getLabelStatesModels(itemModel), {
  259. labelFetcher: maModel,
  260. labelDataIndex: idx,
  261. defaultText: areaData.getName(idx) || '',
  262. inheritColor: typeof style.fill === 'string' ? colorUtil.modifyAlpha(style.fill, 1) : '#000'
  263. });
  264. setStatesStylesFromModel(polygon, itemModel);
  265. enableHoverEmphasis(polygon);
  266. getECData(polygon).dataModel = maModel;
  267. });
  268. inner(polygonGroup).data = areaData;
  269. polygonGroup.group.silent = maModel.get('silent') || seriesModel.get('silent');
  270. };
  271. MarkAreaView.type = 'markArea';
  272. return MarkAreaView;
  273. }(MarkerView);
  274. function createList(coordSys, seriesModel, maModel) {
  275. var areaData;
  276. var dataDims;
  277. var dims = ['x0', 'y0', 'x1', 'y1'];
  278. if (coordSys) {
  279. var coordDimsInfos_1 = map(coordSys && coordSys.dimensions, function (coordDim) {
  280. var data = seriesModel.getData();
  281. var info = data.getDimensionInfo(data.mapDimension(coordDim)) || {}; // In map series data don't have lng and lat dimension. Fallback to same with coordSys
  282. return extend(extend({}, info), {
  283. name: coordDim,
  284. // DON'T use ordinalMeta to parse and collect ordinal.
  285. ordinalMeta: null
  286. });
  287. });
  288. dataDims = map(dims, function (dim, idx) {
  289. return {
  290. name: dim,
  291. type: coordDimsInfos_1[idx % 2].type
  292. };
  293. });
  294. areaData = new SeriesData(dataDims, maModel);
  295. } else {
  296. dataDims = [{
  297. name: 'value',
  298. type: 'float'
  299. }];
  300. areaData = new SeriesData(dataDims, maModel);
  301. }
  302. var optData = map(maModel.get('data'), curry(markAreaTransform, seriesModel, coordSys, maModel));
  303. if (coordSys) {
  304. optData = filter(optData, curry(markAreaFilter, coordSys));
  305. }
  306. var dimValueGetter = coordSys ? function (item, dimName, dataIndex, dimIndex) {
  307. // TODO should convert to ParsedValue?
  308. var rawVal = item.coord[Math.floor(dimIndex / 2)][dimIndex % 2];
  309. return parseDataValue(rawVal, dataDims[dimIndex]);
  310. } : function (item, dimName, dataIndex, dimIndex) {
  311. return parseDataValue(item.value, dataDims[dimIndex]);
  312. };
  313. areaData.initData(optData, null, dimValueGetter);
  314. areaData.hasItemOption = true;
  315. return areaData;
  316. }
  317. export default MarkAreaView;