2016-03-27 57 views
1

我是REDX世界的新手,我試圖製作報紙應用程序。我目前正在研究用戶可以搜索特定報紙標題的搜索功能。問題是,當我第一次輸入'a'時,狀態是''。而當我輸入更多,例如'b'時,狀態表明當它應該是'ab'時,該術語是'a'。我正在使用redux chrome工具來檢查這個全局狀態。Redux/React - 搜索字段沒有立即更新REDX狀態

我Actioncreator是非常簡單(只返回傳遞給它的術語):

export function search(term) { 
    return{ 
    type:SEARCH, 
    term 
    } 
} 

這裏是減速機:

const SearchReducer = (state = '', action) => { 

    switch (action.type) { 
     case SEARCH: 
      return action.term; 
     default: 
      return state; 
    } 

} 

這裏是根減速機:

/*Application state*/ 
const rootReducer = combineReducers({ 
    weather: WeatherReducer, 
    filters: FilterReducer, 
    articles:ArticleReducer, 
    search: SearchReducer // this should be 'ab', but is 'a' 
}); 

這是非常簡單的設置。以下是我如何與redux溝通。

我有我的材料UI文本框(我試過香草輸入字段太)

<TextField style={style.searchWidget.search} 
      floatingLabelText="Search" 
      value={this.state.term} 
      onChange={this._onSearchChange} 
/> 

當用戶鍵入的東西的_onSearchChange func被解僱。

_onSearchChange(event) { 
    this.setState({term: event.target.value}); 
    this.props.search(this.state.term); 
} 

這將設置此搜索組件的當前狀態。然後它將調度將更新全局狀態的搜索操作。但不能正常工作。全球國家總是落後一步。

有什麼想法?

編輯: 它看起來不是重複但反應。組件狀態不會立即更新。正確的術語被傳遞給actionreducer,所以它不是redux的錯。設置狀態後,我試圖打印出this.state.term。而且看起來狀態並未更新。

回答

1

其實它與redux無關。在處理反應時,您必須記住,只要您更新反應狀態,就無法獲得更新的狀態。我們舉個例子吧。

getInitialState: function() { 
    return { 
    myState: 0 
    } 
}, 

updateState: function(stateVersion) { 
    console.log(this.state.myState); //this will print 0 
    this.setState({ myState: stateVersion }); 
    console.log(this.state.myState); //this will print 0 
} 

現在是第一次,如果我們所說的與國家的版本作爲參數updateState功能,它能向兩家即使我們發送1或2或任何數量作爲參數控制檯打印0。 假設我們已經發送了2個參數。那麼我們可以用另一個參數在該函數的下一次調用中獲得該狀態。 但反應也照顧這一點。 您可能會認爲,如果狀態一旦我們更新就沒有更新,那麼我該如何處理。但是,反應是一個好孩子......如果你調用一個函數來更新狀態,然後調用另一個函數來處理上次更新的狀態,那麼你可以使用它。

我想我已經回答了你的問題,爲什麼不更新redux狀態。

另一個想法是,當您爲搜索縮減器使用redux狀態時,爲什麼您還要處理反應狀態。你可以直接將搜索到的參數傳遞給你的動作。您可以從Reducer狀態即時獲得該更新。 它將幫助您簡化代碼。

+0

感謝您的提示。它效果不錯:) – onurhb

0

我找到了解決方案。 React - State not updated 看來setState實際上並不是立即設置狀態。 所以我使用了一個回調函數。

_onSearchChange(event) { 
    this.setState({term: event.target.value}, function() { 
     console.log(this.state.term) 
    }); 
    } 

現在當我輸入'a'時,它會記錄'a'!

+0

在這種方法中,我仍然建議您確保您使用Redux以來的'調度操作'方法。但是,如果您正在使用狀態來設置輸入(看起來您可能正在做什麼?),那麼請確保允許新的道具在從上方下來時覆蓋該更改。這讓我覺得這是一種'樂觀的渲染/更新'。因此,如果您正在使用狀態來設置輸入 - 確保在來自Redux流程的newProps進入時更新組件的本地狀態的方法。 – marcacyr

