blib/lib/Mojolicious/Plugin/BootstrapHelpers/Helpers.pm | |||
---|---|---|---|
Criterion | Covered | Total | % |
statement | 503 | 511 | 98.4 |
branch | 204 | 238 | 85.7 |
condition | 36 | 53 | 67.9 |
subroutine | 61 | 63 | 96.8 |
pod | 0 | 44 | 0.0 |
total | 804 | 909 | 88.4 |
line | stmt | bran | cond | sub | pod | time | code | ||||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
1 | 14 | 14 | 107 | use 5.20.0; | |||||||||||||||||||
14 | 32 | ||||||||||||||||||||||
2 | 14 | 14 | 44 | use warnings; | |||||||||||||||||||
14 | 17 | ||||||||||||||||||||||
14 | 737 | ||||||||||||||||||||||
3 | |||||||||||||||||||||||
4 | package Mojolicious::Plugin::BootstrapHelpers::Helpers; | ||||||||||||||||||||||
5 | |||||||||||||||||||||||
6 | # ABSTRACT: Supporting module | ||||||||||||||||||||||
7 | our $AUTHORITY = 'cpan:CSSON'; # AUTHORITY | ||||||||||||||||||||||
8 | our $VERSION = '0.0204'; | ||||||||||||||||||||||
9 | |||||||||||||||||||||||
10 | 14 | 14 | 51 | use List::Util qw/uniq/; | |||||||||||||||||||
14 | 15 | ||||||||||||||||||||||
14 | 1021 | ||||||||||||||||||||||
11 | 14 | 14 | 60 | use Mojo::ByteStream; | |||||||||||||||||||
14 | 16 | ||||||||||||||||||||||
14 | 406 | ||||||||||||||||||||||
12 | 14 | 14 | 42 | use Mojo::Util 'xml_escape'; | |||||||||||||||||||
14 | 18 | ||||||||||||||||||||||
14 | 479 | ||||||||||||||||||||||
13 | 14 | 14 | 48 | use Scalar::Util 'blessed'; | |||||||||||||||||||
14 | 13 | ||||||||||||||||||||||
14 | 550 | ||||||||||||||||||||||
14 | 14 | 14 | 5700 | use String::Trim; | |||||||||||||||||||
14 | 6749 | ||||||||||||||||||||||
14 | 567 | ||||||||||||||||||||||
15 | 14 | 14 | 5556 | use String::Random; | |||||||||||||||||||
14 | 37804 | ||||||||||||||||||||||
14 | 709 | ||||||||||||||||||||||
16 | 14 | 14 | 5781 | use experimental qw/postderef signatures/; | |||||||||||||||||||
14 | 32871 | ||||||||||||||||||||||
14 | 64 | ||||||||||||||||||||||
17 | |||||||||||||||||||||||
18 | sub bootstraps_bootstraps { | ||||||||||||||||||||||
19 | 6 | 6 | 0 | 45578 | my $c = shift; | ||||||||||||||||||
20 | 6 | 6 | my $arg = shift; | ||||||||||||||||||||
21 | |||||||||||||||||||||||
22 | 6 | 6 | my $css = q{}; | ||||||||||||||||||||
23 | 6 | 7 | my $theme = q{}; | ||||||||||||||||||||
24 | 6 | 3 | my $js = q{}; | ||||||||||||||||||||
25 | 6 | 5 | my $jq = q{}; | ||||||||||||||||||||
26 | |||||||||||||||||||||||
27 | 6 | 50 | 42 | return out( | |||||||||||||||||||
100 | |||||||||||||||||||||||
100 | |||||||||||||||||||||||
100 | |||||||||||||||||||||||
100 | |||||||||||||||||||||||
100 | |||||||||||||||||||||||
28 | !defined $arg ? $css | ||||||||||||||||||||||
29 | : $arg eq 'css' ? join "\n" => $css, $theme | ||||||||||||||||||||||
30 | : $arg eq 'js' ? join "\n" => $js | ||||||||||||||||||||||
31 | : $arg eq 'jsq' ? join "\n" => $jq, $js | ||||||||||||||||||||||
32 | : $arg eq 'all' ? join "\n" => $css, $theme, $js | ||||||||||||||||||||||
33 | : $arg eq 'allq' ? join "\n" => $css, $theme, $jq, $js | ||||||||||||||||||||||
34 | : '' | ||||||||||||||||||||||
35 | ); | ||||||||||||||||||||||
36 | } | ||||||||||||||||||||||
37 | |||||||||||||||||||||||
38 | sub bootstrap_panel { | ||||||||||||||||||||||
39 | 4 | 4 | 0 | 20567 | my($c, $title, $callback, $content, $attr) = parse_call(@_); | ||||||||||||||||||
40 | |||||||||||||||||||||||
41 | 4 | 20 | $attr = add_classes($attr, 'panel', { panel => 'panel-%s', panel_default => 'default'}); | ||||||||||||||||||||
42 | |||||||||||||||||||||||
43 | 4 | 11 | my $body = qq{ | ||||||||||||||||||||
44 | |
||||||||||||||||||||||
45 | } . contents($callback, $content) . qq{ | ||||||||||||||||||||||
46 | |||||||||||||||||||||||
47 | }; | ||||||||||||||||||||||
48 | |||||||||||||||||||||||
49 | 4 | 66 | return create_panel($c, $title, $body, $attr); | ||||||||||||||||||||
50 | |||||||||||||||||||||||
51 | } | ||||||||||||||||||||||
52 | #-header => [buttongroup => ['Scan', ['#'], data => { bind => 'click: scanDatabases'}]] | ||||||||||||||||||||||
53 | sub create_panel { | ||||||||||||||||||||||
54 | 6 | 6 | 0 | 7 | my $c = shift; | ||||||||||||||||||
55 | 6 | 9 | my $title = shift; | ||||||||||||||||||||
56 | 6 | 6 | my $body = shift; | ||||||||||||||||||||
57 | 6 | 8 | my $attr = shift; | ||||||||||||||||||||
58 | |||||||||||||||||||||||
59 | 6 | 100 | 17 | my $header_attr = exists $attr->{'-header'} ? delete($attr->{'-header'}) : []; | |||||||||||||||||||
60 | 6 | 10 | my $header_button_groups = ''; | ||||||||||||||||||||
61 | 6 | 100 | 20 | if(scalar keys @$header_attr) { | |||||||||||||||||||
62 | 1 | 3 | for my $attr (shift @$header_attr) { | ||||||||||||||||||||
63 | 1 | 50 | 5 | if($attr eq 'buttongroup') { | |||||||||||||||||||
64 | 1 | 4 | $header_button_groups .= bootstrap_buttongroup($c, class => 'pull-right', (shift @$header_attr)->@*); | ||||||||||||||||||||
65 | } | ||||||||||||||||||||||
66 | } | ||||||||||||||||||||||
67 | } | ||||||||||||||||||||||
68 | |||||||||||||||||||||||
69 | 6 | 100 | 48 | my $tag = qq{ | |||||||||||||||||||
70 | |
||||||||||||||||||||||
71 | } . (defined $title ? qq{ | ||||||||||||||||||||||
72 | |
||||||||||||||||||||||
73 | $header_button_groups$title |
||||||||||||||||||||||
74 | |||||||||||||||||||||||
75 | } : '') . qq{ | ||||||||||||||||||||||
76 | $body | ||||||||||||||||||||||
77 | |||||||||||||||||||||||
78 | }; | ||||||||||||||||||||||
79 | |||||||||||||||||||||||
80 | 6 | 11 | return out($tag); | ||||||||||||||||||||
81 | } | ||||||||||||||||||||||
82 | |||||||||||||||||||||||
83 | sub bootstrap_table { | ||||||||||||||||||||||
84 | 6 | 6 | 0 | 23564 | my $c = shift; | ||||||||||||||||||
85 | 6 | 50 | 17 | my $callback = ref $_[-1] eq 'CODE' ? pop : undef; | |||||||||||||||||||
86 | 6 | 100 | 14 | my $title = scalar @_ % 2 ? shift : undef; | |||||||||||||||||||
87 | 6 | 14 | my $attr = parse_attributes(@_); | ||||||||||||||||||||
88 | |||||||||||||||||||||||
89 | 6 | 22 | $attr = add_classes($attr, 'table', { table => 'table-%s' }); | ||||||||||||||||||||
90 | 6 | 16 | my $html = htmlify_attrs($attr); | ||||||||||||||||||||
91 | |||||||||||||||||||||||
92 | 6 | 27 | my $table = qq{ | ||||||||||||||||||||
93 |
|
||||||||||||||||||||||
96 | }; | ||||||||||||||||||||||
97 | |||||||||||||||||||||||
98 | 6 | 100 | 144 | if(defined $title) { | |||||||||||||||||||
99 | 2 | 9 | $attr->{'panel'} = add_classes($attr->{'panel'}, 'panel', { panel => 'panel-%s', panel_default => 'default'}); | ||||||||||||||||||||
100 | } | ||||||||||||||||||||||
101 | |||||||||||||||||||||||
102 | 6 | 100 | 21 | return defined $title ? create_panel($c, $title, $table, $attr->{'panel'}) : out($table); | |||||||||||||||||||
103 | } | ||||||||||||||||||||||
104 | |||||||||||||||||||||||
105 | sub htmlify_attrs { | ||||||||||||||||||||||
106 | 231 | 231 | 0 | 207 | my $attr = shift; | ||||||||||||||||||
107 | 231 | 50 | 341 | return '' if !defined $attr; | |||||||||||||||||||
108 | 231 | 590 | $attr = cleanup_attrs({$attr->%*}); #* Make a copy | ||||||||||||||||||||
109 | |||||||||||||||||||||||
110 | 231 | 417 | my $html = join ' ' => map { qq{$_="$attr->{ $_ }"} } grep { length $attr->{ $_ } } sort keys $attr->%*; | ||||||||||||||||||||
331 | 611 | ||||||||||||||||||||||
340 | 347 | ||||||||||||||||||||||
111 | 231 | 50 | 673 | return ' ' . $html if defined $html; | |||||||||||||||||||
112 | 0 | 0 | return ''; | ||||||||||||||||||||
113 | } | ||||||||||||||||||||||
114 | |||||||||||||||||||||||
115 | sub bootstrap_formgroup { | ||||||||||||||||||||||
116 | 12 | 12 | 0 | 48494 | my $c = shift; | ||||||||||||||||||
117 | 12 | 100 | 39 | my $title = ref $_[-1] eq 'CODE' ? pop | |||||||||||||||||||
100 | |||||||||||||||||||||||
118 | : scalar @_ % 2 ? shift | ||||||||||||||||||||||
119 | : undef; | ||||||||||||||||||||||
120 | 12 | 23 | my $attr = parse_attributes(@_); | ||||||||||||||||||||
121 | |||||||||||||||||||||||
122 | 12 | 100 | 25 | $attr->{'column_information'} = delete $attr->{'cols'} if ref $attr->{'cols'} eq 'HASH'; | |||||||||||||||||||
123 | |||||||||||||||||||||||
124 | 12 | 20 | my($id, $input) = fix_input($c, $attr); | ||||||||||||||||||||
125 | 12 | 100 | 101 | my $label = defined $title ? fix_label($c, $id, $title, $attr) : ''; | |||||||||||||||||||
126 | |||||||||||||||||||||||
127 | 12 | 505 | $attr = add_classes($attr, 'form-group', { size => 'form-group-%s'}); | ||||||||||||||||||||
128 | 12 | 24 | $attr = cleanup_attrs($attr); | ||||||||||||||||||||
129 | |||||||||||||||||||||||
130 | |||||||||||||||||||||||
131 | 12 | 37 | my $tag = qq{ | ||||||||||||||||||||
132 | |
||||||||||||||||||||||
133 | $label | ||||||||||||||||||||||
134 | $input | ||||||||||||||||||||||
135 | |||||||||||||||||||||||
136 | }; | ||||||||||||||||||||||
137 | |||||||||||||||||||||||
138 | 12 | 43 | return out($tag); | ||||||||||||||||||||
139 | } | ||||||||||||||||||||||
140 | |||||||||||||||||||||||
141 | sub bootstrap_button { | ||||||||||||||||||||||
142 | 51 | 51 | 0 | 21183 | my $c = shift; | ||||||||||||||||||
143 | 51 | 100 | 105 | my $content = ref $_[-1] eq 'CODE' ? pop : shift; | |||||||||||||||||||
144 | 51 | 100 | 99 | $content = '' if !defined $content; | |||||||||||||||||||
145 | |||||||||||||||||||||||
146 | 51 | 100 | 112 | my @url = shift->@* if ref $_[0] eq 'ARRAY'; | |||||||||||||||||||
147 | 51 | 76 | my $attr = parse_attributes(@_); | ||||||||||||||||||||
148 | |||||||||||||||||||||||
149 | 51 | 100 | 66 | 158 | my $caret = exists $attr->{'__caret'} && $attr->{'__caret'} ? (length $content ? ' ' : '') . q{} : ''; | ||||||||||||||||||
100 | |||||||||||||||||||||||
150 | |||||||||||||||||||||||
151 | 51 | 100 | 66 | 154 | $attr->{'type'} = 'button' if !scalar @url && !exists $attr->{'type'}; | ||||||||||||||||||
152 | 51 | 173 | $attr = add_classes($attr, 'btn', { size => 'btn-%s', button => 'btn-%s', button_default => 'default' }); | ||||||||||||||||||||
153 | 51 | 100 | 126 | $attr = add_classes($attr, 'active') if $attr->{'__active'}; | |||||||||||||||||||
154 | 51 | 100 | 105 | $attr = add_classes($attr, 'block') if $attr->{'__block'}; | |||||||||||||||||||
155 | 51 | 77 | $attr = add_disabled($attr, scalar @url); | ||||||||||||||||||||
156 | 51 | 74 | $attr = cleanup_attrs($attr); | ||||||||||||||||||||
157 | |||||||||||||||||||||||
158 | # We have an url | ||||||||||||||||||||||
159 | 51 | 100 | 76 | if(scalar @url) { | |||||||||||||||||||
160 | 12 | 37 | $attr->{'href'} = url_for($c, \@url); | ||||||||||||||||||||
161 | |||||||||||||||||||||||
162 | 12 | 1191 | my $html = htmlify_attrs($attr); | ||||||||||||||||||||
163 | 12 | 33 | return out(qq{} . content_single($content) . qq{$caret}); | ||||||||||||||||||||
164 | } | ||||||||||||||||||||||
165 | else { | ||||||||||||||||||||||
166 | 39 | 59 | my $html = htmlify_attrs($attr); | ||||||||||||||||||||
167 | 39 | 111 | return out(qq{}); | ||||||||||||||||||||
168 | } | ||||||||||||||||||||||
169 | |||||||||||||||||||||||
170 | } | ||||||||||||||||||||||
171 | |||||||||||||||||||||||
172 | sub bootstrap_submit { | ||||||||||||||||||||||
173 | 6 | 6 | 0 | 7037 | push @_ => (type => 'submit'); | ||||||||||||||||||
174 | 6 | 12 | return bootstrap_button(@_); | ||||||||||||||||||||
175 | } | ||||||||||||||||||||||
176 | |||||||||||||||||||||||
177 | sub bootstrap_context_menu { | ||||||||||||||||||||||
178 | 1 | 1 | 0 | 12616 | my $c = shift; | ||||||||||||||||||
179 | 1 | 3 | my %args = @_; | ||||||||||||||||||||
180 | 1 | 2 | my $items = delete $args{'items'}; | ||||||||||||||||||||
181 | 1 | 2 | my $list = make_dropdown_list($c, \%args, $items); | ||||||||||||||||||||
182 | |||||||||||||||||||||||
183 | 1 | 9 | return out($list); | ||||||||||||||||||||
184 | } | ||||||||||||||||||||||
185 | |||||||||||||||||||||||
186 | sub bootstrap_dropdown { | ||||||||||||||||||||||
187 | 2 | 2 | 0 | 16 | my $meat = make_dropdown_meat(shift, shift->@*); | ||||||||||||||||||
188 | |||||||||||||||||||||||
189 | 2 | 18 | my $dropdown = qq{ | ||||||||||||||||||||
190 | |
||||||||||||||||||||||
191 | $meat | ||||||||||||||||||||||
192 | |||||||||||||||||||||||
193 | }; | ||||||||||||||||||||||
194 | 2 | 10 | return out($dropdown); | ||||||||||||||||||||
195 | } | ||||||||||||||||||||||
196 | |||||||||||||||||||||||
197 | sub make_dropdown_meat { | ||||||||||||||||||||||
198 | 11 | 11 | 0 | 11 | my $c = shift; | ||||||||||||||||||
199 | |||||||||||||||||||||||
200 | 11 | 13 | my $button_text = shift; | ||||||||||||||||||||
201 | 11 | 100 | 28 | my @url = ref $_[0] eq 'ARRAY' ? shift->@* : (); | |||||||||||||||||||
202 | 11 | 26 | my $attr = parse_attributes(@_); | ||||||||||||||||||||
203 | |||||||||||||||||||||||
204 | 11 | 50 | 27 | my $items = delete $attr->{'items'} || []; | |||||||||||||||||||
205 | 11 | 100 | 31 | my $ulattr = { __right => exists $attr->{'__right'} ? delete $attr->{'__right'} : 0 }; | |||||||||||||||||||
206 | 11 | 24 | my $listhtml = make_dropdown_list($c, $ulattr, $items); | ||||||||||||||||||||
207 | |||||||||||||||||||||||
208 | 11 | 57 | $attr = add_classes($attr, 'dropdown-toggle'); | ||||||||||||||||||||
209 | 11 | 21 | $attr->{'data-toggle'} = 'dropdown'; | ||||||||||||||||||||
210 | 11 | 18 | $attr->{'type'} = 'button'; | ||||||||||||||||||||
211 | 11 | 40 | my $button = bootstrap_button($c, $button_text, @url, $attr->%*); | ||||||||||||||||||||
212 | |||||||||||||||||||||||
213 | 11 | 80 | my $out = qq{ | ||||||||||||||||||||
214 | $button | ||||||||||||||||||||||
215 | $listhtml | ||||||||||||||||||||||
216 | }; | ||||||||||||||||||||||
217 | 11 | 75 | return out($out); | ||||||||||||||||||||
218 | } | ||||||||||||||||||||||
219 | |||||||||||||||||||||||
220 | sub make_dropdown_list { | ||||||||||||||||||||||
221 | 12 | 12 | 0 | 13 | my $c = shift; | ||||||||||||||||||
222 | 12 | 15 | my $attr = shift; | ||||||||||||||||||||
223 | 12 | 9 | my $items = shift; | ||||||||||||||||||||
224 | |||||||||||||||||||||||
225 | 12 | 22 | $attr = add_classes($attr, 'dropdown-menu'); | ||||||||||||||||||||
226 | 12 | 100 | 44 | $attr = add_classes($attr, 'dropdown-menu-right') if $attr->{'__right'}; | |||||||||||||||||||
227 | 12 | 26 | my $attrhtml = htmlify_attrs($attr); | ||||||||||||||||||||
228 | 12 | 19 | my $menuitems = ''; | ||||||||||||||||||||
229 | |||||||||||||||||||||||
230 | ITEM: | ||||||||||||||||||||||
231 | 12 | 22 | foreach my $item ($items->@*) { | ||||||||||||||||||||
232 | 49 | 100 | 348 | if(ref $item eq '') { | |||||||||||||||||||
233 | 1 | 3 | $menuitems .= qq{ |
||||||||||||||||||||
234 | } | ||||||||||||||||||||||
235 | 49 | 100 | 77 | next ITEM if ref $item ne 'ARRAY'; | |||||||||||||||||||
236 | 48 | 100 | 76 | if(!scalar $item->@*) { | |||||||||||||||||||
237 | 12 | 20 | $menuitems .= q{} ; | ||||||||||||||||||||
238 | } | ||||||||||||||||||||||
239 | else { | ||||||||||||||||||||||
240 | 36 | 58 | $menuitems .= create_dropdown_menuitem($c, $item->@*); | ||||||||||||||||||||
241 | } | ||||||||||||||||||||||
242 | |||||||||||||||||||||||
243 | } | ||||||||||||||||||||||
244 | 12 | 127 | my $out = qq{ | ||||||||||||||||||||
245 | |
||||||||||||||||||||||
246 | $menuitems | ||||||||||||||||||||||
247 | |||||||||||||||||||||||
248 | }; | ||||||||||||||||||||||
249 | 12 | 21 | return out($out); | ||||||||||||||||||||
250 | } | ||||||||||||||||||||||
251 | |||||||||||||||||||||||
252 | sub create_dropdown_menuitem { | ||||||||||||||||||||||
253 | 36 | 36 | 0 | 31 | my $c = shift; | ||||||||||||||||||
254 | 36 | 50 | 71 | my $item_text = iscoderef($_[-1]) ? pop : shift; | |||||||||||||||||||
255 | 36 | 59 | my @url = shift->@*; | ||||||||||||||||||||
256 | |||||||||||||||||||||||
257 | 36 | 48 | my $attr = parse_attributes(@_); | ||||||||||||||||||||
258 | 36 | 49 | $attr = add_classes($attr, 'menuitem'); | ||||||||||||||||||||
259 | 36 | 100 | 76 | my $liattr = { __disabled => exists $attr->{'__disabled'} ? delete $attr->{'__disabled'} : 0 }; | |||||||||||||||||||
260 | 36 | 60 | $liattr = add_disabled($liattr, 1); | ||||||||||||||||||||
261 | 36 | 100 | 152 | $attr->{'tabindex'} ||= -1; | |||||||||||||||||||
262 | 36 | 53 | $attr->{'href'} = url_for($c, \@url); | ||||||||||||||||||||
263 | |||||||||||||||||||||||
264 | 36 | 8433 | my $html = htmlify_attrs($attr); | ||||||||||||||||||||
265 | 36 | 50 | my $lihtml = htmlify_attrs($liattr); | ||||||||||||||||||||
266 | |||||||||||||||||||||||
267 | 36 | 66 | my $tag = qq{ |
||||||||||||||||||||
268 | |||||||||||||||||||||||
269 | 36 | 52 | return out($tag); | ||||||||||||||||||||
270 | } | ||||||||||||||||||||||
271 | |||||||||||||||||||||||
272 | sub bootstrap_buttongroup { | ||||||||||||||||||||||
273 | 11 | 11 | 0 | 13134 | my $c = shift; | ||||||||||||||||||
274 | |||||||||||||||||||||||
275 | #* Shortcut for one button menus | ||||||||||||||||||||||
276 | 11 | 100 | 30 | if(ref $_[0] eq 'ARRAY') { | |||||||||||||||||||
277 | 2 | 4 | my $meat = make_dropdown_meat($c, $_[0]->@*); | ||||||||||||||||||||
278 | 2 | 13 | my $menu = qq{ $meat }; |
||||||||||||||||||||
279 | 2 | 9 | return out($menu); | ||||||||||||||||||||
280 | } | ||||||||||||||||||||||
281 | 9 | 19 | my($buttons, $html) = make_buttongroup_meat($c, @_); | ||||||||||||||||||||
282 | |||||||||||||||||||||||
283 | 9 | 47 | my $tag = qq{ | ||||||||||||||||||||
284 | |
||||||||||||||||||||||
285 | $buttons | ||||||||||||||||||||||
286 | }; | ||||||||||||||||||||||
287 | |||||||||||||||||||||||
288 | 9 | 12 | return out($tag); | ||||||||||||||||||||
289 | } | ||||||||||||||||||||||
290 | |||||||||||||||||||||||
291 | sub make_buttongroup_meat { | ||||||||||||||||||||||
292 | 10 | 10 | 0 | 12 | my $c = shift; | ||||||||||||||||||
293 | |||||||||||||||||||||||
294 | 10 | 19 | my $attr = parse_attributes(@_); | ||||||||||||||||||||
295 | 10 | 19 | my $buttons_info = delete $attr->{'buttons'}; | ||||||||||||||||||||
296 | |||||||||||||||||||||||
297 | 10 | 100 | 29 | my $button_group_class = delete $attr->{'__vertical'} ? 'btn-group-vertical' : 'btn-group'; | |||||||||||||||||||
298 | 10 | 100 | 22 | my $justified_class = delete $attr->{'__justified'} ? 'btn-group-justified' : (); | |||||||||||||||||||
299 | |||||||||||||||||||||||
300 | 10 | 26 | $attr = add_classes($attr, { size => 'btn-group-%s' }); | ||||||||||||||||||||
301 | |||||||||||||||||||||||
302 | #* For the possible inner btn-group, use the same base classes (except justified/vertical/pull-right). | ||||||||||||||||||||||
303 | #* We add possible .dropup in the loop | ||||||||||||||||||||||
304 | 10 | 34 | my $inner_attr = add_classes({ class => $attr->{'class'} }, 'btn-group'); | ||||||||||||||||||||
305 | 10 | 18 | $inner_attr->{'class'} =~ s{\bpull-right\b}{}; | ||||||||||||||||||||
306 | |||||||||||||||||||||||
307 | #* These must come after the inner button group has been given the classes. | ||||||||||||||||||||||
308 | 10 | 19 | $attr = add_classes($attr, $button_group_class, $justified_class); | ||||||||||||||||||||
309 | 10 | 22 | my $html = htmlify_attrs($attr); | ||||||||||||||||||||
310 | |||||||||||||||||||||||
311 | |||||||||||||||||||||||
312 | 10 | 16 | my $buttons = ''; | ||||||||||||||||||||
313 | |||||||||||||||||||||||
314 | BUTTON: | ||||||||||||||||||||||
315 | 10 | 20 | foreach my $button ($buttons_info->@*) { | ||||||||||||||||||||
316 | 29 | 50 | 78 | next BUTTON if ref $button ne 'ARRAY'; | |||||||||||||||||||
317 | |||||||||||||||||||||||
318 | 29 | 32 | my $button_text = shift $button->@*; | ||||||||||||||||||||
319 | 29 | 100 | 65 | my @url = ref $button->[0] eq 'ARRAY' ? shift $button->@* : (); | |||||||||||||||||||
320 | 29 | 41 | my $button_attr = parse_attributes($button->@*); | ||||||||||||||||||||
321 | 29 | 100 | 105 | my $items = delete $button_attr->{'items'} || []; | |||||||||||||||||||
322 | |||||||||||||||||||||||
323 | 29 | 100 | 44 | if(!scalar $items->@*) { | |||||||||||||||||||
324 | 23 | 51 | my $bootstrap_button = bootstrap_button($c, $button_text, @url, $button_attr->%*); | ||||||||||||||||||||
325 | |||||||||||||||||||||||
326 | #* Justified + No url -> button -> must nest | ||||||||||||||||||||||
327 | 23 | 100 | 100 | 168 | if(length $justified_class && !scalar @url) { | ||||||||||||||||||
328 | 3 | 6 | $buttons .= qq{ $bootstrap_button }; |
||||||||||||||||||||
329 | } | ||||||||||||||||||||||
330 | else { | ||||||||||||||||||||||
331 | 20 | 93 | $buttons .= $bootstrap_button; | ||||||||||||||||||||
332 | } | ||||||||||||||||||||||
333 | 23 | 150 | next BUTTON; | ||||||||||||||||||||
334 | } | ||||||||||||||||||||||
335 | |||||||||||||||||||||||
336 | 6 | 100 | 15 | my $dropup_class = delete $button_attr->{'__dropup'} ? 'dropup' : (); | |||||||||||||||||||
337 | 6 | 11 | $inner_attr = add_classes($inner_attr, $dropup_class); | ||||||||||||||||||||
338 | 6 | 11 | my $inner_html = htmlify_attrs($inner_attr); | ||||||||||||||||||||
339 | 6 | 100 | 34 | my $meat = make_dropdown_meat($c, $button_text, (scalar @url ? \@url : ()), $button_attr->%*, items => $items); | |||||||||||||||||||
340 | 6 | 44 | $buttons .= qq{ | ||||||||||||||||||||
341 | |
||||||||||||||||||||||
342 | $meat | ||||||||||||||||||||||
343 | |||||||||||||||||||||||
344 | }; | ||||||||||||||||||||||
345 | |||||||||||||||||||||||
346 | } | ||||||||||||||||||||||
347 | 10 | 49 | return ($buttons, $html); | ||||||||||||||||||||
348 | } | ||||||||||||||||||||||
349 | |||||||||||||||||||||||
350 | sub bootstrap_toolbar { | ||||||||||||||||||||||
351 | 1 | 1 | 0 | 5 | my $c = shift; | ||||||||||||||||||
352 | |||||||||||||||||||||||
353 | 1 | 3 | my $attr = parse_attributes(@_); | ||||||||||||||||||||
354 | 1 | 2 | my $groups = delete $attr->{'groups'}; | ||||||||||||||||||||
355 | |||||||||||||||||||||||
356 | 1 | 3 | $attr = add_classes($attr, 'btn-toolbar'); | ||||||||||||||||||||
357 | 1 | 3 | my $html = htmlify_attrs($attr); | ||||||||||||||||||||
358 | |||||||||||||||||||||||
359 | 1 | 2 | my $toolbar = ''; | ||||||||||||||||||||
360 | 1 | 2 | foreach my $group ($groups->@*) { | ||||||||||||||||||||
361 | 2 | 16 | $toolbar .= bootstrap_buttongroup($c, $group->%*); | ||||||||||||||||||||
362 | } | ||||||||||||||||||||||
363 | |||||||||||||||||||||||
364 | 1 | 9 | my $tag = qq{ | ||||||||||||||||||||
365 | |
||||||||||||||||||||||
366 | $toolbar | ||||||||||||||||||||||
367 | |||||||||||||||||||||||
368 | }; | ||||||||||||||||||||||
369 | |||||||||||||||||||||||
370 | 1 | 1 | return out($tag); | ||||||||||||||||||||
371 | } | ||||||||||||||||||||||
372 | |||||||||||||||||||||||
373 | sub bootstrap_navbar { | ||||||||||||||||||||||
374 | 5 | 5 | 0 | 20 | my $c = shift; | ||||||||||||||||||
375 | |||||||||||||||||||||||
376 | 5 | 7 | my($possible_toggler_id, $navbar_header) = (); | ||||||||||||||||||||
377 | |||||||||||||||||||||||
378 | 5 | 6 | my $content_html = ''; | ||||||||||||||||||||
379 | 5 | 5 | my $has_inverse = 0; | ||||||||||||||||||||
380 | 5 | 5 | my $container = 'fluid'; | ||||||||||||||||||||
381 | |||||||||||||||||||||||
382 | 5 | 14 | while(scalar @_) { | ||||||||||||||||||||
383 | 20 | 14 | my $key = shift; | ||||||||||||||||||||
384 | 20 | 23 | my @arguments = ($c, shift); | ||||||||||||||||||||
385 | |||||||||||||||||||||||
386 | 20 | 100 | 67 | $content_html .= $key eq 'nav' ? make_navbar_nav(@arguments) | |||||||||||||||||||
100 | |||||||||||||||||||||||
100 | |||||||||||||||||||||||
100 | |||||||||||||||||||||||
387 | : $key eq 'form' ? make_navbar_form(@arguments) | ||||||||||||||||||||||
388 | : $key eq 'button' ? make_navbar_button(@arguments) | ||||||||||||||||||||||
389 | : $key eq 'p' ? make_navbar_p(@arguments) | ||||||||||||||||||||||
390 | : '' | ||||||||||||||||||||||
391 | ; | ||||||||||||||||||||||
392 | 20 | 100 | 94 | if($key eq 'header') { | |||||||||||||||||||
393 | 5 | 11 | ($possible_toggler_id, $navbar_header) = make_navbar_header(@arguments); | ||||||||||||||||||||
394 | } | ||||||||||||||||||||||
395 | 20 | 100 | 30 | if($key eq '__inverse') { | |||||||||||||||||||
396 | 2 | 3 | $has_inverse = 1; | ||||||||||||||||||||
397 | } | ||||||||||||||||||||||
398 | 20 | 100 | 49 | if($key eq 'container') { | |||||||||||||||||||
399 | 1 | 2 | $container = $arguments[1]; | ||||||||||||||||||||
400 | } | ||||||||||||||||||||||
401 | |||||||||||||||||||||||
402 | } | ||||||||||||||||||||||
403 | 5 | 100 | 11 | $container = $container eq 'normal' ? 'container' : 'container-fluid'; | |||||||||||||||||||
404 | |||||||||||||||||||||||
405 | 5 | 100 | 8 | my $attr = $has_inverse ? { __inverse => 1 } : {}; | |||||||||||||||||||
406 | 5 | 13 | $attr = add_classes($attr, 'navbar', { navbar => 'navbar-%s', navbar_default => 'default' }); | ||||||||||||||||||||
407 | 5 | 10 | my $html = htmlify_attrs($attr); | ||||||||||||||||||||
408 | 5 | 100 | 9 | if(length $content_html) { | |||||||||||||||||||
409 | 4 | 17 | $content_html = qq{ | ||||||||||||||||||||
410 | |||||||||||||||||||||||
411 | $content_html | ||||||||||||||||||||||
412 | |||||||||||||||||||||||
413 | }; | ||||||||||||||||||||||
414 | } | ||||||||||||||||||||||
415 | |||||||||||||||||||||||
416 | 5 | 17 | my $tag = qq{ | ||||||||||||||||||||
417 | |||||||||||||||||||||||
418 | |
||||||||||||||||||||||
419 | $navbar_header | ||||||||||||||||||||||
420 | $content_html | ||||||||||||||||||||||
421 | |||||||||||||||||||||||
422 | |||||||||||||||||||||||
423 | }; | ||||||||||||||||||||||
424 | |||||||||||||||||||||||
425 | 5 | 6 | return out($tag); | ||||||||||||||||||||
426 | |||||||||||||||||||||||
427 | } | ||||||||||||||||||||||
428 | sub make_navbar_header { | ||||||||||||||||||||||
429 | 5 | 5 | 0 | 4 | my($c, $header, $html_header) = @_; | ||||||||||||||||||
430 | |||||||||||||||||||||||
431 | 5 | 50 | 7 | return (undef, $html_header) if $html_header; | |||||||||||||||||||
432 | |||||||||||||||||||||||
433 | 5 | 9 | my $brand = shift $header->@*; | ||||||||||||||||||||
434 | 5 | 50 | 15 | my $url = url_for($c, shift $header->@* || []); | |||||||||||||||||||
435 | 5 | 11 | my $header_attr = parse_attributes($header->@*); | ||||||||||||||||||||
436 | 5 | 33 | 14 | my $toggler_id = delete $header_attr->{'toggler'} || 'collapsable-' . String::Random->new->randregex('[a-z]{20}'); | |||||||||||||||||||
437 | 5 | 6 | my $has_hamburger = delete $header_attr->{'__hamburger'}; | ||||||||||||||||||||
438 | 5 | 50 | 11 | my $hamburger = $has_hamburger ? get_hamburger($toggler_id) : ''; | |||||||||||||||||||
439 | 5 | 9 | $header_attr = add_classes($header_attr, 'navbar-brand'); | ||||||||||||||||||||
440 | |||||||||||||||||||||||
441 | 5 | 50 | 16 | my $brand_html = defined $brand ? qq{$brand} : ''; | |||||||||||||||||||
442 | |||||||||||||||||||||||
443 | 5 | 8 | my $navbar_header = qq{ | ||||||||||||||||||||
444 | |||||||||||||||||||||||
445 | $hamburger | ||||||||||||||||||||||
446 | $brand_html | ||||||||||||||||||||||
447 | |||||||||||||||||||||||
448 | }; | ||||||||||||||||||||||
449 | |||||||||||||||||||||||
450 | 5 | 10 | return ($toggler_id, $navbar_header); | ||||||||||||||||||||
451 | |||||||||||||||||||||||
452 | } | ||||||||||||||||||||||
453 | |||||||||||||||||||||||
454 | sub make_navbar_nav { | ||||||||||||||||||||||
455 | 5 | 5 | 0 | 4 | my $c = shift; | ||||||||||||||||||
456 | 5 | 4 | my $nav = shift; | ||||||||||||||||||||
457 | |||||||||||||||||||||||
458 | 5 | 10 | my $attr = parse_attributes($nav->@*); | ||||||||||||||||||||
459 | 5 | 7 | my $items = delete $attr->{'items'}; | ||||||||||||||||||||
460 | 5 | 12 | $attr = add_classes($attr, 'nav', 'navbar-nav', { direction => 'navbar-%s' }); | ||||||||||||||||||||
461 | 5 | 11 | my $html = htmlify_attrs($attr); | ||||||||||||||||||||
462 | |||||||||||||||||||||||
463 | 5 | 31 | my $tag = "
|
||||||||||||||||||||
464 | 5 | 11 | $tag .= make_nav_meat($c, $items); | ||||||||||||||||||||
465 | |||||||||||||||||||||||
466 | 5 | 6 | $tag .= ''; | ||||||||||||||||||||
467 | 5 | 10 | return $tag; | ||||||||||||||||||||
468 | } | ||||||||||||||||||||||
469 | |||||||||||||||||||||||
470 | sub make_navbar_form { | ||||||||||||||||||||||
471 | 3 | 3 | 0 | 3 | my $c = shift; | ||||||||||||||||||
472 | 3 | 5 | my $form = shift; | ||||||||||||||||||||
473 | 3 | 3 | my $args = shift $form->@*; | ||||||||||||||||||||
474 | 3 | 4 | my $contents = shift $form->@*; | ||||||||||||||||||||
475 | 3 | 3 | my $url = shift $args->@*; | ||||||||||||||||||||
476 | |||||||||||||||||||||||
477 | 3 | 4 | my $attr = parse_attributes($args->@*); | ||||||||||||||||||||
478 | |||||||||||||||||||||||
479 | 3 | 7 | $attr = add_classes($attr, 'navbar-form', { direction => 'navbar-%s', direction_default => 'left' }); | ||||||||||||||||||||
480 | 3 | 7 | $attr = cleanup_attrs($attr); | ||||||||||||||||||||
481 | |||||||||||||||||||||||
482 | 3 | 4 | my $tag = ''; | ||||||||||||||||||||
483 | 3 | 8 | for (my $index = 0; $index < scalar $contents->@*; $index += 2) { | ||||||||||||||||||||
484 | 6 | 36 | my $key = $contents->[$index]; | ||||||||||||||||||||
485 | 6 | 14 | my @arguments = ($c, $contents->[$index + 1]->@*); | ||||||||||||||||||||
486 | |||||||||||||||||||||||
487 | 6 | 100 | 13 | if($key eq 'formgroup') { | |||||||||||||||||||
50 | |||||||||||||||||||||||
0 | |||||||||||||||||||||||
0 | |||||||||||||||||||||||
488 | 3 | 5 | $tag .= bootstrap_formgroup(@arguments); | ||||||||||||||||||||
489 | } | ||||||||||||||||||||||
490 | elsif($key eq 'submit_button') { | ||||||||||||||||||||||
491 | 3 | 6 | $tag .= bootstrap_submit(@arguments); | ||||||||||||||||||||
492 | } | ||||||||||||||||||||||
493 | elsif($key eq 'button') { | ||||||||||||||||||||||
494 | 0 | 0 | $tag .= bootstrap_button(@arguments) | ||||||||||||||||||||
495 | } | ||||||||||||||||||||||
496 | elsif($key eq 'input') { | ||||||||||||||||||||||
497 | 0 | 0 | $tag .= bootstrap_input(@arguments); | ||||||||||||||||||||
498 | } | ||||||||||||||||||||||
499 | } | ||||||||||||||||||||||
500 | |||||||||||||||||||||||
501 | 3 | 3 | 51 | $tag = Mojolicious::Plugin::TagHelpers::_form_for($c, $url->@*, $attr->%*, sub { $tag }); | |||||||||||||||||||
3 | 617 | ||||||||||||||||||||||
502 | 3 | 681 | return out($tag); | ||||||||||||||||||||
503 | |||||||||||||||||||||||
504 | } | ||||||||||||||||||||||
505 | |||||||||||||||||||||||
506 | 2 | 50 | 2 | 0 | 5 | sub make_navbar_button($c, $arg) { | |||||||||||||||||
2 | 50 | 5 | |||||||||||||||||||||
2 | 1 | ||||||||||||||||||||||
2 | 2 | ||||||||||||||||||||||
2 | 2 | ||||||||||||||||||||||
507 | 2 | 2 | my $text = shift $arg->@*; | ||||||||||||||||||||
508 | 2 | 2 | my $url = shift $arg->@*; | ||||||||||||||||||||
509 | 2 | 5 | my $attr = parse_attributes($arg->@*); | ||||||||||||||||||||
510 | 2 | 5 | $attr = add_classes($attr, 'navbar-btn', { direction => 'navbar-%s' }); | ||||||||||||||||||||
511 | 2 | 6 | return bootstrap_button($c, $text, $url, $attr->%*); | ||||||||||||||||||||
512 | } | ||||||||||||||||||||||
513 | |||||||||||||||||||||||
514 | 2 | 50 | 2 | 0 | 5 | sub make_navbar_p($c, $arg) { | |||||||||||||||||
2 | 50 | 5 | |||||||||||||||||||||
2 | 1 | ||||||||||||||||||||||
2 | 2 | ||||||||||||||||||||||
2 | 3 | ||||||||||||||||||||||
515 | 2 | 2 | my $text = shift $arg->@*; | ||||||||||||||||||||
516 | 2 | 3 | my $attr = parse_attributes($arg->@*); | ||||||||||||||||||||
517 | 2 | 5 | $attr = add_classes($attr, 'navbar-text', { direction => 'navbar-%s' }); | ||||||||||||||||||||
518 | 2 | 5 | my $html = htmlify_attrs($attr); | ||||||||||||||||||||
519 | |||||||||||||||||||||||
520 | 2 | 6 | return out(qq{ $text }); |
||||||||||||||||||||
521 | } | ||||||||||||||||||||||
522 | |||||||||||||||||||||||
523 | sub get_hamburger { | ||||||||||||||||||||||
524 | 5 | 5 | 0 | 5 | my $toggler_id = shift; | ||||||||||||||||||
525 | |||||||||||||||||||||||
526 | 5 | 9 | my $tag = qq{ | ||||||||||||||||||||
527 | |||||||||||||||||||||||
528 | |||||||||||||||||||||||
529 | |||||||||||||||||||||||
530 | |||||||||||||||||||||||
531 | |||||||||||||||||||||||
532 | }; | ||||||||||||||||||||||
533 | 5 | 6 | return $tag; | ||||||||||||||||||||
534 | } | ||||||||||||||||||||||
535 | |||||||||||||||||||||||
536 | sub make_nav_meat { | ||||||||||||||||||||||
537 | 7 | 7 | 0 | 8 | my $c = shift; | ||||||||||||||||||
538 | 7 | 6 | my $contents = shift; | ||||||||||||||||||||
539 | |||||||||||||||||||||||
540 | 7 | 7 | my $tag = ''; | ||||||||||||||||||||
541 | CONTENT: | ||||||||||||||||||||||
542 | 7 | 11 | foreach my $content ($contents->@*) { | ||||||||||||||||||||
543 | 18 | 50 | 37 | next CONTENT if ref $content ne 'ARRAY'; | |||||||||||||||||||
544 | |||||||||||||||||||||||
545 | 18 | 18 | my $text = shift $content->@*; | ||||||||||||||||||||
546 | 18 | 25 | my $url = url_for($c, shift $content->@*); | ||||||||||||||||||||
547 | 18 | 26 | my $attr = parse_attributes($content->@*); | ||||||||||||||||||||
548 | |||||||||||||||||||||||
549 | 18 | 100 | 50 | my $items = delete $attr->{'items'} || []; | |||||||||||||||||||
550 | #* No sub menu | ||||||||||||||||||||||
551 | 18 | 100 | 36 | if(!scalar $items->@*) { | |||||||||||||||||||
552 | 14 | 16 | my $active = delete $attr->{'__active'}; | ||||||||||||||||||||
553 | 14 | 22 | my $disabled = delete $attr->{'__disabled'}; | ||||||||||||||||||||
554 | 14 | 100 | 22 | my $li_attr = exists $attr->{'-li'} ? parse_attributes(delete($attr->{'-li'})->@*) : {}; | |||||||||||||||||||
555 | 14 | 100 | 33 | $li_attr = add_classes($li_attr, $active ? 'active' : (), $disabled ? 'disabled' : ()); | |||||||||||||||||||
100 | |||||||||||||||||||||||
556 | 14 | 17 | my $li_html = htmlify_attrs($li_attr); | ||||||||||||||||||||
557 | |||||||||||||||||||||||
558 | 14 | 19 | my $a_attr = htmlify_attrs($attr); | ||||||||||||||||||||
559 | |||||||||||||||||||||||
560 | 14 | 21 | my $link_html = qq{$text}; | ||||||||||||||||||||
561 | 14 | 20 | $tag .= qq{ |
||||||||||||||||||||
562 | 14 | 61 | next CONTENT; | ||||||||||||||||||||
563 | } | ||||||||||||||||||||||
564 | else { | ||||||||||||||||||||||
565 | 4 | 6 | $attr = add_classes($attr, 'dropdown-toggle'); | ||||||||||||||||||||
566 | 4 | 8 | $attr->{'data-toggle'} = 'dropdown'; | ||||||||||||||||||||
567 | 4 | 6 | $attr->{'href'} = $url; | ||||||||||||||||||||
568 | 4 | 50 | 10 | my $caret = delete $attr->{'__caret'} ? ' ' : ''; | |||||||||||||||||||
569 | 4 | 6 | my $button_arg = htmlify_attrs($attr); | ||||||||||||||||||||
570 | 4 | 11 | my $button_html = qq{$text$caret}; | ||||||||||||||||||||
571 | |||||||||||||||||||||||
572 | 4 | 6 | my $lis = ''; | ||||||||||||||||||||
573 | ITEM: | ||||||||||||||||||||||
574 | 4 | 6 | foreach my $item ($items->@*) { | ||||||||||||||||||||
575 | 20 | 100 | 30 | if(!scalar $item->@*) { | |||||||||||||||||||
576 | 5 | 6 | $lis .= q{}; | ||||||||||||||||||||
577 | 5 | 6 | next ITEM; | ||||||||||||||||||||
578 | } | ||||||||||||||||||||||
579 | 15 | 14 | my $text = shift $item->@*; | ||||||||||||||||||||
580 | 15 | 20 | my $url = url_for($c, shift $item->@*); | ||||||||||||||||||||
581 | 15 | 19 | my $a_attr = parse_attributes($item->@*); | ||||||||||||||||||||
582 | 15 | 18 | $a_attr->{'href'} = $url; | ||||||||||||||||||||
583 | 15 | 16 | my $a_html = htmlify_attrs($a_attr); | ||||||||||||||||||||
584 | 15 | 30 | $lis .= qq{ |
||||||||||||||||||||
585 | } | ||||||||||||||||||||||
586 | 4 | 15 | $tag .= qq{ | ||||||||||||||||||||
587 | |
||||||||||||||||||||||
588 | $button_html | ||||||||||||||||||||||
589 | |||||||||||||||||||||||
590 | $lis | ||||||||||||||||||||||
591 | |||||||||||||||||||||||
592 | |||||||||||||||||||||||
593 | }; | ||||||||||||||||||||||
594 | } | ||||||||||||||||||||||
595 | } | ||||||||||||||||||||||
596 | 7 | 12 | return $tag; | ||||||||||||||||||||
597 | } | ||||||||||||||||||||||
598 | |||||||||||||||||||||||
599 | sub bootstrap_nav { | ||||||||||||||||||||||
600 | 2 | 2 | 0 | 6 | my $c = shift; | ||||||||||||||||||
601 | 2 | 5 | my $attr = parse_attributes(@_); | ||||||||||||||||||||
602 | 2 | 3 | my $pills = delete $attr->{'pills'}; | ||||||||||||||||||||
603 | 2 | 2 | my $tabs = delete $attr->{'tabs'}; | ||||||||||||||||||||
604 | |||||||||||||||||||||||
605 | 2 | 50 | 6 | my $which = $pills ? 'nav-pills' | |||||||||||||||||||
100 | |||||||||||||||||||||||
606 | : $tabs ? 'nav-tabs' | ||||||||||||||||||||||
607 | : () | ||||||||||||||||||||||
608 | ; | ||||||||||||||||||||||
609 | 2 | 100 | 4 | my $justified = delete $attr->{'__justified'} ? 'nav-justified' : (); | |||||||||||||||||||
610 | 2 | 4 | $attr = add_classes($attr, 'nav', $which, $justified); | ||||||||||||||||||||
611 | 2 | 5 | my $html = htmlify_attrs($attr); | ||||||||||||||||||||
612 | 2 | 66 | 7 | my $either = $pills || $tabs; | |||||||||||||||||||
613 | |||||||||||||||||||||||
614 | 2 | 3 | my $tag = make_nav_meat($c, $either); | ||||||||||||||||||||
615 | 2 | 5 | $tag = qq{
|
||||||||||||||||||||
616 | |||||||||||||||||||||||
617 | 2 | 3 | return out($tag); | ||||||||||||||||||||
618 | } | ||||||||||||||||||||||
619 | |||||||||||||||||||||||
620 | sub bootstrap_badge { | ||||||||||||||||||||||
621 | 3 | 3 | 0 | 12131 | my $c = shift; | ||||||||||||||||||
622 | 3 | 50 | 8 | my $content = iscoderef($_[-1]) ? pop : shift; | |||||||||||||||||||
623 | 3 | 8 | my $attr = parse_attributes(@_); | ||||||||||||||||||||
624 | |||||||||||||||||||||||
625 | 3 | 8 | $attr = add_classes($attr, 'badge', { direction => 'pull-%s' }); | ||||||||||||||||||||
626 | 3 | 8 | my $html = htmlify_attrs($attr); | ||||||||||||||||||||
627 | |||||||||||||||||||||||
628 | 3 | 50 | 33 | 12 | my $badge = defined $content && length $content ? qq{$content} : ''; | ||||||||||||||||||
629 | |||||||||||||||||||||||
630 | 3 | 5 | return out($badge); | ||||||||||||||||||||
631 | } | ||||||||||||||||||||||
632 | |||||||||||||||||||||||
633 | sub bootstrap_icon { | ||||||||||||||||||||||
634 | 4 | 4 | 0 | 27597 | my $c = shift; | ||||||||||||||||||
635 | 4 | 4 | my $icon = shift; | ||||||||||||||||||||
636 | |||||||||||||||||||||||
637 | 4 | 24 | my $icon_class = $c->config->{'Plugin::BootstrapHelpers'}{'icons'}{'class'}; | ||||||||||||||||||||
638 | 4 | 168 | my $formatter = $c->config->{'Plugin::BootstrapHelpers'}{'icons'}{'formatter'}; | ||||||||||||||||||||
639 | |||||||||||||||||||||||
640 | 4 | 99 | my $this_icon = sprintf $formatter => $icon; | ||||||||||||||||||||
641 | 4 | 8 | my $attr = parse_attributes(@_); | ||||||||||||||||||||
642 | 4 | 8 | $attr = add_classes($attr, $icon_class, $this_icon); | ||||||||||||||||||||
643 | 4 | 9 | my $html = htmlify_attrs($attr); | ||||||||||||||||||||
644 | |||||||||||||||||||||||
645 | 4 | 50 | 33 | 15 | return '' if !defined $icon || !length $icon; | ||||||||||||||||||
646 | 4 | 10 | return out(qq{}); | ||||||||||||||||||||
647 | } | ||||||||||||||||||||||
648 | |||||||||||||||||||||||
649 | sub bootstrap_input { | ||||||||||||||||||||||
650 | 5 | 5 | 0 | 22968 | my $c = shift; | ||||||||||||||||||
651 | 5 | 22 | my $attr = parse_attributes(@_); | ||||||||||||||||||||
652 | |||||||||||||||||||||||
653 | 5 | 12 | my $prepend = delete $attr->{'prepend'}; | ||||||||||||||||||||
654 | 5 | 7 | my $append = delete $attr->{'append'}; | ||||||||||||||||||||
655 | |||||||||||||||||||||||
656 | 5 | 19 | my(undef, $input_tag) = fix_input($c, (delete $attr->{'input'}) ); | ||||||||||||||||||||
657 | 5 | 61 | $attr = add_classes($attr, 'input-group', { size => 'input-group-%s' }); | ||||||||||||||||||||
658 | 5 | 22 | my $html = htmlify_attrs($attr); | ||||||||||||||||||||
659 | |||||||||||||||||||||||
660 | 5 | 9 | my($prepend_tag, $append_tag) = undef; | ||||||||||||||||||||
661 | |||||||||||||||||||||||
662 | 5 | 100 | 11 | if($prepend) { | |||||||||||||||||||
663 | 3 | 13 | $prepend_tag = fix_input_ender($c, $prepend); | ||||||||||||||||||||
664 | } | ||||||||||||||||||||||
665 | 5 | 100 | 13 | if($append) { | |||||||||||||||||||
666 | 3 | 11 | $append_tag = fix_input_ender($c, $append); | ||||||||||||||||||||
667 | } | ||||||||||||||||||||||
668 | |||||||||||||||||||||||
669 | 5 | 100 | 39 | my $tag = qq{ | |||||||||||||||||||
100 | |||||||||||||||||||||||
670 | |
||||||||||||||||||||||
671 | } . ($prepend_tag || '') . qq{ | ||||||||||||||||||||||
672 | $input_tag | ||||||||||||||||||||||
673 | } . ($append_tag || '') . qq{ | ||||||||||||||||||||||
674 | |||||||||||||||||||||||
675 | }; | ||||||||||||||||||||||
676 | |||||||||||||||||||||||
677 | 5 | 9 | return out($tag); | ||||||||||||||||||||
678 | |||||||||||||||||||||||
679 | } | ||||||||||||||||||||||
680 | |||||||||||||||||||||||
681 | sub fix_input_ender { | ||||||||||||||||||||||
682 | 6 | 6 | 0 | 9 | my $c = shift; | ||||||||||||||||||
683 | 6 | 13 | my $ender = shift; | ||||||||||||||||||||
684 | 6 | 9 | my $where = shift; | ||||||||||||||||||||
685 | |||||||||||||||||||||||
686 | 6 | 100 | 15 | if(ref $ender eq '') { | |||||||||||||||||||
687 | 1 | 3 | return qq{$ender}; | ||||||||||||||||||||
688 | } | ||||||||||||||||||||||
689 | |||||||||||||||||||||||
690 | 5 | 16 | my $key = (keys $ender->%*)[0]; | ||||||||||||||||||||
691 | 5 | 4 | my $tag = undef; | ||||||||||||||||||||
692 | 5 | 100 | 100 | 46 | if($key eq 'check_box' || $key eq 'radio_button') { | ||||||||||||||||||
100 | |||||||||||||||||||||||
50 | |||||||||||||||||||||||
693 | 2 | 100 | 4 | my $type = $key eq 'check_box' ? 'checkbox' : 'radio'; | |||||||||||||||||||
694 | 2 | 8 | my $extra_input = Mojolicious::Plugin::TagHelpers::_input($c, $ender->{ $key }->@*, type => $type); | ||||||||||||||||||||
695 | 2 | 186 | $tag = qq{ | ||||||||||||||||||||
696 | $extra_input | ||||||||||||||||||||||
697 | }; | ||||||||||||||||||||||
698 | } | ||||||||||||||||||||||
699 | elsif($key eq 'button') { | ||||||||||||||||||||||
700 | 1 | 6 | my $button = bootstrap_button($c, $ender->{ $key }->@*); | ||||||||||||||||||||
701 | 1 | 8 | $tag = qq{ | ||||||||||||||||||||
702 | $button | ||||||||||||||||||||||
703 | }; | ||||||||||||||||||||||
704 | } | ||||||||||||||||||||||
705 | elsif($key eq 'buttongroup') { | ||||||||||||||||||||||
706 | 2 | 50 | 7 | return '' if ref $ender->{ $key } ne 'ARRAY'; | |||||||||||||||||||
707 | my($button_group) = scalar $ender->{ $key }->@* == 1 ? make_dropdown_meat($c, $ender->{ $key }[0]->@*) | ||||||||||||||||||||||
708 | 2 | 100 | 12 | : make_buttongroup_meat($c, $ender->{ $key }->@*) | |||||||||||||||||||
709 | ; | ||||||||||||||||||||||
710 | 2 | 21 | $tag = qq{ | ||||||||||||||||||||
711 | $button_group |
||||||||||||||||||||||
712 | } | ||||||||||||||||||||||
713 | } | ||||||||||||||||||||||
714 | 0 | 0 | else { $tag = $key; } | ||||||||||||||||||||
715 | |||||||||||||||||||||||
716 | 5 | 24 | return $tag; | ||||||||||||||||||||
717 | } | ||||||||||||||||||||||
718 | |||||||||||||||||||||||
719 | sub iscoderef { | ||||||||||||||||||||||
720 | 39 | 39 | 0 | 89 | return ref shift eq 'CODE'; | ||||||||||||||||||
721 | } | ||||||||||||||||||||||
722 | sub url_for { | ||||||||||||||||||||||
723 | 86 | 86 | 0 | 73 | my $c = shift; | ||||||||||||||||||
724 | 86 | 62 | my $url = shift; | ||||||||||||||||||||
725 | 86 | 50 | 148 | return '' if ref $url ne 'ARRAY'; | |||||||||||||||||||
726 | 86 | 100 | 66 | 384 | return $url->[0] if scalar $url->@* == 1 && substr ($url->[0], 0, 1) eq '#'; | ||||||||||||||||||
727 | 43 | 392 | return $c->url_for($url->@*)->to_string; | ||||||||||||||||||||
728 | } | ||||||||||||||||||||||
729 | |||||||||||||||||||||||
730 | sub fix_input { | ||||||||||||||||||||||
731 | 17 | 17 | 0 | 16 | my $c = shift; | ||||||||||||||||||
732 | 17 | 19 | my $attr = shift; | ||||||||||||||||||||
733 | |||||||||||||||||||||||
734 | 17 | 19 | my $tagname; | ||||||||||||||||||||
735 | my $info; | ||||||||||||||||||||||
736 | |||||||||||||||||||||||
737 | 17 | 100 | 26 | if((grep { exists $attr->{"${_}_field"} } qw/date datetime month time week color email number range search tel text url password/)[0]) { | |||||||||||||||||||
238 | 50 | 280 | |||||||||||||||||||||
738 | 16 | 24 | $tagname = (grep { exists $attr->{"${_}_field"} } qw/date datetime month time week color email number range search tel text url password/)[0]; | ||||||||||||||||||||
224 | 218 | ||||||||||||||||||||||
739 | 16 | 25 | $info = $attr->{"${tagname}_field"}; | ||||||||||||||||||||
740 | } | ||||||||||||||||||||||
741 | elsif(exists $attr->{'text_area'}) { | ||||||||||||||||||||||
742 | 1 | 2 | $tagname = 'textarea'; | ||||||||||||||||||||
743 | 1 | 1 | $info = $attr->{'text_area'}; | ||||||||||||||||||||
744 | } | ||||||||||||||||||||||
745 | 17 | 49 | my $id = shift $info->@*; | ||||||||||||||||||||
746 | |||||||||||||||||||||||
747 | # if odd number of elements, the first one is the value (shortcut to avoid having to: value => 'value') | ||||||||||||||||||||||
748 | 17 | 100 | 37 | if($info->@* % 2) { | |||||||||||||||||||
749 | 2 | 4 | push $info->@* => (value => shift $info->@*); | ||||||||||||||||||||
750 | } | ||||||||||||||||||||||
751 | 17 | 25 | my $tag_attr = { $info->@* }; | ||||||||||||||||||||
752 | |||||||||||||||||||||||
753 | 17 | 48 | my @column_classes = get_column_classes($attr->{'column_information'}, 1); | ||||||||||||||||||||
754 | 17 | 54 | $tag_attr = add_classes($tag_attr, 'form-control', { size => 'input-%s' }); | ||||||||||||||||||||
755 | |||||||||||||||||||||||
756 | 17 | 50 | 33 | 100 | $tag_attr->{'id'} = $id if defined $id && !exists $tag_attr->{'id'}; | ||||||||||||||||||
757 | 17 | 50 | 50 | my $name_attr = defined $id ? $id =~ s{-}{_}rg : undef; | |||||||||||||||||||
758 | |||||||||||||||||||||||
759 | 17 | 29 | $tag_attr = cleanup_attrs($tag_attr); | ||||||||||||||||||||
760 | |||||||||||||||||||||||
761 | 17 | 100 | 31 | my $horizontal_before = scalar @column_classes ? qq{ ' : ''; |
|||||||||||||||||||
762 | 17 | 100 | 53 | my $horizontal_after = scalar @column_classes ? '' : ''; | |||||||||||||||||||
763 | 17 | 100 | 76 | my $input = exists $attr->{'text_area'} ? Mojolicious::Plugin::TagHelpers::_text_area($c, $name_attr, delete $tag_attr->{'value'}, $tag_attr->%*) | |||||||||||||||||||
764 | : Mojolicious::Plugin::TagHelpers::_input($c, $name_attr, $tag_attr->%*, type => $tagname) | ||||||||||||||||||||||
765 | ; | ||||||||||||||||||||||
766 | |||||||||||||||||||||||
767 | 17 | 6604 | return ($id => $horizontal_before . $input . $horizontal_after); | ||||||||||||||||||||
768 | |||||||||||||||||||||||
769 | } | ||||||||||||||||||||||
770 | |||||||||||||||||||||||
771 | sub fix_label { | ||||||||||||||||||||||
772 | 8 | 8 | 0 | 6 | my $c = shift; | ||||||||||||||||||
773 | 8 | 7 | my $for = shift; | ||||||||||||||||||||
774 | 8 | 5 | my $title = shift; | ||||||||||||||||||||
775 | 8 | 7 | my $attr = shift; | ||||||||||||||||||||
776 | |||||||||||||||||||||||
777 | 8 | 17 | my @column_classes = get_column_classes($attr->{'column_information'}, 0); | ||||||||||||||||||||
778 | 8 | 23 | my @args = (class => trim join ' ' => ('control-label', @column_classes)); | ||||||||||||||||||||
779 | 8 | 100 | 137 | ref $title eq 'CODE' ? push @args => $title : unshift @args => $title; | |||||||||||||||||||
780 | |||||||||||||||||||||||
781 | 8 | 18 | return Mojolicious::Plugin::TagHelpers::_label_for($c, $for, @args); | ||||||||||||||||||||
782 | } | ||||||||||||||||||||||
783 | |||||||||||||||||||||||
784 | sub parse_call { | ||||||||||||||||||||||
785 | 4 | 4 | 0 | 7 | my $c = shift; | ||||||||||||||||||
786 | 4 | 5 | my $title = shift; | ||||||||||||||||||||
787 | 4 | 100 | 12 | my $callback = ref $_[-1] eq 'CODE' ? pop : undef; | |||||||||||||||||||
788 | 4 | 50 | 11 | my $content = scalar @_ % 2 ? pop : ''; | |||||||||||||||||||
789 | 4 | 12 | my $attr = parse_attributes(@_); | ||||||||||||||||||||
790 | |||||||||||||||||||||||
791 | 4 | 14 | return ($c, $title, $callback, $content, $attr); | ||||||||||||||||||||
792 | } | ||||||||||||||||||||||
793 | |||||||||||||||||||||||
794 | sub parse_attributes { | ||||||||||||||||||||||
795 | 226 | 226 | 0 | 377 | my %attr = @_; | ||||||||||||||||||
796 | 226 | 100 | 66 | 495 | if($attr{'data'} && ref $attr{'data'} eq 'HASH') { | ||||||||||||||||||
797 | 9 | 9 | while(my($key, $value) = each %{ $attr{'data'} }) { | ||||||||||||||||||||
18 | 59 | ||||||||||||||||||||||
798 | 9 | 36 | $key =~ tr/_/-/; | ||||||||||||||||||||
799 | 9 | 23 | $attr{ lc("data-$key") } = $value; | ||||||||||||||||||||
800 | } | ||||||||||||||||||||||
801 | 9 | 14 | delete $attr{'data'}; | ||||||||||||||||||||
802 | } | ||||||||||||||||||||||
803 | 226 | 281 | return \%attr; | ||||||||||||||||||||
804 | } | ||||||||||||||||||||||
805 | |||||||||||||||||||||||
806 | sub get_column_classes { | ||||||||||||||||||||||
807 | 25 | 25 | 0 | 41 | my $attr = shift; | ||||||||||||||||||
808 | 25 | 22 | my $index = shift; | ||||||||||||||||||||
809 | |||||||||||||||||||||||
810 | 25 | 31 | my @classes = (); | ||||||||||||||||||||
811 | 25 | 54 | foreach my $key (keys $attr->%*) { | ||||||||||||||||||||
812 | 6 | 8 | my $correct_name = get_size_for($key); | ||||||||||||||||||||
813 | 6 | 50 | 17 | if(defined $correct_name) { | |||||||||||||||||||
814 | 6 | 20 | push @classes => sprintf "col-%s-%d" => $correct_name, $attr->{ $key }[ $index ]; | ||||||||||||||||||||
815 | } | ||||||||||||||||||||||
816 | } | ||||||||||||||||||||||
817 | 25 | 61 | return sort @classes; | ||||||||||||||||||||
818 | } | ||||||||||||||||||||||
819 | |||||||||||||||||||||||
820 | sub add_classes { | ||||||||||||||||||||||
821 | 248 | 248 | 0 | 214 | my $attr = shift; | ||||||||||||||||||
822 | 248 | 100 | 410 | my $formatter = ref $_[-1] eq 'HASH' ? pop : undef; | |||||||||||||||||||
823 | |||||||||||||||||||||||
824 | 14 | 14 | 67357 | no warnings 'uninitialized'; | |||||||||||||||||||
14 | 25 | ||||||||||||||||||||||
14 | 14109 | ||||||||||||||||||||||
825 | |||||||||||||||||||||||
826 | 248 | 391 | my @classes = ($attr->{'class'}, @_); | ||||||||||||||||||||
827 | |||||||||||||||||||||||
828 | 248 | 100 | 396 | if($formatter) { | |||||||||||||||||||
829 | 127 | 100 | 207 | if(exists $formatter->{'size'}) { | |||||||||||||||||||
830 | 95 | 237 | push @classes => sprintfify_class($attr, $formatter->{'size'}, $formatter->{'size_default'}, _sizes()); | ||||||||||||||||||||
831 | } | ||||||||||||||||||||||
832 | 127 | 100 | 393 | if(exists $formatter->{'button'}) { | |||||||||||||||||||
833 | 51 | 96 | push @classes => sprintfify_class($attr, $formatter->{'button'}, $formatter->{'button_default'}, _button_contexts()); | ||||||||||||||||||||
834 | } | ||||||||||||||||||||||
835 | 127 | 100 | 317 | if(exists $formatter->{'panel'}) { | |||||||||||||||||||
836 | 6 | 21 | push @classes => sprintfify_class($attr, $formatter->{'panel'}, $formatter->{'panel_default'}, _panel_contexts()); | ||||||||||||||||||||
837 | } | ||||||||||||||||||||||
838 | 127 | 100 | 245 | if(exists $formatter->{'table'}) { | |||||||||||||||||||
839 | 6 | 18 | push @classes => sprintfify_class($attr, $formatter->{'table'}, $formatter->{'table_default'}, _table_contexts()); | ||||||||||||||||||||
840 | } | ||||||||||||||||||||||
841 | 127 | 100 | 222 | if(exists $formatter->{'direction'}) { | |||||||||||||||||||
842 | 15 | 33 | push @classes => sprintfify_class($attr, $formatter->{'direction'}, $formatter->{'direction_default'}, _direction_contexts()); | ||||||||||||||||||||
843 | } | ||||||||||||||||||||||
844 | 127 | 100 | 234 | if(exists $formatter->{'navbar'}) { | |||||||||||||||||||
845 | 5 | 9 | push @classes => sprintfify_class($attr, $formatter->{'navbar'}, $formatter->{'navbar_default'}, _navbar_contexts()); | ||||||||||||||||||||
846 | } | ||||||||||||||||||||||
847 | } | ||||||||||||||||||||||
848 | |||||||||||||||||||||||
849 | 248 | 264 | my %uniqs = (); | ||||||||||||||||||||
850 | 248 | 1499 | $attr->{'class'} = trim join ' ' => uniq sort @classes; | ||||||||||||||||||||
851 | |||||||||||||||||||||||
852 | 248 | 4778 | return $attr; | ||||||||||||||||||||
853 | |||||||||||||||||||||||
854 | } | ||||||||||||||||||||||
855 | |||||||||||||||||||||||
856 | sub sprintfify_class { | ||||||||||||||||||||||
857 | 178 | 178 | 0 | 150 | my $attr = shift; | ||||||||||||||||||
858 | 178 | 178 | my $format = shift; | ||||||||||||||||||||
859 | 178 | 122 | my $possibilities = pop; | ||||||||||||||||||||
860 | 178 | 203 | my $default = shift; | ||||||||||||||||||||
861 | |||||||||||||||||||||||
862 | 178 | 416 | my @founds = (grep { exists $attr->{ $_ } } (keys $possibilities->%*)); | ||||||||||||||||||||
2186 | 1880 | ||||||||||||||||||||||
863 | |||||||||||||||||||||||
864 | 178 | 100 | 66 | 671 | return if !scalar @founds && !defined $default; | ||||||||||||||||||
865 | 85 | 100 | 157 | push @founds => $default if !scalar @founds; | |||||||||||||||||||
866 | |||||||||||||||||||||||
867 | 85 | 85 | return map { sprintf $format => $possibilities->{ $_ } } @founds; | ||||||||||||||||||||
91 | 357 | ||||||||||||||||||||||
868 | |||||||||||||||||||||||
869 | } | ||||||||||||||||||||||
870 | |||||||||||||||||||||||
871 | sub add_disabled { | ||||||||||||||||||||||
872 | 87 | 87 | 0 | 74 | my $attr = shift; | ||||||||||||||||||
873 | 87 | 69 | my $add_as_class = shift; # if false, add as attribute | ||||||||||||||||||||
874 | |||||||||||||||||||||||
875 | 87 | 100 | 66 | 196 | if(exists $attr->{'__disabled'} && $attr->{'__disabled'}) { | ||||||||||||||||||
876 | 3 | 100 | 10 | if($add_as_class) { | |||||||||||||||||||
877 | 2 | 6 | $attr = add_classes($attr, 'disabled'); | ||||||||||||||||||||
878 | } | ||||||||||||||||||||||
879 | else { | ||||||||||||||||||||||
880 | 1 | 3 | $attr->{'disabled'} = 'disabled'; | ||||||||||||||||||||
881 | } | ||||||||||||||||||||||
882 | } | ||||||||||||||||||||||
883 | 87 | 92 | return $attr; | ||||||||||||||||||||
884 | } | ||||||||||||||||||||||
885 | |||||||||||||||||||||||
886 | sub contents { | ||||||||||||||||||||||
887 | 4 | 4 | 0 | 6 | my $callback = shift; | ||||||||||||||||||
888 | 4 | 4 | my $content = shift; | ||||||||||||||||||||
889 | |||||||||||||||||||||||
890 | 4 | 100 | 13 | return defined $callback ? $callback->() : xml_escape($content); | |||||||||||||||||||
891 | } | ||||||||||||||||||||||
892 | |||||||||||||||||||||||
893 | sub content_single { | ||||||||||||||||||||||
894 | 51 | 51 | 0 | 46 | my $content = shift; | ||||||||||||||||||
895 | |||||||||||||||||||||||
896 | 51 | 100 | 148 | return ref $content eq 'CODE' ? $content->() : xml_escape($content); | |||||||||||||||||||
897 | } | ||||||||||||||||||||||
898 | |||||||||||||||||||||||
899 | sub cleanup_attrs { | ||||||||||||||||||||||
900 | 314 | 314 | 0 | 220 | my $hash = shift; | ||||||||||||||||||
901 | |||||||||||||||||||||||
902 | #* delete all shortcuts (-> __*) | ||||||||||||||||||||||
903 | 314 | 457 | map { delete $hash->{ $_ } } grep { substr($_, 0, 2) eq '__' } keys $hash->%*; | ||||||||||||||||||||
98 | 163 | ||||||||||||||||||||||
616 | 864 | ||||||||||||||||||||||
904 | |||||||||||||||||||||||
905 | #* delete all keys whose value is not a string | ||||||||||||||||||||||
906 | 314 | 50 | 366 | map { delete $hash->{ $_ } } grep { $_ ne 'data' && ref $hash->{ $_ } ne '' } keys $hash->%*; | |||||||||||||||||||
15 | 24 | ||||||||||||||||||||||
518 | 1496 | ||||||||||||||||||||||
907 | |||||||||||||||||||||||
908 | 314 | 345 | return $hash; | ||||||||||||||||||||
909 | } | ||||||||||||||||||||||
910 | |||||||||||||||||||||||
911 | sub get_size_for { | ||||||||||||||||||||||
912 | 6 | 6 | 0 | 5 | my $input = shift; | ||||||||||||||||||
913 | |||||||||||||||||||||||
914 | 6 | 8 | return _sizes()->{ $input }; | ||||||||||||||||||||
915 | } | ||||||||||||||||||||||
916 | |||||||||||||||||||||||
917 | sub _sizes { | ||||||||||||||||||||||
918 | return { | ||||||||||||||||||||||
919 | 101 | 101 | 654 | __xsmall => 'xs', xsmall => 'xs', xs => 'xs', | |||||||||||||||||||
920 | __small => 'sm', small => 'sm', sm => 'sm', | ||||||||||||||||||||||
921 | __medium => 'md', medium => 'md', md => 'md', | ||||||||||||||||||||||
922 | __large => 'lg', large => 'lg', lg => 'lg', | ||||||||||||||||||||||
923 | } | ||||||||||||||||||||||
924 | } | ||||||||||||||||||||||
925 | |||||||||||||||||||||||
926 | sub _button_contexts { | ||||||||||||||||||||||
927 | 51 | 51 | 59 | return { map { ("__$_" => $_, $_ => $_) } qw/default primary success info warning danger link/ }; | |||||||||||||||||||
357 | 717 | ||||||||||||||||||||||
928 | } | ||||||||||||||||||||||
929 | sub _panel_contexts { | ||||||||||||||||||||||
930 | 6 | 6 | 12 | return { map { ("__$_" => $_, $_ => $_) } qw/default primary success info warning danger/ }; | |||||||||||||||||||
36 | 107 | ||||||||||||||||||||||
931 | } | ||||||||||||||||||||||
932 | sub _table_contexts { | ||||||||||||||||||||||
933 | 6 | 6 | 7 | return { map { ("__$_" => $_, $_ => $_) } qw/striped bordered hover condensed responsive/ }; | |||||||||||||||||||
30 | 81 | ||||||||||||||||||||||
934 | } | ||||||||||||||||||||||
935 | sub _direction_contexts { | ||||||||||||||||||||||
936 | 15 | 15 | 18 | return { map { ("__$_" => $_, $_ => $_) } qw/right block vertical justified dropup left/ }; | |||||||||||||||||||
90 | 185 | ||||||||||||||||||||||
937 | } | ||||||||||||||||||||||
938 | sub _menu_contexts { | ||||||||||||||||||||||
939 | 0 | 0 | 0 | return { map { ("__$_" => undef, $_ => undef) } qw/caret hamburger/ }; | |||||||||||||||||||
0 | 0 | ||||||||||||||||||||||
940 | } | ||||||||||||||||||||||
941 | sub _misc_contexts { | ||||||||||||||||||||||
942 | 0 | 0 | 0 | return { map { ("__$_" => $_, $_ => $_) } qw/active disabled/ }; | |||||||||||||||||||
0 | 0 | ||||||||||||||||||||||
943 | } | ||||||||||||||||||||||
944 | sub _navbar_contexts { | ||||||||||||||||||||||
945 | 5 | 5 | 5 | return { map { ("__$_" => $_, $_ => $_) } qw/default inverse/ }; | |||||||||||||||||||
10 | 36 | ||||||||||||||||||||||
946 | } | ||||||||||||||||||||||
947 | |||||||||||||||||||||||
948 | sub out { | ||||||||||||||||||||||
949 | 177 | 177 | 0 | 454 | my $tag = shift; | ||||||||||||||||||
950 | 177 | 495 | return Mojo::ByteStream->new($tag); | ||||||||||||||||||||
951 | } | ||||||||||||||||||||||
952 | |||||||||||||||||||||||
953 | 1; | ||||||||||||||||||||||
954 | |||||||||||||||||||||||
955 | __END__ |