在 react-select 2 中显示带有选项的图像
display Image with options in react-select 2
我正在尝试使用 react-avatar 在 react-select v2 的每个选项中添加图像。
这是我到目前为止尝试过的方法:
import React from 'react';
import createClass from 'create-react-class';
import PropTypes from 'prop-types';
import Select from 'react-select';
import Avatar from 'react-avatar';
const USERS = [
{
value: 'John Smith', label: 'John Smith', email: 'john@smith.com', avatar: '',
},
{
value: 'Merry Jane', label: 'Merry Jane', email: 'merry@jane.com', avatar: 'https://upload.wikimedia.org/wikipedia/commons/thumb/9/9c/Hrithik_at_Rado_launch.jpg/220px-Hrithik_at_Rado_launch.jpg',
},
{
value: 'Stan Hoper', label: 'Stan Hoper', email: 'stan@hoper.com', avatar: 'https://adminui.liscio.me/wp-content/uploads/2018/05/james_wurbs.png',
},
];
const GRAVATAR_SIZE = 30;
const stringOrNode = PropTypes.oneOfType([
PropTypes.string,
PropTypes.node,
]);
const GravatarOption = createClass({
propTypes: {
children: PropTypes.node,
className: PropTypes.string,
isDisabled: PropTypes.bool,
isFocused: PropTypes.bool,
isSelected: PropTypes.bool,
onFocus: PropTypes.func,
onSelect: PropTypes.func,
option: PropTypes.object.isRequired,
},
handleMouseDown(event) {
event.preventDefault();
event.stopPropagation();
this.props.onSelect(this.props.option, event);
},
handleMouseEnter(event) {
this.props.onFocus(this.props.option, event);
},
handleMouseMove(event) {
if (this.props.isFocused) return;
this.props.onFocus(this.props.option, event);
},
render() {
return (
<div
className={this.props.className}
onMouseDown={this.handleMouseDown}
onMouseEnter={this.handleMouseEnter}
onMouseMove={this.handleMouseMove}>
<Avatar round size={GRAVATAR_SIZE} className="avatar" color="#0366d6" name={this.props.option.label} src={this.props.option.avatar} />
{this.props.option.label}
</div>
);
},
});
const GravatarValue = createClass({
propTypes: {
children: PropTypes.node,
placeholder: stringOrNode,
value: PropTypes.object,
},
render() {
return (
<div className="Select-value">
<span className="Select-value-label">
<Avatar round size={GRAVATAR_SIZE} className="avatar" color="#0366d6" name={this.props.value.label} src={this.props.value.avatar} />
{this.props.value.label}
</span>
</div>
);
},
});
const UsersField = createClass({
propTypes: {
hint: PropTypes.string,
label: PropTypes.string,
},
getInitialState() {
return {};
},
setValue(value) {
this.setState({ value });
},
render() {
const placeholder = <span>☺ Select User</span>;
return (
<div className="section text-left">
<Select
onChange={this.setValue}
components={{ Option: GravatarOption, Value: GravatarValue }}
options={USERS}
placeholder={placeholder}
value={this.state.value}
/>
</div>
);
},
});
export default UsersField;
由于未定义 prop 选项,此示例无法正常工作。但是在示例中,它与 react-select v1 一起工作正常,但它不适用于 react-select v2.
如有任何帮助,我们将不胜感激。谢谢
首先,您需要确保将 innerRef 和 innerProps 传递给您的 Option,否则它不会触发鼠标悬停和单击事件(这在文档中,但没有很好地说明)。这是一个例子:
const Option = props => {
const { innerProps, innerRef } = props;
return (
<article ref={innerRef} {...innerProps} className={'custom-option'}>
<h4>{props.data.artist}</h4>
<div className={'sub'}>{props.data.title} </div>
</article>
);
};
<Select {...selectProps} components={{Option}}/>
接下来,Control中显示的'value'是SingleValue还是MultiValue,取决于isMulti。要控制 SingleValue 标签的显示,您需要覆盖 SingleValue。要覆盖 MultiValue 的显示,您可能要覆盖 MultiValueLabel。所有这些都在 Components documentation 中列出,并附有示例。
最后,您可以从我上面的选项示例中看到,选项 data
是存储对象的位置。您的选项可能只需要这样的内容:
import { components } from 'react-select';
const Option = props => {
const {data} = props;
return (
<components.Option {...props}>
<Avatar round size={GRAVATAR_SIZE} className="avatar" color="#0366d6" name={data.label} src={data.avatar} />
{data.label}
</components.Option>
);
};
我正在尝试使用 react-avatar 在 react-select v2 的每个选项中添加图像。
这是我到目前为止尝试过的方法:
import React from 'react';
import createClass from 'create-react-class';
import PropTypes from 'prop-types';
import Select from 'react-select';
import Avatar from 'react-avatar';
const USERS = [
{
value: 'John Smith', label: 'John Smith', email: 'john@smith.com', avatar: '',
},
{
value: 'Merry Jane', label: 'Merry Jane', email: 'merry@jane.com', avatar: 'https://upload.wikimedia.org/wikipedia/commons/thumb/9/9c/Hrithik_at_Rado_launch.jpg/220px-Hrithik_at_Rado_launch.jpg',
},
{
value: 'Stan Hoper', label: 'Stan Hoper', email: 'stan@hoper.com', avatar: 'https://adminui.liscio.me/wp-content/uploads/2018/05/james_wurbs.png',
},
];
const GRAVATAR_SIZE = 30;
const stringOrNode = PropTypes.oneOfType([
PropTypes.string,
PropTypes.node,
]);
const GravatarOption = createClass({
propTypes: {
children: PropTypes.node,
className: PropTypes.string,
isDisabled: PropTypes.bool,
isFocused: PropTypes.bool,
isSelected: PropTypes.bool,
onFocus: PropTypes.func,
onSelect: PropTypes.func,
option: PropTypes.object.isRequired,
},
handleMouseDown(event) {
event.preventDefault();
event.stopPropagation();
this.props.onSelect(this.props.option, event);
},
handleMouseEnter(event) {
this.props.onFocus(this.props.option, event);
},
handleMouseMove(event) {
if (this.props.isFocused) return;
this.props.onFocus(this.props.option, event);
},
render() {
return (
<div
className={this.props.className}
onMouseDown={this.handleMouseDown}
onMouseEnter={this.handleMouseEnter}
onMouseMove={this.handleMouseMove}>
<Avatar round size={GRAVATAR_SIZE} className="avatar" color="#0366d6" name={this.props.option.label} src={this.props.option.avatar} />
{this.props.option.label}
</div>
);
},
});
const GravatarValue = createClass({
propTypes: {
children: PropTypes.node,
placeholder: stringOrNode,
value: PropTypes.object,
},
render() {
return (
<div className="Select-value">
<span className="Select-value-label">
<Avatar round size={GRAVATAR_SIZE} className="avatar" color="#0366d6" name={this.props.value.label} src={this.props.value.avatar} />
{this.props.value.label}
</span>
</div>
);
},
});
const UsersField = createClass({
propTypes: {
hint: PropTypes.string,
label: PropTypes.string,
},
getInitialState() {
return {};
},
setValue(value) {
this.setState({ value });
},
render() {
const placeholder = <span>☺ Select User</span>;
return (
<div className="section text-left">
<Select
onChange={this.setValue}
components={{ Option: GravatarOption, Value: GravatarValue }}
options={USERS}
placeholder={placeholder}
value={this.state.value}
/>
</div>
);
},
});
export default UsersField;
由于未定义 prop 选项,此示例无法正常工作。但是在示例中,它与 react-select v1 一起工作正常,但它不适用于 react-select v2.
如有任何帮助,我们将不胜感激。谢谢
首先,您需要确保将 innerRef 和 innerProps 传递给您的 Option,否则它不会触发鼠标悬停和单击事件(这在文档中,但没有很好地说明)。这是一个例子:
const Option = props => {
const { innerProps, innerRef } = props;
return (
<article ref={innerRef} {...innerProps} className={'custom-option'}>
<h4>{props.data.artist}</h4>
<div className={'sub'}>{props.data.title} </div>
</article>
);
};
<Select {...selectProps} components={{Option}}/>
接下来,Control中显示的'value'是SingleValue还是MultiValue,取决于isMulti。要控制 SingleValue 标签的显示,您需要覆盖 SingleValue。要覆盖 MultiValue 的显示,您可能要覆盖 MultiValueLabel。所有这些都在 Components documentation 中列出,并附有示例。
最后,您可以从我上面的选项示例中看到,选项 data
是存储对象的位置。您的选项可能只需要这样的内容:
import { components } from 'react-select';
const Option = props => {
const {data} = props;
return (
<components.Option {...props}>
<Avatar round size={GRAVATAR_SIZE} className="avatar" color="#0366d6" name={data.label} src={data.avatar} />
{data.label}
</components.Option>
);
};