add: 增加节点、在线编辑
This commit is contained in:
parent
3541510576
commit
d7cb124f94
|
@ -9,3 +9,15 @@
|
||||||
color: #f50;
|
color: #f50;
|
||||||
transition: all .3s ease;
|
transition: all .3s ease;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.title-middle {
|
||||||
|
display: inline-block;
|
||||||
|
vertical-align: middle;
|
||||||
|
}
|
||||||
|
.edit-icon {
|
||||||
|
float:right;
|
||||||
|
font-size: 14px;
|
||||||
|
}
|
||||||
|
.title-con {
|
||||||
|
min-width: 150px;
|
||||||
|
}
|
|
@ -10,7 +10,7 @@ import React, {
|
||||||
Component
|
Component
|
||||||
} from 'react';
|
} from 'react';
|
||||||
import Tree from '../../src';
|
import Tree from '../../src';
|
||||||
|
import Icon from 'bee-icon';
|
||||||
const TreeNode = Tree.TreeNode;
|
const TreeNode = Tree.TreeNode;
|
||||||
|
|
||||||
const defaultProps = {
|
const defaultProps = {
|
||||||
|
@ -36,7 +36,7 @@ class Demo1 extends Component {
|
||||||
render() {
|
render() {
|
||||||
return (
|
return (
|
||||||
|
|
||||||
<Tree className="myCls" checkable openIcon="uf-minus" closeIcon="uf-plus"
|
<Tree className="myCls" checkable openIcon={<Icon type="uf-minus" />} closeIcon={<Icon type="uf-plus" />}
|
||||||
defaultExpandedKeys={this.state.defaultExpandedKeys}
|
defaultExpandedKeys={this.state.defaultExpandedKeys}
|
||||||
defaultSelectedKeys={this.state.defaultSelectedKeys}
|
defaultSelectedKeys={this.state.defaultSelectedKeys}
|
||||||
defaultCheckedKeys={this.state.defaultCheckedKeys}
|
defaultCheckedKeys={this.state.defaultCheckedKeys}
|
||||||
|
|
|
@ -14,18 +14,20 @@ import Button from 'bee-button';
|
||||||
|
|
||||||
const TreeNode = Tree.TreeNode;
|
const TreeNode = Tree.TreeNode;
|
||||||
|
|
||||||
|
|
||||||
class Demo7 extends Component {
|
class Demo7 extends Component {
|
||||||
constructor(props) {
|
constructor(props) {
|
||||||
super(props);
|
super(props);
|
||||||
debugger;
|
|
||||||
console.log('keys--' + this.props.keys);
|
|
||||||
this.state = {
|
this.state = {
|
||||||
treeData: [],
|
treeData: [],
|
||||||
defaultExpandedKeys: ['0-0', '0-1', '0-2']
|
defaultExpandedKeys: ['0-0', '0-1', '0-2'],
|
||||||
|
parentNode: {}
|
||||||
};
|
};
|
||||||
this.onSelect = this.onSelect.bind(this);
|
this.onSelect = this.onSelect.bind(this);
|
||||||
this.addNode = this.addNode.bind(this);
|
this.addNode = this.addNode.bind(this);
|
||||||
this.clickFun = this.clickFun.bind(this);
|
this.clickFun = this.clickFun.bind(this);
|
||||||
|
this.getNodeByKey = this.getNodeByKey.bind(this);
|
||||||
|
this.parentNode = null
|
||||||
}
|
}
|
||||||
componentDidMount() {
|
componentDidMount() {
|
||||||
setTimeout(() => {
|
setTimeout(() => {
|
||||||
|
@ -65,22 +67,52 @@ class Demo7 extends Component {
|
||||||
*/
|
*/
|
||||||
addNode(prKey, nodeItem) {
|
addNode(prKey, nodeItem) {
|
||||||
const data = this.state.treeData;
|
const data = this.state.treeData;
|
||||||
data.forEach((item) => {
|
let parNode;
|
||||||
if (prKey === item.key) {
|
if (prKey) {
|
||||||
if (!item.children) {
|
// 如果prKey存在则搜索父节点进行添加
|
||||||
item.children = [];
|
parNode = this.getNodeByKey(data, prKey);
|
||||||
|
//如果父节点存在的话,添加到父节点上
|
||||||
|
if (parNode) {
|
||||||
|
if (!parNode.children) {
|
||||||
|
parNode.children = [];
|
||||||
}
|
}
|
||||||
// 如果key不存在就动态生成一个
|
// 如果key不存在就动态生成一个
|
||||||
if (!nodeItem.key) {
|
if (!nodeItem.key) {
|
||||||
nodeItem.key = prKey + item.children.length + 1;
|
nodeItem.key = prKey + parNode.children.length + 1;
|
||||||
}
|
}
|
||||||
item.children.push(nodeItem);
|
parNode.children.push(nodeItem);
|
||||||
}
|
}
|
||||||
});
|
} else {
|
||||||
|
// 没有穿prKey添加到根下成为一级节点
|
||||||
|
if (!nodeItem.key) {
|
||||||
|
nodeItem.key = "0-" + data.length + 1;
|
||||||
|
}
|
||||||
|
data.push(nodeItem);
|
||||||
|
}
|
||||||
|
|
||||||
this.setState({
|
this.setState({
|
||||||
data
|
data
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
getNodeByKey(data, key) {
|
||||||
|
if (!this.parentNode) {
|
||||||
|
data.find(item => {
|
||||||
|
if (item.key === key) {
|
||||||
|
console.log('item.name---' + item.name)
|
||||||
|
this.parentNode = item;
|
||||||
|
return (true);
|
||||||
|
} else if (item.children) {
|
||||||
|
return this.getNodeByKey(item.children, key);
|
||||||
|
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
return this.parentNode;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
onSelect(info) {
|
onSelect(info) {
|
||||||
console.log('selected', info);
|
console.log('selected', info);
|
||||||
}
|
}
|
||||||
|
@ -89,9 +121,9 @@ class Demo7 extends Component {
|
||||||
*/
|
*/
|
||||||
clickFun() {
|
clickFun() {
|
||||||
let prKey, nodeItem;
|
let prKey, nodeItem;
|
||||||
prKey = '0-2';
|
prKey = '0-1';
|
||||||
nodeItem = {
|
nodeItem = {
|
||||||
name: 'leaf 0-2-0'
|
name: 'leaf 0-0-4'
|
||||||
}
|
}
|
||||||
this.addNode(prKey, nodeItem);
|
this.addNode(prKey, nodeItem);
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,127 @@
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @title Tree 节点可编辑
|
||||||
|
* @description 双击节点可编辑
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
import React, {
|
||||||
|
Component
|
||||||
|
} from 'react';
|
||||||
|
import Tree from '../../src';
|
||||||
|
import Button from 'bee-button';
|
||||||
|
import Icon from 'bee-icon';
|
||||||
|
|
||||||
|
const TreeNode = Tree.TreeNode;
|
||||||
|
|
||||||
|
let timer = 0;
|
||||||
|
let delay = 200;
|
||||||
|
let prevent = false;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
class Demo8 extends Component {
|
||||||
|
constructor(props) {
|
||||||
|
super(props);
|
||||||
|
|
||||||
|
this.state = {
|
||||||
|
treeData: [],
|
||||||
|
isHover: "",
|
||||||
|
editKey: ""
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
onMouseEnter = (e) => {
|
||||||
|
this.setState({
|
||||||
|
isHover: e.node.props.pos
|
||||||
|
})
|
||||||
|
}
|
||||||
|
onMouseLeave = (e, treenode) => {
|
||||||
|
this.setState({
|
||||||
|
isHover: "",
|
||||||
|
editKey: ""
|
||||||
|
})
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
editRender = (item) => {
|
||||||
|
this.setState({
|
||||||
|
editKey: item.key
|
||||||
|
});
|
||||||
|
}
|
||||||
|
nodechange = (item, value) => {
|
||||||
|
item.name = value;
|
||||||
|
}
|
||||||
|
renderTreeTitle = (item) => {
|
||||||
|
let titleIcon, titleInfo;
|
||||||
|
//编辑时input框
|
||||||
|
if (this.state.editKey == item.key) {
|
||||||
|
titleInfo = <input type="text" id="itemKey" defaultValue={item.name} onChange={(e) => this.nodechange(item,e.target.value)}/>
|
||||||
|
} else {
|
||||||
|
titleInfo = <span className="title-middle">{item.name}</span>
|
||||||
|
}
|
||||||
|
//编辑图标
|
||||||
|
if (this.state.isHover == item.key) {
|
||||||
|
titleIcon = <Icon className="title-middle edit-icon" type="uf-pencil" onClick={(e)=>this.editRender(item)}></Icon>;
|
||||||
|
}
|
||||||
|
return (<div className="title-con">
|
||||||
|
|
||||||
|
{titleInfo}
|
||||||
|
{titleIcon}
|
||||||
|
</div>);
|
||||||
|
}
|
||||||
|
|
||||||
|
componentDidMount = () => {
|
||||||
|
setTimeout(() => {
|
||||||
|
this.setState({
|
||||||
|
treeData: [{
|
||||||
|
name: 'pNode 01',
|
||||||
|
key: '0-0',
|
||||||
|
children: [{
|
||||||
|
name: 'leaf 0-0-0',
|
||||||
|
key: '0-0-0'
|
||||||
|
}, {
|
||||||
|
name: 'leaf 0-0-1',
|
||||||
|
key: '0-0-1'
|
||||||
|
}]
|
||||||
|
}, {
|
||||||
|
name: 'pNode 02',
|
||||||
|
key: '0-1',
|
||||||
|
children: [{
|
||||||
|
name: 'leaf 0-1-0',
|
||||||
|
key: '0-1-0'
|
||||||
|
}, {
|
||||||
|
name: 'leaf 0-1-1',
|
||||||
|
key: '0-1-1'
|
||||||
|
}]
|
||||||
|
}, {
|
||||||
|
name: 'pNode 03',
|
||||||
|
key: '0-2',
|
||||||
|
isLeaf: true
|
||||||
|
}, ],
|
||||||
|
});
|
||||||
|
}, 100);
|
||||||
|
}
|
||||||
|
render() {
|
||||||
|
const loop = data => data.map((item) => {
|
||||||
|
if (item.children) {
|
||||||
|
return <TreeNode title={this.renderTreeTitle(item)} key={item.key}>{loop(item.children)}</TreeNode>;
|
||||||
|
}
|
||||||
|
return <TreeNode title={this.renderTreeTitle(item)} key={item.key} isLeaf={item.isLeaf} disabled={item.key === '0-0-0'} />;
|
||||||
|
});
|
||||||
|
const treeNodes = loop(this.state.treeData);
|
||||||
|
return (
|
||||||
|
<Tree onMouseLeave={this.onMouseLeave} onMouseEnter={this.onMouseEnter}>
|
||||||
|
{treeNodes}
|
||||||
|
</Tree>
|
||||||
|
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
export default Demo8;
|
File diff suppressed because one or more lines are too long
119
package.json
119
package.json
|
@ -1,61 +1,62 @@
|
||||||
{
|
{
|
||||||
"name": "bee-tree",
|
"name": "bee-tree",
|
||||||
"version": "1.0.0",
|
"version": "1.0.0",
|
||||||
"description": "Tree ui component for react",
|
"description": "Tree ui component for react",
|
||||||
"keywords": [
|
"keywords": [
|
||||||
"react",
|
"react",
|
||||||
"react-component",
|
"react-component",
|
||||||
"bee-tree",
|
"bee-tree",
|
||||||
"iuap-design",
|
"iuap-design",
|
||||||
"tinper-bee",
|
"tinper-bee",
|
||||||
"Tree"
|
"Tree"
|
||||||
],
|
],
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">=4.0.0"
|
"node": ">=4.0.0"
|
||||||
},
|
},
|
||||||
"homepage": "https://github.com/tinper-bee/bee-tree.git",
|
"homepage": "https://github.com/tinper-bee/bee-tree.git",
|
||||||
"author": "Yonyou FED",
|
"author": "Yonyou FED",
|
||||||
"repository": "http://github.com/tinper-bee/bee-tree",
|
"repository": "http://github.com/tinper-bee/bee-tree",
|
||||||
"bugs": "https://github.com/tinper-bee/bee-tree.git/issues",
|
"bugs": "https://github.com/tinper-bee/bee-tree.git/issues",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"main": "./build/index.js",
|
"main": "./build/index.js",
|
||||||
"config": {
|
"config": {
|
||||||
"port": 3000
|
"port": 3000
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"dev": "bee-tools run start",
|
"dev": "bee-tools run start",
|
||||||
"build": "bee-tools run build",
|
"build": "bee-tools run build",
|
||||||
"lint": "bee-tools run lint",
|
"lint": "bee-tools run lint",
|
||||||
"test": "bee-tools run test",
|
"test": "bee-tools run test",
|
||||||
"chrome": "bee-tools run chrome",
|
"chrome": "bee-tools run chrome",
|
||||||
"coveralls": "bee-tools run coverage",
|
"coveralls": "bee-tools run coverage",
|
||||||
"browsers": "bee-tools run browsers",
|
"browsers": "bee-tools run browsers",
|
||||||
"pub": "bee-tools run pub"
|
"pub": "bee-tools run pub"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"bee-animate": "latest",
|
"babel-runtime": "^6.23.0",
|
||||||
"bee-checkbox": "latest",
|
"bee-animate": "latest",
|
||||||
"bee-form-control": "latest",
|
"bee-checkbox": "latest",
|
||||||
"classnames": "^2.2.5",
|
"bee-form-control": "latest",
|
||||||
"object-assign": "latest",
|
"bee-icon": "^1.0.0",
|
||||||
"babel-runtime": "^6.23.0",
|
"classnames": "^2.2.5",
|
||||||
"tinper-bee-core": "latest"
|
"object-assign": "latest",
|
||||||
},
|
"tinper-bee-core": "latest"
|
||||||
"peerDependencies": {
|
},
|
||||||
"react": "^15.3.0 || ^16.0",
|
"peerDependencies": {
|
||||||
"react-dom": "^15.3.0 || ^16.0",
|
"react": "^15.3.0 || ^16.0",
|
||||||
"prop-types": "15.6.0"
|
"react-dom": "^15.3.0 || ^16.0",
|
||||||
},
|
"prop-types": "15.6.0"
|
||||||
"devDependencies": {
|
},
|
||||||
"chai": "^3.5.0",
|
"devDependencies": {
|
||||||
"enzyme": "^2.4.1",
|
"chai": "^3.5.0",
|
||||||
"react": "15.3.2",
|
"enzyme": "^2.4.1",
|
||||||
"react-addons-test-utils": "15.3.2",
|
"react": "15.3.2",
|
||||||
"react-dom": "15.3.2",
|
"react-addons-test-utils": "15.3.2",
|
||||||
"console-polyfill": "~0.2.1",
|
"react-dom": "15.3.2",
|
||||||
"es5-shim": "~4.1.10",
|
"console-polyfill": "~0.2.1",
|
||||||
"bee-panel": "latest",
|
"es5-shim": "~4.1.10",
|
||||||
"bee-layout": "latest",
|
"bee-panel": "latest",
|
||||||
"bee-button": "latest"
|
"bee-layout": "latest",
|
||||||
}
|
"bee-button": "latest"
|
||||||
|
}
|
||||||
}
|
}
|
|
@ -268,7 +268,6 @@ class Tree extends React.Component {
|
||||||
}
|
}
|
||||||
|
|
||||||
onSelect(treeNode) {
|
onSelect(treeNode) {
|
||||||
debugger;
|
|
||||||
const props = this.props;
|
const props = this.props;
|
||||||
const selectedKeys = [...this.state.selectedKeys];
|
const selectedKeys = [...this.state.selectedKeys];
|
||||||
const eventKey = treeNode.props.eventKey;
|
const eventKey = treeNode.props.eventKey;
|
||||||
|
@ -438,7 +437,6 @@ class Tree extends React.Component {
|
||||||
}
|
}
|
||||||
|
|
||||||
getDragNodes(treeNode) {
|
getDragNodes(treeNode) {
|
||||||
debugger;
|
|
||||||
const dragNodesKeys = [];
|
const dragNodesKeys = [];
|
||||||
const tPArr = treeNode.props.pos.split('-');
|
const tPArr = treeNode.props.pos.split('-');
|
||||||
loopAllChildren(this.props.children, (item, index, pos, newKey) => {
|
loopAllChildren(this.props.children, (item, index, pos, newKey) => {
|
||||||
|
@ -596,7 +594,7 @@ class Tree extends React.Component {
|
||||||
}
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<ul {...domProps} unselectable ref="tree">
|
<ul {...domProps} unselectable="true" ref="tree">
|
||||||
{React.Children.map(props.children, this.renderTreeNode, this)}
|
{React.Children.map(props.children, this.renderTreeNode, this)}
|
||||||
</ul>
|
</ul>
|
||||||
);
|
);
|
||||||
|
|
|
@ -323,9 +323,14 @@
|
||||||
* 自定义switcher图标
|
* 自定义switcher图标
|
||||||
*/
|
*/
|
||||||
|
|
||||||
.u-tree li span.u-tree-switcher.uf {
|
.u-tree li span.u-tree-switcher.icon-none {
|
||||||
font-size: 14px;
|
|
||||||
&:after{
|
&:after{
|
||||||
content:"";
|
content:"";
|
||||||
}
|
}
|
||||||
|
.uf {
|
||||||
|
padding: 0px;
|
||||||
|
font-size: 14px;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -165,18 +165,20 @@ class TreeNode extends React.Component {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (expandedState === 'open' && props.openIcon) {
|
if (expandedState === 'open' && props.openIcon) {
|
||||||
stateIcon = `uf ${props.openIcon}`;
|
stateIcon = props.openIcon;
|
||||||
|
switcherCls['icon-none'] = true;
|
||||||
}
|
}
|
||||||
if (expandedState === 'close' && props.closeIcon) {
|
if (expandedState === 'close' && props.closeIcon) {
|
||||||
stateIcon = [`uf ${props.closeIcon}`];
|
stateIcon = props.closeIcon;
|
||||||
|
switcherCls['icon-none'] = true;
|
||||||
}
|
}
|
||||||
switcherCls[stateIcon] = stateIcon;
|
//switcherCls[stateIcon] = stateIcon;
|
||||||
|
|
||||||
if (props.disabled) {
|
if (props.disabled) {
|
||||||
switcherCls[`${prefixCls}-switcher-disabled`] = true;
|
switcherCls[`${prefixCls}-switcher-disabled`] = true;
|
||||||
return <span className={classNames(switcherCls)}></span>;
|
return <span className={classNames(switcherCls)}>{stateIcon}</span>;
|
||||||
}
|
}
|
||||||
return <span className={classNames(switcherCls)} onClick={this.onExpand}></span>;
|
return <span className={classNames(switcherCls)} onClick={this.onExpand}>{stateIcon}</span>;
|
||||||
}
|
}
|
||||||
|
|
||||||
renderCheckbox(props) {
|
renderCheckbox(props) {
|
||||||
|
@ -263,6 +265,12 @@ class TreeNode extends React.Component {
|
||||||
let newChildren = this.renderChildren(props);
|
let newChildren = this.renderChildren(props);
|
||||||
let openIconCls = false,
|
let openIconCls = false,
|
||||||
closeIconCls = false;
|
closeIconCls = false;
|
||||||
|
|
||||||
|
//以下变量控制是否鼠标单机双击方法中的变量
|
||||||
|
let timer = 0;
|
||||||
|
let delay = 500;
|
||||||
|
let prevent = false;
|
||||||
|
|
||||||
if (!newChildren || newChildren === props.children) {
|
if (!newChildren || newChildren === props.children) {
|
||||||
// content = newChildren;
|
// content = newChildren;
|
||||||
newChildren = null;
|
newChildren = null;
|
||||||
|
@ -294,15 +302,18 @@ class TreeNode extends React.Component {
|
||||||
domProps.className += ` ${prefixCls}-node-selected`;
|
domProps.className += ` ${prefixCls}-node-selected`;
|
||||||
}
|
}
|
||||||
domProps.onClick = (e) => {
|
domProps.onClick = (e) => {
|
||||||
|
var _this = this;
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
if (props.selectable) {
|
if (props.selectable) {
|
||||||
this.onSelect();
|
_this.onSelect();
|
||||||
}
|
}
|
||||||
|
|
||||||
// not fire check event
|
// not fire check event
|
||||||
// if (props.checkable) {
|
// if (props.checkable) {
|
||||||
// this.onCheck();
|
// this.onCheck();
|
||||||
// }
|
// }
|
||||||
};
|
};
|
||||||
|
|
||||||
if (props.onRightClick) {
|
if (props.onRightClick) {
|
||||||
domProps.onContextMenu = this.onContextMenu;
|
domProps.onContextMenu = this.onContextMenu;
|
||||||
}
|
}
|
||||||
|
@ -312,6 +323,7 @@ class TreeNode extends React.Component {
|
||||||
if (props.onMouseLeave) {
|
if (props.onMouseLeave) {
|
||||||
domProps.onMouseLeave = this.onMouseLeave;
|
domProps.onMouseLeave = this.onMouseLeave;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (props.draggable) {
|
if (props.draggable) {
|
||||||
domProps.className += ' draggable';
|
domProps.className += ' draggable';
|
||||||
if (ieOrEdge) {
|
if (ieOrEdge) {
|
||||||
|
@ -390,8 +402,8 @@ TreeNode.propTypes = {
|
||||||
isLeaf: PropTypes.bool,
|
isLeaf: PropTypes.bool,
|
||||||
root: PropTypes.object,
|
root: PropTypes.object,
|
||||||
onSelect: PropTypes.func,
|
onSelect: PropTypes.func,
|
||||||
openIcon: PropTypes.string,
|
openIcon: PropTypes.element,
|
||||||
closeIcon: PropTypes.string
|
closeIcon: PropTypes.element
|
||||||
};
|
};
|
||||||
|
|
||||||
TreeNode.defaultProps = {
|
TreeNode.defaultProps = {
|
||||||
|
|
Loading…
Reference in New Issue