Jake.JS
Jake.JS

Reputation: 3446

react native this.setState will not re-render child component

I am trying to write a to-do app in react native. I have confirmed that the state that holds all todo's is receiving the to-do item added by the user. this.setState is not triggering a re-render. Anyone have any thoughts as to why? From what I have read this.setState should trigger a re-render.

var React = require('react-native');
var {
  AppRegistry,
  StyleSheet,
  Text,
  View,
  TextInput,
  TouchableHighlight,
  ListView
} = React;

var AwesomeProject = React.createClass({
  getInitialState: function(){
    return{
      toDos: ["hello world", "jake"]
    }
  },
  addToDo: function(todo){
    console.log(todo)  //this is printing the todo item added
    this.setState({
      toDos: this.state.toDos.concat([todo])
    });
    console.log(this.state.toDos) //this is printing state with item added
  },
  render: function() {
    return (
      <View>
        <Input addNew={this.addToDo} />
        <ToDos toDos={this.state.toDos} />
      </View>
    );
  }
});


var ToDos = React.createClass({
  getInitialState: function(){
    var ds = new ListView.DataSource({rowHasChanged: (r1, r2) => r1 !== r2});
    return {
      dataSource: ds.cloneWithRows(this.props.toDos)
    };
  },
  render: function(){
      return (
        <ListView dataSource={this.state.dataSource} renderRow={(rowData) => <Text>{rowData}</Text>}/>
      )
    }
});

var Input = React.createClass({
  getInitialState: function(){
      return {
        inputTxt: ''
      }
    },
    updateInput: function(e){
      this.setState({
        inputTxt: e.target.value
      });
    },
    handleAddNew: function(){
      this.props.addNew(this.state.inputTxt);
      this.setState({
        inputTxt: ''
      });
    },
    render: function(){
      return (
          <View>
            <Text> Input todo:
            </Text>
            <TextInput style={{height: 40, borderColor: 'gray', borderWidth: 1}} type="text" value={this.state.inputTxt} onChange={this.updateInput} onChangeText={(text) => this.setState({inputTxt: text})}/>
            <TouchableHighlight onPress={this.handleAddNew}><Text>Add Todo </Text></TouchableHighlight>
          </View>
      );
    }

});


var styles = StyleSheet.create({
  container: {
    flex: 1,
    justifyContent: 'center',
    alignItems: 'center',
    backgroundColor: '#F5FCFF',
  },
  welcome: {
    fontSize: 20,
    textAlign: 'center',
    margin: 10,
  },
  instructions: {
    textAlign: 'center',
    color: '#333333',
    marginBottom: 5,
  },
});

AppRegistry.registerComponent('AwesomeProject', () => AwesomeProject);

Any help with this would be greatly appreciated!

Upvotes: 1

Views: 4799

Answers (2)

Brackets
Brackets

Reputation: 514

Try

componentWillReceiveProps(nextProps) { 
   this.setState({ dataSource: dataSource.cloneWithRows(nextProps.toDos) 
}

Upvotes: 3

Looks like your ToDos component needs a componentWillReceiveProps method: https://facebook.github.io/react/docs/component-specs.html#updating-componentwillreceiveprops

Upvotes: 1

Related Questions