> I'm writing my GUI using the Tcl::Tk perl module. I've created a BLT 
> graph widget. I'd like to be able to display the graph element 
> information if the user mouses over it. I can do this with pure 
> Tcl/Tk/BLT, but I'm unable to find the right combination of commands 
> within this Tcl/Tk/BLT perl hybrid.
> 
> In Tcl/Tk, I can figure out which element the user is 
> interested in by 
> passing a procedure %x and %y. How is this doable in perl?
> When I tried to use Eval, I got strange answers:

yes, the '%' is working different in Tcl::Tk, compared to Perl/Tk

the reason lies is some internal optimizations for callbacks within Tcl/Tk

The point is - when Tcl/Tk do not see '%x' '%y' etc in its callback string - it 
even do not fill proper event struct with these values.

As a special workaround it was introduced a syntax to fake those %something by 
\\'xy', so in $widget->method(arg1,arg2, \\'xy', sub {code});
the code within callback will get in this case


> 
> my $graph = $frame->BLTGraph->pack();
> $graph->bind('<Motion>'=>[\&displayInfo,$graph]);
> 
> sub displayInfo {
>     my $graph = $_[0];
>     $int->Eval("$graph element closest %x %y info 
> -interpolate false");
> }
> 
> Running with this eval command gave the error:
>     bad screen distance "c63c760": bad window x-coordinate
> 
> Anyway, in summary, the X,Y coordinates of the mouse will need to be 
> known to determine the information.
> Any help would be appreciated.

Instead of doing \\'xy', I use another technique to deal with the problem is to 
bind all given Perl routines at once to Tcl/Tk, and then use them in callbacks 
with usual %x and %y syntax:

Here is a helper sub that I often use:

sub Tcl::Tk::bind_ptcl {
    my $int = shift;
    no strict 'refs';
    for my $subname (keys %::ptcl::) {
        #deb print STDERR "binding sub $subname\n";
        $int->CreateCommand("ptcl_$subname",\&{"ptcl::$subname"});
    }
    for my $varname (keys %::ptclv::) {
        #deb print STDERR "binding var $varname\n";
        tie ${"ptclv::$varname"}, 'Tcl::Var', $int, "ptclv_$varname";
    }
}

it binds all Perl subroutines from ptcl:: package (and also all Perl  variables 
from ptclv package, which is not needed in the current example, but useful 
approach anyway, IMHO)

All I need to do is:
1. create proper callback subroutines in my helper "ptcl::" package
sub ptcl::subrg {
  my (undef,undef,undef, $arg1, $arg2, $arg3) = @_;
  print "I am subrg arg1=$arg1 arg2=$arg2 arg3=$arg3\n";
}
2. use it from pure-tcltk callback way as (which still uses perl/Tk syntax, BTW)

$mw->Button->(-command=>"ptcl_subrg foo bar fluffy")->pack;

this way you will not lose %x, %y modifiers, as long as they will be.directly 
in the string which is passed to Tcl/Tk.

Best regards,
Vadim.

Reply via email to