React-当父组件更改时更新子组件中的状态

时间:2019-09-19 10:06:55

标签: javascript asp.net-mvc reactjs react-native asp.net-core

我有一个具有两个react组件的简单应用程序:

  1. vacancies.jsx-列出空缺
  2. counter.jsx-显示vacancies.jsx中的空缺数量

当应用程序加载时,计数器会显示正确的空缺数量,但是当我开始在vacancies.jsx中添加/删除空缺时,计数保持不变。

vacancies.jsx:

export class Vacancy extends React.Component {

    constructor(props) {

        super(props);

        this.state = { vacancies: [], loading: true, title:"" };

        fetch('/api/Vacancy/Vacancies')
            .then(response => response.json())
            .then(data => {
                this.setState({ vacancies: data, loading: false });
            });
    }

    delete(id) {

        var vacancies = this.state.vacancies;

        this.setState(
            {
                vacancies: this.state.vacancies.filter((v) => {
                    return (v.id != id);
                })
            });

    }

    loadVacancies(vacancies) {
        return (
            <table className='table table-striped'>
                <thead>
                    <tr>
                        <th>Title</th>
                        <th>Min Salary</th>
                        <th>Max Salary</th>
                    </tr>
                </thead>
                <tbody>
                    {vacancies.map(v =>
                        <tr key={v.id}>
                            <td>{v.title}</td>
                            <td>{v.currency} {v.minSalary}</td>
                            <td>{v.currency} {v.maxSalary}</td>
                            <td>
                                <a href="#" onClick={(id) => this.delete(v.id)}>Delete</a>
                            </td>
                        </tr>
                    )}
                </tbody>
            </table>
        );
    }

    render() {

        let contents = this.state.loading
            ? <p><em>Loading...</em></p>
            : this.loadVacancies(this.state.vacancies);

        return (
            <div>
                {contents}
            </div>
        );
    }
}

const containerElement = document.getElementById('content');
ReactDOM.render(<Vacancy />, containerElement);

counter.jsx

import { Vacancy } from "./vacancies";

export class Counter extends Vacancy {

    constructor(props) {

        super(props);
    }

    render() {

        return (
            <div>
                <h1>Items:{this.state.vacancies.length}</h1>
            </div>
        );
    }
}

ReactDOM.render(<Counter />, document.getElementById('counter'));

用户界面: enter image description here

1 个答案:

答案 0 :(得分:2)

根据React小组的建议,他们建议使用合成代替继承:

  

React具有强大的组合模型,我们建议使用组合而不是继承来在组件之间重用代码。

  

在Facebook,我们在成千上万的组件中使用React,但还没有发现建议创建组件继承层次结构的用例。

https://reactjs.org/docs/composition-vs-inheritance.html

因此,根据您的代码,重新创建Counter组件,如下所示:

export const Counter = props => {
    return (
        <div>Items: {props.items}</div>
    );
};

然后只需更改您的Vacancies组件,包括在那里的新Counter组件:

loadVacancies(vacancies) {
    return (

        <Counter items={this.state.vacancies.length} />

        <table className='table table-striped'>
            <thead>
                <tr>
                    <th>Title</th>
                    <th>Min Salary</th>
                    <th>Max Salary</th>
                </tr>
            </thead>
            <tbody>
                {vacancies.map(v =>
                    <tr key={v.id}>
                        <td>{v.title}</td>
                        <td>{v.currency} {v.minSalary}</td>
                        <td>{v.currency} {v.maxSalary}</td>
                        <td>
                            <a href="#" onClick={(id) => this.delete(v.id)}>Delete</a>
                        </td>
                    </tr>
                )}
            </tbody>
        </table>
    );
}