Tree.js 8.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235
  1. import _objectWithoutProperties from 'babel-runtime/helpers/objectWithoutProperties';
  2. import _extends from 'babel-runtime/helpers/extends';
  3. import _defineProperty from 'babel-runtime/helpers/defineProperty';
  4. import warning from 'warning';
  5. import { Tree as VcTree, TreeNode } from '../vc-tree';
  6. import animation from '../_util/openAnimation';
  7. import PropTypes from '../_util/vue-types';
  8. import { initDefaultProps, getOptionProps, filterEmpty, getComponentFromProp, getListeners } from '../_util/props-util';
  9. import { cloneElement } from '../_util/vnode';
  10. import { ConfigConsumerProps } from '../config-provider/configConsumerProps';
  11. import Icon from '../icon';
  12. function TreeProps() {
  13. return {
  14. showLine: PropTypes.bool,
  15. /** 是否支持多选 */
  16. multiple: PropTypes.bool,
  17. /** 是否自动展开父节点 */
  18. autoExpandParent: PropTypes.bool,
  19. /** checkable状态下节点选择完全受控(父子节点选中状态不再关联)*/
  20. checkStrictly: PropTypes.bool,
  21. /** 是否支持选中 */
  22. checkable: PropTypes.bool,
  23. /** 是否禁用树 */
  24. disabled: PropTypes.bool,
  25. /** 默认展开所有树节点 */
  26. defaultExpandAll: PropTypes.bool,
  27. /** 默认展开对应树节点 */
  28. defaultExpandParent: PropTypes.bool,
  29. /** 默认展开指定的树节点 */
  30. defaultExpandedKeys: PropTypes.array,
  31. /** (受控)展开指定的树节点 */
  32. expandedKeys: PropTypes.array,
  33. /** (受控)选中复选框的树节点 */
  34. checkedKeys: PropTypes.oneOfType([PropTypes.array, PropTypes.shape({
  35. checked: PropTypes.array,
  36. halfChecked: PropTypes.array
  37. }).loose]),
  38. /** 默认选中复选框的树节点 */
  39. defaultCheckedKeys: PropTypes.array,
  40. /** (受控)设置选中的树节点 */
  41. selectedKeys: PropTypes.array,
  42. /** 默认选中的树节点 */
  43. defaultSelectedKeys: PropTypes.array,
  44. selectable: PropTypes.bool,
  45. /** 展开/收起节点时触发 */
  46. // onExpand: (expandedKeys: string[], info: AntTreeNodeExpandedEvent) => void | PromiseLike<any>,
  47. /** 点击复选框触发 */
  48. // onCheck: (checkedKeys: string[] | { checked: string[]; halfChecked: string[] }, e: AntTreeNodeCheckedEvent) => void,
  49. /** 点击树节点触发 */
  50. // onSelect: (selectedKeys: string[], e: AntTreeNodeSelectedEvent) => void,
  51. /** 单击树节点触发 */
  52. // onClick: (e: React.MouseEvent<HTMLElement>, node: AntTreeNode) => void,
  53. /** 双击树节点触发 */
  54. // onDoubleClick: (e: React.MouseEvent<HTMLElement>, node: AntTreeNode) => void,
  55. /** filter some AntTreeNodes as you need. it should return true */
  56. filterAntTreeNode: PropTypes.func,
  57. /** 异步加载数据 */
  58. loadData: PropTypes.func,
  59. loadedKeys: PropTypes.array,
  60. // onLoaded: (loadedKeys: string[], info: { event: 'load', node: AntTreeNode; }) => void,
  61. /** 响应右键点击 */
  62. // onRightClick: (options: AntTreeNodeMouseEvent) => void,
  63. /** 设置节点可拖拽(IE>8)*/
  64. draggable: PropTypes.bool,
  65. // /** 开始拖拽时调用 */
  66. // onDragStart: (options: AntTreeNodeMouseEvent) => void,
  67. // /** dragenter 触发时调用 */
  68. // onDragEnter: (options: AntTreeNodeMouseEvent) => void,
  69. // /** dragover 触发时调用 */
  70. // onDragOver: (options: AntTreeNodeMouseEvent) => void,
  71. // /** dragleave 触发时调用 */
  72. // onDragLeave: (options: AntTreeNodeMouseEvent) => void,
  73. // /** drop 触发时调用 */
  74. // onDrop: (options: AntTreeNodeMouseEvent) => void,
  75. showIcon: PropTypes.bool,
  76. icon: PropTypes.func,
  77. switcherIcon: PropTypes.any,
  78. prefixCls: PropTypes.string,
  79. filterTreeNode: PropTypes.func,
  80. openAnimation: PropTypes.any,
  81. treeNodes: PropTypes.array,
  82. treeData: PropTypes.array,
  83. /**
  84. * @default{title,key,children}
  85. * 替换treeNode中 title,key,children字段为treeData中对应的字段
  86. */
  87. replaceFields: PropTypes.object,
  88. blockNode: PropTypes.bool
  89. };
  90. }
  91. export { TreeProps };
  92. export default {
  93. name: 'ATree',
  94. model: {
  95. prop: 'checkedKeys',
  96. event: 'check'
  97. },
  98. props: initDefaultProps(TreeProps(), {
  99. checkable: false,
  100. showIcon: false,
  101. openAnimation: {
  102. on: animation,
  103. props: { appear: null }
  104. },
  105. blockNode: false
  106. }),
  107. inject: {
  108. configProvider: { 'default': function _default() {
  109. return ConfigConsumerProps;
  110. } }
  111. },
  112. created: function created() {
  113. warning(!('treeNodes' in getOptionProps(this)), '`treeNodes` is deprecated. please use treeData instead.');
  114. },
  115. TreeNode: TreeNode,
  116. methods: {
  117. renderSwitcherIcon: function renderSwitcherIcon(prefixCls, switcherIcon, _ref) {
  118. var isLeaf = _ref.isLeaf,
  119. expanded = _ref.expanded,
  120. loading = _ref.loading;
  121. var h = this.$createElement;
  122. var showLine = this.$props.showLine;
  123. if (loading) {
  124. return h(Icon, {
  125. attrs: { type: 'loading' },
  126. 'class': prefixCls + '-switcher-loading-icon' });
  127. }
  128. if (isLeaf) {
  129. return showLine ? h(Icon, {
  130. attrs: { type: 'file' },
  131. 'class': prefixCls + '-switcher-line-icon' }) : null;
  132. }
  133. var switcherCls = prefixCls + '-switcher-icon';
  134. if (switcherIcon) {
  135. return cloneElement(switcherIcon, {
  136. 'class': _defineProperty({}, switcherCls, true)
  137. });
  138. }
  139. return showLine ? h(Icon, {
  140. attrs: {
  141. type: expanded ? 'minus-square' : 'plus-square',
  142. theme: 'outlined'
  143. },
  144. 'class': prefixCls + '-switcher-line-icon' }) : h(Icon, {
  145. attrs: { type: 'caret-down', theme: 'filled' },
  146. 'class': switcherCls });
  147. },
  148. updateTreeData: function updateTreeData(treeData) {
  149. var _this = this;
  150. var $slots = this.$slots,
  151. $scopedSlots = this.$scopedSlots;
  152. var defaultFields = { children: 'children', title: 'title', key: 'key' };
  153. var replaceFields = _extends({}, defaultFields, this.$props.replaceFields);
  154. return treeData.map(function (item) {
  155. var key = item[replaceFields.key];
  156. var children = item[replaceFields.children];
  157. var _item$on = item.on,
  158. on = _item$on === undefined ? {} : _item$on,
  159. _item$slots = item.slots,
  160. slots = _item$slots === undefined ? {} : _item$slots,
  161. _item$scopedSlots = item.scopedSlots,
  162. scopedSlots = _item$scopedSlots === undefined ? {} : _item$scopedSlots,
  163. cls = item['class'],
  164. style = item.style,
  165. restProps = _objectWithoutProperties(item, ['on', 'slots', 'scopedSlots', 'class', 'style']);
  166. var treeNodeProps = _extends({}, restProps, {
  167. icon: $scopedSlots[scopedSlots.icon] || $slots[slots.icon] || restProps.icon,
  168. switcherIcon: $scopedSlots[scopedSlots.switcherIcon] || $slots[slots.switcherIcon] || restProps.switcherIcon,
  169. title: $scopedSlots[scopedSlots.title] || $slots[slots.title] || $scopedSlots.title || restProps[replaceFields.title],
  170. dataRef: item,
  171. on: on,
  172. key: key,
  173. 'class': cls,
  174. style: style
  175. });
  176. if (children) {
  177. return _extends({}, treeNodeProps, { children: _this.updateTreeData(children) });
  178. }
  179. return treeNodeProps;
  180. });
  181. }
  182. },
  183. render: function render() {
  184. var _this2 = this,
  185. _class2;
  186. var h = arguments[0];
  187. var props = getOptionProps(this);
  188. var $slots = this.$slots,
  189. $scopedSlots = this.$scopedSlots;
  190. var customizePrefixCls = props.prefixCls,
  191. showIcon = props.showIcon,
  192. treeNodes = props.treeNodes,
  193. blockNode = props.blockNode;
  194. var getPrefixCls = this.configProvider.getPrefixCls;
  195. var prefixCls = getPrefixCls('tree', customizePrefixCls);
  196. var _switcherIcon = getComponentFromProp(this, 'switcherIcon');
  197. var checkable = props.checkable;
  198. var treeData = props.treeData || treeNodes;
  199. if (treeData) {
  200. treeData = this.updateTreeData(treeData);
  201. }
  202. var vcTreeProps = {
  203. props: _extends({}, props, {
  204. prefixCls: prefixCls,
  205. checkable: checkable ? h('span', { 'class': prefixCls + '-checkbox-inner' }) : checkable,
  206. children: filterEmpty($scopedSlots['default'] ? $scopedSlots['default']() : $slots['default']),
  207. __propsSymbol__: Symbol(),
  208. switcherIcon: function switcherIcon(nodeProps) {
  209. return _this2.renderSwitcherIcon(prefixCls, _switcherIcon, nodeProps);
  210. }
  211. }),
  212. on: getListeners(this),
  213. ref: 'tree',
  214. 'class': (_class2 = {}, _defineProperty(_class2, prefixCls + '-icon-hide', !showIcon), _defineProperty(_class2, prefixCls + '-block-node', blockNode), _class2)
  215. };
  216. if (treeData) {
  217. vcTreeProps.props.treeData = treeData;
  218. }
  219. return h(VcTree, vcTreeProps);
  220. }
  221. };