phoenix_storybook
phoenix_storybook copied to clipboard
allow passing additional options to story
I'm trying to solve the following problem.
I'm working on a headless UI component library called Doggo. It ships with a storybook folder that you can reference in your own application, so that you can see the components with your own styles. To set this up, you have to reference that library folder in your application's storybook module:
defmodule MyAppWeb.Storybook.Doggo do
use PhoenixStorybook,
otp_app: :my_app_web,
content_path: Path.join(:code.priv_dir(:doggo), "/storybook"),
title: "Doggo Storybook",
css_path: "/assets/storybook.css",
js_path: "/assets/storybook.js",
sandbox_class: "my-app-web"
end
So far, so good.
Currently, the components come with a fixed set of modifier attributes. For example, it comes with fixed values for sizes (small, normal, medium, large), and with fixed values for variants (primary, secondary, info, warning, etc.). Since not everybody will need all of those modifiers for all components, and some may need additional modifiers, I want to make them configurable in a future version.
I don't know exactly how I want to implement that yet. Maybe by adding a __using__
macro that generates customized components. But the details aren't important here. What's important is that the stories should automatically render all configured variations. I didn't find a way to pass additional options from the storybook configuration to the stories to achieve that.
What I imagine is something like this.
- Allow to pass an additional option to
use PhoenixStorybook
with arbitrary options. If I'm going to implement this with__using__
as described, I would need to pass the module name, but it might just be any other options I need to customize a pre-configured story. This would be in the application that uses my library:
defmodule MyAppWeb.Storybook.Doggo do
use PhoenixStorybook,
otp_app: :my_app_web,
content_path: Path.join(:code.priv_dir(:doggo), "/storybook"),
extra_opts: [
doggo_module: MyAppWeb.Doggo
]
end
- Pass those options to the story functions. At the minimum, to stick with my example, I'd need to be able to read the options in the
function
andvariations
functions. Something similar to this would be in the storybook stories defined in the library:
defmodule Storybook.Components.Button do
use PhoenixStorybook.Story, :component
def function(opts) do
module = Keyword.fetch!(opts, :doggo_module)
&module.button/1
end
def variations(opts) do
module = Keyword.fetch!(opts, :doggo_module)
[
%VariationGroup{
id: :sizes,
variations:
for size <- module.sizes() do
%Variation{
id: size,
attributes: %{size: size},
slots: ["click me"]
}
end
}
]
end
end
Whether I'm going to use __using__
and just pass a module, or whether I pass the options directly, I'll need some way to pass options from use PhoenixStorybook
to the story functions.
Does this feature make sense to you?
Hey Mathias, Doggo looks very cool!
I think your idea is good, can you open a PR?
One constraint tho: current stories using function/0
and variations/0
should still work