Updated styled components wrapping

This commit is contained in:
Dustin Brett
2021-01-16 22:22:15 -08:00
parent c19683ed6c
commit d210e43954
10 changed files with 90 additions and 51 deletions

View File

@@ -48,6 +48,7 @@
"max-lines": ["error", 80],
"react/jsx-filename-extension": [1, { "extensions": [".tsx"] }],
"react/jsx-props-no-spreading": "off",
"react/prop-types": "off",
"semi": ["error", "always"],
"simple-import-sort/exports": "error",
"simple-import-sort/imports": "error"

View File

@@ -1,13 +1,12 @@
import { render } from '@testing-library/react';
import StyledApp from 'components/pages/StyledApp';
import Index from 'pages/index';
import { ThemeProvider } from 'styled-components';
import defaultTheme from 'themes/default.json';
test('renders index page', () => {
const { getByText } = render(
<ThemeProvider theme={defaultTheme}>
<StyledApp>
<Index />
</ThemeProvider>
</StyledApp>
);
const helloWorldElement = getByText('Hello, world!');

View File

@@ -0,0 +1,17 @@
import type { FC } from 'react';
import { ThemeProvider } from 'styled-components';
import GlobalStyle from 'styles/GlobalStyle';
import themes from 'styles/themes.json';
import type { StyledAppProps } from 'types/components/pages/StyledApp';
const StyledApp: FC<StyledAppProps> = ({
children,
theme = themes.default
}) => (
<>
<GlobalStyle />
<ThemeProvider theme={theme}>{children}</ThemeProvider>
</>
);
export default StyledApp;

View File

@@ -1,21 +1,8 @@
import StyledApp from 'components/pages/StyledApp';
import type { AppProps } from 'next/app';
import Head from 'next/head';
import { description, name } from 'package.json';
import type { ReactElement } from 'react';
import { createGlobalStyle, ThemeProvider } from 'styled-components';
import defaultTheme from 'themes/default.json';
const GlobalStyle = createGlobalStyle`
html,
body {
margin: 0;
padding: 0;
}
* {
box-sizing: border-box;
}
`;
export default function App({ Component, pageProps }: AppProps): ReactElement {
return (
@@ -24,10 +11,9 @@ export default function App({ Component, pageProps }: AppProps): ReactElement {
<title>{name}</title>
<meta name="description" content={description} />
</Head>
<GlobalStyle />
<ThemeProvider theme={defaultTheme}>
<StyledApp>
<Component {...pageProps} />
</ThemeProvider>
</StyledApp>
</>
);
}

View File

@@ -1,36 +1,13 @@
import type { DocumentContext, DocumentInitialProps } from 'next/document';
import Document, { Head, Html, Main, NextScript } from 'next/document';
import type { ReactElement } from 'react';
import { ServerStyleSheet } from 'styled-components';
import withServerStyleSheet from 'utils/withServerStyleSheet';
class MyDocument extends Document {
static async getInitialProps(
ctx: DocumentContext
): Promise<DocumentInitialProps> {
const originalRenderPage = ctx.renderPage;
const sheet = new ServerStyleSheet();
try {
ctx.renderPage = () =>
originalRenderPage({
enhanceApp: (App) => (props) =>
sheet.collectStyles(<App {...props} />)
});
const initialProps = await Document.getInitialProps(ctx);
return {
...initialProps,
styles: (
<>
{initialProps.styles}
{sheet.getStyleElement()}
</>
)
};
} finally {
sheet.seal();
}
return withServerStyleSheet(ctx);
}
render(): ReactElement {

15
styles/GlobalStyle.tsx Normal file
View File

@@ -0,0 +1,15 @@
import { createGlobalStyle } from 'styled-components';
const GlobalStyle = createGlobalStyle`
html,
body {
margin: 0;
padding: 0;
}
* {
box-sizing: border-box;
}
`;
export default GlobalStyle;

7
styles/themes.json Normal file
View File

@@ -0,0 +1,7 @@
{
"default": {
"colors": {
"primary": "#008000"
}
}
}

View File

@@ -1,5 +0,0 @@
{
"colors": {
"primary": "#008000"
}
}

View File

@@ -0,0 +1,9 @@
export type Theme = {
colors: {
primary: string;
};
};
export type StyledAppProps = {
theme?: Theme;
};

View File

@@ -0,0 +1,33 @@
import type { DocumentContext, DocumentInitialProps } from 'next/document';
import Document from 'next/document';
import { ServerStyleSheet } from 'styled-components';
const withServerStyleSheet = async (
ctx: DocumentContext
): Promise<DocumentInitialProps> => {
const originalRenderPage = ctx.renderPage;
const sheet = new ServerStyleSheet();
try {
ctx.renderPage = () =>
originalRenderPage({
enhanceApp: (App) => (props) => sheet.collectStyles(<App {...props} />)
});
const initialProps = await Document.getInitialProps(ctx);
return {
...initialProps,
styles: (
<>
{initialProps.styles}
{sheet.getStyleElement()}
</>
)
};
} finally {
sheet.seal();
}
};
export default withServerStyleSheet;