Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
4.1k views
in Technique[技术] by (71.8m points)

reactjs - React-Select, passing props with multiple selects in one form

I am using React-Select in my first React App and I am not sure how to handle multiple selects in one form.

Is there anyway to pass props into the ReactSelect.jsx file so that I can have multiple selects in one form, each with their own attributes/data?

What is the proper way to deal with this?

Ref: Experimental Popout

App.js

import React from 'react';
import ReactSelect from './ReactSelect'


function App() {
    return (
        <ReactSelect name="select1" placeholder="Select 1" label="Select 1" data={} />
        <ReactSelect name="select2" placeholder="Select 2" label="Select 2" data={} />
        <ReactSelect name="select3" placeholder="Select 3" label="Select 3" data={} />
    );
  }
  
  export default App;

ReactSelect.jsx

/** @jsx jsx */
import { Component } from 'react';
import { jsx } from '@emotion/core';
import Button from '@atlaskit/button';
import CreatableSelect from 'react-select/creatable';
import { defaultTheme } from 'react-select';


const { colors } = defaultTheme;

const selectStyles = {
  control: provided => ({ ...provided, minWidth: 240, margin: 8 }),
  menu: () => ({ boxShadow: 'inset 0 1px 0 rgba(0, 0, 0, 0.1)' }),
};

const State = {
    isOpen: false,
    options: [{ [""]: "" }], 
    value: "",
    isLoading: false,
};

const createOption = (label = "") => ({
    value: label.toLowerCase().replace(/W/g, ''),
    label,
});
const groupStyles = {
    width: '100%',
    textAlign: 'left',
    borderRadius: 4,
    backgroundColor: 'white',
    border: '1px solid #ced4da',
};

const options=[
    { value: 'one', label: 'One' },
    { value: 'two', label: 'Two' },
    { value: 'three', label: 'Three' },
];

export default class ReactSelect extends Component {
    state = {
        isOpen: false,
        options: options,
        value: undefined,
        isLoading: false,
    };
    toggleOpen = () => {
        this.setState(state => ({ isOpen: !state.isOpen }));
    };
    onSelectChange = value => {
        this.toggleOpen();
        this.setState({ value });
        console.log(value.value);
    };
    handleCreate = (inputValue = "") => {
        this.setState({ isLoading: true });
        setTimeout(() => {
            const { options } = this.state;
            const newOption = createOption(inputValue);
            const newOptions = [...options, newOption];
            newOptions.sort((a, b) =>
            a.value.localeCompare(b.value)
        );
        this.setState(state => ({
            isOpen: false,
            options: newOptions,
            value: newOption
        }));
        this.setState({ isLoading: false });
    }, 1000);
    }
  render() {
    const { isOpen, options, value, isLoading } = this.state;
    return (
      <Dropdown
        isOpen={isOpen}
        onClose={this.toggleOpen}
        target={
          <Button
            iconAfter={<ChevronDown />}
            onClick={this.toggleOpen}
            isSelected={isOpen}
            style={groupStyles}>
            {value ? `Location: ${value.label}` : 'Select a Location'}
          </Button>
        }>
        <CreatableSelect
            backspaceRemovesValue={false}
            components={{ DropdownIndicator, IndicatorSeparator: null }}
            controlShouldRenderValue={true}
            hideSelectedOptions={false}
            isClearable={true}
            menuIsOpen
            isLoading={isLoading}
            isDisabled={isLoading}
            onChange={this.onSelectChange}
            onCreateOption={this.handleCreate}
            options={options}
            placeholder="Search..."
            styles={selectStyles}
            tabSelectsValue={false}
            value={value} />
        </Dropdown>
    );
  }
}

// styled components
const Menu = props => {
  const shadow = 'hsla(218, 50%, 10%, 0.1)';
  console.log(props);
  return (
    <div
      css={{
        backgroundColor: 'white',
        borderRadius: 4,
        boxShadow: `0 0 0 1px ${shadow}, 0 4px 11px ${shadow}`,
        marginTop: 8,
        position: 'absolute',
        zIndex: 2,
        width:'100%',
      }}
      {...props}
    />
  );
};
const Blanket = props => (
  <div
    css={{
      bottom: 0,
      left: 0,
      top: 0,
      right: 0,
      position: 'fixed',
      zIndex: 1,
    }}
    {...props}
  />
);
const Dropdown = ({ children, isOpen, target, onClose }) => (
  <div css={{ position: 'relative' }}>
    {target}
    {isOpen ? <Menu>{children}</Menu> : null}
    {isOpen ? <Blanket onClick={onClose} /> : null}
  </div>
);

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Answer

0 votes
by (71.8m points)

The following seems to work for me...

this.props.name
this.props.placeholder    
this.props.data

Example: To set the placeholder

{value ? `${this.props.placeholder} ${value.label}` : this.props.placeholder}

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...