@@ -, +, @@
- Display a unique item block at once
- PrepareItemrecordDisplay is now used for cloning block
---
acqui/check_uniqueness.pl | 70 +++++
acqui/neworderempty.pl | 13 +-
acqui/orderreceive.pl | 12 +-
.../intranet-tmpl/prog/en/includes/additem.js.inc | 10 +
koha-tmpl/intranet-tmpl/prog/en/js/additem.js | 326 +++++++++++++------
.../prog/en/modules/acqui/neworderempty.tt | 90 ++++---
.../prog/en/modules/acqui/orderreceive.tt | 119 +++++---
.../prog/en/modules/services/itemrecorddisplay.tt | 25 ++
services/itemrecorddisplay.pl | 58 ++++
9 files changed, 522 insertions(+), 201 deletions(-)
create mode 100755 acqui/check_uniqueness.pl
create mode 100644 koha-tmpl/intranet-tmpl/prog/en/includes/additem.js.inc
create mode 100644 koha-tmpl/intranet-tmpl/prog/en/modules/services/itemrecorddisplay.tt
create mode 100755 services/itemrecorddisplay.pl
--- a/acqui/check_uniqueness.pl
+++ a/acqui/check_uniqueness.pl
@@ -0,0 +1,70 @@
+#!/usr/bin/perl
+
+# Copyright 2011 BibLibre SARL
+#
+# This file is part of Koha.
+#
+# Koha is free software; you can redistribute it and/or modify it under the
+# terms of the GNU General Public License as published by the Free Software
+# Foundation; either version 2 of the License, or (at your option) any later
+# version.
+#
+# Koha is distributed in the hope that it will be useful, but WITHOUT ANY
+# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
+# A PARTICULAR PURPOSE. See the GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License along
+# with Koha; if not, write to the Free Software Foundation, Inc.,
+# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+
+use Modern::Perl;
+
+use CGI;
+use C4::Context;
+use C4::Output;
+use C4::Auth;
+
+my $input = new CGI;
+my @field = $input->param('field');
+my @value = $input->param('value');
+
+my $dbh = C4::Context->dbh;
+
+my $r;
+my $index = 0;
+for my $f ( @field ) {
+ my $query;
+ given ( $f ) {
+ when ( "barcode" ) {
+ $query = "SELECT barcode FROM items WHERE barcode=?";
+ }
+ when ( "stocknumber" ) {
+ $query = "SELECT stocknumber FROM items WHERE stocknumber=?";
+ }
+ when ( "copynumber" ) {
+ $query = "SELECT copynumber FROM items WHERE copynumber=?";
+ }
+ }
+
+ if($query) {
+ my $sth = $dbh->prepare( $query );
+ $sth->execute( $value[$index] );
+ my @values = $sth->fetchrow_array;
+ if ( @values ) {
+ $r .= "$f:$values[0];";
+ }
+ }
+ $index++;
+}
+
+my ( $template, $loggedinuser, $cookie ) = get_template_and_user(
+ { template_name => "acqui/ajax.tmpl",
+ query => $input,
+ type => "intranet",
+ authnotrequired => 0,
+ debug => 1,
+ }
+);
+$template->param( return => $r );
+
+output_html_with_http_headers $input, $cookie, $template->output;
--- a/acqui/neworderempty.pl
+++ a/acqui/neworderempty.pl
@@ -317,17 +317,12 @@ if ($CGIsort2) {
}
if (C4::Context->preference('AcqCreateItem') eq 'ordering' && !$ordernumber) {
- # prepare empty item form
- my $cell = PrepareItemrecordDisplay('','','','ACQ');
-# warn "==> ".Data::Dumper::Dumper($cell);
- unless ($cell) {
- $cell = PrepareItemrecordDisplay('','','','');
+ # Check if ACQ framework exists
+ my $marc = GetMarcStructure(1, 'ACQ');
+ unless($marc) {
$template->param('NoACQframework' => 1);
}
- my @itemloop;
- push @itemloop,$cell;
-
- $template->param(items => \@itemloop);
+ $template->param(AcqCreateItemOrdering => 1);
}
# Get the item types list, but only if item_level_itype is YES. Otherwise, it will be in the item, no need to display it in the biblio
my @itemtypes;
--- a/acqui/orderreceive.pl
+++ a/acqui/orderreceive.pl
@@ -116,16 +116,12 @@ my ( $template, $loggedinuser, $cookie ) = get_template_and_user(
# prepare the form for receiving
if ( $count == 1 ) {
if (C4::Context->preference('AcqCreateItem') eq 'receiving') {
- # prepare empty item form
- my $cell = PrepareItemrecordDisplay('','','','ACQ');
- unless ($cell) {
- $cell = PrepareItemrecordDisplay('','','','');
+ # Check if ACQ framework exists
+ my $marc = GetMarcStructure(1, 'ACQ');
+ unless($marc) {
$template->param('NoACQframework' => 1);
}
- my @itemloop;
- push @itemloop,$cell;
-
- $template->param(items => \@itemloop);
+ $template->param(AcqCreateItemReceiving => 1);
}
if ( @$results[0]->{'quantityreceived'} == 0 ) {
--- a/koha-tmpl/intranet-tmpl/prog/en/includes/additem.js.inc
+++ a/koha-tmpl/intranet-tmpl/prog/en/includes/additem.js.inc
@@ -0,0 +1,10 @@
+
--- a/koha-tmpl/intranet-tmpl/prog/en/js/additem.js
+++ a/koha-tmpl/intranet-tmpl/prog/en/js/additem.js
@@ -1,110 +1,230 @@
-function deleteItemBlock(index) {
- var aDiv = document.getElementById(index);
- aDiv.parentNode.removeChild(aDiv);
- var quantity = document.getElementById('quantity');
- quantity.setAttribute('value',parseFloat(quantity.getAttribute('value'))-1);
+function addItem( node ) {
+ var index = $(node).parent().attr('id');
+ var current_qty = parseInt($("#quantity").val());
+ var max_qty;
+ if($("#quantity_to_receive").length != 0){
+ max_qty = parseInt($("#quantity_to_receive").val());
+ } else {
+ max_qty = 99999;
+ }
+ if ( $("#items_list table").find('tr[idblock="' + index + '"]').length == 0 ) {
+ if ( current_qty < max_qty ) {
+ if ( current_qty < max_qty - 1 )
+ cloneItemBlock(index);
+ addItemInList(index);
+ $("#quantity").val(current_qty + 1);
+ } else if ( current_qty >= max_qty ) {
+ alert(window.MSG_ADDITEM_JS_CANT_RECEIVE_MORE_ITEMS
+ || "You can't receive any more items.");
+ }
+ } else {
+ if ( current_qty < max_qty )
+ cloneItemBlock(index);
+ var tr = constructTrNode(index);
+ $("#items_list table").find('tr[idblock="' + index + '"]:first').replaceWith(tr);
+ }
+ $("#" + index).hide();
+}
+
+function showItem(index) {
+ $("#outeritemblock").children("div").each(function(){
+ if ( $(this).attr('id') == index ) {
+ $(this).show();
+ } else {
+ if ( $("#items_list table").find('tr[idblock="' + $(this).attr('id') + '"]').length == 0 ) {
+ $(this).remove();
+ } else {
+ $(this).hide();
+ }
+ }
+ });
+}
+
+function constructTrNode(index) {
+ var barcode = $('#' + index).find("[name='kohafield'][value='items.barcode']").prevAll("[name='field_value']")[0];
+ barcode = $(barcode).val();
+ var homebranch = $("#" + index).find("[name='kohafield'][value='items.homebranch']").prevAll("[name='field_value']")[0];
+ homebranch = $(homebranch).val();
+ var loc = $("#" + index).find("[name='kohafield'][value='items.location']").prevAll("[name='field_value']")[0];
+ loc = $(loc).val();
+ var callnumber = $("#" + index).find("[name='kohafield'][value='items.itemcallnumber']").prevAll("[name='field_value']")[0];
+ callnumber = $(callnumber).val();
+ var show_link = ""
+ + (window.MSG_ADDITEM_JS_SHOW || "Show") + " ";
+ var del_link = ""
+ + (window.MSG_ADDITEM_JS_DELETE || "Delete") + " ";
+ var result = "
";
+ result += "" + barcode + " ";
+ result += "" + homebranch + " ";
+ result += "" + loc + " ";
+ result += "" + callnumber + " ";
+ result += "" + show_link + " ";
+ result += "" + del_link + " ";
+ result += " ";
+
+ return result;
}
-function cloneItemBlock(index) {
- var original = document.getElementById(index); //original
- var clone = clone_with_selected(original)
+
+function addItemInList(index) {
+ $("#items_list").show();
+ var tr = constructTrNode(index);
+ $("#items_list table tbody").append(tr);
+}
+
+function deleteItemBlock(node_a, index) {
+ $("#" + index).remove();
+ var current_qty = parseInt($("#quantity").val());
+ var max_qty;
+ if($("#quantity_to_receive").length != 0) {
+ max_qty = parseInt($("#quantity_to_receive").val());
+ } else {
+ max_qty = 99999;
+ }
+ $("#quantity").val(current_qty - 1);
+ $(node_a).parents('tr').remove();
+ if(current_qty - 1 == 0)
+ $("#items_list").hide();
+
+ if ( $("#quantity").val() <= max_qty - 1) {
+ if ( $("#outeritemblock").children("div :visible").length == 0 ) {
+ $("#outeritemblock").children("div:last").show();
+ }
+ }
+ if ( $("#quantity").val() == 0 && $("#outeritemblock > div").length == 0) {
+ cloneItemBlock();
+ }
+}
+
+function cloneItemBlock(index) {
+ var original;
+ if(index) {
+ original = $("#" + index); //original
+ }
+ var dont_copy_fields = ['items.barcode'];
+
var random = Math.floor(Math.random()*100000); // get a random itemid.
- // set the attribute for the new 'div' subfields
- clone.setAttribute('id',index + random);//set another id.
- var NumTabIndex;
- NumTabIndex = parseInt(original.getAttribute('tabindex'));
- if(isNaN(NumTabIndex)) NumTabIndex = 0;
- clone.setAttribute('tabindex',NumTabIndex+1);
- var CloneButtonPlus;
- var CloneButtonMinus;
- // try{
- var jclone = $(clone);
- CloneButtonPlus = $("a.addItem", jclone).get(0);
- CloneButtonPlus.setAttribute('onclick',"cloneItemBlock('" + index + random + "')");
- CloneButtonMinus = $("a.delItem", jclone).get(0);
- CloneButtonMinus.setAttribute('onclick',"deleteItemBlock('" + index + random + "')");
- CloneButtonMinus.setAttribute('style',"display:inline");
- // change itemids of the clone
- var elems = clone.getElementsByTagName('input');
- for( i = 0 ; elems[i] ; i++ )
- {
- if(elems[i].name.match(/^itemid/)) {
- elems[i].value = random;
+ var clone = $("
")
+ $.ajax({
+ url: "/cgi-bin/koha/services/itemrecorddisplay.pl",
+ dataType: 'html',
+ data: {
+ frameworkcode: 'ACQ'
+ },
+ success: function(data, textStatus, jqXHR) {
+ /* Create the item block */
+ $(clone).append(data);
+ /* Change all itemid fields value */
+ $(clone).find("input[name='itemid']").each(function(){
+ $(this).val(random);
+ });
+ /* Add buttons + and Clear */
+ var buttonPlus = '
+ ';
+ var buttonClear = '
' + (window.MSG_ADDITEM_JS_CLEAR || 'Clear') + ' ';
+ $(clone).append(buttonPlus).append(buttonClear);
+ /* Copy values from the original block (input) */
+ $(original).find("input[name='field_value']").each(function(){
+ var kohafield = $(this).siblings("input[name='kohafield']").val();
+ if($(this).val() && dont_copy_fields.indexOf(kohafield) == -1) {
+ $(this).parent("div").attr("id").match(/^(subfield.)/);
+ var id = RegExp.$1;
+ var value = $(this).val();
+ $(clone).find("div[id^='"+id+"'] input[name='field_value']").val(value);
+ }
+ });
+ /* Copy values from the original block (select) */
+ $(original).find("select[name='field_value']").each(function(){
+ var kohafield = $(this).siblings("input[name='kohafield']").val();
+ if($(this).val() && dont_copy_fields.indexOf(kohafield) == -1) {
+ $(this).parent("div").attr("id").match(/^(subfield.)/);
+ var id = RegExp.$1;
+ var value = $(this).val();
+ $(clone).find("div[id^='"+id+"'] select[name='field_value']").val(value);
+ }
+ });
+
+ $("#outeritemblock").append(clone);
}
- }
- // }
- //catch(e){ // do nothig if ButtonPlus & CloneButtonPlus don't exist.
- //}
- // insert this line on the page
- original.parentNode.insertBefore(clone,original.nextSibling);
- var quantity = document.getElementById('quantity');
- quantity.setAttribute('value',parseFloat(quantity.getAttribute('value'))+1);
+ });
+}
+
+function clearItemBlock(node) {
+ var index = $(node).parent().attr('id');
+ var block = $("#"+index);
+ $(block).find("input[type='text']").each(function(){
+ $(this).val("");
+ });
+ $(block).find("select").each(function(){
+ $(this).find("option:first").attr("selected", true);
+ });
}
+
function check_additem() {
- var barcodes = document.getElementsByName('barcode');
- var success = true;
- for(i=0;i
j) && (barcodes[i].value == barcodes[j].value) && barcodes[i].value !='') {
- barcodes[i].className='error';
- barcodes[j].className='error';
- success = false;
- }
- }
- }
- // TODO : Add AJAX function to test against barcodes already in the database, not just
- // duplicates within the form.
- return success;
+ var success = true;
+ var array_fields = ['items.barcode'];
+ var url = '../acqui/check_uniqueness.pl?'; // Url for ajax call
+ $(".error").empty(); // Clear error div
+
+ // Check if a value is duplicated in form
+ for ( field in array_fields ) {
+ var fieldname = array_fields[field].split('.')[1];
+ var values = new Array();
+ $("[name='kohafield'][value="+array_fields[field]+"]").each(function(){
+ var input = $(this).prevAll("input[name='field_value']")[0];
+ if($(input).val()) {
+ values.push($(input).val());
+ url += "field=" + fieldname + "&value=" + $(input).val() + "&"; // construct url
+ }
+ });
+
+ var sorted_arr = values.sort();
+ for (var i = 0; i < sorted_arr.length - 1; i += 1) {
+ if (sorted_arr[i + 1] == sorted_arr[i]) {
+ $(".error").append(
+ fieldname + " '" + sorted_arr[i] + "' "
+ + (window.MSG_ADDITEM_JS_IS_DUPLICATE || "is duplicated")
+ + " ");
+ success = false;
+ }
+ }
+ }
+
+ // If there is a duplication, we raise an error
+ if ( success == false ) {
+ $(".error").show();
+ return false;
+ }
+
+ // Else, we check in DB
+ var xmlhttp = null;
+ xmlhttp = new XMLHttpRequest();
+ if ( typeof xmlhttp.overrideMimeType != 'undefined') {
+ xmlhttp.overrideMimeType('text/xml');
+ }
+
+ xmlhttp.open('GET', url, false);
+ xmlhttp.send(null);
+
+ xmlhttp.onreadystatechange = function() {
+ if (xmlhttp.readyState == 4 && xmlhttp.status == 200) {} else {}
+ };
+ var response = xmlhttp.responseText;
+ var elts = response.split(';');
+ if ( response.length > 0 && elts.length > 0 ) {
+ for ( var i = 0 ; i < elts.length - 1 ; i += 1 ) {
+ var fieldname = elts[i].split(':')[0];
+ var value = elts[i].split(':')[1];
+ $(".error").append(
+ fieldname + " '" + value + "' "
+ + window.MSG_ADDITEM_JS_ALREADY_EXISTS_IN_DB || "already exists in database"
+ + " "
+ );
+ }
+ success = false;
+ }
+
+ if ( success == false ) {
+ $(".error").show();
+ }
+ return success;
}
-function clone_with_selected (node) {
- var origin = node.getElementsByTagName("select");
- var tmp = node.cloneNode(true)
- var selectelem = tmp.getElementsByTagName("select");
- for (var i=0; i
+[% INCLUDE 'additem.js.inc' %]
+
[% INCLUDE 'header.inc' %]
@@ -18,10 +52,11 @@
Receive items from : [% name %] [% IF ( invoice ) %][[% invoice %]] [% END %] (order #[% ordernumber %])
[% IF ( count ) %]
-
[% ELSE %]
--- a/koha-tmpl/intranet-tmpl/prog/en/modules/services/itemrecorddisplay.tt
+++ a/koha-tmpl/intranet-tmpl/prog/en/modules/services/itemrecorddisplay.tt
@@ -0,0 +1,25 @@
+
+ [% FOREACH iteminfo IN iteminformation %]
+
+
+
+ [% iteminfo.subfield %] -
+ [% IF ( iteminfo.mandatory ) %]
+
+ [% END %]
+ [% iteminfo.marc_lib %]
+ [% IF ( iteminfo.mandatory ) %]
+ *
+ [% END %]
+
+ [% iteminfo.marc_value %]
+
+
+
+
+
+
+
+ [% END %]
+
+
--- a/services/itemrecorddisplay.pl
+++ a/services/itemrecorddisplay.pl
@@ -0,0 +1,58 @@
+#!/usr/bin/perl
+
+# Copyright 2011 BibLibre SARL
+# This file is part of Koha.
+#
+# Koha is free software; you can redistribute it and/or modify it under the
+# terms of the GNU General Public License as published by the Free Software
+# Foundation; either version 2 of the License, or (at your option) any later
+# version.
+#
+# Koha is distributed in the hope that it will be useful, but WITHOUT ANY
+# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
+# A PARTICULAR PURPOSE. See the GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License along
+# with Koha; if not, write to the Free Software Foundation, Inc.,
+# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+
+=head1 NAME
+
+itemrecorddisplay.pl
+
+=head1 DESCRIPTION
+
+Return a HTML form for Item record modification or creation.
+It uses PrepareItemrecordDisplay
+
+=cut
+
+use strict;
+use warnings;
+
+use CGI;
+use C4::Auth;
+use C4::Output;
+use C4::Biblio;
+
+my $input = new CGI;
+my ($template, $loggedinuser, $cookie, $flags) = get_template_and_user( {
+ template_name => 'services/itemrecorddisplay.tmpl',
+ query => $input,
+ type => 'intranet',
+ authnotrequired => 1,
+} );
+
+my $biblionumber = $input->param('biblionumber') || '';
+my $itemnumber = $input->param('itemnumber') || '';
+my $frameworkcode = $input->param('frameworkcode') || '';
+
+my $result = PrepareItemrecordDisplay($biblionumber, $itemnumber, undef, $frameworkcode);
+unless($result) {
+ $result = PrepareItemrecordDisplay($biblionumber, $itemnumber, undef, '');
+}
+
+$template->param(%$result);
+
+output_html_with_http_headers $input, $cookie, $template->output;
+
--