Prevent implicit Widget construction
[xonotic/netradiant.git] / contrib / prtview / ConfigDialog.cpp
1 /*
2    PrtView plugin for GtkRadiant
3    Copyright (C) 2001 Geoffrey Dewan, Loki software and qeradiant.com
4
5    This library is free software; you can redistribute it and/or
6    modify it under the terms of the GNU Lesser General Public
7    License as published by the Free Software Foundation; either
8    version 2.1 of the License, or (at your option) any later version.
9
10    This library 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 GNU
13    Lesser General Public License for more details.
14
15    You should have received a copy of the GNU Lesser General Public
16    License along with this library; if not, write to the Free Software
17    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
18  */
19
20 #include "ConfigDialog.h"
21 #include <stdio.h>
22 #include <gtk/gtk.h>
23 #include <uilib/uilib.h>
24 #include "gtkutil/pointer.h"
25
26 #include "iscenegraph.h"
27
28 #include "prtview.h"
29 #include "portals.h"
30
31 static void dialog_button_callback( GtkWidget *widget, gpointer data ){
32         GtkWidget *parent;
33         int *loop, *ret;
34
35         parent = gtk_widget_get_toplevel( widget );
36         loop = (int*)g_object_get_data( G_OBJECT( parent ), "loop" );
37         ret = (int*)g_object_get_data( G_OBJECT( parent ), "ret" );
38
39         *loop = 0;
40         *ret = gpointer_to_int( data );
41 }
42
43 static gint dialog_delete_callback( GtkWidget *widget, GdkEvent* event, gpointer data ){
44         int *loop;
45
46         gtk_widget_hide( widget );
47         loop = (int*)g_object_get_data( G_OBJECT( widget ), "loop" );
48         *loop = 0;
49
50         return TRUE;
51 }
52
53 // =============================================================================
54 // Color selection dialog
55
56 static int DoColor( PackedColour *c ){
57         GdkColor clr;
58         int loop = 1, ret = IDCANCEL;
59
60         clr.red = (guint16) (GetRValue(*c) * (65535 / 255));
61         clr.blue = (guint16) (GetGValue(*c) * (65535 / 255));
62         clr.green = (guint16) (GetBValue(*c) * (65535 / 255));
63
64         auto dlg = ui::Widget(gtk_color_selection_dialog_new( "Choose Color" ));
65         gtk_color_selection_set_current_color( GTK_COLOR_SELECTION( gtk_color_selection_dialog_get_color_selection(GTK_COLOR_SELECTION_DIALOG(dlg)) ), &clr );
66         dlg.connect( "delete_event", G_CALLBACK( dialog_delete_callback ), NULL );
67         dlg.connect( "destroy", G_CALLBACK( gtk_widget_destroy ), NULL );
68
69         GtkWidget *ok_button, *cancel_button;
70         g_object_get(dlg, "ok-button", &ok_button, "cancel-button", &cancel_button, nullptr);
71
72         ui::Widget(ok_button).connect( "clicked", G_CALLBACK( dialog_button_callback ), GINT_TO_POINTER( IDOK ) );
73         ui::Widget(cancel_button).connect( "clicked", G_CALLBACK( dialog_button_callback ), GINT_TO_POINTER( IDCANCEL ) );
74         g_object_set_data( G_OBJECT( dlg ), "loop", &loop );
75         g_object_set_data( G_OBJECT( dlg ), "ret", &ret );
76
77         gtk_widget_show( dlg );
78         gtk_grab_add( dlg );
79
80         while ( loop )
81                 gtk_main_iteration();
82
83         gtk_color_selection_get_current_color( GTK_COLOR_SELECTION( gtk_color_selection_dialog_get_color_selection(GTK_COLOR_SELECTION_DIALOG(dlg)) ), &clr );
84
85         gtk_grab_remove( dlg );
86         gtk_widget_destroy( dlg );
87
88         if ( ret == IDOK ) {
89                 *c = RGB( clr.red / (65535 / 255), clr.green / (65535 / 255), clr.blue / (65535 / 255));
90         }
91
92         return ret;
93 }
94
95 static void Set2DText( GtkWidget* label ){
96         char s[40];
97
98         sprintf( s, "Line Width = %6.3f", portals.width_2d * 0.5f );
99
100         gtk_label_set_text( GTK_LABEL( label ), s );
101 }
102
103 static void Set3DText( GtkWidget* label ){
104         char s[40];
105
106         sprintf( s, "Line Width = %6.3f", portals.width_3d * 0.5f );
107
108         gtk_label_set_text( GTK_LABEL( label ), s );
109 }
110
111 static void Set3DTransText( GtkWidget* label ){
112         char s[40];
113
114         sprintf( s, "Polygon transparency = %d%%", (int)portals.trans_3d );
115
116         gtk_label_set_text( GTK_LABEL( label ), s );
117 }
118
119 static void SetClipText( GtkWidget* label ){
120         char s[40];
121
122         sprintf( s, "Cubic clip range = %d", (int)portals.clip_range * 64 );
123
124         gtk_label_set_text( GTK_LABEL( label ), s );
125 }
126
127 static void OnScroll2d( GtkAdjustment *adj, gpointer data ){
128         portals.width_2d = static_cast<float>( gtk_adjustment_get_value(adj) );
129         Set2DText( GTK_WIDGET( data ) );
130
131         Portals_shadersChanged();
132         SceneChangeNotify();
133 }
134
135 static void OnScroll3d( GtkAdjustment *adj, gpointer data ){
136         portals.width_3d = static_cast<float>( gtk_adjustment_get_value(adj) );
137         Set3DText( GTK_WIDGET( data ) );
138
139         SceneChangeNotify();
140 }
141
142 static void OnScrollTrans( GtkAdjustment *adj, gpointer data ){
143         portals.trans_3d = static_cast<float>( gtk_adjustment_get_value(adj) );
144         Set3DTransText( GTK_WIDGET( data ) );
145
146         SceneChangeNotify();
147 }
148
149 static void OnScrollClip( GtkAdjustment *adj, gpointer data ){
150         portals.clip_range = static_cast<float>( gtk_adjustment_get_value(adj) );
151         SetClipText( GTK_WIDGET( data ) );
152
153         SceneChangeNotify();
154 }
155
156 static void OnAntiAlias2d( GtkWidget *widget, gpointer data ){
157         portals.aa_2d = gtk_toggle_button_get_active( GTK_TOGGLE_BUTTON( widget ) ) ? true : false;
158
159         Portals_shadersChanged();
160
161         SceneChangeNotify();
162 }
163
164 static void OnConfig2d( GtkWidget *widget, gpointer data ){
165         portals.show_2d = gtk_toggle_button_get_active( GTK_TOGGLE_BUTTON( widget ) ) ? true : false;
166
167         SceneChangeNotify();
168 }
169
170 static void OnColor2d( GtkWidget *widget, gpointer data ){
171         if ( DoColor( &portals.color_2d ) == IDOK ) {
172                 Portals_shadersChanged();
173
174                 SceneChangeNotify();
175         }
176 }
177
178 static void OnConfig3d( GtkWidget *widget, gpointer data ){
179         portals.show_3d = gtk_toggle_button_get_active( GTK_TOGGLE_BUTTON( widget ) ) ? true : false;
180
181         SceneChangeNotify();
182 }
183
184
185 static void OnAntiAlias3d( GtkWidget *widget, gpointer data ){
186         portals.aa_3d = gtk_toggle_button_get_active( GTK_TOGGLE_BUTTON( widget ) ) ? true : false;
187
188         Portals_shadersChanged();
189         SceneChangeNotify();
190 }
191
192 static void OnColor3d( GtkWidget *widget, gpointer data ){
193         if ( DoColor( &portals.color_3d ) == IDOK ) {
194                 Portals_shadersChanged();
195
196                 SceneChangeNotify();
197         }
198 }
199
200 static void OnColorFog( GtkWidget *widget, gpointer data ){
201         if ( DoColor( &portals.color_fog ) == IDOK ) {
202                 Portals_shadersChanged();
203
204                 SceneChangeNotify();
205         }
206 }
207
208 static void OnFog( GtkWidget *widget, gpointer data ){
209         portals.fog = gtk_toggle_button_get_active( GTK_TOGGLE_BUTTON( widget ) ) ? true : false;
210
211         Portals_shadersChanged();
212         SceneChangeNotify();
213 }
214
215 static void OnSelchangeZbuffer( GtkWidget *widget, gpointer data ){
216         portals.zbuffer = gpointer_to_int( data );
217
218         Portals_shadersChanged();
219         SceneChangeNotify();
220 }
221
222 static void OnPoly( GtkWidget *widget, gpointer data ){
223         portals.polygons = gtk_toggle_button_get_active( GTK_TOGGLE_BUTTON( widget ) );
224
225         SceneChangeNotify();
226 }
227
228 static void OnLines( GtkWidget *widget, gpointer data ){
229         portals.lines = gtk_toggle_button_get_active( GTK_TOGGLE_BUTTON( widget ) );
230
231         SceneChangeNotify();
232 }
233
234 static void OnClip( GtkWidget *widget, gpointer data ){
235         portals.clip = gtk_toggle_button_get_active( GTK_TOGGLE_BUTTON( widget ) ) ? true : false;
236
237         SceneChangeNotify();
238 }
239
240 void DoConfigDialog(){
241         GtkWidget *hbox, *table;
242         GtkWidget *lw3slider, *lw3label, *lw2slider, *lw2label, *item;
243         GtkWidget *transslider, *translabel, *clipslider, *cliplabel;
244         int loop = 1, ret = IDCANCEL;
245
246         auto dlg = ui::Window( ui::window_type::TOP );
247         gtk_window_set_title( GTK_WINDOW( dlg ), "Portal Viewer Configuration" );
248         dlg.connect( "delete_event",
249                                                 G_CALLBACK( dialog_delete_callback ), NULL );
250         dlg.connect( "destroy",
251                                                 G_CALLBACK( gtk_widget_destroy ), NULL );
252         g_object_set_data( G_OBJECT( dlg ), "loop", &loop );
253         g_object_set_data( G_OBJECT( dlg ), "ret", &ret );
254
255         auto vbox = ui::VBox( FALSE, 5 );
256         vbox.show();
257         dlg.add(vbox);
258         gtk_container_set_border_width( GTK_CONTAINER( vbox ), 5 );
259
260         auto frame = ui::Frame( "3D View" );
261         frame.show();
262         gtk_box_pack_start( GTK_BOX( vbox ), frame, TRUE, TRUE, 0 );
263
264         auto vbox2 = ui::VBox( FALSE, 5 );
265         vbox2.show();
266         frame.add(vbox2);
267         gtk_container_set_border_width( GTK_CONTAINER( vbox2 ), 5 );
268
269         hbox = ui::HBox( FALSE, 5 );
270         gtk_widget_show( hbox );
271         gtk_box_pack_start( GTK_BOX( vbox2 ), hbox, TRUE, TRUE, 0 );
272
273         auto adj = ui::Adjustment( portals.width_3d, 2, 40, 1, 1, 0 );
274         lw3slider = ui::HScale( adj );
275         gtk_widget_show( lw3slider );
276         gtk_box_pack_start( GTK_BOX( hbox ), lw3slider, TRUE, TRUE, 0 );
277         gtk_scale_set_draw_value( GTK_SCALE( lw3slider ), FALSE );
278
279         lw3label = ui::Label( "" );
280         gtk_widget_show( lw3label );
281         gtk_box_pack_start( GTK_BOX( hbox ), lw3label, FALSE, TRUE, 0 );
282         adj.connect( "value_changed", G_CALLBACK( OnScroll3d ), lw3label );
283
284         table = ui::Table( 2, 4, FALSE );
285         gtk_widget_show( table );
286         gtk_box_pack_start( GTK_BOX( vbox2 ), table, TRUE, TRUE, 0 );
287         gtk_table_set_row_spacings( GTK_TABLE( table ), 5 );
288         gtk_table_set_col_spacings( GTK_TABLE( table ), 5 );
289
290         auto button = ui::Button( "Color" );
291         gtk_widget_show( button );
292         gtk_table_attach( GTK_TABLE( table ), button, 0, 1, 0, 1,
293                                           (GtkAttachOptions) ( GTK_FILL ),
294                                           (GtkAttachOptions) ( 0 ), 0, 0 );
295         button.connect( "clicked", G_CALLBACK( OnColor3d ), NULL );
296
297         button = ui::Button( "Depth Color" );
298         gtk_widget_show( button );
299         gtk_table_attach( GTK_TABLE( table ), button, 0, 1, 1, 2,
300                                           (GtkAttachOptions) ( GTK_FILL ),
301                                           (GtkAttachOptions) ( 0 ), 0, 0 );
302         button.connect( "clicked", G_CALLBACK( OnColorFog ), NULL );
303
304         auto aa3check = ui::CheckButton( "Anti-Alias (May not work on some video cards)" );
305         gtk_widget_show( aa3check );
306         gtk_table_attach( GTK_TABLE( table ), aa3check, 1, 4, 0, 1,
307                                           (GtkAttachOptions) ( GTK_EXPAND | GTK_FILL ),
308                                           (GtkAttachOptions) ( 0 ), 0, 0 );
309         aa3check.connect( "toggled", G_CALLBACK( OnAntiAlias3d ), NULL );
310
311         auto depthcheck = ui::CheckButton( "Depth Cue" );
312         gtk_widget_show( depthcheck );
313         gtk_table_attach( GTK_TABLE( table ), depthcheck, 1, 2, 1, 2,
314                                           (GtkAttachOptions) ( GTK_EXPAND | GTK_FILL ),
315                                           (GtkAttachOptions) ( 0 ), 0, 0 );
316         depthcheck.connect( "toggled", G_CALLBACK( OnFog ), NULL );
317
318         auto linescheck = ui::CheckButton( "Lines" );
319         gtk_widget_show( linescheck );
320         gtk_table_attach( GTK_TABLE( table ), linescheck, 2, 3, 1, 2,
321                                           (GtkAttachOptions) ( GTK_EXPAND | GTK_FILL ),
322                                           (GtkAttachOptions) ( 0 ), 0, 0 );
323         linescheck.connect( "toggled", G_CALLBACK( OnLines ), NULL );
324
325         auto polyscheck = ui::CheckButton( "Polygons" );
326         gtk_widget_show( polyscheck );
327         gtk_table_attach( GTK_TABLE( table ), polyscheck, 3, 4, 1, 2,
328                                           (GtkAttachOptions) ( GTK_EXPAND | GTK_FILL ),
329                                           (GtkAttachOptions) ( 0 ), 0, 0 );
330         polyscheck.connect( "toggled", G_CALLBACK( OnPoly ), NULL );
331
332         auto zlist = ui::ComboBoxText(ui::New);
333         gtk_widget_show( zlist );
334         gtk_box_pack_start( GTK_BOX( vbox2 ), zlist, TRUE, FALSE, 0 );
335
336         gtk_combo_box_text_append_text(zlist, "Z-Buffer Test and Write (recommended for solid or no polygons)");
337         gtk_combo_box_text_append_text(zlist, "Z-Buffer Test Only (recommended for transparent polygons)");
338         gtk_combo_box_text_append_text(zlist, "Z-Buffer Off");
339
340         zlist.connect("changed", G_CALLBACK(+[](GtkComboBox *self, void *) {
341                 OnSelchangeZbuffer(GTK_WIDGET(self), GINT_TO_POINTER(gtk_combo_box_get_active(self)));
342         }), nullptr);
343
344         table = ui::Table( 2, 2, FALSE );
345         gtk_widget_show( table );
346         gtk_box_pack_start( GTK_BOX( vbox2 ), table, TRUE, TRUE, 0 );
347         gtk_table_set_row_spacings( GTK_TABLE( table ), 5 );
348         gtk_table_set_col_spacings( GTK_TABLE( table ), 5 );
349
350         adj = ui::Adjustment( portals.trans_3d, 0, 100, 1, 1, 0 );
351         transslider = ui::HScale( adj );
352         gtk_widget_show( transslider );
353         gtk_table_attach( GTK_TABLE( table ), transslider, 0, 1, 0, 1,
354                                           (GtkAttachOptions) ( GTK_EXPAND | GTK_FILL ),
355                                           (GtkAttachOptions) ( 0 ), 0, 0 );
356         gtk_scale_set_draw_value( GTK_SCALE( transslider ), FALSE );
357
358         translabel = ui::Label( "" );
359         gtk_widget_show( translabel );
360         gtk_table_attach( GTK_TABLE( table ), translabel, 1, 2, 0, 1,
361                                           (GtkAttachOptions) ( GTK_FILL ),
362                                           (GtkAttachOptions) ( 0 ), 0, 0 );
363         gtk_misc_set_alignment( GTK_MISC( translabel ), 0.0, 0.0 );
364         adj.connect( "value_changed", G_CALLBACK( OnScrollTrans ), translabel );
365
366         adj = ui::Adjustment( portals.clip_range, 1, 128, 1, 1, 0 );
367         clipslider = ui::HScale( adj );
368         gtk_widget_show( clipslider );
369         gtk_table_attach( GTK_TABLE( table ), clipslider, 0, 1, 1, 2,
370                                           (GtkAttachOptions) ( GTK_EXPAND | GTK_FILL ),
371                                           (GtkAttachOptions) ( 0 ), 0, 0 );
372         gtk_scale_set_draw_value( GTK_SCALE( clipslider ), FALSE );
373
374         cliplabel = ui::Label( "" );
375         gtk_widget_show( cliplabel );
376         gtk_table_attach( GTK_TABLE( table ), cliplabel, 1, 2, 1, 2,
377                                           (GtkAttachOptions) ( GTK_FILL ),
378                                           (GtkAttachOptions) ( 0 ), 0, 0 );
379         gtk_misc_set_alignment( GTK_MISC( cliplabel ), 0.0, 0.0 );
380         adj.connect( "value_changed", G_CALLBACK( OnScrollClip ), cliplabel );
381
382         hbox = ui::HBox( TRUE, 5 );
383         gtk_widget_show( hbox );
384         gtk_box_pack_start( GTK_BOX( vbox2 ), hbox, TRUE, FALSE, 0 );
385
386         auto show3check = ui::CheckButton( "Show" );
387         gtk_widget_show( show3check );
388         gtk_box_pack_start( GTK_BOX( hbox ), show3check, TRUE, TRUE, 0 );
389         show3check.connect( "toggled", G_CALLBACK( OnConfig3d ), NULL );
390
391         auto portalcheck = ui::CheckButton( "Portal cubic clipper" );
392         gtk_widget_show( portalcheck );
393         gtk_box_pack_start( GTK_BOX( hbox ), portalcheck, TRUE, TRUE, 0 );
394         portalcheck.connect( "toggled", G_CALLBACK( OnClip ), NULL );
395
396         frame = ui::Frame( "2D View" );
397         gtk_widget_show( frame );
398         gtk_box_pack_start( GTK_BOX( vbox ), frame, TRUE, TRUE, 0 );
399
400         vbox2 = ui::VBox( FALSE, 5 );
401         vbox2.show();
402         frame.add(vbox2);
403         gtk_container_set_border_width( GTK_CONTAINER( vbox2 ), 5 );
404
405         hbox = ui::HBox( FALSE, 5 );
406         gtk_widget_show( hbox );
407         gtk_box_pack_start( GTK_BOX( vbox2 ), hbox, TRUE, FALSE, 0 );
408
409         adj = ui::Adjustment( portals.width_2d, 2, 40, 1, 1, 0 );
410         lw2slider = ui::HScale( adj );
411         gtk_widget_show( lw2slider );
412         gtk_box_pack_start( GTK_BOX( hbox ), lw2slider, TRUE, TRUE, 0 );
413         gtk_scale_set_draw_value( GTK_SCALE( lw2slider ), FALSE );
414
415         lw2label = ui::Label( "" );
416         gtk_widget_show( lw2label );
417         gtk_box_pack_start( GTK_BOX( hbox ), lw2label, FALSE, TRUE, 0 );
418         adj.connect( "value_changed", G_CALLBACK( OnScroll2d ), lw2label );
419
420         hbox = ui::HBox( FALSE, 5 );
421         gtk_widget_show( hbox );
422         gtk_box_pack_start( GTK_BOX( vbox2 ), hbox, TRUE, FALSE, 0 );
423
424         button = ui::Button( "Color" );
425         gtk_widget_show( button );
426         gtk_box_pack_start( GTK_BOX( hbox ), button, FALSE, FALSE, 0 );
427         button.connect( "clicked", G_CALLBACK( OnColor2d ), NULL );
428         gtk_widget_set_size_request( button, 60, -1 );
429
430         auto aa2check = ui::CheckButton( "Anti-Alias (May not work on some video cards)" );
431         gtk_widget_show( aa2check );
432         gtk_box_pack_start( GTK_BOX( hbox ), aa2check, TRUE, TRUE, 0 );
433         aa2check.connect( "toggled", G_CALLBACK( OnAntiAlias2d ), NULL );
434
435         hbox = ui::HBox( FALSE, 5 );
436         gtk_widget_show( hbox );
437         gtk_box_pack_start( GTK_BOX( vbox2 ), hbox, TRUE, FALSE, 0 );
438
439         auto show2check = ui::CheckButton( "Show" );
440         gtk_widget_show( show2check );
441         gtk_box_pack_start( GTK_BOX( hbox ), show2check, FALSE, FALSE, 0 );
442         show2check.connect( "toggled", G_CALLBACK( OnConfig2d ), NULL );
443
444         hbox = ui::HBox( FALSE, 5 );
445         gtk_widget_show( hbox );
446         gtk_box_pack_start( GTK_BOX( vbox ), hbox, FALSE, FALSE, 0 );
447
448         button = ui::Button( "OK" );
449         gtk_widget_show( button );
450         gtk_box_pack_end( GTK_BOX( hbox ), button, FALSE, FALSE, 0 );
451         button.connect( "clicked",
452                                                 G_CALLBACK( dialog_button_callback ), GINT_TO_POINTER( IDOK ) );
453         gtk_widget_set_size_request( button, 60, -1 );
454
455         // initialize dialog
456         gtk_toggle_button_set_active( GTK_TOGGLE_BUTTON( show2check ), portals.show_2d );
457         gtk_toggle_button_set_active( GTK_TOGGLE_BUTTON( aa2check ), portals.aa_2d );
458         Set2DText( lw2label );
459
460         gtk_toggle_button_set_active( GTK_TOGGLE_BUTTON( show3check ), portals.show_3d );
461         gtk_toggle_button_set_active( GTK_TOGGLE_BUTTON( depthcheck ), portals.fog );
462         gtk_toggle_button_set_active( GTK_TOGGLE_BUTTON( polyscheck ), portals.polygons );
463         gtk_toggle_button_set_active( GTK_TOGGLE_BUTTON( linescheck ), portals.lines );
464         gtk_toggle_button_set_active( GTK_TOGGLE_BUTTON( aa3check ), portals.aa_3d );
465         gtk_combo_box_set_active(zlist, portals.zbuffer);
466         gtk_toggle_button_set_active( GTK_TOGGLE_BUTTON( portalcheck ), portals.clip );
467
468         Set3DText( lw3label );
469         Set3DTransText( translabel );
470         SetClipText( cliplabel );
471
472         gtk_grab_add( dlg );
473         gtk_widget_show( dlg );
474
475         while ( loop )
476                 gtk_main_iteration();
477
478         gtk_grab_remove( dlg );
479         gtk_widget_destroy( dlg );
480 }