@salesforce/design-system-react
Version:
Salesforce Lightning Design System for React
561 lines (499 loc) • 14.9 kB
JSX
/* eslint-disable max-lines */
import React from 'react';
import PropTypes from 'prop-types';
import { storiesOf } from '@storybook/react';
import { action } from '@storybook/addon-actions';
import { APP_LAUNCHER } from '../../../utilities/constants';
import AppLauncher from '../../app-launcher';
import AppLauncherTile from '../../app-launcher/tile';
import AppLauncherSection from '../../app-launcher/section';
import Icon from '../../icon';
import Button from '../../button';
import Search from '../../input/search';
import GlobalNavigationBar from '../../global-navigation-bar';
import GlobalNavigationBarRegion from '../../global-navigation-bar/region';
import IconSettings from '../../icon-settings';
import SLDSSettings from '../../SLDSSettings';
import DefaultExample from '../__examples__/default';
import { canUseDOM } from '../../../utilities/execution-environment';
// used by Modal component
if (canUseDOM && document.querySelector('#root')) {
SLDSSettings.setAppElement('#root');
} else {
SLDSSettings.setAppElement(document.createElement('div'));
}
const standardTileDemoStyles = {
width: '20rem',
paddingLeft: '.5rem',
paddingRight: '.5rem',
};
const smallTileDemoStyles = {
width: '6rem',
paddingLeft: '.5rem',
paddingRight: '.5rem',
};
class DemoAppLauncherTile extends React.Component {
static displayName = 'DemoAppLauncherTile';
static propTypes = {
search: PropTypes.string,
size: PropTypes.string,
};
render() {
return (
<AppLauncherTile
title="Marketing Cloud"
iconText="MC"
description="Send emails, track emails, read emails! Emails!"
href="https://www.marketingcloud.com/"
onClick={action('Tile clicked! Actual href should be ignored')}
search={this.props.search}
size={this.props.size}
/>
);
}
}
class DemoAppLauncherSmallTile extends React.Component {
static displayName = 'DemoAppLauncherSmallTile';
render() {
return (
<AppLauncherTile
title="Journey Builder"
iconText="JB"
size="small"
onClick={action('Tiny tile clicked!')}
/>
);
}
}
class DemoAppLauncherTileWithIconNode extends React.Component {
static displayName = 'DemoAppLauncherTileWithIconNode';
static propTypes = {
search: PropTypes.string,
size: PropTypes.string,
};
render() {
const icon = <Icon name="campaign" category="standard" size="large" />;
return (
<AppLauncherTile
title="Sales Cloud"
description="The primary internal Salesforce org."
href="https://www.salesforce.com/"
iconNode={icon}
onClick={action('Tile with icon node clicked!')}
search={this.props.search}
size={this.props.size}
/>
);
}
}
class DemoAppLauncherTileWithIconText extends React.Component {
static displayName = 'DemoAppLauncherTileWithIconText';
static propTypes = {
search: PropTypes.string,
size: PropTypes.string,
};
render() {
return (
<AppLauncherTile
title="Sales Cloud"
description="The primary internal Salesforce org."
iconText="SC"
onClick={action('Tile with icon text clicked!')}
search={this.props.search}
size={this.props.size}
/>
);
}
}
class DemoAppLauncherTileWithTruncatedText extends React.Component {
static displayName = 'DemoAppLauncherTileWithTruncatedText';
static propTypes = {
search: PropTypes.string,
size: PropTypes.string,
};
render() {
return (
<AppLauncherTile
title="Call Center"
description="The key to call center and contact center is not to use too many words!"
iconText="CC"
onClick={action('Tile with icon text clicked!')}
search={this.props.search}
size={this.props.size}
/>
);
}
}
class DemoAppLauncherTileWithDescriptionHeading extends React.Component {
static displayName = 'DemoAppLauncherTileWithDescriptionHeading';
static propTypes = {
search: PropTypes.string,
size: PropTypes.string,
};
static defaultProps = {
search: 'journey',
};
render() {
return (
<AppLauncherTile
title="Journey Builder"
description="Build 1:1 journeys blah blah blah and use way too many words"
descriptionHeading="Journey Builder"
iconText="JB"
onClick={action('Tile with description heading clicked!')}
search={this.props.search}
size={this.props.size}
/>
);
}
}
class DemoAppLauncherTileWithSearchText extends React.Component {
static displayName = 'DemoAppLauncherTileWithSearchText';
static propTypes = {
search: PropTypes.string,
size: PropTypes.string,
};
static defaultProps = {
search: 'Call',
};
render() {
return (
<DemoAppLauncherTileWithTruncatedText
search={this.props.search}
size={this.props.size}
/>
);
}
}
class DemoAppLauncherSection extends React.Component {
static displayName = 'DemoAppLauncherSection';
render() {
return (
<div>
<AppLauncherSection
assistiveText={{ collapseSection: 'Collapse Section' }}
title="All Items"
toggleable
onToggleClick={action('Section `All Items` open -->')}
>
<DemoAppLauncherTile />
<DemoAppLauncherTileWithIconText />
<DemoAppLauncherTileWithIconNode />
</AppLauncherSection>
<AppLauncherSection
title="All Apps"
onToggleClick={action('Section `All App` open -->')}
>
<DemoAppLauncherTile />
<DemoAppLauncherTileWithIconNode />
</AppLauncherSection>
</div>
);
}
}
class DemoAppLauncherSectionWithSmallTiles extends React.Component {
static displayName = 'DemoAppLauncherSectionWithSmallTiles';
render() {
return (
<div>
<AppLauncherSection
title="All Items"
onToggleClick={action('Section `All Items` open -->')}
>
<DemoAppLauncherTile />
<DemoAppLauncherTileWithIconText />
<DemoAppLauncherTileWithIconNode />
</AppLauncherSection>
<AppLauncherSection
title="All Apps"
onToggleClick={action('Section `All App` open -->')}
>
<DemoAppLauncherTile size="small" />
<DemoAppLauncherTileWithIconNode size="small" />
</AppLauncherSection>
</div>
);
}
}
class DemoAppLauncher extends React.Component {
static displayName = 'DemoAppLauncher';
state = {
search: '',
appLauncherOpen: this.props.isOpen || false, // eslint-disable-line react/prop-types
allItemsSectionIsOpen: false,
};
onClear = () => {
this.setState({ search: '' });
};
onSearch = (event) => {
this.setState({ search: event.target.value });
};
toggleAppLauncher = () => {
this.setState({ appLauncherOpen: !this.state.appLauncherOpen });
};
toggleSection = () => {
this.setState({ allItemsSectionIsOpen: !this.state.allItemsSectionIsOpen });
};
render() {
const search = (
<Search
clearable={this.state.search !== ''}
onChange={this.onSearch}
onClear={this.onClear}
placeholder="Find an app"
assistiveText={{ label: 'Find an app' }}
value={this.state.search}
/>
);
const modalHeaderButton = (
<Button label="App Exchange" onClick={action('Modal Button clicked!')} />
);
return (
<GlobalNavigationBar>
<GlobalNavigationBarRegion region="primary">
<AppLauncher
assistiveText={{ trigger: 'Open App Launcher' }}
triggerName="App Name"
search={search}
modalClassName="custom-modal-class"
modalHeaderButton={modalHeaderButton}
isOpen={this.state.appLauncherOpen}
triggerOnClick={this.toggleAppLauncher}
onClose={this.toggleAppLauncher}
>
<AppLauncherSection
toggleable
title="All Items"
isOpen={this.state.allItemsSectionIsOpen}
onToggleClick={this.toggleSection}
>
<DemoAppLauncherTile search={this.state.search} />
<DemoAppLauncherTileWithIconNode search={this.state.search} />
<DemoAppLauncherTileWithIconText search={this.state.search} />
<DemoAppLauncherTile search={this.state.search} />
<DemoAppLauncherTileWithIconNode search={this.state.search} />
<DemoAppLauncherTileWithIconText search={this.state.search} />
</AppLauncherSection>
<AppLauncherSection title="All Apps" toggleable>
<DemoAppLauncherTile search={this.state.search} />
<DemoAppLauncherTileWithTruncatedText
search={this.state.search}
/>
<DemoAppLauncherTileWithDescriptionHeading
search={this.state.search}
/>
<DemoAppLauncherTile search={this.state.search} />
<DemoAppLauncherTileWithTruncatedText
search={this.state.search}
/>
<DemoAppLauncherTileWithDescriptionHeading
search={this.state.search}
/>
<DemoAppLauncherTile search={this.state.search} />
<DemoAppLauncherTileWithTruncatedText
search={this.state.search}
/>
<DemoAppLauncherTileWithDescriptionHeading
search={this.state.search}
/>
</AppLauncherSection>
</AppLauncher>
</GlobalNavigationBarRegion>
</GlobalNavigationBar>
);
}
}
class DemoAppLauncherNoHeaderButton extends React.Component {
static displayName = 'DemoAppLauncherNoHeaderButton';
state = {
search: '',
appLauncherOpen: false,
allItemsSectionIsOpen: false,
};
onSearch = (event) => {
this.setState({ search: event.target.value });
};
toggleAppLauncher = () => {
this.setState({ appLauncherOpen: !this.state.appLauncherOpen });
};
render() {
const search = (
<Search
onChange={this.onSearch}
placeholder="Find an app"
assistiveText={{ label: 'Find an app' }}
/>
);
return (
<GlobalNavigationBar>
<GlobalNavigationBarRegion region="primary">
<AppLauncher
triggerName="App Name"
search={search}
isOpen={this.state.appLauncherOpen}
triggerOnClick={this.toggleAppLauncher}
onClose={this.toggleAppLauncher}
>
<AppLauncherSection toggleable title="All Items">
<DemoAppLauncherTile search={this.state.search} />
<DemoAppLauncherTileWithIconNode search={this.state.search} />
<DemoAppLauncherTileWithIconText search={this.state.search} />
</AppLauncherSection>
<AppLauncherSection title="All Apps" toggleable>
<DemoAppLauncherTile search={this.state.search} />
<DemoAppLauncherTileWithTruncatedText
search={this.state.search}
/>
</AppLauncherSection>
</AppLauncher>
</GlobalNavigationBarRegion>
</GlobalNavigationBar>
);
}
}
class DemoAppLauncherNoSearch extends React.Component {
static displayName = 'DemoAppLauncherNoSearch';
state = {
appLauncherOpen: false,
allItemsSectionIsOpen: false,
};
toggleAppLauncher = () => {
this.setState({ appLauncherOpen: !this.state.appLauncherOpen });
};
render() {
const modalHeaderButton = (
<Button label="App Exchange" onclick={action('Modal Button clicked!')} />
);
return (
<GlobalNavigationBar>
<GlobalNavigationBarRegion region="primary">
<AppLauncher
triggerName="App Name"
modalHeaderButton={modalHeaderButton}
isOpen={this.state.appLauncherOpen}
triggerOnClick={this.toggleAppLauncher}
onClose={this.toggleAppLauncher}
>
<AppLauncherSection toggleable title="All Items">
<DemoAppLauncherTile />
<DemoAppLauncherTileWithIconNode />
<DemoAppLauncherTileWithIconText />
</AppLauncherSection>
<AppLauncherSection title="All Apps" toggleable>
<DemoAppLauncherTile />
<DemoAppLauncherTileWithTruncatedText />
</AppLauncherSection>
</AppLauncher>
</GlobalNavigationBarRegion>
</GlobalNavigationBar>
);
}
}
class DemoAppLauncherWithSeveralSections extends React.Component {
static displayName = 'DemoAppLauncherWithSeveralSections';
onSearch = () => {
// stub
};
render() {
const search = (
<Search
onChange={this.onSearch}
placeholder="Find an app"
assistiveText={{ label: 'Find an app' }}
/>
);
const modalHeaderButton = (
<Button label="App Exchange" onclick={action('Modal Button clicked!')} />
);
return (
<GlobalNavigationBar>
<GlobalNavigationBarRegion region="primary">
<AppLauncher
triggerName="App Name"
search={search}
modalHeaderButton={modalHeaderButton}
>
<AppLauncherSection title="First Section">
<DemoAppLauncherTile />
<DemoAppLauncherTileWithIconNode />
<DemoAppLauncherTileWithTruncatedText />
</AppLauncherSection>
<AppLauncherSection title="Second Section">
<DemoAppLauncherTile />
<DemoAppLauncherTileWithIconNode />
<DemoAppLauncherTileWithTruncatedText />
</AppLauncherSection>
<AppLauncherSection title="Third Section">
<DemoAppLauncherTile />
<DemoAppLauncherTileWithIconNode />
<DemoAppLauncherTileWithTruncatedText />
</AppLauncherSection>
<AppLauncherSection title="Fourth Section">
<DemoAppLauncherTile />
<DemoAppLauncherTileWithIconNode />
<DemoAppLauncherTileWithTruncatedText />
</AppLauncherSection>
<AppLauncherSection title="Fifth Section">
<DemoAppLauncherTile />
<DemoAppLauncherTileWithIconNode />
<DemoAppLauncherTileWithTruncatedText />
</AppLauncherSection>
</AppLauncher>
</GlobalNavigationBarRegion>
</GlobalNavigationBar>
);
}
}
storiesOf(APP_LAUNCHER, module)
.addDecorator((getStory) => (
<div className="slds-p-around_medium">
<IconSettings iconPath="/assets/icons">{getStory()}</IconSettings>
</div>
))
.add('App Launcher (open)', () => <DemoAppLauncher isOpen />)
.add('App Launcher', () => <DemoAppLauncher />)
.add('App Launcher no header button', () => <DemoAppLauncherNoHeaderButton />)
.add('App Launcher no search', () => <DemoAppLauncherNoSearch />)
.add('App Launcher with several sections (no toggle)', () => (
<DemoAppLauncherWithSeveralSections />
))
.add('Tile', () => (
<div style={standardTileDemoStyles}>
<DemoAppLauncherTile />
</div>
))
.add('Small Tile', () => (
<div style={smallTileDemoStyles}>
<DemoAppLauncherSmallTile />
</div>
))
.add('Tile with Icon node', () => (
<div style={standardTileDemoStyles}>
<DemoAppLauncherTileWithIconNode />
</div>
))
.add('Tile with icon text', () => (
<div style={standardTileDemoStyles}>
<DemoAppLauncherTileWithIconText />
</div>
))
.add('Tile with search text', () => (
<div style={standardTileDemoStyles}>
<DemoAppLauncherTileWithSearchText />
</div>
))
.add('Tile with truncated text', () => (
<div style={standardTileDemoStyles}>
<DemoAppLauncherTileWithTruncatedText />
</div>
))
.add('Tile with description heading', () => (
<div style={standardTileDemoStyles}>
<DemoAppLauncherTileWithDescriptionHeading />
</div>
))
.add('Section', () => <DemoAppLauncherSection />)
.add('Section with small tiles', () => (
<DemoAppLauncherSectionWithSmallTiles />
))
.add('Doc site example', () => <DefaultExample />);