【问题标题】:this.state with if else in React在 React 中使用 if else 的 this.state
【发布时间】:2022-10-02 14:20:53
【问题描述】:

我正在尝试 this.state 在构造函数中的 _app 文件的开头...

但是页面无法获取状态...

console.log response = null , 获取数据 , null

this.state 在渲染之前总是为空...

但是如果我使用: setstate 尽管 this.state 在构造函数中......页面加载没有这样的问题但是,这次的问题是页面加载多次导致 setstate..

我该如何处理......有什么想法吗?

import React                    from \'react\'

import thunk                    from \'redux-thunk\';
import logger                   from \'redux-logger\';
import Mystore                  from \'../store/store\';

import { Provider }             from \'react-redux\';
import { composeWithDevTools }  from \'redux-devtools-extension\';
import { compose,applyMiddleware,legacy_createStore as createStore} from \'redux\';

import AuthControl              from \'../Middleware/AuthControl\';

import MyLoading                from \'../components/loading\';
import Header                   from \'../components/Main/header\';
import Footer                   from \'../components/Main/footer\';

import Head                     from \'next/head\';
import App                      from \'next/app\'

import \'../styles/globals.css\';
export default class MyApp extends App {
constructor(props){
  super(props)
  const allEnhancers = compose(
    composeWithDevTools(
      applyMiddleware(thunk),
    )
  );

  var store   =   createStore(Mystore,allEnhancers);
  const checkLog  = async () => {
    const promt   = Promise.resolve(AuthControl());
    try {
      const value = await promt;
      this.setState((state)=> ({
        store       : store,
        Loginstatus : value.data,
        mobile      : (window.innerWidth <= 700),
        onLine      : window.navigator.onLine,
        loading     : (window.innerWidth <= 175),
      }))
    } catch (err) {
        this.setState((state)=> ({
          store       : store,
          Loginstatus : err,
          mobile      : true,
          onLine      : window.navigator.onLine,
          loading     : true,
        }))
    }
  }
if (typeof window !== \'undefined\') {checkLog();}
}
componentDidMount(){
  if (typeof window !== \'undefined\') {
    window.addEventListener(\'resize\'  , () => {
      this.setState((state)=> ({
        ...this.state,
        loading : (window.innerWidth < 175),
        mobile  : (window.innerWidth < 700)
    }));
    });
    window.addEventListener(\'online\'  , () =>
    this.setState((state)=> ({...this.state,onLine:window.navigator.onLine})));
    window.addEventListener(\'offline\' , () => 
    this.setState((state)=> ({...this.state,onLine:window.navigator.onLine})));
  }
}

render() {
const { Component, pageProps } = this.props;
if(this.state == null  || !Component || !pageProps || !this.state.onLine || this.state.loading || this.state.rendered != null){
return( 
  <>
  <Head>
  <title>Loading</title>
  <meta name=\"description\" content=\"Generated by Imtaki\" />
  <link rel=\"icon\" href=\"/favicon.ico\" />
  </Head>
  <MyLoading/>
  </>
)}
const {Loginstatus, mobile, store, loading}  = this.state;

console.log(\"123\",this.state);

return( 
  <Provider store={store}>
    <Head>
    <title>Imtaki</title>
    <meta name=\"description\" content=\"Generated by Imtaki\" />
    <link rel=\"icon\" href=\"/favicon.ico\" />
    </Head>
    <Header     logstatus={Loginstatus} winWidth={mobile}/>
    <Component  logstatus={Loginstatus} winWidth={mobile} {...pageProps} />
    <Footer     logstatus={Loginstatus} mobile={mobile} loc={\"body\"}/>
  </Provider>  
)
}}
  • 当您说“页面加载多次”时,您是什么意思?你的意思是你的渲染方法被调用了不止一次?这真的会导致问题吗?附言你有一些不必要的代码重复和this.setState 不需要传播...this.state
  • 我的意思是如果我在构造函数中使用 setstate,这次 console.log(\"123\") 在第一次加载时调用了多次......
  • 顺便说一句,哪些代码是重复的?
  • 您的活动之一是立即触发吗? RE 重复我的逻辑可能不完全正确,但我的意思是这样的:pastebin.mozilla.org/Dy1hRABD
  • 好的,我明白你的意思..谢谢你的建议......你也知道我的主要问题吗?

标签: reactjs


【解决方案1】:

不建议创建 React 组件的子类。见https://reactjs.org/docs/composition-vs-inheritance.html

正如@Dominic 所说,没有必要在setState 内传播this.state。不仅没有必要,而且还可能导致错误。例如:你可以这样做:

this.setState((state)=> ({
    mobile: (window.innerWidth <= 720 && !state.mobile)
});

当您需要使用之前的值更新状态时,请使用setState 的回调参数。这可以防止使用过时的状态值。见https://reactjs.org/docs/state-and-lifecycle.html#state-updates-may-be-asynchronous

onlineoffline 的事件侦听器保存在单独的方法中。不要忘记使用箭头函数或绑定。

componentDidMount 内执行addEventListener 而不是直接在构造函数内。

不要忘记在componentWillUnmount 回调中调用removeEventListener。因此需要将侦听器存储在单独的方法中。

【讨论】:

    猜你喜欢
    • 2021-01-11
    • 1970-01-01
    • 1970-01-01
    • 2019-04-25
    • 1970-01-01
    • 1970-01-01
    • 2020-01-27
    • 1970-01-01
    相关资源
    最近更新 更多