2017-09-02 2 views
0

まず、私はReact NativeとShoutemのトータルノブです。私は私の質問の主題でShoutemまたはReact Nativeを書くべきかどうか分からないが、ここに私の問題がある。Shoutemのフェッチデータが表示されない

私は2つの画面があります。

  1. Screen1.js
  2. Screen2.js

を画面1は、フェッチから返されたアイテムのリストが表示されます。アイテムをクリックすると、詳細画面である第2画面が開きます。

私はscreen1からscreen2にデータを渡しています。 screen2では、私は別のデータの別のフェッチ呼び出しを行う必要がありますが、動作しません。私は両方の画面でまったく同じことをやっています。ここで

は、画面1のために私のコードです:

import React, { 
    Component 
} from 'react'; 

import { 
    ActivityIndicator, 
    TouchableOpacity 
} from 'react-native'; 

import { 
    View, 
    ListView, 
    Text, 
    Image, 
    Tile, 
    Title, 
    Subtitle, 
    Overlay, 
    Screen 
} from '@shoutem/ui'; 

import { 
    NavigationBar 
} from '@shoutem/ui/navigation'; 

import { 
    navigateTo 
} from '@shoutem/core/navigation'; 

import { 
    ext 
} from '../extension'; 

import { 
    connect 
} from 'react-redux'; 

export class List extends Component { 
    constructor(props) { 
    super(props); 
    this.renderRow = this.renderRow.bind(this); 
    this.state = { 
     isLoading: true, 
     content: null, 
    } 

    } 

    componentDidMount() { 
    return fetch('https://www.cannabisreports.com/api/v1.0/strains').then((response) => response.json()).then((responseData) => { 
     this.setState({ 
     isLoading: false, 
     content: responseData 
     }); 
    }).done(); 
    } 

    renderRow(rowData) { 
    const { navigateTo } = this.props; 

    return (
     //<Text>{rowData.name}, {rowData.createdAt.datetime}</Text> 
     <TouchableOpacity onPress={() => navigateTo({ 
      screen: ext('Strain'), 
      props: { rowData } 
     })}> 
      <Image styleName="large-banner" source={{ uri: rowData.image && 
      rowData.image ? rowData.image : undefined }}> 
      <Tile> 
       <Title>{rowData.name}</Title> 
       <Subtitle>none</Subtitle> 
      </Tile> 
      </Image> 
     </TouchableOpacity> 
    ); 
    } 

    render() { 
    if (this.state.isLoading) { 
     return (
     <View style={{flex: 1, paddingTop: 20}}> 
      <ActivityIndicator /> 
     </View> 
    ); 
    } 

    return (
     <View style={{flex: 1, paddingTop: 20}}> 
     <ListView 
      data={this.state.content.data} 
      renderRow={rowData => this.renderRow(rowData)} 
     /> 
     </View> 
    ); 
    } 
} 

// connect screen to redux store 
export default connect(
    undefined, 
    { navigateTo } 
)(List); 

私はScreen2ににrowDataを渡しています。私はrowDataのデータを使って別のフェッチ呼び出しを行う必要があります。これは、Screen2のAPI呼び出しに必要なパスパラメーターです。

だから、基本的に私はこのようにScreen2にしてフェッチを呼び出す行う必要があります。ここでは

fetch('https://mywebsite.com/'+rowData.something+'/myotherdata') 
     .then((response) => response.json()) 
     .then((responseJson) => { 
     this.setState({ 
      content: responseJson.data 
     }) 
     }) 
     .catch((error) => { 
     console.error(error); 
     }); 

がScreen2にのために私のコードです:

export default class Strain extends Component { 

    constructor(props) { 
    super(props); 
    this.state = { 
     content: null, 
    } 
    } 

    componentDidMount() { 
    return fetch('https://mywebsite.com/'+rowData.something+'/myotherdata') 
     .then((response) => response.json()) 
     .then((responseJson) => { 
     this.setState({ 
      content: responseJson.data 
     }) 
     }) 
     .catch((error) => { 
     console.error(error); 
     }); 
    } 

