Fixing the character set (now utf-8).
[terminatorX.git] / src / tX_dialog.cc
1 /*
2     terminatorX - realtime audio scratching software
3     Copyright (C) 1999-2011  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_dialog.cc
20  
21     Description: Contains the implementation of the Options and About
22                  Dialogs. (And some really ugly "WE WANT TO 
23                  TYPE LESS" macros)
24                  
25     Changes:
26     
27     28 Jul 1999: Now display compiletime settings in the about dialog.
28 */    
29
30 #include "config.h"
31 #include "tX_types.h"
32 #include "tX_global.h"
33 #include "tX_dialog.h"
34 #include <gtk/gtk.h>
35 #include <string.h>
36 #include <gdk/gdk.h>
37 #include "tX_icon.h"
38 #include "tX_glade_interface.h"
39 #include "tX_glade_support.h"
40
41 #include "tX_widget.h"
42 #include "tX_flash.h"
43
44 #ifndef WIN32
45 #include <X11/extensions/XInput.h>
46 #include <X11/X.h>
47 #endif
48
49 #include "license.c"
50 #include "tX_mastergui.h"
51 #include "version.h"
52 #include "tX_vtt.h"
53 #include <dirent.h>
54 #include "tX_engine.h"
55
56 #ifdef USE_SCHEDULER
57 #include <sched.h>
58 #include <pthread.h>
59 #endif
60
61 #ifdef USE_JACK
62 extern void jack_check();
63 #endif
64
65 extern char *logo_xpm[];
66 GtkWidget *opt_dialog;
67 int opt_hidden=0;
68
69 static GtkWidget *last_alsa_device_widget=NULL;
70 static GtkWidget *alsa_device_entry=NULL;
71
72 void apply_options(GtkWidget *dialog) {
73         /* Audio */
74         if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "alsa_driver")))) {
75                 globals.audiodevice_type=ALSA;
76         } else if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "oss_driver")))) {
77                 globals.audiodevice_type=OSS;
78         } else if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "jack_driver")))) {
79                 globals.audiodevice_type=JACK;
80         }
81         globals.use_realtime=gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "use_realtime")));
82         
83         /* Audio: OSS */
84         strcpy(globals.oss_device, gtk_entry_get_text(GTK_ENTRY(GTK_COMBO(lookup_widget(dialog, "oss_audio_device"))->entry)));
85         globals.oss_buff_no=(int) gtk_spin_button_get_value(GTK_SPIN_BUTTON(lookup_widget(dialog, "oss_buffers")));
86         globals.oss_buff_size=(int) gtk_range_get_value(GTK_RANGE(lookup_widget(dialog, "oss_buffersize")));
87         globals.oss_samplerate=atoi(gtk_entry_get_text(GTK_ENTRY(GTK_COMBO(lookup_widget(dialog, "oss_samplerate"))->entry)));
88         
89         /* Audio: ALSA */
90         strcpy(globals.alsa_device_id, gtk_entry_get_text(GTK_ENTRY(GTK_COMBO(lookup_widget(dialog, "alsa_audio_device"))->entry)));
91         globals.alsa_buffer_time=(int) gtk_range_get_value(GTK_RANGE(lookup_widget(dialog, "alsa_buffer_time")));
92         globals.alsa_buffer_time*=1000;
93         globals.alsa_period_time=(int) gtk_range_get_value(GTK_RANGE(lookup_widget(dialog, "alsa_period_time")));
94         globals.alsa_period_time*=1000;
95         globals.alsa_samplerate=atoi(gtk_entry_get_text(GTK_ENTRY(GTK_COMBO(lookup_widget(dialog, "alsa_samplerate"))->entry)));        
96         globals.alsa_free_hwstats=gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "alsa_free_hwstats")));
97         
98         /* TODO: JACK
99         */
100         
101         /* Input */
102         globals.xinput_enable=(gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "xinput_enable")))==TRUE);
103         strcpy(globals.xinput_device, gtk_entry_get_text(GTK_ENTRY(GTK_COMBO(lookup_widget(dialog, "xinput_device"))->entry)));
104         globals.mouse_speed=gtk_range_get_value(GTK_RANGE(lookup_widget(dialog, "mouse_speed")));
105         globals.sense_cycles=(int) gtk_range_get_value(GTK_RANGE(lookup_widget(dialog, "stop_sense_cycles")));
106         globals.vtt_inertia=gtk_range_get_value(GTK_RANGE(lookup_widget(dialog, "vtt_inertia")));
107         
108         /* User Interface */ 
109         globals.show_nag=(gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "startup_nagbox")))==TRUE);
110         globals.tooltips=(gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "mainwin_tooltips")))==TRUE);
111         globals.filename_length=gtk_spin_button_get_value_as_int(GTK_SPIN_BUTTON(lookup_widget(dialog, "filename_length")));
112         if (globals.tooltips) gtk_tooltips_enable(gui_tooltips);
113         else gtk_tooltips_disable(gui_tooltips);
114
115         if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "buttons_text_only")))) {
116                 globals.button_type=BUTTON_TYPE_TEXT;
117         } else if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "buttons_icon_only")))) {
118                 globals.button_type=BUTTON_TYPE_ICON;
119         } else if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "buttons_text_and_icon")))) {
120                 globals.button_type=BUTTON_TYPE_BOTH;
121         }
122         
123         globals.update_delay=(int) gtk_range_get_value(GTK_RANGE(lookup_widget(dialog, "update_delay")));
124         globals.update_idle=(int) gtk_range_get_value(GTK_RANGE(lookup_widget(dialog, "update_idle")));
125         globals.flash_response=gtk_range_get_value(GTK_RANGE(lookup_widget(dialog, "vumeter_decay")));
126         
127         /* Audio Colors */
128         
129         strcpy(globals.wav_display_bg_focus, (char *) g_object_get_data(G_OBJECT(lookup_widget(dialog, "wav_display_bg_focus")), "Color"));
130         strcpy(globals.wav_display_bg_no_focus, (char *) g_object_get_data(G_OBJECT(lookup_widget(dialog, "wav_display_bg_no_focus")), "Color"));
131         strcpy(globals.wav_display_fg_focus, (char *) g_object_get_data(G_OBJECT(lookup_widget(dialog, "wav_display_fg_focus")), "Color"));
132         strcpy(globals.wav_display_fg_no_focus, (char *) g_object_get_data(G_OBJECT(lookup_widget(dialog, "wav_display_fg_no_focus")), "Color"));
133         strcpy(globals.wav_display_cursor, (char *) g_object_get_data(G_OBJECT(lookup_widget(dialog, "wav_display_cursor")), "Color"));
134         strcpy(globals.wav_display_cursor_mute, (char *) g_object_get_data(G_OBJECT(lookup_widget(dialog, "wav_display_cursor_mute")), "Color"));
135
136         /* VU Colors */ 
137         strcpy(globals.vu_meter_bg, (char *) g_object_get_data(G_OBJECT(lookup_widget(dialog, "vu_meter_bg")), "Color"));
138         strcpy(globals.vu_meter_loud, (char *) g_object_get_data(G_OBJECT(lookup_widget(dialog, "vu_meter_loud")), "Color"));
139         strcpy(globals.vu_meter_normal, (char *) g_object_get_data(G_OBJECT(lookup_widget(dialog, "vu_meter_normal")), "Color"));
140
141         globals.vu_meter_border_intensity=gtk_range_get_value(GTK_RANGE(lookup_widget(dialog, "vu_meter_border_intensity")));
142         
143         /* Misc */
144         strcpy(globals.file_editor, gtk_entry_get_text(GTK_ENTRY(lookup_widget(dialog, "soundfile_editor"))));
145         strcpy(globals.lrdf_path, gtk_entry_get_text(GTK_ENTRY(lookup_widget(dialog, "ladspa_rdf_path"))));
146         globals.compress_set_files=(gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "compress_set_files")))==TRUE);        
147         globals.prelis=(gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "prelisten_enabled")))==TRUE);
148         globals.restore_midi_connections=(gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "reconnect_enabled")))==TRUE);
149         globals.quit_confirm=(gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "quit_confirm")))==TRUE);
150         globals.verbose_plugin_loading=(gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "verbose_plugin_loading")))==TRUE);
151         globals.force_nonrt_plugins=(gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "force_nonrt_plugins")))==TRUE);
152         
153         /* update colors */
154         std::list<vtt_class *>::iterator vtt;
155         
156         for (vtt=vtt_class::main_list.begin(); vtt!=vtt_class::main_list.end(); vtt++) {
157                 gtk_tx_update_colors(GTK_TX((*vtt)->gui.display));
158                 gtk_widget_queue_draw((*vtt)->gui.display);
159                 gtk_tx_flash_update_colors(GTK_TX_FLASH((*vtt)->gui.flash));
160                 gtk_widget_queue_draw((*vtt)->gui.flash);
161         }
162         
163         gtk_tx_flash_update_colors(GTK_TX_FLASH(main_flash));
164         gtk_widget_queue_draw(main_flash);
165         
166 #ifdef USE_JACK
167         jack_check();
168 #endif  
169 }
170
171
172 #define WID_DYN TRUE, TRUE, 0
173 #define WID_FIX FALSE, FALSE, 0
174
175 #define my_new_subsec(s); \
176         separator=gtk_hseparator_new(); \
177         gtk_box_pack_start(GTK_BOX(vbox), separator, WID_DYN);\
178         gtk_widget_show(separator); \
179         label=gtk_label_new(s); \
180         gtk_misc_set_alignment (GTK_MISC(label), 0 ,0.5); \
181         gtk_box_pack_start(GTK_BOX(vbox), label, WID_DYN); \
182         gtk_widget_show(label); 
183
184 #define my_new_button(btn, s); \
185         btn=gtk_button_new_with_label(s); \
186         gtk_box_pack_start(GTK_BOX(aa), btn, WID_DYN); \
187         gtk_widget_show(btn);
188         
189
190 #define begin_box(); box=gtk_hbox_new(FALSE, 5);
191
192 #define begin_hom_box(); box=gtk_hbox_new(TRUE, 5);
193
194 #define end_box(); gtk_box_pack_start(GTK_BOX(vbox), box, WID_DYN); \
195         gtk_widget_show(box);
196
197 #define add_widget_dyn(wid); gtk_box_pack_start(GTK_BOX(box), wid, WID_DYN);\
198         gtk_widget_show(wid);
199         
200 #define add_widget_fix(wid); gtk_box_pack_start(GTK_BOX(box), wid, WID_FIX);\
201         gtk_widget_show(wid);
202
203 #define add_expl(s); label=gtk_label_new(s); \
204         gtk_misc_set_alignment(GTK_MISC(label), 0.5, 0.5);\
205         add_widget_fix(label);
206
207 #define add_expl_dyn(s); label=gtk_label_new(s); \
208         gtk_misc_set_alignment(GTK_MISC(label), 0.5, 0.5);\
209         add_widget_dyn(label);
210
211 #ifdef USE_ALSA
212 static GList *alsa_devices=NULL;
213
214 GList *get_alsa_device_list() {
215         if (alsa_devices) {
216                 return alsa_devices;
217         }
218         
219         FILE *file;
220         char buffer[PATH_MAX+1];
221         alsa_devices=NULL;
222         
223         if ((file = fopen("/proc/asound/pcm", "r"))) {
224                 while(fgets(buffer, PATH_MAX, file)) {
225                         buffer[PATH_MAX]=0;
226                         if (strlen(buffer)) buffer[strlen(buffer)-1]=0;
227                         if(strstr(buffer, "playback")) {
228                                 char foo[PATH_MAX];
229                                 char tmp[PATH_MAX];
230                                 memset(foo, 0, PATH_MAX);
231                                 int card;
232                                 int device;
233  
234                                 sscanf(buffer, "%i-%i: %1024c", &card, &device, foo);
235                                 sprintf(tmp, "hw:%i,%i# %s", card, device, foo);
236                                 
237                                 alsa_devices=g_list_append (alsa_devices, strdup(tmp));
238                         }
239                 }
240                 fclose(file);
241         }
242         
243         return alsa_devices;
244 }
245 #else
246 GList *get_alsa_device_list() {
247         return NULL;
248 }
249 #endif
250
251
252 #ifdef USE_OSS
253 static GList *oss_devices=NULL;
254
255 int oss_select_dsp_only(const struct dirent *entry){
256         return (strstr(entry->d_name, "dsp")!=0);
257 }
258
259 GList *get_oss_device_list() {
260         if (oss_devices) {
261                 return oss_devices;
262         }
263                 
264     struct dirent **namelist;
265     int n,i;
266     n = scandir("/dev", &namelist, oss_select_dsp_only, alphasort);
267     
268         oss_devices=NULL;
269         
270     if (n>0) {
271         for (i=0; i<n; i++) {
272                         char buffer[256];
273             sprintf(buffer, "/dev/%s", namelist[i]->d_name);
274             free(namelist[i]);
275                         oss_devices=g_list_append (oss_devices, strdup(buffer));
276                 }
277         }
278         
279         return oss_devices;
280 }
281 #endif
282
283 static GList *sampling_rates=NULL;
284
285 GList *get_sampling_rates_list() {
286         if (sampling_rates) {
287                 return sampling_rates;
288         }
289
290         sampling_rates=g_list_append(sampling_rates, (void *) "22000");
291         sampling_rates=g_list_append(sampling_rates, (void *) "32000");
292         sampling_rates=g_list_append(sampling_rates, (void *) "44100");
293         sampling_rates=g_list_append(sampling_rates, (void *) "48000");
294
295         return sampling_rates;  
296 }
297
298 static GList *xinput_devices=NULL;
299
300 GList *get_xinput_devices_list() {
301         if (xinput_devices) {
302                 return xinput_devices;
303         }
304         
305         int devmax;
306         Display *dpy=XOpenDisplay(NULL);
307         XDeviceInfo *xdev=XListInputDevices(dpy, &devmax);
308         XCloseDisplay(dpy);
309
310         for (int i=0; i<devmax; i++) {
311                 xinput_devices=g_list_append(xinput_devices, strdup(xdev[i].name));
312         }
313         
314         XFreeDeviceList(xdev);
315         
316         return xinput_devices;
317 }
318
319 #define MAX_COLORS 10
320 char *colors[MAX_COLORS]={ NULL };
321
322 #define set_color_button(s,g); \
323         sprintf(tmp, "<span foreground=\"%s\"><b>%s</b></span>", s, s);\
324         gtk_label_set_markup(GTK_LABEL(gtk_container_get_children(GTK_CONTAINER(lookup_widget(dialog, g)))->data), tmp);\
325         strcpy(colors[ctr], s);\
326         g_object_set_data(G_OBJECT(lookup_widget(dialog, g)), "Color", colors[ctr]);\
327         ctr++;
328
329
330 void init_tx_options(GtkWidget *dialog) {
331         GtkTooltips *tooltips=GTK_TOOLTIPS(lookup_widget(dialog, "tooltips"));
332         
333         if (colors[0]==NULL) {
334                 for (int i=0; i<MAX_COLORS; i++) {
335                         colors[i]=new char[8];
336                         colors[i][0]=0;
337                 }
338         }
339         
340         /* Audio */
341         switch (globals.audiodevice_type) {             
342                 case ALSA: gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "alsa_driver")), 1);
343                         break;
344                 
345                 case JACK: gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "jack_driver")), 1);
346                         break;
347
348                 case OSS: 
349                 default:
350                         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "oss_driver")), 1);
351                         break;
352         }
353
354         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "use_realtime")), globals.use_realtime);
355
356 #ifndef USE_CAPABILITIES
357         /* rt's not configurable without capabilities. */
358         gtk_widget_hide(lookup_widget(dialog, "use_realtime"));
359         gtk_widget_hide(lookup_widget(dialog, "use_realtime_label"));   
360 #endif
361         
362 #ifndef USE_OSS
363         gtk_widget_set_sensitive(lookup_widget(dialog, "oss_driver"), 0);
364         gtk_widget_set_sensitive(lookup_widget(dialog, "oss_audio_device"), 0);
365         gtk_widget_set_sensitive(lookup_widget(dialog, "oss_buffers"), 0);
366         gtk_widget_set_sensitive(lookup_widget(dialog, "oss_buffersize"), 0);
367 #endif
368         
369 #ifndef USE_ALSA
370         gtk_widget_set_sensitive(lookup_widget(dialog, "alsa_driver"), 0);      
371         // TODO: Rest!  
372 #endif
373         
374 #ifndef USE_JACK
375         gtk_widget_set_sensitive(lookup_widget(dialog, "jack_driver"), 0);
376 #endif  
377         
378         /* Audio: OSS */
379         GList *oss_list=get_oss_device_list();
380         if (oss_list) {
381                 gtk_combo_set_popdown_strings(GTK_COMBO(lookup_widget(dialog, "oss_audio_device")), oss_list);
382         }
383         gtk_entry_set_text(GTK_ENTRY(GTK_COMBO(lookup_widget(dialog, "oss_audio_device"))->entry), globals.oss_device);
384
385         gtk_spin_button_set_value(GTK_SPIN_BUTTON(lookup_widget(dialog, "oss_buffers")), globals.oss_buff_no);
386         gtk_range_set_value(GTK_RANGE(lookup_widget(dialog, "oss_buffersize")), globals.oss_buff_size);
387         gtk_tooltips_set_tip(tooltips, lookup_widget(dialog, "oss_buffersize"), "Set the size of the kernel level audio buffers. On slower systems you might have to increase this value (if you hear \"clicks\" or drop-outs). Lower values mean lower latency though.", NULL);        
388         gtk_combo_set_popdown_strings(GTK_COMBO(lookup_widget(dialog, "oss_samplerate")), get_sampling_rates_list());
389         char tmp[64];
390         sprintf(tmp, "%i", globals.oss_samplerate);
391         gtk_entry_set_text(GTK_ENTRY(GTK_COMBO(lookup_widget(dialog, "oss_samplerate"))->entry), tmp);
392         
393         
394         /* Audio: ALSA */
395         GtkCombo *combo=GTK_COMBO(lookup_widget(dialog, "alsa_audio_device"));
396         GList *alsa_list=get_alsa_device_list();
397         last_alsa_device_widget=NULL;
398         alsa_device_entry=combo->entry;
399         
400         if (alsa_list) {
401                 gtk_combo_set_popdown_strings(combo, get_alsa_device_list());
402         }
403         gtk_entry_set_text(GTK_ENTRY(combo->entry), globals.alsa_device_id);
404
405         gtk_range_set_value(GTK_RANGE(lookup_widget(dialog, "alsa_buffer_time")), globals.alsa_buffer_time/1000);
406         gtk_tooltips_set_tip(tooltips, lookup_widget(dialog, "alsa_buffer_time"), "Sets the size of the ALSA ring buffer. On slower systems you might have to increase this value (if you hear \"clicks\" or drop-outs). Lower values mean lower latency though.", NULL);       
407         gtk_range_set_value(GTK_RANGE(lookup_widget(dialog, "alsa_period_time")), globals.alsa_period_time/1000);
408         gtk_tooltips_set_tip(tooltips, lookup_widget(dialog, "alsa_period_time"), "The ALSA period time determines how much audio data will be written to the device at once. It is recommended to set this value to a half or a third of the ALSA buffer time.", NULL);        
409
410         gtk_combo_set_popdown_strings(GTK_COMBO(lookup_widget(dialog, "alsa_samplerate")), get_sampling_rates_list());
411         sprintf(tmp, "%i", globals.alsa_samplerate);
412         gtk_entry_set_text(GTK_ENTRY(GTK_COMBO(lookup_widget(dialog, "alsa_samplerate"))->entry), tmp);
413         
414         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "alsa_free_hwstats")), globals.alsa_free_hwstats);
415         
416         /* Input */
417         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "xinput_enable")), globals.xinput_enable);
418         
419         gtk_combo_set_popdown_strings(GTK_COMBO(lookup_widget(dialog, "xinput_device")), get_xinput_devices_list());
420         gtk_entry_set_text(GTK_ENTRY(GTK_COMBO(lookup_widget(dialog, "xinput_device"))->entry), globals.xinput_device);
421
422         gtk_range_set_value(GTK_RANGE(lookup_widget(dialog, "mouse_speed")), globals.mouse_speed);
423         gtk_tooltips_set_tip(tooltips, lookup_widget(dialog, "mouse_speed"), "The speed of your mouse in scratch mode. Use negative values to invert motion.", NULL);
424         
425         gtk_range_set_value(GTK_RANGE(lookup_widget(dialog, "stop_sense_cycles")), globals.sense_cycles);
426         gtk_tooltips_set_tip(tooltips, lookup_widget(dialog, "stop_sense_cycles"),"If there is no \"motion-event\" for x cycles, where x is the number of cycles you select here, terminatorX assumes mouse motion has stopped. For smaller buffer sizes (=> shorter cycle times) you might have to increase this value", NULL);        
427
428         gtk_range_set_value(GTK_RANGE(lookup_widget(dialog, "vtt_inertia")), globals.vtt_inertia);
429         gtk_tooltips_set_tip(tooltips, lookup_widget(dialog, "vtt_inertia"),"This value defines how fast the turntables will adapt to the speed input - the higher this value, the longer it will take the turntable to actually reach the target speed.", NULL);       
430
431         gtk_spin_button_set_value(GTK_SPIN_BUTTON(lookup_widget(dialog, "filename_length")), globals.filename_length);
432
433         /* User Interface */ 
434         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "startup_nagbox")), globals.show_nag);
435         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "mainwin_tooltips")), globals.tooltips);
436         
437         switch (globals.button_type) {
438                 case BUTTON_TYPE_TEXT:
439                         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "buttons_text_only")), 1);
440                         break;
441                 
442                 case BUTTON_TYPE_ICON:
443                         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "buttons_icon_only")), 1);
444                         break;
445                 
446                 case BUTTON_TYPE_BOTH:
447                 default:
448                         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "buttons_text_and_icon")), 1);
449         }
450         
451         gtk_range_set_value(GTK_RANGE(lookup_widget(dialog, "update_delay")), globals.update_delay);
452         gtk_tooltips_set_tip(tooltips, lookup_widget(dialog, "update_delay"), "How often to update the slow widgets.", NULL);   
453         gtk_range_set_value(GTK_RANGE(lookup_widget(dialog, "update_idle")), globals.update_idle);
454         gtk_tooltips_set_tip(tooltips, lookup_widget(dialog, "update_idle"), "The update thread will idle for the selcted amount of milliseconds. If you want to have a more responsive display update reduce this value - if you have performance problems increase this value.", NULL);       
455         gtk_range_set_value(GTK_RANGE(lookup_widget(dialog, "vumeter_decay")), globals.flash_response);
456         gtk_tooltips_set_tip(tooltips, lookup_widget(dialog, "vumeter_decay"), "Defines how fast the maximum values of the VU meters should be decayed.", NULL);        
457
458         /* Audio Colors */
459         int ctr=0;
460         
461         set_color_button(globals.wav_display_bg_focus, "wav_display_bg_focus");
462         set_color_button(globals.wav_display_bg_no_focus, "wav_display_bg_no_focus");
463         set_color_button(globals.wav_display_fg_focus, "wav_display_fg_focus");
464         set_color_button(globals.wav_display_fg_no_focus, "wav_display_fg_no_focus");
465         set_color_button(globals.wav_display_cursor, "wav_display_cursor");
466         set_color_button(globals.wav_display_cursor_mute, "wav_display_cursor_mute");
467         
468         /* VU Colors */
469         set_color_button(globals.vu_meter_bg, "vu_meter_bg");
470         set_color_button(globals.vu_meter_loud, "vu_meter_loud");
471         set_color_button(globals.vu_meter_normal, "vu_meter_normal");
472         
473         gtk_range_set_value(GTK_RANGE(lookup_widget(dialog, "vu_meter_border_intensity")), globals.vu_meter_border_intensity);
474         
475         /* Misc */
476         gtk_entry_set_text(GTK_ENTRY(lookup_widget(dialog, "soundfile_editor")), globals.file_editor);
477         gtk_entry_set_text(GTK_ENTRY(lookup_widget(dialog, "ladspa_rdf_path")), globals.lrdf_path);
478         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "compress_set_files")), globals.compress_set_files);
479         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "prelisten_enabled")), globals.prelis);
480         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "reconnect_enabled")), globals.restore_midi_connections);
481         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "quit_confirm")), globals.quit_confirm);
482         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "force_nonrt_plugins")), globals.force_nonrt_plugins);     
483         gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(lookup_widget(dialog, "verbose_plugin_loading")), globals.verbose_plugin_loading);       
484 }
485
486 void create_options()
487 {
488         opt_dialog=create_tx_options();
489         tX_set_icon(opt_dialog);
490         init_tx_options(opt_dialog);
491         gtk_widget_show(opt_dialog);
492 }
493
494 void display_options()
495 {
496         if (opt_dialog) {
497                 gdk_window_raise(opt_dialog->window);   
498         } else {
499                 create_options();
500         }
501 }
502
503 GtkWidget *about=NULL;
504
505 void raise_about()
506 {
507         if (about) gdk_window_raise(about->window);
508 }
509
510
511 void destroy_about()
512 {
513         if (about) {    
514                 gtk_widget_destroy(about);
515                 about=NULL;
516         }
517 }
518
519 #define add_about_wid(wid); gtk_box_pack_start(GTK_BOX(box), wid, WID_DYN); \
520         gtk_widget_show(wid);
521
522 #define add_about_wid_fix(wid); gtk_box_pack_start(GTK_BOX(box), wid, WID_FIX); \
523         gtk_widget_show(wid);
524
525 GdkFont *GPL_font=NULL;
526
527 void show_about(int nag)
528 {
529         GtkWidget *window;
530         GtkWidget *btn;
531         GtkWidget *box;
532         GtkWidget *hbox;
533         GtkWidget *label;
534         GtkWidget *sep;
535         GtkWidget *text;
536         GtkWidget *scroll;
537         GtkWidget *iwid;
538         
539         /* Only raise the window if it's already open... */
540         if (about)  {
541                 gdk_window_raise(about->window);
542                 return;
543         }
544         
545         /* Create the window... */
546         window = gtk_window_new(GTK_WINDOW_TOPLEVEL);
547         gtk_container_set_border_width(GTK_CONTAINER(window), 5);
548         gtk_window_set_title(GTK_WINDOW(window), "terminatorX - About");
549         gtk_window_set_position(GTK_WINDOW(window), GTK_WIN_POS_CENTER);
550         gtk_window_set_modal(GTK_WINDOW(window), TRUE);
551         gtk_window_set_resizable(GTK_WINDOW(window), nag ? TRUE: FALSE);
552
553         GdkPixbuf *image=gdk_pixbuf_new_from_xpm_data((const char **)logo_xpm);
554         iwid = gtk_image_new_from_pixbuf(image);
555         
556         if (nag) {
557                 GtkWidget *box=gtk_vbox_new(FALSE, 2);
558                 GtkWidget *box2=gtk_hbox_new(FALSE, 2);
559                 GtkWidget *label;
560                 
561                 gtk_container_add(GTK_CONTAINER(window), box);
562                 gtk_box_pack_start(GTK_BOX(box), iwid, WID_FIX);
563                 gtk_box_pack_start(GTK_BOX(box), box2, WID_FIX);
564                 
565                 label=gtk_label_new(PACKAGE" release "VERSION);
566                 gtk_box_pack_start(GTK_BOX(box2), label, WID_DYN);
567                 gtk_misc_set_alignment(GTK_MISC(label), 0.1, 0.5);
568                 gtk_widget_show(label);
569
570                 label=gtk_label_new("Copyright (C) 1999-2011 by Alexander König");
571                 gtk_box_pack_start(GTK_BOX(box2), label, WID_DYN);
572                 gtk_misc_set_alignment(GTK_MISC(label), 0.9, 0.5);
573                 gtk_widget_show(label);
574                 
575                 gtk_widget_show(box2);
576                 gtk_widget_show(box);
577                 gtk_widget_show(iwid);
578
579                 gtk_window_set_decorated(GTK_WINDOW(window), FALSE);            
580                 gtk_widget_show(window);
581         } else {
582                 box=gtk_vbox_new(FALSE, 5);
583                 add_about_wid_fix(iwid);
584                 
585                 sep=gtk_hseparator_new();
586                 add_about_wid_fix(sep);
587                 
588                 label=gtk_label_new("This is "PACKAGE" release "VERSION" - Copyright (C) 1999-2011 by Alexander König"
589                 "\nSend comments, patches and scratches to: alex@lisas.de\nterminatorX-homepage: http://www.terminatorX.org");
590
591                 gtk_label_set_justify(GTK_LABEL(label), GTK_JUSTIFY_CENTER);
592                 add_about_wid_fix(label);
593
594                 sep=gtk_hseparator_new();
595                 add_about_wid_fix(sep);
596                 
597                 label=gtk_label_new(
598                 "Compilation flags: "
599                 "sox: "
600 #ifdef USE_SOX_INPUT
601                 "ON"
602 #else
603                 "OFF"
604 #endif          
605                 " - mpg123: "
606 #ifdef USE_MPG123_INPUT
607                 "ON"
608 #else
609                 "OFF"
610 #endif
611                 " - ogg123: "
612 #ifdef USE_OGG123_INPUT
613                 "ON"
614 #else
615                 "OFF"
616 #endif
617                 " - libmad: "
618 #ifdef USE_MAD_INPUT
619                 "ON"
620 #else
621                 "OFF"
622 #endif
623
624                 " - libvorbis: "
625 #ifdef USE_VORBIS_INPUT
626                 "ON"
627 #else
628                 "OFF"
629 #endif
630
631                 " - libaudiofile: "
632 #ifdef USE_AUDIOFILE_INPUT
633                 "ON"
634 #else
635                 "OFF"
636 #endif
637
638                 " - MIDI: "
639 #ifdef USE_ALSA_MIDI_IN
640                 "ON"
641 #else
642                 "OFF"
643 #endif
644
645                 " - OSS: "
646 #ifdef USE_OSS
647                 "ON"
648 #else
649                 "OFF"
650 #endif
651
652                 " - ALSA: "
653 #ifdef USE_ALSA
654                 "ON"
655 #else
656                 "OFF"
657 #endif
658
659                 " - JACK: "
660 #ifdef USE_JACK
661                 "ON"
662 #else
663                 "OFF"
664 #endif
665
666                 " - liblrdf: "
667 #ifdef USE_LRDF
668                 "ON"
669 #else
670                 "OFF"
671 #endif
672
673                 " - rt scheduling: "
674 #ifdef USE_SCHEDULER
675                 "ON"
676 #else
677                 "OFF"
678 #endif
679
680                 " - capabilities: "
681 #ifdef USE_CAPABILITIES
682                 "ON"
683 #else
684                 "OFF"
685 #endif
686
687                 " - "
688 #ifdef WORDS_BIGENDIAN
689                 "big"
690 #else
691                 "little"
692 #endif
693                 " endian.");
694         
695                 gtk_label_set_line_wrap(GTK_LABEL(label), TRUE);
696                 gtk_widget_set_size_request(label, 640, -1);
697                 gtk_label_set_justify(GTK_LABEL(label), GTK_JUSTIFY_CENTER);
698                 add_about_wid_fix(label);
699
700 #ifdef  USE_SCHEDULER
701                 sep=gtk_hseparator_new();
702                 add_about_wid_fix(sep);
703
704                 char buffer[4096];
705                 
706                 int policy=-1;
707                 struct sched_param parm;
708                 
709                 pthread_getschedparam(tX_engine::get_instance()->get_thread_id(), &policy, &parm);
710                 char prio_str[32]="";
711                 
712                 switch (policy) {
713                         case SCHED_OTHER:
714                                 strcpy(prio_str, "SCHED_OTHER");
715                                 break;
716                         
717                         case SCHED_RR:
718                                 strcpy(prio_str, "SCHED_RR");
719                                 break;
720                         
721                         case SCHED_FIFO:
722                                 strcpy(prio_str, "SCHED_FIFO");
723                                 break;
724                         
725                         default:
726                                 sprintf(prio_str, "UNKOWN (%i)", policy);
727                 }
728                 
729                 sprintf(buffer, "Audio engine scheduling policy: %s.\n(Note: SCHED_FIFO equals realtime scheduling.)", prio_str);
730
731                 label=gtk_label_new(buffer);
732
733                 gtk_label_set_justify(GTK_LABEL(label), GTK_JUSTIFY_CENTER);
734                 add_about_wid_fix(label);
735 #endif
736
737                 sep=gtk_hseparator_new();
738                 add_about_wid_fix(sep);
739
740                 label=gtk_label_new("License (GPL V2):");
741                 gtk_label_set_justify(GTK_LABEL(label), GTK_JUSTIFY_CENTER);
742                 add_about_wid_fix(label);
743
744                 hbox=gtk_hbox_new(FALSE, 5);            
745
746                 GtkTextIter iter;
747                 GtkTextBuffer *tbuffer;
748
749                 text=gtk_text_view_new();
750                 tbuffer=gtk_text_view_get_buffer(GTK_TEXT_VIEW(text));
751                 gtk_text_view_set_wrap_mode(GTK_TEXT_VIEW(text), GTK_WRAP_NONE);
752                 gtk_text_view_set_editable(GTK_TEXT_VIEW(text), false);
753                 gtk_text_buffer_get_iter_at_offset (tbuffer, &iter, 0);
754                 
755                 scroll=gtk_scrolled_window_new (NULL, NULL);
756         gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (scroll), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC);
757                 gtk_container_add (GTK_CONTAINER (scroll), text);
758                 gtk_text_buffer_create_tag (tbuffer, "courier", "family", "courier", NULL);
759                 
760                 gtk_text_buffer_insert_with_tags_by_name(tbuffer, &iter, license, -1, "courier", NULL);
761                 gtk_text_view_set_left_margin(GTK_TEXT_VIEW(text), 5);
762                 gtk_text_view_set_right_margin(GTK_TEXT_VIEW(text), 5);
763                 gtk_widget_set_size_request(GTK_WIDGET(text), 640, 200);
764                 gtk_widget_show(text);          
765                 
766                 gtk_box_pack_start(GTK_BOX(hbox), scroll, WID_DYN);
767                 gtk_widget_show(scroll);                
768                 
769                 add_about_wid(hbox);
770
771                 sep=gtk_hseparator_new();
772                 add_about_wid_fix(sep);
773
774                 btn=gtk_button_new_with_label("Close");
775                 add_about_wid_fix(btn);
776
777                 gtk_container_add(GTK_CONTAINER(window), box);
778                 gtk_widget_show(box);
779                 
780                 g_signal_connect(G_OBJECT(btn), "clicked", (GtkSignalFunc) destroy_about, NULL);                
781                 g_signal_connect(G_OBJECT(window), "delete-event", (GtkSignalFunc) destroy_about, NULL);                
782         }
783         gtk_widget_show(window);        
784         tX_set_icon(window);
785         
786         while (gtk_events_pending()) gtk_main_iteration();
787                 
788         about=window;
789 }
790
791 static GdkPixbuf *tX_window_icon=NULL;
792
793 void tX_set_icon(GtkWidget *widget)
794 {       
795         if (!tX_window_icon) {
796                 tX_window_icon=gdk_pixbuf_new_from_inline(-1, tX_icon, FALSE, NULL);
797         }
798
799         gtk_window_set_icon(GTK_WINDOW(widget), tX_window_icon);
800 }