首先,你需要将 Vuetify 的字体加载器和插件添加到你的 Storybook 配置中。为此,将以下内容添加到你的 .storybook/preview.js
文件中
// .storybook/preview.js
import { setup } from '@storybook/vue3';
import { registerPlugins } from '../src/plugins';
setup((app) => {
// Registers your app's plugins into Storybook
registerPlugins(app);
});
在这里,registerPlugins
会加载 Vuetify 的字体,并将所有组件注册到 Storybook 的 Vue 应用中。
接下来,你需要用 Vuetify 的 v-app
组件包裹你的故事,以便使用其一些大型布局组件,例如 v-app-bar
。为此,在 .storybook/
目录中创建一个名为 StoryWrapper.vue
的组件。
<!-- .storybook/StoryWrapper.vue -->
<template>
<v-app>
<v-main>
<slot name="story"></slot>
</v-main>
</v-app>
</template>
<script></script>
withVuetifyTheme
装饰器现在创建一个 Storybook 装饰器,用它来将你的故事包裹在 StoryWrapper 组件中。
下面我在 .storybook
目录中创建了一个新文件,名为 withVuetifyTheme.decorator.js
。
// .storybook/withVeutifyTheme.decorator.js
import { h } from 'vue';
import StoryWrapper from './StoryWrapper.vue';
export const withVuetifyTheme = (storyFn, context) => {
const story = storyFn();
return () => {
return h(
StoryWrapper,
{}, // Props for StoryWrapper
{
// Puts your story into StoryWrapper's "story" slot with your story args
story: () => h(story, { ...context.args }),
}
);
};
};
现在,在你的 preview.js
文件中将此装饰器提供给 Storybook。
// .storybook/preview.js
import { setup } from '@storybook/vue3';
import { registerPlugins } from '../src/plugins';
import { withVuetifyTheme } from './withVuetifyTheme.decorator';
setup((app) => {
registerPlugins(app);
});
/* snipped for brevity */
export const decorators = [withVuetifyTheme];
Vuetify 自带浅色和深色主题,你可以覆盖它们或添加新主题。为了充分利用你的故事,你应该有一个在所有主题之间切换的方式。
要添加我们的切换器,请在 .storybook/preview.js
文件中声明一个名为 theme
的 全局类型,并为其指定一个支持的主题列表供选择。
// .storybook/preview.js
export const globalTypes = {
theme: {
name: 'Theme',
description: 'Global theme for components',
toolbar: {
icon: 'paintbrush',
// Array of plain string values or MenuItem shape
items: [
{ value: 'light', title: 'Light', left: '🌞' },
{ value: 'dark', title: 'Dark', left: '🌛' },
],
// Change title based on selected value
dynamicTitle: true,
},
},
};
这段代码将在工具栏中创建一个新菜单,用于为你的故事选择所需的主题。
需要有一种方法告知 Vuetify 使用工具栏中选定的主题。这可以通过更新我们的 StoryWrapper
组件和 withVuetifyTheme
装饰器来实现。
首先,给 StoryWrapper
组件一个 themeName
prop,该 prop 可以传递给 v-app
组件。
<template>
<v-app :theme="themeName">
<v-main>
<slot name="story"></slot>
</v-main>
</v-app>
</template>
<script>
export default {
props: {
themeName: String,
},
};
</script>
现在,通过我们的装饰器,将我们的全局 theme
变量作为 prop 传递给我们的 StoryWrapper
组件。
// .storybook/withVeutifyTheme.decorator.js
import { h } from 'vue';
import StoryWrapper from './StoryWrapper.vue';
export const DEFAULT_THEME = 'light';
export const withVuetifyTheme = (storyFn, context) => {
// Pull our global theme variable, fallback to DEFAULT_THEME
const themeName = context.globals.theme || DEFAULT_THEME;
const story = storyFn();
return () => {
return h(
StoryWrapper,
// give themeName to StoryWrapper as a prop
{ themeName },
{
story: () => h(story, { ...context.args }),
}
);
};
};
现在你已经准备好在 Storybook 中使用 Vuetify 了。🎉 查看示例仓库以便快速开始。
如果你在工作中使用 Vuetify,我们很希望能得到你的帮助来制作一个插件,它能自动应用上述配置。加入 Discord 与维护者交流并参与贡献,或者直接阅读插件文档。