administrate_tailwind_theme 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.rubocop.yml +33 -0
- data/.ruby-version +1 -0
- data/.rubycritic.yml +5 -0
- data/CODE_OF_CONDUCT.md +84 -0
- data/LICENSE.txt +21 -0
- data/README.md +104 -0
- data/Rakefile +10 -0
- data/administrate_tailwind_theme.gemspec +33 -0
- data/app/assets/config/administrate_tailwind_theme_manifest.js +2 -0
- data/app/assets/images/administrate/tailwind/theme/.keep +0 -0
- data/app/assets/javascripts/administrate-tailwind-theme.js +1 -0
- data/app/assets/stylesheets/administrate-tailwind-theme.css +0 -0
- data/app/controllers/.keep +0 -0
- data/app/controllers/concerns/.keep +0 -0
- data/app/helpers/.keep +0 -0
- data/app/helpers/application_helper.rb +4 -0
- data/app/jobs/.keep +0 -0
- data/app/mailers/.keep +0 -0
- data/app/models/.keep +0 -0
- data/app/models/concerns/.keep +0 -0
- data/app/views/.keep +0 -0
- data/app/views/admin/application/_flashes.html.erb +29 -0
- data/app/views/admin/application/_icons.html.erb +13 -0
- data/app/views/admin/application/_javascript.html.erb +21 -0
- data/app/views/admin/application/_navigation.html.erb +39 -0
- data/app/views/admin/application/_stylesheet.html.erb +14 -0
- data/app/views/administrate/application/_collection.html.erb +78 -0
- data/app/views/administrate/application/_collection_header_actions.html.erb +5 -0
- data/app/views/administrate/application/_collection_item_actions.html.erb +22 -0
- data/app/views/administrate/application/_flashes.html.erb +35 -0
- data/app/views/administrate/application/_form.html.erb +58 -0
- data/app/views/administrate/application/_icons.html.erb +13 -0
- data/app/views/administrate/application/_index_header.html.erb +28 -0
- data/app/views/administrate/application/_javascript.html.erb +21 -0
- data/app/views/administrate/application/_navigation.html.erb +27 -0
- data/app/views/administrate/application/_pagination.html.erb +1 -0
- data/app/views/administrate/application/_search.html.erb +21 -0
- data/app/views/administrate/application/_stylesheet.html.erb +14 -0
- data/app/views/administrate/application/edit.html.erb +42 -0
- data/app/views/administrate/application/index.html.erb +49 -0
- data/app/views/administrate/application/new.html.erb +43 -0
- data/app/views/administrate/application/show.html.erb +71 -0
- data/app/views/administrate/navigation/icons/_comments.html.erb +4 -0
- data/app/views/administrate/navigation/icons/_messages.html.erb +4 -0
- data/app/views/administrate/navigation/icons/_users.erb +6 -0
- data/app/views/fields/belongs_to/_form.html.erb +29 -0
- data/app/views/fields/belongs_to/_index.html.erb +27 -0
- data/app/views/fields/belongs_to/_show.html.erb +28 -0
- data/app/views/fields/boolean/_form.html.erb +24 -0
- data/app/views/fields/boolean/_index.html.erb +19 -0
- data/app/views/fields/boolean/_show.html.erb +24 -0
- data/app/views/fields/boolean_emoji/_form.html.erb +7 -0
- data/app/views/fields/boolean_emoji/_index.html.erb +1 -0
- data/app/views/fields/boolean_emoji/_show.html.erb +3 -0
- data/app/views/fields/country_emoji/_form.html.erb +6 -0
- data/app/views/fields/country_emoji/_index.html.erb +1 -0
- data/app/views/fields/country_emoji/_show.html.erb +3 -0
- data/app/views/fields/date/_form.html.erb +23 -0
- data/app/views/fields/date/_index.html.erb +21 -0
- data/app/views/fields/date/_show.html.erb +23 -0
- data/app/views/fields/date_time/_form.html.erb +23 -0
- data/app/views/fields/date_time/_index.html.erb +21 -0
- data/app/views/fields/date_time/_show.html.erb +23 -0
- data/app/views/fields/email/_form.html.erb +23 -0
- data/app/views/fields/email/_index.html.erb +18 -0
- data/app/views/fields/email/_show.html.erb +20 -0
- data/app/views/fields/has_many/_form.html.erb +29 -0
- data/app/views/fields/has_many/_index.html.erb +19 -0
- data/app/views/fields/has_many/_show.html.erb +39 -0
- data/app/views/fields/has_one/_form.html.erb +39 -0
- data/app/views/fields/has_one/_index.html.erb +24 -0
- data/app/views/fields/has_one/_show.html.erb +48 -0
- data/app/views/fields/number/_form.html.erb +23 -0
- data/app/views/fields/number/_index.html.erb +19 -0
- data/app/views/fields/number/_show.html.erb +21 -0
- data/app/views/fields/password/_form.html.erb +23 -0
- data/app/views/fields/password/_index.html.erb +18 -0
- data/app/views/fields/password/_show.html.erb +20 -0
- data/app/views/fields/polymorphic/_form.html.erb +29 -0
- data/app/views/fields/polymorphic/_index.html.erb +27 -0
- data/app/views/fields/polymorphic/_show.html.erb +32 -0
- data/app/views/fields/select/_form.html.erb +31 -0
- data/app/views/fields/select/_index.html.erb +16 -0
- data/app/views/fields/select/_show.html.erb +18 -0
- data/app/views/fields/string/_form.html.erb +24 -0
- data/app/views/fields/string/_index.html.erb +18 -0
- data/app/views/fields/string/_show.html.erb +21 -0
- data/app/views/fields/text/_form.html.erb +22 -0
- data/app/views/fields/text/_index.html.erb +18 -0
- data/app/views/fields/text/_show.html.erb +20 -0
- data/app/views/fields/time/_form.html.erb +22 -0
- data/app/views/fields/time/_index.html.erb +19 -0
- data/app/views/fields/time/_show.html.erb +21 -0
- data/app/views/fields/url/_form.html.erb +23 -0
- data/app/views/fields/url/_index.html.erb +20 -0
- data/app/views/fields/url/_show.html.erb +22 -0
- data/app/views/kaminari/_first_page.html.erb +11 -0
- data/app/views/kaminari/_gap.html.erb +8 -0
- data/app/views/kaminari/_last_page.html.erb +11 -0
- data/app/views/kaminari/_next_page.html.erb +11 -0
- data/app/views/kaminari/_page.html.erb +12 -0
- data/app/views/kaminari/_paginator.html.erb +25 -0
- data/app/views/kaminari/_prev_page.html.erb +11 -0
- data/app/views/layouts/admin/application.html.erb +40 -0
- data/config/routes.rb +4 -0
- data/lib/administrate/field/boolean_emoji.rb +13 -0
- data/lib/administrate/field/country_emoji.rb +30 -0
- data/lib/administrate_tailwind_theme/engine.rb +15 -0
- data/lib/administrate_tailwind_theme/version.rb +5 -0
- data/lib/administrate_tailwind_theme/view_generator.rb +49 -0
- data/lib/administrate_tailwind_theme/view_helper.rb +22 -0
- data/lib/administrate_tailwind_theme.rb +9 -0
- data/lib/generators/administrate_tailwind_theme/install/USAGE +10 -0
- data/lib/generators/administrate_tailwind_theme/install/install_generator.rb +35 -0
- data/lib/generators/administrate_tailwind_theme/views/edit_generator.rb +18 -0
- data/lib/generators/administrate_tailwind_theme/views/field_generator.rb +52 -0
- data/lib/generators/administrate_tailwind_theme/views/form_generator.rb +17 -0
- data/lib/generators/administrate_tailwind_theme/views/index_generator.rb +18 -0
- data/lib/generators/administrate_tailwind_theme/views/layout_generator.rb +26 -0
- data/lib/generators/administrate_tailwind_theme/views/navigation_generator.rb +17 -0
- data/lib/generators/administrate_tailwind_theme/views/new_generator.rb +18 -0
- data/lib/generators/administrate_tailwind_theme/views/show_generator.rb +17 -0
- data/lib/generators/administrate_tailwind_theme/views/views_generator.rb +17 -0
- data/lib/tasks/administrate_tailwind/theme_tasks.rake +5 -0
- metadata +235 -0
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
<%#
|
|
2
|
+
# Form Partial
|
|
3
|
+
|
|
4
|
+
This partial is rendered on a resource's `new` and `edit` pages,
|
|
5
|
+
and renders all form fields for a resource's editable attributes.
|
|
6
|
+
|
|
7
|
+
## Local variables:
|
|
8
|
+
|
|
9
|
+
- `page`:
|
|
10
|
+
An instance of [Administrate::Page::Form][1].
|
|
11
|
+
Contains helper methods to display a form,
|
|
12
|
+
and knows which attributes should be displayed in the resource's form.
|
|
13
|
+
|
|
14
|
+
[1]: http://www.rubydoc.info/gems/administrate/Administrate/Page/Form
|
|
15
|
+
%>
|
|
16
|
+
|
|
17
|
+
<%= form_for([namespace, page.resource], html: { class: "max-w-lg mx-auto py-6 px-4 sm:px-6 lg:px-8" }) do |f| %>
|
|
18
|
+
<% if page.resource.errors.any? %>
|
|
19
|
+
<div id="error_explanation" class="bg-red-100 border-l-4 border-red-500 text-red-700 p-4 mb-6" role="alert">
|
|
20
|
+
<h2 class="font-bold">
|
|
21
|
+
<%= t(
|
|
22
|
+
"administrate.form.errors",
|
|
23
|
+
pluralized_errors: pluralize(page.resource.errors.count, t("administrate.form.error")),
|
|
24
|
+
resource_name: display_resource_name(page.resource_name, singular: true)
|
|
25
|
+
) %>
|
|
26
|
+
</h2>
|
|
27
|
+
|
|
28
|
+
<ul class="list-disc pl-6">
|
|
29
|
+
<% page.resource.errors.full_messages.each do |message| %>
|
|
30
|
+
<li><%= message %></li>
|
|
31
|
+
<% end %>
|
|
32
|
+
</ul>
|
|
33
|
+
</div>
|
|
34
|
+
<% end %>
|
|
35
|
+
|
|
36
|
+
<% page.attributes(controller.action_name).each do |title, attributes| -%>
|
|
37
|
+
<fieldset class="mb-6">
|
|
38
|
+
<% if title.present? %>
|
|
39
|
+
<legend class="text-lg font-medium text-gray-900"><%= t "helpers.label.#{f.object_name}.#{title}", default: title %></legend>
|
|
40
|
+
<% end %>
|
|
41
|
+
|
|
42
|
+
<% attributes.each do |attribute| %>
|
|
43
|
+
<div class="mb-4">
|
|
44
|
+
<%= render_field attribute, f: f %>
|
|
45
|
+
|
|
46
|
+
<% hint_key = "administrate.field_hints.#{page.resource_name}.#{attribute.name}" %>
|
|
47
|
+
<% if I18n.exists?(hint_key) -%>
|
|
48
|
+
<p class="text-sm text-gray-600 mt-2"><%= I18n.t(hint_key) %></p>
|
|
49
|
+
<% end -%>
|
|
50
|
+
</div>
|
|
51
|
+
<% end %>
|
|
52
|
+
</fieldset>
|
|
53
|
+
<% end -%>
|
|
54
|
+
|
|
55
|
+
<div class="flex justify-end">
|
|
56
|
+
<%= f.submit class: "text-white bg-gradient-to-r from-blue-500 via-blue-600 to-blue-700 hover:bg-gradient-to-br focus:ring-4 focus:outline-none focus:ring-blue-300 dark:focus:ring-blue-800 shadow-lg shadow-blue-500/50 dark:shadow-lg dark:shadow-blue-800/80 font-medium rounded-lg text-sm px-5 py-2.5 text-center me-2 mb-2 cursor-pointer" %>
|
|
57
|
+
</div>
|
|
58
|
+
<% end %>
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
<svg hidden xmlns="http://www.w3.org/2000/svg">
|
|
2
|
+
<symbol id="icon-cancel" viewBox="0 0 48 48">
|
|
3
|
+
<path fill-rule="evenodd" d="M24 19.757l-8.485-8.485c-.784-.783-2.047-.782-2.827 0l-1.417 1.416c-.777.777-.78 2.046.002 2.827L19.757 24l-8.485 8.485c-.783.784-.782 2.047 0 2.827l1.416 1.417c.777.777 2.046.78 2.827-.002L24 28.243l8.485 8.485c.784.783 2.047.782 2.827 0l1.417-1.416c.777-.777.78-2.046-.002-2.827L28.243 24l8.485-8.485c.783-.784.782-2.047 0-2.827l-1.416-1.417c-.777-.777-2.046-.78-2.827.002L24 19.757zM24 47c12.703 0 23-10.297 23-23S36.703 1 24 1 1 11.297 1 24s10.297 23 23 23z" />
|
|
4
|
+
</symbol>
|
|
5
|
+
|
|
6
|
+
<symbol id="icon-eyeglass" viewBox="0 0 48 48">
|
|
7
|
+
<path d="M27.885 32.515c-2.864 1.966-6.333 3.116-10.07 3.116C7.976 35.63 0 27.656 0 17.817 0 7.976 7.976 0 17.816 0S35.63 7.976 35.63 17.816c0 3.736-1.15 7.205-3.115 10.07l14.53 14.53c1.278 1.277 1.275 3.352 0 4.628-1.28 1.278-3.353 1.278-4.63 0l-14.53-14.53zm-10.07-3.736c6.056 0 10.964-4.91 10.964-10.964 0-6.055-4.91-10.964-10.964-10.964-6.055 0-10.964 4.91-10.964 10.964 0 6.055 4.91 10.963 10.964 10.963z" />
|
|
8
|
+
</symbol>
|
|
9
|
+
|
|
10
|
+
<symbol id="icon-up-caret" viewBox="0 0 48 48">
|
|
11
|
+
<path d="M2.988 33.02c-1.66 0-1.943-.81-.618-1.824l20-15.28c.878-.672 2.31-.67 3.188 0l20.075 15.288c1.316 1.003 1.048 1.816-.62 1.816H2.987z" />
|
|
12
|
+
</symbol>
|
|
13
|
+
</svg>
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
<% content_for(:title) { display_resource_name(page.resource_name) } %>
|
|
2
|
+
<header class="bg-white shadow">
|
|
3
|
+
<div class="mx-auto py-6 px-4 sm:px-6 lg:px-8">
|
|
4
|
+
<h1 class="text-3xl font-bold leading-tight text-gray-700 mb-2" id="page-title">
|
|
5
|
+
<% if icon?(page.resource_name.pluralize) %>
|
|
6
|
+
<%= render partial: "administrate/navigation/icons/#{page.resource_name.pluralize}" %>
|
|
7
|
+
<% end %>
|
|
8
|
+
<%= content_for(:title) %>
|
|
9
|
+
</h1>
|
|
10
|
+
<% if show_search_bar %>
|
|
11
|
+
<%= render(
|
|
12
|
+
"search",
|
|
13
|
+
search_term: search_term,
|
|
14
|
+
resource_name: display_resource_name(page.resource_name)
|
|
15
|
+
) %>
|
|
16
|
+
<% end %>
|
|
17
|
+
<div class="mt-4">
|
|
18
|
+
<%= link_to(
|
|
19
|
+
t(
|
|
20
|
+
"administrate.actions.new_resource",
|
|
21
|
+
name: display_resource_name(page.resource_name, singular: true).downcase
|
|
22
|
+
),
|
|
23
|
+
[:new, namespace, page.resource_path.to_sym],
|
|
24
|
+
class: "inline-flex items-center px-4 py-2 border border-transparent text-sm font-medium rounded-md shadow-sm text-white bg-blue-600 hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500"
|
|
25
|
+
) if accessible_action?(new_resource, :new) %>
|
|
26
|
+
</div>
|
|
27
|
+
</div>
|
|
28
|
+
</header>
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
<%#
|
|
2
|
+
# Javascript Partial
|
|
3
|
+
|
|
4
|
+
This partial imports the necessary javascript on each page.
|
|
5
|
+
By default, it includes the application JS,
|
|
6
|
+
but each page can define additional JS sources
|
|
7
|
+
by providing a `content_for(:javascript)` block.
|
|
8
|
+
%>
|
|
9
|
+
|
|
10
|
+
<% Administrate::Engine.javascripts.each do |js_path| %>
|
|
11
|
+
<%= javascript_include_tag js_path %>
|
|
12
|
+
<% end %>
|
|
13
|
+
|
|
14
|
+
<%= yield :javascript %>
|
|
15
|
+
|
|
16
|
+
<% if Rails.env.test? %>
|
|
17
|
+
<%= javascript_tag do %>
|
|
18
|
+
$.fx.off = true;
|
|
19
|
+
$.ajaxSetup({ async: false });
|
|
20
|
+
<% end %>
|
|
21
|
+
<% end %>
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
<%#
|
|
2
|
+
# Navigation
|
|
3
|
+
|
|
4
|
+
This partial is used to display the navigation in Administrate.
|
|
5
|
+
By default, the navigation contains navigation links
|
|
6
|
+
for all resources in the admin dashboard,
|
|
7
|
+
as defined by the routes in the `admin/` namespace
|
|
8
|
+
%>
|
|
9
|
+
|
|
10
|
+
<nav class="bg-white shadow">
|
|
11
|
+
<div class="container mx-auto px-4 sm:px-6 lg:px-8">
|
|
12
|
+
<div class="flex items-center justify-between h-16">
|
|
13
|
+
<%= link_to(t("administrate.navigation.back_to_app"), root_url, class: "text-gray-700 hover:text-gray-900 px-3 py-2 rounded-md text-sm font-medium") if defined?(root_url) %>
|
|
14
|
+
|
|
15
|
+
<div class="hidden md:block">
|
|
16
|
+
<% Administrate::Namespace.new(namespace).resources_with_index_route.each do |resource| %>
|
|
17
|
+
<%= link_to(
|
|
18
|
+
display_resource_name(resource),
|
|
19
|
+
resource_index_route(resource),
|
|
20
|
+
class: "text-gray-700 px-3 py-2 rounded-md text-sm font-medium hover:text-gray-900 #{'bg-gray-100' if nav_link_state(resource) == 'active'}"
|
|
21
|
+
) if accessible_action?(model_from_resource(resource), :index) %>
|
|
22
|
+
<% end %>
|
|
23
|
+
</div>
|
|
24
|
+
</div>
|
|
25
|
+
</div>
|
|
26
|
+
</nav>
|
|
27
|
+
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
<%= paginate resources, param_name: local_assigns.fetch(:param_name, "_page") %>
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
<form class="relative" role="search">
|
|
2
|
+
<label for="search" class="sr-only">
|
|
3
|
+
<%= t("administrate.search.label", resource: resource_name) %>
|
|
4
|
+
</label>
|
|
5
|
+
|
|
6
|
+
<div class="flex items-center border border-gray-300 rounded-md shadow-sm">
|
|
7
|
+
<div class="pl-3">
|
|
8
|
+
<svg class="h-5 w-5 text-gray-400" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke="currentColor" aria-hidden="true">
|
|
9
|
+
<path d="M16.9994165,16.2923098 L20.8535534,20.1464466 C21.0488155,20.3417088 21.0488155,20.6582912 20.8535534,20.8535534 C20.6582912,21.0488155 20.3417088,21.0488155 20.1464466,20.8535534 L16.2923098,16.9994165 C14.8819612,18.2444908 13.0292099,19 11,19 C6.581722,19 3,15.418278 3,11 C3,6.581722 6.581722,3 11,3 C15.418278,3 19,6.581722 19,11 C19,13.0292099 18.2444908,14.8819612 16.9994165,16.2923098 Z M11,18 C14.8659932,18 18,14.8659932 18,11 C18,7.13400675 14.8659932,4 11,4 C7.13400675,4 4,7.13400675 4,11 C4,14.8659932 7.13400675,18 11,18 Z"/>
|
|
10
|
+
</svg>
|
|
11
|
+
</div>
|
|
12
|
+
<input id="search" class="block w-full pl-5 pr-3 py-2 border-transparent text-gray-900 placeholder-gray-500 focus:outline-none focus:ring-blue-500 focus:border-blue-500 sm:text-sm" placeholder="<%= t("administrate.search.label", resource: resource_name) %>" type="search" name="search" value="<%= search_term %>">
|
|
13
|
+
<% if search_term.present? %>
|
|
14
|
+
<%= link_to clear_search_params, class: "absolute inset-y-0 right-0 pr-3 flex items-center" do %>
|
|
15
|
+
<svg class="h-5 w-5 text-gray-400" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke="currentColor" aria-hidden="true">
|
|
16
|
+
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M6 18L18 6M6 6l12 12"/>
|
|
17
|
+
</svg>
|
|
18
|
+
<% end %>
|
|
19
|
+
<% end %>
|
|
20
|
+
</div>
|
|
21
|
+
</form>
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
<%#
|
|
2
|
+
# Stylesheet Partial
|
|
3
|
+
|
|
4
|
+
This partial imports the necessary stylesheets on each page.
|
|
5
|
+
By default, it includes the application CSS,
|
|
6
|
+
but each page can define additional CSS sources
|
|
7
|
+
by providing a `content_for(:stylesheet)` block.
|
|
8
|
+
%>
|
|
9
|
+
|
|
10
|
+
<% Administrate::Engine.stylesheets.each do |css_path| %>
|
|
11
|
+
<%= stylesheet_link_tag css_path %>
|
|
12
|
+
<% end %>
|
|
13
|
+
|
|
14
|
+
<%= yield :stylesheet %>
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
<%#
|
|
2
|
+
# Edit
|
|
3
|
+
|
|
4
|
+
This view is the template for the edit page.
|
|
5
|
+
|
|
6
|
+
It displays a header, and renders the `_form` partial to do the heavy lifting.
|
|
7
|
+
|
|
8
|
+
## Local variables:
|
|
9
|
+
|
|
10
|
+
- `page`:
|
|
11
|
+
An instance of [Administrate::Page::Form][1].
|
|
12
|
+
Contains helper methods to help display a form,
|
|
13
|
+
and knows which attributes should be displayed in the resource's form.
|
|
14
|
+
|
|
15
|
+
[1]: http://www.rubydoc.info/gems/administrate/Administrate/Page/Form
|
|
16
|
+
%>
|
|
17
|
+
|
|
18
|
+
<% content_for(:title) { t("administrate.actions.edit_resource", name: page.page_title) } %>
|
|
19
|
+
|
|
20
|
+
<header class="bg-white shadow">
|
|
21
|
+
<div class="mx-auto py-6 px-4 sm:px-6 lg:px-8">
|
|
22
|
+
<div class="flex justify-between items-center">
|
|
23
|
+
<h1 class="text-3xl font-bold leading-tight text-gray-900">
|
|
24
|
+
<%= content_for(:title) %>
|
|
25
|
+
</h1>
|
|
26
|
+
|
|
27
|
+
<div>
|
|
28
|
+
<%= link_to(
|
|
29
|
+
t("administrate.actions.show_resource", name: page.page_title),
|
|
30
|
+
[namespace, page.resource],
|
|
31
|
+
class: "text-white bg-gradient-to-r from-blue-500 via-blue-600 to-blue-700 hover:bg-gradient-to-br focus:ring-4 focus:outline-none focus:ring-blue-300 dark:focus:ring-blue-800 shadow-lg shadow-blue-500/50 dark:shadow-lg dark:shadow-blue-800/80 font-medium rounded-lg text-sm px-5 py-2.5 text-center me-2 mb-2"
|
|
32
|
+
) if accessible_action?(page.resource, :show) %>
|
|
33
|
+
</div>
|
|
34
|
+
</div>
|
|
35
|
+
</div>
|
|
36
|
+
</header>
|
|
37
|
+
|
|
38
|
+
<section class="mx-auto py-6 px-4 sm:px-6 lg:px-8">
|
|
39
|
+
<div class="bg-white shadow overflow-hidden rounded-lg">
|
|
40
|
+
<%= render "form", page: page %>
|
|
41
|
+
</div>
|
|
42
|
+
</section>
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
<%#
|
|
2
|
+
# Index
|
|
3
|
+
|
|
4
|
+
This view is the template for the index page.
|
|
5
|
+
It is responsible for rendering the search bar, header and pagination.
|
|
6
|
+
It renders the `_table` partial to display details about the resources.
|
|
7
|
+
|
|
8
|
+
## Local variables:
|
|
9
|
+
|
|
10
|
+
- `page`:
|
|
11
|
+
An instance of [Administrate::Page::Collection][1].
|
|
12
|
+
Contains helper methods to help display a table,
|
|
13
|
+
and knows which attributes should be displayed in the resource's table.
|
|
14
|
+
- `resources`:
|
|
15
|
+
An instance of `ActiveRecord::Relation` containing the resources
|
|
16
|
+
that match the user's search criteria.
|
|
17
|
+
By default, these resources are passed to the table partial to be displayed.
|
|
18
|
+
- `search_term`:
|
|
19
|
+
A string containing the term the user has searched for, if any.
|
|
20
|
+
- `show_search_bar`:
|
|
21
|
+
A boolean that determines if the search bar should be shown.
|
|
22
|
+
|
|
23
|
+
[1]: http://www.rubydoc.info/gems/administrate/Administrate/Page/Collection
|
|
24
|
+
%>
|
|
25
|
+
|
|
26
|
+
<%=
|
|
27
|
+
render("index_header",
|
|
28
|
+
resources: resources,
|
|
29
|
+
search_term: search_term,
|
|
30
|
+
page: page,
|
|
31
|
+
show_search_bar: show_search_bar,
|
|
32
|
+
)
|
|
33
|
+
%>
|
|
34
|
+
|
|
35
|
+
<section class="m-5 bg-white shadow overflow-hidden rounded-lg">
|
|
36
|
+
<%= render(
|
|
37
|
+
"collection",
|
|
38
|
+
collection_presenter: page,
|
|
39
|
+
collection_field_name: resource_name,
|
|
40
|
+
page: page,
|
|
41
|
+
resources: resources,
|
|
42
|
+
table_title: "page-title"
|
|
43
|
+
) %>
|
|
44
|
+
|
|
45
|
+
<div class="bg-white px-4 py-3 border-t border-gray-200 sm:px-6">
|
|
46
|
+
<%= render("pagination", resources: resources) %>
|
|
47
|
+
</div>
|
|
48
|
+
</section>
|
|
49
|
+
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
<%#
|
|
2
|
+
# New
|
|
3
|
+
|
|
4
|
+
This view is the template for the "new resource" page.
|
|
5
|
+
It displays a header, and then renders the `_form` partial
|
|
6
|
+
to do the heavy lifting.
|
|
7
|
+
|
|
8
|
+
## Local variables:
|
|
9
|
+
|
|
10
|
+
- `page`:
|
|
11
|
+
An instance of [Administrate::Page::Form][1].
|
|
12
|
+
Contains helper methods to help display a form,
|
|
13
|
+
and knows which attributes should be displayed in the resource's form.
|
|
14
|
+
|
|
15
|
+
[1]: http://www.rubydoc.info/gems/administrate/Administrate/Page/Form
|
|
16
|
+
%>
|
|
17
|
+
|
|
18
|
+
<% content_for(:title) do %>
|
|
19
|
+
<%= t(
|
|
20
|
+
"administrate.actions.new_resource",
|
|
21
|
+
name: display_resource_name(page.resource_name).titleize
|
|
22
|
+
) %>
|
|
23
|
+
<% end %>
|
|
24
|
+
|
|
25
|
+
<header class="bg-white shadow">
|
|
26
|
+
<div class="mx-auto py-6 px-4 sm:px-6 lg:px-8">
|
|
27
|
+
<div class="flex justify-between items-center">
|
|
28
|
+
<h1 class="text-3xl font-bold leading-tight text-gray-900">
|
|
29
|
+
<%= content_for(:title) %>
|
|
30
|
+
</h1>
|
|
31
|
+
<div>
|
|
32
|
+
<%= link_to t("administrate.actions.back"), :back, class: "inline-flex items-center px-4 py-2 border border-transparent text-sm font-medium rounded-md shadow-sm text-white bg-blue-600 hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500" %>
|
|
33
|
+
</div>
|
|
34
|
+
</div>
|
|
35
|
+
</div>
|
|
36
|
+
</header>
|
|
37
|
+
|
|
38
|
+
<section class="mx-auto py-6 px-4 sm:px-6 lg:px-8">
|
|
39
|
+
<div class="bg-white shadow overflow-hidden rounded-lg">
|
|
40
|
+
<%= render "form", page: page %>
|
|
41
|
+
</div>
|
|
42
|
+
</section>
|
|
43
|
+
|
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
<%#
|
|
2
|
+
# Show
|
|
3
|
+
|
|
4
|
+
This view is the template for the show page.
|
|
5
|
+
It renders the attributes of a resource,
|
|
6
|
+
as well as a link to its edit page.
|
|
7
|
+
|
|
8
|
+
## Local variables:
|
|
9
|
+
|
|
10
|
+
- `page`:
|
|
11
|
+
An instance of [Administrate::Page::Show][1].
|
|
12
|
+
Contains methods for accessing the resource to be displayed on the page,
|
|
13
|
+
as well as helpers for describing how each attribute of the resource
|
|
14
|
+
should be displayed.
|
|
15
|
+
|
|
16
|
+
[1]: http://www.rubydoc.info/gems/administrate/Administrate/Page/Show
|
|
17
|
+
%>
|
|
18
|
+
|
|
19
|
+
<% content_for(:title) { t("administrate.actions.show_resource", name: page.page_title) } %>
|
|
20
|
+
|
|
21
|
+
<header class="bg-white shadow">
|
|
22
|
+
<div class="mx-auto py-6 px-4 sm:px-6 lg:px-8">
|
|
23
|
+
<div class="flex justify-between items-center">
|
|
24
|
+
<h1 class="text-3xl font-bold leading-tight text-gray-900">
|
|
25
|
+
<%= content_for(:title) %>
|
|
26
|
+
</h1>
|
|
27
|
+
|
|
28
|
+
<div class="flex space-x-2">
|
|
29
|
+
<%= link_to(
|
|
30
|
+
t("administrate.actions.edit_resource", name: page.page_title),
|
|
31
|
+
[:edit, namespace, page.resource],
|
|
32
|
+
class: "text-white bg-gradient-to-r from-blue-500 via-blue-600 to-blue-700 hover:bg-gradient-to-br focus:ring-4 focus:outline-none focus:ring-blue-300 dark:focus:ring-blue-800 shadow-lg shadow-blue-500/50 dark:shadow-lg dark:shadow-blue-800/80 font-medium rounded-lg text-sm px-5 py-2.5 text-center me-2 mb-2"
|
|
33
|
+
) if accessible_action?(page.resource, :edit) %>
|
|
34
|
+
|
|
35
|
+
<%= link_to(
|
|
36
|
+
t("administrate.actions.destroy"),
|
|
37
|
+
[namespace, page.resource],
|
|
38
|
+
method: :delete,
|
|
39
|
+
data: { confirm: t("administrate.actions.confirm") },
|
|
40
|
+
class: "text-white bg-gradient-to-r from-red-400 via-red-500 to-red-600 hover:bg-gradient-to-br focus:ring-4 focus:outline-none focus:ring-red-300 dark:focus:ring-red-800 shadow-lg shadow-red-500/50 dark:shadow-lg dark:shadow-red-800/80 font-medium rounded-lg text-sm px-5 py-2.5 text-center me-2 mb-2"
|
|
41
|
+
) if accessible_action?(page.resource, :destroy) %>
|
|
42
|
+
</div>
|
|
43
|
+
</div>
|
|
44
|
+
</div>
|
|
45
|
+
</header>
|
|
46
|
+
|
|
47
|
+
<section class="mx-auto py-6 px-4 sm:px-6 lg:px-8">
|
|
48
|
+
<div class="bg-white shadow overflow-hidden rounded-lg p-6">
|
|
49
|
+
<dl>
|
|
50
|
+
<% page.attributes.each do |title, attributes| %>
|
|
51
|
+
<fieldset class="<%= 'p-4 border-t border-gray-200' if title.present? %>">
|
|
52
|
+
<% if title.present? %>
|
|
53
|
+
<legend class="text-lg font-medium text-gray-900"><%= t "helpers.label.#{page.resource_name}.#{title}", default: title %></legend>
|
|
54
|
+
<% end %>
|
|
55
|
+
|
|
56
|
+
<% attributes.each do |attribute| %>
|
|
57
|
+
<div class="grid grid-cols-1 md:grid-cols-3 gap-4">
|
|
58
|
+
<dt class="text-sm font-medium text-gray-500" id="<%= attribute.name %>">
|
|
59
|
+
<%= t(
|
|
60
|
+
"helpers.label.#{resource_name}.#{attribute.name}",
|
|
61
|
+
default: page.resource.class.human_attribute_name(attribute.name),
|
|
62
|
+
) %>
|
|
63
|
+
</dt>
|
|
64
|
+
<dd class="mt-1 text-sm text-gray-900 md:col-span-2"><%= render_field attribute, page: page %></dd>
|
|
65
|
+
</div>
|
|
66
|
+
<% end %>
|
|
67
|
+
</fieldset>
|
|
68
|
+
<% end %>
|
|
69
|
+
</dl>
|
|
70
|
+
</div>
|
|
71
|
+
</section>
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
<svg class="w-5 h-5 text-gray-500 transition duration-75 dark:text-gray-400 group-hover:text-gray-900 dark:group-hover:text-white" aria-hidden="true" xmlns="http://www.w3.org/2000/svg" fill="currentColor" viewBox="0 0 22 21">
|
|
2
|
+
<path d="M16 11.1c0-1.5-1.5-2.8-3.2-3.3-1.3 1.5-3.9 2.4-6.4 2.4-0.1 0-0.3 0-0.4 0 0 0 0 0-0.1 0-0.1 0.3-0.1 0.5-0.1 0.8 0 2 2.2 3.6 5 3.6 0.2 0 0.4 0 0.6 0 0.4 0.5 1.7 1.4 3.4 1.4 0 0-0.8-0.4-0.8-1.8 0 0 0 0 0 0 0-0.6 2-1.8 2-3.1z"></path>
|
|
3
|
+
<path d="M13 4.6c0-2.5-2.8-4.6-6.4-4.6s-6.6 2.1-6.6 4.6c0 1.7 2 3.2 3 4 0 0 0 0 0 0 0 1.8-1.4 2.4-1.4 2.4 2.3 0 3.6-1.1 4.2-1.8 0.2 0 0.5 0 0.8 0 3.5 0.1 6.4-2 6.4-4.6z"></path>
|
|
4
|
+
</svg>
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
<svg class="w-5 h-5 text-gray-500 transition duration-75 dark:text-gray-400 group-hover:text-gray-900 dark:group-hover:text-white" aria-hidden="true" xmlns="http://www.w3.org/2000/svg" fill="currentColor" viewBox="0 0 22 21">
|
|
2
|
+
<path class="cls-1" d="M18.68,8.16V15.8a2.86,2.86,0,0,1-2.86,2.86H13.91v2.86L8.18,18.66H4.36A2.86,2.86,0,0,1,1.5,15.8V8.16A2.86,2.86,0,0,1,4.36,5.3H15.82A2.86,2.86,0,0,1,18.68,8.16Z"/>
|
|
3
|
+
<path class="cls-1" d="M18.68,14.84h1A2.86,2.86,0,0,0,22.5,12V4.34a2.86,2.86,0,0,0-2.86-2.86H8.18A2.86,2.86,0,0,0,5.32,4.34v1"/>
|
|
4
|
+
</svg>
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
<svg class="w-5 h-5 text-gray-500 transition duration-75 dark:text-gray-400 group-hover:text-gray-900 dark:group-hover:text-white" aria-hidden="true" xmlns="http://www.w3.org/2000/svg" fill="currentColor" viewBox="0 0 22 21">
|
|
2
|
+
<path d="M5.5 0C3.56717 0 2 1.56567 2 3.49804C2 5.43041 3.56717 6.99609 5.5 6.99609C7.43283 6.99609 9 5.43041 9 3.49804C9 1.56567 7.43283 0 5.5 0Z"/>
|
|
3
|
+
<path d="M3.5 8.99414C1.56711 8.99414 0 10.5605 0 12.4936V14.9909H11V12.4936C11 10.5605 9.43289 8.99414 7.5 8.99414H3.5Z"/>
|
|
4
|
+
<path d="M12.5 10H12V15H15V12.5C15 11.1193 13.8807 10 12.5 10Z"/>
|
|
5
|
+
<path d="M11.5 4C10.1193 4 9 5.11929 9 6.5C9 7.88071 10.1193 9 11.5 9C12.8807 9 14 7.88071 14 6.5C14 5.11929 12.8807 4 11.5 4Z"/>
|
|
6
|
+
</svg>
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
<%#
|
|
2
|
+
# BelongsTo Form Partial
|
|
3
|
+
|
|
4
|
+
This partial renders an input element for belongs_to relationships.
|
|
5
|
+
By default, the input is a collection select box
|
|
6
|
+
that displays all possible records to associate with.
|
|
7
|
+
|
|
8
|
+
## Local variables:
|
|
9
|
+
|
|
10
|
+
- `f`:
|
|
11
|
+
A Rails form generator, used to help create the appropriate input fields.
|
|
12
|
+
- `field`:
|
|
13
|
+
An instance of [Administrate::Field::BelongsTo][1].
|
|
14
|
+
Contains helper methods for displaying a collection select box.
|
|
15
|
+
|
|
16
|
+
[1]: http://www.rubydoc.info/gems/administrate/Administrate/Field/BelongsTo
|
|
17
|
+
%>
|
|
18
|
+
|
|
19
|
+
<div class="mb-4">
|
|
20
|
+
<%= f.label field.permitted_attribute, class: "block text-sm font-medium text-gray-700" %>
|
|
21
|
+
<div class="mt-1">
|
|
22
|
+
<%= f.select(
|
|
23
|
+
field.permitted_attribute,
|
|
24
|
+
options_for_select(field.associated_resource_options, field.selected_option),
|
|
25
|
+
{ include_blank: field.include_blank_option },
|
|
26
|
+
{ class: "form-select block w-full py-2 px-3 border border-gray-300 rounded-md shadow-sm focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm" }
|
|
27
|
+
) %>
|
|
28
|
+
</div>
|
|
29
|
+
</div>
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
<%#
|
|
2
|
+
# BelongsTo Index Partial
|
|
3
|
+
|
|
4
|
+
This partial renders a belongs_to relationship,
|
|
5
|
+
to be displayed on a resource's index page.
|
|
6
|
+
|
|
7
|
+
By default, the relationship is rendered as a link to the associated object.
|
|
8
|
+
|
|
9
|
+
## Local variables:
|
|
10
|
+
|
|
11
|
+
- `field`:
|
|
12
|
+
An instance of [Administrate::Field::BelongsTo][1].
|
|
13
|
+
A wrapper around the belongs_to relationship pulled from the database.
|
|
14
|
+
|
|
15
|
+
[1]: http://www.rubydoc.info/gems/administrate/Administrate/Field/BelongsTo
|
|
16
|
+
%>
|
|
17
|
+
|
|
18
|
+
<% if field.data %>
|
|
19
|
+
<% if accessible_action?(field.data, :show) %>
|
|
20
|
+
<%= link_to(
|
|
21
|
+
field.display_associated_resource,
|
|
22
|
+
[namespace, field.data],
|
|
23
|
+
) %>
|
|
24
|
+
<% else %>
|
|
25
|
+
<%= field.display_associated_resource %>
|
|
26
|
+
<% end %>
|
|
27
|
+
<% end %>
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
<%#
|
|
2
|
+
# BelongsTo Show Partial
|
|
3
|
+
|
|
4
|
+
This partial renders a belongs_to relationship,
|
|
5
|
+
to be displayed on a resource's show page.
|
|
6
|
+
|
|
7
|
+
By default, the relationship is rendered as a link to the associated object.
|
|
8
|
+
|
|
9
|
+
## Local variables:
|
|
10
|
+
|
|
11
|
+
- `field`:
|
|
12
|
+
An instance of [Administrate::Field::BelongsTo][1].
|
|
13
|
+
A wrapper around the belongs_to relationship pulled from the database.
|
|
14
|
+
|
|
15
|
+
[1]: http://www.rubydoc.info/gems/administrate/Administrate/Field/BelongsTo
|
|
16
|
+
%>
|
|
17
|
+
|
|
18
|
+
<% if field.data %>
|
|
19
|
+
<% if accessible_action?(field.data, :show) %>
|
|
20
|
+
<div class="bg-gray-50 p-3 rounded-md shadow-sm">
|
|
21
|
+
<%= link_to(field.display_associated_resource, [namespace, field.data]) %>
|
|
22
|
+
</div>
|
|
23
|
+
<% else %>
|
|
24
|
+
<div class="bg-gray-50 p-3 rounded-md shadow-sm">
|
|
25
|
+
<%= field.display_associated_resource %>
|
|
26
|
+
</div>
|
|
27
|
+
<% end %>
|
|
28
|
+
<% end %>
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
<%#
|
|
2
|
+
# Boolean Form Partial
|
|
3
|
+
|
|
4
|
+
This partial renders an input element for a boolean attribute.
|
|
5
|
+
By default, the input is a checkbox.
|
|
6
|
+
|
|
7
|
+
## Local variables:
|
|
8
|
+
|
|
9
|
+
- `f`:
|
|
10
|
+
A Rails form generator, used to help create the appropriate input fields.
|
|
11
|
+
- `field`:
|
|
12
|
+
An instance of [Administrate::Field::Boolean][1].
|
|
13
|
+
A wrapper around the boolean value pulled from the database.
|
|
14
|
+
|
|
15
|
+
[1]: http://www.rubydoc.info/gems/administrate/Administrate/Field/Boolean
|
|
16
|
+
%>
|
|
17
|
+
|
|
18
|
+
<div class="mb-4 flex items-center">
|
|
19
|
+
<%= f.label field.attribute, class: "block text-sm font-medium text-gray-700 mr-2" %>
|
|
20
|
+
<div class="mt-1">
|
|
21
|
+
<%= f.check_box field.attribute, class: "h-4 w-4 text-indigo-600 focus:ring-indigo-500 border-gray-300 rounded" %>
|
|
22
|
+
</div>
|
|
23
|
+
</div>
|
|
24
|
+
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
<%#
|
|
2
|
+
# Boolean Index Partial
|
|
3
|
+
|
|
4
|
+
This partial renders a boolean attribute,
|
|
5
|
+
to be displayed on a resource's index page.
|
|
6
|
+
|
|
7
|
+
By default, the attribute is rendered
|
|
8
|
+
as a string representation of the boolean value.
|
|
9
|
+
|
|
10
|
+
## Local variables:
|
|
11
|
+
|
|
12
|
+
- `field`:
|
|
13
|
+
An instance of [Administrate::Field::Boolean][1].
|
|
14
|
+
A wrapper around the boolean value pulled from the database.
|
|
15
|
+
|
|
16
|
+
[1]: http://www.rubydoc.info/gems/administrate/Administrate/Field/Boolean
|
|
17
|
+
%>
|
|
18
|
+
|
|
19
|
+
<%= field.to_s %>
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
<%#
|
|
2
|
+
# Boolean Show Partial
|
|
3
|
+
|
|
4
|
+
This partial renders a boolean attribute,
|
|
5
|
+
to be displayed on a resource's show page.
|
|
6
|
+
|
|
7
|
+
By default, the attribute is rendered
|
|
8
|
+
as a string representation of the boolean value.
|
|
9
|
+
|
|
10
|
+
## Local variables:
|
|
11
|
+
|
|
12
|
+
- `field`:
|
|
13
|
+
An instance of [Administrate::Field::Boolean][1].
|
|
14
|
+
A wrapper around the boolean value pulled from the database.
|
|
15
|
+
|
|
16
|
+
[1]: http://www.rubydoc.info/gems/administrate/Administrate/Field/Boolean
|
|
17
|
+
%>
|
|
18
|
+
|
|
19
|
+
<% boolean_value = field.data ? 'Yes' : 'No' %>
|
|
20
|
+
<div class="bg-gray-50 p-3 rounded-md shadow-sm">
|
|
21
|
+
<span class="<%= field.data ? 'text-green-600' : 'text-red-600' %> font-medium">
|
|
22
|
+
<%= boolean_value %>
|
|
23
|
+
</span>
|
|
24
|
+
</div>
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
<%= f.label field.attribute, class: 'relative inline-flex items-center cursor-pointer' do %>
|
|
2
|
+
<%= f.check_box field.attribute, class: 'sr-only peer' %>
|
|
3
|
+
<div class="w-11 h-6 bg-gray-200 peer-focus:outline-none peer-focus:ring-4 peer-focus:ring-blue-300 dark:peer-focus:ring-blue-800 rounded-full peer dark:bg-gray-700 peer-checked:after:translate-x-full rtl:peer-checked:after:-translate-x-full peer-checked:after:border-white after:absolute after:bg-white after:border-gray-300 after:border after:rounded-full after:h-5 after:w-5 after:transition-all dark:border-gray-600 peer-checked:bg-blue-600"></div>
|
|
4
|
+
<span class="ms-3 text-sm font-medium text-gray-900 dark:text-gray-300">
|
|
5
|
+
<%= field.attribute %>
|
|
6
|
+
</span>
|
|
7
|
+
<% end %>
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
<%= field.to_emoji %>
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
<div class="mb-4">
|
|
2
|
+
<%= f.label field.attribute, class: "block text-sm font-medium text-gray-700" %>
|
|
3
|
+
<div class="mt-1">
|
|
4
|
+
<%= f.text_field field.attribute, class: "shadow-sm focus:ring-indigo-500 focus:border-indigo-500 block w-full sm:text-sm border-gray-300 rounded-md" %>
|
|
5
|
+
</div>
|
|
6
|
+
</div>
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
<%= field.to_emoji %>
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
<%#
|
|
2
|
+
# Date Form Partial
|
|
3
|
+
|
|
4
|
+
This partial renders an input element for a date attribute.
|
|
5
|
+
|
|
6
|
+
## Local variables:
|
|
7
|
+
|
|
8
|
+
- `f`:
|
|
9
|
+
A Rails form generator, used to help create the appropriate input fields.
|
|
10
|
+
- `field`:
|
|
11
|
+
An instance of [Administrate::Field::Date][1].
|
|
12
|
+
A wrapper around the Date value pulled from the database.
|
|
13
|
+
|
|
14
|
+
[1]: http://www.rubydoc.info/gems/administrate/Administrate/Field/Date
|
|
15
|
+
%>
|
|
16
|
+
|
|
17
|
+
<div class="mb-4">
|
|
18
|
+
<%= f.label field.attribute, class: "block text-sm font-medium text-gray-700" %>
|
|
19
|
+
<div class="mt-1">
|
|
20
|
+
<%= f.date_field field.attribute, class: "shadow-sm focus:ring-indigo-500 focus:border-indigo-500 block w-full sm:text-sm border-gray-300 rounded-md" %>
|
|
21
|
+
</div>
|
|
22
|
+
</div>
|
|
23
|
+
|