Search code examples
javascriptreactjsreact-nativereact-state-management

How to reset state in children class component at the same time with parent component in React Native?


I'm a newbie in React Native and struggling in cleaning up the state of the children component at the same time with the parent.

What I'm trying to do is:

  1. After navigating from MainMap.js to the last screen TripsListScreen.js (the whole process is a Stack of 4 screens, nested in a Drawer), I got all the data stored in Redux's store, and display it in TripsListScreen.
  2. I then press the add button to create new trips. I successfully reset the state at the MainMap. However, the states ( value prop of TextInput) in the PlaceInput component is still there. How can we reset that also ?

Here's the MainMap.js 's states:

const initialState = {
    hasMapPermission: false,
    _userLocationDisplayed: null,
    userLatitude: 0,
    userLongitude: 0,
    initial_UserLatitude: 0,
    initial_UserLongitude: 0,
    userLocationAddress: '',

    destination: [],
    destinationName: [],
    destinationAddress: [],
    destinationCoords: [],
    destinationImageUri: [],

    numOfInput:[0,1],
    counter: 1,
    wayPoints: [],
    markers: [],

    doCleanState: 'no' // Right here I want to pass the prop from PlaceInput as this.state.doCleanState
};
const cleanUpState = {
    hasMapPermission: false,

    destination: [],
    destinationName: [],
    destinationAddress: [],
    destinationCoords: [],
    destinationImageUri: [],

    numOfInput:[0,1],
    counter: 1,
    wayPoints: [],
    markers: [],

    doCleanState: 'yes'
}

class MainMap extends React.Component{

    constructor(props){
        super(props);
        this.state = initialState;
    };


    componentDidMount(){
        console.log('Hello',this.props);
        console.log('This is state', this.state);
        this._requestUserLocation();
        this._unsubscribe = this.props.navigation.addListener('focus', () => {
            this.setState(cleanUpState);

        })
    };

    componentWillUnmount(){
        Geolocation.clearWatch(this.watch_location_id);
        this._unsubscribe();

    }

   render(){
      return(
        //...
        <PlaceInput
            id={itemData}

            defaultValue={this.state._userLocationDisplayed}
            displayDefaultValue={!index}
            doCleanState={this.state.doCleanState}
       />
  );
}

Basically, I've tried to pass a prop from the PlaceInput as a state in MainMap. When resetting the MainMap's states( the state of doCleanState also changes, not reset), the states of PlaceInput doesn't reset

Here's PlaceInput:

//...
class PlaceInput extends React.Component{

    constructor(props){
        super(props);
        this.state={
            predictions: [],
            destinationInput: '',
        }
    }

    componentDidUpdate(prevProps){
        if(this.props.doCleanState !== prevProps.doCleanState){
            this.setState({
                destinationInput: '',
            })
        }
    }

    render(){
        return(
            <TextInput 
                key={this.id}

                placeholder='Search your places'

                onChangeText={(input) => {
                    this.setState({destinationInput: input});
                    this.getPlacesDebounced(input);
                }}
                value={this.props.displayDefaultValue ? this.props.defaultValue : this.state.destinationInput} // props.defaultValue is state of MainMap : 'Your location'
                             // destinationInput is what the users type

             />
   );
}
//...

When I navigate back to MainMap the destinationInput state is still there in the PlaceInput

Problem

PLEASE HELP !!!


Solution

  • In PlaceInput component, pass props value to parent where you want,

    class PlaceInput extends React.Component{
    
        //... your code method
        this.props.updateClean("") // pass your value to parent
    
    }
    

    Then in MainMap component,

    <PlaceInput
            id={itemData}
    
            defaultValue={this.state._userLocationDisplayed}
            displayDefaultValue={!index}
            doCleanState={this.state.doCleanState}
            updateClean={(text)=> setState({doCleanState:text})} // <-- change like this. 
       />