

package ExoSeq2;
use Tk;
use strict;
use BarcodeRevised;
use Checkbarcode;


my $BITMAP_DIR = "$ENV{'BADGER'}/lib/platetrack/bitmaps";


sub new{
    my $pkg = shift;

    # Fonts
    my $setup	= { "title_f"       => "*-times-bold-r-normal--*-180-*-*-p-*-*-*",
		    "entry_f"       => "-adobe-helvetica-medium-r-normal--17-120-100-100-p-88-iso8859-1",
		    "button_f"      => "-adobe-helvetica-bold-r-normal--17-120-100-100-p-92-iso8859-1",
		    "label_f"       => "-adobe-helvetica-bold-r-normal--14-100-100-100-p-82-iso8859-1",
		    "plate_f"       => "-adobe-helvetica-medium-r-normal--10-100-75-75-p-56-iso8859-1",
		    "tiny_f"        => "-adobe-helvetica-medium-r-normal--8-80-75-75-p-46-iso8859-1",
		    "plate_b_f"     => "-adobe-helvetica-bold-r-normal--10-100-75-75-p-60-iso8859-1",
		    "barcode_entry" => "pale green",
		    "pass"          => "light blue",
		    "fail"          => "lemonchiffon2",
		    
	       };
    
    bless ($setup, $pkg);
    return $setup;
}


sub make_mainwindow{
    
    ##### define main window
     my $pkg = shift;
    $pkg->{mw} = MainWindow->new;
    
    $pkg->{mw}->configure(cursor  => 'hand2');
    $pkg->{mw}->wm('minsize', 480, 410); 
    $pkg->{mw}->wm('maxsize', 1300, 1000);
    
    
    $pkg->{mw}->bind('<Alt-Key-q>' => sub {
	
	exit(0);
    });
}


sub wait{

    ##### make a wait box
    my ($pkg) = @_;
    
    my $wd = $pkg->{mw}->WaitBox(
				  -title => 'Please wait...',
				  );
    $wd->wm('minsize', 120, 30);
    $wd->wm('maxsize', 120, 30);
    my $f = $wd->Frame(-height => 30, -width => 120);
    $f->pack();
    $pkg->{mw}->idletasks();
    $wd->packPropagate(0);
    $wd->idletasks();

    return($wd);
}

sub header{

     ##### make title and message box

    my ($pkg) =shift;
    
    my $title_frame = $pkg->{mw}->Frame(-borderwidth => '6');
    $title_frame->pack(-side => 'top',
		       -fill => 'x'
		       );
    
    my $title;
    if(@_){
	$title = shift;
    }
    else{
	warn "no title specified\n";
    }
    ##### create title
    $pkg->{header} = $title_frame->Label(
					-font             =>  $pkg->{title_f},
					-text             =>  $title,
					)->pack(-side => 'top');

    ##### create message box
    $pkg->{message} = $title_frame->ScrlListbox(
						-bg          => 'white',
						-scrollbars  => 'e',
						-height      => 5,
						-width       => 30
						)->pack(-side => 'top', -fill => 'x');
    


}


sub user_boxes{

    #### generic logon/logoff boxes
    my ($pkg) = @_;

    ######## make frame
    my $user_frame  = $pkg->{mw}->Frame(-borderwidth => '6');
    $user_frame->pack(-side => 'top',
		      -expand => 'no', 
		      -fill => 'x');
    
    
    ####### header box
    my $title = "User";
    my $bc_user_title = $user_frame->Entry(
					   -state            => 'disabled',
					   -width            =>  5,
					   -font             =>  $pkg->{title_f},
					   -textvariable     =>  \$title
					   )->pack(-side     => 'left');
    
    ####### bc entry box
    $pkg->{bc_user_label} = $user_frame->Entry(
					       -width            => 10,
					       -font             => $pkg->{button_f},
					       -textvariable     => \$pkg->{user_bc}, 
					       -bg               => $pkg->{barcode_entry},
					       )->pack(-side => 'left');
    $pkg->{bc_user_label}->grab();
    $pkg->{bc_user_label}->focusForce();
 

    
    $pkg->{logout_button} = $user_frame->Button(
						-font                   => $pkg->{button_f},
						-fg                     => 'purple',
						-activebackground       => 'black',
						-activeforeground       => 'white',   
						-text                   => "Logout",
						
						)->pack(-side => 'right');
    
    
   
    return ($pkg->{bc_user_label});

}




