From cedec803fb05b5d92ef32c67352265fc7636500c Mon Sep 17 00:00:00 2001 From: Tim Kolberger Date: Tue, 1 Feb 2022 21:57:06 +0100 Subject: [PATCH 1/5] feat: add [data-css-vars-root=true] as css var root --- .changeset/twenty-cooks-visit.md | 7 +++++++ packages/system/src/providers.tsx | 9 +++++++-- 2 files changed, 14 insertions(+), 2 deletions(-) create mode 100644 .changeset/twenty-cooks-visit.md diff --git a/.changeset/twenty-cooks-visit.md b/.changeset/twenty-cooks-visit.md new file mode 100644 index 00000000000..c8095ae0da3 --- /dev/null +++ b/.changeset/twenty-cooks-visit.md @@ -0,0 +1,7 @@ +--- +"@chakra-ui/system": minor +--- + +Added `[data-css-vars-root=true]` to the CSS variables root selector. This +allows to layer the CSS variable definitions and allow the semantic tokens to +react to `data-theme="dark"` and `data-theme="light"`. diff --git a/packages/system/src/providers.tsx b/packages/system/src/providers.tsx index a54690b2796..5fe06fd9815 100644 --- a/packages/system/src/providers.tsx +++ b/packages/system/src/providers.tsx @@ -34,12 +34,17 @@ export const ThemeProvider = (props: ThemeProviderProps) => { export interface CSSVarsProps { /** * The element to attach the CSS custom properties to. - * @default ":host, :root" + * Re-hoist CSS vars by attaching `data-css-vars-root={true}` to a DOM element. + * @example
+ * + * @default ":host, :root, [data-css-vars-root=true]" */ root?: string } -export const CSSVars = ({ root = ":host, :root" }: CSSVarsProps) => ( +export const CSSVars = ({ + root = ":host, :root, [data-css-vars-root=true]", +}: CSSVarsProps) => ( ({ [root]: theme.__cssVars })} /> ) From 3ef7312262d5c139472d2389a55116ef99da385c Mon Sep 17 00:00:00 2001 From: Tim Kolberger Date: Sat, 26 Feb 2022 17:03:24 +0100 Subject: [PATCH 2/5] feat(semantic-tokens): add support for DarkMode/LightMode components --- .changeset/brown-moose-relate.md | 6 ++ .changeset/mighty-monkeys-wash.md | 6 ++ .changeset/twenty-cooks-visit.md | 6 +- .changeset/wild-shirts-smell.md | 26 +++++ .storybook/preview.tsx | 15 ++- .../color-mode/src/color-mode-provider.tsx | 44 +------- .../test/color-mode-provider.test.tsx | 2 +- .../test/color-mode-provider__server.test.tsx | 2 +- packages/color-mode/test/dark-mode.test.tsx | 77 -------------- .../test/use-color-mode-value.test.tsx | 6 +- packages/color-mode/test/utils.tsx | 28 ++--- packages/styled-system/src/pseudos.ts | 10 +- packages/styled-system/tests/css-var.test.ts | 2 +- packages/system/src/color-mode-components.tsx | 100 ++++++++++++++++++ packages/system/src/index.ts | 1 + packages/system/src/providers.tsx | 17 ++- packages/system/stories/system.stories.tsx | 21 ++++ .../tests/color-mode-component.utils.tsx | 30 ++++++ packages/system/tests/dark-mode.test.tsx | 84 +++++++++++++++ .../test => system/tests}/light-mode.test.tsx | 19 ++-- 20 files changed, 333 insertions(+), 169 deletions(-) create mode 100644 .changeset/brown-moose-relate.md create mode 100644 .changeset/mighty-monkeys-wash.md create mode 100644 .changeset/wild-shirts-smell.md delete mode 100644 packages/color-mode/test/dark-mode.test.tsx create mode 100644 packages/system/src/color-mode-components.tsx create mode 100644 packages/system/tests/color-mode-component.utils.tsx create mode 100644 packages/system/tests/dark-mode.test.tsx rename packages/{color-mode/test => system/tests}/light-mode.test.tsx (72%) diff --git a/.changeset/brown-moose-relate.md b/.changeset/brown-moose-relate.md new file mode 100644 index 00000000000..3fed02f8048 --- /dev/null +++ b/.changeset/brown-moose-relate.md @@ -0,0 +1,6 @@ +--- +"@chakra-ui/color-mode": major +--- + +Moved components `LightMode` and `DarkMode` to package `@chakra-ui/system` to +prevent circular dependencies. diff --git a/.changeset/mighty-monkeys-wash.md b/.changeset/mighty-monkeys-wash.md new file mode 100644 index 00000000000..8b98e6cae05 --- /dev/null +++ b/.changeset/mighty-monkeys-wash.md @@ -0,0 +1,6 @@ +--- +"@chakra-ui/styled-system": minor +--- + +Updated `_dark` and `_light` pseudo selectors to allow semantic tokens to change +with the `DarkMode` and `LightMode` component. diff --git a/.changeset/twenty-cooks-visit.md b/.changeset/twenty-cooks-visit.md index c8095ae0da3..3280fa5fddb 100644 --- a/.changeset/twenty-cooks-visit.md +++ b/.changeset/twenty-cooks-visit.md @@ -2,6 +2,6 @@ "@chakra-ui/system": minor --- -Added `[data-css-vars-root=true]` to the CSS variables root selector. This -allows to layer the CSS variable definitions and allow the semantic tokens to -react to `data-theme="dark"` and `data-theme="light"`. +Added `[data-theme]` to the CSS variables root selector. This allows the +semantic tokens to change according to `data-theme="dark"` and +`data-theme="light"` DOM element attributes. diff --git a/.changeset/wild-shirts-smell.md b/.changeset/wild-shirts-smell.md new file mode 100644 index 00000000000..54170e16200 --- /dev/null +++ b/.changeset/wild-shirts-smell.md @@ -0,0 +1,26 @@ +--- +"@chakra-ui/color-mode": major +--- + +The `LightMode` and `DarkMode` components are now able to toggle semantic tokens +as well. + +For backward compatibility reasons this needs to be enabled by passing the +boolean prop `withSemanticTokens`. + +```tsx live=false + + + This uses always the _dark value of your semantic token + + +``` + +Please note that by adding the prop `withSemanticTokens` the ColorMode +components will render a DOM element which accepts style props as usual. + +```tsx + + ... + +``` diff --git a/.storybook/preview.tsx b/.storybook/preview.tsx index 404d424a85a..9ac9cfabcb0 100644 --- a/.storybook/preview.tsx +++ b/.storybook/preview.tsx @@ -56,7 +56,20 @@ const withChakra = (StoryFn: Function, context: StoryContext) => { }, [dir]) return ( - +
diff --git a/packages/color-mode/src/color-mode-provider.tsx b/packages/color-mode/src/color-mode-provider.tsx index ab7d7e7e04d..e091f158eb5 100644 --- a/packages/color-mode/src/color-mode-provider.tsx +++ b/packages/color-mode/src/color-mode-provider.tsx @@ -1,5 +1,5 @@ import { useEnvironment } from "@chakra-ui/react-env" -import { isBrowser, noop, __DEV__ } from "@chakra-ui/utils" +import { __DEV__, isBrowser, noop } from "@chakra-ui/utils" import * as React from "react" import { addListener, @@ -18,7 +18,7 @@ export interface ColorModeOptions { useSystemColorMode?: boolean } -interface ColorModeContextType { +export interface ColorModeContextType { colorMode: ColorMode toggleColorMode: () => void setColorMode: (value: any) => void @@ -173,46 +173,6 @@ if (__DEV__) { ColorModeProvider.displayName = "ColorModeProvider" } -/** - * Locks the color mode to `dark`, without any way to change it. - */ -export const DarkMode: React.FC = (props) => { - const context = React.useMemo( - () => ({ - colorMode: "dark", - toggleColorMode: noop, - setColorMode: noop, - }), - [], - ) - - return -} - -if (__DEV__) { - DarkMode.displayName = "DarkMode" -} - -/** - * Locks the color mode to `light` without any way to change it. - */ -export const LightMode: React.FC = (props) => { - const context = React.useMemo( - () => ({ - colorMode: "light", - toggleColorMode: noop, - setColorMode: noop, - }), - [], - ) - - return -} - -if (__DEV__) { - LightMode.displayName = "LightMode" -} - /** * Change value based on color mode. * diff --git a/packages/color-mode/test/color-mode-provider.test.tsx b/packages/color-mode/test/color-mode-provider.test.tsx index 55e5950b465..b28b67356f0 100644 --- a/packages/color-mode/test/color-mode-provider.test.tsx +++ b/packages/color-mode/test/color-mode-provider.test.tsx @@ -1,7 +1,7 @@ import { render } from "@testing-library/react" import userEvent from "@testing-library/user-event" import React from "react" -import { ColorModeProvider } from "../src/color-mode-provider" +import { ColorModeProvider } from "../src" import * as colorModeUtils from "../src/color-mode.utils" import { defaultThemeOptions, diff --git a/packages/color-mode/test/color-mode-provider__server.test.tsx b/packages/color-mode/test/color-mode-provider__server.test.tsx index 983ce910571..0a45071af13 100644 --- a/packages/color-mode/test/color-mode-provider__server.test.tsx +++ b/packages/color-mode/test/color-mode-provider__server.test.tsx @@ -1,5 +1,5 @@ /* eslint-disable global-require */ -import React from "react" +import * as React from "react" import { render } from "@testing-library/react" import { createMockStorageManager, diff --git a/packages/color-mode/test/dark-mode.test.tsx b/packages/color-mode/test/dark-mode.test.tsx deleted file mode 100644 index c99aa3d048e..00000000000 --- a/packages/color-mode/test/dark-mode.test.tsx +++ /dev/null @@ -1,77 +0,0 @@ -import { render } from "@testing-library/react" -import userEvent from "@testing-library/user-event" -import React from "react" -import { DarkMode } from "../src/color-mode-provider" -import { - DummyComponent, - getColorModeButton, - MemoizedComponent, - RegularComponent, - resetCounter, -} from "./utils" - -const MemoTest = () => { - const [_, setRenderCount] = React.useState(0) - - return ( - <> - - - - - - ) -} - -const NoMemoTest = () => { - const [_, setRenderCount] = React.useState(0) - - return ( - <> - - - - - - ) -} - -describe("", () => { - beforeEach(() => { - resetCounter() - }) - - test("is always dark", () => { - render( - - - , - ) - - const button = getColorModeButton() - - expect(button).toHaveTextContent("dark") - - userEvent.click(button) - - expect(getColorModeButton()).toHaveTextContent("dark") - }) - - test("memoized component renders once", () => { - const { getByText, getByTestId } = render() - - userEvent.click(getByText("Rerender")) - userEvent.click(getByText("Rerender")) - - expect(getByTestId("rendered")).toHaveTextContent("1") - }) - - test("non memoized component renders multiple", () => { - const { getByText, getByTestId } = render() - - userEvent.click(getByText("Rerender")) - userEvent.click(getByText("Rerender")) - - expect(getByTestId("rendered")).toHaveTextContent("3") - }) -}) diff --git a/packages/color-mode/test/use-color-mode-value.test.tsx b/packages/color-mode/test/use-color-mode-value.test.tsx index 20afdfc2553..740c6a108a3 100644 --- a/packages/color-mode/test/use-color-mode-value.test.tsx +++ b/packages/color-mode/test/use-color-mode-value.test.tsx @@ -1,11 +1,7 @@ import React from "react" import { render, screen } from "@testing-library/react" import userEvent from "@testing-library/user-event" -import { - ColorModeProvider, - useColorModeValue, - useColorMode, -} from "../src/color-mode-provider" +import { ColorModeProvider, useColorModeValue, useColorMode } from "../src" import { defaultThemeOptions } from "./utils" const lightValue = "light-value" diff --git a/packages/color-mode/test/utils.tsx b/packages/color-mode/test/utils.tsx index 3b97684bfe6..8b93af273cb 100644 --- a/packages/color-mode/test/utils.tsx +++ b/packages/color-mode/test/utils.tsx @@ -1,12 +1,14 @@ +import * as React from "react" import theme from "@chakra-ui/theme" import { screen } from "@testing-library/react" -import React from "react" -import { ColorModeOptions } from "../src/color-mode-provider" -import type { ColorMode } from "../src/color-mode.utils" -import type { StorageManager } from "../src/storage-manager" +import { + useColorMode, + ColorModeOptions, + ColorMode, + StorageManager, +} from "../src" export const DummyComponent = () => { - const { useColorMode } = require("../src/color-mode-provider") const { colorMode, toggleColorMode } = useColorMode() return ( @@ -16,22 +18,6 @@ export const DummyComponent = () => { ) } -var renderCount = 0 - -export const resetCounter = () => { - renderCount = 0 -} - -export const MemoizedComponent = React.memo(() => { - renderCount = renderCount + 1 - return
{renderCount}
-}) - -export const RegularComponent = () => { - renderCount = renderCount + 1 - return
{renderCount}
-} - export const getColorModeButton = () => screen.getByRole("button") export const defaultThemeOptions = theme.config as Required diff --git a/packages/styled-system/src/pseudos.ts b/packages/styled-system/src/pseudos.ts index 15277d23432..688f35bab15 100644 --- a/packages/styled-system/src/pseudos.ts +++ b/packages/styled-system/src/pseudos.ts @@ -298,12 +298,18 @@ export const pseudoSelectors = { * Styles for when `data-theme` is applied to any parent of * this component or element. */ - _dark: ".chakra-ui-dark &, [data-theme=dark] &, &[data-theme=dark]", + _dark: + ".chakra-ui-dark &:not([data-theme])," + + "[data-theme=dark] &:not([data-theme])," + + "&[data-theme=dark]", /** * Styles for when `data-theme` is applied to any parent of * this component or element. */ - _light: ".chakra-ui-light &, [data-theme=light] &, &[data-theme=light]", + _light: + ".chakra-ui-light &:not([data-theme])," + + "[data-theme=light] &:not([data-theme])," + + "&[data-theme=light]", } export type Pseudos = typeof pseudoSelectors diff --git a/packages/styled-system/tests/css-var.test.ts b/packages/styled-system/tests/css-var.test.ts index 15162868967..7a16f0f5271 100644 --- a/packages/styled-system/tests/css-var.test.ts +++ b/packages/styled-system/tests/css-var.test.ts @@ -482,7 +482,7 @@ test("should convert semantic tokens", () => { "--colors-red-800": "#ff0080", "--colors-secondary": "var(--colors-red-800)", "--colors-success": "var(--colors-red-100)", - ".chakra-ui-dark &, [data-theme=dark] &, &[data-theme=dark]": Object { + ".chakra-ui-dark &:not([data-theme]),[data-theme=dark] &:not([data-theme]),&[data-theme=dark]": Object { "--colors-primary": "var(--colors-red-400)", "--colors-secondary": "var(--colors-red-700)", }, diff --git a/packages/system/src/color-mode-components.tsx b/packages/system/src/color-mode-components.tsx new file mode 100644 index 00000000000..0a4026dcbd3 --- /dev/null +++ b/packages/system/src/color-mode-components.tsx @@ -0,0 +1,100 @@ +import * as React from "react" +import { __DEV__, noop } from "@chakra-ui/utils" +import { ColorModeContext, ColorModeContextType } from "@chakra-ui/color-mode" +import { HTMLChakraProps } from "./system" +import { chakra } from "./factory" + +type WithDomElement = + | { + withSemanticTokens?: false + children?: React.ReactNode | undefined + } + | ({ + /** + * The DarkMode and LightMode components render a DOM element + * when `withSemanticTokens` is set to `true`. + * This forces the semantic tokens to use the desired color mode as well. + * + * This is an optional prop for backwards compatibility reasons and + * will be the default in an upcoming major release. + */ + withSemanticTokens: true + } & HTMLChakraProps<"div">) + +export type DarkModeProps = WithDomElement + +/** + * Locks the color mode to `dark`, without any way to change it. + */ +export const DarkMode = ({ + withSemanticTokens, + children, + ...restProps +}: DarkModeProps) => { + const colorMode = "dark" + const context = React.useMemo( + () => ({ + colorMode, + toggleColorMode: noop, + setColorMode: noop, + }), + [], + ) + + const maybeDomElement = withSemanticTokens ? ( + + {children} + + ) : ( + children + ) + + return ( + + {maybeDomElement} + + ) +} + +if (__DEV__) { + DarkMode.displayName = "DarkMode" +} + +export type LightModeProps = WithDomElement + +/** + * Locks the color mode to `light` without any way to change it. + */ +export const LightMode: React.FC = ({ + withSemanticTokens, + children, + ...restProps +}) => { + const colorMode = "light" + const context = React.useMemo( + () => ({ + colorMode, + toggleColorMode: noop, + setColorMode: noop, + }), + [], + ) + + const maybeDomElement = withSemanticTokens ? ( + + {children} + + ) : ( + children + ) + + return ( + + {maybeDomElement} + + ) +} + +if (__DEV__) { + LightMode.displayName = "LightMode" +} diff --git a/packages/system/src/index.ts b/packages/system/src/index.ts index 73ef44fc50f..9c17ab9153a 100644 --- a/packages/system/src/index.ts +++ b/packages/system/src/index.ts @@ -1,4 +1,5 @@ export * from "@chakra-ui/color-mode" +export * from "./color-mode-components" export * from "@chakra-ui/styled-system" export { keyframes } from "@emotion/react" export type { Interpolation } from "@emotion/react" diff --git a/packages/system/src/providers.tsx b/packages/system/src/providers.tsx index 5fe06fd9815..47c229eeb8f 100644 --- a/packages/system/src/providers.tsx +++ b/packages/system/src/providers.tsx @@ -34,19 +34,18 @@ export const ThemeProvider = (props: ThemeProviderProps) => { export interface CSSVarsProps { /** * The element to attach the CSS custom properties to. - * Re-hoist CSS vars by attaching `data-css-vars-root={true}` to a DOM element. - * @example
- * - * @default ":host, :root, [data-css-vars-root=true]" + * @default ":host, :root" */ root?: string } -export const CSSVars = ({ - root = ":host, :root, [data-css-vars-root=true]", -}: CSSVarsProps) => ( - ({ [root]: theme.__cssVars })} /> -) +export const CSSVars = ({ root = ":host, :root" }: CSSVarsProps) => { + /** + * Append color mode selector to allow semantic tokens to change according to the color mode + */ + const selector = [root, `[data-theme]`].join(",") + return ({ [selector]: theme.__cssVars })} /> +} export function useTheme() { const theme = React.useContext( diff --git a/packages/system/stories/system.stories.tsx b/packages/system/stories/system.stories.tsx index fa1dd181634..c304ba483c6 100644 --- a/packages/system/stories/system.stories.tsx +++ b/packages/system/stories/system.stories.tsx @@ -4,6 +4,8 @@ import { Text } from "@chakra-ui/layout" import { motion } from "framer-motion" import { chakra, + LightMode, + DarkMode, PropsOf, ThemeProvider, ThemingProps, @@ -195,3 +197,22 @@ export const WithCSSVarToken = () => { ) } + +export const WithSemanticToken = () => { + return ( +
+ I am in the default color mode + + I am forced to light mode + + + I am forced to dark mode + + + I am nested and forced to light mode + + + +
+ ) +} diff --git a/packages/system/tests/color-mode-component.utils.tsx b/packages/system/tests/color-mode-component.utils.tsx new file mode 100644 index 00000000000..9d69629d515 --- /dev/null +++ b/packages/system/tests/color-mode-component.utils.tsx @@ -0,0 +1,30 @@ +import * as React from "react" +import { useColorMode } from "@chakra-ui/color-mode" +import { screen } from "@testing-library/react" + +let renderCount = 0 +export const resetCounter = () => { + renderCount = 0 +} + +export const MemoizedComponent = React.memo(() => { + renderCount = renderCount + 1 + return
{renderCount}
+}) + +export const RegularComponent = () => { + renderCount = renderCount + 1 + return
{renderCount}
+} + +export const DummyComponent = () => { + const { colorMode, toggleColorMode } = useColorMode() + + return ( + + ) +} + +export const getColorModeButton = () => screen.getByRole("button") diff --git a/packages/system/tests/dark-mode.test.tsx b/packages/system/tests/dark-mode.test.tsx new file mode 100644 index 00000000000..48b1a603807 --- /dev/null +++ b/packages/system/tests/dark-mode.test.tsx @@ -0,0 +1,84 @@ +import * as React from "react" +import { render, screen } from "@testing-library/react" +import userEvent from "@testing-library/user-event" +import { DarkMode } from "../src" +import { + DummyComponent, + getColorModeButton, + MemoizedComponent, + RegularComponent, + resetCounter, +} from "./color-mode-component.utils" + +describe("", () => { + const MemoTest = () => { + const [, setRenderCount] = React.useState(0) + + return ( + <> + + + + + + ) + } + + const NoMemoTest = () => { + const [, setRenderCount] = React.useState(0) + + return ( + <> + + + + + + ) + } + + beforeEach(() => { + resetCounter() + }) + + test("is always dark", () => { + render( + + + , + ) + + const button = screen.getByRole("button") + + expect(button).toHaveTextContent("dark") + + userEvent.click(button) + + expect(getColorModeButton()).toHaveTextContent("dark") + }) + + test("renders a DOM element with data-theme attribute when withSemanticTokens prop is set", async () => { + const label = "Test Component" + render({label}) + const element = await screen.findByText(label) + expect(element).toHaveAttribute("data-theme", "dark") + }) + + test("memoized component renders once", () => { + const { getByText, getByTestId } = render() + + userEvent.click(getByText("Rerender")) + userEvent.click(getByText("Rerender")) + + expect(getByTestId("rendered")).toHaveTextContent("1") + }) + + test("non memoized component renders multiple", () => { + const { getByText, getByTestId } = render() + + userEvent.click(getByText("Rerender")) + userEvent.click(getByText("Rerender")) + + expect(getByTestId("rendered")).toHaveTextContent("3") + }) +}) diff --git a/packages/color-mode/test/light-mode.test.tsx b/packages/system/tests/light-mode.test.tsx similarity index 72% rename from packages/color-mode/test/light-mode.test.tsx rename to packages/system/tests/light-mode.test.tsx index c98c240ceee..54910cc1024 100644 --- a/packages/color-mode/test/light-mode.test.tsx +++ b/packages/system/tests/light-mode.test.tsx @@ -1,17 +1,17 @@ -import { render } from "@testing-library/react" +import * as React from "react" +import { render, screen } from "@testing-library/react" import userEvent from "@testing-library/user-event" -import React from "react" -import { LightMode } from "../src/color-mode-provider" +import { LightMode } from "../src" import { DummyComponent, getColorModeButton, MemoizedComponent, RegularComponent, resetCounter, -} from "./utils" +} from "./color-mode-component.utils" const MemoTest = () => { - const [_, setRenderCount] = React.useState(0) + const [, setRenderCount] = React.useState(0) return ( <> @@ -24,7 +24,7 @@ const MemoTest = () => { } const NoMemoTest = () => { - const [_, setRenderCount] = React.useState(0) + const [, setRenderCount] = React.useState(0) return ( <> @@ -57,6 +57,13 @@ describe("", () => { expect(getColorModeButton()).toHaveTextContent("light") }) + test("renders a DOM element with data-theme attribute when withSemanticTokens prop is set", async () => { + const label = "Test Component" + render({label}) + const element = await screen.findByText(label) + expect(element).toHaveAttribute("data-theme", "light") + }) + test("memoized component renders once", () => { const { getByText, getByTestId } = render() From 0246c07871f6d535d5d56775f50ab382304e8d44 Mon Sep 17 00:00:00 2001 From: Tim Kolberger Date: Wed, 9 Mar 2022 19:10:56 +0100 Subject: [PATCH 3/5] Revert "feat(semantic-tokens): add support for DarkMode/LightMode components" This reverts commit ac543306b71b5fca9fd014f69e378451064ad13a. --- .changeset/brown-moose-relate.md | 6 -- .changeset/mighty-monkeys-wash.md | 6 -- .changeset/twenty-cooks-visit.md | 6 +- .changeset/wild-shirts-smell.md | 26 ----- .storybook/preview.tsx | 15 +-- .../color-mode/src/color-mode-provider.tsx | 44 +++++++- .../test/color-mode-provider.test.tsx | 2 +- .../test/color-mode-provider__server.test.tsx | 2 +- packages/color-mode/test/dark-mode.test.tsx | 77 ++++++++++++++ .../test}/light-mode.test.tsx | 19 ++-- .../test/use-color-mode-value.test.tsx | 6 +- packages/color-mode/test/utils.tsx | 28 +++-- packages/styled-system/src/pseudos.ts | 10 +- packages/styled-system/tests/css-var.test.ts | 2 +- packages/system/src/color-mode-components.tsx | 100 ------------------ packages/system/src/index.ts | 1 - packages/system/src/providers.tsx | 17 +-- packages/system/stories/system.stories.tsx | 21 ---- .../tests/color-mode-component.utils.tsx | 30 ------ packages/system/tests/dark-mode.test.tsx | 84 --------------- 20 files changed, 169 insertions(+), 333 deletions(-) delete mode 100644 .changeset/brown-moose-relate.md delete mode 100644 .changeset/mighty-monkeys-wash.md delete mode 100644 .changeset/wild-shirts-smell.md create mode 100644 packages/color-mode/test/dark-mode.test.tsx rename packages/{system/tests => color-mode/test}/light-mode.test.tsx (72%) delete mode 100644 packages/system/src/color-mode-components.tsx delete mode 100644 packages/system/tests/color-mode-component.utils.tsx delete mode 100644 packages/system/tests/dark-mode.test.tsx diff --git a/.changeset/brown-moose-relate.md b/.changeset/brown-moose-relate.md deleted file mode 100644 index 3fed02f8048..00000000000 --- a/.changeset/brown-moose-relate.md +++ /dev/null @@ -1,6 +0,0 @@ ---- -"@chakra-ui/color-mode": major ---- - -Moved components `LightMode` and `DarkMode` to package `@chakra-ui/system` to -prevent circular dependencies. diff --git a/.changeset/mighty-monkeys-wash.md b/.changeset/mighty-monkeys-wash.md deleted file mode 100644 index 8b98e6cae05..00000000000 --- a/.changeset/mighty-monkeys-wash.md +++ /dev/null @@ -1,6 +0,0 @@ ---- -"@chakra-ui/styled-system": minor ---- - -Updated `_dark` and `_light` pseudo selectors to allow semantic tokens to change -with the `DarkMode` and `LightMode` component. diff --git a/.changeset/twenty-cooks-visit.md b/.changeset/twenty-cooks-visit.md index 3280fa5fddb..c8095ae0da3 100644 --- a/.changeset/twenty-cooks-visit.md +++ b/.changeset/twenty-cooks-visit.md @@ -2,6 +2,6 @@ "@chakra-ui/system": minor --- -Added `[data-theme]` to the CSS variables root selector. This allows the -semantic tokens to change according to `data-theme="dark"` and -`data-theme="light"` DOM element attributes. +Added `[data-css-vars-root=true]` to the CSS variables root selector. This +allows to layer the CSS variable definitions and allow the semantic tokens to +react to `data-theme="dark"` and `data-theme="light"`. diff --git a/.changeset/wild-shirts-smell.md b/.changeset/wild-shirts-smell.md deleted file mode 100644 index 54170e16200..00000000000 --- a/.changeset/wild-shirts-smell.md +++ /dev/null @@ -1,26 +0,0 @@ ---- -"@chakra-ui/color-mode": major ---- - -The `LightMode` and `DarkMode` components are now able to toggle semantic tokens -as well. - -For backward compatibility reasons this needs to be enabled by passing the -boolean prop `withSemanticTokens`. - -```tsx live=false - - - This uses always the _dark value of your semantic token - - -``` - -Please note that by adding the prop `withSemanticTokens` the ColorMode -components will render a DOM element which accepts style props as usual. - -```tsx - - ... - -``` diff --git a/.storybook/preview.tsx b/.storybook/preview.tsx index 9ac9cfabcb0..404d424a85a 100644 --- a/.storybook/preview.tsx +++ b/.storybook/preview.tsx @@ -56,20 +56,7 @@ const withChakra = (StoryFn: Function, context: StoryContext) => { }, [dir]) return ( - +
diff --git a/packages/color-mode/src/color-mode-provider.tsx b/packages/color-mode/src/color-mode-provider.tsx index e091f158eb5..ab7d7e7e04d 100644 --- a/packages/color-mode/src/color-mode-provider.tsx +++ b/packages/color-mode/src/color-mode-provider.tsx @@ -1,5 +1,5 @@ import { useEnvironment } from "@chakra-ui/react-env" -import { __DEV__, isBrowser, noop } from "@chakra-ui/utils" +import { isBrowser, noop, __DEV__ } from "@chakra-ui/utils" import * as React from "react" import { addListener, @@ -18,7 +18,7 @@ export interface ColorModeOptions { useSystemColorMode?: boolean } -export interface ColorModeContextType { +interface ColorModeContextType { colorMode: ColorMode toggleColorMode: () => void setColorMode: (value: any) => void @@ -173,6 +173,46 @@ if (__DEV__) { ColorModeProvider.displayName = "ColorModeProvider" } +/** + * Locks the color mode to `dark`, without any way to change it. + */ +export const DarkMode: React.FC = (props) => { + const context = React.useMemo( + () => ({ + colorMode: "dark", + toggleColorMode: noop, + setColorMode: noop, + }), + [], + ) + + return +} + +if (__DEV__) { + DarkMode.displayName = "DarkMode" +} + +/** + * Locks the color mode to `light` without any way to change it. + */ +export const LightMode: React.FC = (props) => { + const context = React.useMemo( + () => ({ + colorMode: "light", + toggleColorMode: noop, + setColorMode: noop, + }), + [], + ) + + return +} + +if (__DEV__) { + LightMode.displayName = "LightMode" +} + /** * Change value based on color mode. * diff --git a/packages/color-mode/test/color-mode-provider.test.tsx b/packages/color-mode/test/color-mode-provider.test.tsx index b28b67356f0..55e5950b465 100644 --- a/packages/color-mode/test/color-mode-provider.test.tsx +++ b/packages/color-mode/test/color-mode-provider.test.tsx @@ -1,7 +1,7 @@ import { render } from "@testing-library/react" import userEvent from "@testing-library/user-event" import React from "react" -import { ColorModeProvider } from "../src" +import { ColorModeProvider } from "../src/color-mode-provider" import * as colorModeUtils from "../src/color-mode.utils" import { defaultThemeOptions, diff --git a/packages/color-mode/test/color-mode-provider__server.test.tsx b/packages/color-mode/test/color-mode-provider__server.test.tsx index 0a45071af13..983ce910571 100644 --- a/packages/color-mode/test/color-mode-provider__server.test.tsx +++ b/packages/color-mode/test/color-mode-provider__server.test.tsx @@ -1,5 +1,5 @@ /* eslint-disable global-require */ -import * as React from "react" +import React from "react" import { render } from "@testing-library/react" import { createMockStorageManager, diff --git a/packages/color-mode/test/dark-mode.test.tsx b/packages/color-mode/test/dark-mode.test.tsx new file mode 100644 index 00000000000..c99aa3d048e --- /dev/null +++ b/packages/color-mode/test/dark-mode.test.tsx @@ -0,0 +1,77 @@ +import { render } from "@testing-library/react" +import userEvent from "@testing-library/user-event" +import React from "react" +import { DarkMode } from "../src/color-mode-provider" +import { + DummyComponent, + getColorModeButton, + MemoizedComponent, + RegularComponent, + resetCounter, +} from "./utils" + +const MemoTest = () => { + const [_, setRenderCount] = React.useState(0) + + return ( + <> + + + + + + ) +} + +const NoMemoTest = () => { + const [_, setRenderCount] = React.useState(0) + + return ( + <> + + + + + + ) +} + +describe("", () => { + beforeEach(() => { + resetCounter() + }) + + test("is always dark", () => { + render( + + + , + ) + + const button = getColorModeButton() + + expect(button).toHaveTextContent("dark") + + userEvent.click(button) + + expect(getColorModeButton()).toHaveTextContent("dark") + }) + + test("memoized component renders once", () => { + const { getByText, getByTestId } = render() + + userEvent.click(getByText("Rerender")) + userEvent.click(getByText("Rerender")) + + expect(getByTestId("rendered")).toHaveTextContent("1") + }) + + test("non memoized component renders multiple", () => { + const { getByText, getByTestId } = render() + + userEvent.click(getByText("Rerender")) + userEvent.click(getByText("Rerender")) + + expect(getByTestId("rendered")).toHaveTextContent("3") + }) +}) diff --git a/packages/system/tests/light-mode.test.tsx b/packages/color-mode/test/light-mode.test.tsx similarity index 72% rename from packages/system/tests/light-mode.test.tsx rename to packages/color-mode/test/light-mode.test.tsx index 54910cc1024..c98c240ceee 100644 --- a/packages/system/tests/light-mode.test.tsx +++ b/packages/color-mode/test/light-mode.test.tsx @@ -1,17 +1,17 @@ -import * as React from "react" -import { render, screen } from "@testing-library/react" +import { render } from "@testing-library/react" import userEvent from "@testing-library/user-event" -import { LightMode } from "../src" +import React from "react" +import { LightMode } from "../src/color-mode-provider" import { DummyComponent, getColorModeButton, MemoizedComponent, RegularComponent, resetCounter, -} from "./color-mode-component.utils" +} from "./utils" const MemoTest = () => { - const [, setRenderCount] = React.useState(0) + const [_, setRenderCount] = React.useState(0) return ( <> @@ -24,7 +24,7 @@ const MemoTest = () => { } const NoMemoTest = () => { - const [, setRenderCount] = React.useState(0) + const [_, setRenderCount] = React.useState(0) return ( <> @@ -57,13 +57,6 @@ describe("", () => { expect(getColorModeButton()).toHaveTextContent("light") }) - test("renders a DOM element with data-theme attribute when withSemanticTokens prop is set", async () => { - const label = "Test Component" - render({label}) - const element = await screen.findByText(label) - expect(element).toHaveAttribute("data-theme", "light") - }) - test("memoized component renders once", () => { const { getByText, getByTestId } = render() diff --git a/packages/color-mode/test/use-color-mode-value.test.tsx b/packages/color-mode/test/use-color-mode-value.test.tsx index 740c6a108a3..20afdfc2553 100644 --- a/packages/color-mode/test/use-color-mode-value.test.tsx +++ b/packages/color-mode/test/use-color-mode-value.test.tsx @@ -1,7 +1,11 @@ import React from "react" import { render, screen } from "@testing-library/react" import userEvent from "@testing-library/user-event" -import { ColorModeProvider, useColorModeValue, useColorMode } from "../src" +import { + ColorModeProvider, + useColorModeValue, + useColorMode, +} from "../src/color-mode-provider" import { defaultThemeOptions } from "./utils" const lightValue = "light-value" diff --git a/packages/color-mode/test/utils.tsx b/packages/color-mode/test/utils.tsx index 8b93af273cb..3b97684bfe6 100644 --- a/packages/color-mode/test/utils.tsx +++ b/packages/color-mode/test/utils.tsx @@ -1,14 +1,12 @@ -import * as React from "react" import theme from "@chakra-ui/theme" import { screen } from "@testing-library/react" -import { - useColorMode, - ColorModeOptions, - ColorMode, - StorageManager, -} from "../src" +import React from "react" +import { ColorModeOptions } from "../src/color-mode-provider" +import type { ColorMode } from "../src/color-mode.utils" +import type { StorageManager } from "../src/storage-manager" export const DummyComponent = () => { + const { useColorMode } = require("../src/color-mode-provider") const { colorMode, toggleColorMode } = useColorMode() return ( @@ -18,6 +16,22 @@ export const DummyComponent = () => { ) } +var renderCount = 0 + +export const resetCounter = () => { + renderCount = 0 +} + +export const MemoizedComponent = React.memo(() => { + renderCount = renderCount + 1 + return
{renderCount}
+}) + +export const RegularComponent = () => { + renderCount = renderCount + 1 + return
{renderCount}
+} + export const getColorModeButton = () => screen.getByRole("button") export const defaultThemeOptions = theme.config as Required diff --git a/packages/styled-system/src/pseudos.ts b/packages/styled-system/src/pseudos.ts index 688f35bab15..15277d23432 100644 --- a/packages/styled-system/src/pseudos.ts +++ b/packages/styled-system/src/pseudos.ts @@ -298,18 +298,12 @@ export const pseudoSelectors = { * Styles for when `data-theme` is applied to any parent of * this component or element. */ - _dark: - ".chakra-ui-dark &:not([data-theme])," + - "[data-theme=dark] &:not([data-theme])," + - "&[data-theme=dark]", + _dark: ".chakra-ui-dark &, [data-theme=dark] &, &[data-theme=dark]", /** * Styles for when `data-theme` is applied to any parent of * this component or element. */ - _light: - ".chakra-ui-light &:not([data-theme])," + - "[data-theme=light] &:not([data-theme])," + - "&[data-theme=light]", + _light: ".chakra-ui-light &, [data-theme=light] &, &[data-theme=light]", } export type Pseudos = typeof pseudoSelectors diff --git a/packages/styled-system/tests/css-var.test.ts b/packages/styled-system/tests/css-var.test.ts index 7a16f0f5271..15162868967 100644 --- a/packages/styled-system/tests/css-var.test.ts +++ b/packages/styled-system/tests/css-var.test.ts @@ -482,7 +482,7 @@ test("should convert semantic tokens", () => { "--colors-red-800": "#ff0080", "--colors-secondary": "var(--colors-red-800)", "--colors-success": "var(--colors-red-100)", - ".chakra-ui-dark &:not([data-theme]),[data-theme=dark] &:not([data-theme]),&[data-theme=dark]": Object { + ".chakra-ui-dark &, [data-theme=dark] &, &[data-theme=dark]": Object { "--colors-primary": "var(--colors-red-400)", "--colors-secondary": "var(--colors-red-700)", }, diff --git a/packages/system/src/color-mode-components.tsx b/packages/system/src/color-mode-components.tsx deleted file mode 100644 index 0a4026dcbd3..00000000000 --- a/packages/system/src/color-mode-components.tsx +++ /dev/null @@ -1,100 +0,0 @@ -import * as React from "react" -import { __DEV__, noop } from "@chakra-ui/utils" -import { ColorModeContext, ColorModeContextType } from "@chakra-ui/color-mode" -import { HTMLChakraProps } from "./system" -import { chakra } from "./factory" - -type WithDomElement = - | { - withSemanticTokens?: false - children?: React.ReactNode | undefined - } - | ({ - /** - * The DarkMode and LightMode components render a DOM element - * when `withSemanticTokens` is set to `true`. - * This forces the semantic tokens to use the desired color mode as well. - * - * This is an optional prop for backwards compatibility reasons and - * will be the default in an upcoming major release. - */ - withSemanticTokens: true - } & HTMLChakraProps<"div">) - -export type DarkModeProps = WithDomElement - -/** - * Locks the color mode to `dark`, without any way to change it. - */ -export const DarkMode = ({ - withSemanticTokens, - children, - ...restProps -}: DarkModeProps) => { - const colorMode = "dark" - const context = React.useMemo( - () => ({ - colorMode, - toggleColorMode: noop, - setColorMode: noop, - }), - [], - ) - - const maybeDomElement = withSemanticTokens ? ( - - {children} - - ) : ( - children - ) - - return ( - - {maybeDomElement} - - ) -} - -if (__DEV__) { - DarkMode.displayName = "DarkMode" -} - -export type LightModeProps = WithDomElement - -/** - * Locks the color mode to `light` without any way to change it. - */ -export const LightMode: React.FC = ({ - withSemanticTokens, - children, - ...restProps -}) => { - const colorMode = "light" - const context = React.useMemo( - () => ({ - colorMode, - toggleColorMode: noop, - setColorMode: noop, - }), - [], - ) - - const maybeDomElement = withSemanticTokens ? ( - - {children} - - ) : ( - children - ) - - return ( - - {maybeDomElement} - - ) -} - -if (__DEV__) { - LightMode.displayName = "LightMode" -} diff --git a/packages/system/src/index.ts b/packages/system/src/index.ts index 9c17ab9153a..73ef44fc50f 100644 --- a/packages/system/src/index.ts +++ b/packages/system/src/index.ts @@ -1,5 +1,4 @@ export * from "@chakra-ui/color-mode" -export * from "./color-mode-components" export * from "@chakra-ui/styled-system" export { keyframes } from "@emotion/react" export type { Interpolation } from "@emotion/react" diff --git a/packages/system/src/providers.tsx b/packages/system/src/providers.tsx index 47c229eeb8f..5fe06fd9815 100644 --- a/packages/system/src/providers.tsx +++ b/packages/system/src/providers.tsx @@ -34,18 +34,19 @@ export const ThemeProvider = (props: ThemeProviderProps) => { export interface CSSVarsProps { /** * The element to attach the CSS custom properties to. - * @default ":host, :root" + * Re-hoist CSS vars by attaching `data-css-vars-root={true}` to a DOM element. + * @example
+ * + * @default ":host, :root, [data-css-vars-root=true]" */ root?: string } -export const CSSVars = ({ root = ":host, :root" }: CSSVarsProps) => { - /** - * Append color mode selector to allow semantic tokens to change according to the color mode - */ - const selector = [root, `[data-theme]`].join(",") - return ({ [selector]: theme.__cssVars })} /> -} +export const CSSVars = ({ + root = ":host, :root, [data-css-vars-root=true]", +}: CSSVarsProps) => ( + ({ [root]: theme.__cssVars })} /> +) export function useTheme() { const theme = React.useContext( diff --git a/packages/system/stories/system.stories.tsx b/packages/system/stories/system.stories.tsx index c304ba483c6..fa1dd181634 100644 --- a/packages/system/stories/system.stories.tsx +++ b/packages/system/stories/system.stories.tsx @@ -4,8 +4,6 @@ import { Text } from "@chakra-ui/layout" import { motion } from "framer-motion" import { chakra, - LightMode, - DarkMode, PropsOf, ThemeProvider, ThemingProps, @@ -197,22 +195,3 @@ export const WithCSSVarToken = () => { ) } - -export const WithSemanticToken = () => { - return ( -
- I am in the default color mode - - I am forced to light mode - - - I am forced to dark mode - - - I am nested and forced to light mode - - - -
- ) -} diff --git a/packages/system/tests/color-mode-component.utils.tsx b/packages/system/tests/color-mode-component.utils.tsx deleted file mode 100644 index 9d69629d515..00000000000 --- a/packages/system/tests/color-mode-component.utils.tsx +++ /dev/null @@ -1,30 +0,0 @@ -import * as React from "react" -import { useColorMode } from "@chakra-ui/color-mode" -import { screen } from "@testing-library/react" - -let renderCount = 0 -export const resetCounter = () => { - renderCount = 0 -} - -export const MemoizedComponent = React.memo(() => { - renderCount = renderCount + 1 - return
{renderCount}
-}) - -export const RegularComponent = () => { - renderCount = renderCount + 1 - return
{renderCount}
-} - -export const DummyComponent = () => { - const { colorMode, toggleColorMode } = useColorMode() - - return ( - - ) -} - -export const getColorModeButton = () => screen.getByRole("button") diff --git a/packages/system/tests/dark-mode.test.tsx b/packages/system/tests/dark-mode.test.tsx deleted file mode 100644 index 48b1a603807..00000000000 --- a/packages/system/tests/dark-mode.test.tsx +++ /dev/null @@ -1,84 +0,0 @@ -import * as React from "react" -import { render, screen } from "@testing-library/react" -import userEvent from "@testing-library/user-event" -import { DarkMode } from "../src" -import { - DummyComponent, - getColorModeButton, - MemoizedComponent, - RegularComponent, - resetCounter, -} from "./color-mode-component.utils" - -describe("", () => { - const MemoTest = () => { - const [, setRenderCount] = React.useState(0) - - return ( - <> - - - - - - ) - } - - const NoMemoTest = () => { - const [, setRenderCount] = React.useState(0) - - return ( - <> - - - - - - ) - } - - beforeEach(() => { - resetCounter() - }) - - test("is always dark", () => { - render( - - - , - ) - - const button = screen.getByRole("button") - - expect(button).toHaveTextContent("dark") - - userEvent.click(button) - - expect(getColorModeButton()).toHaveTextContent("dark") - }) - - test("renders a DOM element with data-theme attribute when withSemanticTokens prop is set", async () => { - const label = "Test Component" - render({label}) - const element = await screen.findByText(label) - expect(element).toHaveAttribute("data-theme", "dark") - }) - - test("memoized component renders once", () => { - const { getByText, getByTestId } = render() - - userEvent.click(getByText("Rerender")) - userEvent.click(getByText("Rerender")) - - expect(getByTestId("rendered")).toHaveTextContent("1") - }) - - test("non memoized component renders multiple", () => { - const { getByText, getByTestId } = render() - - userEvent.click(getByText("Rerender")) - userEvent.click(getByText("Rerender")) - - expect(getByTestId("rendered")).toHaveTextContent("3") - }) -}) From 00d5d151631436777a8dc71a0b46c2be52e71631 Mon Sep 17 00:00:00 2001 From: Tim Kolberger Date: Wed, 9 Mar 2022 19:20:47 +0100 Subject: [PATCH 4/5] feat: re hoist css variables dom elements with data-theme attributes --- .changeset/mighty-monkeys-wash.md | 6 ++++++ .changeset/twenty-cooks-visit.md | 6 +++--- packages/styled-system/src/pseudos.ts | 10 ++++++++-- packages/styled-system/tests/css-var.test.ts | 2 +- packages/system/src/providers.tsx | 17 ++++++++--------- 5 files changed, 26 insertions(+), 15 deletions(-) create mode 100644 .changeset/mighty-monkeys-wash.md diff --git a/.changeset/mighty-monkeys-wash.md b/.changeset/mighty-monkeys-wash.md new file mode 100644 index 00000000000..07a89546218 --- /dev/null +++ b/.changeset/mighty-monkeys-wash.md @@ -0,0 +1,6 @@ +--- +"@chakra-ui/styled-system": minor +--- + +Updated `_dark` and `_light` pseudo selectors to allow semantic tokens to change +with the `data-theme` attributes. diff --git a/.changeset/twenty-cooks-visit.md b/.changeset/twenty-cooks-visit.md index c8095ae0da3..3280fa5fddb 100644 --- a/.changeset/twenty-cooks-visit.md +++ b/.changeset/twenty-cooks-visit.md @@ -2,6 +2,6 @@ "@chakra-ui/system": minor --- -Added `[data-css-vars-root=true]` to the CSS variables root selector. This -allows to layer the CSS variable definitions and allow the semantic tokens to -react to `data-theme="dark"` and `data-theme="light"`. +Added `[data-theme]` to the CSS variables root selector. This allows the +semantic tokens to change according to `data-theme="dark"` and +`data-theme="light"` DOM element attributes. diff --git a/packages/styled-system/src/pseudos.ts b/packages/styled-system/src/pseudos.ts index 15277d23432..688f35bab15 100644 --- a/packages/styled-system/src/pseudos.ts +++ b/packages/styled-system/src/pseudos.ts @@ -298,12 +298,18 @@ export const pseudoSelectors = { * Styles for when `data-theme` is applied to any parent of * this component or element. */ - _dark: ".chakra-ui-dark &, [data-theme=dark] &, &[data-theme=dark]", + _dark: + ".chakra-ui-dark &:not([data-theme])," + + "[data-theme=dark] &:not([data-theme])," + + "&[data-theme=dark]", /** * Styles for when `data-theme` is applied to any parent of * this component or element. */ - _light: ".chakra-ui-light &, [data-theme=light] &, &[data-theme=light]", + _light: + ".chakra-ui-light &:not([data-theme])," + + "[data-theme=light] &:not([data-theme])," + + "&[data-theme=light]", } export type Pseudos = typeof pseudoSelectors diff --git a/packages/styled-system/tests/css-var.test.ts b/packages/styled-system/tests/css-var.test.ts index 15162868967..7a16f0f5271 100644 --- a/packages/styled-system/tests/css-var.test.ts +++ b/packages/styled-system/tests/css-var.test.ts @@ -482,7 +482,7 @@ test("should convert semantic tokens", () => { "--colors-red-800": "#ff0080", "--colors-secondary": "var(--colors-red-800)", "--colors-success": "var(--colors-red-100)", - ".chakra-ui-dark &, [data-theme=dark] &, &[data-theme=dark]": Object { + ".chakra-ui-dark &:not([data-theme]),[data-theme=dark] &:not([data-theme]),&[data-theme=dark]": Object { "--colors-primary": "var(--colors-red-400)", "--colors-secondary": "var(--colors-red-700)", }, diff --git a/packages/system/src/providers.tsx b/packages/system/src/providers.tsx index 5fe06fd9815..47c229eeb8f 100644 --- a/packages/system/src/providers.tsx +++ b/packages/system/src/providers.tsx @@ -34,19 +34,18 @@ export const ThemeProvider = (props: ThemeProviderProps) => { export interface CSSVarsProps { /** * The element to attach the CSS custom properties to. - * Re-hoist CSS vars by attaching `data-css-vars-root={true}` to a DOM element. - * @example
- * - * @default ":host, :root, [data-css-vars-root=true]" + * @default ":host, :root" */ root?: string } -export const CSSVars = ({ - root = ":host, :root, [data-css-vars-root=true]", -}: CSSVarsProps) => ( - ({ [root]: theme.__cssVars })} /> -) +export const CSSVars = ({ root = ":host, :root" }: CSSVarsProps) => { + /** + * Append color mode selector to allow semantic tokens to change according to the color mode + */ + const selector = [root, `[data-theme]`].join(",") + return ({ [selector]: theme.__cssVars })} /> +} export function useTheme() { const theme = React.useContext( From ab161662455cd1f731fa91e21ce218122c93b633 Mon Sep 17 00:00:00 2001 From: Tim Kolberger Date: Wed, 9 Mar 2022 19:29:00 +0100 Subject: [PATCH 5/5] chore: add story --- .storybook/preview.tsx | 15 ++++++++++++++- packages/system/stories/system.stories.tsx | 19 +++++++++++++++++++ 2 files changed, 33 insertions(+), 1 deletion(-) diff --git a/.storybook/preview.tsx b/.storybook/preview.tsx index 404d424a85a..9ac9cfabcb0 100644 --- a/.storybook/preview.tsx +++ b/.storybook/preview.tsx @@ -56,7 +56,20 @@ const withChakra = (StoryFn: Function, context: StoryContext) => { }, [dir]) return ( - +
diff --git a/packages/system/stories/system.stories.tsx b/packages/system/stories/system.stories.tsx index fa1dd181634..e0b280b5916 100644 --- a/packages/system/stories/system.stories.tsx +++ b/packages/system/stories/system.stories.tsx @@ -195,3 +195,22 @@ export const WithCSSVarToken = () => { ) } + +export const WithSemanticTokens = () => { + return ( +
+ I am in the default color mode +
+ I am forced to light mode (red) +
+
+ I am forced to dark mode (blue) +
+ + I am nested and forced to light mode (red) + +
+
+
+ ) +}