    renderRow(dataContent) { 
    return (
     <Text>{dataContent.name}</Text> 
     // This does not work either -> <Text>{dataContent}</Text> 
    ); 
    } 

    render() { 
    const { rowData } = this.props; //This is coming from screen1.js 

    return (
     <ScrollView style = {{marginTop:-70}}> 
     <Image styleName="large-portrait" source={{ uri: rowData.image && 
     rowData.image ? rowData.image : undefined }}> 
      <Tile> 
      <Title>{rowData.name}</Title> 
      <Subtitle>{rowData.createdAt.datetime}</Subtitle> 
      </Tile> 
     </Image> 

     <Row> 
      <Text>Seed Company: {rowData.seedCompany.name}</Text> 
     </Row> 

     <Divider styleName="line" /> 

     <Row> 
      <Icon name="laptop" /> 
      <View styleName="vertical"> 
      <Subtitle>Visit webpage</Subtitle> 
      <Text>{rowData.url}</Text> 
      </View> 
      <Icon name="right-arrow" /> 
     </Row> 

     <Divider styleName="line" /> 

     <View style={{flex: 1, paddingTop: 20}}> 
      <ListView 
      data={content} 
      renderRow={dataContent => this.renderRow(dataContent)} 
      /> 
     </View> 

     <Divider styleName="line" /> 

     </ScrollView> 
    ); 
    } 
} 

は、このようなURLを返すデータをフェッチマイ

{ 
    data: { 
    name: "7.5833", 
    another_name: "8.6000", 
    different_name: "5.7500", 
    } 
} 

これは、上記のような1つのデータオブジェクトのみを返します。 null is not an object (evaluating 'Object.keys(e[t])')

は、あなたがより多くの情報を提供するために、私が必要な場合は私に知らせてください。私は、コードを実行すると

は、私はこのエラーを取得します。

私は非常に多くのものを試しましたが、何も動作しないように見えるので、私はいくつかの助けが必要です。私は間違って何をしていますか?

+1

あなたは 'Object.keys(e [t]) 'というコードを知っていますか?そうでなければ、あなたのブラウザのdevtoolsを見て、それを理解する必要があります。また、質問の 'render()'コードがあなたのフェッチ呼び出しにどのように関係しているのかは明らかではありません。実際に 'render()'を呼び出すコードはどこですか? 'this.setState({ content:responseJson。データ }、function(){ //新しい状態で何かを実行する }); //新しい状態で何かを実際に呼び出すコードは何ですか?それはその質問の残りのコードとどのように関連していますか? – sideshowbarker

+0

@iamthestreetsどこにこのエラーがありますか?小さなコードのエラーのように見えるので、言いにくいです。デバッグビルドを実行して、よりフレンドリーなエラーを取得してみてください。私があなたの 'ListView'に正しい' content'を与えていないと言うことができます。 'this.state.content'を渡すか、' const {content} = this.state; 'をレンダリング関数の第1行として渡します。第1のアプローチ(第2のアプローチ)を破棄し、 'content'が利用できない場合、プレースホルダーをレンダリングすることがベストプラクティスです。 – dodsky

+0

Shoutem Builderを使用してアプリケーションを実行しているので、エラーが表示される唯一の方法です。 @sideshowbarker 'function(){//新しい状態で何かする}'を削除しましたが、それは必要ありません。どのようなコードが 'render()'を呼び出すのかがわかりません。画面がロードされると 'render()'が呼び出されます。 – iamthestreets

答えて

0

なぜこれが機能するのか分かりませんが、

私はfetch私のデータに関数を使用して、このようcomponentDidMountで関数を呼び出す:

その後
getData() { 
    return fetch('https://mywebsite.com/myotherdata') 
     .then((response) => response.json()) 
     .then((responseJson) => { 
     this.setState({ 
      data: responseJson.data 
     }); 
     }) 
     .catch((error) => { 
     console.error(error); 
     }); 
    } 

    componentDidMount() { 
    this.getData(); 
    } 

はJSONレスポンスから値を取得するために、私は、このやっている: this.state.data.name

Iを別の問題を抱えていますが、別の質問を作成します。

関連する問題