sub update_mess {

    #### add to bottom of message box
    my ($pkg) = shift;
    my (@update_contents)= shift;
    $pkg->{message}->insert('end', @update_contents);
    $pkg->{message}->see('end'); 
    $pkg->{message}->update('idletasks');
}
sub clear_mess{

    #### empty message box
    my ($pkg) = shift;
    $pkg->{message}->delete ('0', 'end');
    $pkg->update_mess("Window cleared.");

}



     
sub make_grid {
    
    ###### supply list of titles to make generic grid with $pos{GRID_ROWS} rows
    
    my ($pkg) = shift;
    my ($titles, $DATA, $pos, $window, $grid_name) = @_;
    
    if ( $window eq undef ) {
	$window = 'mw';
    }
    
    if ( $grid_name eq undef ) {
	$grid_name = 'entrywidget';
    }

    my $grid_frame = $pkg->{$window}->Frame(-borderwidth => '6');
    $grid_frame->pack(-side => 'bottom',
		      -expand => 'no', 
		      -fill => 'x');
    
    my $gridt_frame = $pkg->{$window}->Frame(-borderwidth => '6');
    $gridt_frame->pack(-side => 'bottom',
		       -expand => 'no', 
		       -fill => 'x');
    
    
    my $len = scalar @{$titles};
    my $width;
    if($$pos{width}){
	$width = $$pos{width};
    }
    else{
	$width =12;
    }
    
    my $grid_titles = $grid_name."_titles";

    foreach my $title_column (0 .. ($len-1)){
	
	$pkg->{$grid_titles}->[$title_column] = $gridt_frame->Entry(
							  -width => $width,
							  -textvariable => \$titles->[$title_column],
							  -font => $pkg->{button_f},
							  -background => 'white',
							  -state => 'disabled');
	
	$pkg->{$grid_titles}->[$title_column]->grid(-row => 1, -column => $title_column+1, -sticky => 'w');
	
    }
    
    my $row;
    my $c;
    my $entry_width = 12;
  
    
    for ($row=0;$row<$$pos{GRID_ROWS};$row++) {
	foreach $c (0 .. ($len-1)) {
	    
	    $pkg->{$grid_name}->[$row]->[$c] = $grid_frame->Entry(-width => $width,
							    -font => $pkg->{entry_f},
							    -state => 'disabled',
							    -selectbackground=> 'white',
							    );
	    $pkg->{$grid_name}->[$row]->[$c]->grid(-row => $row, -column => $c, -sticky => 'w');
	    $pkg->{$grid_name}->[$row]->[$c]->configure(-textvariable => \$DATA->[$$pos{SECT}]->[$row]->[$c]);
	    
	    
	}
    }
    
    return($pkg->{$grid_name});
    
}

sub bc_entry {
    


    ### make a box to scan in entities
    
    my ($pkg) = shift;

    if(@_){
	
	$pkg->{bc_title} = shift;;   ### allow for static or changing title
    }
    
    my $bc_frame = $pkg->{mw}->Frame(-borderwidth => '6');
    $bc_frame->pack(-side => 'top',
		    -fill => 'x'
		    );
    

    #### entry box for plate id
    
    my $plate_title = $bc_frame->Entry(
				       -state            => 'disabled',
				       -background       =>  'white',
				       -width            => 15,
				       -font             => $pkg->{title_f},
				       -textvariable     => \$pkg->{bc_title},
				      )->pack(side      => 'left');
    
    
    

    $pkg->{bc_label} = $bc_frame->Entry(
					  -width        => 10,
					  -font         => $pkg->{button_f},
					  -textvariable => \$pkg->{bc},
					  -bg           => 'grey85'
					  )->pack(side => 'left');

    $pkg->{page_tag} = "1 of 1"; ### keep track of where we are
    my $page_title = $bc_frame->Entry(
				      -state            => 'disabled',
				      -width            => 8,
				      -font             => $pkg->{title_f},
				      -textvariable     =>  \$pkg->{page_tag},
				      )->pack(side      => 'right');
    
    return($pkg->{bc_label} );
    
}



