1 /*   EXTRAITS DE LA LICENCE
2 	Copyright CEA, contributeurs : Luc BILLARD et Damien
3 	CALISTE, laboratoire L_Sim, (2001-2005)
4 
5 	Adresse mèl :
6 	BILLARD, non joignable par mèl ;
7 	CALISTE, damien P caliste AT cea P fr.
8 
9 	Ce logiciel est un programme informatique servant à visualiser des
10 	structures atomiques dans un rendu pseudo-3D.
11 
12 	Ce logiciel est régi par la licence CeCILL soumise au droit français et
13 	respectant les principes de diffusion des logiciels libres. Vous pouvez
14 	utiliser, modifier et/ou redistribuer ce programme sous les conditions
15 	de la licence CeCILL telle que diffusée par le CEA, le CNRS et l'INRIA
16 	sur le site "http://www.cecill.info".
17 
18 	Le fait que vous puissiez accéder à cet en-tête signifie que vous avez
19 	pris connaissance de la licence CeCILL, et que vous en avez accepté les
20 	termes (cf. le fichier Documentation/licence.fr.txt fourni avec ce logiciel).
21 */
22 
23 /*   LICENCE SUM UP
24 	Copyright CEA, contributors : Luc BILLARD et Damien
25 	CALISTE, laboratoire L_Sim, (2001-2005)
26 
27 	E-mail address:
28 	BILLARD, not reachable any more ;
29 	CALISTE, damien P caliste AT cea P fr.
30 
31 	This software is a computer program whose purpose is to visualize atomic
32 	configurations in 3D.
33 
34 	This software is governed by the CeCILL  license under French law and
35 	abiding by the rules of distribution of free software.  You can  use,
36 	modify and/ or redistribute the software under the terms of the CeCILL
37 	license as circulated by CEA, CNRS and INRIA at the following URL
38 	"http://www.cecill.info".
39 
40 	The fact that you are presently reading this means that you have had
41 	knowledge of the CeCILL license and that you accept its terms. You can
42 	find a copy of this licence shipped with this software at Documentation/licence.en.txt.
43 */
44 #include <gdk/gdkkeysyms.h>
45 
46 #include "support.h"
47 #include "interface.h"
48 #include "gtk_interactive.h"
49 #include "gtk_main.h"
50 #include "visu_gtk.h"
51 
52 #include "gtk_pick.h"
53 #include "gtk_move.h"
54 #include "gtk_renderingWindowWidget.h"
55 #include "openGLFunctions/interactive.h"
56 #include "extraGtkFunctions/gtk_numericalEntryWidget.h"
57 #include "extraGtkFunctions/gtk_orientationChooser.h"
58 
59 /**
60  * SECTION: gtk_interactive
61  * @short_description: The interactive dialog.
62  *
63  * <para>This is the second main interface for V_Sim after the command
64  * panel. It provides widgets to interact with the nodes. There is
65  * three built-in interactive modes : the observe one (as in normal
66  * behaviour), the pick one and the move one.</para>
67  * <para>It is possible to add new action thanks to
68  * visu_ui_interactive_addAction() function. It is also possible to
69  * show a small warning message with visu_ui_interactive_setMessage()
70  * that shows a GtkInfoBar.</para>
71  */
72 
73 /* Local types. */
74 typedef struct ActionInterface_
75 {
76   guint id;
77 
78   gchar *label;
79   gchar *help;
80 
81   GtkWidget *radio;
82 
83   VisuUiInteractiveBuild build;
84   VisuInteractiveId mode;
85   VisuUiInteractiveStartStop onStart, onStop;
86 } ActionInterface;
87 
88 /* Local variables. */
89 static ActionInterface* currentAction;
90 static guint n_actions = 0;
91 static GList *actions;
92 static VisuInteractive *interObserve = NULL;
93 static GBinding *theta_bind, *phi_bind, *omega_bind;
94 static GBinding *xs_bind, *ys_bind, *gross_bind, *persp_bind;
95 
96 /* Callbacks. */
97 static gboolean onHomePressed(GtkWidget *widget _U_, GdkEventKey *event,
98 			      gpointer data);
99 static void onDataNotify(GtkButton *button, GParamSpec *pspec, VisuGlNodeScene *scene);
100 static void observeMethodChanged(GtkToggleButton* button, gpointer data);
101 static void radioObserveToggled(GtkToggleButton *togglebutton, gpointer user_data);
102 static void onCloseButtonClicked(GtkButton *button, gpointer user_data);
103 static void onTabActionChanged(GtkNotebook *book, GtkWidget *child,
104 			       gint num, gpointer data);
105 static void onVisuUiOrientationChooser(GtkButton *button, gpointer data);
106 static gboolean onKillWindowEvent(GtkWidget *widget, GdkEvent *event,
107 				  gpointer user_data);
108 static void onRadioToggled(GtkToggleButton *toggle, gpointer data);
109 static void onObserveStart(VisuUiRenderingWindow *window);
110 static void onObserveStop(VisuUiRenderingWindow *window);
111 
112 /* Local methods. */
113 static void _setGlView(VisuGlView *view);
114 static void connectSignalsObservePick(VisuUiRenderingWindow *window);
115 static void setNamesGtkWidgetObservePick(VisuUiMain *main);
116 static GtkWidget* gtkObserveBuild_interface(VisuUiMain *main, gchar **label,
117 					    gchar **help, GtkWidget **radio);
118 
119 /* Widgets */
120 static GtkWidget *observeWindow, *infoBar;
121 static GtkWidget *orientationChooser;
122 static GtkWidget *spinOmega;
123 
124 
125 /* Help message used in the help area. */
126 #define GTK_PICKOBSERVE_OBSERVE_INFO \
127   _("left-[control]-button\t\t\t: rotations "				\
128     "(\316\270, \317\206, [control]\317\211)\n"				\
129     "shift-left-button\t\t\t\t: translations (dx, dy)\n"		\
130     "middle-[shift]-button or wheel\t: zoom or [shift]perspective\n"	\
131     "key 's' / 'r'\t\t\t\t\t: save/restore camera position\n"		\
132     "right-button\t\t\t\t\t: switch to current tabbed action")
133 
134 /**
135  * visu_ui_interactive_init: (skip)
136  *
137  * Initialise the observe/pick window, connect the
138  * signals, give names to widgets...
139  */
visu_ui_interactive_init()140 void visu_ui_interactive_init()
141 {
142   orientationChooser = (GtkWidget*)0;
143   /* Set the actions tabs. */
144   actions = (GList*)0;
145 
146   visu_ui_interactive_addAction(gtkObserveBuild_interface,
147                                 onObserveStart, onObserveStop);
148   currentAction = (ActionInterface*)actions->data;
149 
150   visu_ui_interactive_addAction(visu_ui_interactive_pick_initBuild,
151                                 visu_ui_interactive_pick_start, visu_ui_interactive_pick_stop);
152 
153   visu_ui_interactive_addAction(visu_ui_interactive_move_initBuild,
154                                 visu_ui_interactive_move_start, visu_ui_interactive_move_stop);
155 }
156 
157 /**
158  * visu_ui_interactive_addAction:
159  * @build: a routine to build a tab.
160  * @start: a routine to run when session is selected.
161  * @stop: a routine to run when session is stopped.
162  *
163  * One can add new interactive mode with specific tab in the
164  * interactive dialog.
165  *
166  * Since: 3.6
167  *
168  * Returns: an id for this new action.
169  */
visu_ui_interactive_addAction(VisuUiInteractiveBuild build,VisuUiInteractiveStartStop start,VisuUiInteractiveStartStop stop)170 guint visu_ui_interactive_addAction(VisuUiInteractiveBuild build,
171 			       VisuUiInteractiveStartStop start,
172 			       VisuUiInteractiveStartStop stop)
173 {
174   ActionInterface *action;
175 
176   g_return_val_if_fail(build && start && stop, 0);
177 
178   action = g_malloc(sizeof(ActionInterface));
179   action->id      = n_actions;
180   action->build   = build;
181   action->onStart = start;
182   action->onStop  = stop;
183 
184   actions       = g_list_append(actions, action);
185   n_actions += 1;
186 
187   return action->id;
188 }
189 
gtkObserveBuild_interface(VisuUiMain * main _U_,gchar ** label,gchar ** help,GtkWidget ** radio)190 static GtkWidget* gtkObserveBuild_interface(VisuUiMain *main _U_, gchar **label,
191 					    gchar **help, GtkWidget **radio)
192 {
193   *label = g_strdup("Observe");
194   *help  = g_strdup(GTK_PICKOBSERVE_OBSERVE_INFO);
195   *radio = lookup_widget(observeWindow, "radioObserve");
196 
197   return (GtkWidget*)0;
198 }
199 /**
200  * visu_ui_interactive_initBuild: (skip)
201  * @main: the command panel the about dialog is associated to.
202  *
203  * create the window.
204  */
visu_ui_interactive_initBuild(VisuUiMain * main)205 void visu_ui_interactive_initBuild(VisuUiMain *main)
206 {
207   GtkWidget *labelHelp, *wd;
208   VisuUiRenderingWindow *window;
209   VisuGlNodeScene *scene;
210   VisuGlView *view;
211   GList *tmpLst;
212   ActionInterface *action;
213   gchar *msg;
214   GSList *lst;
215 
216   window = visu_ui_main_getRendering(main);
217   scene = visu_ui_rendering_window_getGlScene(window);
218   view = visu_gl_node_scene_getGlView(scene);
219 
220   DBG_fprintf(stderr, "Gtk Interactive: init build.\n");
221 
222   interObserve = visu_interactive_new(interactive_observe);
223   g_signal_connect_swapped(G_OBJECT(interObserve), "stop",
224                            G_CALLBACK(visu_ui_interactive_toggle), (gpointer)0);
225 
226   DBG_fprintf(stderr, "Gtk observePick: creating the window.\n");
227   main->interactiveDialog = create_observeDialog();
228   gtk_window_set_default_size(GTK_WINDOW(main->interactiveDialog), 100, -1);
229   g_signal_connect_swapped(G_OBJECT(main->interactiveDialog), "destroy",
230                            G_CALLBACK(g_object_unref), interObserve);
231   observeWindow = main->interactiveDialog;
232   gtk_window_set_type_hint(GTK_WINDOW(main->interactiveDialog),
233 			   GDK_WINDOW_TYPE_HINT_NORMAL);
234   setNamesGtkWidgetObservePick(main);
235   g_signal_connect(G_OBJECT(observeWindow), "key-press-event",
236 		   G_CALLBACK(onHomePressed), (gpointer)observeWindow);
237 
238   /* Create the actions parts. */
239   DBG_fprintf(stderr, "Gtk Interactive: Create the actions parts.\n");
240   lst = (GSList*)0;
241   for (tmpLst = actions; tmpLst; tmpLst = g_list_next(tmpLst))
242     {
243       action = ((ActionInterface*)tmpLst->data);
244       g_return_if_fail(action->build);
245       wd = action->build(main, &action->label, &msg, &action->radio);
246       DBG_fprintf(stderr, " | action '%s'\n", action->label);
247       action->help = g_markup_printf_escaped("<span size=\"smaller\">%s</span>", msg);
248       g_free(msg);
249       if (wd)
250 	gtk_notebook_append_page
251 	  (GTK_NOTEBOOK(lookup_widget(observeWindow, "notebookAction")),
252 	   wd, gtk_label_new(action->label));
253       if (action->id > 0)
254 	gtk_radio_button_set_group(GTK_RADIO_BUTTON(action->radio), lst);
255       lst = gtk_radio_button_get_group(GTK_RADIO_BUTTON(action->radio));
256       g_signal_connect(G_OBJECT(action->radio), "toggled",
257 		       G_CALLBACK(onRadioToggled), (gpointer)action);
258       DBG_fprintf(stderr, " | action '%s' OK\n", action->label);
259     }
260 
261   /* Create and Set the help text. */
262   action = ((ActionInterface*)actions->data);
263   labelHelp = lookup_widget(main->interactiveDialog, "labelInfoObservePick");
264   gtk_label_set_markup(GTK_LABEL(labelHelp), action->help);
265 
266   /* Add an info bar for warning and so on. */
267 #if GTK_MAJOR_VERSION > 2 || GTK_MINOR_VERSION > 17
268   infoBar = gtk_info_bar_new();
269   gtk_widget_set_no_show_all(infoBar, TRUE);
270   gtk_info_bar_add_button(GTK_INFO_BAR(infoBar),
271                           _("_Ok"), GTK_RESPONSE_OK);
272   g_signal_connect(infoBar, "response",
273                    G_CALLBACK(gtk_widget_hide), NULL);
274   wd = gtk_label_new("");
275   gtk_label_set_xalign(GTK_LABEL(wd), 0.);
276   gtk_container_add(GTK_CONTAINER(gtk_info_bar_get_content_area(GTK_INFO_BAR(infoBar))), wd);
277   gtk_widget_show(wd);
278 #else
279   infoBar = gtk_label_new("");
280   gtk_misc_set_alignment(GTK_MISC(infoBar), 0., 0.5);
281 #endif
282   gtk_box_pack_end(GTK_BOX(lookup_widget(observeWindow, "vbox20")),
283                    infoBar, FALSE, FALSE, 2);
284 
285   /* connect the signals to the spins. */
286   connectSignalsObservePick(window);
287   theta_bind = NULL;
288   phi_bind   = NULL;
289   omega_bind = NULL;
290   xs_bind    = NULL;
291   ys_bind    = NULL;
292   gross_bind = NULL;
293   persp_bind = NULL;
294 
295   DBG_fprintf(stderr, "Gtk Interactive: Setup initial values.\n");
296   _setGlView(view);
297 
298   g_signal_connect_object(scene, "notify::data", G_CALLBACK(onDataNotify),
299                           lookup_widget(observeWindow, "buttonBackToCommandPanel"),
300                           G_CONNECT_SWAPPED);
301 }
302 
303 /**
304  * visu_ui_interactive_toggle:
305  *
306  * The user can switch between a current specific interactive action
307  * and the observe mode. This routine is used to do this.*
308  *
309  * Since: 3.6
310  */
visu_ui_interactive_toggle(void)311 void visu_ui_interactive_toggle(void)
312 {
313   GtkWidget *wd;
314   guint id;
315   ActionInterface *action;
316 
317   if (currentAction->id == VISU_UI_ACTION_OBSERVE)
318     {
319       wd = lookup_widget(observeWindow, "notebookAction");
320       id = gtk_notebook_get_current_page(GTK_NOTEBOOK(wd)) + 1;
321     }
322   else
323     id = VISU_UI_ACTION_OBSERVE;
324   action = (ActionInterface*)g_list_nth_data(actions, id);
325 
326   /* We toggle on the radio of the new action. */
327   if (action->radio)
328     gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(action->radio), TRUE);
329 }
330 /**
331  * visu_ui_interactive_start:
332  * @window: the current rendering widget.
333  *
334  * Start the observe & pick session.
335  */
visu_ui_interactive_start(VisuUiRenderingWindow * window)336 void visu_ui_interactive_start(VisuUiRenderingWindow *window)
337 {
338   DBG_fprintf(stderr, "Gtk Interactive: initialise session.\n");
339 
340   visu_ui_rendering_window_pushMessage(window, "");
341   currentAction->onStart(window);
342 }
343 
344 /**
345  * visu_ui_interactive_stop:
346  * @window: a #VisuUiRenderingWindow object.
347  *
348  * Stop the observe and pick session from @window.
349  *
350  * Since: 3.8
351  **/
visu_ui_interactive_stop(VisuUiRenderingWindow * window)352 void visu_ui_interactive_stop(VisuUiRenderingWindow *window)
353 {
354   DBG_fprintf(stderr, "Gtk Interactive: stop session.\n");
355 
356   visu_ui_rendering_window_popMessage(window);
357   currentAction->onStop(window);
358 }
359 /**
360  * visu_ui_interactive_setMessage:
361  * @message: a string.
362  * @type: the type of message.
363  *
364  * Show a message in the interactive dialog.
365  *
366  * Since: 3.6
367  */
visu_ui_interactive_setMessage(const gchar * message,GtkMessageType type)368 void visu_ui_interactive_setMessage(const gchar *message, GtkMessageType type)
369 {
370 #if GTK_MAJOR_VERSION > 2 || GTK_MINOR_VERSION > 17
371   GList *lst;
372 
373   gtk_info_bar_set_message_type(GTK_INFO_BAR(infoBar), type);
374   lst = gtk_container_get_children(GTK_CONTAINER(gtk_info_bar_get_content_area(GTK_INFO_BAR(infoBar))));
375   gtk_label_set_text(GTK_LABEL(lst->data), message);
376   g_list_free(lst);
377 #else
378   gtk_label_set_text(GTK_LABEL(infoBar), message);
379 #endif
380   gtk_widget_show(infoBar);
381 }
382 /**
383  * visu_ui_interactive_unsetMessage:
384  *
385  * Hide any message from the interactive dialog. See also
386  * visu_ui_interactive_setMessage().
387  *
388  * Since: 3.6
389  */
visu_ui_interactive_unsetMessage()390 void visu_ui_interactive_unsetMessage()
391 {
392   gtk_widget_hide(infoBar);
393 }
394 
onKillWindowEvent(GtkWidget * widget _U_,GdkEvent * event _U_,gpointer user_data)395 static gboolean onKillWindowEvent(GtkWidget *widget _U_, GdkEvent *event _U_,
396 				  gpointer user_data)
397 {
398   DBG_fprintf(stderr, "Gtk interactive: window killed.\n");
399 
400   visu_ui_interactive_stop(VISU_UI_RENDERING_WINDOW(user_data));
401   return FALSE;
402 }
onCloseButtonClicked(GtkButton * button _U_,gpointer user_data)403 static void onCloseButtonClicked(GtkButton *button _U_, gpointer user_data)
404 {
405   DBG_fprintf(stderr, "Gtk interactive: click on close button.\n");
406 
407   if (!gtk_widget_get_visible(observeWindow))
408     return;
409   visu_ui_interactive_stop(VISU_UI_RENDERING_WINDOW(user_data));
410 }
411 
412 /****************/
413 /* Private part */
414 /****************/
415 
416 /* Connect the listeners on the signal emitted by the OpenGL server. */
connectSignalsObservePick(VisuUiRenderingWindow * window)417 static void connectSignalsObservePick(VisuUiRenderingWindow *window)
418 {
419   GtkWidget *wd;
420 
421   g_signal_connect(G_OBJECT(observeWindow), "delete-event",
422 		   G_CALLBACK(onKillWindowEvent), window);
423   g_signal_connect(G_OBJECT(observeWindow), "destroy-event",
424 		   G_CALLBACK(onKillWindowEvent), window);
425 
426   wd = lookup_widget(observeWindow, "buttonBackToCommandPanel");
427   g_signal_connect(G_OBJECT(wd), "clicked",
428 		   G_CALLBACK(onCloseButtonClicked), window);
429   wd = lookup_widget(observeWindow, "radioObserve");
430   g_signal_connect(G_OBJECT(wd), "toggled",
431 		   G_CALLBACK(radioObserveToggled), (gpointer)0);
432 
433   wd = lookup_widget(observeWindow, "buttonVisuUiOrientationChooser");
434   g_signal_connect(G_OBJECT(wd), "clicked",
435 		   G_CALLBACK(onVisuUiOrientationChooser), (gpointer)0);
436 
437   /* The observe widgets. */
438   wd = lookup_widget(observeWindow, "radioObserveConstrained");
439   g_signal_connect(G_OBJECT(wd), "toggled", G_CALLBACK(observeMethodChanged),
440 		   GINT_TO_POINTER(interactive_constrained));
441   wd = lookup_widget(observeWindow, "radioObserveWalker");
442   g_signal_connect(G_OBJECT(wd), "toggled", G_CALLBACK(observeMethodChanged),
443 		   GINT_TO_POINTER(interactive_walker));
444 
445   wd = lookup_widget(observeWindow, "notebookAction");
446   g_signal_connect(G_OBJECT(wd), "switch-page",
447 		   G_CALLBACK(onTabActionChanged), (gpointer)0);
448 }
449 
_setGlView(VisuGlView * view)450 static void _setGlView(VisuGlView *view)
451 {
452   if (theta_bind)
453     g_object_unref(theta_bind);
454   theta_bind = (GBinding*)0;
455   if (phi_bind)
456     g_object_unref(phi_bind);
457   phi_bind = (GBinding*)0;
458   if (omega_bind)
459     g_object_unref(omega_bind);
460   omega_bind = (GBinding*)0;
461   if (xs_bind)
462     g_object_unref(xs_bind);
463   xs_bind = (GBinding*)0;
464   if (ys_bind)
465     g_object_unref(ys_bind);
466   ys_bind = (GBinding*)0;
467   if (gross_bind)
468     g_object_unref(gross_bind);
469   gross_bind = (GBinding*)0;
470   if (persp_bind)
471     g_object_unref(persp_bind);
472   persp_bind = (GBinding*)0;
473 
474   if (view)
475     {
476       theta_bind = g_object_bind_property(view, "theta",
477                                           lookup_widget(observeWindow,
478                                                         "spinTheta"), "value",
479                                           G_BINDING_BIDIRECTIONAL |
480                                           G_BINDING_SYNC_CREATE);
481       phi_bind   = g_object_bind_property(view, "phi",
482                                           lookup_widget(observeWindow,
483                                                         "spinPhi"), "value",
484                                           G_BINDING_BIDIRECTIONAL |
485                                           G_BINDING_SYNC_CREATE);
486       omega_bind = g_object_bind_property(view, "omega",
487                                           lookup_widget(observeWindow,
488                                                         "spinOmega"), "value",
489                                           G_BINDING_BIDIRECTIONAL |
490                                           G_BINDING_SYNC_CREATE);
491       xs_bind    = g_object_bind_property(view, "trans-x",
492                                           lookup_widget(observeWindow,
493                                                         "spinDx"), "value",
494                                           G_BINDING_BIDIRECTIONAL |
495                                           G_BINDING_SYNC_CREATE);
496       ys_bind    = g_object_bind_property(view, "trans-y",
497                                           lookup_widget(observeWindow,
498                                                         "spinDy"), "value",
499                                           G_BINDING_BIDIRECTIONAL |
500                                           G_BINDING_SYNC_CREATE);
501       gross_bind = g_object_bind_property(view, "zoom",
502                                           lookup_widget(observeWindow,
503                                                         "spinGross"), "value",
504                                           G_BINDING_BIDIRECTIONAL |
505                                           G_BINDING_SYNC_CREATE);
506       persp_bind = g_object_bind_property(view, "perspective",
507                                           lookup_widget(observeWindow,
508                                                         "spinPersp"), "value",
509                                           G_BINDING_BIDIRECTIONAL |
510                                           G_BINDING_SYNC_CREATE);
511     }
512 }
513 
onDataNotify(GtkButton * button,GParamSpec * pspec _U_,VisuGlNodeScene * scene)514 static void onDataNotify(GtkButton *button, GParamSpec *pspec _U_, VisuGlNodeScene *scene)
515 {
516   if (!visu_gl_node_scene_getData(scene))
517     gtk_button_clicked(button);
518 }
519 
onObserveStart(VisuUiRenderingWindow * window)520 static void onObserveStart(VisuUiRenderingWindow *window)
521 {
522   visu_ui_rendering_window_pushInteractive(window, interObserve);
523 }
onObserveStop(VisuUiRenderingWindow * window)524 static void onObserveStop(VisuUiRenderingWindow *window)
525 {
526   visu_ui_rendering_window_popInteractive(window, interObserve);
527 }
528 
observeMethodChanged(GtkToggleButton * button,gpointer data)529 static void observeMethodChanged(GtkToggleButton* button, gpointer data)
530 {
531   VisuInteractiveMethod method;
532 
533   if (!gtk_toggle_button_get_active(button))
534     return;
535 
536   method = (VisuInteractiveMethod)GPOINTER_TO_INT(data);
537   visu_interactive_class_setPreferedObserveMethod(method);
538   if (method == interactive_constrained)
539     {
540       gtk_widget_set_sensitive(spinOmega, FALSE);
541       g_object_set(visu_gl_node_scene_getGlView(visu_ui_rendering_window_getGlScene
542                                                 (visu_ui_main_class_getDefaultRendering())),
543                    "omega", 0., NULL);
544     }
545   else
546     gtk_widget_set_sensitive(spinOmega, TRUE);
547 }
548 
549 
550 /* Give a name to the widgets present in this window
551    to be able to affect them with a theme. */
setNamesGtkWidgetObservePick(VisuUiMain * main)552 static void setNamesGtkWidgetObservePick(VisuUiMain *main)
553 {
554   GtkWidget *wd;
555   int method;
556 
557   gtk_widget_set_name(main->interactiveDialog, "message");
558 /*   wd = lookup_widget(main->interactiveDialog, "titreObserve"); */
559 /*   gtk_widget_set_name(wd, "message_title"); */
560   wd = lookup_widget(main->interactiveDialog, "labelInfoObservePick");
561   gtk_widget_set_name(wd, "label_info");
562 
563   wd = lookup_widget(main->interactiveDialog, "labelTranslation");
564   gtk_widget_set_name(wd, "label_head_2");
565   wd = lookup_widget(main->interactiveDialog, "labelZoom");
566   gtk_widget_set_name(wd, "label_head_2");
567 
568   wd = lookup_widget(main->interactiveDialog, "radioObserve");
569   gtk_widget_set_name(wd, "message_radio");
570   wd = lookup_widget(main->interactiveDialog, "radioPick");
571   gtk_widget_set_name(wd, "message_radio");
572   wd = lookup_widget(main->interactiveDialog, "radioMove");
573   gtk_widget_set_name(wd, "message_radio");
574 
575   spinOmega = lookup_widget(main->interactiveDialog, "spinOmega");
576 
577   method = visu_interactive_class_getPreferedObserveMethod();
578   if (method == interactive_constrained)
579     gtk_widget_set_sensitive(spinOmega, FALSE);
580 
581   wd = lookup_widget(main->interactiveDialog, "notebookAction");
582   gtk_widget_set_name(wd, "message_notebook");
583 
584   wd = lookup_widget(main->interactiveDialog, "radioObserveConstrained");
585   gtk_widget_set_name(wd, "message_radio");
586   if (method == interactive_constrained)
587     gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(wd), TRUE);
588   wd = lookup_widget(main->interactiveDialog, "radioObserveWalker");
589   gtk_widget_set_name(wd, "message_radio");
590   if (method == interactive_walker)
591     gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(wd), TRUE);
592 }
onHomePressed(GtkWidget * widget _U_,GdkEventKey * event,gpointer data _U_)593 static gboolean onHomePressed(GtkWidget *widget _U_, GdkEventKey *event,
594 			      gpointer data _U_)
595 {
596   GtkWindow *window;
597 
598   DBG_fprintf(stderr, "Gtk Interactive: get key pressed.\n");
599   if(event->keyval == GDK_KEY_Home)
600     {
601       window = visu_ui_getRenderWindow();
602       g_return_val_if_fail(window, FALSE);
603       /* We raised the rendering window, if required. */
604       gtk_window_present(window);
605       return TRUE;
606     }
607   return FALSE;
608 }
609 
onRadioToggled(GtkToggleButton * toggle,gpointer data)610 static void onRadioToggled(GtkToggleButton *toggle, gpointer data)
611 {
612   GtkWidget *labelHelp;
613   VisuUiRenderingWindow *window;
614 
615   if (!gtk_toggle_button_get_active(toggle))
616     return;
617 
618   window = visu_ui_main_class_getDefaultRendering();
619 
620   /* Before setting up the current action, we pop
621      the previous one. */
622   if (currentAction)
623     currentAction->onStop(window);
624 
625   /* Get the new action. */
626   currentAction = (ActionInterface*)data;
627   DBG_fprintf(stderr, "Gtk Interactive: set the action %d current.\n",
628 	      currentAction->id);
629 
630   labelHelp = lookup_widget(observeWindow, "labelInfoObservePick");
631   gtk_label_set_markup(GTK_LABEL(labelHelp), currentAction->help);
632 
633   currentAction->onStart(window);
634 }
635 
radioObserveToggled(GtkToggleButton * togglebutton,gpointer user_data _U_)636 static void radioObserveToggled(GtkToggleButton *togglebutton, gpointer user_data _U_)
637 {
638   gboolean value;
639   GtkWidget *wd;
640 
641   value = gtk_toggle_button_get_active(togglebutton);
642 
643   wd = lookup_widget(observeWindow, "hboxObserve");
644   gtk_widget_set_sensitive(wd, value);
645   wd = lookup_widget(observeWindow, "tableObserve");
646   gtk_widget_set_sensitive(wd, value);
647   if (visu_interactive_class_getPreferedObserveMethod() == interactive_constrained)
648     gtk_widget_set_sensitive(spinOmega, FALSE);
649   else
650     gtk_widget_set_sensitive(spinOmega, value);
651 }
652 
onTabActionChanged(GtkNotebook * book _U_,GtkWidget * child _U_,gint num,gpointer data _U_)653 static void onTabActionChanged(GtkNotebook *book _U_, GtkWidget *child _U_,
654 			       gint num, gpointer data _U_)
655 {
656   ActionInterface *action;
657 
658   DBG_fprintf(stderr, "Gtk Interactive: change the action tab to %d.\n", num);
659 
660   action = (ActionInterface*)g_list_nth_data(actions, num + 1);
661   if (action->radio)
662     gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(action->radio), TRUE);
663 }
onOrientationChanged(VisuUiOrientationChooser * orientationChooser,gpointer data _U_)664 static void onOrientationChanged(VisuUiOrientationChooser *orientationChooser,
665 				 gpointer data _U_)
666 {
667   float values[2];
668 
669   DBG_fprintf(stderr, "Gtk Observe: orientation changed.\n");
670   visu_ui_orientation_chooser_getAnglesValues(orientationChooser, values);
671 
672   g_object_set(visu_gl_node_scene_getGlView(visu_ui_rendering_window_getGlScene
673                                             (visu_ui_main_class_getDefaultRendering())),
674                "theta", values[0], "phi", values[1], NULL);
675 }
onVisuUiOrientationChooser(GtkButton * button _U_,gpointer data _U_)676 static void onVisuUiOrientationChooser(GtkButton *button _U_, gpointer data _U_)
677 {
678   float values[2];
679   VisuUiRenderingWindow *window;
680   VisuGlView *view;
681 
682   window = visu_ui_main_class_getDefaultRendering();
683   view = visu_gl_node_scene_getGlView(visu_ui_rendering_window_getGlScene(window));
684   if (!orientationChooser)
685     {
686       orientationChooser = visu_ui_orientation_chooser_new
687 	(VISU_UI_ORIENTATION_DIRECTION, TRUE, VISU_BOXED(view), GTK_WINDOW(observeWindow));
688 /*       gtk_window_set_modal(GTK_WINDOW(orientationChooser), TRUE); */
689       values[0] = (float)view->camera.theta;
690       values[1] = (float)view->camera.phi;
691       visu_ui_orientation_chooser_setAnglesValues(VISU_UI_ORIENTATION_CHOOSER(orientationChooser),
692 					 values);
693       g_signal_connect(G_OBJECT(orientationChooser), "values-changed",
694 		       G_CALLBACK(onOrientationChanged), (gpointer)0);
695       gtk_widget_show(orientationChooser);
696     }
697   else
698     gtk_window_present(GTK_WINDOW(orientationChooser));
699 
700   switch (gtk_dialog_run(GTK_DIALOG(orientationChooser)))
701     {
702     case GTK_RESPONSE_ACCEPT:
703       DBG_fprintf(stderr, "Gtk Observe: accept changings on orientation.\n");
704       break;
705     default:
706       DBG_fprintf(stderr, "Gtk Observe: reset values on orientation.\n");
707       g_object_set(view, "theta", values[0], "phi", values[1], NULL);
708     }
709   DBG_fprintf(stderr, "Gtk Observe: orientation object destroy.\n");
710   gtk_widget_destroy(orientationChooser);
711   orientationChooser = (GtkWidget*)0;
712 }
713