+0

但是,如果您不使用狀態來設置輸入,您可能會從在setState中使用回調並僅使用Redux存儲區中的分派(正如我在上面的答案中所述)中受益。 本週早些時候,我提出了一個問題(當面,而不是SO),說明爲什麼/何時在'setState'上使用回調選項。在解釋了方法觸發的順序以及實際調用回調的時候,我總結說:「Redux的使用通常會消除對向您的'setState'調用添加回調等變通方法的需求。」 – marcacyr

3

這個答案在Aniket Nandan指出的內容上增加了一點 - 你在你的React組件裏面使用了setState,而不是依靠上面的道具。

使用Redux的主要目的是把你的狀態,並把它放在一個容器旁邊的應用程序。這樣做的好處是您的狀態可以跨多個組件共享,然後您可以通過道具將事情傳遞到組件樹中的組件中。

狀態容器的使用(它總是提醒我一些使用狀態機的方法)允許你構建你的應用程序,而不需要在樹中遞迴回調以獲得更改返回到最佳。相反,Redux處理更改狀態並通過道具將所有內容交給React。

_onSearchChange(event) { 
    this.setState({term: event.target.value}); 
    this.props.search(this.state.term); 
} 

關於這一點,上面看代碼,從你的帖子,我想知道你爲什麼要SETSTATE術語,但後來總是叫你通過道具獲得的功能?然後搜索從Redux商店調用調度方法嗎?如果沒有,那麼你的連接不正確。除此之外,如果您正確使用connect(來自react-redux),那麼您應該從Redux存儲區提供調度方法(這是通過上下文進行的)。

方式Redux的設計工作是更多的東西是這樣的:

_onSearchChange(event) { 
    this.props.dispatch({ type: 'SEARCH', term: event.target.value }); 
} 

然後會發生什麼是終極版應該處理的狀態更新,以及新的狀態將從Redux的流向通過道具反應(這通過Redux引擎蓋下的所有連接發生,這真是太棒了!)。

const SearchReducer = (state = '', action) => { 

    switch (action.type) { 
     case SEARCH: 
      return action.term; 
      break; 
     default: 
      return state; 
    } 

} 

根據您的減速器(以上^^複製)和你的combineReducers使用,您應該結束了與具有{ search: { term: 'ab' } }如果你輸入「AB」的狀態,而「A」只輸入後它應該是'a',而不是落在後面。

您使用setState時發生了什麼實際情況以及來自道具的方法是初始狀態(我假設'')是第一次傳遞給this.props.search。同時,鍵入'a'後,狀態更新組件爲'a'。然後,下一次,當您鍵入'b'時,狀態更新爲'ab',但this.props.search僅在setState完成執行之前從狀態開始接收術語 - 而它仍然是'a'。

這實際上是Redux非常棒的原因之一 - 它提供了一種方法來確保狀態根據用戶在其自己的容器中的操作正確更新,以便您可以保證應用程序在應用程序中同步。

在這個筆記上,我會留下一條關於使用Redux的建議:您應該很少發現自己在使用Redux的應用程序中的React組件中使用setState。關於何時在組件中使用setState的決定取決於您想要設置的狀態塊是否僅存在於該組件中,並且應用程序的其餘部分不需要知道該狀態。我想不出一個例子,我所能提供的任何東西都可能是相當人爲的。至此,我無法想到的原因是因爲我覺得在應用程序中你會有這樣的用例是相當罕見的。

因此,您應該堅持只使用Redux存儲區中的分派方法,並允許Redux通過其工作流程處理狀態更新,並允許狀態通過道具向下流向組件。堅持這一流程將防止很多這些奇怪的「狀態不同步」類型的問題發生。

+0

感謝您的時間,我現在清楚看到事情! – onurhb