簡體   English   中英

setState 后組件不會重新渲染

[英]Component not re-rendering after setState

import Header from './components/Header';
import Bio from './components/Bio';
import styled from 'styled-components';
import Photo from './components/Photo';

class App extends Component {

  constructor(props) {
    super(props);

    this.state = {
      name: "John Smith",
      job: "Noob Developer",
      email: "John@Smith.noob",
      university: "Harvard University",
      study: "Law",
      year: "2020",
      experience: ["Google","Facebook","Airbnb"],
      input: false,
    }

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

  switchShow () {
    this.setState( prevState => ({
      input: !prevState.input
    }))
    console.log(this.state.input)
  }

  render() {


    let {name,job,email,university,study,year,experience,input} = this.state

    return(
      <div className="App">
      <Header/>

      

      <FlexRowContainer>
      <EditButton onClick={this.switchShow}>Edit</EditButton>
      <Photo/>
      <Bio name={name} job={job} email={email} school={university} study={study} year={year} experience={experience} input={input}>
      </Bio>
      </FlexRowContainer>

    </div>
    )
  }
}


export default App;

const FlexRowContainer = styled.div`
  display: flex;
  width: 100%;
  flex-direction: row;
  justify-content: center;
`
const EditButton = styled.button`
float: right;
width: auto;
height: auto;
position: absolute;
border: transparent;`

所以我嘗試使用 switchShow 方法更改 this.state.input 並且在更改之后組件沒有呈現,即使當我 console.log(this.state.input) 它成功地從 false 更改為 true 或再次單擊時它會更改又從真到假。 有什么不對的嗎?

生物成分在這里

import styled from 'styled-components'

class Bio extends Component {
    constructor(props) {
        super(props)

        this.state = {
            name: this.props.name,
            job: this.props.job,
            email: this.props.email,
            school: this.props.school,
            study: this.props.study,
            yearClass: this.props.year,
            experience: this.props.experience,
            input: this.props.input,
        };

    }

    render() {

        let {name,job,email,school,study,yearClass,experience,input} = this.state


        return (
            <div>
            <StyledBioContainer>
                <StyledSubtitle>Name</StyledSubtitle>
                { !input ? <StyledParagraph>{name}</StyledParagraph> : <input></input>}
                <StyledSubtitle>Job</StyledSubtitle>
                { !input ? <StyledParagraph>{job}</StyledParagraph> : <input></input>}
                <StyledSubtitle>Email</StyledSubtitle>
                { !input ? <StyledParagraph>{email}</StyledParagraph> : <input></input>}
                <StyledSubtitle>School</StyledSubtitle>
                { !input ? <StyledParagraph>{school}</StyledParagraph> : <input></input>}
                <StyledSubtitle>Title of Study</StyledSubtitle>
                { !input? <StyledParagraph>{study}</StyledParagraph> : <input></input>}
                <StyledSubtitle>Class</StyledSubtitle>
                { !input? <StyledParagraph>{yearClass}</StyledParagraph> : <input></input>}
                <StyledSubtitle>Experiences</StyledSubtitle>
                { !input? experience.map(experience => <StyledParagraph>{experience}</StyledParagraph>) : <input></input>}
            </StyledBioContainer>
            </div>
        )
    }
}

export default Bio;


const StyledBioContainer = styled.div`
display: flex;
font-family: Cambria, Cochin, Georgia, Times, 'Times New Roman', serif;
flex-direction: column;
width: 100%;
padding: 3rem;
color: black;
height: auto;
background-color: rgba(0,105,255,.05);
text-align: center;
border-radius: 3px;
margin-top: 1.5rem;
`

const StyledSubtitle = styled.h6`
font-family: Verdana, Geneva, Tahoma, sans-serif;
font-size: 12px;
margin-top: 10px;
margin-bottom: 0px;
color: gray;
`

const StyledParagraph = styled.p`
margin-top: 0.75rem;
margin-bottom: 5px;
font-size: 20px;

問題是在 Bio 組件中,您將 props 分配給構造函數中的狀態變量,然后對 Bio 的狀態進行條件渲染。 創建組件時,它獲取 props 並將它們分配給 state,但是當您更改 props 時,永遠不會再次調用構造函數。

您可以跳過從 props 設置狀態並在渲染中使用 props,或者如果您想使用類組件,您可以調用 componentDidUpdate,並使用新的 props 更新您的狀態。

這是在 Bio 組件中使用 props 而不是 state 進行條件渲染的工作示例

https://codesandbox.io/s/focused-rosalind-8rnih?file=/src/Bio.jsx

問題來自您的<Bio />組件沒有監聽道具更改以更新其內部狀態。

您可以通過將其添加到您的<Bio />組件來解決此問題:

componentDidUpdate(prevProps) {
    if (this.props.input !== prevProps.input)
      this.setState({input: this.props.input})
}

這是一個完整的例子: https : //stackblitz.com/edit/react-vums1a?file=src/App.js

編輯:在我打字時沒有看到 @szczocik 的答案,但您也可以建議不要在<Bio />使用不同的狀態,而是使用道具。 它將獲得相同的結果,但您將失去<Bio />的本地狀態,因此這實際上取決於您是否首先需要一個。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM