~ubuntu-branches/ubuntu/lucid/pdl/lucid

« back to all changes in this revision

Viewing changes to Graphics/TriD/TriD/Tk.pm

  • Committer: Bazaar Package Importer
  • Author(s): Ben Gertzfield
  • Date: 2002-04-08 18:47:16 UTC
  • Revision ID: james.westby@ubuntu.com-20020408184716-0hf64dc96kin3htp
Tags: upstream-2.3.2
ImportĀ upstreamĀ versionĀ 2.3.2

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
#!/usr/bin/perl 
 
2
#
 
3
#  PDL::Graphics::TriD::Tk - A Tk widget interface to the PDL::Graphics::TriD
 
4
#  visualization package:  $Revision: 1.6 $  
 
5
#
 
6
#  James P. Edwards
 
7
#  Instituto Nacional de Meteorologia
 
8
#  Brasilia, DF, Brasil
 
9
#  jedwards@inmet.gov.br  
 
10
#
 
11
#  This distribution is free software; you can
 
12
#  redistribute it and/or modify it under the same terms as Perl itself.
 
13
#  
 
14
 
 
15
=head1 NAME
 
16
 
 
17
PDL::Graphics::TriD::Tk - A Tk widget interface to the PDL::Graphics::TriD.
 
18
 
 
19
=head1 SYNOPSIS
 
20
 
 
21
=for usage
 
22
 
 
23
 #
 
24
 # Opens a Tk window with an embedded TriD window - that's all
 
25
 # see Demos/TkTriD_demo.pm for a better example
 
26
 # 
 
27
 use PDL;
 
28
 use PDL::Graphics::TriD;
 
29
 use PDL::Graphics::TriD::GL;
 
30
 use Tk;
 
31
 use PDL::Graphics::TriD::Tk;
 
32
 
 
33
 my $MW = MainWindow->new();
 
34
 my $TriDW = $MW->Tk( )->pack(-expand=>1, -fill=>'both');
 
35
 $TriDW->MainLoop;
 
36
 
 
37
=head1 DESCRIPTION
 
38
 
 
39
The widget is composed of a Frame and the Display device of the TriD output.
 
40
It inherits all of the attributes of a Tk Frame.  All of the events associated 
 
41
with this window are handled through Tk with the exception of the <expose> event
 
42
which must be handled by TriD because the Frame is never exposed.  
 
43
Default Mouse bindings, defined for button1 and button3, 
 
44
control TriD object orientation and size respectively.  
 
45
 
 
46
=cut
 
47
 
 
48
package PDL::Graphics::TriD::Tk;
 
49
use Tk;
 
50
use PDL::Core;
 
51
use PDL::Graphics::TriD;
 
52
use PDL::Graphics::OpenGL;
 
53
use strict;
 
54
 
 
55
 
 
56
@PDL::Graphics::TriD::Tk::ISA = qw(Tk::Frame);
 
57
 
 
58
$PDL::Graphics::TriD::Tk::verbose=0;
 
59
 
 
60
Tk::Widget->Construct('Tk');
 
61
 
 
62
#$PDL::Graphics::TriD::Tk::VERSION = '$Revision: 1.6 $ ' ;
 
63
#$PDL::Graphics::TriD::Tk::VERSION =~ s/\$Revision: 1.6 $\s*$/$1/;
 
64
#sub Version {return $PDL::Graphics::TriD::Tk::VERSION;}
 
65
 
 
66
=head1 FUNCTIONS
 
67
 
 
68
=head2 Populate
 
69
 
 
70
=for ref
 
71
 
 
72
Used for widget initialization by Tk, this function should never be called directly
 
73
 
 
74
=cut
 
75
 
 
76
sub Populate {
 
77
  my($TriD, $args) = @_;
 
78
 
 
79
  if(defined $PDL::Graphics::TriD::cur){
 
80
         print "Current code limitations prevent TriD:Tk from being loaded after ";
 
81
    print "another TriD graphics window has been defined.  If you are running the ";
 
82
         print "PDL demo package, please start it again and run this demo first.\n";
 
83
         exit;
 
84
  }
 
85
 
 
86
  $args->{-height}=300 unless defined $args->{-height};
 
87
  $args->{-width}=300 unless defined $args->{-width};
 
88
 
 
89
  $TriD->SUPER::Populate($args);
 
90
  # This bind causes GL to be initialized after the 
 
91
  # Tk frame is ready to accept it
 
92
  $TriD->bind("<Configure>", [ \&GLinit ]);
 
93
  print "Populate complete\n" if($PDL::Graphics::TriD::Tk::verbose);
 
94
}
 
95
 
 
96
=head2 MainLoop
 
97
 
 
98
=for ref
 
99
 
 
100
Should be used in place of the Tk MainLoop.  Handles all of the Tk 
 
101
callbacks and calls the appropriate TriD display functions.  
 
102
 
 
103
=cut
 
104
 
 
105
 
 
106
 
 
107
sub MainLoop
 
108
{
 
109
  my ($self) = @_;
 
110
 
 
111
  unless ($Tk::inMainLoop)
 
112
  {
 
113
    local $Tk::inMainLoop = 1;
 
114
    while (Tk::MainWindow->Count)
 
115
    {
 
116
      DoOneEvent(Tk::DONT_WAIT());
 
117
      
 
118
 
 
119
      if(defined $self->{GLwin}){
 
120
        if( &XPending()){
 
121
          my @e = &glpXNextEvent();
 
122
#         if($e[0] == &ConfigureNotify) {
 
123
#           print "CONFIGNOTIFE\n" if($PDL::Graphics::TriD::verbose);
 
124
#           $self->reshape($e[1],$e[2]);
 
125
#         }
 
126
 
 
127
          $self->refresh();
 
128
        }
 
129
        my $job=shift(@{$self->{WorkQue}});
 
130
        if(defined $job){
 
131
          my($cmd,@args) = @$job;
 
132
          &{$cmd}(@args);
 
133
        }
 
134
      }
 
135
    }
 
136
  }
 
137
}
 
138
 
 
139
=head2 GLinit
 
140
 
 
141
=for ref
 
142
 
 
143
GLinit is called internally by a Configure callback in Populate.  This insures 
 
144
that the required Tk::Frame is initialized before the TriD::GL window that will go inside.
 
145
 
 
146
=cut
 
147
 
 
148
sub GLinit{
 
149
  my($self,@args) = @_;
 
150
  
 
151
  if(defined $self->{GLwin}){
 
152
#    print "OW= ",$self->width," OH= ",$self->height,"\n";
 
153
#    $self->update;
 
154
#    print "NW= ",$self->width," NH= ",$self->height,"\n";
 
155
         $self->{GLwin}{_GLObject}->XResizeWindow($self->width ,$self->height);
 
156
 
 
157
    $self->{GLwin}->reshape($self->width,$self->height);
 
158
    $self->refresh();
 
159
  }else{
 
160
# width and height represent the largest size on my screen so that the
 
161
# graphics window always fills the frame.
 
162
    my $options={parent=> ${$self->WindowId},
 
163
                 width=> $self->width,
 
164
                 height=>$self->height};
 
165
    $options->{mask} = ( ExposureMask );
 
166
 
 
167
    $self->{GLwin} = PDL::Graphics::TriD::get_current_window($options);
 
168
 
 
169
    $self->{GLwin}->reshape($self->width,$self->height);
 
170
 
 
171
#
 
172
# This is an array for future expansion beyond the twiddle call.
 
173
 
174
    $self->{WorkQue}= [];
 
175
    $self->refresh();
 
176
 
 
177
    $self->bind("<Button1-Motion>",[ \&buttonmotion, 1, Ev('x'),Ev('y')]);
 
178
    $self->bind("<Button2-Motion>",[ \&buttonmotion, 2, Ev('x'),Ev('y')]);
 
179
    $self->bind("<Button3-Motion>",[ \&buttonmotion, 3, Ev('x'),Ev('y')]);
 
180
  }
 
181
 
 
182
}
 
183
 
 
184
=head2 refresh
 
185
 
 
186
=for ref
 
187
 
 
188
refresh() causes a display event to be put at the top of the TriD work que.  
 
189
This should be called at the end of each user defined TriD::Tk callback. 
 
190
 
 
191
=cut
 
192
 
 
193
sub refresh{
 
194
  my($self) = @_;
 
195
  return unless defined $self->{GLwin};
 
196
# put a redraw command at the top of the work queue
 
197
  my $dcall=ref($self->{GLwin})."::display";
 
198
  unshift(@{$self->{WorkQue}}, [\&{$dcall},$self->{GLwin}]);
 
199
}
 
200
 
 
201
=head2 AUTOLOAD
 
202
 
 
203
=for ref 
 
204
 
 
205
Trys to find a subroutine in PDL::Graphics::TriD when it is 
 
206
not found in this package.  
 
207
 
 
208
=cut
 
209
 
 
210
#
 
211
#  This AUTOLOAD allows the PDL::Graphics::TriD::Tk object to act as the PDL::Graphics::TriD
 
212
#  object which it contains.  It seems slow and may not be a good idea.
 
213
#
 
214
 
 
215
sub AUTOLOAD {
 
216
  my ($self,@args)=@_;
 
217
  use vars qw($AUTOLOAD);
 
218
  my $sub = $AUTOLOAD;
 
219
  # get subroutine name
 
220
 
 
221
#  print "In AutoLoad $self $sub\n";
 
222
  if(defined($self->{GLwin})){
 
223
    $sub =~ s/.*:://;
 
224
    return($self->{GLwin}->$sub(@args));
 
225
  }
 
226
}
 
227
 
 
228
 
 
229
 
 
230
 
 
231
=head2 buttonmotion
 
232
 
 
233
=for ref
 
234
 
 
235
Default bindings for mousemotion with buttons 1 and 3
 
236
 
 
237
=cut
 
238
 
 
239
 
 
240
 
 
241
sub buttonmotion{
 
242
  my($self,$but,$x,$y)=@_;
 
243
 
 
244
  $but--;
 
245
 
 
246
  foreach my $vp (@{$self->viewports()}){
 
247
#    use Data::Dumper;        
 
248
#    my $out = Dumper($vp);
 
249
#    print "$out\n";
 
250
#    exit;
 
251
    next unless $vp->{Active};
 
252
         next unless defined $vp->{EHandler}{Buttons}[$but];
 
253
         $vp->{EHandler}{Buttons}[$but]->mouse_moved($vp->{EHandler}{X},
 
254
                                                                                                                                $vp->{EHandler}{Y},
 
255
                                                                                                                                $x,$y);
 
256
         $vp->{EHandler}{X} = $x;
 
257
         $vp->{EHandler}{Y} = $y;
 
258
  }
 
259
  
 
260
  $self->refresh();
 
261
}
 
262
 
 
263
 
 
264
 
 
265
 
 
266
=head1 Author
 
267
 
 
268
B<James P. Edwards, Instituto Nacional de Meteorologia Brasil>
 
269
 
 
270
jedwards@inmet.gov.br
 
271
 
 
272
=cut
 
273
 
 
274
1;
 
275