From fac78ee4aad272e60b6ebfbdc64fdc2d7ef95471 Mon Sep 17 00:00:00 2001 From: Eric Liu Date: Sat, 10 Jul 2021 16:00:03 -0700 Subject: [PATCH] feat(theme): add Theme (#741) * feat(theme): add Theme * fix(theme): fix broken type test * docs(theme): add examples * docs(theme): add description, update carbon theme link [ci skip] * docs: pre-wrap type code snippet [ci skip] --- COMPONENT_INDEX.md | 35 +++++- docs/src/COMPONENT_API.json | 105 +++++++++++++++- docs/src/components/ComponentApi.svelte | 4 + docs/src/pages/_layout.svelte | 4 +- docs/src/pages/components/Theme.svx | 46 +++++++ docs/src/pages/framed/Theme/Theme.svelte | 17 +++ .../pages/framed/Theme/ThemePersist.svelte | 17 +++ .../src/pages/framed/Theme/ThemeSelect.svelte | 5 + .../framed/Theme/ThemeSelectCustom.svelte | 12 ++ .../src/pages/framed/Theme/ThemeToggle.svelte | 5 + .../framed/Theme/ThemeToggleCustom.svelte | 14 +++ .../src/pages/framed/Theme/ThemeTokens.svelte | 14 +++ src/Theme/Theme.svelte | 118 ++++++++++++++++++ src/Theme/index.js | 1 + src/index.js | 1 + tests/Theme.test.svelte | 24 ++++ types/Theme/Theme.d.ts | 56 +++++++++ types/index.d.ts | 1 + 18 files changed, 475 insertions(+), 4 deletions(-) create mode 100644 docs/src/pages/components/Theme.svx create mode 100644 docs/src/pages/framed/Theme/Theme.svelte create mode 100644 docs/src/pages/framed/Theme/ThemePersist.svelte create mode 100644 docs/src/pages/framed/Theme/ThemeSelect.svelte create mode 100644 docs/src/pages/framed/Theme/ThemeSelectCustom.svelte create mode 100644 docs/src/pages/framed/Theme/ThemeToggle.svelte create mode 100644 docs/src/pages/framed/Theme/ThemeToggleCustom.svelte create mode 100644 docs/src/pages/framed/Theme/ThemeTokens.svelte create mode 100644 src/Theme/Theme.svelte create mode 100644 src/Theme/index.js create mode 100644 tests/Theme.test.svelte create mode 100644 types/Theme/Theme.d.ts diff --git a/COMPONENT_INDEX.md b/COMPONENT_INDEX.md index c41c2973..ff123def 100644 --- a/COMPONENT_INDEX.md +++ b/COMPONENT_INDEX.md @@ -1,6 +1,6 @@ # Component Index -> 171 components exported from carbon-components-svelte@0.39.0. +> 172 components exported from carbon-components-svelte@0.39.0. ## Components @@ -153,6 +153,7 @@ - [`TextAreaSkeleton`](#textareaskeleton) - [`TextInput`](#textinput) - [`TextInputSkeleton`](#textinputskeleton) +- [`Theme`](#theme) - [`Tile`](#tile) - [`TileGroup`](#tilegroup) - [`TimePicker`](#timepicker) @@ -4201,6 +4202,38 @@ None. | mouseenter | forwarded | -- | | mouseleave | forwarded | -- | +## `Theme` + +### Types + +```ts +export type CarbonTheme = "white" | "g10" | "g80" | "g90" | "g100"; +``` + +### Props + +| Prop name | Kind | Reactive | Type | Default value | Description | +| :--------- | :--------------- | :------- | :------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------- | +| theme | let | Yes | CarbonTheme | "white" | Set the current Carbon theme | +| tokens | let | No | { [token: string]: any; } | {} | Customize a theme with your own tokens
https://carbondesignsystem.com/guidelines/themes/overview#customizing-a-theme | +| persist | let | No | boolean | false | Set to `true` to persist the theme using window.localStorage | +| persistKey | let | No | string | "theme" | Specify the local storage key | +| render | let | No | "toggle" | "select" | -- | Render a toggle or select dropdown to control the theme | +| toggle | let | No | import("../Toggle/Toggle").ToggleProps & { themes?: [labelA: CarbonTheme, labelB: CarbonTheme]; } | { themes: ["white", "g100"], labelA: "", labelB: "", labelText: "Dark mode", hideLabel: false, } | Override the default toggle props | +| select | let | No | import("../Select/Select").SelectProps & { themes?: CarbonTheme[]; } | { themes: themeKeys, labelText: "Themes", hideLabel: false, } | Override the default select props | + +### Slots + +| Slot name | Default | Props | Fallback | +| :-------- | :------ | :------------------------------------ | :------- | +| -- | Yes | { theme: CarbonTheme; } | -- | + +### Events + +| Event name | Type | Detail | +| :--------- | :--------- | :----------------------------------- | +| update | dispatched | { theme: CarbonTheme; } | + ## `Tile` ### Props diff --git a/docs/src/COMPONENT_API.json b/docs/src/COMPONENT_API.json index dd439d46..9ccebf74 100644 --- a/docs/src/COMPONENT_API.json +++ b/docs/src/COMPONENT_API.json @@ -1,5 +1,5 @@ { - "total": 171, + "total": 172, "components": [ { "moduleName": "Accordion", @@ -11573,6 +11573,109 @@ "typedefs": [], "rest_props": { "type": "Element", "name": "div" } }, + { + "moduleName": "Theme", + "filePath": "src/Theme/Theme.svelte", + "props": [ + { + "name": "theme", + "kind": "let", + "description": "Set the current Carbon theme", + "type": "CarbonTheme", + "value": "\"white\"", + "isFunction": false, + "isFunctionDeclaration": false, + "constant": false, + "reactive": true + }, + { + "name": "tokens", + "kind": "let", + "description": "Customize a theme with your own tokens\nhttps://carbondesignsystem.com/guidelines/themes/overview#customizing-a-theme", + "type": "{ [token: string]: any; }", + "value": "{}", + "isFunction": false, + "isFunctionDeclaration": false, + "constant": false, + "reactive": false + }, + { + "name": "persist", + "kind": "let", + "description": "Set to `true` to persist the theme using window.localStorage", + "type": "boolean", + "value": "false", + "isFunction": false, + "isFunctionDeclaration": false, + "constant": false, + "reactive": false + }, + { + "name": "persistKey", + "kind": "let", + "description": "Specify the local storage key", + "type": "string", + "value": "\"theme\"", + "isFunction": false, + "isFunctionDeclaration": false, + "constant": false, + "reactive": false + }, + { + "name": "render", + "kind": "let", + "description": "Render a toggle or select dropdown to control the theme", + "type": "\"toggle\" | \"select\"", + "isFunction": false, + "isFunctionDeclaration": false, + "constant": false, + "reactive": false + }, + { + "name": "toggle", + "kind": "let", + "description": "Override the default toggle props", + "type": "import(\"../Toggle/Toggle\").ToggleProps & { themes?: [labelA: CarbonTheme, labelB: CarbonTheme]; }", + "value": "{ themes: [\"white\", \"g100\"], labelA: \"\", labelB: \"\", labelText: \"Dark mode\", hideLabel: false, }", + "isFunction": false, + "isFunctionDeclaration": false, + "constant": false, + "reactive": false + }, + { + "name": "select", + "kind": "let", + "description": "Override the default select props", + "type": "import(\"../Select/Select\").SelectProps & { themes?: CarbonTheme[]; }", + "value": "{ themes: themeKeys, labelText: \"Themes\", hideLabel: false, }", + "isFunction": false, + "isFunctionDeclaration": false, + "constant": false, + "reactive": false + } + ], + "slots": [ + { + "name": "__default__", + "default": true, + "slot_props": "{ theme: CarbonTheme; }" + } + ], + "events": [ + { + "type": "dispatched", + "name": "update", + "detail": "{ theme: CarbonTheme; }" + } + ], + "typedefs": [ + { + "type": "\"white\" | \"g10\" | \"g80\" | \"g90\" | \"g100\"", + "name": "CarbonTheme", + "ts": "type CarbonTheme = \"white\" | \"g10\" | \"g80\" | \"g90\" | \"g100\"" + } + ] + }, { "moduleName": "Tile", "filePath": "src/Tile/Tile.svelte", diff --git a/docs/src/components/ComponentApi.svelte b/docs/src/components/ComponentApi.svelte index 495690b2..05a491d1 100644 --- a/docs/src/components/ComponentApi.svelte +++ b/docs/src/components/ComponentApi.svelte @@ -221,4 +221,8 @@ code { word-break: break-word; } + + :global(.cell .bx--snippet--inline code, .bx--snippet--single pre) { + white-space: pre-wrap !important; + } diff --git a/docs/src/pages/_layout.svelte b/docs/src/pages/_layout.svelte index 1a41c8f0..b5743fde 100644 --- a/docs/src/pages/_layout.svelte +++ b/docs/src/pages/_layout.svelte @@ -20,7 +20,7 @@ import Footer from "../components/Footer.svelte"; const deprecated = ["ToggleSmall", "Icon"]; - const new_components = ["Breakpoint", "RecursiveList", "TreeView"]; + const new_components = ["Theme"]; let isOpen = false; let isSideNavOpen = true; @@ -269,6 +269,6 @@ } .bx--side-nav__submenu[aria-expanded="true"] + .bx--side-nav__menu { - max-height: 132rem; + max-height: 144rem; } diff --git a/docs/src/pages/components/Theme.svx b/docs/src/pages/components/Theme.svx new file mode 100644 index 00000000..395e077f --- /dev/null +++ b/docs/src/pages/components/Theme.svx @@ -0,0 +1,46 @@ + + +This utility component dynamically updates the Carbon theme on the client-side using CSS variables. + +### Default + + + +### Persist locally + +Set `persist` to `true` to persist the theme locally using the [Window.localStorage API](https://developer.mozilla.org/en-US/docs/Web/API/Window/localStorage). + + + +### Custom theme + +Define keys and values in the `tokens` prop that override default Carbon theme tokens. Refer to the [Carbon website](https://carbondesignsystem.com/guidelines/themes/overview#customizing-a-theme) for guidance on customizing a theme using token values. + + + +### Theme toggle + +Set `render` to `"toggle"` to render a toggle switch to control the theme. + + + +### Theme toggle (custom) + +Customize the toggle using the `toggle` prop. + + + +### Theme select + +Set `render` to `"select"` to render a select dropdown to control the theme. + + + +### Theme select (custom) + +Customize the select using the `select` prop. + + \ No newline at end of file diff --git a/docs/src/pages/framed/Theme/Theme.svelte b/docs/src/pages/framed/Theme/Theme.svelte new file mode 100644 index 00000000..b99cb540 --- /dev/null +++ b/docs/src/pages/framed/Theme/Theme.svelte @@ -0,0 +1,17 @@ + + + + + + {#each ["white", "g10", "g80", "g90", "g100"] as value} + + {/each} + diff --git a/docs/src/pages/framed/Theme/ThemePersist.svelte b/docs/src/pages/framed/Theme/ThemePersist.svelte new file mode 100644 index 00000000..bd43a91a --- /dev/null +++ b/docs/src/pages/framed/Theme/ThemePersist.svelte @@ -0,0 +1,17 @@ + + + + + + {#each ["white", "g10", "g80", "g90", "g100"] as value} + + {/each} + diff --git a/docs/src/pages/framed/Theme/ThemeSelect.svelte b/docs/src/pages/framed/Theme/ThemeSelect.svelte new file mode 100644 index 00000000..3d967526 --- /dev/null +++ b/docs/src/pages/framed/Theme/ThemeSelect.svelte @@ -0,0 +1,5 @@ + + + diff --git a/docs/src/pages/framed/Theme/ThemeSelectCustom.svelte b/docs/src/pages/framed/Theme/ThemeSelectCustom.svelte new file mode 100644 index 00000000..0a8ad4b1 --- /dev/null +++ b/docs/src/pages/framed/Theme/ThemeSelectCustom.svelte @@ -0,0 +1,12 @@ + + + diff --git a/docs/src/pages/framed/Theme/ThemeToggle.svelte b/docs/src/pages/framed/Theme/ThemeToggle.svelte new file mode 100644 index 00000000..f1020cff --- /dev/null +++ b/docs/src/pages/framed/Theme/ThemeToggle.svelte @@ -0,0 +1,5 @@ + + + diff --git a/docs/src/pages/framed/Theme/ThemeToggleCustom.svelte b/docs/src/pages/framed/Theme/ThemeToggleCustom.svelte new file mode 100644 index 00000000..635bd7b3 --- /dev/null +++ b/docs/src/pages/framed/Theme/ThemeToggleCustom.svelte @@ -0,0 +1,14 @@ + + + diff --git a/docs/src/pages/framed/Theme/ThemeTokens.svelte b/docs/src/pages/framed/Theme/ThemeTokens.svelte new file mode 100644 index 00000000..3a2b1d2f --- /dev/null +++ b/docs/src/pages/framed/Theme/ThemeTokens.svelte @@ -0,0 +1,14 @@ + + + + + diff --git a/src/Theme/Theme.svelte b/src/Theme/Theme.svelte new file mode 100644 index 00000000..97af924b --- /dev/null +++ b/src/Theme/Theme.svelte @@ -0,0 +1,118 @@ + + +{#if persist} + +{/if} + +{#if render === "toggle"} + +{:else if render === "select"} + +{/if} + + diff --git a/src/Theme/index.js b/src/Theme/index.js new file mode 100644 index 00000000..79f7e13d --- /dev/null +++ b/src/Theme/index.js @@ -0,0 +1 @@ +export { default as Theme } from "./Theme.svelte"; diff --git a/src/index.js b/src/index.js index c73f55f6..0b8733d3 100644 --- a/src/index.js +++ b/src/index.js @@ -113,6 +113,7 @@ export { Tabs, Tab, TabContent, TabsSkeleton } from "./Tabs"; export { Tag, TagSkeleton } from "./Tag"; export { TextArea, TextAreaSkeleton } from "./TextArea"; export { TextInput, TextInputSkeleton, PasswordInput } from "./TextInput"; +export { Theme } from "./Theme"; export { Tile, ClickableTile, diff --git a/tests/Theme.test.svelte b/tests/Theme.test.svelte new file mode 100644 index 00000000..3a3c85ba --- /dev/null +++ b/tests/Theme.test.svelte @@ -0,0 +1,24 @@ + + + diff --git a/types/Theme/Theme.d.ts b/types/Theme/Theme.d.ts new file mode 100644 index 00000000..16d10f38 --- /dev/null +++ b/types/Theme/Theme.d.ts @@ -0,0 +1,56 @@ +/// +import { SvelteComponentTyped } from "svelte"; + +export type CarbonTheme = "white" | "g10" | "g80" | "g90" | "g100"; + +export interface ThemeProps { + /** + * Set the current Carbon theme + * @default "white" + */ + theme?: CarbonTheme; + + /** + * Customize a theme with your own tokens + * https://carbondesignsystem.com/guidelines/themes/overview#customizing-a-theme + * @default {} + */ + tokens?: { [token: string]: any }; + + /** + * Set to `true` to persist the theme using window.localStorage + * @default false + */ + persist?: boolean; + + /** + * Specify the local storage key + * @default "theme" + */ + persistKey?: string; + + /** + * Render a toggle or select dropdown to control the theme + */ + render?: "toggle" | "select"; + + /** + * Override the default toggle props + * @default { themes: ["white", "g100"], labelA: "", labelB: "", labelText: "Dark mode", hideLabel: false, } + */ + toggle?: import("../Toggle/Toggle").ToggleProps & { + themes?: [labelA: CarbonTheme, labelB: CarbonTheme]; + }; + + /** + * Override the default select props + * @default { themes: themeKeys, labelText: "Themes", hideLabel: false, } + */ + select?: import("../Select/Select").SelectProps & { themes?: CarbonTheme[] }; +} + +export default class Theme extends SvelteComponentTyped< + ThemeProps, + { update: CustomEvent<{ theme: CarbonTheme }> }, + { default: { theme: CarbonTheme } } +> {} diff --git a/types/index.d.ts b/types/index.d.ts index 4dff84bd..57a8a278 100644 --- a/types/index.d.ts +++ b/types/index.d.ts @@ -129,6 +129,7 @@ export { default as TextAreaSkeleton } from "./TextArea/TextAreaSkeleton"; export { default as TextInput } from "./TextInput/TextInput"; export { default as TextInputSkeleton } from "./TextInput/TextInputSkeleton"; export { default as PasswordInput } from "./TextInput/PasswordInput"; +export { default as Theme } from "./Theme/Theme"; export { default as Tile } from "./Tile/Tile"; export { default as ClickableTile } from "./Tile/ClickableTile"; export { default as ExpandableTile } from "./Tile/ExpandableTile";