首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >使用复选框响应嵌套组件

使用复选框响应嵌套组件
EN

Stack Overflow用户
提问于 2018-08-10 11:46:07
回答 1查看 1.7K关注 0票数 1

我有一个网站,其中包含十几个组件。

每个父组件包含大约5个其他组件。每5个组件都包含一个表单。

父组件有3个复选框。

1:扩展该服务中的所有组件(扩展所有组件),

2:分配该组件中的所有内容(全部分配),

3:展开组件(展开产品)。

每个子组件有两个复选框。

1:展开组件(也扩展产品),

2:分配组件中的所有内容(也分配所有)。

所有这些选项都适用于状态更改。他们都工作正常。问题是,当我单击“父”复选框时,无法取消选择子组件的单个组件。因此,我不能取消选中子组件中的复选框(子扩展产品或子组件分配所有)。

封闭元件

在母体上扩展产品

在父母中扩展产品,在孩子中扩展产品

在父中展开所有,在父中触发展开产品,在childs组件中触发展开产品。

下面是呈现父组件的第一个文件:

代码语言:javascript
复制
 class Offer extends React.Component {
 constructor(props){
    super(props);

    this.state = {
        checkedItems: new Map()
    };

    this.handleChange = this.handleChange.bind(this);
}

handleChange(e) {
    const item = e.target.name;
    const isChecked = e.target.checked;

    this.setState(prevState => ({
        checkedItems: prevState.checkedItems.set(item, isChecked)
    }));
}

render(){
    const { data, country_offer, country_offer_tab, countries, } = this.props;

    return (
        <div className="offer-wrapper">
            <div className={"offer-header " + data[2] }>
                <div>
                    <div className="custom_checkbox">
                        <div className="custom_checkbox">
                            <input
                                type={"checkbox"}
                                name={`${data[2]}_expand_all`}
                                className="expand_all"
                                checked={this.state.checkedItems.get(`${data[2]}_expand_all`) || false}
                                onChange={this.handleChange}
                                id={`${data[2]}_expand_all`}
                            />
                            <label htmlFor={`${data[2]}_expand_all`}>Expand all</label>
                        </div>
                        <div className="custom_checkbox">
                            <input
                                type={"checkbox"}
                                name={`${data[2]}_assign_all`}
                                className="assign_all"
                                checked={this.state.checkedItems.get(`${data[2]}_assign_all`) || false}
                                onChange={this.handleChange}
                                id={`${data[2]}_assign_all`}
                            />
                            <label htmlFor={`${data[2]}_assign_all`}>Assign all products</label>
                        </div>
                        <div className="custom_checkbox">
                            <input
                                type={"checkbox"}
                                name={`${data[2]}_expand_product`}
                                className="expand_product"
                                checked={( this.state.checkedItems.get(`${data[2]}_expand_product`) || this.state.checkedItems.get(`${data[2]}_expand_all`) ) || false}
                                onChange={this.handleChange}
                                id={`${data[2]}_expand_product`}
                            />
                            <label htmlFor={`${data[2]}_expand_product`}>Expand product</label>
                        </div>
                    </div>
                </div>
            </div>

            {
                (this.state.checkedItems.get(`${data[2]}_expand_all`) || this.state.checkedItems.get(`${data[2]}`+'_expand_product'))  &&
                    <CountryOffer
                        country_offer_tab={country_offer_tab}
                        countries={countries}
                        data={data}
                        expand_all={this.state.checkedItems.get(`${data[2]}_expand_all`)}
                        expand_product={this.state.checkedItems.get(`${data[2]}_expand_product`)}
                        assign_all={this.state.checkedItems.get(`${data[2]}_assign_all`)}
                    />
            }
        </div>
    )
}
}

export default Offer;

这是子组件

代码语言:javascript
复制
class CountryOffer extends React.Component{
constructor(props){
    super(props);

    this.state = {
        checkedItems: new Map(),
    };

    this.handleChange = this.handleChange.bind(this);
}

handleChange(e) {
    if (!this.props.expand_all){
        const item = e.target.name;
        const isChecked = e.target.checked;

        this.setState(prevState => ({
            checkedItems: prevState.checkedItems.set(item, isChecked)
        }));
    } else {
        console.log('cant uncheck/check this')
    }
}

render(){
    const { country_offer_tab, countries, data, expand_all, expand_product, assign_all} = this.props;
    return (
        <div className={"offer-details " + data[2]}>
            {country_offer_tab[data[2]].map((country, k) => {
                return (
                    <div key={k}>
                        <div className="offer-country-header" >
                            <div>
                                <span className={"iti-flag "+(countries[k].symbol).toLowerCase()}/>
                                <span>{countries[k].name}</span>
                            </div>
                            <div className='custom_checkbox'>
                                <input
                                    checked={assign_all ? assign_all : (this.state.checkedItems.get(`intersections_for ${data[2]}|${countries[k].id}`) || false)} onChange={this.handleChange}
                                    type="checkbox"
                                    name={"intersections_for "+ data[2] + '|' + countries[k].id}
                                    id={"intersections_for "+ data[2] + '|' + countries[k].id}/>
                                <label className="intersections_group_label" htmlFor={"intersections_for "+ data[2] + '|' + countries[k].id}>Check/uncheck all</label>
                            </div>
                            <div className='custom_checkbox'>
                                <input
                                    checked={expand_all ? expand_all : (this.state.checkedItems.get(`expand_geo ${data[2]}|${countries[k].id}`) || false)} onChange={this.handleChange}
                                    type="checkbox"
                                    name={"expand_geo " + data[2] + '|' + countries[k].id}
                                    id={"expand_geo " + data[2] + '|' + countries[k].id}/>
                                <label htmlFor={"expand_geo "+ data[2] + '|' + countries[k].id}>Expand GEO</label>
                            </div>
                        </div>

                        {
                            (expand_all || this.state.checkedItems.get(`expand_geo ${data[2]}|${countries[k].id}`)) &&
                                <CountryOfferIntersections
                                    country_offer_tab={country_offer_tab}
                                    offer_id={data[2]}
                                    country_id={countries[k].id}
                                    check_all={this.state.checkedItems.get(`intersections_for ${data[2]}|${countries[k].id}`)}
                                    assign_all={assign_all}
                                    expand_product={expand_product}
                                />
                        }
                    </div>
                )
            })}
        </div>
    )}
}

 export default CountryOffer;

我将非常感谢你的帮助

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2018-08-10 12:31:53

如果是true,则assign_all支持覆盖CountryOffer中的任何本地州。

代码语言:javascript
复制
checked={assign_all ? assign_all : ...

这是一个问题,没有一个单一的来源的真相。我将重构您的代码,以便CountryOffer是一个无状态组件,并将所有状态保留在父Offer组件中。

或者,将共享状态的管理完全从组件中删除。(例如,使用反应语境、redux、rxjs)

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/51785823

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档