接收null不是对象(评估'this.state.search')

时间:2016-12-22 19:25:56

标签: javascript null react-native

我收到的null不是一个对象(评估'this.state.search')我是新来的反应原生,所以不是100%确定最新情况。谢谢你的帮助。

这是我的基本搜索栏:

use strict';

import React, { Component }                             from 'react';
import { StyleSheet, Text, View, TextInput, Button }    from 'react-native';
import renderIf                                         from '../common/renderIf';
import { Container, Header, Title, Content, Icon, CardItem, Card, Input, InputGroup} from 'native-base';




export default class SearchBar extends Component {



  render() {
    return (
                <Card> 
                    <CardItem searchBar rounded>                      
                        <InputGroup>
                            <Icon name="ios-search" />
                            <Input placeholder="Search" value={this.state.search} onChangeText={(text) => this.setState({search:text})} onSubmitEditing={()=>this.search()}/>
                        </InputGroup>
                    
                    </CardItem>
                </Card>
    );
  }
}

这是从搜索栏中获取输入的文本并显示结果:

'use strict';

import React, { Component }                             from 'react';
import { StyleSheet, Text, View, TextInput, Button }    from 'react-native';
import renderIf                                         from '../common/renderIf';
import { Container, Content, Icon, CardItem, Card, Thumbnail, Title, List, ListItem} from 'native-base';
import { Col, Row, Grid }                               from "react-native-easy-grid";

export default class AddMovieResults extends Component {

    search() {   
    // Set loading to true when the search starts to display a Spinner        
    this.setState({            
        loading: true          
    });

    var that = this;        
    return fetch('http://www.omdbapi.com/?s=' +this.state.search)       
    .then((response) => response.json())            
    .then((responseJson) => {      
        // Store the results in the state variable results and set loading to                 
         // false to remove the spinner and display the list of repositories                
          that.setState({                    
        results: responseJson,                    
        loading: false                
    });
    return responseJson.Search;            
}) 
    .catch((error) => {
        that.setState({                    
        loading: false                 
    });
        console.error(error);        
    });    
}


  render() {
    return (

                    <Card scrollEnabled={true}> 
                        <CardItem button >  

                           <List dataArray={this.state.results.items} renderRow={(item) =>               
                                <ListItem button >
                                <Row> 

                                  <Col size={1}>
                                    <Thumbnail square style={{ height: 90, width:60, bottom:6,justifyContent: 'center',}} source={{uri: item.poster}} /> 
                                  </Col>  

                                  <Col size={3}>
                                    
                                    <Row size={3}> 
                                    <Text style={{ fontSize: 25, color: '#DD5044',justifyContent: 'center',}}>{item.title}</Text>      
                                    </Row>

                                    <Row size={1}>
                                    <Text style={{ fontSize: 15, color: '#DD5044',}}>{item._year_data}</Text>    
                                   </Row>
                                   
                                   </Col>
                                  </Row>  
                                </ListItem>                            
                            } />
                        </CardItem>
                    </Card> 
    );
  }
}

这是我的索引文件,它在一个页面上显示上述文件:

'use strict';

import React, { Component }                             from 'react';
import { StyleSheet, Text, View, TextInput, Button }    from 'react-native';
import renderIf                                         from '../common/renderIf';
import { Container, Header, Title, Content}             from 'native-base';
import { Col, Row, Grid }                               from "react-native-easy-grid";

import AddMovieResults                                  from './AddMovieResults';
import SearchBar                                        from './SearchBar';


export default class AddNewMovie extends Component {




  render() {
    return (
        <Container scrollEnabled={false}>
            <Header>
                <Title> Add Movie</Title>
            </Header>
            <Content>
        <Grid>
            <Col>
            {/* import search bar */}
                <SearchBar/>
            {/*import search results*/}
                <AddMovieResults/>
            </Col>
        </Grid>
            </Content>
        </Container>
    );
  }
}

2 个答案:

答案 0 :(得分:0)

状态不是全局的,它是每个组件的本地,因此您需要将其作为道具传递给对象。

然而,问题在于,当您定义搜索栏并添加电影结果时,您需要找到一种方法从SearchBar传回状态。

要完成此操作,您可以传递一个引用函数来更新AddNewMovie的状态:

将以下函数添加到addNewMovie类:

&#13;
&#13;
updateAddNewMovieState = (newData) => {
	this.setState({search:newData})
}
&#13;
&#13;
&#13;

接下来将其传递到搜索栏类:

&#13;
&#13;
<SearchBar
  updateState = {this.updateAddNewMovieState}
  currentState = {this.state.search}
/>
&#13;
&#13;
&#13;

现在使用this.props.currentState来访问搜索状态,使用this.props.updateState(newState)来修改AddNewMovie中搜索栏类的状态。

最后,将变量传递给AddMovieResults:

&#13;
&#13;
<AddMovieResults
  search={this.state.search}
/>
&#13;
&#13;
&#13;

然后,您可以通过this.props.search。

访问AddMovieResults中的变量

虽然这种方法相对简单,但如果您传递许多变量,它很快就会变得复杂,为此我建议使用https://github.com/reactjs/react-redux,它允许您通过动作函数和缩减状态更清晰地存储变量。

我还建议在每个组件构造函数中定义状态变量,以便在定义它们时更清楚:

&#13;
&#13;
constructor(props) {
    super(props);

    this.state = {
      something: "Something"
    };
  }
&#13;
&#13;
&#13;

答案 1 :(得分:0)

你需要在构造函数中绑定你的函数,以便能够在继承的React类函数之外访问this,如renderconstructor等......:

export default class AddMovieResults extends Component {
    constructor(props){
         super(props);
         this.search = this.search.bind(this);
    }
    search() {   
    // Set loading to true when the search starts to display a Spinner        
        this.setState({            
            loading: true          
        });
    }
    ...
    ...
}