Fixes and startup-notification - Alex
[terminatorX.git] / src / tX_vttgui.cc
1 /*
2     terminatorX - realtime audio scratching software
3     Copyright (C) 1999-2004  Alexander K├Ânig
4  
5     This program is free software; you can redistribute it and/or modify
6     it under the terms of the GNU General Public License as published by
7     the Free Software Foundation; either version 2 of the License, or
8     (at your option) any later version.
9  
10     This program is distributed in the hope that it will be useful,
11     but WITHOUT ANY WARRANTY; without even the implied warranty of
12     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13     GNU General Public License for more details.
14  
15     You should have received a copy of the GNU General Public License
16     along with this program; if not, write to the Free Software
17     Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18  
19     File: tX_vttgui.cc
20  
21     Description: This implements the gtk+ GUI for the virtual turntable
22                  class implemented in tX_vtt.cc. This code is not in tX_vtt.cc
23                  for mainly to keep the GUI code divided from the audio-rendering
24                  code and as gtk+ callback to C++ method call wrapper.
25                  
26     Changes:
27     
28     before 11-26-2001: too many changes.
29     
30     11-26-2001: applied Adrian's solo/mute patch - Alex
31     
32     11-27-2001: modified solo/mute to use the set_mix_mute/solo function
33                 of the vtts. The previous approach messed up the sequencer
34                 and more. Removed some old unnecessary code, too.
35 */    
36
37 #include <gdk/gdk.h>
38 #include <gtk/gtk.h>
39 #include "tX_vttgui.h"
40 #include "tX_vtt.h"
41 #include "tX_widget.h"
42 #include "tX_mastergui.h"
43 #include "tX_loaddlg.h"
44 #include "tX_prelis.h"
45 #include "tX_pbutton.h"
46 #include "tX_global.h"
47 #include "tX_extdial.h"
48 #include "tX_panel.h"
49 #include "tX_ladspa.h"
50 #include "tX_ladspa_class.h"
51 #include "tX_engine.h"
52 #include "tX_glade_interface.h"
53 #include "tX_glade_support.h"
54 #include "tX_dialog.h"
55
56 #ifdef USE_DIAL
57 #include "tX_dial.h"
58 #endif
59
60 #include "tX_flash.h"
61 #include <stdio.h>
62 #include <ctype.h>
63
64 #define WID_DYN TRUE, TRUE, 0
65 #define WID_FIX FALSE, FALSE, 0
66
67 static gint vg_show_fx_menu(GtkWidget *wid, GdkEventButton *event, vtt_fx *effect);
68
69 void nicer_filename(char *dest, char *source)
70 {
71                 char *fn;
72                 char temp[PATH_MAX];
73                 
74                 fn=strrchr(source, '/');
75                 if (fn) fn++;
76                 else fn=source;
77                 
78                 strcpy (temp, fn);
79                 
80                 fn=strrchr(temp, '.');
81                 if (fn) *fn=0;
82                 
83                 if (strlen(temp) > (unsigned int) globals.filename_length) {
84                         temp[globals.filename_length-3]='.';
85                         temp[globals.filename_length-2]='.';
86                         temp[globals.filename_length-1]='.';
87                         temp[globals.filename_length]=0;
88                 } 
89                 strcpy (dest, temp);
90 }
91
92 void name_changed(GtkWidget *wid, vtt_class *vtt)
93 {
94         vtt->set_name((char *) gtk_entry_get_text(GTK_ENTRY(wid)));
95 }
96
97 void volume_changed(GtkWidget *wid, vtt_class *vtt)
98 {
99         vtt->sp_volume.receive_gui_value(2.0-GTK_ADJUSTMENT(wid)->value);
100 }
101
102 void pan_changed(GtkWidget *wid, vtt_class *vtt)
103 {
104       vtt->sp_pan.receive_gui_value(GTK_ADJUSTMENT(wid)->value);
105 }
106
107 void pitch_changed(GtkWidget *wid, vtt_class *vtt)
108 {
109         vtt->sp_pitch.receive_gui_value(GTK_ADJUSTMENT(wid)->value);
110 }
111
112 #ifdef USE_FILECHOOSER
113 GtkSignalFunc chooser_prelis(GtkWidget *w)
114 {
115         GtkFileChooser *fc=GTK_FILE_CHOOSER(gtk_widget_get_toplevel(w));
116         char *filename=gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(fc));
117         
118         if (filename) {
119                 prelis_start(filename);
120                 g_free(filename);
121         } else {
122                 prelis_stop();
123         }
124         return NULL;
125 }
126 #else
127 GtkSignalFunc trigger_prelis(GtkWidget *w)
128 {
129         GtkFileSelection *fs;
130
131         fs=GTK_FILE_SELECTION(gtk_widget_get_toplevel(w));
132         
133         prelis_start((char *) gtk_file_selection_get_filename(GTK_FILE_SELECTION(fs)));
134         return NULL;
135 }
136
137 void cancel_load_file(GtkWidget *wid, vtt_class *vtt)
138 {
139         prelis_stop();
140         
141         vtt->gui.file_dialog=NULL;
142         if (vtt->gui.fs) gtk_widget_destroy(GTK_WIDGET(vtt->gui.fs));
143 }
144
145 int quit_load_file(GtkWidget *wid, vtt_class *vtt)
146 {
147         return 1;
148 }
149 #endif
150
151 char global_filename_buffer[PATH_MAX];
152
153 void load_part(char *newfile, vtt_class *vtt)
154 {
155         tX_audio_error ret=TX_AUDIO_SUCCESS;
156
157         ld_create_loaddlg(TX_LOADDLG_MODE_SINGLE, 1);
158         ld_set_filename(newfile);
159
160         ret = vtt->load_file(newfile);
161         
162         ld_destroy();
163         if (ret) {
164                 switch(ret) {
165                         case TX_AUDIO_ERR_ALLOC:
166                         tx_note("Failed to load audiofile - there's not enough memory available.", true);
167                         break;
168                         case TX_AUDIO_ERR_PIPE_READ:
169                         tx_note("An error occured on reading from the piped process - probably the file format of the audiofile is not supported by this configuration - please check terminatorX' INSTALL file on howto configure terminatorX for files of this format.", true);
170                         break;
171                         case TX_AUDIO_ERR_SOX:
172                         tx_note("Failed to run sox - to load the given audiofile please ensure that sox is installed correctly.", true);
173                         break;
174                         case TX_AUDIO_ERR_MPG123:
175                         tx_note("Failed to run mpg123 - to load the given mp3 file please ensure that mpg123 (or mpg321) is installed correctly.", true);
176                         break;
177                         case TX_AUDIO_ERR_WAV_NOTFOUND:
178                         tx_note("Couldn't acces the audiofile - file not found.", true);
179                         break;
180                         case TX_AUDIO_ERR_NOT_16BIT:
181                         tx_note("The wav file doesn't use 16 bit wide samples - please compile terminatorX with libaudiofile support to enable loading of such files.", true);
182                         break;
183                         case TX_AUDIO_ERR_NOT_MONO:
184                         tx_note("The wav file is not mono - please compile terminatorX with libaudiofile support to enable loading of such files.", true);
185                         break;
186                         case TX_AUDIO_ERR_WAV_READ:
187                         tx_note("The wav file seems to be corrupt.", true);
188                         break;
189                         case TX_AUDIO_ERR_NOT_SUPPORTED:
190                         tx_note("The file format of the audiofile is not supported - please check terminatorX' INSTALL file on howto configure terminatorX for files of this format.", true);
191                         break;
192                         case TX_AUDIO_ERR_MAD_OPEN:
193                         tx_note("Failed to open this mp3 file - please ensure that the file exists and is readable.", true);
194                         break;  
195                         case TX_AUDIO_ERR_MAD_STAT:
196                         tx_note("Failed to 'stat' this mp3 file - please ensure that the file exists and is readable.", true);
197                         break;
198                         case TX_AUDIO_ERR_MAD_DECODE:
199                         tx_note("Failed to decode the mp3 stream - file is corrupt.", true);
200                         break;
201                         case TX_AUDIO_ERR_MAD_MMAP:
202                         tx_note("Failed to map the audiofile to memory - please ensure the file is readable.", true);
203                         break;
204                         case TX_AUDIO_ERR_MAD_MUNMAP:
205                         tx_note("Failed to unmap audiofile.", true);
206                         break;
207                         case TX_AUDIO_ERR_VORBIS_OPEN:
208                         tx_note("Failed to open ogg file - please ensure the file is an ogg stream and that it is readable.", true);
209                         break;                  
210                         case TX_AUDIO_ERR_VORBIS_NODATA:
211                         tx_note("The vorbis codec failed to decode any data - possibly this ogg stream is corrupt.", true);
212                         break;
213                         case TX_AUDIO_ERR_AF_OPEN:
214                         tx_note("Failed to open this file with libaudiofile - please check terminatorX' INSTALL file on howto configure terminatorX for files of this format.",true);
215                         break;
216                         case TX_AUDIO_ERR_AF_NODATA:
217                         tx_note("libaudiofile failed to decode any data - possilby the audiofile is corrupt.", true);
218                         break;
219                         default:                                        
220                         tx_note("An unknown error occured - if this bug is reproducible please report it, thanks.", true);      
221                 }
222         } else {
223                 nicer_filename(global_filename_buffer, newfile);
224         gtk_button_set_label(GTK_BUTTON(vtt->gui.file), global_filename_buffer);
225         }       
226 }
227
228 #ifndef USE_FILECHOOSER
229 void do_load_file(GtkWidget *wid, vtt_class *vtt)
230 {
231         char newfile[PATH_MAX];
232         
233         prelis_stop();
234
235         strcpy(newfile, gtk_file_selection_get_filename(GTK_FILE_SELECTION(vtt->gui.fs)));
236         gtk_widget_destroy(GTK_WIDGET(vtt->gui.fs));
237         vtt->gui.file_dialog=NULL;
238         
239         tX_cursor::set_cursor(tX_cursor::WAIT_CURSOR);
240         load_part(newfile, vtt);
241         strcpy(globals.current_path, newfile);
242         tX_cursor::reset_cursor();
243 }
244 #endif
245
246 void drop_file(GtkWidget *widget, GdkDragContext *context,
247                 gint x, gint y, GtkSelectionData *selection_data,
248                 guint info, guint time, vtt_class *vtt)
249 {
250         char filename[PATH_MAX];
251         char *fn;
252         
253         strncpy(filename, (char *) selection_data->data, (size_t) selection_data->length);
254         gtk_drag_finish(context, TRUE, FALSE, time);
255         filename[selection_data->length]=0;
256
257         fn = strchr (filename, '\r');
258         *fn=0;  
259         
260         char *realfn=NULL;
261         char *host=NULL;
262         
263         realfn=g_filename_from_uri(filename, &host, NULL);
264         if (realfn) {
265                 fn=realfn;
266         } else {
267                 fn = strchr (filename, ':');
268                 if (fn) fn++; else fn=(char *) selection_data->data;
269         }
270
271         load_part(fn, vtt);
272
273         if (realfn) g_free(realfn);
274         if (host) g_free(host);
275 }
276
277 GtkSignalFunc load_file(GtkWidget *wid, vtt_class *vtt)
278 {       
279 #ifdef USE_FILECHOOSER
280         char *extensions[]={ "mp3", "wav", "ogg", "iff", "aiff", "voc", "au", NULL };
281         
282         GtkWidget * dialog = gtk_file_chooser_dialog_new ("Open Set File",
283                 GTK_WINDOW(main_window), GTK_FILE_CHOOSER_ACTION_OPEN, 
284                 GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, 
285                 GTK_STOCK_OPEN, GTK_RESPONSE_ACCEPT, NULL);
286
287                 
288         GtkFileFilter *filter=gtk_file_filter_new();
289         for (int i=0; extensions[i]!=NULL; i++) {
290                 char buffer[32]="*.";
291                 
292                 gtk_file_filter_add_pattern(filter, strcat(buffer, extensions[i]));
293                 for (int c=0; c<strlen(buffer); c++) {
294                         buffer[c]=toupper(buffer[c]);
295                 }
296                 gtk_file_filter_add_pattern(filter, buffer);
297         }
298         
299         gtk_file_filter_set_name(filter, "Audio Files");
300         gtk_file_chooser_add_filter(GTK_FILE_CHOOSER(dialog), filter); 
301
302         filter=gtk_file_filter_new();
303         gtk_file_filter_add_pattern (filter, "*");
304         gtk_file_filter_set_name(filter, "All Files");
305         gtk_file_chooser_add_filter(GTK_FILE_CHOOSER(dialog), filter); 
306         
307         if (vtt->audiofile) {
308                 gtk_file_chooser_set_filename(GTK_FILE_CHOOSER(dialog), vtt->filename); 
309         } else if (strlen(globals.current_path)>0 ) {
310                 gtk_file_chooser_set_filename(GTK_FILE_CHOOSER(dialog), globals.current_path);
311         }
312         
313         g_signal_connect (G_OBJECT(dialog), "selection-changed", G_CALLBACK(chooser_prelis), vtt);      
314         
315         if (gtk_dialog_run (GTK_DIALOG (dialog)) == GTK_RESPONSE_ACCEPT) {
316         char * filename = gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (dialog));
317                 gtk_widget_hide(dialog);
318                 tX_cursor::set_cursor(tX_cursor::WAIT_CURSOR);
319                 load_part(filename, vtt);
320                 strcpy(globals.current_path, filename);
321                 tX_cursor::reset_cursor();              
322         }       
323         
324         prelis_stop();
325         gtk_widget_destroy(dialog);     
326 #else
327         char buffer[512];
328         
329         if (vtt->gui.file_dialog) {
330                 gdk_window_raise(vtt->gui.file_dialog);
331                 return(0);
332         }
333         
334         sprintf(buffer, "Select Audio File for %s", vtt->name);
335         vtt->gui.fs=gtk_file_selection_new(buffer);
336         
337         if (vtt->audiofile) {
338                 gtk_file_selection_set_filename(GTK_FILE_SELECTION(vtt->gui.fs), vtt->filename);        
339         } else if (strlen(globals.current_path)>0 ) {
340                 gtk_file_selection_set_filename(GTK_FILE_SELECTION(vtt->gui.fs),globals.current_path);
341         }
342         
343         gtk_widget_show(GTK_WIDGET(vtt->gui.fs));       
344         vtt->gui.file_dialog=vtt->gui.fs->window;
345         
346         g_signal_connect (G_OBJECT(GTK_FILE_SELECTION(vtt->gui.fs)->ok_button), "clicked", G_CALLBACK(do_load_file), vtt);
347         g_signal_connect (G_OBJECT(GTK_FILE_SELECTION(vtt->gui.fs)->cancel_button), "clicked", G_CALLBACK (cancel_load_file), vtt);     
348         g_signal_connect (G_OBJECT(vtt->gui.fs), "delete-event", G_CALLBACK(quit_load_file), vtt);      
349         g_signal_connect (G_OBJECT(GTK_FILE_SELECTION(vtt->gui.fs)->file_list), "cursor_changed", G_CALLBACK(trigger_prelis), vtt->gui.fs);             
350 #endif  
351         return NULL;
352 }
353
354 void delete_vtt(GtkWidget *wid, vtt_class *vtt)
355 {
356         if (audioon) tx_note("Sorry, you'll have to stop playback first.");
357         else delete(vtt);
358                 
359         mg_update_status();
360 }
361
362 void edit_vtt_buffer(GtkWidget *wid, vtt_class *vtt)
363 {
364         char command[2*PATH_MAX];
365
366         if (vtt->samples_in_buffer == 0) {
367                 tx_note("No audiofile loaded - so there's nothing to edit.", true);
368         } else if (strlen(globals.file_editor)>0) {
369                 sprintf(command, "%s \"%s\" &", globals.file_editor, vtt->filename);
370                 system(command); /*) tx_note("Failed to run the soundfile editor."); */
371         } else {
372                 tx_note("No soundfile editor has been configured - to do so enter the soundfile editor of your choice in the options dialog.", true);
373         }
374 }
375
376 void reload_vtt_buffer(GtkWidget *wid, vtt_class *vtt)
377 {
378         char reload_buffer[PATH_MAX];
379         
380         while (gtk_events_pending()) gtk_main_iteration();
381         
382         if (vtt->samples_in_buffer > 0) {
383                 strcpy(reload_buffer, vtt->filename);
384                 load_part(reload_buffer, vtt);
385         }
386         else tx_note("No audiofile loaded - so there's nothing to reload.", true);
387 }
388
389 void clone_vtt(GtkWidget *wid, vtt_class *vtt)
390 {
391         vtt->stop();
392 }
393
394 void trigger_vtt(GtkWidget *wid, vtt_class *vtt)
395 {
396         vtt->sp_trigger.receive_gui_value((float) 1.0);
397 }
398
399 void stop_vtt(GtkWidget *wid, vtt_class *vtt)
400 {
401         vtt->sp_trigger.receive_gui_value((float) 0.0);
402 }
403
404 void autotrigger_toggled(GtkWidget *wid, vtt_class *vtt)
405 {
406         vtt->set_autotrigger(GTK_TOGGLE_BUTTON(wid)->active);
407 }
408
409 void loop_toggled(GtkWidget *wid, vtt_class *vtt)
410 {
411         vtt->sp_loop.receive_gui_value(GTK_TOGGLE_BUTTON(wid)->active);
412 }
413
414 void lp_enabled(GtkWidget *wid, vtt_class *vtt)
415 {
416         vtt->sp_lp_enable.receive_gui_value(GTK_TOGGLE_BUTTON(wid)->active);
417 }
418
419 void lp_gain_changed(GtkWidget *wid, vtt_class *vtt)
420 {
421         vtt->sp_lp_gain.receive_gui_value(GTK_ADJUSTMENT(wid)->value);
422 }
423
424 void lp_reso_changed(GtkWidget *wid, vtt_class *vtt)
425 {
426         vtt->sp_lp_reso.receive_gui_value(GTK_ADJUSTMENT(wid)->value);
427 }
428
429 void lp_freq_changed(GtkWidget *wid, vtt_class *vtt)
430 {
431         vtt->sp_lp_freq.receive_gui_value(GTK_ADJUSTMENT(wid)->value);
432 }
433
434 void ec_enabled(GtkWidget *wid, vtt_class *vtt)
435 {
436         vtt->sp_ec_enable.receive_gui_value(GTK_TOGGLE_BUTTON(wid)->active);
437 }
438
439 #ifdef USE_ALSA_MIDI_IN
440 void midi_mapping_clicked(GtkWidget *wid, vtt_class *vtt)
441 {
442         tX_engine::get_instance()->get_midi()->configure_bindings(vtt);
443 }
444 #endif
445
446 void ec_length_changed(GtkWidget *wid, vtt_class *vtt)
447 {
448         vtt->sp_ec_length.receive_gui_value(GTK_ADJUSTMENT(wid)->value);
449 }
450
451 void ec_feedback_changed(GtkWidget *wid, vtt_class *vtt)
452 {
453         vtt->sp_ec_feedback.receive_gui_value(GTK_ADJUSTMENT(wid)->value);
454 }
455
456 void ec_pan_changed(GtkWidget *wid, vtt_class *vtt)
457 {
458         vtt->sp_ec_pan.receive_gui_value(GTK_ADJUSTMENT(wid)->value);
459 }
460
461 void ec_volume_changed(GtkWidget *wid, vtt_class *vtt)
462 {
463         vtt->sp_ec_volume.receive_gui_value(GTK_ADJUSTMENT(wid)->value);
464 }
465
466 void master_setup(GtkWidget *wid, vtt_class *vtt)
467 {
468         vtt->set_sync_master(GTK_TOGGLE_BUTTON(wid)->active);
469 }
470
471 void client_setup(GtkWidget *wid, vtt_class *vtt)
472 {
473         int client;
474         
475         client=gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(vtt->gui.sync_client));   
476         vtt->sp_sync_client.receive_gui_value(client);
477 }
478
479 void client_setup_number(GtkWidget *wid, vtt_class *vtt)
480 {
481         int cycles;
482         
483         cycles=(int) GTK_ADJUSTMENT(vtt->gui.cycles)->value;    
484         
485         vtt->sp_sync_cycles.receive_gui_value(cycles);
486 }
487
488 void mute_volume(GtkWidget *widget, vtt_class *vtt)
489 {
490         if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget))) {
491                 vtt->set_mix_mute(1);
492         } else {
493                 vtt->set_mix_mute(0);
494         }
495 }
496
497 void solo_vtt(GtkWidget *widget, vtt_class *vtt)
498 {
499         if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget))) {
500                 vtt->set_mix_solo(1);
501         } else {
502                 vtt->set_mix_solo(0);
503         }
504 }      
505
506 void minimize_control_panel(GtkWidget *wid, vtt_class *vtt)
507 {
508         vtt->hide_control(true);
509 }
510
511 void unminimize_control_panel(GtkWidget *wid, vtt_class *vtt)
512 {
513         vtt->hide_control(false);
514 }
515
516 void minimize_audio_panel(GtkWidget *wid, vtt_class *vtt)
517 {
518         vtt->hide_audio(true);
519 }
520
521 void unminimize_audio_panel(GtkWidget *wid, vtt_class *vtt)
522 {
523         vtt->hide_audio(false);
524 }
525
526 void vg_xcontrol_dis(GtkWidget *wid, vtt_class *vtt)
527 {
528         vtt->set_x_input_parameter(NULL);
529 }
530
531 void vg_ycontrol_dis(GtkWidget *wid, vtt_class *vtt)
532 {
533         vtt->set_y_input_parameter(NULL);
534 }
535
536 void vg_xcontrol_set(GtkWidget *wid, tX_seqpar *sp)
537 {
538         vtt_class *vtt=(vtt_class *) sp->vtt;
539         vtt->set_x_input_parameter(sp);
540 }
541
542 void vg_ycontrol_set(GtkWidget *wid, tX_seqpar *sp)
543 {
544         vtt_class *vtt=(vtt_class *) sp->vtt;
545         vtt->set_y_input_parameter(sp);
546 }
547
548 gboolean vg_delete_pitch_adjust (GtkWidget *wid, vtt_class *vtt) {
549         vtt->gui.adjust_dialog=NULL;
550         return FALSE;
551 }
552
553 void vg_do_pitch_adjust (GtkWidget *wid, vtt_class *vtt) {
554         int master_cycles=gtk_spin_button_get_value_as_int(GTK_SPIN_BUTTON(lookup_widget(vtt->gui.adjust_dialog, "master_cycles")));
555         int cycles=gtk_spin_button_get_value_as_int(GTK_SPIN_BUTTON(lookup_widget(vtt->gui.adjust_dialog, "cycles")));
556         bool create_event=gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(vtt->gui.adjust_dialog, "create_event")));
557
558         vtt->adjust_to_master_pitch(master_cycles, cycles, create_event);
559         
560         gtk_widget_destroy(vtt->gui.adjust_dialog);
561 }
562
563 void vg_cancel_pitch_adjust (GtkWidget *wid, vtt_class *vtt) {
564         gtk_widget_destroy(vtt->gui.adjust_dialog);
565 }
566
567 void vg_adjust_pitch_vtt(GtkWidget *wid, vtt_class *vtt) {
568         if (vtt->gui.adjust_dialog) {
569                 gtk_widget_destroy(vtt->gui.adjust_dialog);
570                 return;
571         }
572         
573         if (!vtt_class::sync_master) {
574                 tx_note("No master turntable to adjust pitch to selected.", true);
575                 return;
576         }
577         
578         if (vtt==vtt_class::sync_master) {
579                 tx_note("This is the master turntable - cannot adjust a turntable to itself.", true);
580                 return;
581         }
582         
583         vtt->gui.adjust_dialog=create_tx_adjust();
584         tX_set_icon(vtt->gui.adjust_dialog);
585         gtk_widget_show(vtt->gui.adjust_dialog);
586         
587         GtkWidget *ok_button=lookup_widget(vtt->gui.adjust_dialog, "ok");
588         GtkWidget *cancel_button=lookup_widget(vtt->gui.adjust_dialog, "cancel");
589         
590         g_signal_connect(G_OBJECT(ok_button), "clicked", G_CALLBACK(vg_do_pitch_adjust), vtt);
591         g_signal_connect(G_OBJECT(vtt->gui.adjust_dialog), "destroy", G_CALLBACK(vg_delete_pitch_adjust), vtt);
592         g_signal_connect(G_OBJECT(cancel_button), "clicked", G_CALLBACK(vg_cancel_pitch_adjust), vtt);
593 }
594
595 static gint vg_mouse_mapping_pressed(GtkWidget *wid, GdkEventButton *event, vtt_class *vtt) {
596         if (vtt->gui.mouse_mapping_menu) {
597                 gtk_widget_destroy(vtt->gui.mouse_mapping_menu);
598                 vtt->gui.mouse_mapping_menu=NULL;
599         }
600         /* gtk+ seems to cleanup the submenus automatically */
601         
602         vtt->gui.mouse_mapping_menu=gtk_menu_new();
603         GtkWidget *x_item;
604         GtkWidget *y_item;
605         
606         x_item=gtk_menu_item_new_with_label("X-axis (Left <-> Right)");
607         gtk_menu_shell_append(GTK_MENU_SHELL(vtt->gui.mouse_mapping_menu), x_item);
608         gtk_widget_show(x_item);
609
610         y_item=gtk_menu_item_new_with_label("Y-axis (Up <-> Down)");
611         gtk_menu_shell_append(GTK_MENU_SHELL(vtt->gui.mouse_mapping_menu), y_item);
612         gtk_widget_show(y_item);
613         
614         vtt->gui.mouse_mapping_menu_x=gtk_menu_new();
615         vtt->gui.mouse_mapping_menu_y=gtk_menu_new();
616         
617         GtkWidget *item;
618         GtkWidget *item_to_activate=NULL;
619         
620         /* Filling the X menu */
621         item = gtk_check_menu_item_new_with_label("Disable");
622         gtk_menu_shell_append(GTK_MENU_SHELL(vtt->gui.mouse_mapping_menu_x), item);
623         gtk_widget_show(item);
624         g_signal_connect(G_OBJECT(item), "activate", G_CALLBACK(vg_xcontrol_dis), vtt);
625         if (vtt->x_par==NULL) item_to_activate=item;
626
627         list <tX_seqpar *> :: iterator sp;
628
629         for (sp=tX_seqpar::all.begin(); sp!=tX_seqpar::all.end(); sp++) {
630                 if (((*sp)->is_mappable) && ((*sp)->vtt) == (void*) vtt) {
631                         item=gtk_check_menu_item_new_with_label((*sp)->get_name());
632                         gtk_menu_shell_append(GTK_MENU_SHELL(vtt->gui.mouse_mapping_menu_x), item);
633                         gtk_widget_show(item);
634                         g_signal_connect(G_OBJECT(item), "activate", G_CALLBACK(vg_xcontrol_set), (void*) (*sp));
635                         
636                         if (vtt->x_par==(*sp)) item_to_activate=item;
637                 }
638         }
639
640         if (item_to_activate) gtk_check_menu_item_set_active(GTK_CHECK_MENU_ITEM(item_to_activate), TRUE);
641         
642         /* Filling the Y menu */
643         item_to_activate=NULL;
644         
645         item = gtk_check_menu_item_new_with_label("Disable");
646         gtk_menu_shell_append(GTK_MENU_SHELL(vtt->gui.mouse_mapping_menu_y), item);
647         gtk_widget_show(item);
648         g_signal_connect(G_OBJECT(item), "activate", G_CALLBACK(vg_ycontrol_dis), vtt);
649         if (vtt->y_par==NULL) item_to_activate=item;
650
651         for (sp=tX_seqpar::all.begin(); sp!=tX_seqpar::all.end(); sp++) {
652                 if (((*sp)->is_mappable) && ((*sp)->vtt) == (void*) vtt) {
653                         item=gtk_check_menu_item_new_with_label((*sp)->get_name());
654                         gtk_menu_shell_append(GTK_MENU_SHELL(vtt->gui.mouse_mapping_menu_y), item);
655                         gtk_widget_show(item);
656                         g_signal_connect(G_OBJECT(item), "activate", G_CALLBACK(vg_ycontrol_set), (void*) (*sp));
657                         
658                         if (vtt->y_par==(*sp)) item_to_activate=item;
659                 }
660         }
661
662         if (item_to_activate) gtk_check_menu_item_set_active(GTK_CHECK_MENU_ITEM(item_to_activate), TRUE);
663         
664         gtk_menu_item_set_submenu(GTK_MENU_ITEM(x_item), vtt->gui.mouse_mapping_menu_x);
665         gtk_menu_item_set_submenu(GTK_MENU_ITEM(y_item), vtt->gui.mouse_mapping_menu_y);
666         gtk_menu_popup (GTK_MENU(vtt->gui.mouse_mapping_menu), NULL, NULL, NULL, NULL, 0, 0);
667         
668         g_signal_emit_by_name(G_OBJECT(wid), "released", vtt);
669         
670         return TRUE;
671 }
672
673 static gint vg_file_button_pressed(GtkWidget *wid, GdkEventButton *event, vtt_class *vtt) {
674         if (vtt->gui.file_menu==NULL) {
675                 GtkWidget *item;
676                 
677                 vtt->gui.file_menu=gtk_menu_new();
678                 item=gtk_menu_item_new_with_label("Load audio file");
679                 gtk_menu_shell_append(GTK_MENU_SHELL(vtt->gui.file_menu), item);
680                 gtk_widget_show(item);
681                 
682                 g_signal_connect(G_OBJECT(item), "activate", G_CALLBACK(load_file), vtt);
683                 
684                 item=gtk_menu_item_new_with_label("Edit audio file");
685                 gtk_menu_shell_append(GTK_MENU_SHELL(vtt->gui.file_menu), item);
686                 gtk_widget_show(item);
687
688                 g_signal_connect(G_OBJECT(item), "activate", G_CALLBACK(edit_vtt_buffer), vtt);
689
690                 item=gtk_menu_item_new_with_label("Reload current audio file");
691                 gtk_menu_shell_append(GTK_MENU_SHELL(vtt->gui.file_menu), item);
692                 gtk_widget_show(item);
693
694                 g_signal_connect(G_OBJECT(item), "activate", G_CALLBACK(reload_vtt_buffer), vtt);
695         }
696         
697         gtk_menu_popup(GTK_MENU(vtt->gui.file_menu), NULL, NULL, NULL, NULL, 0,0);
698         /* gtk+ is really waiting for this.. */
699         g_signal_emit_by_name(G_OBJECT(wid), "released", vtt);
700         
701         return TRUE;
702 }
703
704 void vg_adjust_zoom(GtkWidget *wid, vtt_class *vtt) {   
705         GtkAdjustment *adj=gtk_range_get_adjustment(GTK_RANGE(vtt->gui.zoom));
706         gtk_tx_set_zoom(GTK_TX(vtt->gui.display), adj->value/100.0);
707 }
708
709 static gint fx_button_pressed(GtkWidget *wid, GdkEventButton *event, vtt_class *vtt)
710 {
711         vtt_gui *g=&vtt->gui;
712
713         LADSPA_Class::set_current_vtt(vtt);
714
715         if (g->ladspa_menu) gtk_object_destroy(GTK_OBJECT(g->ladspa_menu));
716         g->ladspa_menu=LADSPA_Class::get_ladspa_menu();
717         gtk_menu_popup (GTK_MENU(g->ladspa_menu), NULL, NULL, NULL, NULL, 0, 0);
718
719         /* gtk+ is really waiting for this.. */
720         g_signal_emit_by_name(G_OBJECT(wid), "released", vtt);
721         
722         return TRUE;
723 }
724
725 static gint stereo_fx_button_pressed(GtkWidget *wid, GdkEventButton *event, vtt_class *vtt)
726 {
727         vtt_gui *g=&vtt->gui;
728
729         LADSPA_Class::set_current_vtt(vtt);
730
731         if (g->ladspa_menu) gtk_object_destroy(GTK_OBJECT(g->ladspa_menu));
732         g->ladspa_menu=LADSPA_Class::get_stereo_ladspa_menu();
733         gtk_menu_popup (GTK_MENU(g->ladspa_menu), NULL, NULL, NULL, NULL, 0, 0);
734
735         /* gtk+ is really waiting for this.. */
736         g_signal_emit_by_name(G_OBJECT(wid), "released", vtt);
737         
738         return TRUE;
739 }
740
741 void gui_set_name(vtt_class *vtt, char *newname)
742 {
743         char bold_name[128];
744         strcpy(bold_name, "<b>");
745         strcat(bold_name, newname);
746         strcat(bold_name, "</b>");
747         
748         gtk_label_set_markup(GTK_LABEL(vtt->gui.audio_label), bold_name);
749         gtk_label_set_markup(GTK_LABEL(vtt->gui.control_label), bold_name);
750         gtk_entry_set_text(GTK_ENTRY(vtt->gui.name), newname);
751         
752         if (vtt->gui.audio_minimized_panel_bar_button!=NULL) {
753                 gtk_label_set_text(GTK_LABEL(vtt->gui.audio_minimized_panel_bar_label), newname);
754         }
755
756         if (vtt->gui.control_minimized_panel_bar_button!=NULL) {
757                 gtk_label_set_text(GTK_LABEL(vtt->gui.control_minimized_panel_bar_label), newname);
758         }
759 }
760
761 #define connect_entry(wid, func); g_signal_connect(G_OBJECT(g->wid), "activate", G_CALLBACK(func), (void *) vtt);
762 #define connect_adj(wid, func); g_signal_connect(G_OBJECT(g->wid), "value_changed", G_CALLBACK(func), (void *) vtt);
763 #define connect_button(wid, func); g_signal_connect(G_OBJECT(g->wid), "clicked", G_CALLBACK(func), (void *) vtt);
764 #define connect_range(wid, func); g_signal_connect(G_OBJECT(gtk_range_get_adjustment(GTK_RANGE(g->wid))), "value_changed", G_CALLBACK(func), (void *) vtt);
765 #define connect_scale_format(wid, func); g_signal_connect(G_OBJECT(g->wid), "format-value", G_CALLBACK(func), (void *) vtt);
766 #define connect_press_button(wid, func); g_signal_connect(G_OBJECT(g->wid), "button_press_event", G_CALLBACK(func), (void *) vtt);
767 #define connect_rel_button(wid, func); g_signal_connect(G_OBJECT(g->wid), "released", G_CALLBACK(func), (void *) vtt);
768
769 GtkWidget *vg_create_fx_bar(vtt_class *vtt, vtt_fx *effect, int showdel);
770
771 void gui_connect_signals(vtt_class *vtt)
772 {
773         vtt_gui *g=&vtt->gui;
774
775         connect_entry(name, name_changed);
776         connect_adj(volume, volume_changed);
777         connect_adj(pitch, pitch_changed);
778         connect_adj(pan, pan_changed);
779         connect_press_button(file, vg_file_button_pressed);
780         
781         connect_button(del, delete_vtt);
782         connect_button(trigger, trigger_vtt);
783         connect_button(stop, stop_vtt);
784         connect_button(autotrigger, autotrigger_toggled);
785         connect_button(loop, loop_toggled);
786         connect_button(sync_master, master_setup);
787         connect_button(sync_client, client_setup);
788         connect_button(adjust_button, vg_adjust_pitch_vtt);
789         connect_adj(cycles, client_setup_number);
790         connect_press_button(fx_button, fx_button_pressed);
791         connect_press_button(stereo_fx_button, stereo_fx_button_pressed);
792         
793         connect_button(lp_enable, lp_enabled);
794         connect_adj(lp_gain, lp_gain_changed);
795         connect_adj(lp_reso, lp_reso_changed);
796         connect_adj(lp_freq, lp_freq_changed);
797         
798         connect_button(ec_enable, ec_enabled);
799 #ifdef USE_ALSA_MIDI_IN 
800         connect_button(midi_mapping, midi_mapping_clicked);
801 #endif  
802         connect_adj(ec_length, ec_length_changed);
803         connect_adj(ec_feedback, ec_feedback_changed);
804         connect_adj(ec_pan, ec_pan_changed);
805         connect_adj(ec_volume, ec_volume_changed);      
806         connect_range(zoom, vg_adjust_zoom);
807         //connect_scale_format(zoom, vg_format_zoom);
808         connect_press_button(mouse_mapping, vg_mouse_mapping_pressed);
809         connect_button(control_minimize, minimize_control_panel);
810         connect_button(audio_minimize, minimize_audio_panel);
811
812         static GtkTargetEntry drop_types [] = {
813                 { "text/uri-list", 0, 0}
814         };
815         static gint n_drop_types = sizeof (drop_types) / sizeof(drop_types[0]);
816         
817         gtk_drag_dest_set (GTK_WIDGET (g->file), (GtkDestDefaults) (GTK_DEST_DEFAULT_MOTION |GTK_DEST_DEFAULT_HIGHLIGHT |GTK_DEST_DEFAULT_DROP),
818                         drop_types, n_drop_types,
819                         GDK_ACTION_COPY);
820                                                 
821         g_signal_connect (G_OBJECT (g->file), "drag_data_received",
822                         G_CALLBACK(drop_file), (void *) vtt);
823
824         gtk_drag_dest_set (GTK_WIDGET (g->display), (GtkDestDefaults) (GTK_DEST_DEFAULT_MOTION |GTK_DEST_DEFAULT_HIGHLIGHT |GTK_DEST_DEFAULT_DROP),
825                         drop_types, n_drop_types,
826                         GDK_ACTION_COPY);
827                                                 
828         g_signal_connect (G_OBJECT (g->display), "drag_data_received",
829                         G_CALLBACK(drop_file), (void *) vtt);
830         
831 }
832
833 void build_vtt_gui(vtt_class *vtt)
834 {
835         GtkWidget *tempbox;
836         GtkWidget *tempbox2;
837         GtkWidget *tempbox3;
838         GtkWidget *dummy;
839         char nice_name[256];
840         
841         vtt_gui *g;
842         
843         g=&vtt->gui;
844         vtt->have_gui=1;
845         g->par_menu=NULL;
846         g->ladspa_menu=NULL;
847
848         /* Building Audio Box */
849         g->audio_box=gtk_vbox_new(FALSE,2);
850         gtk_widget_show(g->audio_box);
851         
852         tempbox2=gtk_hbox_new(FALSE,2);
853         gtk_widget_show(tempbox2);
854         gtk_box_pack_start(GTK_BOX(g->audio_box), tempbox2, WID_FIX);
855         
856         tempbox=gtk_hbox_new(TRUE,2);
857         gtk_widget_show(tempbox);
858         gtk_box_pack_start(GTK_BOX(tempbox2), tempbox, WID_DYN);
859
860         GtkWidget *pixmap;
861         g->audio_minimize=gtk_button_new();
862         pixmap=tx_pixmap_widget(MINIMIZE_PANEL);
863         gtk_container_add (GTK_CONTAINER (g->audio_minimize), pixmap);  
864         gtk_box_pack_end(GTK_BOX(tempbox2), g->audio_minimize, WID_FIX);
865         gtk_widget_show(pixmap);
866         gtk_widget_show(g->audio_minimize);
867
868
869         g->audio_label=gtk_label_new(vtt->name);
870         gtk_misc_set_alignment(GTK_MISC(g->audio_label), 0.025, 0.5);
871         gtk_widget_show(g->audio_label);
872         gtk_box_pack_start(GTK_BOX(tempbox), g->audio_label, WID_DYN);
873
874         nicer_filename(nice_name, vtt->filename);
875         g->file = gtk_button_new_with_label(nice_name);
876         gtk_widget_show(g->file);
877         gui_set_tooltip(g->file, "Click to Load/Edit/Reload a sample for this turntable. To load you can also drag a file and drop it over this button or the sound data display below.");
878         gtk_box_pack_start(GTK_BOX(tempbox), g->file, WID_DYN);
879
880         g->mouse_mapping=gtk_button_new_with_label("Mouse");
881         gtk_widget_show(g->mouse_mapping);
882         gui_set_tooltip(g->mouse_mapping, "Determines what parameters should be affected on mouse moition in mouse grab mode.");
883         gtk_box_pack_start(GTK_BOX(tempbox2), g->mouse_mapping, WID_FIX);
884
885 #ifdef USE_ALSA_MIDI_IN
886         g->midi_mapping=gtk_button_new_with_label("MIDI");
887         gtk_widget_show(g->midi_mapping);
888         gui_set_tooltip(g->midi_mapping, "Determines what parameters should be bound to what MIDI events.");
889         gtk_box_pack_start(GTK_BOX(tempbox2), g->midi_mapping, WID_FIX);
890         
891         if (!tX_engine::get_instance()->get_midi()->get_is_open()) {
892                 gtk_widget_set_sensitive(g->midi_mapping, FALSE);
893         }
894 #endif
895
896         tempbox=gtk_hbox_new(FALSE, 2);
897
898         g->display=gtk_tx_new(vtt->buffer, vtt->samples_in_buffer);
899         gtk_box_pack_start(GTK_BOX(tempbox), g->display, WID_DYN);
900         gtk_widget_show(g->display);    
901         
902         g->zoom=gtk_vscale_new_with_range(0,99.0,1.0);
903         gtk_range_set_inverted(GTK_RANGE(g->zoom), TRUE);
904         gtk_scale_set_draw_value(GTK_SCALE(g->zoom), TRUE);
905         gtk_scale_set_digits(GTK_SCALE(g->zoom), 0);
906         gtk_scale_set_value_pos(GTK_SCALE(g->zoom), GTK_POS_BOTTOM);
907         gtk_adjustment_set_value(gtk_range_get_adjustment(GTK_RANGE(g->zoom)), 0);
908         
909         gui_set_tooltip(g->zoom, "Set the zoom-level for the audio data display.");
910         gtk_box_pack_start(GTK_BOX(tempbox), g->zoom, WID_FIX);
911         gtk_widget_show(g->zoom);
912         
913         gtk_box_pack_start(GTK_BOX(g->audio_box), tempbox, WID_DYN);
914         gtk_widget_show(tempbox);
915         
916         /* Building Control Box */
917         
918         g->control_box=gtk_vbox_new(FALSE,2);
919         gtk_widget_show(g->control_box);
920
921         tempbox2=gtk_hbox_new(FALSE, 2);
922         gtk_widget_show(tempbox2);
923         gtk_box_pack_start(GTK_BOX(g->control_box), tempbox2, WID_FIX);
924
925         g->control_label=gtk_label_new(vtt->name);
926         gtk_widget_show(g->control_label);
927         gtk_box_pack_start(GTK_BOX(tempbox2), g->control_label, WID_DYN);
928
929         g->control_minimize=gtk_button_new();
930         pixmap=tx_pixmap_widget(MINIMIZE_PANEL);
931         gtk_container_add (GTK_CONTAINER (g->control_minimize), pixmap);        
932         gtk_box_pack_end(GTK_BOX(tempbox2), g->control_minimize, WID_FIX);
933         gtk_widget_show(pixmap);
934         gtk_widget_show(g->control_minimize);
935
936         g->scrolled_win=gtk_scrolled_window_new (NULL, NULL);
937         gtk_container_set_border_width (GTK_CONTAINER (g->scrolled_win), 0);
938         gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (g->scrolled_win),
939                                     GTK_POLICY_NEVER, GTK_POLICY_AUTOMATIC);
940         gtk_widget_show(g->scrolled_win);
941         gtk_box_pack_start(GTK_BOX(g->control_box), g->scrolled_win, WID_DYN);
942                                     
943         g->control_subbox=gtk_vbox_new(FALSE,0);
944         gtk_scrolled_window_add_with_viewport (
945                    GTK_SCROLLED_WINDOW (g->scrolled_win), g->control_subbox);
946         gtk_widget_show(g->control_subbox);
947                    
948
949         /* Main panel */
950         
951         tX_panel *p=new tX_panel("Main", g->control_subbox);
952         g->main_panel=p;
953                         
954         g->name = gtk_entry_new();
955         gtk_entry_set_max_length(GTK_ENTRY(g->name), 256);
956         gtk_entry_set_text(GTK_ENTRY(g->name), vtt->name);
957         p->add_client_widget(g->name);
958         gui_set_tooltip(g->name, "Enter the turntable's name here.");
959         gtk_widget_set_size_request(g->name, 40, -1);
960
961         g->del=gtk_button_new_with_label("Delete");
962         gui_set_tooltip(g->del, "Click here to annihilate this turntable. All events recorded for this turntable will be erased, too.");
963         p->add_client_widget(g->del);
964         
965         g->adjust_button=gtk_button_new_with_label("Pitch Adj.");
966         gui_set_tooltip(g->adjust_button, "Activate this button to adjust this turntable's speed to the master turntable's speed.");
967         p->add_client_widget(g->adjust_button);
968
969         gtk_box_pack_start(GTK_BOX(g->control_subbox), p->get_widget(), WID_FIX);
970                                 
971         p=new tX_panel("Playback", g->control_subbox);
972         g->trigger_panel=p;
973         
974         g->trigger=gtk_button_new_with_label("Trigger!");
975         gui_set_tooltip(g->trigger, "Click here to trigger this turntable right now. If the audio engine is disabled this turntable will be triggerd as soon as the engine is turned on.");
976         p->add_client_widget(g->trigger);
977         
978         g->stop=gtk_button_new_with_label("Stop.");
979         gui_set_tooltip(g->stop, "Stop this turntable's playback.");
980         p->add_client_widget(g->stop);
981         g_signal_connect(G_OBJECT(g->trigger), "button_press_event", (GtkSignalFunc) tX_seqpar::tX_seqpar_press, &vtt->sp_trigger);             
982         g_signal_connect(G_OBJECT(g->stop), "button_press_event", (GtkSignalFunc) tX_seqpar::tX_seqpar_press, &vtt->sp_trigger);                
983         
984         g->autotrigger=gtk_check_button_new_with_label("Auto");
985         p->add_client_widget(g->autotrigger);
986         gui_set_tooltip(g->autotrigger, "If turned on, this turntable will be automagically triggered whenever the audio engine is turned on.");
987         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(g->autotrigger), vtt->autotrigger);
988
989         g->loop=gtk_check_button_new_with_label("Loop");
990         p->add_client_widget(g->loop);
991         gui_set_tooltip(g->loop, "Enable this option to make the turntable loop the audio data.");
992         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(g->loop), vtt->loop);
993         g_signal_connect(G_OBJECT(g->loop), "button_press_event", (GtkSignalFunc) tX_seqpar::tX_seqpar_press, &vtt->sp_loop);           
994         
995         g->sync_master=gtk_check_button_new_with_label("Master");
996         p->add_client_widget(g->sync_master);
997         gui_set_tooltip(g->sync_master, "Click here to make this turntable the sync-master. All turntables marked as sync-clients will be (re-)triggered in relation to the sync-master. Note that only *one* turntable can be the sync-master.");
998         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(g->sync_master), vtt->is_sync_master);
999         
1000         g->sync_client=gtk_check_button_new_with_label("Client");
1001         p->add_client_widget(g->sync_client);
1002         gui_set_tooltip(g->sync_client, "If enabled this turntable will be (re-)triggerd in relation to the sync-master turntable.");
1003         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(g->sync_client), vtt->is_sync_client);
1004         g_signal_connect(G_OBJECT(g->sync_client), "button_press_event", (GtkSignalFunc) tX_seqpar::tX_seqpar_press, &vtt->sp_sync_client);     
1005         
1006         g->cycles=GTK_ADJUSTMENT(gtk_adjustment_new(vtt->sync_cycles, 0, 10.0, 1,1,1));
1007         dummy=gtk_spin_button_new(g->cycles, 1.0, 0);
1008         p->add_client_widget(dummy);
1009         gui_set_tooltip(dummy, "Determines how often a sync-client turntable gets triggered. 0 -> this turntable will be triggered with every trigger of the sync-master table, 1 -> the table will be triggered every 2nd master trigger and so on.");
1010         g_signal_connect(G_OBJECT(dummy), "button_press_event", (GtkSignalFunc) tX_seqpar::tX_seqpar_press, &vtt->sp_sync_cycles);      
1011
1012         gtk_box_pack_start(GTK_BOX(g->control_subbox), p->get_widget(), WID_FIX);
1013         
1014         g->fx_box=gtk_vbox_new(FALSE,0);
1015         gtk_box_pack_start(GTK_BOX(g->control_subbox), g->fx_box, WID_FIX);
1016         gtk_widget_show(g->fx_box);
1017         
1018         dummy=gtk_button_new_with_label("FX");
1019         gtk_container_foreach(GTK_CONTAINER(dummy), (GtkCallback) tX_panel_make_label_bold, NULL);
1020         gtk_widget_show(dummy);
1021         g->fx_button=dummy;
1022         gui_set_tooltip(g->fx_button, "Click here to load a LADSPA plugin. You will get a menu from which you can choose which plugin to load.");
1023         gtk_box_pack_start(GTK_BOX(g->fx_box), dummy, WID_FIX);
1024         
1025         /* Lowpass Panel */
1026
1027         p=new tX_panel("Lowpass", g->fx_box);
1028         g_signal_connect(G_OBJECT(p->get_labelbutton()), "button_press_event", G_CALLBACK(vg_show_fx_menu), vtt->lp_fx);
1029         g->lp_panel=p;
1030                 
1031         g->lp_enable=gtk_check_button_new_with_label("Enable");
1032         gui_set_tooltip(g->lp_enable, "Click here to enable the built-in lowpass effect.");
1033         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(g->lp_enable), vtt->lp_enable);
1034         p->add_client_widget(vg_create_fx_bar(vtt, vtt->lp_fx, 0));
1035         g_signal_connect(G_OBJECT(g->lp_enable), "button_press_event", (GtkSignalFunc) tX_seqpar::tX_seqpar_press, &vtt->sp_ec_enable); 
1036
1037         p->add_client_widget(g->lp_enable);
1038
1039         g->lp_gain=GTK_ADJUSTMENT(gtk_adjustment_new(vtt->lp_gain, 0, 2, 0.1, 0.01, 0.01));
1040         g->lp_reso=GTK_ADJUSTMENT(gtk_adjustment_new(vtt->lp_reso, 0, 0.99, 0.1, 0.01, 0.01));
1041         g->lp_freq=GTK_ADJUSTMENT(gtk_adjustment_new(vtt->lp_freq, 0, 1, 0.1, 0.01, 0.01));
1042
1043         g->lp_gaind=new tX_extdial("Input Gain", g->lp_gain, &vtt->sp_lp_gain);
1044         p->add_client_widget(g->lp_gaind->get_widget());
1045         gui_set_tooltip(g->lp_gaind->get_entry(), "Adjust the input gain. with this parameter you can either amplify or damp the input-signal for the lowpass effect.");
1046
1047         g->lp_freqd=new tX_extdial("Frequency", g->lp_freq, &vtt->sp_lp_freq);
1048         p->add_client_widget(g->lp_freqd->get_widget());
1049         gui_set_tooltip(g->lp_freqd->get_entry(), "Adjust the cutoff frequency of the lowpass filter. 0 is 0 Hz, 1 is 22.1 kHz.");
1050
1051         g->lp_resod=new tX_extdial("Resonance", g->lp_reso, &vtt->sp_lp_reso);
1052         p->add_client_widget(g->lp_resod->get_widget());
1053         gui_set_tooltip(g->lp_resod->get_entry(), "Adjust the resonance of the lowpass filter. This value determines how much the signal at the cutoff frequency will be amplified.");
1054
1055         gtk_box_pack_start(GTK_BOX(g->fx_box), p->get_widget(), WID_FIX);
1056
1057         /* Echo Panel */
1058
1059         p=new tX_panel("Echo", g->fx_box);
1060         g_signal_connect(G_OBJECT(p->get_labelbutton()), "button_press_event",  G_CALLBACK(vg_show_fx_menu), vtt->ec_fx);
1061         g->ec_panel=p;
1062
1063         p->add_client_widget(vg_create_fx_bar(vtt, vtt->ec_fx, 0));
1064         
1065         g->ec_enable=gtk_check_button_new_with_label("Enable");
1066         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(g->ec_enable), vtt->ec_enable);
1067         p->add_client_widget(g->ec_enable);
1068         gui_set_tooltip(g->ec_enable, "Enable the built-in echo effect.");
1069         g_signal_connect(G_OBJECT(g->ec_enable), "button_press_event", (GtkSignalFunc) tX_seqpar::tX_seqpar_press, &vtt->sp_ec_enable); 
1070
1071         g->ec_length=GTK_ADJUSTMENT(gtk_adjustment_new(vtt->ec_length, 0, 1, 0.1, 0.01, 0.001));
1072         g->ec_feedback=GTK_ADJUSTMENT(gtk_adjustment_new(vtt->ec_feedback, 0, 1, 0.1, 0.01, 0.001));
1073         g->ec_pan=GTK_ADJUSTMENT(gtk_adjustment_new(vtt->ec_pan, -1.0, 1, 0.1, 0.01, 0.001));
1074         g->ec_volume=GTK_ADJUSTMENT(gtk_adjustment_new(vtt->ec_volume, 0.0, 3.0, 0.1, 0.01, 0.001));
1075
1076         g->ec_lengthd=new tX_extdial("Duration", g->ec_length, &vtt->sp_ec_length);
1077         p->add_client_widget(g->ec_lengthd->get_widget());
1078         gui_set_tooltip(g->ec_lengthd->get_entry(), "Adjust the length of the echo buffer.");
1079
1080         g->ec_feedbackd=new tX_extdial("Feedback", g->ec_feedback, &vtt->sp_ec_feedback);
1081         p->add_client_widget(g->ec_feedbackd->get_widget());
1082         gui_set_tooltip(g->ec_feedbackd->get_entry(), "Adjust the feedback of the echo effect. Note that a value of 1 will result in a constant signal.");
1083
1084         g->ec_volumed=new tX_extdial("Volume", g->ec_volume, &vtt->sp_ec_volume);
1085         p->add_client_widget(g->ec_volumed->get_widget());
1086         gui_set_tooltip(g->ec_volumed->get_entry(), "Adjust the volume of the echo effect.");
1087
1088         g->ec_pand=new tX_extdial("Pan", g->ec_pan, &vtt->sp_ec_pan);
1089         p->add_client_widget(g->ec_pand->get_widget());
1090         gui_set_tooltip(g->ec_pand->get_entry(), "Adjust the panning of the echo effect.");
1091
1092         gtk_box_pack_start(GTK_BOX(g->fx_box), p->get_widget(), WID_FIX);
1093         
1094         g->stereo_fx_box=gtk_vbox_new(FALSE, 0);
1095         gtk_box_pack_start(GTK_BOX(g->control_subbox), g->stereo_fx_box, WID_FIX);
1096         gtk_widget_show(g->stereo_fx_box);
1097         
1098         dummy=gtk_button_new_with_label("Stereo FX");
1099         gtk_container_foreach(GTK_CONTAINER(dummy), (GtkCallback) tX_panel_make_label_bold, NULL);
1100         gtk_widget_show(dummy);
1101         g->stereo_fx_button=dummy;
1102         gui_set_tooltip(g->stereo_fx_button, "Click here to load a stereo LADSPA plugin. You will get a menu from which you can choose which plugin to load.");
1103         gtk_box_pack_start(GTK_BOX(g->stereo_fx_box), dummy, WID_FIX);
1104
1105         /* Output */
1106         
1107         tempbox=gtk_hbox_new(FALSE,2);
1108         gtk_widget_show(tempbox);
1109         gtk_box_pack_end(GTK_BOX(g->control_box), tempbox, WID_FIX);
1110         
1111         tempbox2=gtk_vbox_new(FALSE,0);
1112         gtk_widget_show(tempbox2);
1113         gtk_box_pack_start(GTK_BOX(tempbox), tempbox2, WID_FIX);
1114         
1115         g->pitch=GTK_ADJUSTMENT(gtk_adjustment_new(vtt->rel_pitch, -3, +3, 0.1, 0.01, 0.001));
1116         g->pan=GTK_ADJUSTMENT(gtk_adjustment_new(0, -1, 1, 0.1, 0.01, 0.001));
1117
1118         g->pitchd=new tX_extdial("Pitch", g->pitch, &vtt->sp_pitch);
1119         gui_set_tooltip(g->pitchd->get_entry(), "Adjust this turntable's pitch.");
1120
1121         gtk_box_pack_start(GTK_BOX(tempbox2), g->pitchd->get_widget(), WID_FIX);
1122
1123         g->pand=new tX_extdial("Pan", g->pan, &vtt->sp_pan);
1124         gtk_box_pack_start(GTK_BOX(tempbox2), g->pand->get_widget(), WID_FIX);
1125         gui_set_tooltip(g->pand->get_entry(), "Specifies the position of this turntable within the stereo spectrum: -1 -> left, 0-> center, 1->right.");
1126
1127         tempbox3=gtk_hbox_new(FALSE,2);
1128         gtk_widget_show(tempbox3);
1129
1130         g->mute=gtk_check_button_new_with_label("M");
1131         gtk_box_pack_start(GTK_BOX(tempbox3), g->mute, WID_FIX);
1132         g_signal_connect(G_OBJECT(g->mute),"clicked", (GtkSignalFunc) mute_volume, vtt);
1133         gtk_widget_show(g->mute);
1134         gui_set_tooltip(g->mute, "Mute this turntable's mixer output.");
1135
1136         g->solo=gtk_check_button_new_with_label("S");
1137         gtk_box_pack_start(GTK_BOX(tempbox3), g->solo, WID_FIX);
1138         g_signal_connect(G_OBJECT(g->solo),"clicked", (GtkSignalFunc) solo_vtt, vtt);
1139         gtk_widget_show(g->solo);
1140         gui_set_tooltip(g->solo, "Allow only this and other solo-switched turntabels' signal to be routed to the mixer.");
1141
1142         gtk_box_pack_start(GTK_BOX(tempbox2), tempbox3, WID_FIX);
1143
1144         tempbox2=gtk_hbox_new(FALSE,0);
1145         gtk_widget_show(tempbox2);
1146         gtk_box_pack_start(GTK_BOX(tempbox), tempbox2, WID_FIX);
1147         
1148         g->volume=GTK_ADJUSTMENT(gtk_adjustment_new(2.0-vtt->rel_volume, 0, 2, 0.01, 0.01, 0.01));
1149         dummy=gtk_vscale_new(GTK_ADJUSTMENT(g->volume)); 
1150         gtk_scale_set_draw_value(GTK_SCALE(dummy), False);
1151         gui_set_tooltip(dummy, "Adjust this turntable's volume.");
1152         g_signal_connect(G_OBJECT(dummy), "button_press_event", (GtkSignalFunc) tX_seqpar::tX_seqpar_press, &vtt->sp_volume);   
1153
1154         gtk_box_pack_start(GTK_BOX(tempbox2), dummy, WID_FIX);
1155         gtk_widget_show(dummy);
1156
1157         g->flash=gtk_tx_flash_new();
1158         gtk_box_pack_start(GTK_BOX(tempbox2), g->flash, WID_FIX);
1159         gtk_widget_show(g->flash);              
1160
1161 #ifndef USE_FILECHOOSER
1162         g->file_dialog=NULL;
1163 #endif
1164         gui_connect_signals(vtt);
1165         
1166         g->audio_minimized_panel_bar_button=NULL;
1167         g->control_minimized_panel_bar_button=NULL;
1168         g->file_menu=NULL;
1169         g->mouse_mapping_menu=NULL;
1170         g->mouse_mapping_menu_x=NULL;
1171         g->mouse_mapping_menu_y=NULL;
1172         
1173         g->adjust_dialog=NULL;
1174         
1175         gui_set_name(vtt, vtt->name);   
1176 }
1177
1178 void fx_up(GtkWidget *wid, vtt_fx *effect)
1179 {
1180         vtt_class *vtt;
1181         
1182         vtt=(vtt_class*)effect->get_vtt();
1183         vtt->effect_up(effect);
1184 }
1185
1186 void fx_down(GtkWidget *wid, vtt_fx *effect)
1187 {
1188         vtt_class *vtt;
1189         
1190         vtt=(vtt_class*)effect->get_vtt();
1191         vtt->effect_down(effect);
1192 }
1193
1194 void fx_kill(GtkWidget *wid, vtt_fx_ladspa *effect)
1195 {
1196         vtt_class *vtt;
1197         
1198         vtt=(vtt_class*)effect->get_vtt();
1199         vtt->effect_remove(effect);
1200 }
1201
1202 GtkWidget *vg_create_fx_bar(vtt_class *vtt, vtt_fx *effect, int showdel)
1203 {
1204         GtkWidget *box;
1205         GtkWidget *pixmap;
1206         GtkWidget *button;
1207         
1208         box=gtk_hbox_new(FALSE,0);
1209
1210         if (showdel) {
1211                 button=gtk_button_new();
1212                 pixmap=tx_pixmap_widget(FX_CLOSE);
1213                 gtk_container_add (GTK_CONTAINER (button), pixmap);     
1214                 gtk_box_pack_end(GTK_BOX(box), button, WID_FIX);
1215                 gtk_widget_show(pixmap);
1216                 gtk_widget_show(button);
1217                 g_signal_connect(G_OBJECT(button), "clicked", (GtkSignalFunc) fx_kill, (void *) effect);
1218         }
1219
1220         button=gtk_button_new();
1221         pixmap=tx_pixmap_widget(FX_DOWN);
1222         gtk_container_add (GTK_CONTAINER (button), pixmap);     
1223         gtk_box_pack_end(GTK_BOX(box), button, WID_FIX);
1224         gtk_widget_show(pixmap);
1225         gtk_widget_show(button);
1226         g_signal_connect(G_OBJECT(button), "clicked", (GtkSignalFunc) fx_down, (void *) effect);
1227
1228         button=gtk_button_new();
1229         pixmap=tx_pixmap_widget(FX_UP);
1230         gtk_container_add (GTK_CONTAINER (button), pixmap);     
1231         gtk_box_pack_end(GTK_BOX(box), button, WID_FIX);
1232         gtk_widget_show(pixmap);
1233         gtk_widget_show(button);
1234         g_signal_connect(G_OBJECT(button), "clicked", (GtkSignalFunc) fx_up, (void *) effect);
1235         
1236         gtk_widget_show(box);
1237         
1238         return box;
1239 }
1240
1241 int gtk_box_get_widget_pos(GtkBox *box, GtkWidget *child)
1242 {
1243         int i=0;
1244         GList *list;
1245  
1246         list = box->children;
1247         while (list)
1248         {
1249                 GtkBoxChild *child_info;
1250                 child_info = (GtkBoxChild *) list->data;
1251                 if (child_info->widget == child)
1252                 break;
1253                 list = list->next; i++;
1254         }
1255         return i;
1256 }
1257
1258 void vg_move_fx_panel_up(GtkWidget *wid, vtt_class *vtt, bool stereo)
1259 {
1260         GtkWidget *box=(stereo ? vtt->gui.stereo_fx_box : vtt->gui.fx_box);
1261         int pos=gtk_box_get_widget_pos(GTK_BOX(box), wid);
1262         gtk_box_reorder_child(GTK_BOX(box), wid, pos-1);
1263 }
1264
1265 void vg_move_fx_panel_down(GtkWidget *wid, vtt_class *vtt, bool stereo)
1266 {
1267         GtkWidget *box=(stereo ? vtt->gui.stereo_fx_box : vtt->gui.fx_box);
1268         int pos=gtk_box_get_widget_pos(GTK_BOX(box), wid);
1269         gtk_box_reorder_child(GTK_BOX(box), wid, pos+1);
1270 }
1271
1272 static gint vg_show_fx_info(GtkWidget *wid, vtt_fx *effect)
1273 {
1274         tx_l_note(effect->get_info_string());
1275         return TRUE;
1276 }
1277
1278 void vg_toggle_drywet(GtkWidget *wid, vtt_fx *effect)
1279 {
1280         effect->toggle_drywet();
1281 }
1282
1283 static gint vg_show_fx_menu(GtkWidget *wid, GdkEventButton *event, vtt_fx *effect)
1284 {
1285         if (event->button==3) {
1286                 GtkWidget *menu=gtk_menu_new();
1287                 GtkWidget *item=gtk_menu_item_new_with_label("View Plugin Details");
1288                 gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
1289                 gtk_widget_set_sensitive(item, (effect->has_drywet_feature()!=NOT_DRYWET_CAPABLE));
1290                 gtk_widget_show(item);
1291                 g_signal_connect(G_OBJECT(item), "activate", G_CALLBACK(vg_show_fx_info), effect);
1292                 
1293                 switch (effect->has_drywet_feature()) {
1294                         case (NOT_DRYWET_CAPABLE):
1295                                 item=gtk_menu_item_new_with_label("Add Dry/Wet Control");
1296                                 gtk_widget_set_sensitive(item, FALSE);
1297                                 break;
1298                         case (DRYWET_ACTIVE):
1299                                 item=gtk_menu_item_new_with_label("Remove Dry/Wet Control");
1300                                 break;
1301                         case (DRYWET_AVAILABLE):
1302                                 item=gtk_menu_item_new_with_label("Add Dry/Wet Control");
1303                                 break;
1304                 }
1305                 
1306                 g_signal_connect(G_OBJECT(item), "activate", G_CALLBACK(vg_toggle_drywet), effect);     
1307                 gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
1308                 gtk_widget_show(item);
1309                 
1310                 item = gtk_menu_item_new();
1311                 gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
1312                 gtk_widget_set_sensitive(item, FALSE);
1313                 gtk_widget_show(item);
1314         
1315                 item=gtk_menu_item_new_with_label("Up");
1316                 gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
1317                 gtk_widget_show(item);
1318                 g_signal_connect(G_OBJECT(item), "activate", G_CALLBACK(fx_up), effect);
1319         
1320                 item=gtk_menu_item_new_with_label("Down");
1321                 gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
1322                 gtk_widget_show(item);
1323                 g_signal_connect(G_OBJECT(item), "activate", G_CALLBACK(fx_down), effect);
1324         
1325                 item=gtk_menu_item_new_with_label("Delete");
1326                 gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
1327                 gtk_widget_set_sensitive(item, (effect->has_drywet_feature()!=NOT_DRYWET_CAPABLE));
1328                 gtk_widget_show(item);
1329                 g_signal_connect(G_OBJECT(item), "activate", G_CALLBACK(fx_kill), effect);
1330         
1331                 gtk_menu_popup (GTK_MENU(menu), NULL, NULL, NULL, NULL, 0, 0);
1332         
1333                 /* gtk+ is really waiting for this.. */
1334                 g_signal_emit_by_name(G_OBJECT(wid), "released", effect);
1335                 return TRUE;
1336         }
1337         return FALSE;
1338 }
1339
1340 void vg_create_fx_gui(vtt_class *vtt, vtt_fx_ladspa *effect, LADSPA_Plugin *plugin)
1341 {
1342         char buffer[1024];
1343         
1344         vtt_gui *g;
1345         g=&vtt->gui;    
1346         tX_panel *p;
1347         list <tX_seqpar_vttfx *> :: iterator sp;
1348         
1349         strcpy(buffer, plugin->getLabel());
1350         if (strlen(buffer) > 6) {
1351                 buffer[5]='.';
1352                 buffer[6]='.';
1353                 buffer[7]='.';
1354                 buffer[8]=0;
1355         }
1356
1357         p=new tX_panel(buffer, g->control_subbox);
1358         
1359         p->add_client_widget(vg_create_fx_bar(vtt, effect, 1));
1360         
1361         for (sp = effect->controls.begin(); sp != effect->controls.end(); sp++) {
1362                         p->add_client_widget((*sp)->get_widget());
1363         }
1364
1365         g_signal_connect(G_OBJECT(p->get_labelbutton()), "button_press_event", (GtkSignalFunc) vg_show_fx_menu, (void *) effect);
1366         gui_set_tooltip(p->get_labelbutton(), "Right-click to access menu.");
1367         effect->set_panel_widget(p->get_widget());
1368         effect->set_panel(p);
1369
1370         gtk_box_pack_start(GTK_BOX((effect->is_stereo() ? g->stereo_fx_box : g->fx_box)), p->get_widget(), WID_FIX);
1371 }
1372
1373 void gui_set_filename (vtt_class *vtt, char *newname)
1374 {
1375         gtk_button_set_label(GTK_BUTTON(vtt->gui.file), newname);
1376 }
1377
1378 void gui_update_display(vtt_class *vtt)
1379 {
1380         nicer_filename(global_filename_buffer, vtt->filename);
1381         gtk_button_set_label(GTK_BUTTON(vtt->gui.file), global_filename_buffer);
1382         gtk_tx_set_data(GTK_TX(vtt->gui.display), vtt->buffer, vtt->samples_in_buffer);
1383 }
1384
1385 void gui_hide_control_panel(vtt_class *vtt, bool hide) {
1386         if (hide) {
1387                 gtk_widget_hide(vtt->gui.control_box);
1388                 vtt->gui.control_minimized_panel_bar_button=tx_xpm_button_new(MIN_CONTROL, vtt->name, 0, &vtt->gui.control_minimized_panel_bar_label);
1389                 g_signal_connect(G_OBJECT(vtt->gui.control_minimized_panel_bar_button), "clicked", (GtkSignalFunc) unminimize_control_panel, vtt);
1390                 gtk_widget_show(vtt->gui.control_minimized_panel_bar_button);
1391                 add_to_panel_bar(vtt->gui.control_minimized_panel_bar_button);
1392         } else {
1393                 gtk_widget_show(vtt->gui.control_box);
1394                 remove_from_panel_bar(vtt->gui.control_minimized_panel_bar_button);
1395                 if (!tX_shutdown) gtk_widget_destroy(vtt->gui.control_minimized_panel_bar_button);
1396                 vtt->gui.control_minimized_panel_bar_button=NULL;
1397         }
1398 }
1399
1400 void gui_hide_audio_panel(vtt_class *vtt, bool hide) {
1401         if (hide) {
1402                 gtk_widget_hide(vtt->gui.audio_box);
1403                 vtt->gui.audio_minimized_panel_bar_button=tx_xpm_button_new(MIN_AUDIO, vtt->name, 0, &vtt->gui.audio_minimized_panel_bar_label);
1404                 g_signal_connect(G_OBJECT(vtt->gui.audio_minimized_panel_bar_button), "clicked", (GtkSignalFunc) unminimize_audio_panel, vtt);          
1405                 gtk_widget_show(vtt->gui.audio_minimized_panel_bar_button);
1406                 add_to_panel_bar(vtt->gui.audio_minimized_panel_bar_button);
1407         } else {
1408                 gtk_widget_show(vtt->gui.audio_box);
1409                 remove_from_panel_bar(vtt->gui.audio_minimized_panel_bar_button);
1410                 if (!tX_shutdown) gtk_widget_destroy(vtt->gui.audio_minimized_panel_bar_button);
1411                 vtt->gui.audio_minimized_panel_bar_button=NULL;
1412         }
1413 }
1414
1415 void delete_gui(vtt_class *vtt)
1416 {
1417         if (vtt->gui.control_minimized_panel_bar_button!=NULL) gui_hide_control_panel(vtt, false);
1418         if (vtt->gui.audio_minimized_panel_bar_button!=NULL) gui_hide_audio_panel(vtt, false);
1419
1420         delete vtt->gui.main_panel;
1421         delete vtt->gui.trigger_panel;
1422         
1423         delete vtt->gui.pitchd;
1424         delete vtt->gui.pand;
1425         
1426         delete vtt->gui.lp_gaind;
1427         delete vtt->gui.lp_resod;
1428         delete vtt->gui.lp_freqd;
1429         delete vtt->gui.lp_panel;
1430         
1431         delete vtt->gui.ec_lengthd;
1432         delete vtt->gui.ec_feedbackd;
1433         delete vtt->gui.ec_volumed;
1434         delete vtt->gui.ec_pand;
1435         delete vtt->gui.ec_panel;
1436
1437         gtk_widget_destroy(vtt->gui.control_box);
1438         gtk_widget_destroy(vtt->gui.audio_box);
1439         if (vtt->gui.file_menu) gtk_widget_destroy(vtt->gui.file_menu);
1440         if (vtt->gui.mouse_mapping_menu) gtk_widget_destroy(vtt->gui.mouse_mapping_menu);
1441         if (vtt->gui.ladspa_menu) gtk_widget_destroy(vtt->gui.ladspa_menu);
1442 }
1443
1444 void cleanup_vtt(vtt_class *vtt)
1445 {
1446         gtk_tx_cleanup_pos_display(GTK_TX(vtt->gui.display));   
1447         gtk_tx_flash_set_level(vtt->gui.flash, 0.0, 0.0);
1448         gtk_tx_flash_clear(vtt->gui.flash);
1449         vtt->cleanup_required=false;
1450 }
1451
1452 void update_all_vtts()
1453 {
1454         list <vtt_class *> :: iterator vtt;
1455         f_prec temp,temp2;
1456         
1457         for (vtt=vtt_class::main_list.begin(); vtt!=vtt_class::main_list.end(); vtt++)
1458         {
1459                 if ((*vtt)->is_playing) {
1460                         gtk_tx_update_pos_display(GTK_TX((*vtt)->gui.display), (*vtt)->pos_i, (*vtt)->mute);
1461                         temp=(*vtt)->max_value*(*vtt)->res_volume*vtt_class::vol_channel_adjust;
1462                         (*vtt)->max_value=0;
1463                         temp2=(*vtt)->max_value2*(*vtt)->res_volume*vtt_class::vol_channel_adjust;
1464                         (*vtt)->max_value2=0;
1465                         gtk_tx_flash_set_level((*vtt)->gui.flash, temp, temp2);
1466                 }
1467                 
1468                 if ((*vtt)->needs_cleaning_up()) {
1469                         cleanup_vtt((*vtt));
1470                 }
1471         }
1472 }
1473
1474 void cleanup_all_vtts()
1475 {
1476         list <vtt_class *> :: iterator vtt;
1477         
1478         for (vtt=vtt_class::main_list.begin(); vtt!=vtt_class::main_list.end(); vtt++)
1479         {
1480                 if ((*vtt)->buffer) gtk_tx_cleanup_pos_display(GTK_TX((*vtt)->gui.display));
1481                 gtk_tx_flash_set_level((*vtt)->gui.flash, 0.0, 0.0);
1482                 gtk_tx_flash_clear((*vtt)->gui.flash);
1483         }
1484 }
1485
1486 void gui_clear_master_button(vtt_class *vtt)
1487 {
1488         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(vtt->gui.sync_master), 0);
1489 }
1490
1491 void gui_show_frame(vtt_class *vtt, int show)
1492 {
1493         gtk_tx_show_frame(GTK_TX(vtt->gui.display), show);
1494 }
1495
1496 #define vgui (*vtt)->gui
1497 #define v (*vtt)
1498
1499 void vg_enable_critical_buttons(int enable)
1500 {
1501         list <vtt_class *> :: iterator vtt;
1502         for (vtt=vtt_class::main_list.begin(); vtt!=vtt_class::main_list.end(); vtt++)
1503         {
1504                 gtk_widget_set_sensitive(vgui.del, enable);
1505                 gtk_widget_set_sensitive(vgui.sync_master, enable);
1506         }
1507 }
1508
1509 void vg_init_all_non_seqpars()
1510 {
1511         list <vtt_class *> :: iterator vtt;
1512         
1513         for (vtt=vtt_class::main_list.begin(); vtt!=vtt_class::main_list.end(); vtt++)
1514         {
1515                 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON((*vtt)->gui.autotrigger), (*vtt)->autotrigger);
1516                 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON((*vtt)->gui.sync_master), (*vtt)->is_sync_master);
1517         }       
1518 }
1519
1520 f_prec gui_get_audio_x_zoom(vtt_class *vtt) {
1521         return gtk_tx_get_zoom(GTK_TX(vtt->gui.display));
1522 }
1523
1524 /* Yes, this is yet another evil hack. Fix it :) */
1525 int vttgui_zoom_depth=0;
1526
1527 extern void gui_set_audio_x_zoom(vtt_class *vtt, f_prec value) {
1528         if (vttgui_zoom_depth==0) {
1529                 vttgui_zoom_depth=1;
1530                 gtk_range_set_value(GTK_RANGE(vtt->gui.zoom), value*100.0);
1531                 vttgui_zoom_depth=0;
1532         } else {
1533                 gtk_tx_set_zoom(GTK_TX(vtt->gui.display), value);
1534         }
1535 }