#!/pro/bin/perl

# csv2tk: show CSV file in Tk::TableMatrix::Spreadsheet
#	  (m)'04 [01-04-2004]

$VERSION = "1.0";

use strict;
use warnings;

sub usage ()
{
    print STDERR
	"usage: csv2tk [-s <sep>] [-q <quot>] [-w <width>] [X11 options] [file.csv]\n",
	"       -s <sep>   use <sep>   as seperator char. Default = ';'\n",
	"       -q <quot>  use <quot>  as quotation char. Default = '\"'\n",
	"       -w <width> use <width> as default column width (4)\n";
    exit;
    } # usage

@ARGV == 1 and $ARGV[0] eq "-?" || $ARGV[0] =~ m/^-+help$/ and usage ();

use Getopt::Long qw(:config bundling nopermute passthrough);
my $sep = ';';	# Yeah I know it should be a ',' (hence Csv), but the majority
		# of the csv files to be shown comes from fucking Micky$hit,
		# that uses semiColon ';' instead.
my $quo = '"';
my $wdt = 4;	# Default minimal column width

GetOptions (
    "c=s"	=> \$sep,
    "q=s"	=> \$quo,
    "w=i"	=> \$wdt,
    ) or usage;

use Tk;
use Tk::TableMatrix::Spreadsheet;

# This will allow ~/.Xdefaults to have lines like
#Csv2tk*font:	-misc-fixed-medium-r-semicondensed--12-110-75-75-c-60-iso10646-1
Tk::CmdLine->LoadResources ();
# This will allow calls like # csv2tk -fg Blue4 shit.csv
Tk::CmdLine->SetArguments ();

# Don't split ourselves when modules do it _much_ better, and follow the standards
use Text::CSV_XS;
my $csv = Text::CSV_XS-> new ({ sep_char => $sep, quote_char => $quo, binary => 1 });

my ($h, $w, @w) = (0, 1); # data height, -width, and default column widths
my $data;
while (<>) {
    $csv->parse ($_);
    my @row = $csv->fields () or next;
    @row > $w and push @w, ($wdt) x (($w = @row) - @w);
    foreach my $c (0 .. $#row) {
	$data->{"$h,$c"} = $row[$c];
	$h && $row[$c] or next;
	my $l = length ($row[$c]);
	$l > $w[$c] and $w[$c] = $l;
	}
    ++$h % 100 or printf STDERR "%6d x %6d\r", $w, $h;
    }
printf STDERR "%6d x %6d\n", $w, $h;

my $ss = MainWindow->new->Scrolled ('Spreadsheet',
    -rows	=> $h,		-cols		=> $w,
    -width	=> 10,		-height		=> 20,
    -titlerows	=>  1,		-titlecols	=>  0,

    -selectmode		=> "extended",
    -resizeborders	=> "both",

    -justify		=> "left",
    -anchor		=> "w",

    -variable		=> $data,
    )->pack (-expand => 1, -fill => "both");
$ss->tagConfigure ("title",  -bg => "#ffffe0", -justify => "left");
$ss->tagConfigure ("active", -bg => "gray95",  -justify => "left");

# autosize columns on data (not on headers)
$ss->colWidth (map { $_ => $w[$_] } 0 .. $#w);

MainLoop;
