Hook up team dropdowns and lists

This commit is contained in:
John Lyon-Smith
2018-03-30 10:37:06 -07:00
parent b301bf17eb
commit bddf717d37
20 changed files with 437 additions and 321 deletions

View File

@@ -41,9 +41,13 @@ export class BoundButton extends React.Component {
const { name, text, submit, width, onClick } = this.props
const { visible, disabled } = this.state
if (!visible) {
return null
}
return (
<Button disabled={disabled} submit={submit} onClick={onClick}
name={name} visible={visible} text={text} width={width} />
name={name} text={text} width={width} />
)
}
}

View File

@@ -36,8 +36,12 @@ export class BoundCheckbox extends React.Component {
const { name, label } = this.props
const { visible, disabled, value } = this.state
if (!visible) {
return null
}
return (
<div style={visible ? {} : { display: 'none' }}>
<div>
<Checkbox id={name} disabled={disabled} value={value} onChange={this.handleChange} />
<label
htmlFor={name}

View File

@@ -0,0 +1,75 @@
import React from 'react'
import PropTypes from 'prop-types'
import { Dropdown } from 'ui'
import autobind from 'autobind-decorator'
import { sizeInfo, fontInfo } from 'ui/style'
export class BoundDropdown extends React.Component {
static propTypes = {
name: PropTypes.string.isRequired,
label: PropTypes.string,
binder: PropTypes.object.isRequired,
items: PropTypes.arrayOf(PropTypes.shape({ value: PropTypes.string, text: PropTypes.string, icon: PropTypes.string })),
icon: PropTypes.string,
}
constructor(props) {
super(props)
this.state = props.binder.getFieldState(props.name)
}
@autobind
handleChange(item) {
const { binder, name } = this.props
const state = binder.getFieldState(name)
if (!state.readOnly && !state.disabled) {
this.setState(binder.updateFieldValue(name, item.value))
}
}
componentWillReceiveProps(nextProps) {
if (nextProps.binder !== this.props.binder) {
this.setState(nextProps.binder.getFieldState(nextProps.name))
}
if (nextProps.items !== this.props.items) {
this.forceUpdate()
}
}
render() {
const { name, label, icon, items } = this.props
const { visible, disabled, value } = this.state
if (!visible) {
return null
}
return (
<div>
<label
htmlFor={name}
style={{
fontSize: fontInfo.size.medium,
fontFamily: fontInfo.family,
color: disabled ? fontInfo.color.dimmed : fontInfo.color.normal,
}}>
{label}
<Dropdown
items={items}
value={value}
emptyItem={{ value: null, text: '', icon: 'team' }}
icon={icon}
onChange={this.handleChange}
render={(item) => (
<Dropdown.Item key={item.value}>
<Dropdown.Icon name={item.icon} size={sizeInfo.dropdownIconSize} />
<Dropdown.Text>{item.text}</Dropdown.Text>
</Dropdown.Item>
)} />
</label>
</div>
)
}
}

View File

@@ -38,12 +38,16 @@ export class BoundInput extends React.Component {
const { label, password, name, placeholder, message } = this.props
const { visible, disabled, value, valid } = this.state
if (!visible) {
return null
}
return (
<div style={{ width: '100%' }}>
<Text>{label}</Text>
<br />
<Input value={value}
visible={visible}
visible
disabled={disabled}
password={password}
name={name}

View File

@@ -8,17 +8,37 @@ import upArrowImage from './images/up-arrow.svg'
import autobind from 'autobind-decorator'
@Radium
export class DropdownList extends Component {
export class Dropdown extends Component {
static propTypes = {
items: PropTypes.array,
items: PropTypes.arrayOf(PropTypes.shape({ value: PropTypes.string, text: PropTypes.string, icon: PropTypes.string })),
value: PropTypes.string,
render: PropTypes.func.isRequired,
emptyItem: PropTypes.shape({ value: PropTypes.string, text: PropTypes.string, icon: PropTypes.string }),
onChange: PropTypes.func,
}
static defaultProps = {
emptyItem: { value: null, text: '', icon: null },
}
constructor(props) {
super(props)
this.state = {
open: false,
selectedItem: (props.items && props.items.length > 0) ? props.items[0] : {},
selectedItem: this.getSelectedFromValue(props.items, props.value)
}
}
@autobind
getSelectedFromValue(items, value) {
return items.find((item) => (item.value === value)) || this.props.emptyItem
}
componentWillReceiveProps(nextProps) {
if (nextProps.value !== this.props.value || nextProps.items !== this.props.items) {
this.setState({
selectedItem: this.getSelectedFromValue(nextProps.items, nextProps.value)
})
}
}
@@ -30,6 +50,9 @@ export class DropdownList extends Component {
@autobind
handleItemClick(e, item) {
this.setState({ selectedItem: item, open: false })
if (this.props.onChange) {
this.props.onChange(item)
}
}
render() {
@@ -100,7 +123,7 @@ export class DropdownList extends Component {
}
}
DropdownList.Item = Radium(class ListItem extends Component {
Dropdown.Item = Radium(class ListItem extends Component {
static propTypes = {
children: PropTypes.node,
active: PropTypes.bool,
@@ -124,7 +147,7 @@ DropdownList.Item = Radium(class ListItem extends Component {
}
})
DropdownList.Icon = Radium(class DropdownIcon extends Component {
Dropdown.Icon = Radium(class DropdownIcon extends Component {
static propTypes = {
name: PropTypes.string,
size: PropTypes.number,
@@ -149,7 +172,7 @@ DropdownList.Icon = Radium(class DropdownIcon extends Component {
}
})
DropdownList.Text = Radium(class DropdownText extends Component {
Dropdown.Text = Radium(class DropdownText extends Component {
static propTypes = {
children: PropTypes.node,
}

View File

@@ -11,7 +11,7 @@ export { Text } from './Text'
export { Link } from './Link'
export { Icon } from './Icon'
export { List } from './List'
export { DropdownList } from './DropdownList'
export { Dropdown } from './Dropdown'
export { Modal } from './Modal'
export { Dimmer } from './Dimmer'
export { Loader } from './Loader'
@@ -21,3 +21,4 @@ export { BoundButton } from './BoundButton'
export { BoundCheckbox } from './BoundCheckbox'
export { BoundInput } from './BoundInput'
export { BoundEmailIcon } from './BoundEmailIcon'
export { BoundDropdown } from './BoundDropdown'