Bugzilla – Attachment 169667 Details for
Bug 35044
Additional fields: Allow for repeatable fields
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Help
|
New Account
|
Log In
[x]
|
Forgot Password
Login:
[x]
[patch]
Bug 35044: Preparation:
Bug-35044-Preparation.patch (text/plain), 19.25 KB, created by
Julian Maurice
on 2024-07-26 07:52:59 UTC
(
hide
)
Description:
Bug 35044: Preparation:
Filename:
MIME Type:
Creator:
Julian Maurice
Created:
2024-07-26 07:52:59 UTC
Size:
19.25 KB
patch
obsolete
>From eba2d18c7a49c6896f7819314d4d1ef2d95f90d5 Mon Sep 17 00:00:00 2001 >From: Pedro Amorim <pedro.amorim@ptfs-europe.com> >Date: Fri, 13 Oct 2023 09:58:17 +0000 >Subject: [PATCH] Bug 35044: Preparation: > >get_additional_field_values_for_template method > >New method to be utilized for retrieval of additional fields of any >class that implements it. >This is to be used when additional_fields are needed to be sent to .tt >files for renderering. Both for form entries and read-only 'show' pages. > >Template files: > >Updated additional-fields-entry.inc: >Now considers entry of repeatable fields. >Repeatable text fields will have a "+New" link to allow for adding of a >new instance of a repeatable field. >Repeatable AV fields will be shown as checkboxes instead of a dropdown > >Update additional-fields-display.inc >When displaying non-editable additional-fields, multiple instances for >each field are now considered. >Label now only shows if field has a non-null value in it. >Option to show value_only >Option to set if its to be displayed on a table cell > >Update histsearch.tt and filter-orders.inc >Now calls additional-fields-entry.inc with search_form=1 to prevent >repetable "+New" controls from showing on search inputs. > >additional-fields-entry.js >New JS asset to be called by template files who require >additional-fields-entry.inc for repeatable fields controls. >This also handles the need for having the marcfield of type >'get' submitted if it is a disabled dropdown (AV marc field) > >Signed-off-by: Martin Renvoize <martin.renvoize@ptfs-europe.com> >Signed-off-by: Julian Maurice <julian.maurice@biblibre.com> >--- > Koha/Object/Mixin/AdditionalFields.pm | 43 ++++++ > .../en/includes/additional-fields-display.inc | 30 ++-- > .../en/includes/additional-fields-entry.inc | 133 +++++++++++++----- > .../prog/en/includes/filter-orders.inc | 2 +- > .../prog/en/modules/acqui/histsearch.tt | 2 +- > .../prog/js/additional-fields-entry.js | 28 ++++ > 6 files changed, 190 insertions(+), 48 deletions(-) > create mode 100644 koha-tmpl/intranet-tmpl/prog/js/additional-fields-entry.js > >diff --git a/Koha/Object/Mixin/AdditionalFields.pm b/Koha/Object/Mixin/AdditionalFields.pm >index bf6598d8c9..77aff5bbc4 100644 >--- a/Koha/Object/Mixin/AdditionalFields.pm >+++ b/Koha/Object/Mixin/AdditionalFields.pm >@@ -91,6 +91,49 @@ sub set_additional_fields { > } > } > >+=head3 get_additional_field_values_for_template >+ >+Returns additional field values in the format expected by the .tt file >+ >+ my $fields = Koha::Acquisition::Baskets->find($basketno)->get_additional_field_values_for_template; >+ >+Expected format is a hash of arrays, where the hash key is the field id and its respective array contains >+the field values 'value' for that field. Example where field_id = 2 is the only repeatable field: >+ >+{ >+ '3' => ['first value for field 3'], >+ '1' => ['first value for field 1'], >+ '4' => ['first value for field 4'], >+ '2' => [ >+ 'first value for field 2', >+ 'second value for field 2', >+ 'third value for field 2' >+ ] >+}; >+ >+=cut >+ >+sub get_additional_field_values_for_template { >+ my ($self) = @_; >+ >+ my $additional_field_ids = $self->additional_field_values->search( >+ {}, >+ { >+ columns => ['field_id'], >+ distinct => 1, >+ } >+ ); >+ >+ my %fields; >+ while ( my $additional_field_value = $additional_field_ids->next ) { >+ my @values = map ( $_->value, >+ $self->additional_field_values->search( { field_id => $additional_field_value->field_id } )->as_list ); >+ $fields{ $additional_field_value->field_id } = \@values; >+ } >+ >+ return \%fields; >+} >+ > =head3 additional_field_values > > Returns additional field values >diff --git a/koha-tmpl/intranet-tmpl/prog/en/includes/additional-fields-display.inc b/koha-tmpl/intranet-tmpl/prog/en/includes/additional-fields-display.inc >index 7b2bab777d..052d462739 100644 >--- a/koha-tmpl/intranet-tmpl/prog/en/includes/additional-fields-display.inc >+++ b/koha-tmpl/intranet-tmpl/prog/en/includes/additional-fields-display.inc >@@ -1,11 +1,25 @@ > [% USE AuthorisedValues %] > [% FOR field IN available %] >- <li> >- <span class="label"> [% field.name | html %]: </span> >- [% IF field.authorised_value_category %] >- [% AuthorisedValues.GetByCode( field.authorised_value_category, values.${field.name} ) | html %] >- [% ELSE %] >- [% values.${field.name} | html %] >- [% END %] >- </li> >+ [% IF is_table_cell %] >+ <td> >+ [% END %] >+ [% SET values_list = [] %] >+ [% FOR value IN values.${field.id} %] >+ [% IF field.authorised_value_category %] >+ [% values_list.push(AuthorisedValues.GetByCode( field.authorised_value_category, value )) %] >+ [% ELSE %] >+ [% values_list.push(value) %] >+ [% END %] >+ [% END %] >+ [% IF value_only %] >+ [% values_list.join(', ') | html %] >+ [% ELSIF !values_list.empty %] >+ <li> >+ <span class="label"> [% field.name | html %]: </span> >+ [% values_list.join(', ') | html %] >+ </li> >+ [% END %] >+ [% IF is_table_cell %] >+ </td> >+ [% END %] > [% END %] >diff --git a/koha-tmpl/intranet-tmpl/prog/en/includes/additional-fields-entry.inc b/koha-tmpl/intranet-tmpl/prog/en/includes/additional-fields-entry.inc >index df874de316..dd3db99683 100644 >--- a/koha-tmpl/intranet-tmpl/prog/en/includes/additional-fields-entry.inc >+++ b/koha-tmpl/intranet-tmpl/prog/en/includes/additional-fields-entry.inc >@@ -3,67 +3,124 @@ > [% USE ClassSources %] > [% USE ItemTypes %] > [% IF wrap_fieldset != 0 %] >-<fieldset class="rows"> >+<fieldset class="rows" id="additional_fields_form_section"> > <legend>Additional fields</legend> > <ol> > [% END %] > [% FOR field IN available %] > [% authorised_value_category = field.effective_authorised_value_category %] >- <li> >+ [% IF authorised_value_category %] >+ <li> > <label for="additional_field_[% field.id | html %]"> [% field.name | html %]: </label> >- [% IF authorised_value_category %] >- [% IF field.marcfield && field.marcfield_mode == 'get' %] >- <select name="additional_field_[% field.id | html %]" id="additional_field_[% field.id | html %]" disabled> >- [% ELSE %] >+ [% IF field.marcfield && field.marcfield_mode == 'get' %] >+ <select name="additional_field_[% field.id | html %]" id="additional_field_[% field.id | html %]" class="marcfieldget" disabled> >+ [% ELSE %] >+ [% IF !field.repeatable %] > <select name="additional_field_[% field.id | html %]" id="additional_field_[% field.id | html %]"> > [% END %] >+ [% END %] >+ [% IF !field.repeatable %] > <option value=""></option> >- [% IF authorised_value_category == 'branches' %] >- [% FOREACH branch IN Branches.all() %] >- [% IF branch.branchcode == values.${field.id} %] >- <option value="[% branch.branchcode | html %]" selected="selected">[% branch.branchname | html %]</option> >- [% ELSE %] >- <option value="[% branch.branchcode | html %]">[% branch.branchname | html %]</option> >- [% END %] >+ [% END %] >+ [% IF authorised_value_category == 'branches' %] >+ [% FOREACH branch IN Branches.all() %] >+ [% IF branch.branchcode == values.${field.id}.0 %] >+ <option value="[% branch.branchcode | html %]" selected="selected">[% branch.branchname | html %]</option> >+ [% ELSE %] >+ <option value="[% branch.branchcode | html %]">[% branch.branchname | html %]</option> > [% END %] >- [% ELSIF authorised_value_category == 'cn_source' %] >- [% FOREACH class_source IN ClassSources.all({ selected => values.${field.id} }) %] >- [% IF class_source.cn_source == values.${field.id} %] >- <option value="[% class_source.cn_source | html %]" selected="selected">[% class_source.description | html %]</option> >- [% ELSE %] >- <option value="[% class_source.cn_source | html %]">[% class_source.description | html %]</option> >- [% END %] >+ [% END %] >+ [% ELSIF authorised_value_category == 'cn_source' %] >+ [% FOREACH class_source IN ClassSources.all({ selected => values.${field.id} }) %] >+ [% IF class_source.cn_source == values.${field.id}.0 %] >+ <option value="[% class_source.cn_source | html %]" selected="selected">[% class_source.description | html %]</option> >+ [% ELSE %] >+ <option value="[% class_source.cn_source | html %]">[% class_source.description | html %]</option> > [% END %] >- [% ELSIF authorised_value_category == 'itemtypes' %] >- [% FOREACH itemtype IN ItemTypes.Get() %] >- [% IF itemtype.itemtype == values.${field.id} %] >- <option value="[% itemtype.itemtype | html %]" selected="selected">[% itemtype.description | html %]</option> >- [% ELSE %] >- <option value="[% itemtype.itemtype | html %]">[% itemtype.description | html %]</option> >- [% END %] >+ [% END %] >+ [% ELSIF authorised_value_category == 'itemtypes' %] >+ [% FOREACH itemtype IN ItemTypes.Get() %] >+ [% IF itemtype.itemtype == values.${field.id}.0 %] >+ <option value="[% itemtype.itemtype | html %]" selected="selected">[% itemtype.description | html %]</option> >+ [% ELSE %] >+ <option value="[% itemtype.itemtype | html %]">[% itemtype.description | html %]</option> > [% END %] >- [% ELSE %] >- [% FOREACH av IN AuthorisedValues.GetAuthValueDropbox( authorised_value_category ) %] >- [% IF av.authorised_value == values.${field.id} %] >+ [% END %] >+ [% ELSE %] >+ [% FOREACH av IN AuthorisedValues.GetAuthValueDropbox( authorised_value_category ) %] >+ [% IF !field.repeatable %] >+ [% IF av.authorised_value == values.${field.id}.0 %] > <option value="[% av.authorised_value | html %]" selected="selected">[% av.lib | html %]</option> > [% ELSE %] > <option value="[% av.authorised_value | html %]">[% av.lib | html %]</option> > [% END %] >+ [% ELSE %] >+ [% SET av_field_value_rendered = 0 %] >+ [% FOR value IN values.${field.id} %] >+ [% IF av.authorised_value == value %] >+ <label class="radio"> >+ <input type="checkbox" id="additional_field_[% field.id | html %]" checked name="additional_field_[% field.id | html %]" value="[% av.authorised_value | html %]">[% av.lib | html %] >+ </label> >+ [% SET av_field_value_rendered = 1 %] >+ [% END %] >+ [% END %] >+ [% IF !av_field_value_rendered %] >+ <label class="radio"> >+ <input type="checkbox" id="additional_field_[% field.id | html %]" name="additional_field_[% field.id | html %]" value="[% av.authorised_value | html %]">[% av.lib | html %] >+ </label> >+ [% END %] > [% END %] > [% END %] >- </select> <span>(Authorised values for [% authorised_value_category | html %])</span> >- [% ELSIF field.marcfield && field.marcfield_mode == 'get' %] >- <input type="text" value="[% values.${field.id} | html %]" id="additional_field_[% field.id | html %]" name="additional_field_[% field.id | html %]" readonly="readonly" /> >- [% ELSE %] >- <input type="text" value="[% values.${field.id} | html %]" id="additional_field_[% field.id | html %]" name="additional_field_[% field.id | html %]" /> >+ [% END %] >+ </select> >+ [% IF !search_form %] >+ <span>(Authorised values for [% authorised_value_category | html %])</span> >+ [% IF field.marcfield && field.marcfield_mode == 'get' %] >+ This value will be filled with the [% field.marcfield | html %] subfield of the selected bibliographic record. >+ [% ELSIF field.marcfield && field.marcfield_mode == 'set' %] >+ This value will be saved to the [% field.marcfield | html %] subfield of the selected bibliographic record. >+ [% END %] > [% END %] >+ </li> > >- [% IF field.marcfield && field.marcfield_mode == 'get' %] >+ [% ELSIF field.marcfield && field.marcfield_mode == 'get' %] >+ <li> >+ <label for="additional_field_[% field.id | html %]"> [% field.name | html %]: </label> >+ <input type="text" value="[% values.${field.id}.0 | html %]" id="additional_field_[% field.id | html %]" name="additional_field_[% field.id | html %]" readonly="readonly" /> >+ [% IF !search_form %] > This value will be filled with the [% field.marcfield | html %] subfield of the selected bibliographic record. >- [% ELSIF field.marcfield && field.marcfield_mode == 'set' %] >+ [% END %] >+ </li> >+ [% ELSE %] >+ [% SET text_field_value_rendered = 0 %] >+ [% FOR value IN values.${field.id} %] >+ <li> >+ <label for="additional_field_[% field.id | html %]"> [% field.name | html %]: </label> >+ <input type="text" value="[% value | html %]" id="additional_field_[% field.id | html %]" name="additional_field_[% field.id | html %]" /> >+ [% UNLESS search_form == 1 %] >+ <a href="#" class="clear_attribute"><i class="fa fa-fw fa-trash-can"></i> Clear</a> >+ [% END %] >+ [% IF field.repeatable && !search_form %] >+ <a href="#" class="clone_attribute"><i class="fa fa-fw fa-plus"></i> New</a> >+ [% END %] >+ [% SET text_field_value_rendered = 1 %] >+ [% END %] >+ [% IF !text_field_value_rendered %] >+ <li> >+ <label for="additional_field_[% field.id | html %]"> [% field.name | html %]: </label> >+ <input type="text" id="additional_field_[% field.id | html %]" name="additional_field_[% field.id | html %]" /> >+ [% UNLESS search_form == 1 %] >+ <a href="#" class="clear_attribute"><i class="fa fa-fw fa-trash-can"></i> Clear</a> >+ [% END %] >+ [% IF field.repeatable && !search_form %] >+ <a href="#" class="clone_attribute"><i class="fa fa-fw fa-plus"></i> New</a> >+ [% END %] >+ [% END %] >+ [% IF field.marcfield && field.marcfield_mode == 'set' && !search_form %] > This value will be saved to the [% field.marcfield | html %] subfield of the selected bibliographic record. > [% END %] >- </li> >+ </li> >+ [% END %] > [% END %] > [% IF wrap_fieldset != 0 %] > </ol> >diff --git a/koha-tmpl/intranet-tmpl/prog/en/includes/filter-orders.inc b/koha-tmpl/intranet-tmpl/prog/en/includes/filter-orders.inc >index d939531a26..626a9f2bd1 100644 >--- a/koha-tmpl/intranet-tmpl/prog/en/includes/filter-orders.inc >+++ b/koha-tmpl/intranet-tmpl/prog/en/includes/filter-orders.inc >@@ -31,7 +31,7 @@ > <label for="basketgroupname">Basket group:</label> > <input type="text" name="basketgroupname" id="basketgroupname" value="[% filters.basketgroupname | html %]" /> > </li> >- [% INCLUDE 'additional-fields-entry.inc' available=available_additional_fields values=additional_field_filters wrap_fieldset=0 %] >+ [% INCLUDE 'additional-fields-entry.inc' available=available_additional_fields values=additional_field_filters wrap_fieldset=0 search_form=1 %] > <li> > <label for="ordernumber">Order line:</label> > <input type="text" name="ordernumber" id="ordernumber" value="[% filters.ordernumber | html %]" /> >diff --git a/koha-tmpl/intranet-tmpl/prog/en/modules/acqui/histsearch.tt b/koha-tmpl/intranet-tmpl/prog/en/modules/acqui/histsearch.tt >index 4c2e5b17fc..cb2107d72b 100644 >--- a/koha-tmpl/intranet-tmpl/prog/en/modules/acqui/histsearch.tt >+++ b/koha-tmpl/intranet-tmpl/prog/en/modules/acqui/histsearch.tt >@@ -210,7 +210,7 @@ > <fieldset class="rows"> > <legend>Search orders</legend> > [% END %] >- [% INCLUDE 'filter-orders.inc' %] >+ [% INCLUDE 'filter-orders.inc' search_form=1 %] > <input type="hidden" name="do_search" value="1" /> > </fieldset> > <fieldset class="action"> >diff --git a/koha-tmpl/intranet-tmpl/prog/js/additional-fields-entry.js b/koha-tmpl/intranet-tmpl/prog/js/additional-fields-entry.js >new file mode 100644 >index 0000000000..590533b7d5 >--- /dev/null >+++ b/koha-tmpl/intranet-tmpl/prog/js/additional-fields-entry.js >@@ -0,0 +1,28 @@ >+$(document).ready(function() { >+ $("#additional_fields_form_section").on("click", ".clone_attribute", function(e){ >+ e.preventDefault(); >+ clone_entry( this ); >+ }); >+ >+ $("#additional_fields_form_section").on("click", ".clear_attribute", function(e){ >+ e.preventDefault(); >+ clear_entry( this ); >+ }); >+ >+ $('#additional_fields_form_section').parents('form ').submit(function() { >+ $('.marcfieldget').prop("disabled", false); >+ return true; >+ }); >+}); >+ >+function clone_entry(node) { >+ var original = $(node).parent(); >+ var clone = $(node).parent().clone(); >+ $(original).after(clone); >+ return false; >+} >+ >+function clear_entry(node) { >+ var original = $(node).parent(); >+ $("input", original).val(''); >+} >\ No newline at end of file >-- >2.39.2
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 35044
:
157324
|
157325
|
157326
|
157327
|
157328
|
157329
|
157330
|
157331
|
157332
|
157333
|
157334
|
158113
|
158498
|
158499
|
158500
|
158501
|
158502
|
158503
|
158504
|
158505
|
158506
|
158507
|
158508
|
158857
|
158858
|
158859
|
158860
|
158861
|
158862
|
158863
|
158864
|
158865
|
158866
|
158867
|
158868
|
159268
|
160177
|
160178
|
160179
|
160180
|
160181
|
160182
|
160183
|
160184
|
160185
|
160186
|
160187
|
160188
|
160189
|
164162
|
164163
|
164164
|
164165
|
164166
|
164167
|
164168
|
164169
|
164170
|
164171
|
164172
|
164173
|
164174
|
167690
|
168537
|
168538
|
168539
|
168540
|
168541
|
168542
|
168543
|
168544
|
168545
|
168546
|
168547
|
168548
|
169545
|
169546
|
169547
|
169603
|
169604
|
169605
|
169606
|
169607
|
169643
|
169644
|
169645
|
169646
|
169647
|
169648
|
169649
|
169650
|
169651
|
169652
|
169653
|
169654
|
169655
|
169656
|
169657
|
169658
|
169659
|
169660
|
169661
|
169662
|
169663
|
169664
|
169665
|
169666
| 169667 |
169668
|
169669
|
169670
|
169671
|
169672
|
169673
|
169674
|
169675
|
169676
|
169677
|
169678
|
169679
|
169680
|
169681
|
169682
|
169683
|
169684
|
169697
|
170501