lookbook 1.0.0.beta.2 → 1.0.0.beta.3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +180 -40
- data/app/components/lookbook/{component.rb → base_component.rb} +1 -1
- data/app/components/lookbook/button/component.rb +1 -1
- data/app/components/lookbook/button_group/component.rb +1 -1
- data/app/components/lookbook/code/component.rb +1 -1
- data/app/components/lookbook/copy_button/component.html.erb +1 -1
- data/app/components/lookbook/copy_button/component.rb +1 -1
- data/app/components/lookbook/dimensions_display/component.rb +1 -1
- data/app/components/lookbook/embed/component.html.erb +3 -2
- data/app/components/lookbook/embed/component.rb +1 -1
- data/app/components/lookbook/filter/component.html.erb +1 -1
- data/app/components/lookbook/filter/component.rb +1 -1
- data/app/components/lookbook/header/component.html.erb +5 -10
- data/app/components/lookbook/header/component.rb +1 -1
- data/app/components/lookbook/icon/component.rb +1 -1
- data/app/components/lookbook/nav/component.rb +1 -1
- data/app/components/lookbook/nav/item/component.html.erb +2 -2
- data/app/components/lookbook/nav/item/component.rb +1 -1
- data/app/components/lookbook/page_tabs/component.rb +1 -1
- data/app/components/lookbook/params_editor/component.rb +1 -1
- data/app/components/lookbook/params_editor/field/component.rb +1 -1
- data/app/components/lookbook/prose/component.rb +1 -1
- data/app/components/lookbook/split_layout/component.rb +1 -1
- data/app/components/lookbook/tab_panels/component.rb +1 -1
- data/app/components/lookbook/tab_panels/panel/component.rb +2 -2
- data/app/components/lookbook/tabs/component.js +6 -6
- data/app/components/lookbook/tabs/component.rb +1 -1
- data/app/components/lookbook/tabs/dropdown_tab/component.rb +1 -1
- data/app/components/lookbook/tabs/tab/component.rb +1 -1
- data/app/components/lookbook/toolbar/component.rb +1 -1
- data/app/components/lookbook/viewport/component.rb +1 -1
- data/app/controllers/lookbook/previews_controller.rb +24 -29
- data/app/helpers/lookbook/application_helper.rb +6 -0
- data/app/helpers/lookbook/component_helper.rb +4 -0
- data/app/helpers/lookbook/page_helper.rb +1 -1
- data/app/views/layouts/lookbook/application.html.erb +1 -1
- data/app/views/layouts/lookbook/shell.html.erb +1 -1
- data/app/views/layouts/lookbook/skeleton.html.erb +7 -1
- data/app/views/lookbook/404.html.erb +1 -1
- data/app/views/lookbook/index.html.erb +1 -1
- data/app/views/lookbook/pages/show.html.erb +2 -2
- data/app/views/lookbook/previews/panels/_notes.html.erb +1 -1
- data/app/views/lookbook/previews/show.html.erb +3 -3
- data/lib/lookbook/collection.rb +1 -1
- data/lib/lookbook/component.rb +31 -0
- data/lib/lookbook/config.rb +54 -9
- data/lib/lookbook/engine.rb +72 -12
- data/lib/lookbook/page.rb +2 -2
- data/lib/lookbook/parser.rb +1 -4
- data/lib/lookbook/preview.rb +24 -7
- data/lib/lookbook/preview_example.rb +1 -1
- data/lib/lookbook/source_inspector.rb +10 -0
- data/lib/lookbook/utils.rb +2 -2
- data/lib/lookbook/version.rb +1 -1
- data/lib/lookbook.rb +1 -12
- data/public/lookbook-assets/js/lookbook.js +105 -104
- data/public/lookbook-assets/js/lookbook.js.map +1 -1
- metadata +3 -2
@@ -117,41 +117,36 @@ module Lookbook
|
|
117
117
|
def inspector_data
|
118
118
|
return @inspector_data if @inspector_data.present?
|
119
119
|
|
120
|
-
|
120
|
+
context_data = {
|
121
121
|
preview_params: preview_params,
|
122
122
|
path: params[:path],
|
123
|
-
query_parameters: request.query_parameters,
|
124
|
-
original: request
|
125
123
|
}
|
126
124
|
|
127
|
-
|
128
|
-
|
129
|
-
|
130
|
-
|
131
|
-
|
132
|
-
}
|
133
|
-
[:id, :label, :notes, :lookup_path, :full_path].each do |prop|
|
134
|
-
preview_data[prop] = @preview.public_send(prop)
|
135
|
-
end
|
125
|
+
example = @example
|
126
|
+
preview = @preview
|
127
|
+
preview.define_singleton_method(:params, proc {
|
128
|
+
example.params
|
129
|
+
})
|
136
130
|
|
137
|
-
|
131
|
+
examples = target_examples.map do |example|
|
138
132
|
render_args = @preview.render_args(example.name, params: preview_controller.params)
|
139
133
|
has_template = render_args[:template] != "view_components/preview"
|
140
|
-
|
141
|
-
|
142
|
-
|
143
|
-
|
144
|
-
})
|
145
|
-
|
146
|
-
|
147
|
-
|
148
|
-
example_data
|
134
|
+
output = preview_controller.process(:render_example_to_string, @preview, example.name)
|
135
|
+
source = has_template ? example.template_source(render_args[:template]) : example.method_source
|
136
|
+
source_lang = has_template ? example.template_lang(render_args[:template]) : example.lang
|
137
|
+
|
138
|
+
example.define_singleton_method(:output, proc { output })
|
139
|
+
example.define_singleton_method(:source, proc { source })
|
140
|
+
example.define_singleton_method(:source_lang, proc { source_lang })
|
141
|
+
example
|
149
142
|
end
|
150
143
|
|
151
144
|
@inspector_data ||= Lookbook::Store.new({
|
152
|
-
|
153
|
-
preview:
|
154
|
-
examples:
|
145
|
+
context: context_data,
|
146
|
+
preview: preview,
|
147
|
+
examples: examples,
|
148
|
+
components: preview.components,
|
149
|
+
app: Lookbook
|
155
150
|
})
|
156
151
|
end
|
157
152
|
|
@@ -163,7 +158,7 @@ module Lookbook
|
|
163
158
|
|
164
159
|
callable_data = {
|
165
160
|
name: name.to_s,
|
166
|
-
index_position: (@panels.
|
161
|
+
index_position: (@panels.select { |p| p.pane == config.pane }.size + 1),
|
167
162
|
**inspector_data
|
168
163
|
}
|
169
164
|
|
@@ -175,15 +170,15 @@ module Lookbook
|
|
175
170
|
@panels << Lookbook::Store.new(resolved_config, deep: false)
|
176
171
|
end
|
177
172
|
|
178
|
-
@panels.
|
173
|
+
@panels = @panels.select(&:show).sort_by { |p| [p.position, p.label] }
|
179
174
|
end
|
180
175
|
|
181
176
|
def main_panels
|
182
|
-
panels.
|
177
|
+
panels.select { |panel| panel.pane == :main }
|
183
178
|
end
|
184
179
|
|
185
180
|
def drawer_panels
|
186
|
-
panels.
|
181
|
+
panels.select { |panel| panel.pane == :drawer }
|
187
182
|
end
|
188
183
|
|
189
184
|
def preview_controller
|
@@ -2,6 +2,10 @@ module Lookbook
|
|
2
2
|
module ComponentHelper
|
3
3
|
COMPONENT_CLASSES = {} # cache for constantized references
|
4
4
|
|
5
|
+
def icon(name, **attrs)
|
6
|
+
render Lookbook::Icon::Component.new(name: name, **attrs)
|
7
|
+
end
|
8
|
+
|
5
9
|
def render_component(ref, **attrs, &block)
|
6
10
|
klass = component_class(ref)
|
7
11
|
comp = attrs.key?(:content) ? klass.new(**attrs.except(:content)).with_content(attrs[:content]) : klass.new(**attrs)
|
@@ -16,7 +16,7 @@ module Lookbook
|
|
16
16
|
|
17
17
|
@embed_counter ||= 0
|
18
18
|
|
19
|
-
preview_lookup = args.first.is_a?(Symbol) ? args.first :
|
19
|
+
preview_lookup = args.first.is_a?(Symbol) ? args.first : preview_class_path(args.first)
|
20
20
|
preview = Lookbook.previews.find(preview_lookup)
|
21
21
|
example = args[1] ? preview&.example(args[1]) : preview&.default_example
|
22
22
|
|
@@ -40,7 +40,7 @@
|
|
40
40
|
<div x-data="{hidden: false}" class="flex-none border-t border-lookbook-divider absolute bottom-0 left-0 right-0" x-show="!hidden">
|
41
41
|
<%= render_component :toolbar do |toolbar| %>
|
42
42
|
<% toolbar.section padded: true, class: "flex items-center" do %>
|
43
|
-
<%=
|
43
|
+
<%= icon :alert_triangle, size: 4, class: "text-red-700" %>
|
44
44
|
<span class="ml-2">Preview load errors</span>
|
45
45
|
<% end %>
|
46
46
|
<% toolbar.section align: :right do %>
|
@@ -28,7 +28,7 @@
|
|
28
28
|
<span class="opacity-60 mr-1">Lookbook</span>
|
29
29
|
<span class="mr-6">v<%= Lookbook::VERSION %></span>
|
30
30
|
<a href="https://github.com/allmarkedup/lookbook" target="_blank" class="ml-auto opacity-70">
|
31
|
-
<%=
|
31
|
+
<%= icon :github, size: 3 %>
|
32
32
|
</a>
|
33
33
|
</div>
|
34
34
|
<div class="px-3 py-2">
|
@@ -8,11 +8,17 @@
|
|
8
8
|
<link href="/lookbook-assets/css/lookbook.css?v=<%= Lookbook::VERSION %>" rel="stylesheet">
|
9
9
|
<link href="/lookbook-assets/css/themes/<%= config.ui_theme %>.css?v=<%= Lookbook::VERSION %>" rel="stylesheet">
|
10
10
|
<% if @theme_overrides.present? %>
|
11
|
-
<style>
|
11
|
+
<style media="all">
|
12
12
|
<%== @theme_overrides %>
|
13
13
|
</style>
|
14
14
|
<% end %>
|
15
15
|
|
16
|
+
<% if content_for? :styles %>
|
17
|
+
<style media="all">
|
18
|
+
<%= content_for :styles %>
|
19
|
+
</style>
|
20
|
+
<% end %>
|
21
|
+
|
16
22
|
<% if config.ui_favicon != false %>
|
17
23
|
<link rel="icon" href="<%= config.ui_favicon || "data:image/svg+xml,<svg xmlns=%22http://www.w3.org/2000/svg%22 viewBox=%220 0 100 100%22><text y=%22.9em%22 font-size=%2290%22>👀</text></svg>" %>">
|
18
24
|
<% end %>
|
@@ -1,6 +1,6 @@
|
|
1
1
|
<div class="bg-white flex flex-col items-center justify-center h-screen w-full">
|
2
2
|
<div class="px-4 text-center max-w-sm">
|
3
|
-
<%=
|
3
|
+
<%= icon :alert_triangle, size: 10, class: "text-red-300 mx-auto" %>
|
4
4
|
<div class="mt-3">
|
5
5
|
<h5 class="text-base">
|
6
6
|
<%== message %>
|
@@ -1,7 +1,7 @@
|
|
1
1
|
<div id="welcome-message" class="flex flex-col h-full w-full">
|
2
2
|
<div class="flex flex-col items-center justify-center h-full">
|
3
3
|
<div class="p-4 text-center mx-auto">
|
4
|
-
<%=
|
4
|
+
<%= icon :layers, size: 10, class: "opacity-30 mx-auto" %>
|
5
5
|
<div class="mt-6 text-base opacity-40">
|
6
6
|
<% if Lookbook.previews.any? %>
|
7
7
|
<h5>Select a preview to get started</h5>
|
@@ -25,7 +25,7 @@
|
|
25
25
|
<% if @previous_page %>
|
26
26
|
<a href="<%= lookbook_page_path @previous_page.lookup_path %>"
|
27
27
|
class="flex items-center flex-none">
|
28
|
-
<%=
|
28
|
+
<%= icon :arrow_left, size: 4, class: "hover:text-indigo-800" %>
|
29
29
|
<span class="ml-2 underline"><%= @previous_page.title %></span>
|
30
30
|
</a>
|
31
31
|
<% end %>
|
@@ -34,7 +34,7 @@
|
|
34
34
|
<a href="<%= lookbook_page_path @next_page.lookup_path %>"
|
35
35
|
class="flex items-center flex-none ml-auto">
|
36
36
|
<span class="mr-2 underline"><%= @next_page.title %></span>
|
37
|
-
<%=
|
37
|
+
<%= icon :arrow_right, size: 4, class: "hover:text-indigo-800" %>
|
38
38
|
</a>
|
39
39
|
<% end %>
|
40
40
|
</footer>
|
@@ -1,4 +1,4 @@
|
|
1
|
-
<% items = examples.
|
1
|
+
<% items = examples.select { |example| example.notes.present? } %>
|
2
2
|
<% if items.many? %>
|
3
3
|
<div class="divide-y divide-dashed divide-lookbook-divider bg-lookbook-prose h-full w-full">
|
4
4
|
<% items.each do |item| %>
|
@@ -55,7 +55,7 @@
|
|
55
55
|
<div class="h-full relative overflow-auto">
|
56
56
|
<%= render_component :tab_panels, alpine_data: "$store.inspector.main" do |tabs| %>
|
57
57
|
<% @main_panels.each do |panel| %>
|
58
|
-
<% tabs.panel name: panel.name, class: panel.panel_classes do %>
|
58
|
+
<% tabs.panel id: panel.id, name: panel.name, class: [panel.panel_classes, { "p-4": panel.padded, "prose": panel.prose }] do %>
|
59
59
|
<%= render panel.partial, **@inspector_data, panel: panel, **panel.locals %>
|
60
60
|
<% end %>
|
61
61
|
<% end %>
|
@@ -80,7 +80,7 @@
|
|
80
80
|
|
81
81
|
<% toolbar.section align: :right, class: "flex-none relative z-10" do %>
|
82
82
|
<%= render_component :button_group do |group| %>
|
83
|
-
<%= @drawer_panels.
|
83
|
+
<%= @drawer_panels.select { |p| !p.disabled && p.copy }.each do |panel| %>
|
84
84
|
<% group.button icon: :copy,
|
85
85
|
tooltip: "Copy panel contents",
|
86
86
|
copy: !!panel.copy,
|
@@ -123,7 +123,7 @@
|
|
123
123
|
<div class="h-full overflow-auto">
|
124
124
|
<%= render_component :tab_panels, alpine_data: "$store.inspector.drawer" do |tabs| %>
|
125
125
|
<% @drawer_panels.each do |panel| %>
|
126
|
-
<% tabs.panel name: panel.name do %>
|
126
|
+
<% tabs.panel id: panel.id, name: panel.name, class: [panel.panel_classes, { "p-4": panel.padded, "prose": panel.prose }] do %>
|
127
127
|
<%= render panel.partial, **@inspector_data, panel: panel, **panel.locals %>
|
128
128
|
<% end %>
|
129
129
|
<% end %>
|
data/lib/lookbook/collection.rb
CHANGED
@@ -0,0 +1,31 @@
|
|
1
|
+
module Lookbook
|
2
|
+
class Component < Entity
|
3
|
+
|
4
|
+
attr_accessor :name
|
5
|
+
|
6
|
+
def initialize(name)
|
7
|
+
@name = name
|
8
|
+
super(path)
|
9
|
+
end
|
10
|
+
|
11
|
+
def path
|
12
|
+
name.underscore
|
13
|
+
end
|
14
|
+
|
15
|
+
def full_path
|
16
|
+
Pathname.new("#{Lookbook.config.components_path}/#{path}.rb")
|
17
|
+
end
|
18
|
+
|
19
|
+
def dir_path
|
20
|
+
full_path.dirname
|
21
|
+
end
|
22
|
+
|
23
|
+
def template_path
|
24
|
+
Dir.glob("#{Lookbook.config.components_path}/#{path}.*.erb").first
|
25
|
+
end
|
26
|
+
|
27
|
+
def inline?
|
28
|
+
template_path.present?
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
data/lib/lookbook/config.rb
CHANGED
@@ -11,6 +11,8 @@ module Lookbook
|
|
11
11
|
project_name: "Lookbook",
|
12
12
|
log_level: 2,
|
13
13
|
auto_refresh: true,
|
14
|
+
|
15
|
+
components_path: "app/components",
|
14
16
|
|
15
17
|
page_controller: "Lookbook::PageController",
|
16
18
|
page_route: "pages",
|
@@ -37,13 +39,22 @@ module Lookbook
|
|
37
39
|
ui_theme: "indigo",
|
38
40
|
ui_theme_overrides: {},
|
39
41
|
|
42
|
+
hooks: {
|
43
|
+
after_initialize: [],
|
44
|
+
before_exit: [],
|
45
|
+
after_change: [],
|
46
|
+
},
|
47
|
+
|
48
|
+
experimental_features: false,
|
49
|
+
|
40
50
|
inspector_panels: {
|
41
51
|
preview: {
|
42
52
|
pane: :main,
|
43
53
|
position: 1,
|
44
54
|
partial: "lookbook/previews/panels/preview",
|
45
55
|
hotkey: "v",
|
46
|
-
panel_classes: "overflow-hidden"
|
56
|
+
panel_classes: "overflow-hidden",
|
57
|
+
padded: false
|
47
58
|
},
|
48
59
|
output: {
|
49
60
|
pane: :main,
|
@@ -51,6 +62,7 @@ module Lookbook
|
|
51
62
|
partial: "lookbook/previews/panels/output",
|
52
63
|
label: "HTML",
|
53
64
|
hotkey: "h",
|
65
|
+
padded: false
|
54
66
|
},
|
55
67
|
source: {
|
56
68
|
pane: :drawer,
|
@@ -58,7 +70,8 @@ module Lookbook
|
|
58
70
|
partial: "lookbook/previews/panels/source",
|
59
71
|
label: "Source",
|
60
72
|
hotkey: "s",
|
61
|
-
copy: ->(data) { data.examples.map { |e| e
|
73
|
+
copy: ->(data) { data.examples.map { |e| e.source }.join("\n") },
|
74
|
+
padded: false
|
62
75
|
},
|
63
76
|
notes: {
|
64
77
|
pane: :drawer,
|
@@ -66,7 +79,8 @@ module Lookbook
|
|
66
79
|
partial: "lookbook/previews/panels/notes",
|
67
80
|
label: "Notes",
|
68
81
|
hotkey: "n",
|
69
|
-
disabled: ->(data) { data.examples.
|
82
|
+
disabled: ->(data) { data.examples.select { |e| e.notes.present? }.none? },
|
83
|
+
padded: false
|
70
84
|
},
|
71
85
|
params: {
|
72
86
|
pane: :drawer,
|
@@ -74,7 +88,8 @@ module Lookbook
|
|
74
88
|
partial: "lookbook/previews/panels/params",
|
75
89
|
label: "Params",
|
76
90
|
hotkey: "p",
|
77
|
-
disabled: ->(data) { data.preview.params.none? }
|
91
|
+
disabled: ->(data) { data.preview.params.none? },
|
92
|
+
padded: false
|
78
93
|
}
|
79
94
|
},
|
80
95
|
|
@@ -90,10 +105,9 @@ module Lookbook
|
|
90
105
|
show: true,
|
91
106
|
copy: nil,
|
92
107
|
panel_classes: nil,
|
93
|
-
locals: {}
|
108
|
+
locals: {},
|
109
|
+
padded: true
|
94
110
|
},
|
95
|
-
|
96
|
-
experimental_features: false,
|
97
111
|
})
|
98
112
|
end
|
99
113
|
|
@@ -105,6 +119,33 @@ module Lookbook
|
|
105
119
|
end
|
106
120
|
end
|
107
121
|
|
122
|
+
def define_inspector_panel(name, opts = {})
|
123
|
+
inspector_panels[name] = opts
|
124
|
+
if opts[:position].present?
|
125
|
+
pane = inspector_panels[name].pane.presence || :drawer
|
126
|
+
siblings = inspector_panels.select do |key, panel|
|
127
|
+
panel.pane == pane && key != name.to_sym
|
128
|
+
end
|
129
|
+
siblings.each do |key, panel|
|
130
|
+
if panel.position >= opts[:position]
|
131
|
+
panel.position += 1
|
132
|
+
end
|
133
|
+
end
|
134
|
+
end
|
135
|
+
end
|
136
|
+
|
137
|
+
def amend_inspector_panel(name, opts = {})
|
138
|
+
if opts == false
|
139
|
+
inspector_panels[name] = false
|
140
|
+
else
|
141
|
+
inspector_panels[name].merge!(opts)
|
142
|
+
end
|
143
|
+
end
|
144
|
+
|
145
|
+
def remove_inspector_panel(name)
|
146
|
+
amend_inspector_panel(name, false)
|
147
|
+
end
|
148
|
+
|
108
149
|
def ui_theme=(name)
|
109
150
|
name = name.to_s
|
110
151
|
if Theme.valid_theme?(name)
|
@@ -141,7 +182,7 @@ module Lookbook
|
|
141
182
|
protected
|
142
183
|
|
143
184
|
def get_inspector_panels(panels)
|
144
|
-
panels.
|
185
|
+
panels.select! { |key, panel| panel }
|
145
186
|
panels
|
146
187
|
end
|
147
188
|
|
@@ -149,9 +190,13 @@ module Lookbook
|
|
149
190
|
name == false ? nil : name
|
150
191
|
end
|
151
192
|
|
193
|
+
def get_components_path(path)
|
194
|
+
absolute_path(path)
|
195
|
+
end
|
196
|
+
|
152
197
|
def normalize_paths(paths)
|
153
198
|
paths.map! { |path| absolute_path(path) }
|
154
|
-
paths.
|
199
|
+
paths.select! { |path| Dir.exist?(path) }
|
155
200
|
paths
|
156
201
|
end
|
157
202
|
|
data/lib/lookbook/engine.rb
CHANGED
@@ -8,16 +8,20 @@ module Lookbook
|
|
8
8
|
autoload :Config, "lookbook/config"
|
9
9
|
|
10
10
|
class << self
|
11
|
+
def version
|
12
|
+
Lookbook::VERSION
|
13
|
+
end
|
14
|
+
|
11
15
|
def config
|
12
16
|
@config ||= Config.new
|
13
17
|
end
|
14
18
|
|
15
|
-
def
|
16
|
-
|
19
|
+
def configure
|
20
|
+
yield(config)
|
17
21
|
end
|
18
22
|
|
19
|
-
def
|
20
|
-
|
23
|
+
def logger
|
24
|
+
@logger ||= Rails.env.development? ? Logger.new($stdout) : Rails.logger
|
21
25
|
end
|
22
26
|
|
23
27
|
def debug_data
|
@@ -28,8 +32,46 @@ module Lookbook
|
|
28
32
|
}
|
29
33
|
end
|
30
34
|
|
31
|
-
def
|
32
|
-
|
35
|
+
def previews
|
36
|
+
Preview.all
|
37
|
+
end
|
38
|
+
|
39
|
+
def pages
|
40
|
+
Page.all
|
41
|
+
end
|
42
|
+
|
43
|
+
def after_initialize(&block)
|
44
|
+
add_hook(:after_initialize, block)
|
45
|
+
end
|
46
|
+
|
47
|
+
def before_exit(&block)
|
48
|
+
add_hook(:before_exit, block)
|
49
|
+
end
|
50
|
+
|
51
|
+
def after_change(&block)
|
52
|
+
add_hook(:after_change, block)
|
53
|
+
end
|
54
|
+
|
55
|
+
def define_panel(name, opts = {})
|
56
|
+
config.define_inspector_panel(name, opts)
|
57
|
+
end
|
58
|
+
|
59
|
+
def amend_panel(name, opts = {})
|
60
|
+
config.amend_inspector_panel(name, opts)
|
61
|
+
end
|
62
|
+
|
63
|
+
def remove_panel(name)
|
64
|
+
config.remove_inspector_panel(name)
|
65
|
+
end
|
66
|
+
|
67
|
+
def broadcast(event_name, data = {})
|
68
|
+
Engine.websocket&.broadcast(event_name.to_s, data)
|
69
|
+
end
|
70
|
+
|
71
|
+
protected
|
72
|
+
|
73
|
+
def add_hook(event_name, block)
|
74
|
+
config.hooks[event_name] << block
|
33
75
|
end
|
34
76
|
end
|
35
77
|
|
@@ -43,8 +85,10 @@ module Lookbook
|
|
43
85
|
config.lookbook.preview_paths += config.view_component.preview_paths
|
44
86
|
config.lookbook.preview_controller ||= config.view_component.preview_controller
|
45
87
|
|
88
|
+
config.lookbook.components_path = config.view_component.view_component_path if config.view_component.view_component_path.present?
|
89
|
+
|
46
90
|
config.lookbook.listen_paths += config.lookbook.preview_paths
|
47
|
-
config.lookbook.listen_paths <<
|
91
|
+
config.lookbook.listen_paths << config.lookbook.components_path
|
48
92
|
end
|
49
93
|
|
50
94
|
initializer "lookbook.logging.development" do
|
@@ -73,12 +117,14 @@ module Lookbook
|
|
73
117
|
only: /\.(rb|html.*)$/,
|
74
118
|
force_polling: Lookbook.config.listen_use_polling
|
75
119
|
) do |modified, added, removed|
|
120
|
+
changes = { modified: modified, added: added, removed: removed }
|
76
121
|
begin
|
77
122
|
parser.parse
|
78
123
|
rescue
|
79
124
|
end
|
80
125
|
Lookbook::Preview.clear_cache
|
81
|
-
Lookbook::Engine.
|
126
|
+
Lookbook::Engine.reload_ui(changes)
|
127
|
+
Lookbook::Engine.run_hooks(:after_change, changes)
|
82
128
|
end
|
83
129
|
Lookbook::Engine.register_listener(preview_listener)
|
84
130
|
|
@@ -87,7 +133,9 @@ module Lookbook
|
|
87
133
|
only: /\.(html.*|md.*)$/,
|
88
134
|
force_polling: Lookbook.config.listen_use_polling
|
89
135
|
) do |modified, added, removed|
|
90
|
-
|
136
|
+
changes = { modified: modified, added: added, removed: removed }
|
137
|
+
Lookbook::Engine.reload_ui(changes)
|
138
|
+
Lookbook::Engine.run_hooks(:after_change, changes)
|
91
139
|
end
|
92
140
|
Lookbook::Engine.register_listener(page_listener)
|
93
141
|
end
|
@@ -103,18 +151,20 @@ module Lookbook
|
|
103
151
|
"
|
104
152
|
end
|
105
153
|
end
|
154
|
+
|
155
|
+
Lookbook::Engine.run_hooks(:after_initialize)
|
106
156
|
end
|
107
157
|
|
108
158
|
at_exit do
|
109
159
|
if config.lookbook.listen
|
110
160
|
Lookbook.logger.debug "Stopping listeners"
|
111
|
-
Lookbook::Engine.listeners.each
|
112
|
-
listener.stop
|
113
|
-
end
|
161
|
+
Lookbook::Engine.listeners.each { |listener| listener.stop }
|
114
162
|
end
|
163
|
+
Lookbook::Engine.run_hooks(:before_exit)
|
115
164
|
end
|
116
165
|
|
117
166
|
class << self
|
167
|
+
|
118
168
|
def websocket
|
119
169
|
if config.lookbook.auto_refresh
|
120
170
|
cable = ActionCable::Server::Configuration.new
|
@@ -162,6 +212,16 @@ module Lookbook
|
|
162
212
|
@listeners ||= []
|
163
213
|
end
|
164
214
|
|
215
|
+
def run_hooks(event_name, *args)
|
216
|
+
Lookbook.config.hooks[event_name].each do |hook|
|
217
|
+
hook.call(Lookbook, *args)
|
218
|
+
end
|
219
|
+
end
|
220
|
+
|
221
|
+
def reload_ui(changed = {})
|
222
|
+
websocket&.broadcast("reload", changed)
|
223
|
+
end
|
224
|
+
|
165
225
|
attr_reader :preview_controller
|
166
226
|
end
|
167
227
|
end
|
data/lib/lookbook/page.rb
CHANGED
@@ -19,7 +19,7 @@ module Lookbook
|
|
19
19
|
|
20
20
|
def initialize(path, base_path)
|
21
21
|
@pathname = Pathname.new path
|
22
|
-
@base_path = base_path
|
22
|
+
@base_path = Pathname.new base_path
|
23
23
|
@options = nil
|
24
24
|
@errors = []
|
25
25
|
@sections = []
|
@@ -177,7 +177,7 @@ module Lookbook
|
|
177
177
|
end
|
178
178
|
|
179
179
|
def page_paths
|
180
|
-
Lookbook.config.page_paths.
|
180
|
+
Lookbook.config.page_paths.select { |dir| Dir.exist? dir }
|
181
181
|
end
|
182
182
|
|
183
183
|
def section_path?(path)
|
data/lib/lookbook/parser.rb
CHANGED
@@ -23,10 +23,6 @@ module Lookbook
|
|
23
23
|
registry.get(path)
|
24
24
|
end
|
25
25
|
|
26
|
-
# def yardoc_file_path
|
27
|
-
# Rails&.root ? Rails.root.join(YARDOC_FILE_PATH) : YARDOC_FILE_PATH
|
28
|
-
# end
|
29
|
-
|
30
26
|
class << self
|
31
27
|
def define_tags
|
32
28
|
YARD::Tags::Library.define_tag("Hidden status", :hidden)
|
@@ -34,6 +30,7 @@ module Lookbook
|
|
34
30
|
YARD::Tags::Library.define_tag("Display", :display)
|
35
31
|
YARD::Tags::Library.define_tag("Position", :position)
|
36
32
|
YARD::Tags::Library.define_tag("ID", :id)
|
33
|
+
YARD::Tags::Library.define_tag("Component", :component)
|
37
34
|
end
|
38
35
|
end
|
39
36
|
end
|
data/lib/lookbook/preview.rb
CHANGED
@@ -8,7 +8,7 @@ module Lookbook
|
|
8
8
|
def initialize(preview)
|
9
9
|
@preview = preview
|
10
10
|
@preview_inspector = SourceInspector.new(@preview.name)
|
11
|
-
super(
|
11
|
+
super(preview_class_path(@preview.name))
|
12
12
|
end
|
13
13
|
|
14
14
|
def id
|
@@ -34,7 +34,7 @@ module Lookbook
|
|
34
34
|
def examples
|
35
35
|
return @examples if @examples.present?
|
36
36
|
public_methods = @preview.public_instance_methods(false)
|
37
|
-
public_method_objects = @preview_inspector&.methods&.
|
37
|
+
public_method_objects = @preview_inspector&.methods&.select { |m| public_methods.include?(m.name) }
|
38
38
|
examples = (public_method_objects || []).map { |m| PreviewExample.new(m.name.to_s, self) }
|
39
39
|
sorted = Lookbook.config.sort_examples ? examples.sort_by(&:label) : examples
|
40
40
|
@examples = []
|
@@ -62,7 +62,7 @@ module Lookbook
|
|
62
62
|
end
|
63
63
|
|
64
64
|
def full_path
|
65
|
-
base_path = Array(preview_paths).detect do |preview_path|
|
65
|
+
base_path = Array(Lookbook.config.preview_paths).detect do |preview_path|
|
66
66
|
Dir["#{preview_path}/#{name.underscore}.rb"].first
|
67
67
|
end
|
68
68
|
Pathname.new(Dir["#{base_path}/#{name.underscore}.rb"].first)
|
@@ -72,10 +72,6 @@ module Lookbook
|
|
72
72
|
lookbook_inspect_path lookup_path
|
73
73
|
end
|
74
74
|
|
75
|
-
def preview_paths
|
76
|
-
ViewComponent::Base.preview_paths
|
77
|
-
end
|
78
|
-
|
79
75
|
def parent_collections_names
|
80
76
|
File.dirname(path).split("/")
|
81
77
|
end
|
@@ -96,6 +92,27 @@ module Lookbook
|
|
96
92
|
true
|
97
93
|
end
|
98
94
|
|
95
|
+
def component
|
96
|
+
components.first
|
97
|
+
end
|
98
|
+
|
99
|
+
def components
|
100
|
+
component_classes = @preview_inspector&.components.any? ? @preview_inspector&.components : [guess_component]
|
101
|
+
component_classes.map do |class_name|
|
102
|
+
Component.new(class_name.to_s)
|
103
|
+
end
|
104
|
+
end
|
105
|
+
|
106
|
+
protected
|
107
|
+
|
108
|
+
def guess_component
|
109
|
+
begin
|
110
|
+
name.chomp("Preview").constantize
|
111
|
+
rescue
|
112
|
+
nil
|
113
|
+
end
|
114
|
+
end
|
115
|
+
|
99
116
|
class << self
|
100
117
|
def find(path)
|
101
118
|
all.find { |p| p.lookup_path == path }
|