我正在使用react-redux。
我有以下JSX(仅包含相关的片段):
getQuestionElement(question) {
if (question) {
return <MultiChoice questionContent={this.props.question.question} buttonClicked={this.choiceClicked} />
}
else {
return (
<div className="center-loader">
<Preloader size='big' />
</div>
)
}
}
render() {
return (
<div>
<Header />
{
this.getQuestionElement(this.props.question)
}
</div>
)
}
function mapStateToProps({ question }) {
return { question };
}
export default connect(mapStateToProps, questionAction)(App);
当动作触发时,减速器更新问题支柱
this.props.question
我期待
{this.getQuestionElement(this.props.question)}
重新加载并提出新问题。
然而,这并没有发生。我不能以这种方式放置一个函数来重新加载它吗?
我的MultiChoice组件:
import React, { Component } from 'react';
import ReactHtmlParser from 'react-html-parser';
import './questions.css';
class MultiChoice extends Component {
constructor(props) {
super(props);
this.state = {
question: this.props.questionContent.question,
answerArray : this.props.questionContent.answers,
information: null
}
this.buttonClick = this.buttonClick.bind(this);
}
createButtons(answerArray) {
var buttons = answerArray.map((element) =>
<span key={element._id} onClick={() => { this.buttonClick(element._id) }}
className={"span-button-wrapper-25 " + (element.active ? "active" : "")}>
<label>
<span>{element.answer}</span>
</label>
</span>
);
return buttons;
}
buttonClick(id) {
var informationElement;
this.props.buttonClicked(id);
var buttonArray = this.state.answerArray.map((element) => {
if (element._id === id ){
element.active = true;
informationElement = element.information;
return element;
}
else{
element.active = false;
return element;
}
});
this.setState({
answerArray: buttonArray,
information: informationElement
})
}
render() {
return (
<div className="question-container">
<div className="question-view">
<div className="icon-row">
<i className="fa fa-code" />
</div>
<div className="title-row">
{this.state.question}
</div>
<div className="button-row">
{this.createButtons(this.state.answerArray)}
</div>
<div className="information-row">
{ReactHtmlParser(this.state.information)}
</div>
</div>
</div>
);
}
}
export default MultiChoice;
QuestionAction.js
import axios from "axios";
import { FETCH_QUESTION } from "./types";
export const fetchQuestion = (questionId, answerId) => async dispatch => {
let question = null;
if (questionId){
question = await axios.get("/api/question/next?questionId=" + questionId + "&answerId=" + answerId);
}
else{
question = await axios.get("/api/question/next");
}
console.log("question", question);
dispatch({ type: FETCH_QUESTION, payload: question });
};
questionReducer.js
import {FETCH_QUESTION } from "../actions/types";
export default function(state = null, action) {
switch (action.type) {
case FETCH_QUESTION:
console.log("payload", action.payload.data);
return { question: action.payload.data, selected: false };
default:
return state;
}
}
index.js(Combined Reducer)
import { combineReducers } from 'redux';
import questionReducer from './questionReducer';
export default combineReducers({
question: questionReducer
});
和我的切入点: index.js
const store = createStore(reducers, {}, applyMiddleware(reduxThunk));
ReactDOM.render(
<Provider store={store}>
<App />
</Provider>,
document.getElementById('root')
);
registerServiceWorker();
请求console.log响应:
render() {
console.log("Stackoverflow:", this.props.question)
.....
并在单击按钮(和reducer更新后,console.log更新,但
this.getQuestionElement(this.props.question)
无法重新渲染
答案 0 :(得分:0)
MultiChoice组件不应该将props
存储在构造函数中的state
中,这里有2个选项:
处理propsWillReceiveProps中的道具更改以更新状态:
class MultiChoice extends Component {
constructor(props) {
super(props);
this.state = {
question: this.props.questionContent.question,
answerArray : this.props.questionContent.answers,
information: null
}
this.buttonClick = this.buttonClick.bind(this);
}
componentWillReceiveProps(nextProps) {
this.setState({
question: nextProps.questionContent.question,
answerArray : nextProps.questionContent.answers,
information: null
});
}
我们必须继续使用构造函数来设置初始状态,如docs:
React不会使用初始道具调用componentWillReceiveProps() 在安装过程中。
第二个选项:将其设为&#34;哑组件&#34;没有state
并且仅使用他的props
来渲染某些内容(要在您的组件中做一些更深层的更改,尤其是处理&#34; active&#34;元素,它将必须由父组件处理。)