/usr/local/CPAN/Tk-TM/Tk/TM/wApp.pm
#!perl -w
#
# Tk Transaction Manager.
# Application window.
#
# makarow, demed
#
use Tk::TM::Lib;
package Tk::TM::wApp;
require 5.000;
use strict;
use Tk::Tree;
use vars qw($VERSION @ISA @EXPORT @EXPORT_OK %EXPORT_TAGS);
$VERSION = '0.53';
@ISA = ('Tk::MainWindow');
@EXPORT_OK = qw(DBILogin);
my $PathLast ='0';
my $PathOpen =undef;
1;
#######################
sub new {
my $class=shift;
my $self =new Tk::MainWindow(@_);
bless $self,$class;
$self->initialize(@_);
}
#######################
sub initialize {
my $self = shift;
my $tmp =$self->Menubutton();
my $fnt =$tmp->cget(-font);
$tmp->destroy;
$self->{-wgmnu} =$self->tmMenu()->pack(-fill=>'x');
$self->{-wgmnu}->set(-dos=>[]);
my $area =$self->Frame()->pack(-expand=>'yes',-fill=>'both');
$self->{-wgnav} =$area->Scrolled('Tree',-scrollbars=>'se',-font=>$fnt
,-itemtype=>'text'
,-command=>sub{$self->ScrOpen(@_)}
# ,-cursor=>'hand2'
)->pack(-fill=>'y',-side=>'left');
$self->{-wgscr} =$area->Frame(-borderwidth=>2,-relief=>'groove')->pack(-expand=>'yes',-fill=>'both');
$self->{-wgmnu}->set(-wgind=>$self->Label(-anchor=>'w',-relief=>'sunken')->pack(-expand=>'yes',-fill=>'x'));
$self->{-title} =$self->cget(-title);
$self->{-mdnav} ='treee';
$self->{-parm} ={}; $self->{-wgmnu}->set(-parm => $self->{-parm});
$self->ConfigSpecs(-font=>['DESCENDANTS']);
$self->ConfigSpecs(-relief=>['CHILDREN']);
$self->ConfigSpecs(-background=>['CHILDREN']);
$self->ConfigSpecs(-foreground=>['CHILDREN']);
$self->bind('<Key-F6>' ,sub{map {$_->focusForce() if /tree/i} $self->{-wgnav}->children()});
$self->bind('<Shift-F6>',sub{map {$_->focusForce() if /tree/i} $self->{-wgnav}->children()});
$self->{-wgnav}->bind('<Key-F6>' ,sub{$self->{-wgnav}->focusNext()});
$self->{-wgnav}->bind('<Shift-F6>',sub{$self->{-wgnav}->focusPrev()});
$self->bind('<Destroy>',sub{$self->destroybind() if $_[0] && $_[0] eq $self});
$self;
}
#######################
sub destroybind {
my $self =$_[0];
print "destroybind(",join(', ',map {defined($_) ? $_ : 'null'} @_),")\n" if $Tk::TM::Common::Debug;
my $pth0 =$PathOpen; return if !$pth0;
my $dta0 =(defined($pth0) ? $self->{-wgnav}->info('data',$pth0) : undef);
ref($dta0->{-cbcmd}) && $self->Try($dta0->{-cbcmd},$dta0,'stop','',undef);
}
#######################
sub set {
return(keys(%{$_[0]})) if scalar(@_) ==1;
return($_[0]->{$_[1]}) if scalar(@_) ==2;
my ($self, %opt) =@_;
foreach my $k (keys(%opt)) {
$self->{$k} =$opt{$k};
}
$self;
}
#######################
sub setscr {
my ($self, $op, $lbl, $sub, $parm, $opt) =@_;
if (!defined($op) ||$op eq '') {
$PathLast =$PathLast =~/^(.*)\.([^\.]+)$/ ? "$1." .($2 +1) : $PathLast +1
}
elsif ($op eq '+') {
eval {$self->{-wgnav}->setmode($PathLast,'open'); $self->{-wgnav}->open($PathLast)};
$PathLast =$PathLast .'.0'
}
elsif ($op =~/^\d/) {
my @a =split(/\./, $PathLast);
eval {$self->{-wgnav}->setmode($PathLast,'open'); $self->{-wgnav}->open($PathLast)}
if $#a <$op;
$a[$op] +=1;
$PathLast =join('.',@a[0..$op])
}
if ($lbl =~/^Login$/ && !ref($sub)) {
$lbl =Tk::TM::Lang::txtMsg($lbl);
$sub =\&DBILogin;
}
$opt ={} if !defined($opt);
$opt->{-cbcmd} =$sub;
$opt->{-cbnme} =$sub;
$opt->{-label} =$lbl;
$opt->{-title} ='';
$opt->{-parm} =(ref($parm) ? $parm : {});
$opt->{-parmc} =$self->{-parm}; # common to app parameters
$opt->{-dos} =undef;
$opt->{-do} =undef; # 1-st data object, autoset
# {-reread} =undef; # reread master always if not current
$opt->{-rereadc}=undef; # reread master toggle, autoclear
$opt->{-wgapp} =$self;
$opt->{-wgmnu} =$self->{-wgmnu};
$opt->{-wgscr} =$self->{-wgscr};
$self->{-wgnav}->add($PathLast,-text=>$lbl,-data=>$opt);
}
#######################
sub Try {
my ($self,$sub) =(shift,shift);
my $ret =ref($sub) eq 'CODE' ? eval {&{$sub}(@_)} : $sub;
print "Try(",join(',',map {defined($_) ? $_ : 'null'} @_),")->",defined($ret) ? $ret : 'null',"\n" if $Tk::TM::Common::Debug;
$self->messageBox(-icon=>'error',-type=>'Ok',-title=>Tk::TM::Lang::txtMsg('Error')
,-message=> $@) if $@;
$ret
}
#######################
sub ScrOpen {
print "ScrOpen(",join(', ',map {defined($_) ? $_ : 'null'} @_),")\n" if $Tk::TM::Common::Debug;
my ($self, $pth1) =@_;
my $dta1 =$self->{-wgnav}->info('data',$pth1);
my $pthM =($pth1 =~/^(.*)\.([^\.]+)$/ ? $1 : undef);
my $dtaM =(defined($pthM) ? $self->{-wgnav}->info('data',$pthM) : undef);
my $pth0 =$PathOpen;
my $dta0 =(defined($pth0) ? $self->{-wgnav}->info('data',$pth0) : undef);
if (!defined($dta1->{-cbnme})) {return($pth0)} # grouping only
if (defined($pth0) && $pth0 eq $pth1 ) {return($pth0)} # the same screen
if (defined($pthM) && !defined($dtaM->{-cbnme})) {$pthM =$dtaM =undef}
if ($self->{-mdnav} =~/tree/i && defined($pthM) && defined($dtaM->{-cbnme})
&& !ref($dtaM->{-dos})) {return($pth0)}
if ($self->{-mdnav} =~/treee/i && defined($pthM) && defined($dtaM->{-cbnme})
&& substr($pth0 ||'',0,length($pthM)) ne $pthM) {return($pth0)}
if (defined($pth0)) {
$dta0->{-do} =ref($dta0->{-dos}) ? $dta0->{-dos}->[0] : undef;
$self->{-wgmnu}->Stop('#save#force');
my $rstp =ref($dta0->{-cbcmd}) ? $self->Try($dta0->{-cbcmd},$dta0,'stop','',$dta1) : 1;
if (!$rstp && $self->{-mdnav} =~/tree/i
&& defined($pthM) && defined($pth0) && $pth0 eq $pthM) {
return($pth0)
}
$self->{-wgmnu}->doAll(sub{shift->Sleep('#wgs#dta')});
}
foreach my $w ($self->{-wgscr}->children) {$w->destroy}
if ($self->{-mdnav} =~/tree/i
&& defined($pthM) && defined($pth0) && $pth0 ne $pthM) {
if ($dtaM->{-reread} || $dtaM->{-rereadc}) { # reread master
$dtaM->{-rereadc} =undef;
$self->{-wgmnu}->set(-dos=>($dtaM->{-dos} ? $dtaM->{-dos} : []));
$self->{-wgmnu}->Reread();
$self->{-wgmnu}->doAll(sub{shift->Sleep('#dta')})
}
$dta0 =$dtaM;
}
$self->{-wgmnu}->set(-dos=>(ref($dta1->{-dos}) ? $dta1->{-dos} : []));
$self->configure(-title=>(($dta1->{-title} ne '' ? $dta1->{-title} .' - ' : '') .$dta1->{-label} .' - ' .$self->{-title}));
if (!ref($dta1->{-cbcmd})) {
foreach my $d (($0 =~/^(.+)[\\\/][^\\\/]+$/ ? "$1" : "."), @INC) {
next if !-f "$d/" .$dta1->{-cbnme};
$self->Try(sub{$dta1->{-cbcmd} =do("$d/" .$dta1->{-cbnme}) });
last;
}
}
if (ref($dta1->{-cbcmd})) {
$self->Try($dta1->{-cbcmd},$dta1,'start','',$dta0);
$dta1->{-do} =ref($dta1->{-dos}) ? $dta1->{-dos}->[0] : undef;
# print join(',',$self->{-wgscr}->children()),"\n";
}
$self->{-wgmnu}->set(-dos=>(ref($dta1->{-dos}) ? $dta1->{-dos} : []));
$self->configure(-title=>(($dta1->{-title} ne '' ? $dta1->{-title} .' - ' : '') .$dta1->{-label} .' - ' .$self->{-title}));
$PathOpen =$pth1
}
#######################
sub Start {
my $self =shift;
my @chld =$self->{-wgnav}->info('children');
$PathOpen =$chld[0];
my $dta =$self->{-wgnav}->info('data',$PathOpen);
$self->Try($dta->{-cbcmd},$dta,'start','');
$dta->{-do} =ref($dta->{-dos}) ? $dta->{-dos}->[0] : undef;
$self->{-wgmnu}->set(-dos=>(ref($dta->{-dos}) ? $dta->{-dos} : []));
$self->configure(-title=>(($dta->{-title} ne '' ? $dta->{-title} .' - ' : '') .$dta->{-label} .' - ' .$self->{-title}));
}
#######################
sub DBILogin {
print "DBILogin(",join(', ',map {defined($_) ? $_ : 'null'} @_),")\n" if $Tk::TM::Common::Debug;
my ($self, $cmd) =@_;
return(1) if $cmd !~/start/;
Tk::TM::Common::DBILogin([$self->{-wgscr}, $self->{-wgmnu}->set(-wgind)]
,$self->{-parm}->{-dsn}
,$self->{-parm}->{-usr}
,$self->{-parm}->{-psw}
,ref($self->{-parm}) ? '#' .join('#',keys(%{$self->{-parm}})): $self->{-parm}
,$self->{-parm}->{-dbopt}
);
$self->{-dos} =[];
}