ant-design/components/tree/Tree.tsx
陈帅 785c132262
meger feature to master (#16421)
* use ul in list

* update snapshot

* update comment

* feat: TreeSelect support `showSearch` in multiple mode (#15933)

* update rc-tree-select

* typo

* update desc & snapshot

* update desc & snapshot

* check default showSearch

* feat: table customizing variable (#15971)

* feat: added table selected row color variable

* fix: @table-selected-row-color default is inherit

* feat: Upload support customize previewFile (#15984)

* support preview file

* use promise

* dealy load

* use canvas of render

* use domHook of test

* update demo

* add snapshot

* update types

* update testcase

* feat: form customizing variables (#15954)

* fix: added styling form input background-color

* feat: added '@form-warning-input-bg' variable

* feat: added '@form-error-input-bg' variable

* use li wrap with comment

* feat: Support append theme less file with less-variable (#16118)

* add override

* add override support

* update doc

* feat: dropdown support set right icon

* docs: update doc of dropdown component

* style: format dropdown-button.md

* test: update updateSnapshot

* style: format dropdown-button.md

* test: update updateSnapshot

* test: update updateSnapshot

* style: change style of dropdown-button demo

* fix: fix document table order

* feat: Support SkeletonAvatarProps.size accept number (#16078) (#16128)

* chore:update style of demo

* feat: Notification functions accept top, bottom and getContainer as arguments

* drawer: add afterVisibleChange

* rm onVisibleChange

* update

* feat: 🇭🇷 hr_HR locale (#16258)

* Added Croatian locale

* fixed lint error

*  Add test cases for hr_HR

* 📝 update i18n documentation

* feat:  add `htmlFor` in Form.Item (#16278)

* add htmlFor in Form.Item

* update doc

* feat: Button support `link` type (#16289)

close #15892

* feat: Add Timeline.Item.position (#16148) (#16193)

* fix: Timeline.pendingDot interface documentation there is a small problem (#16177)

* feat: Add Timeline.Item.position (#16148)

* doc: add version infomation for Timeline.Item.position

* refactor: Update Tree & TreeSelect deps (#16330)

* use CSSMotion

* update snapshot

* feat: Collapse support `expandIconPosition` (#16365)

* update doc

* support expandIconPosition

* update snapshot

* feat: Breadcrumb  support DropDown (#16315)

* breadcrumbs support drop down menu

* update doc

* add require less

* fix test

* fix md doc

* less code

* fix  style warning

* update snap

* add children render test

* feat: TreeNode support checkable

* feat: add optional to support top and left slick dots (#16186) (#16225)

* add optional to support top and left slick dots

* update carousel snapshot

* Update doc, add placement demo

* update carousel placement demo snapshots

* rename dots placement to position

* update vertical as deprecated

* rename dotsPosition to dotPosition

* refine code

* add warning testcase for vertical

* remove unused warning

* update expression

* Additional test case for dotPosition

* refactor: Upgrade `rc-tree-select` to support pure React motion (#16402)

* upgrade `rc-tree-select`

* update snapshot

* 3.17.0 changelog

* fix warning

* fix review warning
2019-05-06 12:04:39 +08:00

236 lines
7.2 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import * as React from 'react';
import RcTree, { TreeNode } from 'rc-tree';
import DirectoryTree from './DirectoryTree';
import classNames from 'classnames';
import Icon from '../icon';
import { ConfigConsumer, ConfigConsumerProps } from '../config-provider';
import { collapseMotion } from '../_util/motion';
export interface AntdTreeNodeAttribute {
eventKey: string;
prefixCls: string;
className: string;
expanded: boolean;
selected: boolean;
checked: boolean;
halfChecked: boolean;
children: React.ReactNode;
title: React.ReactNode;
pos: string;
dragOver: boolean;
dragOverGapTop: boolean;
dragOverGapBottom: boolean;
isLeaf: boolean;
selectable: boolean;
disabled: boolean;
disableCheckbox: boolean;
}
export interface AntTreeNodeProps {
className?: string;
checkable?: boolean;
disabled?: boolean;
disableCheckbox?: boolean;
title?: string | React.ReactNode;
key?: string;
eventKey?: string;
isLeaf?: boolean;
checked?: boolean;
expanded?: boolean;
loading?: boolean;
selected?: boolean;
selectable?: boolean;
icon?: ((treeNode: AntdTreeNodeAttribute) => React.ReactNode) | React.ReactNode;
children?: React.ReactNode;
[customProp: string]: any;
}
export interface AntTreeNode extends React.Component<AntTreeNodeProps, {}> {}
export interface AntTreeNodeBaseEvent {
node: AntTreeNode;
nativeEvent: MouseEvent;
}
export interface AntTreeNodeCheckedEvent extends AntTreeNodeBaseEvent {
event: 'check';
checked?: boolean;
checkedNodes?: AntTreeNode[];
}
export interface AntTreeNodeSelectedEvent extends AntTreeNodeBaseEvent {
event: 'select';
selected?: boolean;
selectedNodes?: AntTreeNode[];
}
export interface AntTreeNodeExpandedEvent extends AntTreeNodeBaseEvent {
expanded?: boolean;
}
export interface AntTreeNodeMouseEvent {
node: AntTreeNode;
event: React.MouseEventHandler<any>;
}
export interface AntTreeNodeDropEvent {
node: AntTreeNode;
dragNode: AntTreeNode;
dragNodesKeys: string[];
dropPosition: number;
dropToGap?: boolean;
event: React.MouseEventHandler<any>;
}
export interface TreeProps {
showLine?: boolean;
className?: string;
/** 是否支持多选 */
multiple?: boolean;
/** 是否自动展开父节点 */
autoExpandParent?: boolean;
/** checkable状态下节点选择完全受控父子节点选中状态不再关联*/
checkStrictly?: boolean;
/** 是否支持选中 */
checkable?: boolean;
/** 是否禁用树 */
disabled?: boolean;
/** 默认展开所有树节点 */
defaultExpandAll?: boolean;
/** 默认展开对应树节点 */
defaultExpandParent?: boolean;
/** 默认展开指定的树节点 */
defaultExpandedKeys?: string[];
/** (受控)展开指定的树节点 */
expandedKeys?: string[];
/** (受控)选中复选框的树节点 */
checkedKeys?: string[] | { checked: string[]; halfChecked: string[] };
/** 默认选中复选框的树节点 */
defaultCheckedKeys?: string[];
/** (受控)设置选中的树节点 */
selectedKeys?: string[];
/** 默认选中的树节点 */
defaultSelectedKeys?: string[];
selectable?: boolean;
/** 展开/收起节点时触发 */
onExpand?: (expandedKeys: string[], info: AntTreeNodeExpandedEvent) => void | PromiseLike<any>;
/** 点击复选框触发 */
onCheck?: (
checkedKeys: string[] | { checked: string[]; halfChecked: string[] },
e: AntTreeNodeCheckedEvent,
) => void;
/** 点击树节点触发 */
onSelect?: (selectedKeys: string[], e: AntTreeNodeSelectedEvent) => void;
/** 单击树节点触发 */
onClick?: (e: React.MouseEvent<HTMLElement>, node: AntTreeNode) => void;
/** 双击树节点触发 */
onDoubleClick?: (e: React.MouseEvent<HTMLElement>, node: AntTreeNode) => void;
/** filter some AntTreeNodes as you need. it should return true */
filterAntTreeNode?: (node: AntTreeNode) => boolean;
/** 异步加载数据 */
loadData?: (node: AntTreeNode) => PromiseLike<any>;
loadedKeys?: string[];
onLoad?: (loadedKeys: string[], info: { event: 'load'; node: AntTreeNode }) => void;
/** 响应右键点击 */
onRightClick?: (options: AntTreeNodeMouseEvent) => void;
/** 设置节点可拖拽IE>8*/
draggable?: boolean;
onDragStart?: (options: AntTreeNodeMouseEvent) => void;
onDragEnter?: (options: AntTreeNodeMouseEvent) => void;
onDragOver?: (options: AntTreeNodeMouseEvent) => void;
onDragLeave?: (options: AntTreeNodeMouseEvent) => void;
onDragEnd?: (options: AntTreeNodeMouseEvent) => void;
onDrop?: (options: AntTreeNodeDropEvent) => void;
style?: React.CSSProperties;
showIcon?: boolean;
icon?: (nodeProps: AntdTreeNodeAttribute) => React.ReactNode | React.ReactNode;
switcherIcon?: React.ReactElement<any>;
prefixCls?: string;
filterTreeNode?: (node: AntTreeNode) => boolean;
children?: React.ReactNode | React.ReactNode[];
blockNode?: boolean;
}
export default class Tree extends React.Component<TreeProps, any> {
static TreeNode: React.ComponentClass<AntTreeNodeProps> = TreeNode;
static DirectoryTree = DirectoryTree;
static defaultProps = {
checkable: false,
showIcon: false,
motion: {
...collapseMotion,
motionAppear: false,
},
blockNode: false,
};
tree: any;
renderSwitcherIcon = (
prefixCls: string,
switcherIcon: React.ReactElement<any> | undefined,
{ isLeaf, expanded, loading }: AntTreeNodeProps,
) => {
const { showLine } = this.props;
if (loading) {
return <Icon type="loading" className={`${prefixCls}-switcher-loading-icon`} />;
}
if (showLine) {
if (isLeaf) {
return <Icon type="file" className={`${prefixCls}-switcher-line-icon`} />;
}
return (
<Icon
type={expanded ? 'minus-square' : 'plus-square'}
className={`${prefixCls}-switcher-line-icon`}
theme="outlined"
/>
);
} else {
const switcherCls = `${prefixCls}-switcher-icon`;
if (isLeaf) {
return null;
} else if (switcherIcon) {
const switcherOriginCls = switcherIcon.props.className || '';
return React.cloneElement(switcherIcon, {
className: classNames(switcherOriginCls, switcherCls),
});
} else {
return <Icon type="caret-down" className={switcherCls} theme="filled" />;
}
}
};
setTreeRef = (node: any) => {
this.tree = node;
};
renderTree = ({ getPrefixCls }: ConfigConsumerProps) => {
const props = this.props;
const { prefixCls: customizePrefixCls, className, showIcon, switcherIcon, blockNode } = props;
const checkable = props.checkable;
const prefixCls = getPrefixCls('tree', customizePrefixCls);
return (
<RcTree
ref={this.setTreeRef}
{...props}
prefixCls={prefixCls}
className={classNames(className, {
[`${prefixCls}-icon-hide`]: !showIcon,
[`${prefixCls}-block-node`]: blockNode,
})}
checkable={checkable ? <span className={`${prefixCls}-checkbox-inner`} /> : checkable}
switcherIcon={(nodeProps: AntTreeNodeProps) =>
this.renderSwitcherIcon(prefixCls, switcherIcon, nodeProps)
}
>
{this.props.children}
</RcTree>
);
};
render() {
return <ConfigConsumer>{this.renderTree}</ConfigConsumer>;
}
}