【问题标题】:ReactJS Radiobutton-Group with multiple varibales具有多个变量的 ReactJS 单选按钮组
【发布时间】:2019-01-26 10:59:40
【问题描述】:

我正在尝试在 ReactJS 中构建一个 Radiobutton-Group,就像这样:

我也在使用 Bootstrap 自定义单选按钮。

首先我制作了这个组件:

import React from "react";
import ReactDOM from 'react-dom';
import PropTypes from "prop-types";
import FormsStatic from "../FormsStatic";

class IPMRadiobutton extends React.Component {
    constructor(props) {
        super(props);
    }
    render() {
        const uniqueId = FormsStatic.guid();
        return (
            <div className="custom-control custom-radio">
                <input
                    type="radio"
                    className="custom-control-input"
                    id={"others-" + uniqueId}
                    checked={this.props.checked}
                    onChange={this.props.onChange}
                    disabled={this.props.readOnly}
                />
                <label className="custom-control-label" style={{ 'fontWeight': 'normal' }} htmlFor={"others-" + uniqueId}>
                    <p>{this.props.description ? this.props.description : ""}</p>
                </label>
            </div>
        );
    }
}

IPMRadiobutton.propTypes = {
    className: PropTypes.string,
    onChange: PropTypes.func,
    readOnly: PropTypes.bool,
    description: PropTypes.string,
    checked: PropTypes.bool
}

export default IPMRadiobutton;

现在我想像这样使用这个单选按钮:

   <IPMRadiobutton {...this.props.formControlProps} checked={variable1} description="H-Akte" name="Akte" onChange={() => { console.log("Do i have to change the variable1 and variable2 here?") }} />
   <IPMRadiobutton {...this.props.formControlProps} checked={variable2} description="U-Akte" name="Akte" onChange={() => { console.log("Do i have to change the variable1 and variable2 here?") }} />

我的问题是每个单选按钮都应该绑定到一个变量(或者更确切地说更改“onChange-event”中其他单选按钮的所有变量)。所以如果我检查第一个 Radiobutton,variable1 应该设置为 true,variable2 应该设置为 false。

如何使用我的组件完成这项任务?

或者有没有更好的方法来做到这一点(就像一个完整的其他概念)?

【问题讨论】:

    标签: javascript reactjs radio


    【解决方案1】:

    如果您需要在某个非常重要的项目的生产中使用它,我建议您为此使用一些 react 插件。您可以在那里找到它,相信我。但是如果您正在修改 react 并享受您的时间编码你可以检查我的(丑陋但有一些想法)的例子。

    您可以使用这个想法创建自己的 RadioGroup 组件。将 options 传递给 RadioGroup 并让组件根据属性呈现无线电输入似乎是一种简单的解决方法。但是这个解决方案并不完美,但我发现很容易申请。

    我认为将值传递给 RadioGroup 组件并通过将 onChange 回调传递给组件来更新值是好的,因为无论如何您都希望保存此值,也不在 RadioGroup 组件中存储内部值会使其更具反应性,这反过来简化与外部源的值同步。

    作为奖励,我已将 multiSelect 道具添加到 RadioGroup,只是为了好玩! 丹尼尔,你怎么看?

    class RadioOption extends React.Component {
        constructor(props) {
            super(props)
    
            this.onChange = this.onChange.bind(this)
        }
        render() {
            const { onChange, option: { description, ...restOptionProps }, ...restProps } = this.props
            return (
                <div className="custom-control custom-radio">
                    <input
                        type="radio"
                        className="custom-control-input"
                        onChange={this.onChange}
                        {...restProps}
                        {...restOptionProps}
                    />
                    <label className="custom-control-label" style={{ 'fontWeight': 'normal' }} htmlFor={this.props.option.id}>
                        <p>{description ? description : ""}</p>
                    </label>
                </div>
            )
    
        }
    
        onChange() {
            this.props.onToggle(this.props.option)
        }
    
    }
    
    
    class IPMRadioGroup extends React.Component {
        constructor(props) {
            super(props)
    
    
            this.onRadioOptionToggle = this.onRadioOptionToggle.bind(this)
            this.isChecked = this.isChecked.bind(this)
        }
        render() {
            return (
                <div className="radio-group-container">
                    {this.props.options.map(option => {
                        return (
                            <RadioOption checked={this.isChecked(option)} key={option.id} onToggle={this.onRadioOptionToggle} option={option} />
                        )
                    })}
                </div>
            )
        }
    
        isChecked(option) {
    
            return this.props.value.some(currentOption => option.id === currentOption.id)
    
        }
    
        onRadioOptionToggle(option) {
    
            let value = [].concat(this.props.value)
            let valueFound = false;
            let updatedValue = value.reduce((values, currentValue) => {
    
                if (currentValue.id === option.id) {
                    valueFound = true;
                    return values
                }
    
                if (!this.props.multiSelect) {
                    return values
                }
    
                return values.concat(currentValue)
            }, [])
    
            if (!valueFound) { updatedValue.push(option) }
            this.props.onChange(updatedValue)
    
        }
    
    }
    
    IPMRadioGroup.defaultProps = {
        value: [],
        multiSelect: false,
    }
    
    
    
    
    class Example extends React.Component {
    
        constructor(props) {
            super(props)
            this.state = {
                radioGroupValue: []
            }
            this.onRadioGroupChange = this.onRadioGroupChange.bind(this)
        }
    
        render() {
            return (
            <div>
                <IPMRadioGroup onChange={this.onRadioGroupChange} value={this.state.radioGroupValue} options={[
                    { description: 'test1', id: "uniqueId1", disabled: true },
                    { description: 'test2', id: "uniqueId2" },
                    { description: 'test3', id: "uniqueId3" },
                ]} />
                Current Selection {JSON.stringify(this.state.radioGroupValue)}
                </div>
            )
        }
    
        onRadioGroupChange(value) {
            this.setState({radioGroupValue:value})
        }
    
    }
    
    ReactDOM.render(<Example />, document.getElementById('example'))
    <script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.js"></script>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.js"></script>
    
    <div id="example"></div>

    作为旁注,我使用了一些很酷的 fauters,例如:

    我喜欢 prop-types 的用法!干杯!

    【讨论】:

      猜你喜欢
      • 2015-12-31
      • 1970-01-01
      • 2015-08-27
      • 1970-01-01
      • 2015-03-18
      • 2018-06-09
      • 1970-01-01
      • 2013-06-15
      • 2018-07-20
      相关资源
      最近更新 更多