Bugzilla – Attachment 193048 Details for
Bug 25314
Make OPAC facets collapse
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Help
|
New Account
|
Log In
[x]
|
Forgot Password
Login:
[x]
[patch]
Bug 25314: Make OPAC facets collapse
Bug-25314-Make-OPAC-facets-collapse.patch (text/plain), 28.09 KB, created by
Katrin Fischer
on 2026-02-13 10:20:18 UTC
(
hide
)
Description:
Bug 25314: Make OPAC facets collapse
Filename:
MIME Type:
Creator:
Katrin Fischer
Created:
2026-02-13 10:20:18 UTC
Size:
28.09 KB
patch
obsolete
>From 8643effe0c8ae409eff0c8bb21bfe7a6b9c5011e Mon Sep 17 00:00:00 2001 >From: Owen Leonard <oleonard@myacpl.org> >Date: Thu, 29 Jan 2026 12:38:39 +0000 >Subject: [PATCH] Bug 25314: Make OPAC facets collapse > >This patch implements collapsing facets using the Bootstrap Collapse >component. > >To test, apply the patch and rebuild the OPAC CSS. > >1. Clear your browser cache if necessary. >2. Using the sample data, go to Advanced Search in the OPAC. Check the > "Books" checkbox under the "Item types" tab and submit. >3. In the left-hand sidebar you should see the facets you normally see, > but now each one has an arrow icon to show whether the facet is > expanded or collapsed. >4. All facets should be expanded by default. Adding expanded/collapsed > settings to system preferences is out of scope for this bug. >5. Test expanding and collapsing facets, as well as the "Show more" link > under each one. >6. Click the "Fiction" link under the "Collections" facet. When the > refined search results load you clicked should now have a red "X" > link next to "Fiction," which should no longer be a link. > - Because "Fiction" is the only uption under the "Collections" facet, > the facet is not collapsible. I reasoned that it would be important > not to let a facet limitation disappear behind hidden facets. > * The only way I know to do this in the template is to check for > facets with only one option this has the possibly-unwanted side > effect of making facets which haven't been selected but still only > have one option not collapsible. In this example search "Holding > libraries" and "Topics" show this. I'm open to suggestions on this! >7. Test with the displayFacetCount preference both enabled and disabled. > >Sponsored-by: Athens County Public Libraries >Signed-off-by: Paul Derscheid <paul.derscheid@lmscloud.de> >Signed-off-by: Katrin Fischer <katrin.fischer@bsz-bw.de> >--- > .../opac-tmpl/bootstrap/css/src/_common.scss | 9 + > .../opac-tmpl/bootstrap/css/src/opac.scss | 66 ++++- > .../bootstrap/en/includes/opac-facets.inc | 275 ++++++++++-------- > 3 files changed, 210 insertions(+), 140 deletions(-) > >diff --git a/koha-tmpl/opac-tmpl/bootstrap/css/src/_common.scss b/koha-tmpl/opac-tmpl/bootstrap/css/src/_common.scss >index 87fb0fa0b9b..17b96490fa1 100644 >--- a/koha-tmpl/opac-tmpl/bootstrap/css/src/_common.scss >+++ b/koha-tmpl/opac-tmpl/bootstrap/css/src/_common.scss >@@ -176,6 +176,15 @@ caption { > } > } > >+.badge { >+ &.bg-info-subtle, >+ &.bg-secondary-subtle { >+ color: #000 !important; >+ margin-left: .3em; >+ text-indent: 0; >+ } >+} >+ > .btn-primary { > background-color: $base-theme-color; > border: 1px solid darken( $base-theme-color, 10% ); >diff --git a/koha-tmpl/opac-tmpl/bootstrap/css/src/opac.scss b/koha-tmpl/opac-tmpl/bootstrap/css/src/opac.scss >index 42268b4b126..4c73efaefcd 100644 >--- a/koha-tmpl/opac-tmpl/bootstrap/css/src/opac.scss >+++ b/koha-tmpl/opac-tmpl/bootstrap/css/src/opac.scss >@@ -1874,18 +1874,9 @@ nav { > } > > li { >- font-size: 90%; >- font-weight: bold; >+ font-size: 95%; > list-style-type: none; > >- li { >- font-size: 95%; >- font-weight: normal; >- line-height: 125%; >- margin-bottom: 2px; >- padding: .1em .2em; >- } >- > &.showmore { > a { > font-weight: bold; >@@ -1898,8 +1889,59 @@ nav { > font-weight: normal; > } > >- .facet-count { >- display: inline-block; >+ .facet-label-selected { >+ font-weight: bold; >+ } >+ >+ .facet-toggle, >+ .facet-toggle:hover, >+ .facet-static { >+ color: #6F6F6F; >+ cursor: pointer; >+ display: inline-flex; >+ font-weight: bold; >+ padding: 0.3em 0; >+ text-decoration: none; >+ } >+ .facet-toggle::before { >+ color: #5A5A5A; >+ content: "\f0da"; >+ font-family: "Font Awesome 6 Free"; >+ font-size: 90%; >+ line-height: 1.5em; >+ padding: 0 0.35em 0 0; >+ transition: transform 0.2s ease; >+ } >+ >+ .facet-toggle[aria-expanded="true"]::before { >+ content: "\f0d7"; >+ padding-top: 0; >+ padding-bottom: 0; >+ } >+ >+ .facet-static::before { >+ color: #5A5A5A; >+ content: "\f0c8"; >+ cursor: default; >+ font-family: "Font Awesome 6 Free"; >+ font-size: 50%; >+ line-height: 1.5em; >+ padding: .7em 1em 0 0; >+ } >+ >+ .facet-collapse li { >+ padding: 0.1em 0 0.1em 1.6em; >+ text-indent: -1em; >+ } >+ .facet-remove { >+ background:#FFF none !important; >+ color:red !important; >+ padding:.2em .4em; >+ border:1px solid rgb(255, 0, 0); >+ text-indent:0; >+ } >+ .facet-remove:hover { >+ background: rgba(255, 0, 0, 0.1) none !important; > } > } > >diff --git a/koha-tmpl/opac-tmpl/bootstrap/en/includes/opac-facets.inc b/koha-tmpl/opac-tmpl/bootstrap/en/includes/opac-facets.inc >index e56965d6634..38742be1d10 100644 >--- a/koha-tmpl/opac-tmpl/bootstrap/en/includes/opac-facets.inc >+++ b/koha-tmpl/opac-tmpl/bootstrap/en/includes/opac-facets.inc >@@ -10,161 +10,180 @@ > <ul class="menu-collapse"> > [% IF Koha.Preference("SavedSearchFilters") && search_filters.size > 0 %] > <li id="search-filters"> >- <h3 id="filter_facets">Custom search filters</h3> >+ <a class="facet-toggle" aria-expanded="true" data-bs-toggle="collapse" data-bs-target="#custom_search_collapse" id="filter_facets">Custom search filters</a> >+ <div class="facet-collapse collapse show" id="custom_search_collapse"> >+ <ul> >+ [% SET base_url = "/cgi-bin/koha/opac-search.pl?" _ query_cgi _ limit_cgi %] >+ [% FOREACH search_filter IN search_filters %] >+ [% SET search_filter_id = search_filter.id | uri %] >+ <li> >+ [% IF active_filters.${search_filter.id} %] >+ <span class="filter_label">[% search_filter.name | html %]<a href="[% base_url _ '&nolimit=search_filter:' _ search_filter_id | $raw %]">[x]</a></span> >+ [% ELSE %] >+ <span class="filter_label"><a href="[% base_url _ '&limit=search_filter:' _ search_filter_id | $raw %]">[% search_filter.name | html %]</a></span> >+ [% END %] >+ </li> >+ [% END %] >+ </ul> >+ </div> >+ </li> >+ [% END %] >+ <li id="availability_facet"> >+ <a class="facet-toggle" aria-expanded="true" data-bs-toggle="collapse" data-bs-target="#availability_collapse" id="filter_facets">Availability</a> >+ <div class="facet-collapse collapse show" id="availability_collapse"> > <ul> >- [% SET base_url = "/cgi-bin/koha/opac-search.pl?" _ query_cgi _ limit_cgi %] >- [% FOREACH search_filter IN search_filters %] >- [% SET search_filter_id = search_filter.id | uri %] >- <li> >- [% IF active_filters.${search_filter.id} %] >- <span class="filter_label">[% search_filter.name | html %]<a href="[% base_url _ '&nolimit=search_filter:' _ search_filter_id | $raw %]">[x]</a></span> >- [% ELSE %] >- <span class="filter_label"><a href="[% base_url _ '&limit=search_filter:' _ search_filter_id | $raw %]">[% search_filter.name | html %]</a></span> >- [% END %] >- </li> >+ [% IF ( available ) %] >+ <li><strong>Showing only records with available items</strong></li >+ ><li><a href="/cgi-bin/koha/opac-search.pl?[% query_cgi | $raw %][% limit_cgi_not_availablity | $raw %][% IF ( sort_by ) %]&sort_by=[% sort_by |uri %][% END %]">Show all records</a> </li> >+ [% ELSE %] >+ <li >+ ><a href="/cgi-bin/koha/opac-search.pl?[% query_cgi | $raw %][% limit_cgi | $raw %][% IF ( sort_by ) %]&sort_by=[% sort_by |uri %][% END %]&limit=available" >+ >Limit to records with available items</a >+ ></li >+ > > [% END %] >+ [% IF ( related ) %]<li>(related searches: [% FOREACH relate IN related %][% relate.related_search | html %][% END %])</li>[% END %] > </ul> >- </li> >- [% END %] >- <li id="availability_facet" >- ><h3 id="facet-availability">Availability</h3> >- <ul> >- [% IF ( available ) %] >- <li><strong>Showing only records with available items</strong></li >- ><li><a href="/cgi-bin/koha/opac-search.pl?[% query_cgi | $raw %][% limit_cgi_not_availablity | $raw %][% IF ( sort_by ) %]&sort_by=[% sort_by |uri %][% END %]">Show all records</a> </li> >- [% ELSE %] >- <li><a href="/cgi-bin/koha/opac-search.pl?[% query_cgi | $raw %][% limit_cgi | $raw %][% IF ( sort_by ) %]&sort_by=[% sort_by |uri %][% END %]&limit=available">Limit to records with available items</a></li> >- [% END %] >- </ul> >- [% IF ( related ) %]<li>(related searches: [% FOREACH relate IN related %][% relate.related_search | html %][% END %])</li>[% END %] >+ </div> > </li> > > [% FOREACH facets_loo IN facets_loop %] > [% IF facets_loo.facets.size > 0 %] > <li id="[% facets_loo.type_id | html %]"> >+ [% IF ( facets_loo.facets.size == 1 ) %] >+ [% attrs = "class='facet-static'" %] >+ [% ELSE %] >+ [% attrs = "class='facet-toggle' aria-expanded='true' data-bs-toggle='collapse' data-bs-target='#" _ facets_loo.type_id _ "_collapse'" %] >+ [% END %] > [% SWITCH facets_loo.label %] > [% CASE 'Authors' %] >- <h3 id="facet-authors">Authors</h3> >+ <a [% attrs | $raw %] id="facet-authors">Authors</a> > [% CASE 'Titles' %] >- <h3 id="facet-titles">Titles</h3> >+ <a [% attrs | $raw %] id="facet-titles">Titles</a> > [% CASE 'Topics' %] >- <h3 id="facet-topics">Topics</h3> >+ <a [% attrs | $raw %] id="facet-topics">Topics</a> > [% CASE 'Places' %] >- <h3 id="facet-places">Places</h3> >+ <a [% attrs | $raw %] id="facet-places">Places</a> > [% CASE 'Series' %] >- <h3 id="facet-series">Series</h3> >+ <a [% attrs | $raw %] id="facet-series">Series</a> > [% CASE 'Item types' %] >- <h3 id="facet-itemtypes">Item types</h3> >+ <a [% attrs | $raw %] id="facet-itemtypes">Item types</a> > [% CASE 'Home libraries' %] >- <h3 id="facet-home-libraries">Home libraries</h3> >+ <a [% attrs | $raw %] id="facet-home-libraries">Home libraries</a> > [% CASE 'Holding libraries' %] >- <h3 id="facet-holding-libraries">Holding libraries</h3> >+ <a [% attrs | $raw %] id="facet-holding-libraries">Holding libraries</a> > [% CASE 'Location' %] >- <h3 id="facet-locations">Locations</h3> >+ <a [% attrs | $raw %] id="facet-locations">Locations</a> > [% CASE 'Collections' %] >- <h3 id="facet-collections">Collections</h3> >+ <a [% attrs | $raw %] id="facet-collections">Collections</a> > [% CASE 'Languages' %] >- <h3 id="facet-languages">Languages</h3> >+ <a [% attrs | $raw %] id="facet-languages">Languages</a> > [% CASE %] >- <h3 id="facet-[% facets_loo.type_link_value | html %]">[% facets_loo.label | html %]</h3> >+ <a [% attrs | $raw %] id="facet-[% facets_loo.type_link_value | html %]">[% facets_loo.type_id | html %]</a> > [% END %] >- <ul> >- [% SET url = "/cgi-bin/koha/opac-search.pl?" _ query_cgi _ limit_cgi %] >- [% IF ( sort_by ) %] >- [% url = BLOCK %][% url | $raw %][% "&sort_by=" _ sort_by | url %][% END %] >- [% END %] >- [% IF ( results_per_page ) %] >- [% url = BLOCK %][% url | $raw %][% "&count=" _ results_per_page | url %][% END %] >- [% END %] >- [% FOREACH facet IN facets_loo.facets %] >- [% IF facets_loo.label == 'Collections' %][% SET facet.facet_label_value = AuthorisedValues.GetDescriptionByKohaField( kohafield => 'items.ccode', authorised_value => facet.facet_label_value, opac =>1 ) || facet.facet_label_value %][% END %] >- [% IF facets_loo.label == 'Languages' %][% SET facet.facet_label_value = Languages.GetByISOCode(lang,facet.facet_label_value) || facet.facet_label_value %][% END %] >- [% SET li_class = '' %] >- [% SET li_style = '' %] >- [% IF loop.count > 5 && !facet.active %] >- [% li_class = "collapsible-facet" %] >- [% li_style = "display:none" %] >+ <div class="facet-collapse collapse show" id="[% facets_loo.type_id | html %]_collapse"> >+ <ul> >+ [% SET url = "/cgi-bin/koha/opac-search.pl?" _ query_cgi _ limit_cgi %] >+ [% IF ( sort_by ) %] >+ [% url = BLOCK %][% url | $raw %][% "&sort_by=" _ sort_by | url %][% END %] >+ [% END %] >+ [% IF ( results_per_page ) %] >+ [% url = BLOCK %][% url | $raw %][% "&count=" _ results_per_page | url %][% END %] > [% END %] >- <li class="[% li_class | html %]" style="[% li_style | html %]"> >- [% IF facet.active %] >- [% local_url = BLOCK %][% url | $raw %][% "&nolimit=" _ facet.type_link_value _ ":" _ facet.facet_link_value | url %][% END %] >- <span class="facet-label">[% facet.facet_label_value | html %]</span> >- [% IF ( displayFacetCount ) %] >- <span class="facet-count-selected">([% facet.facet_count | html %])</span> >+ [% FOREACH facet IN facets_loo.facets %] >+ [% IF facets_loo.label == 'Collections' %][% SET facet.facet_label_value = AuthorisedValues.GetDescriptionByKohaField( kohafield => 'items.ccode', authorised_value => facet.facet_label_value, opac =>1 ) || facet.facet_label_value %][% END %] >+ [% IF facets_loo.label == 'Languages' %][% SET facet.facet_label_value = Languages.GetByISOCode(lang,facet.facet_label_value) || facet.facet_label_value %][% END %] >+ [% SET li_class = '' %] >+ [% SET li_style = '' %] >+ [% IF loop.count > 5 && !facet.active %] >+ [% li_class = "collapsible-facet" %] >+ [% li_style = "display:none" %] >+ [% END %] >+ <li class="[% li_class | html %]" style="[% li_style | html %]"> >+ [% IF facet.active %] >+ [% local_url = BLOCK %][% url | $raw %][% "&nolimit=" _ facet.type_link_value _ ":" _ facet.facet_link_value | url %][% END %] >+ [% FILTER collapse %] >+ <span class="facet-label facet-label-selected"> >+ [% facet.facet_label_value | html %] >+ [% IF ( displayFacetCount ) %] >+ <span class="badge bg-info-subtle facet-count-selected">[% facet.facet_count | html %]</span> >+ [% END %] >+ <a href="[% local_url | $raw %]" title="Remove facet [% facet.facet_label_value | html %]"><span class="badge facet-remove">x</span></a> >+ </span> >+ [% END %] >+ [% ELSE %] >+ [% local_url = BLOCK %][% url | $raw %][% "&limit=" _ facet.type_link_value _ ":" _ facet.facet_link_value | url %][% END %] >+ <span class="facet-label"><a href="[% local_url | $raw %]" title="[% facet.facet_title_value | html %]">[% facet.facet_label_value | html %]</a></span> >+ [% IF ( displayFacetCount ) %] >+ <span class="badge bg-info-subtle facet-count"> [% facet.facet_count | html %]</span> >+ [% END %] > [% END %] >- [<a href="[% local_url | $raw %]" title="Remove facet [% facet.facet_label_value | html %]">x</a>] >- [% ELSE %] >- [% local_url = BLOCK %][% url | $raw %][% "&limit=" _ facet.type_link_value _ ":" _ facet.facet_link_value | url %][% END %] >- <span class="facet-label"><a href="[% local_url | $raw %]" title="[% facet.facet_title_value | html %]">[% facet.facet_label_value | html %]</a></span> >- [% IF ( displayFacetCount ) %] >- <span class="facet-count"> ([% facet.facet_count | html %])</span> >+ </li> >+ [% END %] >+ [% IF facets_loo.facets.size > 5 %] >+ <li class="moretoggle"> >+ [% SET aria_label = t("Show more") %] >+ [% SWITCH facets_loo.label %] >+ [% CASE 'Authors' %] >+ [% aria_label = t("Show more authors") %] >+ [% CASE 'Titles' %] >+ [% aria_label = t("Show more titles") %] >+ [% CASE 'Topics' %] >+ [% aria_label = t("Show more topics") %] >+ [% CASE 'Places' %] >+ [% aria_label = t("Show more places") %] >+ [% CASE 'Series' %] >+ [% aria_label = t("Show more series") %] >+ [% CASE 'Item types' %] >+ [% aria_label = t("Show more item types") %] >+ [% CASE 'Home libraries' %] >+ [% aria_label = t("Show more home libraries") %] >+ [% CASE 'Holding libraries' %] >+ [% aria_label = t("Show more holding libraries") %] >+ [% CASE 'Location' %] >+ [% aria_label = t("Show more locations") %] >+ [% CASE 'Collections' %] >+ [% aria_label = t("Show more collections") %] >+ [% CASE 'Languages' %] >+ [% aria_label = t("Show more languages") %] > [% END %] >- [% END %] >- </li> >- [% END %] >- [% IF facets_loo.facets.size > 5 %] >- <li class="moretoggle"> >- [% SET aria_label = t("Show more") %] >- [% SWITCH facets_loo.label %] >- [% CASE 'Authors' %] >- [% aria_label = t("Show more authors") %] >- [% CASE 'Titles' %] >- [% aria_label = t("Show more titles") %] >- [% CASE 'Topics' %] >- [% aria_label = t("Show more topics") %] >- [% CASE 'Places' %] >- [% aria_label = t("Show more places") %] >- [% CASE 'Series' %] >- [% aria_label = t("Show more series") %] >- [% CASE 'Item types' %] >- [% aria_label = t("Show more item types") %] >- [% CASE 'Home libraries' %] >- [% aria_label = t("Show more home libraries") %] >- [% CASE 'Holding libraries' %] >- [% aria_label = t("Show more holding libraries") %] >- [% CASE 'Location' %] >- [% aria_label = t("Show more locations") %] >- [% CASE 'Collections' %] >- [% aria_label = t("Show more collections") %] >- [% CASE 'Languages' %] >- [% aria_label = t("Show more languages") %] >- [% END %] > >- <a href="#" aria-label="[% aria_label | html | trim %]"><strong>Show more</strong></a> >- </li> >- <li class="moretoggle" style="display:none"> >- [% SET aria_label = t("Show more") %] >- [% SWITCH facets_loo.label %] >- [% CASE 'Authors' %] >- [% aria_label = t("Show fewer authors") %] >- [% CASE 'Titles' %] >- [% aria_label = t("Show fewer titles") %] >- [% CASE 'Topics' %] >- [% aria_label = t("Show fewer topics") %] >- [% CASE 'Places' %] >- [% aria_label = t("Show fewer places") %] >- [% CASE 'Series' %] >- [% aria_label = t("Show fewer series") %] >- [% CASE 'Item types' %] >- [% aria_label = t("Show fewer item types") %] >- [% CASE 'Home libraries' %] >- [% aria_label = t("Show fewer home libraries") %] >- [% CASE 'Holding libraries' %] >- [% aria_label = t("Show fewer holding libraries") %] >- [% CASE 'Location' %] >- [% aria_label = t("Show fewer locations") %] >- [% CASE 'Collections' %] >- [% aria_label = t("Show fewer collections") %] >- [% CASE 'Languages' %] >- [% aria_label = t("Show fewer languages") %] >- [% END %] >+ <a href="#" aria-label="[% aria_label | html | trim %]"><strong>Show more</strong></a> >+ </li> >+ <li class="moretoggle" style="display:none"> >+ [% SET aria_label = t("Show more") %] >+ [% SWITCH facets_loo.label %] >+ [% CASE 'Authors' %] >+ [% aria_label = t("Show fewer authors") %] >+ [% CASE 'Titles' %] >+ [% aria_label = t("Show fewer titles") %] >+ [% CASE 'Topics' %] >+ [% aria_label = t("Show fewer topics") %] >+ [% CASE 'Places' %] >+ [% aria_label = t("Show fewer places") %] >+ [% CASE 'Series' %] >+ [% aria_label = t("Show fewer series") %] >+ [% CASE 'Item types' %] >+ [% aria_label = t("Show fewer item types") %] >+ [% CASE 'Home libraries' %] >+ [% aria_label = t("Show fewer home libraries") %] >+ [% CASE 'Holding libraries' %] >+ [% aria_label = t("Show fewer holding libraries") %] >+ [% CASE 'Location' %] >+ [% aria_label = t("Show fewer locations") %] >+ [% CASE 'Collections' %] >+ [% aria_label = t("Show fewer collections") %] >+ [% CASE 'Languages' %] >+ [% aria_label = t("Show fewer languages") %] >+ [% END %] > >- [% IF aria_label %] >- <a href="#" aria-label="[% aria_label | html | trim %]"><strong>Show less</strong></a> >- [% END %] >- </li> >- [% END %] >- </ul> >+ [% IF aria_label %] >+ <a href="#" aria-label="[% aria_label | html | trim %]"><strong>Show less</strong></a> >+ [% END %] >+ </li> >+ [% END %] >+ </ul> >+ </div> > </li> > [% END # / IF facets_loo.facets.size > 0 %] > [% END # / FOREACH facets_loo %] >-- >2.39.5
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Diff
|
Splinter Review
Attachments on
bug 25314
:
103957
|
103958
|
103997
|
107447
|
107448
|
107450
|
107451
|
107452
|
192334
|
192341
|
192597
|
192615
|
193046
|
193047
| 193048 |
193049