Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: orxonox.OLD/orxonox/branches/updater/src/gui/orxonox_gui_gtk.cc @ 3296

Last change on this file since 3296 was 3296, checked in by bensch, 19 years ago

orxonox/branches/updater: now the GUI just opens the first time, and the seccond time only if requested by —gui.

File size: 35.1 KB
Line 
1/*
2   orxonox - the future of 3D-vertical-scrollers
3
4   Copyright (C) 2004 orx
5
6   This program is free software; you can redistribute it and/or modify
7   it under the terms of the GNU General Public License as published by
8   the Free Software Foundation; either version 2, or (at your option)
9   any later version.
10
11   This program is distributed in the hope that it will be useful,
12   but WITHOUT ANY WARRANTY; without even the implied warranty of
13   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14   GNU General Public License for more details.
15
16   You should have received a copy of the GNU General Public License
17   along with this program; if not, write to the Free Software Foundation,
18   Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. 
19
20
21   ### File Specific:
22   main-programmer: Benjamin Grauer
23
24*/
25
26
27#include <iostream>
28
29#include "orxonox_gui_gtk.h"
30
31
32using namespace std;
33
34// temporarily.
35#include "orxonox_gui_flags.h"
36#include "orxonox_gui_exec.h"
37extern Window* orxonoxGUI;
38extern OrxonoxGuiFlags* flags;
39extern OrxonoxGuiExec* exec;
40
41#ifdef HAVE_GTK2
42/**
43   \brief Initializes the Guis GTK-stuff.
44   \param argc the argument count.
45   \param argv The Argument strings.
46*/
47bool initGTK(int argc, char *argv[])
48{
49#ifdef HAVE_GTHREAD
50  PRINTF(3)("Initializing the ThreadSystem of the GUI\n");
51  g_thread_init(NULL);
52  gdk_threads_init();
53#endif /* HAVE_GTHREAD */
54  gtk_init (&argc, &argv);
55  gtk_rc_parse( "rc" );
56}
57
58/**
59   \brief enters the GTK-main-loop
60*/
61bool mainloopGTK(void)
62{
63  gdk_threads_enter();
64  gtk_main();
65  gdk_threads_leave();
66  delete Window::mainWindow;
67}
68#endif /* HAVE_GTK2 */
69
70
71//////////////////////////////
72/// DEFINING WIDGET-CLASES ///
73//////////////////////////////
74
75/* WIDGET */
76
77/**
78   \brief deletes any given Widget
79   This is still pretty crappy.
80*/
81Widget::~Widget()
82{
83  this->destroy();
84}
85
86/**
87   \brief Initializes a widget.
88   Initializes the next Pointer and the other Widget-specific Defaults.
89*/
90void Widget::init()
91{
92  next = NULL;
93  this->title = NULL;
94  return;
95}
96
97/**
98   \brief Destroys a Widget
99*/
100void Widget::destroy(void)
101{
102  if (this->title)
103    {
104      delete []this->title;
105    }
106 
107  PRINTF(4)("deleting the Widget part.\n");
108
109  PRINTF(4)("deleting recursively\n");
110
111  // deleting next item if existent
112  if (this->next)
113    delete this->next;
114  this->next = NULL;
115
116  //!  \todo not hiding widget, deleting.
117  //  this->hide();
118  //  delete this->widget;
119}
120
121/**
122   \brief makes the widget visible.
123*/
124void Widget::show()
125{
126#ifdef HAVE_GTK2
127  gtk_widget_show (this->widget);
128#endif /* HAVE_GTK2 */
129}
130
131/**
132   \brief hides the widget.
133*/
134void Widget::hide()
135{
136#ifdef HAVE_GTK2
137  gtk_widget_hide (this->widget);
138#endif /* HAVE_GTK2 */
139}
140
141/**
142   \brief Sets the resolution of a specific widget to the given size.
143   \param width the width of the widget to set.
144   \param height the height of the widget to set.
145*/
146void Widget::setSize(int width, int height)
147{
148#ifdef HAVE_GTK2
149  gtk_widget_set_usize (this->widget, width, height);
150#endif /* HAVE_GTK2 */
151}
152
153/**
154   \brief searches through widgets for a Name.
155*/
156Widget* Widget::findWidgetByName(char* name, unsigned int depth)
157{
158  Widget* tmp = NULL;
159  if (this->title && !strcmp(this->title, name))
160    return this;
161
162  if (this->isOption < 0 && static_cast<Packer*>(this)->down)
163    tmp = static_cast<Packer*>(this)->down->findWidgetByName(name, depth+1);
164  if (tmp)
165    return tmp;
166
167 
168  if (depth>0 && this->next)
169    return this->next->findWidgetByName(name, depth);
170
171  return NULL;
172}
173
174/**
175   \brief Moves through all the Widgets downwards from this and executes the function on them.
176   \param function must be of type void and takes a Widget* as an Input.
177   \param depth the current depth. if > 0 then the next Widget will also be walked through.
178*/
179void Widget::walkThrough (void (*function)(Widget*), unsigned int depth)
180{
181  function(this);
182  if (this->isOption < 0)
183    {
184      static_cast<Packer*>(this)->down->walkThrough (function, depth+1);
185    } 
186
187  if (this->next && depth != 0)
188    this->next->walkThrough(function, depth);
189}
190
191/**
192   \brief Moves through all the Widgets downwards from this and executes the function on them.
193   \param function must be of type void and takes a Widget* as an Input.
194   \param data Additional Data you want to pass to the function.
195   \param depth the current depth. if > 0 then the next Widget will also be walked through.
196*/
197void Widget::walkThrough (void (*function)(Widget*, void*), void* data, unsigned int depth)
198{
199  function(this, data);
200  if (this->isOption < 0)
201    {
202      static_cast<Packer*>(this)->down->walkThrough(function, data, depth+1);
203    }
204  if (this->next && depth != 0)
205    this->next->walkThrough(function, data, depth);
206}
207
208/**
209    \brief This is for listing the option of "widget"
210    \param widget specifies the widget that should be listed
211*/
212void Widget::listOptions (Widget* widget)
213{
214  if (widget->isOption < 0 && static_cast<Packer*>(widget)->groupName)
215    cout << "[" << static_cast<Packer*>(widget)->groupName << "]\n";
216  if (widget->isOption >= 1 && widget->isOption <= 3)
217    cout << "  " << static_cast<Option*>(widget)->title <<" is : " << static_cast<Option*>(widget)->value <<endl;
218  else if (widget->isOption == 5)
219    cout << "  " << static_cast<Option*>(widget)->title <<" is : " << static_cast<OptionLabel*>(widget)->cValue <<endl;
220}
221
222/**
223    \brief This is for setting the option of "widget"
224    \param widget specifies the widget that should be set.
225*/
226void Widget::setOptions (Widget* widget)
227{
228  if (widget->isOption >= 1)
229    static_cast<Option*>(widget)->redraw();
230}
231
232/**
233   \brief Walks through all the Flags given at startuptime.
234*/
235void Widget::flagCheck(Widget* widget, void* flagName)
236{
237  if (widget->isOption>=1)
238    {     
239      Option* option = (Option*)widget;
240      char* name = (char*)flagName;
241      char* value = NULL;
242      bool found = false;
243      // check if long flag matches
244      if ((option->flagName && strlen(name)>2 && !strncmp(name+2, option->flagName, strlen(option->flagName)) && (name[strlen(option->flagName)+2] == '\0' || name[strlen(option->flagName)+2] == '=') ))
245        {
246          found = true;
247          if (name[strlen(option->flagName)+2] == '=')
248            {
249              value = name+strlen(option->flagName)+3;
250            }
251        }
252      else if (option->flagNameShort && strlen(name)>1 && !strncmp(name+1, option->flagNameShort, strlen(option->flagNameShort))&& (name[strlen(option->flagNameShort)+1] == '\0' || name[strlen(option->flagNameShort)+1] == '=')) // check if short flag matches
253        {
254          found = true;
255          if (name[strlen(option->flagNameShort)+1] == '=')
256            {
257              value = name+strlen(option->flagNameShort)+2;
258            }     
259        }
260
261      if (found)
262        {
263          PRINT(3)("found matching Flag %s\n", name);
264          if (value)
265            {
266              PRINT(3)("with Value %s\n", value);
267              option->value = atoi(value);
268            }
269          else
270            {
271              option->value = !option->defaultValue;
272            }
273          option->redraw();
274        }
275
276    }
277}
278
279#ifdef HAVE_GTK2
280/**
281    \brief Connect any signal to any given Sub-widget
282*/
283gulong Widget::connectSignal (char* event, gint (*signal)(GtkWidget*, GdkEvent*, void *))
284{
285  return g_signal_connect (G_OBJECT (this->widget), event, G_CALLBACK (signal), NULL);
286}
287
288/**
289   \brief Connect a signal with additionally passing the whole Object
290*/
291gulong Widget::connectSignal (char* event, gint (*signal)( GtkWidget*, Widget *))
292{
293  return g_signal_connect (G_OBJECT (this->widget), event, G_CALLBACK (signal), this);
294}
295
296/**
297   \brief Connect a signal with additionally passing a whole external Object
298*/
299gulong Widget::connectSignal (char* event, void* extObj, gint (*signal)(GtkWidget*, GdkEvent*, void *))
300{
301  return g_signal_connect (G_OBJECT (this->widget), event, G_CALLBACK (signal), extObj);
302}
303
304/**
305   \brief Connect a signal with additionally passing a whole external Object
306*/
307gulong Widget::connectSignal (char* event, void* extObj, gint (*signal)(GtkWidget*, GdkEventKey*, void *))
308{
309  return g_signal_connect (G_OBJECT (this->widget), event, G_CALLBACK (signal), extObj);
310}
311
312void Widget::disconnectSignal (gulong signalID)
313{
314  g_signal_handler_disconnect (G_OBJECT (this->widget), signalID);
315}
316
317/**
318   \brief Signal that does absolutely nothing
319   \param widget The widget that initiated the Signal
320   \param event The event-type.
321   \param nothing nothin.
322*/
323gint Widget::doNothingSignal (GtkWidget *widget, GdkEvent* event, void* nothing)
324{
325}
326#endif /* HAVE_GTK2 */
327
328//void deleteWidget(Widget* lastWidget)
329
330
331/* PACKERS */
332
333/**
334   \brief Initializes a Packer.
335
336   Sets the down-pinter to NULL and other PackerSpecific-values to their defaults.
337*/
338void Packer::init (void)
339{
340  down = NULL;
341  groupName = NULL;
342
343
344  static_cast<Widget*>(this)->init();
345  return;
346}
347
348/**
349   \brief Destroys a Packer.
350*/
351void Packer::destroy(void)
352{ 
353  PRINTF(4)("deleting the Packer part.\n");
354 
355  if (groupName)
356    delete []groupName;
357
358  //deleting recursively.
359  if (this->down)
360    delete this->down;
361  this->down = NULL;
362
363  static_cast<Widget*>(this)->destroy();
364}
365
366/**
367   \brief Sets the group name under which all the lower widgets of this will be saved.
368   \param name The name of the group.
369*/
370void Packer::setGroupName (char* name)
371{
372  if (groupName)
373    delete groupName;
374  groupName = new char [strlen(name)+1];
375  strcpy(groupName, name);
376}
377
378/**
379   \brief Retrieves the group name under which all the lower widgets of this will be saved.
380   \returns name The name of the group.
381*/
382char* Packer::getGroupName (void)
383{
384  return groupName;
385}
386
387/* CONTAINERS */
388
389/**
390   \brief Initializes a Container.
391
392   sets the Container-Specific defaults.
393*/
394void Container::init (void)
395{
396  isOption = -1;
397
398  static_cast<Packer*>(this)->init();
399
400  return;
401}
402
403/**
404   \brief Destroys a Container.
405*/
406void Container::destroy(void)
407{ 
408  PRINTF(4)("deleting the Container part.\n");
409
410  static_cast<Packer*>(this)->destroy();
411}
412
413/**
414   \briefFills a Container with lowerWidget.
415   \param lowerWidget the Widget that should be filled into the Container.
416
417   It does this by filling up the down pointer only if down points to NULL.
418*/
419void Container::fill (Widget *lowerWidget)
420{
421  if (this->down == NULL)
422    {
423#ifdef HAVE_GTK2
424      gtk_container_add (GTK_CONTAINER (this->widget), lowerWidget->widget);
425#endif /* HAVE_GTK2 */
426      this->down = lowerWidget;
427    }
428  else
429    PRINTF(1)("!!error!! You try to put more than one Widget into a Container. \nNot including this item.\nThis is only possible with Boxes.\n");
430}
431
432// gtk_container_set_border_width (GTK_CONTAINER (widget), 5);
433
434/* WINDOW */
435
436Window* Window::mainWindow = NULL;
437
438/**
439   \brief Adds a new Window Windows to the List of Windows.
440   \param windowToAdd The Windows that should be added to the List
441   \todo this instead of windowToAdd (possibly)
442*/
443void Window::addWindow(Window* windowToAdd)
444{
445  if (!mainWindow)
446    {
447      mainWindow = windowToAdd;
448      return;
449    }
450
451  Widget* tmpWindow = mainWindow;
452  while (tmpWindow->next)
453    tmpWindow = tmpWindow->next;
454  tmpWindow->next = windowToAdd;
455 
456  return;
457}
458     
459
460/**
461   \brief Creating a new Window without a Name
462*/
463Window::Window (void)
464{
465  this->init();
466}
467
468/**
469   \brief Creating a Window with a name
470   \param windowName the name the window should get.
471*/
472
473Window::Window (char* windowName)
474{
475  this->init();
476  this->setTitle (windowName);
477}
478
479/**
480   \brief Destructs a Window.
481*/
482Window::~Window(void)
483{
484  this->destroy();
485}
486
487/**
488   \brief initializes a new Window
489*/
490void Window::init()
491{
492  if (!mainWindow)
493    mainWindow = this;
494 
495  isOpen = false;
496
497  static_cast<Container*>(this)->init();
498
499#ifdef HAVE_GTK2
500  widget = gtk_window_new (GTK_WINDOW_TOPLEVEL);
501  gtk_window_set_policy (GTK_WINDOW(widget), TRUE, TRUE, TRUE);
502#if !defined(__WIN32__)
503  //  gtk_window_set_decorated (GTK_WINDOW (widget), FALSE);
504#endif
505  gtk_container_set_border_width (GTK_CONTAINER (widget), 3);
506#endif /* HAVE_GTK2 */
507}
508
509/**
510   \brief Destroys a Window.
511*/
512void Window::destroy(void)
513{ 
514  if (this->title)
515    PRINTF(3)("deleting the Window: %s\n", this->title);
516  else 
517    PRINTF(3)("deleting the Window.\n");
518
519  this->hide();
520  static_cast<Container*>(this)->destroy();
521 
522}
523
524/**
525   \brief Shows all Widgets that are included within this->widget.
526*/
527void Window::showall ()
528{
529  if (!isOpen)
530    {
531      //      printf ("showall\n");
532#ifdef HAVE_GTK2
533      gtk_widget_show_all  (widget);
534#endif /* HAVE_GTK2 */ 
535     isOpen = true;
536    }
537  else
538    {
539      //      printf ("showone\n");
540#ifdef HAVE_GTK2
541      gtk_widget_show (widget);
542#endif /* HAVE_GTK2 */
543    }
544}
545
546/**
547   \brief Set The Window-title to title
548   \param title title the Window should get.
549*/
550void Window::setTitle (char* title)
551{
552  if (this->title)
553    delete []this->title;
554  this->title = new char[strlen(title)+1];
555  strcpy(this->title, title);
556#ifdef HAVE_GTK2
557  gtk_window_set_title (GTK_WINDOW (widget), title);
558#endif /* HAVE_GTK2 */
559}
560
561/**
562   \brief opens up a Window and fixes the Focus to it
563*/
564void Window::open()
565{
566  if (this != mainWindow)
567    {
568      isOpen = true;
569#ifdef HAVE_GTK2
570      gtk_widget_show_all(widget);
571      gtk_grab_add(widget);
572#endif /* HAVE_GTK2 */
573    }
574}
575
576/**
577   \brief closes up a Window and removes the Focus from it
578*/
579void Window::close()
580{
581  if (this != mainWindow)
582    {
583      isOpen = false;
584#ifdef HAVE_GTK2
585      gtk_grab_remove(widget);
586      gtk_widget_hide (widget);
587#endif /* HAVE_GTK2 */
588    }
589}
590
591#ifdef HAVE_GTK2
592/**
593   \brief opens up a window (not topmost Window).
594   this is the Signal that does it. !!SIGNALS ARE STATIC!!
595   \param widget the widget that did it.
596   \param event the event that did it.
597   \param window the Window that should be opened
598*/
599gint Window::windowOpen (GtkWidget *widget, GdkEvent* event, void* window)
600{
601  static_cast<Window*>(window)->open();
602}
603
604/**
605   \brief closes a window (not topmost Window).
606   this is the Signal that does it. !!SIGNALS ARE STATIC!!
607   \param widget the widget that did it!
608   \param event the event that did it!
609   \param window the Window that should be closed
610*/
611gint Window::windowClose (GtkWidget *widget, GdkEvent* event, void* window)
612{
613  static_cast<Window*>(window)->close();
614}
615
616/**
617 * Quits the orxonox_GUI.
618 * This can be called as a Signal and is therefor static
619 \param widget The widget that called this function
620 \param event the event that happened to execute this function
621 \param data some data passed with the Signal
622 */
623gint Window::orxonox_gui_quit (GtkWidget *widget, GdkEvent *event, gpointer data)
624{
625  if (exec->shouldsave())
626    exec->writeToFile (Window::mainWindow);
627
628  gtk_main_quit();
629  return FALSE;
630}
631#endif /* HAVE_GTK2 */
632
633
634/* FRAME */
635
636/**
637    \brief Creates a new Frame without a name
638*/
639Frame::Frame (void)
640{
641  this->init();
642}
643
644/**
645   \brief Creates a new Frame with name title
646*/
647Frame::Frame (char* title)
648{
649  this->init();
650  this->setTitle(title);
651}
652
653/**
654   \brief destrcucts a Frame
655*/
656Frame::~Frame()
657{
658  this->destroy();
659}
660
661/**
662    \brief Initializes a new Frame with default settings
663*/
664void Frame::init()
665{
666  static_cast<Container*>(this)->init();
667
668#ifdef HAVE_GTK2
669  widget = gtk_frame_new ("");
670  gtk_container_set_border_width (GTK_CONTAINER (widget), 3);
671#endif /* HAVE_GTK2 */
672}
673
674/**
675   \brief Destroys a Frame.
676*/
677void Frame::destroy(void)
678{ 
679  if (this->title)
680    PRINTF(3)("deleting the Frame: %s\n", this->title);
681  else 
682    PRINTF(3)("deleting the Frame.\n");
683
684   static_cast<Container*>(this)->destroy();
685}
686
687/**
688   \brief Sets the Frames name to title
689   \param title The title the Frame should get.
690*/
691void Frame::setTitle (char* title)
692{
693  if (this->title)
694    delete []this->title;
695  this->title = new char[strlen(title)+1];
696  strcpy(this->title, title);
697#ifdef HAVE_GTK2
698  gtk_frame_set_label (GTK_FRAME (widget), title);
699#endif /* HAVE_GTK2 */
700}
701
702// EVENTBOX //
703
704/**
705   \brief Creates a new EventBox with default settings.
706*/
707EventBox::EventBox (void)
708{
709  this->init();
710}
711
712/**
713   \brief Creates a new EventBox with name title
714   \param title title the Eventbox should get (only data-structure-internal)
715*/
716EventBox::EventBox (char* title)
717{
718  this->init();
719  this->setTitle(title);
720}
721
722/**
723   \brief destructs an EventBox.
724*/
725EventBox::~EventBox(void)
726{
727  this->destroy();
728
729}
730
731/**
732   \brief Initializes a new EventBox
733*/
734void EventBox::init(void)
735{
736  isOption = -1;
737
738  static_cast<Container*>(this)->init();
739
740#ifdef HAVE_GTK2
741  widget = gtk_event_box_new ();
742  gtk_container_set_border_width (GTK_CONTAINER (widget), 3);
743#endif /* HAVE_GTK2 */
744}
745
746/**
747   \brief Destroys an EventBox.
748*/
749void EventBox::destroy(void)
750{ 
751  if (this->title)
752    PRINTF(3)("deleting the EventBox: %s\n", this->title);
753  else 
754    PRINTF(3)("deleting the EventBox.\n");
755
756  static_cast<Container*>(this)->destroy();
757}
758
759/**
760   \brief Sets the Title of the EventBox (not implemented)
761   \param title Name the EventBox should get (only datastructure-internal).
762*/
763void EventBox::setTitle (char* title)
764{
765  if (this->title)
766    delete []this->title;
767  this->title = new char[strlen(title)+1];
768  strcpy(this->title, title);
769}
770
771/* BOX */
772
773/**
774   \brief Creates a new horizontal Box
775*/
776Box::Box (void)
777{
778  this->init('h');
779}
780
781/**
782   \brief Creates a new Box of type boxtype
783   \param boxtype if 'v' the Box will be vertically, if 'h' the Box will be horizontally
784*/
785Box::Box (char boxtype)
786{
787  this->init(boxtype);
788}
789
790/**
791   \brief destructs a Box.
792*/
793Box::~Box(void)
794{
795  this->destroy();
796}
797
798/**
799   \brief Initializes a new Box with type boxtype
800   \param boxtype see Box(char boxtype)
801*/
802void Box::init(char boxtype)
803{
804  isOption = -2;
805
806  static_cast<Packer*>(this)->init();
807#ifdef HAVE_GTK2
808  if (boxtype == 'v')
809    {
810      widget = gtk_vbox_new (FALSE, 0);
811    }
812  else
813    {
814      widget = gtk_hbox_new (FALSE, 0);
815    }
816#endif /* HAVE_GTK2 */
817}
818
819/**
820   \brief Destroys a Box.
821*/
822void Box::destroy(void)
823{ 
824  if (this->title)
825    PRINTF(3)("deleting the Box: %s\n", this->title);
826  else 
827    PRINTF(3)("deleting the Box.\n");
828
829  static_cast<Packer*>(this)->destroy();
830}
831
832/**
833    \brief Fills a box with a given Widget.
834    \param lowerWidget the next Widget that should be appendet to this Box
835
836    It does this by apending the first one to its down-pointer and all its following ones to the preceding next-pointer. The last one will receive a NULL pointer as Next
837*/
838void Box::fill (Widget *lowerWidget)
839{
840#ifdef HAVE_GTK2
841  gtk_box_pack_start (GTK_BOX (this->widget), lowerWidget->widget, TRUE, TRUE, 0);
842#endif /* HAVE_GTK2 */
843  if (this->down == NULL)
844    this->down = lowerWidget;
845  else
846    {
847      Widget* tmp;
848      tmp = this->down;
849      while (tmp->next != NULL)
850        {
851          tmp = tmp->next;
852        }
853      tmp->next = lowerWidget;
854    }
855}
856
857/**
858   \brief Sets the Title of a Box.
859   \param title the new Title to set.
860*/
861void Box::setTitle(char* title)
862{
863  if (this->title)
864    delete []this->title;
865  this->title = new char[strlen(title)+1];
866  strcpy(this->title, title);
867}
868
869/* OPTION */
870
871/**
872   \brief Initializes a new Option.
873   sets all Option-Specific-Values to their defaults.
874*/
875void Option::init()
876{
877  value = 0;
878  flagName = NULL;
879  flagNameShort = NULL;
880  saveable = false;
881  defaultValue = 0;
882
883  static_cast<Widget*>(this)->init();
884
885  return;
886}
887
888/**
889   \brief Destroys an Option.
890*/
891void Option::destroy(void)
892{ 
893  PRINTF(4)("deleting the Option Part.\n");
894  if (flagName)
895    delete []flagName;
896  if (flagNameShort)
897    delete []flagNameShort;
898
899  static_cast<Widget*>(this)->destroy();
900}
901
902/**
903   \brief This sets The FlagName of an Option and defines its default Values
904   !! Options will be saved if flagname is different from NULL !!
905   \param flagname the Name that will be displayed in the output
906   \param defaultvalue the default Value for this Option (see definition of defaultvalue
907*/
908void Option::setFlagName (char* flagname, int defaultvalue)
909{
910  if (flagName)
911    delete flagName;
912  flagName = new char [strlen(flagname)+1];
913  strcpy(flagName, flagname);
914  defaultValue = defaultvalue;
915
916  //  cout << "Set Flagname of " << this->title << " to " << flagname << endl;
917}
918
919/**
920    \brief see Option::setFlagName (char* flagname, int defaultvalue)
921    \param flagname the Name that will be displayed in the output
922    \param defaultvalue the default Value for this Option (see definition of defaultvalue
923    \param flagnameshort a short flagname to be displayed in the output
924*/
925void Option::setFlagName (char* flagname, char* flagnameshort,  int defaultvalue)
926{
927  if (flagName)
928    delete flagName;
929  flagName = new char [strlen(flagname)+1];
930  strcpy(flagName, flagname);
931
932  if (flagNameShort)
933    delete flagNameShort;
934  flagNameShort = new char [strlen(flagnameshort)+1];
935  strcpy(flagNameShort, flagnameshort);
936  defaultValue = defaultvalue;
937  //  cout << "Set Flagname of " << this->title << " to " << flagname << endl;
938}
939
940/**
941   \brief Sets the saveable-state of the option to true.
942*/
943void Option::saveability(void)
944{
945  this->saveable = true;
946}
947
948/**
949   \brief Sets the saveable-state of the option.
950   \param isSaveable the saveable-state to set.
951*/
952void Option::saveability(bool isSaveable)
953{
954  this->saveable = isSaveable;
955}
956
957/**
958   \returns The saveable-state.
959*/
960bool Option::isSaveable(void)
961{
962  return this->saveable;
963}
964
965/* BUTTON */
966
967/**
968   \brief Creates a new Button with a buttonname
969   \param buttonname sets the Name of the Button
970*/
971Button::Button(char* buttonname)
972{
973  this->init();
974  this->setTitle(buttonname);
975}
976
977/**
978   \brief destructs a Button.
979*/
980Button::~Button(void)
981{
982  this->destroy();
983}
984
985/**
986   \brief Initializes a new Button
987*/
988void Button::init(void)
989{
990  isOption = 0;
991
992  static_cast<Option*>(this)->init();
993
994#ifdef HAVE_GTK2
995  widget = gtk_button_new_with_label ("");
996#endif /* HAVE_GTK2 */
997}
998
999/**
1000   \brief Destroys a Button.
1001*/
1002void Button::destroy(void)
1003{ 
1004  if (this->title)
1005    PRINTF(3)("deleting the Label: %s\n", this->title);
1006  else 
1007    PRINTF(3)("deleting the Label.\n");
1008
1009  static_cast<Option*>(this)->destroy();
1010}
1011
1012/**
1013   \brief Sets a new name to the Button
1014   \param title The name the Button should get
1015*/
1016void Button::setTitle (char *title)
1017{
1018  if (this->title)
1019    delete []this->title;
1020  this->title = new char[strlen(title)+1];
1021  strcpy(this->title, title);
1022#ifdef HAVE_GTK2
1023  gtk_button_set_label (GTK_BUTTON(widget), title);
1024#endif /* HAVE_GTK2 */
1025}
1026
1027/**
1028   \brief redraws the Button
1029   not implemented yet
1030*/
1031void Button::redraw ()
1032{
1033}
1034
1035/* CHECKBUTTON */
1036
1037/**
1038   \brief Creates a new CheckButton with an ame
1039   \param buttonname The name the CheckButton should display.
1040*/
1041CheckButton::CheckButton (char* buttonname)
1042{
1043  this->init();
1044  this->setTitle(buttonname);
1045
1046#ifdef HAVE_GTK2
1047  this->connectSignal ("clicked", this->OptionChange);
1048#endif /* HAVE_GTK2 */
1049}
1050
1051/**
1052   \brief destructs a CheckButton.
1053*/
1054CheckButton::~CheckButton(void)
1055{
1056  this->destroy();
1057}
1058
1059/**
1060   \brief Initialize a new CheckButton with default settings
1061*/
1062void CheckButton::init(void)
1063{
1064  isOption = 1;
1065
1066  static_cast<Option*>(this)->init();
1067
1068#ifdef HAVE_GTK2
1069  widget = gtk_check_button_new_with_label ("");
1070#endif /* HAVE_GTK2 */
1071}
1072
1073/**
1074   \brief Destroys a CheckButton.
1075*/
1076void CheckButton::destroy(void)
1077{ 
1078  if (this->title)
1079    PRINTF(3)("deleting the CheckButton: %s\n", this->title);
1080  else 
1081    PRINTF(3)("deleting the CheckButton.\n");
1082
1083  static_cast<Option*>(this)->destroy();
1084}
1085
1086/**
1087   \brief Sets a new Title to a CheckButton
1088   \param title The new Name the CheckButton should display.
1089*/
1090void CheckButton::setTitle(char* title)
1091{
1092  if (this->title)
1093    delete []this->title;
1094  this->title = new char[strlen(title)+1];
1095  strcpy(this->title, title);
1096#ifdef HAVE_GTK2
1097  gtk_button_set_label(GTK_BUTTON(widget), title);
1098#endif /* HAVE_GTK2 */
1099}
1100
1101bool CheckButton::isActive()
1102{
1103#ifdef HAVE_GTK2
1104  return gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget));
1105#endif /* HAVE_GTK2 */
1106}
1107
1108#ifdef HAVE_GTK2
1109/**
1110    \brief Signal OptionChange writes the Value from the CheckButton to its Object-Database.
1111    \param widget The widget(CheckButton) that has a changed Value
1112    \param checkbutton the CheckButton-Object that should receive the change.
1113*/
1114gint CheckButton::OptionChange (GtkWidget *widget, Widget* checkbutton)
1115{
1116  static_cast<CheckButton*>(checkbutton)->value = (int)gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON ((CheckButton*)checkbutton->widget));
1117  flags->setTextFromFlags(orxonoxGUI);   ////// must be different!!!
1118  cout << static_cast<CheckButton*>(checkbutton)->title << " set to: " << static_cast<CheckButton*>(checkbutton)->value << endl;
1119}
1120#endif /* HAVE_GTK2 */
1121
1122/**
1123   \brief Redraws the CheckButton (if option has changed).
1124   Example: if new settings are loaded the Button must be redrawn for the GUI to display that Change
1125*/
1126void CheckButton::redraw ()
1127{
1128#ifdef HAVE_GTK2
1129  gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (widget), value);
1130#endif /* HAVE_GTK2 */
1131}
1132
1133/* SLIDER */
1134
1135/**
1136   \brief Creates a new Slider
1137   \param slidername The data-structure-name of the slider.
1138   \param start The minimal Value of the slider.
1139   \param end The maximal Value of the slider.
1140*/
1141Slider::Slider (char* slidername, int start, int end)
1142{
1143  this->init(start, end);
1144  this->setValue(start);
1145  this->setTitle(slidername);
1146#ifdef HAVE_GTK2
1147  this->connectSignal ("value_changed", this->OptionChange);
1148#endif /* HAVE_GTK2 */
1149}
1150
1151/**
1152   \brief destructs a Slider.
1153*/
1154Slider::~Slider(void)
1155{
1156  this->destroy();
1157}
1158
1159/**
1160   \brief Initializes a Slider with start and end Values
1161   params: see Slider::Slider (char* slidername, int start, int end)
1162*/
1163void Slider::init(int start, int end)
1164{
1165  isOption = 2;
1166
1167  static_cast<Option*>(this)->init();
1168
1169#ifdef HAVE_GTK2
1170 widget = gtk_hscale_new_with_range (start, end, 5);
1171#endif /* HAVE_GTK2 */
1172}
1173
1174/**
1175   \brief Destroys a Slider.
1176*/
1177void Slider::destroy(void)
1178{ 
1179  if (this->title)
1180    PRINTF(3)("deleting the Slider: %s\n", this->title);
1181  else 
1182    PRINTF(3)("deleting the Slider.\n");
1183
1184  static_cast<Option*>(this)->destroy();
1185
1186}
1187
1188/**
1189   \brief Sets a new Title to the Slider
1190   \param title The new Name of the slider
1191*/
1192void Slider::setTitle(char* title)
1193{
1194  if (this->title)
1195    delete []this->title;
1196  this->title = new char[strlen(title)+1];
1197  strcpy(this->title, title);
1198}
1199
1200/**
1201   \brief Setting a new value to the Slider.
1202   Maybe you also require a Slider::redraw() for this to display
1203*/
1204void Slider::setValue(int value)
1205{
1206  this->value = value;
1207}
1208
1209/**
1210   \brief Redraws the widget
1211   Example: see void CheckButton::redraw ()
1212*/
1213void Slider::redraw ()
1214{
1215#ifdef HAVE_GTK2
1216  gtk_range_set_value (GTK_RANGE (widget), value);
1217#endif /* HAVE_GTK2 */
1218}
1219
1220#ifdef HAVE_GTK2
1221/**
1222    \brief Signal OptionChange writes the Value from the Slider to its Object-Database.
1223    \param widget The widget(Slider) that has a changed Value
1224    \param slider the Slider-Object that should receive the change.
1225*/
1226gint Slider::OptionChange (GtkWidget *widget, Widget* slider)
1227{
1228  static_cast<Slider*>(slider)->value = (int)gtk_range_get_value (GTK_RANGE ((Slider*)slider->widget));
1229  flags->setTextFromFlags(orxonoxGUI);  //// must be different !!!
1230  cout << static_cast<Slider*>(slider)->title << " set to: "<< static_cast<Slider*>(slider)->value << endl;
1231}
1232#endif /* HAVE_GTK2 */
1233
1234
1235/* MENU */
1236
1237/**
1238    \brief Creates a Menu-Item-list out of multiple input.
1239    !! Consider, that the last input argument has to be "lastItem" for this to work!!
1240    \param menuname The Database-Name of this Menu
1241    \param ... items to be added to this Menu. !! Consider, that the last input argument has to be "lastItem" for this to work!!
1242*/
1243Menu::Menu (char* menuname, ...)
1244{
1245  this->init();
1246  this->setTitle(menuname);
1247   
1248  char *itemName;
1249
1250#ifdef HAVE_GTK2             /////////////////////// REINPLEMENT
1251  va_start (itemlist, menuname);
1252  while (strcmp (itemName = va_arg (itemlist, char*), "lastItem"))
1253    {
1254      this->addItem(itemName);
1255    }
1256  va_end(itemlist);
1257#endif /* HAVE_GTK2 */
1258
1259#ifdef HAVE_GTK2
1260  gtk_option_menu_set_menu (GTK_OPTION_MENU (widget), menu);
1261  this->connectSignal ("changed", this->OptionChange);
1262#endif /* HAVE_GTK2 */
1263}
1264
1265/**
1266   \brief destructs a Menu.
1267*/
1268Menu::~Menu(void)
1269{
1270  this->destroy();
1271}
1272
1273/**
1274   \brief Initializes a new Menu with no items
1275*/
1276void Menu::init(void)
1277{
1278  isOption = 2;
1279
1280  static_cast<Option*>(this)->init();
1281
1282#ifdef HAVE_GTK2
1283  widget = gtk_option_menu_new ();
1284  menu = gtk_menu_new ();
1285#endif /* HAVE_GTK2 */
1286
1287}
1288
1289/**
1290   \brief Destroys a Menu.
1291*/
1292void Menu::destroy(void)
1293{ 
1294  if (this->title)
1295    PRINTF(3)("deleting the Menu: %s\n", this->title);
1296  else 
1297    PRINTF(3)("deleting the Menu.\n");
1298  //! \todo destroy menu
1299 
1300  static_cast<Option*>(this)->destroy();
1301}
1302
1303
1304/**
1305 * Sets the Database-Name of this Menu
1306 \param title Database-Name to be set.
1307*/
1308void Menu::setTitle(char* title)
1309{
1310  if (this->title)
1311    delete []this->title;
1312  this->title = new char[strlen(title)+1];
1313  strcpy(this->title, title);
1314}
1315
1316/**
1317   \brief appends a new Item to the Menu-List.
1318   \param itemName the itemName to be appendet.
1319*/
1320void Menu::addItem (char* itemName)
1321{
1322#ifdef HAVE_GTK2
1323  item = gtk_menu_item_new_with_label (itemName);
1324  gtk_menu_shell_append(GTK_MENU_SHELL (menu), item);
1325#endif /* HAVE_GTK2 */
1326}
1327
1328/**
1329   \brief Redraws the widget
1330   Example: see void CheckButton::redraw ()
1331*/
1332void Menu::redraw ()
1333{
1334#ifdef HAVE_GTK2
1335 gtk_option_menu_set_history (GTK_OPTION_MENU (widget), value);
1336#endif /* HAVE_GTK2 */
1337}
1338
1339#ifdef HAVE_GTK2
1340/**
1341    \brief Signal OptionChange writes the Value from the Menu to its Object-Database.
1342    \param widget The widget(Menu) that has a changed Value
1343    \param menu the Menu-Object that should receive the change.
1344*/
1345gint Menu::OptionChange (GtkWidget *widget, Widget* menu)
1346{
1347  static_cast<Menu*>(menu)->value = (int)gtk_option_menu_get_history (GTK_OPTION_MENU (menu->widget));
1348  flags->setTextFromFlags(orxonoxGUI); //// must be different !!!
1349  cout << static_cast<Menu*>(menu)->title << " changed to : " << static_cast<Menu*>(menu)->value << endl;
1350}
1351#endif /* HAVE_GTK2 */
1352
1353/* OPTION LABEL */
1354
1355/**
1356   \brief Creates a new OptionLabel with a LabelName and a Value.
1357   \param label The name of the OptionLabel.
1358   \param value The Value of the OptionLabel (what will be displayed).
1359*/
1360OptionLabel::OptionLabel(char* label, char* value)
1361{
1362  init();
1363  setTitle(label);
1364  setValue(value);
1365}
1366
1367/**
1368   \brief destructs an OptionLabel.
1369*/
1370OptionLabel::~OptionLabel(void)
1371{
1372  this->destroy();
1373}
1374
1375/**
1376   \brief Initializes an OptionLabel
1377*/
1378void OptionLabel::init(void)
1379{
1380  static_cast<Option*>(this)->init();
1381  isOption = 5;
1382  cValue = NULL;
1383
1384#ifdef HAVE_GTK2
1385  widget = gtk_label_new ("");
1386#endif /* HAVE_GTK2 */
1387}
1388
1389/**
1390   \brief Destroys a OptionLabel.
1391*/
1392void OptionLabel::destroy(void)
1393{ 
1394  if (this->title)
1395    PRINTF(3)("deleting the OptionLabel: %s\n", this->title);
1396  else 
1397    PRINTF(3)("deleting the OptionLabel.\n");
1398  if (cValue)
1399    delete []cValue;
1400
1401  static_cast<Option*>(this)->destroy();
1402}
1403
1404
1405/**
1406   \brief Updates the value of an OptionLabel
1407   \param newValue The new Name that should be displayed.
1408*/
1409void OptionLabel::setValue(char* newValue)
1410{
1411  if (cValue)
1412    delete cValue;
1413  cValue = new char [strlen(newValue)+1];
1414  strcpy(cValue, newValue);
1415#ifdef HAVE_GTK2
1416  gtk_label_set_text (GTK_LABEL (widget), cValue);
1417#endif /* HAVE_GTK2 */
1418}
1419
1420/**
1421   \brief Sets a ned Title to the OptionLabel.
1422   \param title The now title of the OptionLabel.
1423*/
1424void OptionLabel::setTitle(char* title)
1425{
1426  if (this->title)
1427    delete []this->title;
1428  this->title = new char [strlen(title)+1];
1429  strcpy(this->title, title);
1430#ifdef HAVE_GTK2
1431  gtk_label_set_text (GTK_LABEL (widget), title);
1432#endif /* HAVE_GTK2 */
1433}
1434
1435/**
1436   \brief Redraws an OptionLabel (not implemented yet, but it works).
1437*/
1438void OptionLabel::redraw(void)
1439{
1440 
1441}
1442
1443/**
1444   \brief Creates a new default Label with no Text.
1445   You migth consider adding Label::setTitle with this.
1446*/
1447Label::Label ()
1448{
1449  this->init();
1450}
1451
1452/**
1453   \brief Creates a new Label with a Text.
1454   \param text The text to be displayed.
1455*/
1456Label:: Label (char* text)
1457{
1458  this->init();
1459  this->setTitle(text);
1460}
1461
1462/**
1463   \brief destructs a Label.
1464*/
1465Label::~Label(void)
1466{
1467  this->destroy();
1468}
1469
1470/**
1471   \brief initializes a new Label
1472*/
1473void Label::init(void)
1474{
1475  isOption = 0;
1476
1477  static_cast<Widget*>(this)->init();
1478
1479#ifdef HAVE_GTK2
1480  widget = gtk_label_new ("");
1481  gtk_label_set_line_wrap (GTK_LABEL(widget), TRUE);
1482#endif /* HAVE_GTK2 */
1483}
1484
1485/**
1486   \brief Destroys a Label.
1487*/
1488void Label::destroy(void)
1489{ 
1490  if (this->title)
1491    PRINTF(3)("deleting the Label: %s\n", this->title);
1492  else 
1493    PRINTF(3)("deleting the Label.\n");
1494
1495  static_cast<Widget*>(this)->destroy();
1496}
1497
1498/**
1499   \brief Sets a new Text to a Label.
1500   \param text The text to be inserted into the Label.
1501*/
1502void Label::setTitle(char* text)
1503{
1504  if (this->title)
1505    delete []this->title;
1506  this->title = new char[strlen(text)+1];
1507  strcpy(this->title, text);
1508#ifdef HAVE_GTK2
1509  gtk_label_set_text (GTK_LABEL (this->widget), text);
1510#endif /* HAVE_GTK2 */
1511}
1512
1513/**
1514   \brief get the Text of a Label
1515   \return The Text the Label holds.
1516*/
1517char* Label::getText ()
1518{
1519  return this->title;
1520}
1521
1522/**
1523   \brief Creates a new ProgressBar.
1524*/
1525ProgressBar::ProgressBar (void)
1526{
1527  this->init ();
1528}
1529
1530/**
1531   \brief Creates a new ProgressBar.
1532   \param label The name you want to get the ProgressBar.
1533*/
1534ProgressBar::ProgressBar (char* label)
1535{
1536  this->init();
1537  this->setTitle (label);
1538}
1539
1540/**
1541   \brief destructs a ProgressBar
1542*/
1543ProgressBar::~ProgressBar ()
1544{
1545  this->destroy();
1546}
1547
1548/**
1549   \brief Initializes a ProgressBar
1550*/
1551void ProgressBar::init (void)
1552{
1553  isOption = 0;
1554  progress = 0.0;
1555  totalSize = 0.0;
1556
1557  static_cast<Widget*>(this)->init();
1558#ifdef HAVE_GTK2
1559  adjustment = (GtkAdjustment*)gtk_adjustment_new(0, 0, 100, 0, 0, 0);
1560  widget = gtk_progress_bar_new_with_adjustment(adjustment);
1561#endif /* HAVE_GTK2 */
1562}
1563
1564/**
1565   \brief Destroys a ProgressBar.
1566*/
1567void ProgressBar::destroy(void)
1568{ 
1569  if (this->title)
1570    PRINTF(3)("deleting the ProgressBar: %s\n", this->title);
1571  else 
1572    PRINTF(3)("deleting the ProgressBar.\n");
1573
1574  static_cast<Widget*>(this)->destroy();
1575}
1576
1577/**
1578   \brief Sets a ned Title to the ProgressBar.
1579   \param title The now title of the ProgressBar.
1580*/
1581void ProgressBar::setTitle(char* title)
1582{
1583  if (this->title)
1584    delete []this->title;
1585  this->title = new char [strlen(title)+1];
1586  strcpy(this->title, title);
1587}
1588
1589/**
1590   \brief Sets the Total size of the Bar. (ex. The maximum one can download)
1591*/
1592void ProgressBar::setTotalSize (double totalSize)
1593{
1594  this->totalSize = totalSize;
1595}
1596
1597/**
1598   \brief Sets the progress maximum is this->totalSize
1599*/
1600void ProgressBar::setProgress (double progress)
1601{
1602  this->progress = progress;
1603
1604  if (this->progress > this->totalSize)
1605    this->progress = this->totalSize;
1606
1607#ifdef HAVE_GTK2
1608  gtk_progress_set_value(GTK_PROGRESS(widget), this->progress*100.0/this->totalSize);
1609#endif /* HAVE_GTK2 */
1610  PRINTF(3)("Progress: %f\n", progress*100.0/totalSize);
1611}
1612
1613/**
1614    \brief returns the Progress Status
1615*/
1616double ProgressBar::getProgress (void)
1617{
1618  return this->progress;
1619}
1620
1621/* IMAGE */
1622
1623/**
1624   \brief Creates a new Image
1625   \param imagename the location of the Image on the Hard Disc
1626*/
1627Image::Image (char* imagename)
1628{
1629  this->init();
1630  if (this->title)
1631    delete []this->title;
1632  this->title = new char[strlen(imagename)+1];
1633  strcpy(this->title, imagename);
1634
1635#ifdef HAVE_GTK2
1636  widget = gtk_image_new_from_file (imagename);
1637#endif /* HAVE_GTK2 */
1638}
1639
1640/**
1641   \brief destructs an Image.
1642*/
1643Image::~Image(void)
1644{
1645  this->destroy();
1646}
1647
1648/**
1649    \brief Initializes a new Image
1650*/
1651void Image::init()
1652{
1653  isOption = 0;
1654
1655  static_cast<Widget*>(this)->init();
1656}
1657
1658/**
1659   \brief Destroys a Image.
1660*/
1661void Image::destroy(void)
1662{ 
1663  if (this->title)
1664    PRINTF(3)("deleting the Image: %s\n", this->title);
1665  else 
1666    PRINTF(3)("deleting the Image.\n");
1667
1668  static_cast<Widget*>(this)->destroy();
1669}
1670
1671/**
1672   \brief Sets a ned Title to the Image.
1673   \param title The now title of the OptionLabel.
1674*/
1675void Image::setTitle(char* title)
1676{
1677  if (this->title)
1678    delete []this->title;
1679  this->title = new char [strlen(title)+1];
1680  strcpy(this->title, title);
1681}
Note: See TracBrowser for help on using the repository browser.