Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

widget to widget communication via bind: why this code doesn't work?

3 views
Skip to first unread message

Freddie

unread,
Nov 24, 2009, 2:40:21 AM11/24/09
to
Hello,

I want two subs of my program to communicate asynchronously. I tried
to implement this code but it doesn't work. Is there a better way to
get this working? I'd like to create a new event (i.e.
<<myPersonal_event>>) instead of using key-binding.

Thanks in advance
Freddie

###### CODE
#!/usr/bin/perl

use strict;
use warnings;
use Tk;

my $mw = MainWindow->new(-takefocus => 1);

sub sub1 {
my $window1_w = $mw->Toplevel;
my $send = sub { $mw->eventGenerate('<Key-a>')};
my $but1_b = $window1_w->Button(-text => 'SEND IT', -command =>
$send)->pack;
}


sub sub2 {
my $window2_w = $mw->Toplevel;
my $log_text = $window2_w->Text(-width => 35, -height => 6, )->pack;
$mw->bind('<Key-a>' => sub {$log_text->insert('end', 'GOT IT! ')});
}

&sub1;
&sub2;
MainLoop;

####### END

V. Ul. Peculus

unread,
Nov 24, 2009, 4:03:39 AM11/24/09
to
There are two problems with your code:

1. You receive the event <Key-a> with mw, but want it delivered to a
subwidget of window2.
2. When you press $but1 to send the event, the input focus is with
window1 instead of window2.

So the following code works:

<code>


my $mw = MainWindow->new(-takefocus => 1);

my $window1_w = $mw->Toplevel;
my $window2_w = $mw->Toplevel;
sub sub1 {
my $send = sub { $window2_w->focus;


$mw->eventGenerate('<Key-a>')
};
my $but1_b = $window1_w->Button(-text => 'SEND IT', -command =>
$send)->pack;
}


sub sub2 {


my $log_text = $window2_w->Text(-width => 35, -height => 6, )->pack;

$window2_w->bind('<Key-a>' => sub {$log_text->insert('end', 'GOT
IT! ')});
}

&sub1;
&sub2;
MainLoop;
</code>


But this seems a bit circuitous. The button can directly call the
appropriate method:

<code>


my $mw = MainWindow->new(-takefocus => 1);

my $window1_w = $mw->Toplevel;


my $window2_w = $mw->Toplevel;
my $log_text = $window2_w->Text(-width => 35, -height => 6, )->pack;

my $but1_b = $window1_w->Button(


-text => 'SEND IT',

-command => sub {$log_text->insert('end', 'GOT
IT! ')}
)->pack;

MainLoop;
</code>

Freddie

unread,
Nov 24, 2009, 4:26:34 AM11/24/09
to
Hello Peculus,

the actual code is much more complicated. The point is that I have
subroutines istantiating Toplevel, each toplevel implements a portion
of my program. Sometimes I'd like a subroutine (toplevel+code) signals
another subroutine to do something and I'd like to do it
asyncronously.

I cannot change the whole program structure (30k+ lines), so I cannot
change the following

#################


my $mw = MainWindow->new(-takefocus => 1);
sub sub1 {
my $window1_w = $mw->Toplevel;
}

sub sub2 {


my $window2_w = $mw->Toplevel;
}

&sub1;
&sub2;
MainLoop;
#####################

is there another way to get it working?

Thanks and best regards,
Freddie

felix.da.ru

unread,
Nov 24, 2009, 4:27:35 AM11/24/09
to

Don't know why, but your original code does not work for me, while
with <<myPersonal_event>> it works perfectly.
Environment:
Perl=5.008008 Tk=804.027 OS=Red Hat Enterprise Linux WS release 4
Perl=5.008008 Tk=804.027 OS=MSWin32 XP Pro SP2

felix.da.ru

unread,
Nov 24, 2009, 4:33:58 AM11/24/09
to

Oh, now I got what's the intent... :-)
Maybe $mw->after( <ms>, <callback> ) is the solution?
It runs in parallel <callback> after <ms> period (that could be zero).

Freddie

unread,
Nov 25, 2009, 7:46:29 AM11/25/09
to

the event should be triggered by user actions, I cannot use the after
command.
My environment is perl 5.8.9 on win32/solaris

0 new messages