Skip to content

Commit 5b5d78b

Browse files
authored
Allow individual fields to configure their own display component (#3808)
* Allow individual fields to configure their own display component The use case: for certain long fields, we would like to have a different layout that includes a "Show more"/"Show less" toggle. This allows us to add the following to our catalog controller: ``` config.add_show_field 'contents_display', label: 'Contents', layout_component: DisplayMoreFieldLayoutComponent ``` * Add documentation for layout_component option
1 parent a82c672 commit 5b5d78b

5 files changed

Lines changed: 37 additions & 2 deletions

File tree

app/components/blacklight/metadata_field_component.rb

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ class MetadataFieldComponent < Blacklight::Component
99
# @param show [Boolean] are we showing only a single document (vs a list of search results); used for backwards-compatibility
1010
def initialize(field:, layout: nil, show: false, view_type: nil)
1111
@field = field
12-
@layout = layout || Blacklight::MetadataFieldLayoutComponent
12+
@layout = layout || field.layout_component || Blacklight::MetadataFieldLayoutComponent
1313
@view_type = view_type
1414
@show = show
1515
end

app/presenters/blacklight/field_presenter.rb

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ def initialize(view_context, document, field_config, options = {})
3131

3232
attr_reader :view_context, :document, :field_config, :except_operations, :options
3333

34-
delegate :key, :component, to: :field_config
34+
delegate :key, :component, :layout_component, to: :field_config
3535

3636
# @return [Array<String>]
3737
def render

lib/blacklight/configuration/display_field.rb

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,7 @@ def initialize(*args, **kwargs, &)
3535
# @return [Blacklight::FieldPresenter]
3636
# @!attribute component
3737
# @return [Blacklight::MetadataFieldComponent]
38+
# @!attribute layout_component
3839

3940
##
4041
# Default rendering pipeline:

lib/generators/blacklight/templates/catalog_controller.rb

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -164,6 +164,14 @@ class <%= controller_name.classify %>Controller < ApplicationController
164164

165165
# solr fields to be displayed in the show (single result) view
166166
# The ordering of the field names is the order of the display
167+
# You can configure some components related to the show field:
168+
# - component: should have a similar API to
169+
# Blacklight::MetadataFieldComponent, and describes how
170+
# the values should be displayed
171+
# - layout_component: should have a similar API to
172+
# Blacklight::MetadataFieldLayoutComponent, and describes
173+
# how the overall layout of the field (both label and
174+
# values) should be displayed
167175
config.add_show_field 'title_tsim', label: 'Title'
168176
config.add_show_field 'title_vern_ssim', label: 'Title'
169177
config.add_show_field 'subtitle_tsim', label: 'Subtitle'

spec/components/blacklight/metadata_field_component_spec.rb

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,14 @@
22

33
require 'spec_helper'
44

5+
class CustomLayoutComponent < ViewComponent::Base
6+
def initialize(field:); end
7+
8+
def call
9+
'Hello from the custom layout component!'
10+
end
11+
end
12+
513
RSpec.describe Blacklight::MetadataFieldComponent, type: :component do
614
let(:view_context) { vc_test_controller.view_context }
715
let(:document) { SolrDocument.new('field' => ['Value']) }
@@ -35,5 +43,23 @@
3543
it 'renders the right field label' do
3644
expect(page).to have_css 'dt.blacklight-field', text: 'custom label'
3745
end
46+
47+
context 'with a custom layout component specified in the field config' do
48+
let(:field_config) { Blacklight::Configuration::Field.new(layout_component: CustomLayoutComponent, key: 'field', field: 'field', label: 'Field label') }
49+
50+
it 'displays the custom layout component' do
51+
expect(page.text).to include 'Hello from the custom layout component!'
52+
end
53+
end
54+
end
55+
56+
context 'with a custom layout component passed in through args' do
57+
before do
58+
render_inline(described_class.new(field: field, layout: CustomLayoutComponent))
59+
end
60+
61+
it 'displays the custom layout component' do
62+
expect(page.text).to include 'Hello from the custom layout component!'
63+
end
3864
end
3965
end

0 commit comments

Comments
 (0)