@salesforce/design-system-react
Version:
Salesforce Lightning Design System for React
164 lines (148 loc) • 4.34 kB
JSX
import React from 'react';
import createReactClass from 'create-react-class';
import PropTypes from 'prop-types';
import { storiesOf, action } from '@storybook/react';
import IconSettings from '../../icon-settings';
import { TREE } from '../../../utilities/constants';
import sampleNodes from '../../../utilities/sample-data/tree';
import Tree from '../../tree';
import Search from '../../forms/input/search';
const branchExpandClicked = action;
const itemClicked = action;
const treeScrolled = action;
const DemoTree = createReactClass({
displayName: 'DemoTree',
// ### Prop Types
propTypes: {
exampleNodesIndex: PropTypes.string,
noBranchSelection: PropTypes.bool,
searchTerm: PropTypes.string,
searchable: PropTypes.bool,
singleSelection: PropTypes.bool
},
getDefaultProps () {
return {
exampleNodesIndex: 'sampleNodesDefault',
id: 'example-tree'
};
},
getInitialState () {
const initalNodes = this.props.exampleNodesIndex
? sampleNodes[this.props.exampleNodesIndex]
: sampleNodes.sampleNodesDefault;
return {
nodes: initalNodes,
selectedNode: undefined,
searchTerm: this.props.searchable ? 'fruit' : undefined
};
},
// By default Tree can have multiple selected nodes and folders/branches can be selected. To disable either of these, you can use the following logic. However, `props` are immutable. The node passed in shouldn't be modified, and due to object and arrays being reference variables, forceUpate is needed. This is just a "working example" not a prescription.
handleExpandClick (event, data) {
branchExpandClicked('Expand Branch')(event, data);
data.node.loading = data.expand ? true : undefined;
// Fake delay to demonstrate use of loading node attibute
setTimeout(
(node) => {
node.loading = false;
this.forceUpdate();
},
500,
data.node
);
data.node.expanded = data.expand;
},
handleClick (event, data) {
if (this.props.singleSelection) {
data.node.selected = data.select;
this.setState((prevState) => {
if (
this.state.selectedNode &&
this.state.selectedNode.id !== data.node.id
) {
this.state.selectedNode.selected = false;
}
return { selectedNode: data.node };
});
itemClicked('Node Clicked')(event, data);
} else if (
!this.props.noBranchSelection ||
(this.props.noBranchSelection && data.node.type !== 'branch')
) {
data.node.selected = data.select;
// trigger render
this.setState((prevState) => ({ ...prevState }));
itemClicked('Node Clicked')(event, data);
}
},
handleScroll (event, data) {
treeScrolled('Tree scrolled')(event, data);
},
handleSearchChange (event) {
this.setState({ searchTerm: event.target.value });
},
render () {
return (
<div>
{this.props.searchable ? (
<div>
<Search
assistiveText="Search Tree"
value={this.state.searchTerm}
onChange={this.handleSearchChange}
/>
<br />
</div>
) : null}
<Tree
nodes={this.state.nodes}
onExpandClick={this.handleExpandClick}
onClick={this.handleClick}
onScroll={this.handleScroll}
searchTerm={this.state.searchTerm}
{...this.props}
/>
</div>
);
}
});
storiesOf(TREE, module)
.addDecorator((getStory) => (
<div className="slds-p-around--medium">
<IconSettings iconPath="/assets/icons">{getStory()}</IconSettings>
</div>
))
.add('Base', () => <DemoTree heading="Miscellaneous Foods" />)
.add('Initial Expanded/Selection', () => (
<DemoTree
heading="Miscellaneous Foods"
exampleNodesIndex="sampleNodesWithInitialState"
/>
))
.add('No Branch Select', () => (
<DemoTree heading="Miscellaneous Foods" noBranchSelection />
))
.add('Single Selection', () => (
<DemoTree heading="Miscellaneous Foods" singleSelection />
))
.add('Assistive Heading', () => (
<DemoTree assistiveText="Miscellaneous Foods" />
))
.add('Overflow Hidden', () => (
<DemoTree
heading="Miscellaneous Foods"
exampleNodesIndex="sampleNodesWithLargeDataset"
listStyle={{
height: '300px',
overflowY: 'auto'
}}
/>
))
.add('Large dataset (300+)', () => (
<DemoTree
heading="Miscellaneous Foods"
exampleNodesIndex="sampleNodesWithLargeDataset"
/>
))
.add('Highlighted Search', () => (
<DemoTree heading="Results for fruit" searchable />
));