gtkIOStream  1.7.0
GTK+ << C++ IOStream operators for GTK+. Now with ORBing, numerical computation, audio client and more ...
Buttons.H
Go to the documentation of this file.
1 /* Copyright 2000-2018 Matt Flax <flatmax@flatmax.org>
2  This file is part of GTK+ IOStream class set
3 
4  GTK+ IOStream is free software; you can redistribute it and/or modify
5  it under the terms of the GNU General Public License as published by
6  the Free Software Foundation; either version 2 of the License, or
7  (at your option) any later version.
8 
9  GTK+ IOStream is distributed in the hope that it will be useful,
10  but WITHOUT ANY WARRANTY; without even the implied warranty of
11  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12  GNU General Public License for more details.
13 
14  You have received a copy of the GNU General Public License
15  along with GTK+ IOStream
16  */
17 #ifndef BUTTONS_H_
18 #define BUTTONS_H_
19 
20 #include <iomanip>
21 #include <gtk/gtk.h>
22 #include <gdk/gdk.h>
23 #include <mffm/LinkList.H>
24 #include <string>
25 using namespace std;
26 
27 #ifdef _MSC_VER
28 #pragma warning( disable : 4005 4554)
29 #endif
30 
33 class AnyFuncData {
34 public:
35  AnyFuncData(void) {
36  str=NULL;
37  func=NULL;
38  data=NULL;
39  }
40  //AnyFuncData(char *s, GCallback f, gpointer d){str=s; func=f; data=d;}
41  AnyFuncData(const string &s, GCallback f, gpointer d) {
42  str=s.c_str();
43  func=f;
44  data=d;
45  }
46  AnyFuncData(const char *s, GCallback f, gpointer d) {
47  str=s;
48  func=f;
49  data=d;
50  }
51  //AnyFuncData(char *s, void (*f)(void *, void *), gpointer d){str=s; func=reinterpret_cast<GCallback>(f); data=d;}
52  AnyFuncData(const char *s, void (*f)(void *, void *), gpointer d) {
53  str=s;
54  func=reinterpret_cast<GCallback>(f);
55  data=d;
56  }
57  const char *str;
58  void (*func)();
59  gpointer data;
60 };
61 #define ANYSTRUCT(s,f,d) AnyFuncData(s,f,d)
62 #define BUTTONANYSTRUCT(s,f,d) AnyFuncData(s,f,d)
63 
66 class LabelFuncData : public AnyFuncData {
67 public:
69  LabelFuncData(const string &s, GCallback f, gpointer d) : AnyFuncData(s, f, d) {}
70  LabelFuncData(const char *s, GCallback f, gpointer d) : AnyFuncData(s, f, d) {}
71  LabelFuncData(const char *s, void (*f)(void *, void *), gpointer d) : AnyFuncData(s, f, d) {}
72 };
73 #define BUTTONLABELSTRUCT(s,f,d) LabelFuncData(s,f,d) // visual C++ doesn't support compound literals
74 
76 #define GDKPIXMAPCREATE(win, ref) gdk_pixmap_colormap_create_from_xpm_d(gtk_widget_get_window(win),gtk_widget_get_colormap(win),NULL,NULL,ref)
77 #define GTKPIXMAPCREATE(pixGdk) (GtkPixmap*)gtk_image_new_from_pixmap(pixGdk, NULL)
79 
81 class PixmapFuncData : public AnyFuncData {
82 public:
83  PixmapFuncData(const char **p, void (*f)(void *, void *), gpointer d) : AnyFuncData(NULL, f, d) {
84  pixGtk=p;
85  }
86  PixmapFuncData(const char **p, GCallback f, gpointer d) : AnyFuncData(NULL, f, d) {
87  pixGtk=p;
88  }
90  pixGtk=NULL;
91  }
92  const char **pixGtk;
93 };
94 #define BUTTONPIXMAPSTRUCT(p,f,d) PixmapFuncData(p,f,d)
95 
99 public:
100  PixmapFuncDataTransparent(const char **i, void (*f)(void *, void *), gpointer d) : AnyFuncData(NULL, f, d) {
101  imageXPM=i;
102  }
103  PixmapFuncDataTransparent(const char **i, GCallback f, gpointer d) : AnyFuncData(NULL, f, d) {
104  imageXPM=i;
105  }
107  imageXPM=NULL;
108  }
109  const char **imageXPM;
110 };
111 #define BUTTONPIXMAPSTRUCTTRANSPARENT(i,f,d) PixmapFuncDataTransparent(i,f,d)
112 
115 class ToggleFuncData : public AnyFuncData {
116 public:
118  ToggleFuncData(const string &s, GCallback f, gpointer d) : AnyFuncData(s, f, d) {}
119  ToggleFuncData(const char *s, GCallback f, gpointer d) : AnyFuncData(s, f, d) {}
120  ToggleFuncData(const char *s, void (*f)(void *, void *), gpointer d) : AnyFuncData(s, f, d) {}
121 };
122 #define BUTTONTOGGLESTRUCT(s,f,d) ToggleFuncData(s,f,d)
123 
126 class ArrowFuncData : public AnyFuncData {
127 public:
129  whichArrow=(GtkArrowType)0;
130  whichShadow=(GtkShadowType)0;
131  }
132  ArrowFuncData(void (*f)(void *, void *), gpointer d, GtkArrowType at, GtkShadowType sh, GtkWidget *a) : AnyFuncData(NULL, f, d) {
133  whichArrow=at;
134  whichShadow=sh;
135  }
136  ArrowFuncData(GCallback f, gpointer d, GtkArrowType at, GtkShadowType sh, GtkWidget *a) : AnyFuncData(NULL, f, d) {
137  whichArrow=at;
138  whichShadow=sh;
139  }
140  GtkArrowType whichArrow;
141  GtkShadowType whichShadow;
142 };
143 #define BUTTONARROWSTRUCT(f,d,a,sh) arrowFuncData(f,d,a,sh)
144 
147 class RadioFuncData : public AnyFuncData {
148 public:
150  RadioFuncData(const string &s, GCallback f, gpointer d) : AnyFuncData(s, f, d) {}
151  RadioFuncData(const char *s, GCallback f, gpointer d) : AnyFuncData(s, f, d) {}
152  RadioFuncData(const char *s, void (*f)(void *, void *), gpointer d) : AnyFuncData(s, f, d) {}
153 };
154 #define BUTTONRADIOSTRUCT(s,f,d) RadioFuncData(s,f,d)
155 
158 class CheckFuncData : public AnyFuncData {
159 public:
161  CheckFuncData(const string &s, GCallback f, gpointer d) : AnyFuncData(s, f, d) {}
162  CheckFuncData(const char *s, GCallback f, gpointer d) : AnyFuncData(s, f, d) {}
163  CheckFuncData(const char *s, void (*f)(void *, void *), gpointer d) : AnyFuncData(s, f, d) {}
164 };
165 #define BUTTONCHECKSTRUCT(s,f,d) CheckFuncData(s,f,d)
166 
184 class Buttons : public LinkList<GtkWidget *> {
185 public:
186 
189  Buttons(void) {
190 #if GTK_MAJOR_VERSION==2
191  gdk_colormap_new(gdk_visual_get_best(),1);
192 #endif
193  }
194 
200  void setAlignment(float xAlign, float yAlign) {
201  gtk_button_set_alignment(GTK_BUTTON(current()), xAlign, yAlign);
202  gtk_widget_queue_draw(current());
203  }
204 
211  void getAlignment(float *xAlign, float *yAlign) {
212  gtk_button_get_alignment(GTK_BUTTON(current()), xAlign, yAlign);
213  }
214 
215 // /** \brief Destructor
216 // */
217 // ~Buttons(void){
218 // for (int i=1; i<=getCount(); i++)
219 // if (g_object_is_floating(current()))
220 // delete remove();
221 // }
222 //
227  if (nf.func)
228  g_signal_connect_after(G_OBJECT((GtkButton*)current()), "released",reinterpret_cast<GCallback>(nf.func), nf.data);
229  }
230 
234  void signalConnectAfter(const AnyFuncData &af) {
235  if (af.func)
236  g_signal_connect_after(G_OBJECT((GtkButton*)current()), "released", af.func, af.data);
237  }
238 
244  if (nfOld.func)
245  g_signal_handlers_disconnect_by_func(G_OBJECT((GtkButton*)current()), (void *)(nfOld.func), nfOld.data);
246  if (nfNew.func)
247  g_signal_connect(G_OBJECT((GtkButton*)current()), "released",reinterpret_cast<GCallback>(nfNew.func), nfNew.data);
248  }
249 
250 
254  void signalRemove(AnyFuncData nfOld) {
255  if (nfOld.func) {
256  g_signal_handlers_disconnect_by_func(G_OBJECT((GtkButton*)current()), (void *)(nfOld.func), nfOld.data);
257  }
258  }
259 
265  if (nf.str)
266  LinkList<GtkWidget *>::add(gtk_button_new_with_label(nf.str));
267  else
268  LinkList<GtkWidget *>::add(gtk_button_new());
269 
270  if (nf.func)
271  g_signal_connect(G_OBJECT((GtkButton*)current()), "released",reinterpret_cast<GCallback>(nf.func), nf.data);
272  gtk_widget_show(current());
273  return *this;
274  }
275 
281  LinkList<GtkWidget *>::add(gtk_button_new());
282  g_signal_connect_after(current(), "expose-event", G_CALLBACK(exposePixmap), (gpointer)nf.pixGtk);
283 
284  if (nf.func)
285  g_signal_connect(G_OBJECT(current()), "released",reinterpret_cast<GCallback>(nf.func), nf.data);
286  gtk_widget_show(current());
287  return *this;
288  }
289 
295  LinkList<GtkWidget *>::add(gtk_toggle_button_new_with_label(nf.str));
296  // working on insensitive colour modifications ... for later.
297 // #if GTK_MAJOR_VERSION==2
302 //
303 // #else
304 // GdkRGBA yellow = { 1., 1., 0., 0.5 };
305 // gtk_widget_override_background_colorcurrent(), GTK_STATE_FLAG_INCONSISTENT, &yellow);
306 // #endif
307 
308  if (nf.func)
309  g_signal_connect(G_OBJECT((GtkButton*)current()), "released",reinterpret_cast<GCallback>(nf.func), nf.data);
310  gtk_widget_show(current());
311  return *this;
312  }
313 
319  LinkList<GtkWidget *>::add(gtk_button_new());
320 
321  g_signal_connect_after(current(), "expose-event", G_CALLBACK(exposePixmap), (gpointer)pfdt.imageXPM);
322 
323  if (pfdt.func)
324  g_signal_connect(G_OBJECT(current()), "released",reinterpret_cast<GCallback>(pfdt.func), pfdt.data);
325  gtk_widget_show(current());
326  return *this;
327  }
328 
336  LinkList<GtkWidget *>::add(gtk_button_new());
337  GtkWidget *arrow=gtk_arrow_new(af.whichArrow,af.whichShadow);
338  gtk_container_add (GTK_CONTAINER (current()), arrow);
339  gtk_widget_show(arrow);
340 
341  if (af.func)
342  g_signal_connect(G_OBJECT((GtkButton*)current()), "released",reinterpret_cast<GCallback>(af.func), af.data);
343  gtk_widget_show_all(current());
344  return *this;
345  }
346 
353  if (!LinkList<GtkWidget *>::getCount()) // this is the first
354  LinkList<GtkWidget *>::add(gtk_radio_button_new_with_label(NULL,nf.str));
355  else
356  LinkList<GtkWidget *>::add(gtk_radio_button_new_with_label_from_widget(GTK_RADIO_BUTTON (current()), nf.str));
357  if (nf.func)
358  g_signal_connect(G_OBJECT((GtkButton*)current()), "released",reinterpret_cast<GCallback>(nf.func), nf.data);
359  gtk_widget_show(current());
360  return *this;
361  }
362 
368  if (nf.str)
369  LinkList<GtkWidget *>::add(gtk_check_button_new_with_label(nf.str));
370  else
371  LinkList<GtkWidget *>::add(gtk_check_button_new());
372 
373  if (nf.func)
374  g_signal_connect(G_OBJECT((GtkButton*)current()), "released",reinterpret_cast<GCallback>(nf.func), nf.data);
375  gtk_widget_show(current());
376  return *this;
377  }
378 
387  static gboolean exposePixmap(GtkWidget *widget, GdkEventExpose *event, gpointer data) {
388  GdkPixbuf *tipGDKPixBuf = gdk_pixbuf_new_from_xpm_data(static_cast<const char**>(data)); // get the pixbuf
389  int width = gdk_pixbuf_get_width(tipGDKPixBuf), height = gdk_pixbuf_get_height(tipGDKPixBuf);
390  gint allocWidth, allocHeight, allocX;//, allocY;
391 #if GTK_MAJOR_VERSION==2
392  allocX=widget->allocation.x;
393  allocWidth=widget->allocation.width;
394  allocHeight=widget->allocation.height;
395  //allocY=widget->allocation.y;
396 #else
397  GtkAllocation widgetAlloc;
398  gtk_widget_get_allocation(widget, &widgetAlloc);
399  allocX=widgetAlloc.x;
400  allocWidth=widgetAlloc.width;
401  allocHeight=widgetAlloc.height;
402  //allocY=widgetAlloc.y;
403 #endif
404  if ((allocWidth<width) | (allocHeight<height))
405  gtk_widget_set_size_request(widget, width, height); // resize the button to match the pixmap
406  else {
407  cairo_t *cr=gdk_cairo_create(gtk_widget_get_window(widget)); // get a cairo context for rendering
408 
409  // use alignment to draw appropriately
410  float xAlign, yAlign;
411  gtk_button_get_alignment(GTK_BUTTON(widget), &xAlign, &yAlign);
412  int xOffset=(int)((float)(allocWidth-width-1)*xAlign);
413  if (xOffset<0) xOffset=0;
414  int yOffset=(int)((float)(allocHeight-height-1)*yAlign);
415  if (yOffset<0) yOffset=0;
416 
417  gdk_cairo_set_source_pixbuf(cr, tipGDKPixBuf, allocX+xOffset, allocX+yOffset); // set the source to the pixbuf at the correct location
418  cairo_paint(cr); // paint it to the cairo context
419  cairo_destroy(cr); // destroy the context
420  }
421  return FALSE;
422  }
423 
435  void setLabelsFont(PangoFontDescription *pangoFontDescription) {
436  if (pangoFontDescription) {
437  GtkWidget *child=gtk_bin_get_child(GTK_BIN(current()));
438  if (child)
439  gtk_widget_modify_font(child,pangoFontDescription);
440  }
441  }
442 
446  void setLabel(const char*l) {
447  gtk_button_set_label(GTK_BUTTON(current()),l);
448  }
449 
453  const gchar *getLabel() {
454  return gtk_button_get_label(GTK_BUTTON(current()));
455  }
456 
461  int findIndex(GtkWidget* widget) {
462  int ret=0;
463  if (getCount()) {
464  GtkWidget *c=current(); // remember our current location
465  grab(1);
466  prev(); // we are at the last on the list
467  for (int i=1; i<=getCount(); i++) {
468  if (next()==widget) {
469  ret=i;
470  break;
471  }
472  }
473  while (next()!=c) ; // return to the original button
474  }
475  //std::cout<<"Buttons::findIndex = "<<ret<<std::endl;
476  return ret;
477  }
478 
483  GtkWidget *findWidget(int index) {
484  GtkWidget *retVal=NULL;
485  if (index<getCount() && index>0)
486  retVal=grab(index);
487  return retVal;
488  }
489 
495  static void setActive(GtkWidget *wid, bool state) {
496  gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(wid), state);
497  }
498 
503  void setActive(bool state) {
504  if (getCount())
505  gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(current()), state);
506  }
507 
512  bool getActive(void) {
513  if (getCount())
514  return gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(current()));
515  return false;
516  }
517 
523  static bool getActive(GtkWidget *wid) {
524  return gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(wid));
525  }
526 
532  grab(1);
533  for (int i=1; i<=getCount(); i++)
534  if (getActive())
535  return i;
536  else
537  next();
538  return 0;
539  }
540 };
541 #endif //BUTTONS_H_
class to pass for creating a transparent XPM overlay on a button
Definition: Buttons.H:98
void setAlignment(float xAlign, float yAlign)
Definition: Buttons.H:200
ToggleFuncData(const char *s, GCallback f, gpointer d)
Definition: Buttons.H:119
void setLabel(const char *l)
Definition: Buttons.H:446
PixmapFuncData(const char **p, GCallback f, gpointer d)
Definition: Buttons.H:86
bool getActive(void)
Definition: Buttons.H:512
CheckFuncData(const char *s, GCallback f, gpointer d)
Definition: Buttons.H:162
int findIndex(GtkWidget *widget)
Definition: Buttons.H:461
const char ** pixGtk
The pixmap to show.
Definition: Buttons.H:92
const gchar * getLabel()
Definition: Buttons.H:453
CheckFuncData(const char *s, void(*f)(void *, void *), gpointer d)
Definition: Buttons.H:163
class to pass using operator<< for creating a regular pixmap on a button
Definition: Buttons.H:81
ArrowFuncData(void)
Definition: Buttons.H:128
AnyFuncData(void)
Definition: Buttons.H:35
PixmapFuncDataTransparent(const char **i, void(*f)(void *, void *), gpointer d)
Definition: Buttons.H:100
LabelFuncData(const string &s, GCallback f, gpointer d)
Definition: Buttons.H:69
STL namespace.
GtkWidget * findWidget(int index)
Definition: Buttons.H:483
class to pass using operator<< for creating a toggle button with a label
Definition: Buttons.H:115
Buttons(void)
Constructor.
Definition: Buttons.H:189
GtkShadowType whichShadow
The shadow to use {GTK_SHADOW_NONE, GTK_SHADOW_IN, GTK_SHADOW_OUT, GTK_SHADOW_ETCHED_IN, GTK_SHADOW_ETCHED_OUT}.
Definition: Buttons.H:141
CheckFuncData(const string &s, GCallback f, gpointer d)
Definition: Buttons.H:161
float p
LabelFuncData(const char *s, GCallback f, gpointer d)
Definition: Buttons.H:70
class to pass using operator<< for creating a check button with a label
Definition: Buttons.H:158
void getAlignment(float *xAlign, float *yAlign)
Definition: Buttons.H:211
static void setActive(GtkWidget *wid, bool state)
Definition: Buttons.H:495
void setLabelsFont(PangoFontDescription *pangoFontDescription)
Definition: Buttons.H:435
RadioFuncData(const string &s, GCallback f, gpointer d)
Definition: Buttons.H:150
GtkArrowType whichArrow
The type of arrow to create {GTK_ARROW_UP, GTK_ARROW_DOWN, GTK_ARROW_LEFT, GTK_ARROW_RIGHT, GTK_ARROW_NONE}.
Definition: Buttons.H:140
ArrowFuncData(GCallback f, gpointer d, GtkArrowType at, GtkShadowType sh, GtkWidget *a)
Definition: Buttons.H:136
RadioFuncData(const char *s, void(*f)(void *, void *), gpointer d)
Definition: Buttons.H:152
ArrowFuncData(void(*f)(void *, void *), gpointer d, GtkArrowType at, GtkShadowType sh, GtkWidget *a)
Definition: Buttons.H:132
gpointer data
The data to pass to func when the button it pressed.
Definition: Buttons.H:59
RadioFuncData(void)
Definition: Buttons.H:149
int findActiveButtonIndex()
Definition: Buttons.H:531
const char * str
The label to show in the button.
Definition: Buttons.H:57
class to pass using operator<< for creating an arrow button
Definition: Buttons.H:126
static gboolean exposePixmap(GtkWidget *widget, GdkEventExpose *event, gpointer data)
overlay the pixmap image onto the button whenever required This method allows transparent XPMs to be ...
Definition: Buttons.H:387
LabelFuncData(const char *s, void(*f)(void *, void *), gpointer d)
Definition: Buttons.H:71
void signalRemove(AnyFuncData nfOld)
disconnect the old callback and reconnect a new callback
Definition: Buttons.H:254
static bool getActive(GtkWidget *wid)
Definition: Buttons.H:523
class to pass using operator<< for creating a label button
Definition: Buttons.H:66
ToggleFuncData(void)
Definition: Buttons.H:117
std::ostream & operator<<(std::ostream &stream, const BitStream &bitStream)
Definition: BitStream.C:204
void signalConnectAfter(LabelFuncData nf)
Destructor.
Definition: Buttons.H:226
AnyFuncData(const char *s, GCallback f, gpointer d)
Definition: Buttons.H:46
void(* func)()
The function to call when the button is pressed.
Definition: Buttons.H:58
AnyFuncData(const char *s, void(*f)(void *, void *), gpointer d)
Definition: Buttons.H:52
PixmapFuncDataTransparent(const char **i, GCallback f, gpointer d)
Definition: Buttons.H:103
const char ** imageXPM
The pointer to the image for overlaying on the button.
Definition: Buttons.H:109
CheckFuncData(void)
Definition: Buttons.H:160
ToggleFuncData(const string &s, GCallback f, gpointer d)
Definition: Buttons.H:118
ToggleFuncData(const char *s, void(*f)(void *, void *), gpointer d)
Definition: Buttons.H:120
RadioFuncData(const char *s, GCallback f, gpointer d)
Definition: Buttons.H:151
class to pass using operator<< for creating a radio button with a label
Definition: Buttons.H:147
void signalReplace(LabelFuncData nfOld, LabelFuncData nfNew)
disconnect the old callback and reconnect a new callback
Definition: Buttons.H:243
PixmapFuncData(const char **p, void(*f)(void *, void *), gpointer d)
Definition: Buttons.H:83
Class to setup buttons whic are either text, image or toggle types. Buttons are defined in terms of t...
Definition: Buttons.H:184
PixmapFuncData(void)
Definition: Buttons.H:89
AnyFuncData(const string &s, GCallback f, gpointer d)
Definition: Buttons.H:41
void setActive(bool state)
Definition: Buttons.H:503
class to pass using connectSignalAfter for connecting a signal to a widget
Definition: Buttons.H:33
void signalConnectAfter(const AnyFuncData &af)
connect a callback to execute after the currently connected callbacks
Definition: Buttons.H:234
LabelFuncData(void)
Definition: Buttons.H:68
gtkIOStream: /tmp/gtkiostream/include/Buttons.H Source File
GTK+ IOStream  Beta