Javascript 当存储状态更改时,响应组件不更新
下面是我的组件类。该组件似乎从未执行componentWillUpdate(),即使在MapStateTops中返回之前,我可以通过日志记录看到状态更新。状态正在100%更改,但组件不会刷新Javascript 当存储状态更改时,响应组件不更新,javascript,reactjs,state,redux,Javascript,Reactjs,State,Redux,下面是我的组件类。该组件似乎从未执行componentWillUpdate(),即使在MapStateTops中返回之前,我可以通过日志记录看到状态更新。状态正在100%更改,但组件不会刷新 import React, { Component } from 'react' import { connect } from 'react-redux' import { search } from './mapActions' import L from 'leaflet' class Map e
import React, { Component } from 'react'
import { connect } from 'react-redux'
import { search } from './mapActions'
import L from 'leaflet'
class Map extends Component {
componentDidMount() {
L.Icon.Default.imagePath = './images'
this.map = new L.Map('map', {
center: new L.LatLng(this.props.lat, this.props.lng),
zoom: this.props.zoom,
layers: L.tileLayer('http://{s}.tile.osm.org/{z}/{x}/{y}.png', {
attribution: '<a href="http://osm.org/copyright">OpenStreetMap</a> contributors'
})
})
}
componentWillUpdate() {
console.log('UPDATE MAP')
L.geoJson(this.props.data).addTo(this.map)
}
render() {
return <div id="map"></div>
}
}
const mapStateToProps = (state) => {
return {
isFetching: state.isFetching,
data: state.data
}
}
const mapDispatchToProps = (dispatch) => {
return {
search: (name) => {
dispatch(search(name))
}
}
}
export default connect(
mapStateToProps,
mapDispatchToProps
)(Map)
经过更多的测试和日志记录之后,当它将state映射到props时,它用来映射到props的state对象似乎包含正确的数据,因此state.map.data是正确的,我可以看到从fetch返回的数据。但是,当我将this.props记录到componentWillUpdate()中时,数据对象在那里但为空。将传入的props作为参数接收。此时,this.props
仍然是旧道具。尝试更改您的方法,如下所示:
void componentWillUpdate(nextProps, nextState) {
L.geoJson(nextProps.data).addTo(this.map);
}
我有一个类似的问题,我在读了这篇文章后找到了答案: 通过在减速机中处理操作的结果,在存储中设置/更新/删除数据。还原程序接收应用程序片段的当前状态,并期望返回新状态。组件可能不会重新呈现的最常见原因之一是,您正在修改reducer中的现有状态,而不是返回状态的新副本,并进行必要的更改(请参阅疑难解答部分)。当您直接改变现有状态时,Redux不会检测到状态的差异,也不会通知组件存储已更改。 所以我一定要检查一下你们的减缩器,确保你们并没有改变现有的状态。希望有帮助!() 当我试着像你一样使用
Object.assign({},Object)
时,它还是不起作用。当我发现这个的时候也是这样:
Object.assign仅创建浅拷贝。()
然后我明白了我必须这么做:JSON.parse(JSON.stringify(object))
或者仅仅是这样:
{…object}
对于阵列:
[…阵列]
我希望这将帮助您,因为您没有更改引用,因此React的浅层比较不会检测到更新 我将用一个简单的例子来说明博客文章。在减速器中,您可能正在执行以下操作:
case FETCH_NEW_POSTS
let posts = state.posts;
posts.push(action.payload.posts);
return {
...state,
posts
};
相反,您必须执行以下操作:
case FETCH_NEW_POSTS
let posts = [...state.posts]; // we're destructuring `state.posts` inside of array, essentially assigning the elements to a new array.
posts.push(action.payload.posts);
return {
...state,
posts
};
取决于您的用例对象。assign()或lodash的clone/deepclone可能更为惯用。如果您通过地图文件向组件传递道具,请确保您正在收听地图文件中的存储
export const listenToStores = [CommonStore, store];
@connection(maps.listenToStores, maps.getStateFromStores)
你能把你的减速机也拿出来吗?可能是你改变了状态,而不是发送新对象,因此redux认为没有理由更新。
渲染中没有任何内容:
@Davintroon我使用的传单处理它自己的渲染,但是它仍然应该像在更新组件一样。@Mijamo我已经添加了这一点,谢谢。嗨,Brandon,谢谢你的回复。该函数似乎仍然没有被调用。在我的三个动作中,request、receive和fetch,我已经登录到控制台,一切似乎都很顺利。我还在reducer中做了一些日志记录,状态肯定会发生变化。你需要显示你的操作的代码以及分派这些操作的代码。嗨,Brandon,刚刚发现一些奇怪的东西可能会有所帮助。检查问题的细节。啊,我想我解决了它。。。数据似乎在componentDidUpdate()期间存在,但在componentWillUpdate()期间不存在。数据后期更新不是毫无意义吗?你肯定需要新的数据预更新吗?这个。谢谢,这正是问题所在,应该是最重要的答案,只是为了重写它,在第一种情况下,你推到一个数组,它会修改它,但数组在内存中保留相同的引用。因此,当您返回POST时,您仍然返回相同的数组,因此状态不会更新。在第二种情况下,您正在创建阵列的副本。此解决方案应位于顶部,这是完美的解决方案这正是我一天来试图解决的问题。帮助了我很多;)@dillon.harless,不,在JS中,对象是引用类型。在第一个块中,您将posts
设置为与state.posts
相同的引用。由于React的浅层比较会注意到相同的对象指针,因此不会对其进行更新。请参阅此处的更多信息:特别是底部的“比较对象”部分。我尝试使用Lodash
的克隆功能,但没有成功。然而,使用{…object}
却成功了。这似乎是我的方案的答案,但是连接
函数从何处导入?
export const listenToStores = [CommonStore, store];
@connection(maps.listenToStores, maps.getStateFromStores)