我想在我的GatsbyJS中加入Theme UI的presets来切换模式(暗和亮)和主题。
我不能修改原始代码的export来将两个const函数合并到一个export中,因为export需要定义children。我不想使用children,因为JSX中的另一个布局文件已经有了children。我也不能将一个const合并到另一个const中。您将在最后检查错误。我将在最后分享我的repo的小文件夹,以供您测试。In Angular2+ is there any way to extends on inherit const into another const?也帮不上忙。
请参阅我的小原始代码,并注意const和export
import React from 'react'
import {Context} from '../../common'
import SelectLanguage from './SelectLanguage'
import {Links} from './styles'
import {Navegador, StyledHeader} from './styles'
const Header = () => (
<Context.Consumer>
{({ toggleLanguage, lang }) => (
<StyledHeader>
<Navegador id="menu">
<li>
<Links>
{/* ... */}
<SelectLanguage lang={lang} toggleLanguage={toggleLanguage} />
</Links>
</li>
</Navegador>
</StyledHeader>
)}
</Context.Consumer>
)
export default Header我的另一个小主题UI代码,您可以注意到export中的const函数
/** @jsx jsx */
import { jsx, Styled, useColorMode } from 'theme-ui'
import ButtonUI from '../../theme-ui/button-ui'
const themes = ['deep', 'funk', 'future', 'swiss']
const modes = ['default', 'dark']
const getThemeName = (theme) =>
{
switch (theme)
{
case 'deep':
return 'Deep'
case 'funk':
return 'Funk'
case 'future':
return 'Future'
case 'swiss':
return 'Swiss'
default:
return theme
}
}
const getModeName = (mode) =>
{
switch (mode)
{
case 'dark':
return (<span role="img" aria-label="moon">? </span>)
case 'default':
return (<span role="img" aria-label="sun">☀️ </span>)
default:
return mode
}
}
export default function Layout({ children })
{
const [theme, setTheme] = useColorMode()
const [mode, setMode] = useColorMode()
const cycleTheme = (e) =>
{
const i = themes.indexOf(theme)
const next = themes[(i + 1) % themes.length]
setTheme(next)
}
const cycleMode = (e) =>
{
const i = modes.indexOf(mode)
const next = modes[(i + 1) % modes.length]
setMode(next)
}
return (
<Styled.root>
<ButtonUI
sx={{
ml: 2,
}}
onClick={cycleTheme}>
<span role="img" aria-label="theme">? </span>
{getThemeName(theme)}
</ButtonUI>
<ButtonUI
sx={{
ml: 2,
}}
onClick={cycleMode}>
{getModeName(mode)}
</ButtonUI>
</Styled.root>
)
}让我们将第二个代码合并到第一个代码中,并将const重命名为function,因为我不能将const放入另一个const或修改export (因为需要定义children ):
/** @jsx jsx */
import { jsx, Styled, useColorMode } from 'theme-ui'
import {Context} from '../../common'
import SelectLanguage from './SelectLanguage'
import {Links} from './styles'
import {Navegador, StyledHeader} from './styles'
import ButtonUI from '../../theme-ui/button-ui'
const themes = ['deep', 'funk', 'future', 'swiss']
const modes = ['default', 'dark']
const getThemeName = (theme) =>
{
switch (theme)
{
case 'deep':
return 'Deep'
case 'funk':
return 'Funk'
case 'future':
return 'Future'
case 'swiss':
return 'Swiss'
default:
return theme
}
}
const getModeName = (mode) =>
{
switch (mode)
{
case 'dark':
return (<span role="img" aria-label="moon">? </span>)
case 'default':
return (<span role="img" aria-label="sun">☀️ </span>)
default:
return mode
}
}
const [theme, setTheme] = useColorMode();
const [mode, setMode] = useColorMode();
function cycleTheme (e) {
const i = themes.indexOf(theme)
const next = themes[(i + 1) % themes.length]
setTheme(next)
}
function cycleMode (e) {
const i = modes.indexOf(mode)
const next = modes[(i + 1) % modes.length]
setMode(next)
}
function Header () {
return (
<Styled.root>
<Context.Consumer>
{({ toggleLanguage, lang }) => (
<StyledHeader>
<Navegador id="menu">
<li>
<ButtonUI
sx={{
ml: 2,
}}
onClick={cycleTheme}>
<span role="img" aria-label="theme">? </span>
{getThemeName(theme)}
</ButtonUI>
<ButtonUI
sx={{
ml: 2,
}}
onClick={cycleMode}>
{getModeName(mode)}
</ButtonUI>
<Links>
<SelectLanguage lang={lang} toggleLanguage={toggleLanguage} />
</Links>
</li>
</Navegador>
</StyledHeader>
)}
</Context.Consumer>
</Styled.root>
)
}
export default Header出现以下错误:
Error: Invalid hook call. Hooks can only be called inside of the body of a function component. This could happen for one of the following reasons:
1. You might have mismatching versions of React and the renderer (such as React DOM)
2. You might be breaking the Rules of Hooks
3. You might have more than one copy of React in the same app
See https://reactjs.org/warnings/invalid-hook-call-warning.html for tips about how to debug and fix this problem.
resolveDispatcher
node_modules/react/cjs/react.development.js:1465
useContext
node_modules/react/cjs/react.development.js:1473
patch/React$$1.useContext
node_modules/react-hot-loader/dist/react-hot-loader.development.js:2939
useThemeUI
node_modules/@theme-ui/core/dist/index.esm.js:40
useColorMode
node_modules/@theme-ui/color-modes/dist/index.esm.js:169
./src/components/theme/Header/index.jsx/<
src/components/theme/Header/index.jsx:43
40 | }
41 | }
42 |
> 43 | const [theme, setTheme] = useColorMode();
44 | const [mode, setMode] = useColorMode();
45 |
46 | function cycleTheme (e) {
./src/components/theme/Header/index.jsx您可以下载我的存储库的小文件夹:http://sendanywhe.re/HQ19EMJK或https://filetransfer.io/data-package/i03Or3CD或https://fromsmash.com/Gatsby-i81n-Starter。使用index-example.js。
发布于 2020-08-16 20:59:23
你可以把所有的布局功能都放到你的Header组件中,但是为什么要这么做呢?
// Above this is your imports and various constants
function Header () {
const [theme, setTheme] = useColorMode();
const [mode, setMode] = useColorMode();
function cycleTheme (e) {
const i = themes.indexOf(theme)
const next = themes[(i + 1) % themes.length]
setTheme(next)
}
function cycleMode (e) {
const i = modes.indexOf(mode)
const next = modes[(i + 1) % modes.length]
setMode(next)
}
return (
<Styled.root>
<Context.Consumer>
{({ toggleLanguage, lang }) => (
<StyledHeader>
<Navegador id="menu">
<li>
<ButtonUI
sx={{
ml: 2,
}}
onClick={cycleTheme}>
<span role="img" aria-label="theme">? </span>
{getThemeName(theme)}
</ButtonUI>
<ButtonUI
sx={{
ml: 2,
}}
onClick={cycleMode}>
{getModeName(mode)}
</ButtonUI>
<Links>
<SelectLanguage lang={lang} toggleLanguage={toggleLanguage} />
</Links>
</li>
</Navegador>
</StyledHeader>
)}
</Context.Consumer>
</Styled.root>
)
}
export default Header;https://stackoverflow.com/questions/63436448
复制相似问题