@@ -21,10 +18,9 @@
<%= ff.hidden_field :object_id, value: f.object.object_id %>
<%= ff.hidden_field :resource, value: f.object.options&.dig(:resource) %>
- <%= ff.search_field :search, placeholder: t("spina.search"), class: "form-input sticky top-0 text-sm w-80", data: {action: "input->form#submit focus->form#submit", page_select_target: "search"} %>
+ <%= ff.search_field :search, placeholder: t("spina.search"), class: "form-input sticky top-0 text-sm w-80", data: {action: "input->form#submit focus->form#submit", select_target: "search"} %>
<%= turbo_frame_tag "page_select_options_#{f.object.object_id}" do %>
<% end %>
diff --git a/app/views/spina/admin/parts/resource_links/_form.html.erb b/app/views/spina/admin/parts/resource_links/_form.html.erb
new file mode 100644
index 000000000..7bb601570
--- /dev/null
+++ b/app/views/spina/admin/parts/resource_links/_form.html.erb
@@ -0,0 +1,32 @@
+
+
+
<%= f.object.hint %>
+
" class="relative mt-1" data-reveal-away-value>
+ <%= f.hidden_field :resource_id, data: {select_target: "input"} %>
+
+
+
+
+ <%= form_with url: spina.search_admin_resource_select_options_path, data: {turbo_frame: "resource_select_options_#{f.object.object_id}", controller: "form", debounce_time: 100} do |ff| %>
+ <%= ff.hidden_field :object_id, value: f.object.object_id %>
+ <%= ff.hidden_field :resource, value: f.object.options&.dig(:resource) %>
+
+ <%= ff.search_field :search, placeholder: t("spina.search"), class: "form-input sticky top-0 text-sm w-80", data: {action: "input->form#submit focus->form#submit", select_target: "search"} %>
+
+ <% end %>
+
+ <%= turbo_frame_tag "resource_select_options_#{f.object.object_id}" do %>
+ <% end %>
+
+
+
+
+
+
diff --git a/app/views/spina/admin/resource_select_options/index.html.erb b/app/views/spina/admin/resource_select_options/index.html.erb
new file mode 100644
index 000000000..dd3af48a5
--- /dev/null
+++ b/app/views/spina/admin/resource_select_options/index.html.erb
@@ -0,0 +1,13 @@
+<%= turbo_frame_tag "resource_select_options_#{params[:object_id]}" do %>
+ <% if params[:search].blank? %>
+
+ <% end %>
+
+ <% @resources.each do |resource| %>
+
+ <% end %>
+<% end %>
diff --git a/app/views/spina/admin/resource_select_options/show.html.erb b/app/views/spina/admin/resource_select_options/show.html.erb
new file mode 100644
index 000000000..670695de7
--- /dev/null
+++ b/app/views/spina/admin/resource_select_options/show.html.erb
@@ -0,0 +1,3 @@
+<%= turbo_frame_tag :resource_title do %>
+ <%= @resource.label %>
+<% end %>
diff --git a/config/locales/en.yml b/config/locales/en.yml
index 0a50c5747..0bf0acb16 100644
--- a/config/locales/en.yml
+++ b/config/locales/en.yml
@@ -242,7 +242,7 @@ en:
options:
choose_option: Choose option
pages:
- add_page_to: 'Add page to:'
+ add_page_to: "Add page to:"
add_translation: Add %{language} translation
advanced: Advanced
cannot_be_deleted: Page can't be deleted
@@ -270,7 +270,7 @@ en:
page_content: Content
page_part: Page section
page_seo: Search engines
- path: 'Path:'
+ path: "Path:"
photo_picker: Choose image
photos_picker: Choose images
preview: Preview
@@ -295,7 +295,7 @@ en:
deleted: Translation deleted
permanently_delete: Permanently delete
photos:
- cannot_be_created: 'Image could not be processed:'
+ cannot_be_created: "Image could not be processed:"
choose_images: Choose images
delete: Delete
delete_confirmation: Are you sure you want to delete this
image?
@@ -303,7 +303,7 @@ en:
done_organizing: Done organizing
insert_photo: Insert image
insert_photos: Choose images
- link: 'URL of your image:'
+ link: "URL of your image:"
new_folder: New folder
organize: Organize images
rename_folder: Rename folder
@@ -335,6 +335,7 @@ en:
manual_sorting: Manual sorting
no_default_template: No default template
saved: Page collection saved
+ select_resource: Select resource
settings: "%{label} settings"
settings_description: All pages inside this collection will be prepended with this slug.
save: Save
@@ -379,7 +380,7 @@ en:
delete: Delete user
delete_confirmation_html: Are you sure you want to delete the user
%{user}?
deleted: User deleted
- last_login: 'Last login:'
+ last_login: "Last login:"
never_logged_in: Never logged in
new: New user
profile: Profile
diff --git a/config/routes.rb b/config/routes.rb
index 191cdfb45..cf40ec22e 100644
--- a/config/routes.rb
+++ b/config/routes.rb
@@ -48,7 +48,7 @@
get :children
post :sort_one
end
-
+
collection do
post :sort
end
@@ -58,6 +58,9 @@
resources :page_select_options, only: [:show, :index] do
post :search, on: :collection
end
+ resources :resource_select_options, only: [:show, :index] do
+ post :search, on: :collection
+ end
resources :page_translations, only: [:destroy]
resources :parent_pages
resource :layout, controller: :layout, only: [:edit, :update]
diff --git a/docs/v2/rendering_content/10_resource_link.md b/docs/v2/rendering_content/10_resource_link.md
new file mode 100644
index 000000000..015ecbc13
--- /dev/null
+++ b/docs/v2/rendering_content/10_resource_link.md
@@ -0,0 +1,16 @@
+# ResourceLink
+
+An ResourceLink is a part where you can link to or reference a resource. This is useful for displaying a list of pages contained within a resource.
+
+## Theme configuration
+
+```
+config.parts = [
+ # ...
+ {
+ name: "content_group",
+ title: "Content Group",
+ part_type: "Spina::Parts::ResourceLink"
+ }
+]
+```
diff --git a/lib/spina/engine.rb b/lib/spina/engine.rb
index 19ad8b6c0..930f929ac 100644
--- a/lib/spina/engine.rb
+++ b/lib/spina/engine.rb
@@ -38,7 +38,8 @@ class Engine < ::Rails::Engine
Spina::Parts::Repeater,
Spina::Parts::Option,
Spina::Parts::Attachment,
- Spina::Parts::PageLink
+ Spina::Parts::PageLink,
+ Spina::Parts::ResourceLink
)
end
end
diff --git a/test/dummy/config/initializers/themes/demo.rb b/test/dummy/config/initializers/themes/demo.rb
index d814d7751..eae69b458 100644
--- a/test/dummy/config/initializers/themes/demo.rb
+++ b/test/dummy/config/initializers/themes/demo.rb
@@ -69,6 +69,10 @@
options: {
resource: "blog"
}
+ }, {
+ name: "page_group",
+ title: "Pagegroup",
+ part_type: "Spina::Parts::ResourceLink",
}]
theme.view_templates = [{
@@ -80,12 +84,12 @@
title: "Simple page",
description: "Default layout",
usage: "Use for your content",
- parts: ["body", "blogpost", "page", "testrepeater"]
+ parts: ["body", "blogpost", "page", "testrepeater", "page_group"]
}, {
name: "demo",
title: "Demo",
description: "Example including all parts",
- parts: ["repeater", "repeater2", "attachment", "option", "body", "image_collection", "image", "portrait", "landscape", "wide"],
+ parts: ["repeater", "repeater2", "attachment", "option", "body", "image_collection", "image", "portrait", "landscape", "wide", "page_group"],
exclude_from: %w[guides]
}, {
name: "blogpost",