sub bc_entry_only {
    
    ### make a box to scan in entities
    
    my ($pkg) = shift;

    if(@_){
	$pkg->{bc_title} = shift;;   ### allow for static or changing title
    }
    
    my $bc_frame = $pkg->{mw}->Frame(-borderwidth => '6');
    $bc_frame->pack(-side => 'top',
		    -fill => 'x'
		    );
    

    #### entry box for plate id
    
    my $plate_title = $bc_frame->Entry(
				       -state            => 'disabled',
				       -background       =>  'white',
				       -width            => 15,
				       -font             => $pkg->{label_f},
				       -textvariable     => \$pkg->{bc_title},
				      )->pack(side      => 'left');
    

    $pkg->{bc_label} = $bc_frame->Entry(
					  -width        => 10,
					  -font         => $pkg->{button_f},
					  -textvariable => \$pkg->{bc},
					  -bg           => 'grey85'
					  )->pack(side => 'left');

    return($pkg->{bc_label} );
    
}


sub remark_entry {

    my ($pkg) = shift;

    ### frame for title and entry box

    my $rem_frame = $pkg->{mw}->Frame(-borderwidth => '6');
    $rem_frame->pack(-side => 'top',
		     -fill => 'x'
		     );

    ### title box

    my $title = 'Remark';

    my $rem_title = $rem_frame->Entry( -state            => 'disabled',
				       -background       => 'white',
				       -width            => 15,
				       -font             => $pkg->{title_f},
				       -textvariable     => \$title,
				      )->pack(side => 'left');

    $pkg->{rem_entry} = $rem_frame->Entry( -state          => 'disabled',
					   -width          => 25,
					   -font           => $pkg->{button_f},
					   -textvariable   => \$pkg->{remark}
					   )->pack(side => 'left');

    return ($pkg->{rem_entry});

}


sub make_button_frame{

    #### make frame a botton to hold buttons
    my ($pkg) = shift;
                            
    $pkg->{button_frame} = $pkg->{mw}->Frame(-borderwidth => '6');
    $pkg->{button_frame}->pack(-side => 'bottom',
			       -fill => 'x'
			       );


}


sub make_quit_button{

    my ($pkg) = shift;

    my ($side) = @_;

    if ( $side eq undef ) {
	$side = 'right';
    }

    unless(defined $pkg->{button_frame}){$pkg->make_button_frame();}

    my $quit_button = $pkg->{button_frame}->Button(
					    -font                   => $pkg->{button_f},
					    -fg                     => 'purple',
					    -activebackground       => 'black',
					    -activeforeground       => 'white',   
					    -text                   => "Quit<alt-q>",
					    -command                => sub{$pkg->{mw}->destroy;}
					    )->pack(-side => $side);
    return($quit_button);
}

sub make_clear_button{
    
    my ($pkg) = shift;

    unless(defined $pkg->{button_frame}){$pkg->make_button_frame();}

    $pkg->{clear_button} = $pkg->{button_frame}->Button(
						    -font                   => $pkg->{button_f},
						    -fg                     => 'purple',
						    -activebackground       => 'black',
						    -activeforeground       => 'white',   
						    -text                   => "Clear All",
						    )->pack(-side => 'right');
    return($pkg->{clear_button});
}


sub make_clear_last_button{
    
    my ($pkg) = shift;

    unless(defined $pkg->{button_frame}){$pkg->make_button_frame();}

     $pkg->{clear_last_button} = $pkg->{button_frame}->Button(
							 -font                   => $pkg->{button_f},
							 -fg                     => 'purple',
							 -activebackground       => 'black',
							 -activeforeground       => 'white',   
							 -text                   => "Clear Last",
							
							 )->pack(-side => 'right');
    
    return($pkg->{clear_last_button});
}




sub make_printer_button{


    my ($pkg) = shift;

    unless(defined $pkg->{button_frame}){$pkg->make_button_frame();}
    
    my $printer_button = $pkg->{button_frame}->Button(
						      -font                   => $pkg->{button_f},
						      -fg                     => 'purple',
						      -activebackground       => 'black',
						      -activeforeground       => 'white',   
						      -text                   => "Printer",
						   
						      )->pack(-side => 'left');
    return($printer_button);
}

sub make_update_button{
    
    
    my ($pkg) = shift;

    unless(defined $pkg->{button_frame}){$pkg->make_button_frame();}
    
    my $update_button = $pkg->{button_frame}->Button(
					      -font                   => $pkg->{button_f},
					      -fg                     => 'purple',
					      -activebackground       => 'black',
					      -activeforeground       => 'white',   
					      -text                   => "Update",
					     
					      )->pack(-side => 'right');
    my $balloon = $pkg->{button_frame}->Balloon( -background       =>   'white');
    
    $balloon->attach($update_button,
		     -balloonmsg => 'Update database and create labels',
		     );

    return($update_button);

}

