This patch ports LCCN splitting code from Koha 2.2.9 to Koha 3.0
This algorithm has been ported just as it appears on some production
systems. LCCNs that do not split correctly should have a bug opened
and include an exact example so that the regexp's can be adjusted.

This patch also adds code to split DDCNs using the *loosest* possible
interpretation of DDCN rules. On the simple end, the DDCN split
algorithm will handle being passed just a Dewey call number.
However, there may be some unusually complex DDCNs that will not
split properly. These will need to have a bug submitted for them
including a specific example so that the regexp's can be adjusted.

The correct choice of splitting alogrithm is determimed by the
item level classification source (items.cn_source).

Documentation should be updated to reflect these changes. Please include
the bit about complex call numbers and the need of a bug report.

[LL Bug 26]
---
 C4/Labels.pm              |  104 ++++++++++++++++++++++++++++++---------------
 labels/label-print-pdf.pl |   49 ++-------------------
 2 files changed, 75 insertions(+), 78 deletions(-)

diff --git a/C4/Labels.pm b/C4/Labels.pm
index 82d4c6b..3bed6da 100644
--- a/C4/Labels.pm
+++ b/C4/Labels.pm
@@ -28,7 +28,7 @@ use C4::Branch;
 use C4::Debug;
 use C4::Biblio;
 use Text::CSV_XS;
