admin管理员组文章数量:1397048
I'm ing from a Vue background and I'm having a really hard time understanding how to show something conditionally when the HTML is split into multiple parts.
Suppose I got the following structure:
import React, { useState } from "react";
const [mobileNavOpen, setMobileNavOpen] = useState(false);
function Home() {
return (
<div>
<button
onClick={(): void => setMobileNavOpen(true)}
type="button"
className="btn"
>
X
</button>
{mobileNavOpen && <MobileNav />}
</div>
);
}
function MobileNav() {
return (
<div>
<button
onClick={(): void => setMobileNavOpen(false)}
type="button"
className="btn"
>
X
</button>
</div>
);
}
export default Home;
How would I be able to access [mobileNavOpen, setMobileNavOpen] in both Home() and MobileNav(). Basically what I want to achieve is a Home Component where users can press a button upon which a MobileMenu Component opens with yet another button they can use to close the menu again.
Right now, the 2nd line from the top const [mobileNavOpen, setMobileNavOpen] = useState(false);
results in Error: Invalid hook call. Hooks can only be called inside of the body of a function ponent.
but where would I put it?
Should this line be in the Home() Component and all child ponents emit an event to show or close the Menu? Or do I need a state management library for something as simple as this? What is the "React" way to do this?
I'm ing from a Vue background and I'm having a really hard time understanding how to show something conditionally when the HTML is split into multiple parts.
Suppose I got the following structure:
import React, { useState } from "react";
const [mobileNavOpen, setMobileNavOpen] = useState(false);
function Home() {
return (
<div>
<button
onClick={(): void => setMobileNavOpen(true)}
type="button"
className="btn"
>
X
</button>
{mobileNavOpen && <MobileNav />}
</div>
);
}
function MobileNav() {
return (
<div>
<button
onClick={(): void => setMobileNavOpen(false)}
type="button"
className="btn"
>
X
</button>
</div>
);
}
export default Home;
How would I be able to access [mobileNavOpen, setMobileNavOpen] in both Home() and MobileNav(). Basically what I want to achieve is a Home Component where users can press a button upon which a MobileMenu Component opens with yet another button they can use to close the menu again.
Right now, the 2nd line from the top const [mobileNavOpen, setMobileNavOpen] = useState(false);
results in Error: Invalid hook call. Hooks can only be called inside of the body of a function ponent.
but where would I put it?
Should this line be in the Home() Component and all child ponents emit an event to show or close the Menu? Or do I need a state management library for something as simple as this? What is the "React" way to do this?
Share Improve this question asked Mar 11, 2020 at 21:39 Alex GoglAlex Gogl 7191 gold badge9 silver badges27 bronze badges 04 Answers
Reset to default 4import React, { useState } from "react";
function Home() {
const [mobileNavOpen, setMobileNavOpen] = useState(false);
return (
<div>
<button
onClick={() => setMobileNavOpen(true)}
type="button"
className="btn"
>
X
</button>
{mobileNavOpen && <MobileNav setMobileNavOpen={setMobileNavOpen} />}
</div>
);
}
function MobileNav({setMobileNavOpen}) {
return (
<div>
<button
onClick={() => setMobileNavOpen(false)}
type="button"
className="btn"
>
X
</button>
</div>
);
}
export default Home;
- you have to move the useState hook to the ponent body
- pass down the state setter function to your child ponent
if your Home() Component
renders MobileNav() Component
you should put const [mobileNavOpen, setMobileNavOpen] = useState(false)
in Home()
like:
const Home = () => {
const [mobileNavOpen, setMobileNavOpen] = useState(false)
return (
<>
...
<MobileNav
handleMobileNav={mobileNavOpen}
/>
...
</>)
}
const MobileNav = ({ handleMobileNav }) => {
return <></>
}
A simple way would be to pass the state modifier down to the child ponent. For this the hook needs to be moved inside the parent ponent.
import React, { useState } from "react";
function Home() {
const [mobileNavOpen, setMobileNavOpen] = useState(false);
return (
<div>
<button
onClick={(): void => setMobileNavOpen(true)}
type="button"
className="btn"
>
X
</button>
{mobileNavOpen && <MobileNav setMobileNavOpen={setMobileNavOpen} />}
</div>
);
}
function MobileNav(setMobileNavOpen) {
return (
<div>
<button
onClick={(): void => setMobileNavOpen(false)}
type="button"
className="btn"
>
X
</button>
</div>
);
}
export default Home;
Alternatively, you could abstract this a little so that your child ponent defines only what's required:
import React, { useState } from "react";
function Home() {
const [mobileNavOpen, setMobileNavOpen] = useState(false);
return (
<div>
<button
onClick={(): void => setMobileNavOpen(true)}
type="button"
className="btn"
>
X
</button>
{mobileNavOpen && <MobileNav onClose={() => setMobileNavOpen(false)} />}
</div>
);
}
function MobileNav(onClose) {
return (
<div>
<button
onClick={(): void => onClose()}
type="button"
className="btn"
>
X
</button>
</div>
);
}
export default Home;
The docs provide some good best practices for managing shared state.
Should this line be in the Home() Component and all child ponents emit an event to show or close the Menu?
Yes. Then pass state to the MobileNavComponent
本文标签: javascriptReact Hookshow to share state between two functionsStack Overflow
版权声明:本文标题:javascript - React Hooks, how to share state between two functions - Stack Overflow 内容由网友自发贡献,该文观点仅代表作者本人, 转载请联系作者并注明出处:http://www.betaflare.com/web/1744148250a2592939.html, 本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,一经查实,本站将立刻删除。
发表评论