sub make_up_button{
	
    
    my ($pkg) = shift;
    
    unless(defined $pkg->{button_frame}){$pkg->make_button_frame();}
    # Make an 'up-button';
    $pkg->{mw}->Bitmap('up',
			-file => "$BITMAP_DIR/uarrw.xbm",
			-maskfile => "$BITMAP_DIR/uarrw.xbm"
			);
    my $upButton = $pkg->{button_frame}->Button( -image   => 'up', 
						 )->pack(-side => 'left'); 
    
    return($upButton);
}

sub make_down_button{
	
    
    my ($pkg) = shift;

# Make a 'down-button';
    $pkg->{mw}->Bitmap('down',
		       -file => "$BITMAP_DIR/darrw.xbm",
		       -maskfile => "$BITMAP_DIR/darrw.xbm"
		       );
    
    my $downButton = $pkg->{button_frame}->Button( 
						   -image => 'down', 
						   )->pack(-side => 'left');
    
    
    return($downButton);
    
}







sub gridUpdate {
    
    
    my ($pkg) = shift;
    my ($DATA, $pos, $grid_name, $page) = @_;

    if ( $grid_name eq undef ) {
	$grid_name = 'entrywidget';
    }

    if ( $page eq undef ) {
	$page = 'page_tag';
    }

    $pkg->{$page} = "$$pos{SECT} of $$pos{lastSECT}"; 
    my $nrows;
    warn "updating grid $pkg->{$page} $$pos{SECT} $$pos{nrows}\n";
    for ($nrows=0;$nrows< $$pos{GRID_ROWS};$nrows++) {
	
	foreach my $c (0 .. ($$pos{cols} -1)) {
	    
	    $pkg->{$grid_name}->[$nrows]->[$c]->configure(-textvariable =>
						    \$DATA->[$$pos{SECT}]->[$nrows]->[$c]);
	}
    }	
    
} 


sub make_childwindow {
    
    my ($pkg) = shift;
    my ($win_name, $title) = @_;
    $pkg->{$win_name} = $pkg->{mw}->Toplevel();

    $pkg->{$win_name}->configure(-title => $title);

}


sub display_plate {

    my ($pkg) = shift;
    my ($name, $layout, %contents) = @_;

    my (%pl_pos, $rows, $cols, @headings);
    
    if ( $layout = 96 ) {
	$rows = 8;
	$cols = 12;

	%pl_pos = ( "nrows"     => 0,           ### current row to insert in
		    "SECT"      => 1,           ### current section viewed
		    "lastSECT"  => 1,           ### current section to insert in
		    "cols"      => $cols + 1,   ### num columns - static
		    "GRID_ROWS" => $rows,       ### num rows  - static
		    "width"     => 8,
		    );
    }

    ### column numbers for headings
    push(@headings, '');
    for (my $i=1; $i<=$cols; $i++) {
	push(@headings, $i);
    }

    my $DATA = [ [] ];

    ### put data from hash into 2D array (row by row)
    for (my $i=0; $i<=$rows; $i++) {
	$DATA->[1]->[$i]->[0] = chr($i+97);
	for ( my $j=1; $j<=$cols; $j++) {

	    my $well = chr($i+97) . $j;
	    if ( %contents->{$well} ne undef ) {
		$DATA->[1]->[$i]->[$j] = %contents->{$well}->[0];
	    }
	    else {
		$DATA->[1]->[$i]->[$j] = '----';
	    }
	}
    }

    my $win_name = 'plate';

    $pkg->make_childwindow($win_name, $name);

    my $close_button = $pkg->{$win_name}->Button( -font                   => $pkg->{button_f},
						  -fg                     => 'purple',
						  -activebackground       => 'black',
						  -activeforeground       => 'white',   
						  -text                   => "Close",
						  -command                => sub{$pkg->{$win_name}->destroy}
    )->pack(-side => 'bottom'); 



    $pkg->make_grid(\@headings, $DATA, \%pl_pos, $win_name, 'plate_grid');

    
    for (my $j=0; $j<$cols; $j++) {
	$pkg->{plate_grid_titles}->[$j]->configure(-font => $pkg->{label_f});
	for ( my $i=0; $i<$rows; $i++) {
	    $pkg->{plate_grid}->[$i]->[$j]->configure(-font => $pkg->{label_f});
	}
    }

####    $pkg->{plate}->withdraw();


}


sub make_gel_score {

    ## number of lanes, number of rows, contents of dropdown, identifier for each lane




}


1;



