2015-04-14 33 views
16

我正在開發一個使用React Native的簡單待辦事項列表應用程序,我的問題如下:我的項目根目錄中有一個NavigatorIOS,其中包含一個包含ListView的組件路線和一個導航欄按鈕,導致任務創建視圖。在同級視圖之間React Native Pass數據

一旦創建了新任務,視圖就會彈出,以便顯示ListView。我試圖將我新創建的任務添加到此ListView(其數據源包含在組件狀態中)。

如何執行這樣的操作,有什麼好的做法?我會在純原生應用程序中使用委託,但在這裏,這兩個視圖都由NavigatorIOS實例處理。

index.ios.js

addTask() { 
    console.log("Test"); 
}, 

render() { 
     return (
      <React.NavigatorIOS 
       ref="nav" 
       style={styles.container} 
       tintColor="#ED6063" 
       initialRoute={{ 
        title: "Tasks", 
        component: TasksList, 
        rightButtonTitle: 'Add', 
        onRightButtonPress:() => { 
         this.refs.nav.navigator.push({ 
          title: "New task", 
          component: NewTask, 
          passProps: { 
           onTaskAdded: this.addTask 
          }, 
          leftButtonTitle: "Cancel" 
         }); 
        } 
       }}/> 
     ); 
    } 

NewTask.js

taskAdded() { 
console.log("Added: " + this.state.title + " - " + this.state.description); 
this.props.onTaskAdded({ 
    title: this.state.title, 
    description: this.state.description 
}); 
this.props.navigator.pop(); 
} 

TasksList.js

var dataSource = new ListView.DataSource({ 
    rowHasChanged: (r1, r2) => r1 !== r2 
}); 
this.state = { 
    dataSource: dataSource.cloneWithRows(data) 
}; 

您可以找到complete source code here

回答

0

您應該重寫您的constructor函數以從動態方式獲取數據。然後當頁面重新加載時,它會得到一個包含新任務的正確數據。在這裏你從一個靜態數組中獲得數據,這個數組不會改變。

將任務列表保存到本地文件或Firebase,並在構建時讀取。

+0

所以你建議用某種巨大的全局變量/面積與視圖之間傳遞數據?這聽起來像極壞的架構...... – Blackus

+0

@Blackus否則,你如何獲得任務列表? 「全球」是可選的。 – KChen

+0

這裏就是這一點。在開發本機時,我們可以使用協議或傳遞代碼塊來執行(如回調)。所以任務列表只與這兩個視圖「共享」,它與其他事物並不存在很大的共同點。 – Blackus

15

React-Native文檔包含有關communicating between components方法的簡要部分。

當你試圖做一些事情比父 - >兒童或兒童安全>父母關係比較複雜,有幾個選項:

  1. 管理模式。對於真正的兄弟姐妹< - >兄弟姐妹通信(即兩個兄弟姐妹通過組合共享父母的地方),您可以讓父母管理該狀態。例如,您可能有一個<MyConsole>小部件,其中包含<TextInput><ListView>,其中包含用戶過去的輸入,它們都是<Console>小部件的子項。

    • 在這裏,<Console>可以充當經理。當<TextInput>更改其值時,可以使用onChangeText事件將新值傳遞給父代<MyConsole>組件,該組件將更新其狀態並將其傳遞給子組件。
  2. 事件(發佈 - 訂閱)模式。請記住,組件只是對象,因此您可以使用面向對象的方法在組件之間進行通信。 React文檔注意:

    對於沒有父子關係的兩個組件之間的通信,您可以設置您自己的全局事件系統。在收到事件時,訂閱componentDidMount()中的事件,取消訂閱componentWillUnmount(),並調用setState()。

    • 在這裏,你可以像使用pubsub.js一個簡單的發佈 - 訂閱庫,這樣,當一個組件改變它只是出版的變化和其他相關部件可以監聽的事件和自我更新。這對小型應用程序來說可能是一種非常有效的方法
  3. 通量模式。純粹的發佈/訂閱系統的一個缺點是,跟蹤狀態變得困難。舉例來說,如果你有2個組件(例如EditTitle,EditBody),它可以同時更新如電子郵件消息的一些狀態,那麼一個純粹的事件系統最終通過不同的版本狀態的周圍會導致混亂與衝突,因爲沒有「單版本的真相「。這是陣營的flux approach用武之地。用焊劑,部件更新的數據存儲器,其負責更新和協調數據(例如EmailDataStore),並且在商店然後通知更新的狀態的部件。

    • 因此,在你的榜樣,任務視圖將發出一個更新(例如通過發佈或直接函數調用)的TasksDataStore,那麼這可能會發佈一個事件像tasks-updated它的用戶。任務面板和結果面板都會訂閱數據存儲。

當設置訂閱,這是最好的組件坐騎後添加訂閱和絕對分量卸裝前刪除它們(否則你最終得到了很多孤兒訂閱)。

+0

TKS @tohster,你是對的,建立一個全球性的事件系統是最好的方式,但我是新來的反應本地的,我不知道如何使一個全球性的事件系統的反應本地。 – backslash112