mirror of
https://github.com/storybookjs/storybook.git
synced 2025-04-02 05:03:44 +08:00
feat!(vue3): remove args-as-props & replace with returning args from setup
This commit is contained in:
parent
bbade6137e
commit
64a8885681
@ -14,8 +14,6 @@ import { IStorybookSection, StoryFnVueReturnType } from './types';
|
||||
|
||||
import render, { storybookApp } from './render';
|
||||
|
||||
const PROPS = 'STORYBOOK_PROPS';
|
||||
|
||||
/*
|
||||
This normalizes a functional component into a render method in ComponentOptions.
|
||||
|
||||
@ -36,31 +34,12 @@ function prepare(story: StoryFnVueReturnType, innerStory?: ConcreteComponent): C
|
||||
// Normalize so we can always spread an object
|
||||
...normalizeFunctionalComponent(story),
|
||||
components: { story: innerStory },
|
||||
props: innerStory.props,
|
||||
inject: {
|
||||
props: {
|
||||
from: PROPS,
|
||||
default: null,
|
||||
},
|
||||
},
|
||||
provide() {
|
||||
return {
|
||||
[PROPS]: this.props || this.$props,
|
||||
};
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
return {
|
||||
props: story.props,
|
||||
inject: {
|
||||
props: {
|
||||
from: PROPS,
|
||||
default: null,
|
||||
},
|
||||
},
|
||||
render() {
|
||||
return h(story, this.props || this.$props);
|
||||
return h(story);
|
||||
},
|
||||
};
|
||||
}
|
||||
|
@ -1,10 +1,8 @@
|
||||
import type { Args } from '@storybook/addons';
|
||||
import dedent from 'ts-dedent';
|
||||
import { createApp, h, shallowRef, ComponentPublicInstance } from 'vue';
|
||||
import { RenderContext, StoryFnVueReturnType } from './types';
|
||||
|
||||
const activeStoryComponent = shallowRef<StoryFnVueReturnType | null>(null);
|
||||
const activeProps = shallowRef<Args>({});
|
||||
|
||||
let root: ComponentPublicInstance | null = null;
|
||||
|
||||
@ -18,7 +16,7 @@ export const storybookApp = createApp({
|
||||
return () => {
|
||||
if (!activeStoryComponent.value)
|
||||
throw new Error('No Vue 3 Story available. Was it set correctly?');
|
||||
return h(activeStoryComponent.value, activeProps.value);
|
||||
return h(activeStoryComponent.value);
|
||||
};
|
||||
},
|
||||
});
|
||||
@ -51,7 +49,6 @@ export default function render({
|
||||
showMain();
|
||||
|
||||
activeStoryComponent.value = element;
|
||||
activeProps.value = args;
|
||||
|
||||
if (!root) {
|
||||
root = storybookApp.mount('#root');
|
||||
|
@ -10,10 +10,15 @@ export default {
|
||||
},
|
||||
};
|
||||
|
||||
const Template = (args, { argTypes }) => ({
|
||||
props: Object.keys(argTypes),
|
||||
const Template = (args) => ({
|
||||
// Components used in your story `template` are defined in the `components` object
|
||||
components: { MyButton },
|
||||
template: '<my-button @click="onClick" v-bind="$props" />',
|
||||
// The story's `args` need to be mapped into the template through the `setup()` method
|
||||
setup() {
|
||||
return { args };
|
||||
},
|
||||
// And then the `args` are bound to your component with `v-bind="args"`
|
||||
template: '<my-button v-bind="args" />',
|
||||
});
|
||||
|
||||
export const Primary = Template.bind({});
|
||||
|
@ -20,7 +20,6 @@ export default {
|
||||
},
|
||||
size: {
|
||||
type: String,
|
||||
default: 'medium',
|
||||
validator: function (value) {
|
||||
return ['small', 'medium', 'large'].indexOf(value) !== -1;
|
||||
},
|
||||
@ -40,7 +39,7 @@ export default {
|
||||
'storybook-button': true,
|
||||
'storybook-button--primary': props.primary,
|
||||
'storybook-button--secondary': !props.primary,
|
||||
[`storybook-button--${props.size}`]: true,
|
||||
[`storybook-button--${props.size || 'medium'}`]: true,
|
||||
})),
|
||||
style: computed(() => ({
|
||||
backgroundColor: props.backgroundColor,
|
||||
|
@ -24,10 +24,11 @@ export default {
|
||||
/*
|
||||
You can return a Vue 3 functional component from a Story.
|
||||
|
||||
Make sure to specify the `props` the component expects to receive!
|
||||
Make sure to pass the `args` the component expects to receive as the props!
|
||||
*/
|
||||
const Template: Story = (args, { argTypes }) => {
|
||||
const component: FunctionalComponent<Props> = (props) => h(DynamicHeading, props, 'Hello World!');
|
||||
const component: FunctionalComponent<Props> = () =>
|
||||
h(DynamicHeading, args as Props, 'Hello World!');
|
||||
component.props = Object.keys(argTypes);
|
||||
return component;
|
||||
};
|
||||
@ -38,12 +39,12 @@ One.args = {
|
||||
};
|
||||
One.decorators = [
|
||||
// Vue 3 "ComponentOptions" component as decorator
|
||||
() => ({
|
||||
// Story Args can be destructured from the 2nd argument (`context`) to a decorator
|
||||
(storyFn, { args }) => ({
|
||||
// The `story` component is always injected into a decorator
|
||||
template: '<div :style="{ color: activeColor }"><story /></div>',
|
||||
data() {
|
||||
// Story Args can be accessed on `this.props`
|
||||
switch (this.props.level) {
|
||||
switch (args.level) {
|
||||
case 1:
|
||||
return { activeColor: 'purple' };
|
||||
case 2:
|
||||
|
@ -6,10 +6,15 @@ export default {
|
||||
argTypes: {},
|
||||
};
|
||||
|
||||
const Template = (args, { argTypes }) => ({
|
||||
props: Object.keys(argTypes),
|
||||
const Template = (args) => ({
|
||||
// Components used in your story `template` are defined in the `components` object
|
||||
components: { GlobalUsage },
|
||||
template: '<global-usage v-bind="$props" />',
|
||||
// The story's `args` need to be mapped into the template through the `setup()` method
|
||||
setup() {
|
||||
return { args };
|
||||
},
|
||||
// And then the `args` are bound to your component with `v-bind="args"`
|
||||
template: '<global-usage v-bind="args" />',
|
||||
});
|
||||
|
||||
export const Primary = Template.bind({});
|
||||
|
@ -5,9 +5,15 @@ export default {
|
||||
component: MyHeader,
|
||||
};
|
||||
|
||||
const Template = (args, { argTypes }) => ({
|
||||
props: Object.keys(argTypes),
|
||||
const Template = (args) => ({
|
||||
// Components used in your story `template` are defined in the `components` object
|
||||
components: { MyHeader },
|
||||
// The story's `args` need to be mapped into the template through the `setup()` method
|
||||
setup() {
|
||||
// Story args can be spread into the returned object
|
||||
return { ...args };
|
||||
},
|
||||
// Then, the spread values can be accessed directly in the template
|
||||
template: '<my-header :user="user" />',
|
||||
});
|
||||
|
||||
|
@ -26,16 +26,19 @@ export default {
|
||||
},
|
||||
};
|
||||
|
||||
const Template = (args, { argTypes }) => {
|
||||
const Template = (args) => {
|
||||
// Individual properties can be overridden by spreading the args
|
||||
// and the replacing the key-values that need to be updated
|
||||
args = { ...args, icon: icons[args.icon] }; // eslint-disable-line no-param-reassign
|
||||
return {
|
||||
props: Object.keys(argTypes),
|
||||
// Components used in your story `template` are defined in the `components` object
|
||||
components: { OverrideArgs },
|
||||
template: '<override-args v-bind="$props" :icon="icon" />',
|
||||
setup(props) {
|
||||
return {
|
||||
icon: icons[props.icon],
|
||||
};
|
||||
// Updated `args` need to be mapped into the template through the `setup()` method
|
||||
setup() {
|
||||
return { args };
|
||||
},
|
||||
// And then the `args` are bound to your component with `v-bind="args"`
|
||||
template: '<override-args v-bind="args" />',
|
||||
};
|
||||
};
|
||||
|
||||
|
@ -6,11 +6,15 @@ export default {
|
||||
component: MyPage,
|
||||
};
|
||||
|
||||
// If your props are optional and don't always exist in argTypes,
|
||||
// you can specify them explicitly as you normally specify props
|
||||
const Template = () => ({
|
||||
props: ['user'],
|
||||
const Template = (args) => ({
|
||||
// Components used in your story `template` are defined in the `components` object
|
||||
components: { MyPage },
|
||||
// The story's `args` need to be mapped into the template through the `setup()` method
|
||||
setup() {
|
||||
// Story args can be mapped to keys in the returned object
|
||||
return { user: args.user };
|
||||
},
|
||||
// Then, those values can be accessed directly in the template
|
||||
template: '<my-page :user="user" />',
|
||||
});
|
||||
|
||||
|
@ -23,10 +23,15 @@ export default {
|
||||
decorators: [withTheme],
|
||||
};
|
||||
|
||||
const Template = (args, { argTypes }) => ({
|
||||
props: Object.keys(argTypes),
|
||||
const Template = (args) => ({
|
||||
// Components used in your story `template` are defined in the `components` object
|
||||
components: { MyButton },
|
||||
template: '<my-button @click="onClick" v-bind="$props" />',
|
||||
// The story's `args` need to be mapped into the template through the `setup()` method
|
||||
setup() {
|
||||
return { args };
|
||||
},
|
||||
// And then the `args` are bound to your component with `v-bind="args"`
|
||||
template: '<my-button v-bind="args" />',
|
||||
});
|
||||
|
||||
export const ButtonWithTheme = Template.bind({});
|
||||
|
@ -10,10 +10,15 @@ export default {
|
||||
},
|
||||
};
|
||||
|
||||
const Template = (args, { argTypes }) => ({
|
||||
props: Object.keys(argTypes),
|
||||
const Template = (args) => ({
|
||||
// Components used in your story `template` are defined in the `components` object
|
||||
components: { MyButton },
|
||||
template: '<my-button @click="onClick" v-bind="$props" />',
|
||||
// The story's `args` need to be mapped into the template through the `setup()` method
|
||||
setup() {
|
||||
return { args };
|
||||
},
|
||||
// And then the `args` are bound to your component with `v-bind="args"`
|
||||
template: '<my-button v-bind="args" />',
|
||||
});
|
||||
|
||||
export const Primary = Template.bind({});
|
||||
|
@ -20,7 +20,6 @@ export default {
|
||||
},
|
||||
size: {
|
||||
type: String,
|
||||
default: 'medium',
|
||||
validator: function (value) {
|
||||
return ['small', 'medium', 'large'].indexOf(value) !== -1;
|
||||
},
|
||||
@ -39,7 +38,7 @@ export default {
|
||||
'storybook-button': true,
|
||||
'storybook-button--primary': props.primary,
|
||||
'storybook-button--secondary': !props.primary,
|
||||
[`storybook-button--${props.size}`]: true,
|
||||
[`storybook-button--${props.size || 'medium'}`]: true,
|
||||
})),
|
||||
style: computed(() => ({
|
||||
backgroundColor: props.backgroundColor,
|
||||
|
@ -5,9 +5,15 @@ export default {
|
||||
component: MyHeader,
|
||||
};
|
||||
|
||||
const Template = (args, { argTypes }) => ({
|
||||
props: Object.keys(argTypes),
|
||||
const Template = (args) => ({
|
||||
// Components used in your story `template` are defined in the `components` object
|
||||
components: { MyHeader },
|
||||
// The story's `args` need to be mapped into the template through the `setup()` method
|
||||
setup() {
|
||||
// Story args can be spread into the returned object
|
||||
return { ...args };
|
||||
},
|
||||
// Then, the spread values can be accessed directly in the template
|
||||
template: '<my-header :user="user" />',
|
||||
});
|
||||
|
||||
@ -17,4 +23,6 @@ LoggedIn.args = {
|
||||
};
|
||||
|
||||
export const LoggedOut = Template.bind({});
|
||||
LoggedOut.args = {};
|
||||
LoggedOut.args = {
|
||||
user: null,
|
||||
};
|
||||
|
@ -6,9 +6,15 @@ export default {
|
||||
component: MyPage,
|
||||
};
|
||||
|
||||
const Template = (args, { argTypes }) => ({
|
||||
props: Object.keys(argTypes),
|
||||
const Template = (args) => ({
|
||||
// Components used in your story `template` are defined in the `components` object
|
||||
components: { MyPage },
|
||||
// The story's `args` need to be mapped into the template through the `setup()` method
|
||||
setup() {
|
||||
// Story args can be mapped to keys in the returned object
|
||||
return { user: args.user };
|
||||
},
|
||||
// Then, those values can be accessed directly in the template
|
||||
template: '<my-page :user="user" />',
|
||||
});
|
||||
|
||||
@ -18,6 +24,4 @@ LoggedIn.args = {
|
||||
};
|
||||
|
||||
export const LoggedOut = Template.bind({});
|
||||
LoggedOut.args = {
|
||||
...HeaderStories.LoggedOut.args,
|
||||
};
|
||||
LoggedOut.args = {};
|
||||
|
Loading…
x
Reference in New Issue
Block a user