React Router V4 - 路由更改的初始状态
React Router V4 - Initial State on Route Change
学习 React Router 我注意到当从路由 a 切换到 b.
时,组件会回到其初始状态
为什么在同一条路线上再次点击时不会发生同样的情况,即 a 到 a?
我如何实现一种方法,点击相同的路由 <NavLink/>
组件恢复到其原始状态 - Should/Could 在 React Router 的 onChange
挂钩上完成?
如果这是一个反模式,请告诉我我还能如何完成以下任务:我需要我的组件恢复到其原始状态,不仅在切换路由时,而且在 用户选择再次点击同一路线。
下面是问题的抽象:
单击猫 <p/>
标签应将其颜色更改为 green
,单击同一路线 <NavLink to="/cat-view">cat</NavLink>
应将猫颜色状态恢复为初始状态。即 color: false
就像从路线 a 切换到 b 时一样(在我的例子中是猫到狗)
// Cat Component
import React, { useState } from "react";
export const Cat = () => {
const [color, setColor] = useState(false);
function ChangeColor() {
setColor(true);
}
console.log(color)
return (
<p onClick={ChangeColor}>
Click on this <span className={color ? "green" : " "}>Cat</span>
</p>
);
};
import {
BrowserRouter as Router,
Route,
NavLink,
Switch,
withRouter,
browserHistory
} from "react-router-dom";
// Main Component
class PetShop extends Component {
state = {};
render() {
return (
<Router history={browserHistory}>
<div>
<ul>
<li>
<NavLink to="/">home</NavLink>
</li>
<li>
<NavLink to="/cat-view">cat</NavLink>
</li>
<li>
<NavLink to="/dog-view">dog</NavLink>
</li>
</ul>
<Switch>
<Route
path="/cat-view"
render={() => <Cat/>}
onChange={console.log("cat route changed")}
/>
<Route
path="/dog-view"
render={() => <Dog/>}
onChange={console.log("dog route changed")}
/>
</Switch>
</div>
</Router>
);
}
}
export default withRouter(PetShop);
这里是 code sandbox
由于您使用的 react-router Switch
组件仅呈现第一个匹配项,因此当您从路线 a 切换到 b, a 正在卸载;这会抛出它的所有状态,所以如果你切换回 a 你有一个全新的组件,它获取你为其状态指定的初始值(例如 false
for Cat
color
)。单击不会更改呈现的 Route
的 NavLink
会保留相同的元素,并且不会影响其状态。
如果你想在点击 NavLink
时改变状态,那么你需要明确地这样做。
您可以通过两种主要方式执行此操作:
- 将状态提升到 parent 并在单击 link
时明确更改它
- 更改元素的键以强制重新挂载
- 为 parent 提供一种机制以进入 child 并告诉它重置其状态
这是您的沙箱的修改版本,演示了所有这些:
Cat
演示了第一种方法。
我已将状态从 Cat
移动到 PetShop
(Cat 现在只使用道具)。我还在 cat 的 NavLink
中添加了一个 onClick
,将状态设置回 false
。
Dog
演示了第二种方法。
这种方法在更复杂的情况下效果更好,在这种情况下,组件有很多自己的状态,如果您再次单击 link,您希望它全部重置。
Bunny
演示了第三种方法。
这类似于 Dog 示例的密钥 属性,但不会导致重新挂载。 Bunny
只是在效果中使用 resetIndex
导致 Bunny
自行重置。为此可能有几种技术方法。您只需要一种方法来通知 child 自行重置。
学习 React Router 我注意到当从路由 a 切换到 b.
时,组件会回到其初始状态为什么在同一条路线上再次点击时不会发生同样的情况,即 a 到 a?
我如何实现一种方法,点击相同的路由 <NavLink/>
组件恢复到其原始状态 - Should/Could 在 React Router 的 onChange
挂钩上完成?
如果这是一个反模式,请告诉我我还能如何完成以下任务:我需要我的组件恢复到其原始状态,不仅在切换路由时,而且在 用户选择再次点击同一路线。
下面是问题的抽象:
单击猫 <p/>
标签应将其颜色更改为 green
,单击同一路线 <NavLink to="/cat-view">cat</NavLink>
应将猫颜色状态恢复为初始状态。即 color: false
就像从路线 a 切换到 b 时一样(在我的例子中是猫到狗)
// Cat Component
import React, { useState } from "react";
export const Cat = () => {
const [color, setColor] = useState(false);
function ChangeColor() {
setColor(true);
}
console.log(color)
return (
<p onClick={ChangeColor}>
Click on this <span className={color ? "green" : " "}>Cat</span>
</p>
);
};
import {
BrowserRouter as Router,
Route,
NavLink,
Switch,
withRouter,
browserHistory
} from "react-router-dom";
// Main Component
class PetShop extends Component {
state = {};
render() {
return (
<Router history={browserHistory}>
<div>
<ul>
<li>
<NavLink to="/">home</NavLink>
</li>
<li>
<NavLink to="/cat-view">cat</NavLink>
</li>
<li>
<NavLink to="/dog-view">dog</NavLink>
</li>
</ul>
<Switch>
<Route
path="/cat-view"
render={() => <Cat/>}
onChange={console.log("cat route changed")}
/>
<Route
path="/dog-view"
render={() => <Dog/>}
onChange={console.log("dog route changed")}
/>
</Switch>
</div>
</Router>
);
}
}
export default withRouter(PetShop);
这里是 code sandbox
由于您使用的 react-router Switch
组件仅呈现第一个匹配项,因此当您从路线 a 切换到 b, a 正在卸载;这会抛出它的所有状态,所以如果你切换回 a 你有一个全新的组件,它获取你为其状态指定的初始值(例如 false
for Cat
color
)。单击不会更改呈现的 Route
的 NavLink
会保留相同的元素,并且不会影响其状态。
如果你想在点击 NavLink
时改变状态,那么你需要明确地这样做。
您可以通过两种主要方式执行此操作:
- 将状态提升到 parent 并在单击 link 时明确更改它
- 更改元素的键以强制重新挂载
- 为 parent 提供一种机制以进入 child 并告诉它重置其状态
这是您的沙箱的修改版本,演示了所有这些:
Cat
演示了第一种方法。
我已将状态从 Cat
移动到 PetShop
(Cat 现在只使用道具)。我还在 cat 的 NavLink
中添加了一个 onClick
,将状态设置回 false
。
Dog
演示了第二种方法。
这种方法在更复杂的情况下效果更好,在这种情况下,组件有很多自己的状态,如果您再次单击 link,您希望它全部重置。
Bunny
演示了第三种方法。
这类似于 Dog 示例的密钥 属性,但不会导致重新挂载。 Bunny
只是在效果中使用 resetIndex
导致 Bunny
自行重置。为此可能有几种技术方法。您只需要一种方法来通知 child 自行重置。