Bug 36156: None value selected on clone field/subfield linked to AV
[koha.git] / koha-tmpl / intranet-tmpl / prog / js / cataloging.js
1 /* global __ */
2 /* exported openAuth ExpandField CloneField CloneSubfield UnCloneField CloneItemSubfield CheckMandatorySubfields */
3
4 /*
5  * Unified file for catalogue edition
6  */
7
8 /* Functions developed for addbiblio.tt and authorities.tt */
9
10 // returns the fieldcode based upon tag div id
11 function getFieldCode(tagDivId){
12     // format : tag_<tagnumber>_...
13     return tagDivId.substr(3+1,3);
14 }
15
16 //returns the field and subfieldcode based upon subfield div id
17 function getFieldAndSubfieldCode(subfieldDivId){
18     // format : subfield<tagnumber><subfieldnumber>...
19     return subfieldDivId.substr(8,3+1);
20 }
21
22 //returns the subfieldcode based upon subfieldid writing
23 function getSubfieldCode(tagsubfieldid){
24     // 3 : tag +3 : tagnumber +4 : number of _ +8 subfield -1 begins at 0
25     return tagsubfieldid.substr(3+3+4+8-1,1);
26 }
27
28 // Take the base of tagsubfield information (removing the subfieldcodes and subfieldindexes)
29 // returns the filter
30 function getTagInputnameFilter(tagsubfieldid){
31     var tagsubfield=tagsubfieldid.substr(0,tagsubfieldid.lastIndexOf("_"));
32     var tagcode=tagsubfield.substr(tagsubfield.lastIndexOf("_"));
33     tagsubfield=tagsubfield.substr(0,tagsubfield.lastIndexOf("_"));
34     tagsubfield=tagsubfield.substr(0,tagsubfield.lastIndexOf("_"));
35     tagsubfield=tagsubfield+"_."+tagcode;
36     return tagsubfield;
37 }
38
39 // if source is "auth", we are editing an authority otherwise it is a biblio
40 function openAuth(tagsubfieldid,authtype,source) {
41     // let's take the base of tagsubfield information (removing the indexes and the codes
42     var element=document.getElementById(tagsubfieldid);
43     var tagsubfield=getTagInputnameFilter(tagsubfieldid);
44     var elementsubfcode=getSubfieldCode(element.name);
45     var mainmainstring=element.value;
46     var mainstring = new Array();
47
48     var ul = element.closest('ul');
49     var inputs = ul ? ul.getElementsByTagName('input') : element.parentNode.getElementsByTagName('input');
50     for (var myindex =0; myindex<inputs.length;myindex++){
51         if (inputs[myindex].name && inputs[myindex].name.match(tagsubfield)){
52             var subfieldcode=getSubfieldCode(inputs[myindex].name);
53             if (isNaN(parseInt(subfieldcode)) && inputs[myindex].value != "" && subfieldcode!=elementsubfcode){
54                 mainstring.push(inputs[myindex].value);
55             }
56         }
57     }
58     mainstring = mainstring.join(' ');
59     window.open("../authorities/auth_finder.pl?source="+source+"&authtypecode="+authtype+"&index="+tagsubfieldid+"&value_mainstr="+encodeURIComponent(mainmainstring)+"&value_main="+encodeURIComponent(mainstring), "_blank",'width=700,height=550,toolbar=false,scrollbars=yes');
60 }
61
62 function ExpandField() {
63     let index = this.dataset.field_id;
64     var original = document.getElementById(index); //original <li>
65     var lis = original.getElementsByTagName('li');
66     for(var i=0,lislen = lis.length ; i<lislen ; i++){   // foreach li
67         if(lis[i].hasAttribute('id') == 0 ) {continue; } // li element is specific to Select2
68         if(lis[i].getAttribute('id').match(/^subfield/)){  // if it s a subfield
69             if (!lis[i].style.display) {
70                 // first time => show all subfields
71                 lis[i].style.display = 'flex';
72             } else if (lis[i].style.display == 'none') {
73                 // show
74                 lis[i].style.display = 'flex';
75             } else {
76                 // hide
77                 lis[i].style.display = 'none';
78             }
79         }
80     }
81     return false;
82 }
83
84 var current_select2;
85 var Select2Utils = {
86     removeSelect2: function(selects) {
87         if ($.fn.select2) {
88             $(selects).each(function(){
89                 $(this).select2('destroy');
90             });
91         }
92     },
93
94     initSelect2: function(selects) {
95         if ($.fn.select2) {
96             if ( window.auth_values_creation === undefined || ! auth_values_creation ) {
97                 $(selects).select2().on("select2:clear", function () {
98                     $(this).on("select2:opening.cancelOpen", function (evt) {
99                         evt.preventDefault();
100                         $(this).off("select2:opening.cancelOpen");
101                     });
102                 });
103             } else {
104                 $(selects).each(function(){
105                     if ( !$(this).data("category") ) {
106                         $(this).select2().on("select2:clear", function () {
107                             $(this).on("select2:opening.cancelOpen", function (evt) {
108                                 evt.preventDefault();
109                                 $(this).off("select2:opening.cancelOpen");
110                             });
111                         });
112                     } else {
113                         $(this).select2({
114                             tags: true,
115                             createTag: function (tag) {
116                                 return {
117                                     id: tag.term,
118                                     text: tag.term,
119                                     newTag: true
120                                 };
121                             },
122                             templateResult: function(state) {
123                                 if (state.newTag) {
124                                     return state.text + " " + __("(select to create)");
125                                 }
126                                 return state.text;
127                             }
128                         }).on("select2:select", function(e) {
129                             if(e.params.data.newTag){
130                                 current_select2 = this;
131                                 var category = $(this).data("category");
132                                 $("#avCreate #new_av_category").html(category);
133                                 $("#avCreate input[name='category']").val(category);
134                                 $("#avCreate input[name='value']").val('');
135                                 $("#avCreate input[name='description']").val(e.params.data.text);
136
137                                 $(this).val($(this).find("option:first").val()).trigger('change');
138                                 $('#avCreate').modal({show:true});
139                             }
140                         }).on("select2:clear", function () {
141                             $(this).on("select2:opening.cancelOpen", function (evt) {
142                                 evt.preventDefault();
143
144                                 $(this).off("select2:opening.cancelOpen");
145                             });
146                         });
147                     }
148                 });
149             }
150         }
151     }
152 };
153
154 /**
155  * To clone a field
156  * @param hideMarc '0' for false, '1' for true
157  * @param advancedMARCEditor '0' for false, '1' for true
158  */
159 function CloneField(index, hideMarc, advancedMARCEditor) {
160     var original = document.getElementById(index); //original <li>
161     Select2Utils.removeSelect2($(original).find('select'));
162
163     var clone = original.cloneNode(true);
164     var new_key = CreateKey();
165     var new_id  = original.getAttribute('id')+new_key;
166
167     clone.setAttribute('id',new_id); // setting a new id for the parent li
168
169     var divs = Array.from(clone.getElementsByTagName('li')).concat(Array.from(clone.getElementsByTagName('div')));
170
171     // if hide_marc, indicators are hidden fields
172     // setting a new name for the new indicator
173     for(var i=0; i < 2; i++) {
174         var indicator = clone.getElementsByTagName('input')[i];
175         indicator.setAttribute('name',indicator.getAttribute('name')+new_key);
176     }
177
178     // settings all subfields
179     var divslen = divs.length;
180     for( i=0; i < divslen ; i++ ){      // foreach div/li
181         if( divs[i].getAttribute("id") && divs[i].getAttribute("id").match(/^subfield/)){  // if it s a subfield
182
183             // set the attribute for the new 'li' subfields
184             divs[i].setAttribute('id',divs[i].getAttribute('id')+new_key);
185
186             var inputs   = divs[i].getElementsByTagName('input');
187             var id_input = "";
188             var olddiv;
189             var oldcontrol;
190
191             for( j = 0 ; j < inputs.length ; j++ ) {
192                 if(inputs[j].getAttribute("id") && inputs[j].getAttribute("id").match(/^tag_/) ){
193                     inputs[j].value = "";
194
195                     //Remove the color added by the automatic linker
196                     $(inputs[j]).removeClass("matching_authority_field no_matching_authority_field");
197                 }
198             }
199             var textareas = divs[i].getElementsByTagName('textarea');
200             for( j = 0 ; j < textareas.length ; j++ ) {
201                 if(textareas[j].getAttribute("id") && textareas[j].getAttribute("id").match(/^tag_/) ){
202                     textareas[j].value = "";
203                 }
204             }
205             // Remove the status icons added by the automatic linker
206             $(divs[i]).find('.subfield_status').remove();
207             if( inputs.length > 0 ){
208                 inputs[0].setAttribute('id',inputs[0].getAttribute('id')+new_key);
209                 inputs[0].setAttribute('name',inputs[0].getAttribute('name')+new_key);
210
211                 try {
212                     id_input = inputs[1].getAttribute('id')+new_key;
213                     inputs[1].setAttribute('id',id_input);
214                     inputs[1].setAttribute('name',inputs[1].getAttribute('name')+new_key);
215                 } catch(e) {
216                     try{ // it s a select if it is not an input
217                         var selects = divs[i].getElementsByTagName('select');
218                         id_input = selects[0].getAttribute('id')+new_key;
219                         selects[0].setAttribute('id',id_input);
220                         selects[0].setAttribute('name',selects[0].getAttribute('name')+new_key);
221                         selects[0].selectedIndex = -1;
222                     }catch(e2){ // it is a textarea if it s not a select or an input
223                         var textareas = divs[i].getElementsByTagName('textarea');
224                         if( textareas.length > 0 ){
225                             id_input = textareas[0].getAttribute('id')+new_key;
226                             textareas[0].setAttribute('id',id_input);
227                             textareas[0].setAttribute('name',textareas[0].getAttribute('name')+new_key);
228                         }
229                     }
230                 }
231                 if( $(inputs[1]).hasClass('framework_plugin') ) {
232                     olddiv= original.getElementsByTagName('li')[i];
233                     oldcontrol= olddiv.getElementsByTagName('input')[1];
234                     AddEventHandlers( oldcontrol,inputs[1],id_input );
235                 }
236             }
237             // when cloning a subfield, re set its label too.
238             try {
239                 var labels = divs[i].getElementsByTagName('label');
240                 labels[0].setAttribute('for', id_input);
241             }
242             catch(e) {
243                 // do nothing if label does not exist.
244             }
245
246             // setting its '+' and '-' buttons
247             try {
248                 var anchors = divs[i].getElementsByTagName('a');
249                 for (var j = 0; j < anchors.length; j++) {
250                     if(anchors[j].getAttribute('class') == 'buttonPlus'){
251                         anchors[j].setAttribute('onclick',"CloneSubfield('" + divs[i].getAttribute('id') + "','" + advancedMARCEditor + "'); return false;");
252                     } else if (anchors[j].getAttribute('class') == 'buttonMinus') {
253                         anchors[j].setAttribute('onclick',"UnCloneField('" + divs[i].getAttribute('id') + "'); return false;");
254                     }
255                 }
256             }
257             catch(e){
258                 // do nothig if ButtonPlus & CloneButtonPlus don t exist.
259             }
260
261             // button ...
262             var spans=0;
263             try {
264                 spans = divs[i].getElementsByTagName('a');
265             } catch(e) {
266                 // no spans
267             }
268             if(spans){
269                 var buttonDot;
270                 if(!CloneButtonPlus){ // it s impossible to have  + ... (buttonDot AND buttonPlus)
271                     buttonDot = spans[0];
272                     if(buttonDot){
273                         // 2 possibilities :
274                         try{
275                             if( $(buttonDot).hasClass('framework_plugin') ) {
276                                 olddiv= original.getElementsByTagName('li')[i];
277                                 oldcontrol= olddiv.getElementsByTagName('a')[0];
278                                 AddEventHandlers(oldcontrol,buttonDot,id_input);
279                             }
280                             try {
281                                 // do not copy the script section.
282                                 var script = spans[0].getElementsByTagName('script')[0];
283                                 spans[0].removeChild(script);
284                             } catch(e) {
285                                 // do nothing if there is no script
286                             }
287                         } catch(e){
288                             //
289                         }
290                     }
291                 }
292             }
293
294         } else { // it's a indicator div
295             if ( divs[i].getAttribute("id") && divs[i].getAttribute('id').match(/^div_indicator/)) {
296
297                 // setting a new id for the indicator div
298                 divs[i].setAttribute('id',divs[i].getAttribute('id')+new_key);
299
300                 inputs = divs[i].getElementsByTagName('input');
301                 inputs[0].setAttribute('id',inputs[0].getAttribute('id')+new_key);
302                 inputs[1].setAttribute('id',inputs[1].getAttribute('id')+new_key);
303
304                 var CloneButtonPlus;
305                 try {
306                     anchors = divs[i].getElementsByTagName('a');
307                     for ( j = 0; j < anchors.length; j++) {
308                         if (anchors[j].getAttribute('class') == 'buttonPlus') {
309                             anchors[j].setAttribute('onclick',"CloneField('" + new_id + "','" + hideMarc + "','" + advancedMARCEditor + "'); return false;");
310                         } else if (anchors[j].getAttribute('class') == 'buttonMinus') {
311                             anchors[j].setAttribute('onclick',"UnCloneField('" + new_id + "'); return false;");
312                         } else if (anchors[j].getAttribute('class') == 'expandfield') {
313                             anchors[j].setAttribute('data-field_id',new_id);
314                         }
315                     }
316                 }
317                 catch(e){
318                     // do nothig CloneButtonPlus doesn't exist.
319                 }
320
321             }
322         }
323     }
324
325     // insert this line on the page
326     original.parentNode.insertBefore(clone,original.nextSibling);
327
328     $("ul.sortable_subfield", clone).sortable();
329
330     Select2Utils.initSelect2($(original).find('select'));
331     Select2Utils.initSelect2($(clone).find('select'));
332 }
333
334
335 /**
336  * To clone a subfield
337  * @param index
338  * @param advancedMARCEditor '0' for false, '1' for true
339  */
340 function CloneSubfield(index, advancedMARCEditor){
341     var original = document.getElementById(index); //original <div>
342     Select2Utils.removeSelect2($(original).find('select'));
343     var clone = original.cloneNode(true);
344     var new_key = CreateKey();
345     // set the attribute for the new 'li' subfields
346     var inputs     = clone.getElementsByTagName('input');
347     var selects    = clone.getElementsByTagName('select');
348     var textareas  = clone.getElementsByTagName('textarea');
349     var linkid;
350     var oldcontrol;
351
352     // input
353     var id_input = "";
354     for(var i=0,len=inputs.length; i<len ; i++ ){
355         id_input = inputs[i].getAttribute('id')+new_key;
356         inputs[i].setAttribute('id',id_input);
357         inputs[i].setAttribute('name',inputs[i].getAttribute('name')+new_key);
358         if(inputs[i].getAttribute("id") && inputs[i].getAttribute("id").match(/^tag_/) ){
359             inputs[i].value = "";
360         }
361         linkid = id_input;
362     }
363
364     // Plugin input
365     if( $(inputs[1]).hasClass('framework_plugin') ) {
366         oldcontrol= original.getElementsByTagName('input')[1];
367         AddEventHandlers( oldcontrol, inputs[1], linkid );
368     }
369
370     // select
371     for(i=0,len=selects.length; i<len ; i++ ){
372         id_input = selects[i].getAttribute('id')+new_key;
373         selects[i].setAttribute('id',selects[i].getAttribute('id')+new_key);
374         selects[i].setAttribute('name',selects[i].getAttribute('name')+new_key);
375         selects[i].selectedIndex = -1;
376         linkid = id_input;
377     }
378
379     // textarea
380     for( i=0,len=textareas.length; i<len ; i++ ){
381         id_input = textareas[i].getAttribute('id')+new_key;
382         textareas[i].setAttribute('id',textareas[i].getAttribute('id')+new_key);
383         textareas[i].setAttribute('name',textareas[i].getAttribute('name')+new_key);
384         if(textareas[i].getAttribute("id") && textareas[i].getAttribute("id").match(/^tag_/) ){
385             textareas[i].value = "";
386         }
387         linkid = id_input;
388     }
389
390     // Handle click event on buttonDot for plugin
391     var links  = clone.getElementsByTagName('a');
392     if( $(links[0]).hasClass('framework_plugin') ) {
393         oldcontrol= original.getElementsByTagName('a')[0];
394         AddEventHandlers( oldcontrol, links[0], linkid );
395     }
396
397     if(advancedMARCEditor == '0') {
398         // when cloning a subfield, reset its label too.
399         var label = clone.getElementsByTagName('label')[0];
400         if( label ){
401             label.setAttribute('for',id_input);
402         }
403     }
404
405     // setting a new id for the parent div
406     var new_id  = original.getAttribute('id')+new_key;
407     clone.setAttribute('id',new_id);
408
409     try {
410         var anchors = clone.getElementsByTagName('a');
411         if(anchors.length){
412             for( i = 0 ,len = anchors.length ; i < len ; i++){
413                 if(anchors[i].getAttribute('class') == 'buttonPlus'){
414                     anchors[i].setAttribute('onclick',"CloneSubfield('" + new_id + "','" + advancedMARCEditor + "'); return false;");
415                 } else if (anchors[i].getAttribute('class') == 'buttonMinus') {
416                     anchors[i].setAttribute('onclick',"UnCloneField('" + new_id + "'); return false;");
417                 }
418             }
419         }
420     }
421     catch(e){
422         // do nothig if ButtonPlus & CloneButtonPlus don't exist.
423     }
424     // insert this line on the page
425     original.parentNode.insertBefore(clone,original.nextSibling);
426
427     //Restablish select2 for the cloned elements.
428     Select2Utils.initSelect2($(original).find('select'));
429     Select2Utils.initSelect2($(clone).find('select'));
430
431     // delete data of cloned subfield
432     clone.querySelectorAll('input.input_marceditor').value = "";
433 }
434
435 function AddEventHandlers (oldcontrol, newcontrol, newinputid ) {
436 // This function is a helper for CloneField and CloneSubfield.
437 // It adds the event handlers from oldcontrol to newcontrol.
438 // newinputid is the id attribute of the cloned controlling input field
439 // Note: This code depends on the jQuery data for events; this structure
440 // is moved to _data as of jQuery 1.8.
441     var ev = $._data(oldcontrol, "events");
442     if(typeof ev != 'undefined') {
443         $.each(ev, function(prop,val) {
444             $.each(val, function(prop2,val2) {
445                 $(newcontrol).off( val2.type );
446                 $(newcontrol).on( val2.type, {id: newinputid}, val2.handler );
447             });
448         });
449     }
450 }
451
452 /**
453  * This function removes or clears unwanted subfields
454  */
455 function UnCloneField(index) {
456     var original = document.getElementById(index);
457     var canUnclone = false;
458     if ($(original).hasClass("tag")) {
459         // unclone a field, check if there will remain one field
460         var fieldCode = getFieldCode(index);
461         // tag divs with id begining with original field code
462         var cloneFields = $('.tag[id^="tag_'+fieldCode+'"]');
463         if (cloneFields.length > 1) {
464             canUnclone = true;
465         }
466     } else {
467         // unclone a subfield, check if there will remain one subfield
468         var subfieldCode = getFieldAndSubfieldCode(index);
469         // subfield divs of same field with id begining with original field and subfield field code
470         var cloneSubfields = $(original).parent().children('.subfield_line[id^="subfield'+subfieldCode+'"]');
471         if (cloneSubfields.length > 1) {
472             canUnclone = true;
473         }
474     }
475     if (canUnclone) {
476         // remove clone
477         original.parentNode.removeChild(original);
478     } else {
479         // clear inputs, but don't delete
480         $(":input.input_marceditor", original).each(function(){
481             // thanks to http://www.learningjquery.com/2007/08/clearing-form-data for
482             // hint about clearing selects correctly
483             var type = this.type;
484             var tag = this.tagName.toLowerCase();
485             if (type == 'text' || type == 'password' || tag == 'textarea') {
486                 this.value = "";
487             } else if (type == 'checkbox' || type == 'radio') {
488                 this.checked = false;
489             } else if (tag == 'select') {
490                 this.selectedIndex = -1;
491                 // required for Select2 to be able to update its control
492                 $(this).trigger('change');
493             }
494         });
495         $(":input.indicator", original).val("");
496     }
497 }
498
499 /**
500  * This function create a random number
501  */
502 function CreateKey(){
503     return parseInt(Math.random() * 100000);
504 }
505
506 /* Functions developed for additem.tt */
507
508 /**
509  * To clone a subfield.<br>
510  * @param original subfield div to clone
511  */
512 function CloneItemSubfield(original){
513     Select2Utils.removeSelect2($(original).find('select'));
514     var clone = original.cloneNode(true);
515     var new_key = CreateKey();
516
517     // set the attribute for the new 'li' subfields
518     var inputs     = clone.getElementsByTagName('input');
519     var selects    = clone.getElementsByTagName('select');
520     var textareas  = clone.getElementsByTagName('textarea');
521
522     // input (except hidden type)
523     var id_input = "";
524     for(var i=0,len=inputs.length; i<len ; i++ ){
525         if (inputs[i].getAttribute('type') != 'hidden') {
526             id_input = inputs[i].getAttribute('id')+new_key;
527             inputs[i].setAttribute('id',id_input);
528         }
529     }
530
531     // select
532     for( i=0,len=selects.length; i<len ; i++ ){
533         id_input = selects[i].getAttribute('id')+new_key;
534         selects[i].setAttribute('id',selects[i].getAttribute('id')+new_key);
535     }
536
537     // textarea
538     for( i=0,len=textareas.length; i<len ; i++ ){
539         id_input = textareas[i].getAttribute('id')+new_key;
540         textareas[i].setAttribute('id',textareas[i].getAttribute('id')+new_key);
541     }
542
543     // when cloning a subfield, reset its label too.
544     var label = clone.getElementsByTagName('label')[0];
545     label.setAttribute('for',id_input);
546
547     // setting a new if for the parent div
548     var new_id = original.getAttribute('id')+new_key;
549     clone.setAttribute('id',new_id);
550
551     // Don't clone "RegEx". We don't handle it for repeatable subfields
552     var links = clone.getElementsByTagName('a');
553     for( i = 0 ,len = links.length ; i < len ; i++){
554         if( $(links[i]).hasClass('field_regex') ) {
555             $(links[i]).remove();
556         }
557     }
558
559     // insert this line on the page
560     original.parentNode.insertBefore(clone,original.nextSibling);
561     Select2Utils.initSelect2($(original).find('select'));
562     Select2Utils.initSelect2($(clone).find('select'));
563 }
564
565 /**
566  * Check mandatory subfields of a cataloging form and adds <code>missing</code> class to those who are empty.<br>
567  * @param p the parent object of subfields to check
568  * @return the number of empty mandatory subfields
569  */
570 function CheckMandatorySubfields(p){
571     var total = 0;
572     $(p).find(".subfield_line input[name='mandatory'][value='1']").each(function(){
573         var editor = $(this).siblings(".input_marceditor");
574         if ( !editor.length ) { // Deal with date inputs
575             editor = $(this).siblings(".flatpickr_wrapper").find(".input_marceditor");
576         }
577         if (!editor.val()) {
578             editor.addClass("missing");
579             total++;
580         }
581     });
582     return total;
583 }
584
585 function CheckImportantSubfields(p){
586     var total = 0;
587     $(p).find(".subfield_line input[name='important'][value='1']").each(function(i){
588         var editor = $(this).siblings(".input_marceditor");
589         if ( !editor.length ) { // Deal with date inputs
590             editor = $(this).siblings(".flatpickr_wrapper").find(".input_marceditor");
591         }
592         if (!editor.val()) {
593             editor.addClass("missing");
594             total++;
595         }
596     });
597     return total;
598 }
599
600 $(document).ready(function() {
601     $("input.input_marceditor, input.indicator").addClass('noEnterSubmit');
602     $(document).ajaxSuccess(function() {
603         $("input.input_marceditor, input.indicator").addClass('noEnterSubmit');
604     });
605
606     if ( window.editor === undefined ) { // TODO This does not work with the advanced editor
607         Select2Utils.initSelect2($('.subfield_line select[data-category=""]')); // branches, itemtypes and cn_source
608         Select2Utils.initSelect2($('.subfield_line select[data-category!=""]'));
609     }
610
611     $("#avCreate").on("hidden.bs.modal", function(){
612         add_new_av.resetForm(); /* resets form state for jQuery Validate plugin */
613         $("#add_new_av")[0].reset();
614         $(".avCreate_error").hide();
615     });
616
617     var add_new_av = $("#add_new_av").validate({
618         submitHandler: function(form) {
619             var category         = form.category.value;
620             var value            = form.value.value;
621             var description      = form.description.value;
622             var opac_description = form.opac_description.value;
623
624             var data = "category="+encodeURIComponent(category)
625                 +"&value="+encodeURIComponent(value)
626                 +"&description="+encodeURIComponent(description)
627                 +"&opac_description="+encodeURIComponent(opac_description);
628             $.ajax({
629                 type: "POST",
630                 url: "/cgi-bin/koha/svc/authorised_values",
631                 data: data,
632                 success: function(response) {
633                     $('#avCreate').modal('hide');
634
635                     $(current_select2).append('<option selected value="'+response.value+'">'+response.description+'</option>');
636                     $("#avCreate").modal("hide");
637                 },
638                 error: function() {
639                     $(".avCreate_error").html(__("Something went wrong. Maybe the value already exists?")).show();
640                 }
641             });
642             return false;
643         }
644     });
645
646 });