Storybook 的主題、主題提供器和真正的暗黑模式
Storybook Facelift 是零設定的,它只會為原生主題返回一個淺色/深色模式按鈕
但你也可以
- 使用內建的主題支援,新增可以主題化 Storybook 的主題,來自
- Storybook 主題
- Material UI 主題
- 如果提供主題轉換器,則提供自訂主題
- 新增可以使用內建主題提供器來裝飾元件的主題,來自
- 真正的暗黑模式
- 為 @storybook/addon-docs 和更多 UI 控制項解鎖暗黑模式和欄控制
安裝
npm i -D storybook-facelift
設定擴充套件
將擴充套件新增到你的 Storybook main.js
檔案中 (或 main.ts
- 從現在開始只假設為 js...)
module.exports = {
addons: ['storybook-facelift'],
}
為了充分利用擴充套件,你可能需要在 preview.js
中透過參數來設定它。
export const parameters = {
facelift: {...},
}
TypeScript 支援範例
Storybook Facelift 提供自訂的 Parameters
型別,以協助你在參數中獲得型別安全。
它接受一個泛型,讓你可以從其他擴充套件新增更多參數型別,並保留 Storybook 參數的型別安全
import type { Parameters } from 'storybook-facelift'
import type { OtherAddonParam } from 'other-addon'
export const parameters: Parameters<{
otherAddon: OtherAddonParam,
}> = {
actions: { argTypesRegex: '^on[A-Z].*' },
otherAddon: {...},
facelift: {...},
}
設定 Story
你也可以在 Story 層級設定 Storybook Facelift,例如在 Story 層級而非全域層級啟用帶有主題提供器的自動主題化,甚至可以為此 Story 新增一個特殊的主題提供器
import React from 'react'
import { Tag } from './Tag'
export default {
title: 'UI/Tag',
component: Tag,
parameters: {
facelift: {
addProvider: true,
provider: 'styled',
providerTheme: 'theme-1',
},
},
}
const Template = (args) => <Tag {...args} />
export const Controllable = Template.bind({})
Controllable.args = {
label: 'Tag',
}
TypeScript 支援範例
Storybook Facelift 提供自訂的 Meta 型別,以協助你在 Story 參數中獲得型別安全。
此型別接受 2 個泛型引數,即額外的參數型別和 Storybook 自己的 Args
(遺憾的是,如果你希望應用 Args
泛型並且沒有額外的擴充套件參數型別要提供,則必須提供一個空物件作為第一個泛型)
import React from 'react'
import { Tag } from './Tag'
import type { Story } from '@storybook/react'
import type { Meta } from 'storybook-facelift'
import type { TagProps } from './Tag'
import type { OtherAddonParam } from 'other-addon'
export default {
title: 'UI/Tag',
component: Tag,
parameters: {
otherAddon: {...},
facelift: {...},
},
} as Meta<{otherAddon: OtherAddonParam}>
const Template: Story<TagProps> = (args) => <Tag {...args} />
export const Controllable = Template.bind({})
Controllable.args = {
label: 'Tag',
}
擴充套件參數
"addProvider"?: boolean
"autoThemeStory"?: boolean // deprecated - use addProvider
"defaultTheme"?: string
"defaultVariant"?: "light" | "dark"
"docs"?: ParamDocs
"enhanceUi"?: boolean
"includeNative"?: boolean
"native"?: ParamNative
"override"?: ThemeOptionsOverride
"provider"?: "mui" | "styled" | "emotion"
"providerTheme"?: string
"themeConverters"?: Record<string, ThemeConverterFn>
"themes"?: ParamTheme[]
"ui"?: ParamUi
addProvider boolean
全域或在 Story 層級啟用主題提供器
defaultTheme string
啟動 Storybook 時使用的預設主題 - 主題參數中的鍵用作參考
defaultVariant "light" | "dark"
用於 Storybook 主題的預設主題變體
docs ParamDocs
增強的文件控制
// Set to true to hide the column borders in docs table
"hidePropertyBorders"?: boolean
// Set to true to hide description column in docs table
"hideDescription"?: boolean
// Set to true to hide default value column in docs table
"hideDefaults"?: boolean
// Set to true to hide the controls column in docs
"hideControls"?: boolean
// Set to true to hide the sibling stories shown below property table
"hideStories"?: boolean
// Set to either full or simple - full is default, and simple will ONLY show docs table
"type"?: "full" | "simple"
enhanceUi boolean
修正一些小的 css 錯誤,並允許使用 ui
參數
includeNative boolean
如果提供了自訂主題,則將此參數設定為 true
,以便包含原生的 Storybook 主題
override ThemeOptionsOverride
Storybook 主題選項物件,它將擴充到預設的 Storybook 主題選項,用作所有主題建立的預設值
除非稍後覆寫值,否則此處新增的任何值都會出現在最終的主題輸出中 (通常除了 brandTitle
、brandUrl
和 brandImage
之外的所有值)
"colorPrimary"?: string
"colorSecondary"?: string
"appBg"?: string
"appContentBg"?: string
"appBorderColor"?: string
"appBorderRadius"?: number
"fontBase"?: string
"fontCode"?: string
"textColor"?: string
"textInverseColor"?: string
"textMutedColor"?: string
"barTextColor"?: string
"barSelectedColor"?: string
"barBg"?: string
"inputBg"?: string
"inputBorder"?: string
"inputTextColor"?: string
"inputBorderRadius"?: number
"brandTitle"?: string
"brandUrl"?: string
"brandImage"?: string
"gridCellSize"?: number
native ParamNative
調整原生主題的簡單便利參數,以及透過 override
完全控制
// Title to show in the menu picker
"title"?: string
// Control which theme variants are available - defaults to ["light", "dark"]
"variants"?: ("light" | "dark")[]
// Control the usage of Storybooks theme values in the backgrounds
"background"?: "normal" | "reverse" | "equal" | "equal-reverse" | "equal-app" | "equal-content"
// Override any default native theme options from Storybook
"override"?: ThemeOptionsOverride
themeConverters Record<string, ThemeConverterFn>
提供自訂轉換器函式,將你的自訂主題轉換為 Storybook 主題
函式的鍵將使轉換器可以透過主題的 converter
選項存取主題
前往 範例 以了解如何實作自訂主題
[key]: (props: {
"override"?: ThemeOptionsOverride
"theme": ThemeOptions
"variant": "light" | "dark"
"background"?: "normal" | "reverse" | "equal" | "equal-reverse" | "equal-app" | "equal-content"
"responsiveFontSizes"?: boolean
}) => {
"storybook": StorybookThemeOptions
"instanciated": ThemeInstanciated
"options": ThemeOptions
} | null
themes ParamTheme[]
主題設定
// Unique key for this theme entry
"key": string
// Use the built in support of Storybook or Material UI
// Or indicate you are providing a custom theme
"type": "native" | "mui" | "custom"
// The title used in the theme picker
"title": string
// The name of the converter function to use - if the theme type
// is "mui" or "native" you do not need to set this
"converter"?: string
// The theme provider to use for this theme if "addProvider" for story is true
"provider"?: "mui" | "styled" | "emotion"
// The key of the theme to use for the theme provider if "addProvider" is true
"providerTheme"?: string
// Indicate that this theme is only to be used for theme providers - not to theme Storybook
"providerOnly"?: boolean
// These are the theme options for light and/or dark mode.
"variants": {
"light"?: ThemeOptions
"dark"?: ThemeOptions
}
// Override any Storybook theme options value for this theme
"override"?: ThemeOptionsOverride
// Ability to configure how backgrounds are used in the Storybook theme
// 'reverse' will swap between app and content etc..
"background"?: "normal" | "reverse" | "equal" | "equal-reverse" | "equal-app" | "equal-content"
// This is for typography - use responsive font sizes or not (only MUI support)
"resposiveFontSizes"?: boolean
ui ParamUi
// How much to elevate the content panel
"elevation"?: 0 | 1 | 2 | 3 | 4
// Ability to override SB's own preview panel padding
"padding"?: string
// Ability to use a custom css box-shadow string for content elevation
"shadow"?: string
範例
僅具有淺色變體的最小原生 Storybook 主題
export const parameters = {
facelift: {
themes: [
{
key: 'native-1',
type: 'native',
title: 'Custom Storybook theme',
variants: {
light: {
colorPrimary: '#0000ff',
},
},
},
],
},
}
具有預設 Material UI 淺色和深色主題的範例
使用預設 Material UI 主題設定 Storybook 主題,並為所有 Story 新增具有相同主題的 Material UI 主題提供器
export const parameters = {
facelift: {
addProvider: true,
themes: [
{
type: 'mui',
key: 'mui-1',
title: 'Default Material UI theme',
variants: {
light: {},
dark: {},
},
},
],
},
}
具有自訂淺色主題和 Styled Components 主題提供器的範例
這個非常小的範例將以最小的自訂主題設定 Storybook 主題,並為 Story 新增一個 Style Components 主題提供器
export const parameters = {
facelift: {
addProvider: true,
themeConverters: {
myCustomConverter: ({ theme, variant }) => ({
storybook: {
base: variant,
colorPrimary: theme.primary,
colorSecondary: theme.secondary,
},
options: theme,
instanciated: theme,
}),
},
themes: [
{
type: 'custom',
key: 'custom-1',
title: 'Custom UI theme',
converter: 'myCustomConverter',
provider: 'styled',
variants: {
light: {
primary: '#ff0000',
secondary: '#0000ff',
},
},
},
],
},
}