dev*_*_el 5 javascript reactjs
我有以下组件
const ListItem = ({ children, title = '' }) => {
const [isActive, setIsActive] = useState(false)
useEffect(() => {
console.log('isActive', isActive)
}, [isActive])
return (
<li className={`depth1${(isActive ? ' is-active' : '')}`} onMouseEnter={() => {
console.log('onMouseEnter')
setIsActive(true)
}} onMouseLeave={() => {
console.log('onMouseLeave')
setIsActive(false)
}}>
<a href="#" onClick={(e) => {
console.log('onClick a')
e.preventDefault()
setIsActive(!isActive)
}}>{title}</a>
{isActive && (
<ul onClick={() => {
console.log('onClick ul')
setIsActive(!isActive)
}}>
{children}
</ul>
)}
</li>
)
}
Run Code Online (Sandbox Code Playgroud)
该组件在以下上下文中使用
<ul>
<ListItem title="BRAND">
<li>
<a href="#" onClick={(e) => {
e.preventDefault()
}}>Link</a>
</li>
<li>
<a href="#" onClick={(e) => {
e.preventDefault()
}}>Link</a>
</li>
<li>
<a href="#" onClick={(e) => {
e.preventDefault()
}}>Link</a>
</li>
</ListItem>
<ListItem title="SERVICE">
<li>
<a href="#" onClick={(e) => {
e.preventDefault()
}}>Link</a>
</li>
<li>
<a href="#" onClick={(e) => {
e.preventDefault()
}}>Link</a>
</li>
</ListItem>
<ListItem title="CLIENT">
<li>
<a href="#" onClick={(e) => {
e.preventDefault()
}}>Link</a>
</li>
</ListItem>
<ListItem title="CONTENTS">
<li>
<a href="#" onClick={(e) => {
e.preventDefault()
}}>Link</a>
</li>
</ListItem>
</ul>
Run Code Online (Sandbox Code Playgroud)
在我的 PC 上,当鼠标悬停在 a 上时ListItem,onMouseEnter激活和控制台日志
onMouseEnter
isActive true
Run Code Online (Sandbox Code Playgroud)
在我的 PC 上,当鼠标离开时ListItem,onMouseLeave激活和控制台日志
onMouseLeave
isActive false
Run Code Online (Sandbox Code Playgroud)
这里一切正常。当我打开导航菜单时,问题出在移动设备上,我控制台日志
isActive false
Run Code Online (Sandbox Code Playgroud)
正如预期的那样。
但是当我ListItem第一次点击 a时,我控制台日志
onMouseEnter
isActive true
onClick a
isActive false
Run Code Online (Sandbox Code Playgroud)
而我的ListItem children不打开。但是当我ListItem第二次点击控制台日志时
onClick a
isActive true
Run Code Online (Sandbox Code Playgroud)
这打开了我的ListItem children. 如果我ListItem第三次点击,我会控制台日志
onClick a
isActive false
Run Code Online (Sandbox Code Playgroud)
这关闭了我的 ListItem children
我如何解开我的状态更改,以便在我的第一次而不是第二次点击时,我ListItem children在移动设备上打开?
我发现很难理清这些状态,所以我用以下方法解决了这个问题
const [isMobileNav, setIsMobileNav] = useState(false)
const windowWidthOnLoad = () => {
const browser = window.innerWidth
if (browser <= 1024) {
setIsMobileNav(true)
} else {
setIsMobileNav(false)
}
}
const windowWidthOnResize = () => {
const browser = window.innerWidth
if (browser <= 1024) {
setIsMobileNav(true)
} else {
setIsMobileNav(false)
}
}
useEffect(() => {
windowWidthOnLoad()
window.addEventListener('resize', windowWidthOnResize)
}, [])
const ListItem = ({ children, title = '' }) => {
const [isActive, setIsActive] = useState(false)
return (
<>
{/* click link once to show ListItem children on mobile */}
{isMobileNav
? <li className={`depth1${(isActive ? ' is-active' : '')}`}>
<a href="#" onClick={(e) => {
e.preventDefault()
setIsActive(!isActive)
}}>{title}</a>
{isActive && (
<ul onClick={() => {
setIsActive(!isActive)
}}>
{children}
</ul>
)}
</li>
: <li className={`depth1${(isActive ? ' is-active' : '')}`} onMouseEnter={() => {
setIsActive(true)
}} onMouseLeave={() => {
setIsActive(false)
}}>
<a href="#" onClick={(e) => {
e.preventDefault()
setIsActive(!isActive)
}}>{title}</a>
{isActive && (
<ul onClick={() => {
setIsActive(!isActive)
}}>
{children}
</ul>
)}
</li>
}
</>
)
}
Run Code Online (Sandbox Code Playgroud)