linkList.js 5.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167
  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. var zrUtil = require("zrender/lib/core/util");
  20. /*
  21. * Licensed to the Apache Software Foundation (ASF) under one
  22. * or more contributor license agreements. See the NOTICE file
  23. * distributed with this work for additional information
  24. * regarding copyright ownership. The ASF licenses this file
  25. * to you under the Apache License, Version 2.0 (the
  26. * "License"); you may not use this file except in compliance
  27. * with the License. You may obtain a copy of the License at
  28. *
  29. * http://www.apache.org/licenses/LICENSE-2.0
  30. *
  31. * Unless required by applicable law or agreed to in writing,
  32. * software distributed under the License is distributed on an
  33. * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
  34. * KIND, either express or implied. See the License for the
  35. * specific language governing permissions and limitations
  36. * under the License.
  37. */
  38. /**
  39. * Link lists and struct (graph or tree)
  40. */
  41. var each = zrUtil.each;
  42. var DATAS = '\0__link_datas';
  43. var MAIN_DATA = '\0__link_mainData'; // Caution:
  44. // In most case, either list or its shallow clones (see list.cloneShallow)
  45. // is active in echarts process. So considering heap memory consumption,
  46. // we do not clone tree or graph, but share them among list and its shallow clones.
  47. // But in some rare case, we have to keep old list (like do animation in chart). So
  48. // please take care that both the old list and the new list share the same tree/graph.
  49. /**
  50. * @param {Object} opt
  51. * @param {module:echarts/data/List} opt.mainData
  52. * @param {Object} [opt.struct] For example, instance of Graph or Tree.
  53. * @param {string} [opt.structAttr] designation: list[structAttr] = struct;
  54. * @param {Object} [opt.datas] {dataType: data},
  55. * like: {node: nodeList, edge: edgeList}.
  56. * Should contain mainData.
  57. * @param {Object} [opt.datasAttr] {dataType: attr},
  58. * designation: struct[datasAttr[dataType]] = list;
  59. */
  60. function linkList(opt) {
  61. var mainData = opt.mainData;
  62. var datas = opt.datas;
  63. if (!datas) {
  64. datas = {
  65. main: mainData
  66. };
  67. opt.datasAttr = {
  68. main: 'data'
  69. };
  70. }
  71. opt.datas = opt.mainData = null;
  72. linkAll(mainData, datas, opt); // Porxy data original methods.
  73. each(datas, function (data) {
  74. each(mainData.TRANSFERABLE_METHODS, function (methodName) {
  75. data.wrapMethod(methodName, zrUtil.curry(transferInjection, opt));
  76. });
  77. }); // Beyond transfer, additional features should be added to `cloneShallow`.
  78. mainData.wrapMethod('cloneShallow', zrUtil.curry(cloneShallowInjection, opt)); // Only mainData trigger change, because struct.update may trigger
  79. // another changable methods, which may bring about dead lock.
  80. each(mainData.CHANGABLE_METHODS, function (methodName) {
  81. mainData.wrapMethod(methodName, zrUtil.curry(changeInjection, opt));
  82. }); // Make sure datas contains mainData.
  83. zrUtil.assert(datas[mainData.dataType] === mainData);
  84. }
  85. function transferInjection(opt, res) {
  86. if (isMainData(this)) {
  87. // Transfer datas to new main data.
  88. var datas = zrUtil.extend({}, this[DATAS]);
  89. datas[this.dataType] = res;
  90. linkAll(res, datas, opt);
  91. } else {
  92. // Modify the reference in main data to point newData.
  93. linkSingle(res, this.dataType, this[MAIN_DATA], opt);
  94. }
  95. return res;
  96. }
  97. function changeInjection(opt, res) {
  98. opt.struct && opt.struct.update(this);
  99. return res;
  100. }
  101. function cloneShallowInjection(opt, res) {
  102. // cloneShallow, which brings about some fragilities, may be inappropriate
  103. // to be exposed as an API. So for implementation simplicity we can make
  104. // the restriction that cloneShallow of not-mainData should not be invoked
  105. // outside, but only be invoked here.
  106. each(res[DATAS], function (data, dataType) {
  107. data !== res && linkSingle(data.cloneShallow(), dataType, res, opt);
  108. });
  109. return res;
  110. }
  111. /**
  112. * Supplement method to List.
  113. *
  114. * @public
  115. * @param {string} [dataType] If not specified, return mainData.
  116. * @return {module:echarts/data/List}
  117. */
  118. function getLinkedData(dataType) {
  119. var mainData = this[MAIN_DATA];
  120. return dataType == null || mainData == null ? mainData : mainData[DATAS][dataType];
  121. }
  122. function isMainData(data) {
  123. return data[MAIN_DATA] === data;
  124. }
  125. function linkAll(mainData, datas, opt) {
  126. mainData[DATAS] = {};
  127. each(datas, function (data, dataType) {
  128. linkSingle(data, dataType, mainData, opt);
  129. });
  130. }
  131. function linkSingle(data, dataType, mainData, opt) {
  132. mainData[DATAS][dataType] = data;
  133. data[MAIN_DATA] = mainData;
  134. data.dataType = dataType;
  135. if (opt.struct) {
  136. data[opt.structAttr] = opt.struct;
  137. opt.struct[opt.datasAttr[dataType]] = data;
  138. } // Supplement method.
  139. data.getLinkedData = getLinkedData;
  140. }
  141. var _default = linkList;
  142. module.exports = _default;