-use Data::Dumper;
+#use Data::Dumper;
 # use Smart::Comments;
 
 BEGIN {
@@ -89,8 +89,6 @@ sub get_label_options {
 }
 
 sub get_layouts {
-
-## FIXME: this if/else could be compacted...
     my $dbh = C4::Context->dbh;
     my @data;
     my $query = " Select * from labels_conf";
@@ -103,9 +101,6 @@ sub get_layouts {
         push( @resultsloop, $data );
     }
     $sth->finish;
-
-    # @resultsloop
-
     return @resultsloop;
 }
 
@@ -208,7 +203,7 @@ sub get_text_fields {
                }
        } else {
     # These fields are hardcoded based on the template for label-edit-layout.pl
-               my @text_fields = (
+            my @text_fields = (
        {
         code  => 'itemtype',
         desc  => "Item Type",
@@ -787,8 +782,8 @@ sub GetLabelItems {
     while ( my $data = $sth->fetchrow_hashref ) {
 
         # lets get some summary info from each item
-        my $query1 = " 
-        select i.*, bi.*, b.*  from items i,biblioitems bi,biblio b 
+        my $query1 = "
+        select i.*, bi.*, b.*  from items i,biblioitems bi,biblio b 
                where itemnumber=? and  i.biblioitemnumber=bi.biblioitemnumber 
and                  
                bi.biblionumber=b.biblionumber"; 
      
@@ -817,7 +812,6 @@ sub GetItemFields {
       barcode title subtitle
       dewey isbn issn author class
       itemtype subclass itemcallnumber
-
     );
     return @fields;
 }
@@ -936,11 +930,56 @@ sub deduplicate_batch {
        return $killed, undef;
 }
 
+sub split_lccn {
+    my ($lccn) = @_;    
+    my ( $ll, $wnl, $dec, $cutter, $pubdate);
+
+    $_ = $lccn;
+
+    # lccn example 'HE8700.7 .P6T44 1983';
+    my    @splits   = m/
+        (^[a-zA-Z]+)            # HE
+        ([0-9]+\.*[0-9]*)             # 8700.7
+        \s*
+        (\.*[a-zA-Z0-9]*)       # P6T44
+        \s*
+        ([0-9]*)                # 1983
+        /x;  
+
+    # strip something occuring spaces too
+    $splits[0] =~ s/\s+$//;
+    $splits[1] =~ s/\s+$//;
+    $splits[2] =~ s/\s+$//;
+
+    # if the regex fails, then just return the whole string, 
+    # better than nothing
+    # FIXME It seems we should handle all cases, have some graceful error 
handling, or at least inform the caller of the failure to split
+    $splits[0] = $lccn if  $splits[0]  eq '' ;
+    return @splits;
+}
+
+sub split_ddcn {
+    my ($ddcn) = @_;
+    $ddcn =~ s/\///g;   # in theory we should be able to simply remove all 
segmentation markers and arrive at the correct call number...
+    $_ = $ddcn;
+    # ddcn example R220.3 H2793Z H32 c.2
+    my @splits = m/^([A-Z]{0,3})                # R (OS, REF, etc. up do three 
letters)
+                    ([0-9]+\.[0-9]*)            # 220.3
+                    \s?                         # space (not requiring 
anything beyond the call number)
+                    ([a-zA-Z0-9]*\.?[a-zA-Z0-9])# cutter number... maybe, but 
if so it is in this position (Z indicates literary criticism)
+                    \s?                         # space if it exists
+                    ([a-zA-Z]*\.?[0-9]*)        # other indicators such as 
cutter for author of literary criticism in this example if it exists
+                    \s?                         # space if ie exists
+                    ([a-zA-Z]*\.?[0-9]*)        # other indicators such as 
volume number, copy number, edition date, etc. if it exists
+                    /x;
+    return @splits;
+}
+
 sub DrawSpineText {
 
     my ( $x_pos, $y_pos, $label_height, $label_width, $fontname, $fontsize, 
$left_text_margin,
-        $text_wrap_cols, $item, $conf_data, $printingtype, $nowrap ) = @_;
-
+        $text_wrap_cols, $item, $conf_data, $printingtype ) = @_;
+    
     # Replaced item's itemtype with the more user-friendly description...
     my $dbh = C4::Context->dbh;
     my %itemtypes;
@@ -960,20 +999,19 @@ sub DrawSpineText {
     my $vPos = ( $y_pos + ( $label_height - $top_text_margin ) );
 
     my @str_fields = get_text_fields($layout_id, 'codes' );
-       my $record = GetMarcBiblio($$item->{biblionumber});
-       # FIXME - returns all items, so you can't get data from an embedded 
holdings field.
-       # TODO - add a GetMarcBiblio1item(bibnum,itemnum) or a 
GetMarcItem(itemnum).
+    my $record = GetMarcBiblio($$item->{biblionumber});
+    # FIXME - returns all items, so you can't get data from an embedded 
holdings field.
+    # TODO - add a GetMarcBiblio1item(bibnum,itemnum) or a 
GetMarcItem(itemnum).
 
     my $old_fontname = $fontname; # We need to keep track of the original font 
passed in...
-    
+    my $cn_source = $$item->{'cn_source'}; 
     for my $field (@str_fields) {
-               $field->{'code'} or warn "get_text_fields($layout_id, 'codes') 
element missing 'code' field";
-               if ($$conf_data->{'formatstring'}) {
-                       $field->{'data'} =  
GetBarcodeData($field->{'code'},$$item,$record) ;
-               } else {
-                       $field->{data} =   $$item->{$field->{'code'}}  ;
-               }
-
+        $field->{'code'} or warn "get_text_fields($layout_id, 'codes') element 
missing 'code' field";
+        if ($$conf_data->{'formatstring'}) {
+                $field->{'data'} =  
GetBarcodeData($field->{'code'},$$item,$record) ;
+        } else {
+                $field->{data} =   $$item->{$field->{'code'}}  ;
+        }
         # This allows us to print the title in italic (oblique) type... (Times 
Roman has a different nomenclature.)
         # It seems there should be a better way to handle fonts in the 
label/patron card tool altogether -fbcit
         ($field->{code} eq 'title') ? (($old_fontname =~ /T/) ? ($fontname = 
'TI') : ($fontname = ($old_fontname . 'O'))) : ($fontname = $old_fontname);
@@ -987,16 +1025,14 @@ sub DrawSpineText {
             $str =~ s/\n//g;
             $str =~ s/\r//g;
             my @strings;
-            if ($field->{code} eq 'itemcallnumber') { # If the field contains 
the call number, we do some special processing on it here...
-                if (($nowrap == 0) || (!$nowrap)) { # wrap lines based on 
segmentation markers: '/' (other types of segmentation markers can be added as 
needed here or this could be added as a syspref.)
-                    while ( $str =~ /\// ) {
-                        $str =~ /^(.*)\/(.*)$/;
-                        unshift @strings, $2;
-                        $str = $1;
-                    }   
-                    unshift @strings, $str;
+            if ($field->{code} eq 'itemcallnumber' and $printingtype eq 'BIB') 
{ # If the field contains the call number, we do some special processing on it 
here...
+                if ($cn_source eq 'lcc') {
+                    @strings = split_lccn($str);
+                } elsif ($cn_source eq 'ddc') {
+                    @strings = split_ddcn($str);
                 } else {
-                    push @strings, $str;    # if $nowrap == 1 do not wrap or 
remove segmentation markers...
+                    # FIXME Need error trapping here; something to be 
informative to the user perhaps -crn
+                    push @strings, $str;
                 }
             } else {
                 $str =~ s/\/$//g;       # Here we will strip out all trailing 
'/' in fields other than the call number...
@@ -1032,8 +1068,8 @@ sub DrawSpineText {
                 PrintText( $hPos, $vPos, $font, $fontsize, $str );
                 $vPos = $vPos - $line_spacer;
             }
-       } 
-       }       #foreach field
+       }
+    }  #foreach field
 }
 
 sub PrintText {
diff --git a/labels/label-print-pdf.pl b/labels/label-print-pdf.pl
index 7d54a6f..8855f9f 100755
--- a/labels/label-print-pdf.pl
+++ b/labels/label-print-pdf.pl
@@ -13,7 +13,6 @@ use PDF::Reuse;
 use PDF::Reuse::Barcode;
 use POSIX;
 use Data::Dumper;
-#use Smart::Comments;
 
 my $DEBUG = 0;
 my $DEBUG_LPT = 0;
@@ -24,8 +23,6 @@ print $cgi->header( -type => 'application/pdf', -attachment 
=> 'barcode.pdf' );
 
 my $spine_text = "";
 
-#warn "label-print-pdf ***";
-
 # get the printing settings
 my $template    = GetActiveLabelTemplate();
 my $conf_data   = get_label_options();
@@ -34,8 +31,6 @@ my $profile     = 
GetAssociatedProfile($template->{'tmpl_id'});
 my $batch_id =   $cgi->param('batch_id');
 my @resultsloop;
 
-#$DB::single = 1;
-
 my $batch_type   = $conf_data->{'type'};
 my $barcodetype  = $conf_data->{'barcodetype'};
 my $printingtype = $conf_data->{'printingtype'};
@@ -112,9 +107,6 @@ my $upperRightY = $page_height;
 
 prMbox( $lowerLeftX, $lowerLeftY, $upperRightX, $upperRightY );
 
-#warn "STARTROW = $startrow\n";
-
-#my $page_break_count = $startrow;
 my $codetype; # = 'Code39';
 
 #do page border
@@ -158,8 +150,6 @@ if ( $DEBUG && $profile->{'prof_id'} ) {
 my $item;
 my ( $i, $i2 );    # loop counters
 
-# big row loop
-
 #warn " $lowerLeftX, $lowerLeftY, $upperRightX, $upperRightY";
 #warn "$label_rows, $label_cols\n";
 #warn "$label_height, $label_width\n";
@@ -175,30 +165,17 @@ if ( $start_label eq 1 ) {
 }
 
 else {
-
-    #eval {
     $rowcount = ceil( $start_label / $label_cols );
-
-    #} ;
-    #$rowcount = 1 if $@;
-
     $colcount = ( $start_label - ( ( $rowcount - 1 ) * $label_cols ) );
-
     $x_pos = $left_margin + ( $label_width * ( $colcount - 1 ) ) +
       ( $colspace * ( $colcount - 1 ) );
-
     $y_pos = $page_height - $top_margin - ( $label_height * $rowcount ) -
       ( $rowspace * ( $rowcount - 1 ) );
-
     warn "Start label specified: $start_label Beginning in row $rowcount, 
column $colcount" if $DEBUG;
     warn "X position = $x_pos Y position = $y_pos" if $DEBUG;
     warn "Rowspace = $rowspace Label height = $label_height" if $DEBUG;
 }
 
-#warn "ROW COL $rowcount, $colcount";
-
-#my $barcodetype; # = 'Code39';
-
 #
 #    main foreach loop
 #
@@ -222,7 +199,7 @@ foreach $item (@resultsloop) {
         DrawBarcode( $x_pos, $barcode_y, $barcode_height, $label_width,
             $item->{'barcode'}, $barcodetype );
         DrawSpineText( $x_pos, $y_pos, $label_height, $label_width, $fontname, 
$fontsize,
-            $left_text_margin, $text_wrap_cols, \$item, \$conf_data, 
$printingtype, '1' );
+            $left_text_margin, $text_wrap_cols, \$item, \$conf_data, 
$printingtype );
 
         CalcNextLabelPos();
 
@@ -233,7 +210,7 @@ foreach $item (@resultsloop) {
         DrawBarcode( $x_pos, $y_pos, $barcode_height, $label_width, 
$item->{'barcode'},
             $barcodetype );
         DrawSpineText( $x_pos, $y_pos, $label_height, $label_width, $fontname, 
$fontsize,
-            $left_text_margin, $text_wrap_cols, \$item, \$conf_data, 
$printingtype, '1' );
+            $left_text_margin, $text_wrap_cols, \$item, \$conf_data, 
$printingtype );
 
         CalcNextLabelPos();
     }
@@ -245,7 +222,7 @@ foreach $item (@resultsloop) {
         CalcNextLabelPos();
         drawbox( $x_pos, $y_pos, $label_width, $label_height ) if $guidebox;
         DrawSpineText( $x_pos, $y_pos, $label_height, $label_width, $fontname, 
$fontsize,
-            $left_text_margin, $text_wrap_cols, \$item, \$conf_data, 
$printingtype, '1' );
+            $left_text_margin, $text_wrap_cols, \$item, \$conf_data, 
$printingtype );
 
         CalcNextLabelPos();
     }
@@ -254,7 +231,7 @@ foreach $item (@resultsloop) {
     elsif ( $printingtype eq 'BIB' ) {
         drawbox( $x_pos, $y_pos, $label_width, $label_height ) if $guidebox;
         DrawSpineText( $x_pos, $y_pos, $label_height, $label_width, $fontname, 
$fontsize,
-            $left_text_margin, $text_wrap_cols, \$item, \$conf_data, 
$printingtype, '0' );
+            $left_text_margin, $text_wrap_cols, \$item, \$conf_data, 
$printingtype );
         CalcNextLabelPos();
     }
 
@@ -268,7 +245,7 @@ foreach $item (@resultsloop) {
             $patron_data->{'branchname'}   => ($fontsize + 3),
         };
 
-        warn "Generating patron card for cardnumber 
$patron_data->{'cardnumber'}";
+        $DEBUG and warn "Generating patron card for cardnumber 
$patron_data->{'cardnumber'}";
 
         drawbox( $x_pos, $y_pos, $label_width, $label_height ) if $guidebox;
         my $barcode_height = $label_height / 2.75; #FIXME: Scaling barcode 
height; this needs to be a user parameter.
@@ -278,25 +255,9 @@ foreach $item (@resultsloop) {
             $left_text_margin, $text_wrap_cols, $text, $printingtype );
         CalcNextLabelPos();
     }
-
-
-
-
-
-
-
-
-
-
-
 }    # end for item loop
 prEnd();
 
-#
-#
-#
-#
-#
 sub CalcNextLabelPos {
     if ( $colcount lt $label_cols ) {
 
-- 
1.5.5.GIT

_______________________________________________
Koha-patches mailing list
[email protected]
http://lists.koha.org/mailman/listinfo/koha-patches

Reply via email to