2016-11-17 8 views
0

コンポーネントからgetBgColorファンクションへの自己呼び出し関数を渡します。WeatherForecastコンポーネントです。これは、子コンポーネントWeatherForecastから値を取得し、Appのコンポーネントに渡して、this.state.appColorClassを更新します。loop with componentDidUpdate

* getBgColor機能がありませんcomponentDidUpdate()ループを作成してブラウザをクラッシュします。この問題を解決する方法がわからない場合は、新しく反応してください。

export default class App extends Component { 
    constructor(props) { 
    super(props); 

    this.state = { appColorClass: 'app-bg1' }; 
    } 

    setAppColor(colorClass) { 
    alert("set className"); 
    this.setState({ appColorClass: colorClass }); 
    } 

    render() { 
    return (
    <div className={"app-container " + this.state.appColorClass}> 
     <div className="main-wrapper"> 

      <WeatherForecast getBgColor={color => this.setAppColor(color)} /> 

     </div> 
    </div> 
    ); 
    } 
} 


class WeatherForecast extends Component { 
    componentDidUpdate() { 
    console.log('Component DID UPDATE!') 
     //The function `setAppColor` from `App` component is passed into `getBgColor` 
     this.props.getBgColor(this.appColor(this.props.weather)); 
    } 

    appColor(weatherData) { 
    console.log("app color working"); 

    let temp = 0; 
    if (typeof weatherData === 'undefined' || weatherData === null) { 
     console.log(" initial Color went through"); 
     return 'app-bg1'; 
    } 
    temp = Math.round(weatherData.list[0].main.temp - 273.15); 
    if (temp <= -30) { 
     return "app-bg1"; 
    } 
    if (temp >= -29 && temp <= -21) { 
     return "app-bg2"; 
    } 
    if (temp >= -20 && temp <= -11) { 
     return "app-bg3"; 
    } 
    if (temp >= -10 && temp <= 4) { 
     return "app-bg4"; 
    } 
    if (temp >= 5 && temp <= 15) { 
     return "app-bg5"; 
    } 
    if (temp >= 16 && temp <= 24) { 
     return "app-bg6"; 
    } 
    if (temp >= 25 && temp <= 32) { 
     return "app-bg7"; 
    } 
    if (temp >= 33 && temp <= 38) { 
     return "app-bg8"; 
    } 
    if (temp >= 39) { 
     return "app-bg9"; 
    } 
    } 

    render() { 

    return (
     <div className="text-center col-xs-12"> 
     <h1 id="temp">{this.displayTemp(this.props.weather)}<sup>&deg;</sup></h1> 
     <h1>{this.displayCity(this.props.weather)}</h1> 
     </div> 
    ); 
    } 
} 
+1

weatherForecastにshouldComponentUpdateを追加し、this.props.weather === nextProps.weatherがfalseの場合はfalseを返します。または、何をしようとしているかに応じて、getBgColorの呼び出しをcomponentDidMountに移動して、一度だけ呼び出されるようにします。 –

+0

' this.setAppColor(color)} />'はちょうど ''であり、追加機能は不要です。 –

答えて

0

私はshouldComponentUpdateにプロパティの値に応じて、trueまたはfalseが返さジョニーKlironomosの提案と一緒に行くことになりました。

* this.props.weatherは、ユーザーが天気を表示するために都市を選択する必要があるため、アプリケーションが読み込まれると未定義です。

shouldComponentUpdate(nextProps) { 
    if(this.props.weather === 'undefined'){ 
     return true 
    } 
    return this.props.weather !== nextProps.weather 
    } 
1

WeatherForecastコンポーネントマウント(更新)した後、それはgetBgColorを呼び出し、子の更新を、トリガー親状態を設定getBgColor小道具を、呼び出し...そして、あなたが画像を取得するため、ループは再帰的です。

正直言って、論理を少し動かすことをお勧めします... weatherが小道具として渡されてから色が戻ってくるので、それは親の中でそれを扱うような "React"成分。データが下流に流れるときは、それに従う方が簡単です。要件を満たしていると仮定すると、setAppColorの簡単なチェックを追加すると問題が解決します。

setAppColor(colorClass) { 
    alert("set className"); 
    // only set state if it's changing 
    if (colorClass != this.state.appColorClass) { 
    this.setState({ appColorClass: colorClass }); 
    } 
} 
+0

私は、 'Weather'Firstcast'コンポーネントの中に' App'コンポーネントの 'state.weather'の別のmapStateToPropsがあります。これは、親に子のプロパティを渡す方法を学ぶために、学習経験/運動の多くでした。 setAppColorのifステートメントの提案に感謝します:) –