diff options
author | 2013-08-15 20:38:57 +0200 | |
---|---|---|
committer | 2013-08-15 20:38:57 +0200 | |
commit | 60b4644d37583566563641185d13aaa1a453f908 (patch) | |
tree | d0f1bb918840647b0e9f18b22b3c270e6d8601ec /plugins/gtkui/gtkglext-gtk3/gtk | |
parent | 1ab7955320ef408889a220bd87af33ccc7de7a52 (diff) |
gtkui: added experimental gtkglext port to GTK3, fixed GTK3 build errors
Diffstat (limited to 'plugins/gtkui/gtkglext-gtk3/gtk')
-rw-r--r-- | plugins/gtkui/gtkglext-gtk3/gtk/gtkgl.h | 33 | ||||
-rw-r--r-- | plugins/gtkui/gtkglext-gtk3/gtk/gtkgldebug.h | 67 | ||||
-rw-r--r-- | plugins/gtkui/gtkglext-gtk3/gtk/gtkgldefs.h | 42 | ||||
-rw-r--r-- | plugins/gtkui/gtkglext-gtk3/gtk/gtkglinit.c | 230 | ||||
-rw-r--r-- | plugins/gtkui/gtkglext-gtk3/gtk/gtkglinit.h | 44 | ||||
-rw-r--r-- | plugins/gtkui/gtkglext-gtk3/gtk/gtkglprivate.h | 32 | ||||
-rw-r--r-- | plugins/gtkui/gtkglext-gtk3/gtk/gtkglversion.c | 29 | ||||
-rw-r--r-- | plugins/gtkui/gtkglext-gtk3/gtk/gtkglversion.h | 62 | ||||
-rw-r--r-- | plugins/gtkui/gtkglext-gtk3/gtk/gtkglwidget.c | 550 | ||||
-rw-r--r-- | plugins/gtkui/gtkglext-gtk3/gtk/gtkglwidget.h | 61 |
10 files changed, 1150 insertions, 0 deletions
diff --git a/plugins/gtkui/gtkglext-gtk3/gtk/gtkgl.h b/plugins/gtkui/gtkglext-gtk3/gtk/gtkgl.h new file mode 100644 index 00000000..331327eb --- /dev/null +++ b/plugins/gtkui/gtkglext-gtk3/gtk/gtkgl.h @@ -0,0 +1,33 @@ +/* GtkGLExt - OpenGL Extension to GTK+ + * Copyright (C) 2002-2004 Naofumi Yasufuku + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +#ifndef __GTK_GL_H__ +#define __GTK_GL_H__ + +#include <gdk/gdkgl.h> + +#define __GTKGL_H_INSIDE__ + +#include "gtkgldefs.h" +#include "gtkglversion.h" +#include "gtkglinit.h" +#include "gtkglwidget.h" + +#undef __GTKGL_H_INSIDE__ + +#endif /* __GTK_GL_H__ */ diff --git a/plugins/gtkui/gtkglext-gtk3/gtk/gtkgldebug.h b/plugins/gtkui/gtkglext-gtk3/gtk/gtkgldebug.h new file mode 100644 index 00000000..9d23f72b --- /dev/null +++ b/plugins/gtkui/gtkglext-gtk3/gtk/gtkgldebug.h @@ -0,0 +1,67 @@ +/* GtkGLExt - OpenGL Extension to GTK+ + * Copyright (C) 2002-2004 Naofumi Yasufuku + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +#ifndef __GTK_GL_DEBUG_H__ +#define __GTK_GL_DEBUG_H__ + +#include <glib.h> + +#include <gtk/gtkgldefs.h> + +G_BEGIN_DECLS + +typedef enum { + GTK_GL_DEBUG_MISC = 1 << 0, + GTK_GL_DEBUG_FUNC = 1 << 1 +} GtkGLDebugFlag; + +#ifdef G_ENABLE_DEBUG + +#define GTK_GL_NOTE(type, action) G_STMT_START { \ + if (gtk_gl_debug_flags & GTK_GL_DEBUG_##type) \ + { action; }; } G_STMT_END + +#if __STDC_VERSION__ < 199901L +# if __GNUC__ >= 2 +# define __func__ __FUNCTION__ +# else +# define __func__ "<unknown>" +# endif +#endif + +#define GTK_GL_NOTE_FUNC() G_STMT_START { \ + if (gtk_gl_debug_flags & GTK_GL_DEBUG_FUNC) \ + g_message (" - %s ()", __func__); } G_STMT_END + +#define GTK_GL_NOTE_FUNC_PRIVATE() G_STMT_START { \ + if (gtk_gl_debug_flags & GTK_GL_DEBUG_FUNC) \ + g_message (" -- %s ()", __func__); } G_STMT_END + +#else /* !G_ENABLE_DEBUG */ + +#define GTK_GL_NOTE(type, action) +#define GTK_GL_NOTE_FUNC() +#define GTK_GL_NOTE_FUNC_PRIVATE() + +#endif /* G_ENABLE_DEBUG */ + +GTK_GL_VAR guint gtk_gl_debug_flags; + +G_END_DECLS + +#endif /* __GTK_GL_DEBUG_H__ */ diff --git a/plugins/gtkui/gtkglext-gtk3/gtk/gtkgldefs.h b/plugins/gtkui/gtkglext-gtk3/gtk/gtkgldefs.h new file mode 100644 index 00000000..c2b3e57a --- /dev/null +++ b/plugins/gtkui/gtkglext-gtk3/gtk/gtkgldefs.h @@ -0,0 +1,42 @@ +/* GtkGLExt - OpenGL Extension to GTK+ + * Copyright (C) 2002-2004 Naofumi Yasufuku + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +#if !defined (__GTKGL_H_INSIDE__) && !defined (GTK_GL_COMPILATION) +#error "Only <gtk/gtkgl.h> can be included directly." +#endif + +#ifndef __GTK_GL_DEFS_H__ +#define __GTK_GL_DEFS_H__ + +#include <glib.h> + +G_BEGIN_DECLS + +#ifdef G_OS_WIN32 +# ifdef GTK_GL_COMPILATION +# define GTK_GL_VAR __declspec(dllexport) +# else +# define GTK_GL_VAR extern __declspec(dllimport) +# endif +#else +# define GTK_GL_VAR extern +#endif + +G_END_DECLS + +#endif /* __GTK_GL_DEFS_H__ */ diff --git a/plugins/gtkui/gtkglext-gtk3/gtk/gtkglinit.c b/plugins/gtkui/gtkglext-gtk3/gtk/gtkglinit.c new file mode 100644 index 00000000..ba658094 --- /dev/null +++ b/plugins/gtkui/gtkglext-gtk3/gtk/gtkglinit.c @@ -0,0 +1,230 @@ +/* GtkGLExt - OpenGL Extension to GTK+ + * Copyright (C) 2002-2004 Naofumi Yasufuku + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif /* HAVE_CONFIG_H */ + +#include <string.h> + +#include "gtkglprivate.h" +#include "gtkglinit.h" + +static gboolean gtk_gl_initialized = FALSE; + +guint gtk_gl_debug_flags = 0; /* Global GtkGLExt debug flag */ + +#ifdef G_ENABLE_DEBUG + +static const GDebugKey gtk_gl_debug_keys[] = { + {"misc", GTK_GL_DEBUG_MISC}, + {"func", GTK_GL_DEBUG_FUNC} +}; + +static const guint gtk_gl_ndebug_keys = G_N_ELEMENTS (gtk_gl_debug_keys); + +#endif /* G_ENABLE_DEBUG */ + +/** + * gtk_gl_parse_args: + * @argc: the number of command line arguments. + * @argv: the array of command line arguments. + * + * Parses command line arguments, and initializes global + * attributes of GtkGLExt. + * + * Any arguments used by GtkGLExt are removed from the array and + * @argc and @argv are updated accordingly. + * + * You shouldn't call this function explicitely if you are using + * gtk_gl_init(), or gtk_gl_init_check(). + **/ +static void +gtk_gl_parse_args (int *argc, + char ***argv) +{ + const gchar *env_string; + + if (gtk_gl_initialized) + return; + + /* + * If window manager doesn't watch the WM_COLORMAP_WINDOWS property on + * the top-level window, we have to set OpenGL window's colormap to the + * top-level window, especially in color index mode (color index mode + * uses own private colormap). This is achieved by setting the window's + * visual. + */ + env_string = g_getenv ("GTK_GL_INSTALL_VISUAL"); + if (env_string != NULL) + { + _gtk_gl_widget_install_toplevel_visual = !!g_ascii_strtoll (env_string, NULL, 0); + env_string = NULL; + } + +#ifdef G_ENABLE_DEBUG + env_string = g_getenv ("GTK_GL_DEBUG"); + if (env_string != NULL) + { + gtk_gl_debug_flags = g_parse_debug_string (env_string, + gtk_gl_debug_keys, + gtk_gl_ndebug_keys); + env_string = NULL; + } +#endif /* G_ENABLE_DEBUG */ + + if (argc && argv) + { + gint i, j, k; + + for (i = 1; i < *argc;) + { + if (strcmp ("--gtk-gl-install-visual", (*argv)[i]) == 0) + { + _gtk_gl_widget_install_toplevel_visual = TRUE; + (*argv)[i] = NULL; + } +#ifdef G_ENABLE_DEBUG + else if ((strcmp ("--gtk-gl-debug", (*argv)[i]) == 0) || + (strncmp ("--gtk-gl-debug=", (*argv)[i], 15) == 0)) + { + gchar *equal_pos = strchr ((*argv)[i], '='); + + if (equal_pos != NULL) + { + gtk_gl_debug_flags |= g_parse_debug_string (equal_pos+1, + gtk_gl_debug_keys, + gtk_gl_ndebug_keys); + } + else if ((i + 1) < *argc && (*argv)[i + 1]) + { + gtk_gl_debug_flags |= g_parse_debug_string ((*argv)[i+1], + gtk_gl_debug_keys, + gtk_gl_ndebug_keys); + (*argv)[i] = NULL; + i += 1; + } + (*argv)[i] = NULL; + } + else if ((strcmp ("--gtk-gl-no-debug", (*argv)[i]) == 0) || + (strncmp ("--gtk-gl-no-debug=", (*argv)[i], 18) == 0)) + { + gchar *equal_pos = strchr ((*argv)[i], '='); + + if (equal_pos != NULL) + { + gtk_gl_debug_flags &= ~g_parse_debug_string (equal_pos+1, + gtk_gl_debug_keys, + gtk_gl_ndebug_keys); + } + else if ((i + 1) < *argc && (*argv)[i + 1]) + { + gtk_gl_debug_flags &= ~g_parse_debug_string ((*argv)[i+1], + gtk_gl_debug_keys, + gtk_gl_ndebug_keys); + (*argv)[i] = NULL; + i += 1; + } + (*argv)[i] = NULL; + } +#endif /* G_ENABLE_DEBUG */ + i += 1; + } + + for (i = 1; i < *argc; i++) + { + for (k = i; k < *argc; k++) + if ((*argv)[k] != NULL) + break; + + if (k > i) + { + k -= i; + for (j = i + k; j < *argc; j++) + (*argv)[j-k] = (*argv)[j]; + *argc -= k; + } + } + + } + + /* Set the 'initialized' flag. */ + gtk_gl_initialized = TRUE; +} + +/** + * gtk_gl_init_check: + * @argc: Address of the <parameter>argc</parameter> parameter of your + * <function>main()</function> function. Changed if any arguments + * were handled. + * @argv: Address of the <parameter>argv</parameter> parameter of + * <function>main()</function>. Any parameters understood by + * gtk_gl_init() are stripped before return. + * + * This function does the same work as gtk_gl_init() with only + * a single change: It does not terminate the program if the library can't be + * initialized. Instead it returns %FALSE on failure. + * + * This way the application can fall back to some other means of communication + * with the user - for example a curses or command line interface. + * + * Return value: %TRUE if the GUI has been successfully initialized, + * %FALSE otherwise. + **/ +gboolean +gtk_gl_init_check (int *argc, + char ***argv) +{ + /* Init GdkGLExt library. */ + if (!gdk_gl_init_check (argc, argv)) + return FALSE; + + /* Parse args and init GtkGLExt library. */ + gtk_gl_parse_args (argc, argv); + + return TRUE; +} + +/** + * gtk_gl_init: + * @argc: Address of the <parameter>argc</parameter> parameter of your + * <function>main()</function> function. Changed if any arguments + * were handled. + * @argv: Address of the <parameter>argv</parameter> parameter of + * <function>main()</function>. Any parameters understood by + * gtk_gl_init() are stripped before return. + * + * Call this function before using any other GtkGLExt functions in your + * applications. It will initialize everything needed to operate the library + * and parses some standard command line options. @argc and + * @argv are adjusted accordingly so your own code will + * never see those standard arguments. + * + * <note><para> + * This function will terminate your program if it was unable to initialize + * the library for some reason. If you want your program to fall back to a + * textual interface you want to call gtk_gl_init_check() instead. + * </para></note> + **/ +void +gtk_gl_init (int *argc, + char ***argv) +{ + if (!gtk_gl_init_check (argc, argv)) + g_error ("GdkGLExt library initialization fails."); +} diff --git a/plugins/gtkui/gtkglext-gtk3/gtk/gtkglinit.h b/plugins/gtkui/gtkglext-gtk3/gtk/gtkglinit.h new file mode 100644 index 00000000..376ef6b9 --- /dev/null +++ b/plugins/gtkui/gtkglext-gtk3/gtk/gtkglinit.h @@ -0,0 +1,44 @@ +/* GtkGLExt - OpenGL Extension to GTK+ + * Copyright (C) 2002-2004 Naofumi Yasufuku + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +#if !defined (__GTKGL_H_INSIDE__) && !defined (GTK_GL_COMPILATION) +#error "Only <gtk/gtkgl.h> can be included directly." +#endif + +#ifndef __GTK_GL_INIT_H__ +#define __GTK_GL_INIT_H__ + +#include <gdk/gdk.h> + +#include <gdk/gdkgl.h> + +G_BEGIN_DECLS + +/* + * Initialization routines. + */ + +gboolean gtk_gl_init_check (int *argc, + char ***argv); + +void gtk_gl_init (int *argc, + char ***argv); + +G_END_DECLS + +#endif /* __GTK_GL_INIT_H__ */ diff --git a/plugins/gtkui/gtkglext-gtk3/gtk/gtkglprivate.h b/plugins/gtkui/gtkglext-gtk3/gtk/gtkglprivate.h new file mode 100644 index 00000000..9fde29bb --- /dev/null +++ b/plugins/gtkui/gtkglext-gtk3/gtk/gtkglprivate.h @@ -0,0 +1,32 @@ +/* GtkGLExt - OpenGL Extension to GTK+ + * Copyright (C) 2002-2004 Naofumi Yasufuku + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +#ifndef __GTK_GL_PRIVATE_H__ +#define __GTK_GL_PRIVATE_H__ + +#include <gtk/gtkgldefs.h> +#include <gtk/gtkgldebug.h> + +G_BEGIN_DECLS + +/* Install visual to top-level window. */ +extern gboolean _gtk_gl_widget_install_toplevel_visual; + +G_END_DECLS + +#endif /* __GTK_GL_PRIVATE_H__ */ diff --git a/plugins/gtkui/gtkglext-gtk3/gtk/gtkglversion.c b/plugins/gtkui/gtkglext-gtk3/gtk/gtkglversion.c new file mode 100644 index 00000000..8b5c5990 --- /dev/null +++ b/plugins/gtkui/gtkglext-gtk3/gtk/gtkglversion.c @@ -0,0 +1,29 @@ +/* GtkGLExt - OpenGL Extension to GTK+ + * Copyright (C) 2002-2004 Naofumi Yasufuku + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif /* HAVE_CONFIG_H */ + +#include "gtkglversion.h" + +const guint gtkglext_major_version = GTKGLEXT_MAJOR_VERSION; +const guint gtkglext_minor_version = GTKGLEXT_MINOR_VERSION; +const guint gtkglext_micro_version = GTKGLEXT_MICRO_VERSION; +const guint gtkglext_interface_age = GTKGLEXT_INTERFACE_AGE; +const guint gtkglext_binary_age = GTKGLEXT_BINARY_AGE; diff --git a/plugins/gtkui/gtkglext-gtk3/gtk/gtkglversion.h b/plugins/gtkui/gtkglext-gtk3/gtk/gtkglversion.h new file mode 100644 index 00000000..2dd74d81 --- /dev/null +++ b/plugins/gtkui/gtkglext-gtk3/gtk/gtkglversion.h @@ -0,0 +1,62 @@ +/* GtkGLExt - OpenGL Extension to GTK+ + * Copyright (C) 2002-2004 Naofumi Yasufuku + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +#if !defined (__GTKGL_H_INSIDE__) && !defined (GTK_GL_COMPILATION) +#error "Only <gtk/gtkgl.h> can be included directly." +#endif + +#ifndef __GTK_GL_VERSION_H__ +#define __GTK_GL_VERSION_H__ + +#include <glib.h> + +#include <gtk/gtkgldefs.h> + +G_BEGIN_DECLS + +/* + * Compile time version. + */ +#define GTKGLEXT_MAJOR_VERSION (2) +#define GTKGLEXT_MINOR_VERSION (99) +#define GTKGLEXT_MICRO_VERSION (0) +#define GTKGLEXT_INTERFACE_AGE (0) +#define GTKGLEXT_BINARY_AGE (9900) + +/* + * Check whether a GtkGLExt version equal to or greater than + * major.minor.micro is present. + */ +#define GTKGLEXT_CHECK_VERSION(major, minor, micro) \ + (GTKGLEXT_MAJOR_VERSION > (major) || \ + (GTKGLEXT_MAJOR_VERSION == (major) && GTKGLEXT_MINOR_VERSION > (minor)) || \ + (GTKGLEXT_MAJOR_VERSION == (major) && GTKGLEXT_MINOR_VERSION == (minor) && \ + GTKGLEXT_MICRO_VERSION >= (micro))) + +/* + * Library version. + */ +GTK_GL_VAR const guint gtkglext_major_version; +GTK_GL_VAR const guint gtkglext_minor_version; +GTK_GL_VAR const guint gtkglext_micro_version; +GTK_GL_VAR const guint gtkglext_interface_age; +GTK_GL_VAR const guint gtkglext_binary_age; + +G_END_DECLS + +#endif /* __GTK_GL_VERSION_H__ */ diff --git a/plugins/gtkui/gtkglext-gtk3/gtk/gtkglwidget.c b/plugins/gtkui/gtkglext-gtk3/gtk/gtkglwidget.c new file mode 100644 index 00000000..4bb372bb --- /dev/null +++ b/plugins/gtkui/gtkglext-gtk3/gtk/gtkglwidget.c @@ -0,0 +1,550 @@ +/* GtkGLExt - OpenGL Extension to GTK+ + * Copyright (C) 2002-2004 Naofumi Yasufuku + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif /* HAVE_CONFIG_H */ + +#include "gtkglprivate.h" +#include "gtkglwidget.h" + +#include <GL/gl.h> + +typedef struct +{ + GdkGLConfig *glconfig; + GdkGLContext *share_list; + gboolean direct; + int render_type; + + GdkGLContext *glcontext; + + gulong unrealize_handler; + + guint is_realized : 1; + +} GLWidgetPrivate; + +static const gchar quark_gl_private_string[] = "gtk-gl-widget-private"; +static GQuark quark_gl_private = 0; + +gboolean _gtk_gl_widget_install_toplevel_visual = FALSE; + +static void gtk_gl_widget_realize (GtkWidget *widget, + GLWidgetPrivate *private); +static gboolean gtk_gl_widget_configure_event (GtkWidget *widget, + GdkEventConfigure *event, + GLWidgetPrivate *private); +static void gtk_gl_widget_size_allocate (GtkWidget *widget, + GtkAllocation *allocation, + GLWidgetPrivate *private); +static void gtk_gl_widget_unrealize (GtkWidget *widget, + GLWidgetPrivate *private); +static void gtk_gl_widget_parent_set (GtkWidget *widget, + GObject *old_parent, + GdkVisual *visual); +static void gtk_gl_widget_style_set (GtkWidget *widget, + GtkStyle *previous_style, + gpointer user_data); + +static void gl_widget_private_destroy (GLWidgetPrivate *private); + +/* + * Signal handlers. + */ + +static void +gtk_gl_widget_realize (GtkWidget *widget, + GLWidgetPrivate *private) +{ + GdkWindow *window; + GdkGLWindow *glwindow; + + GTK_GL_NOTE_FUNC_PRIVATE (); + + /* + * Set OpenGL-capability to widget->window, then connect some signal + * handlers. + */ + + window = gtk_widget_get_window (widget); + if (!gdk_window_is_gl_capable (window)) + { + glwindow = gdk_window_set_gl_capability (window, + private->glconfig, + NULL); + if (glwindow == NULL) + { + g_warning ("cannot set OpenGL-capability to widget->window\n"); + return; + } + + /* Connect "unrealize" signal handler. */ + if (private->unrealize_handler == 0) + private->unrealize_handler = g_signal_connect (G_OBJECT (widget), "unrealize", + G_CALLBACK (gtk_gl_widget_unrealize), + private); + } + + private->is_realized = TRUE; +} + +static gboolean +gtk_gl_widget_configure_event (GtkWidget *widget, + GdkEventConfigure *event, + GLWidgetPrivate *private) +{ + GTK_GL_NOTE_FUNC_PRIVATE (); + + if (!private->is_realized) + { + /* Realize if OpenGL-capable window is not realized yet. */ + gtk_gl_widget_realize (widget, private); + } + + return FALSE; +} + +static void +gtk_gl_widget_size_allocate (GtkWidget *widget, + GtkAllocation *allocation, + GLWidgetPrivate *private) +{ + GdkGLDrawable *gldrawable; + + GTK_GL_NOTE_FUNC_PRIVATE (); + + /* + * Synchronize OpenGL and window resizing request streams. + */ + + if (gtk_widget_get_realized (widget) && private->is_realized) + { + gldrawable = gdk_window_get_gl_drawable (gtk_widget_get_window (widget)); + gdk_gl_drawable_wait_gdk (gldrawable); + } +} + +static void +gtk_gl_widget_unrealize (GtkWidget *widget, + GLWidgetPrivate *private) +{ + GTK_GL_NOTE_FUNC_PRIVATE (); + + /* + * Destroy OpenGL rendering context. + */ + + if (private->glcontext != NULL) + { + g_object_unref (private->glcontext); + private->glcontext = NULL; + } + + /* + * Remove OpenGL-capability from widget->window. + */ + + if (gtk_widget_get_realized (widget)) + gdk_window_unset_gl_capability (gtk_widget_get_window (widget)); + + private->is_realized = FALSE; +} + +static void +gtk_gl_widget_parent_set (GtkWidget *widget, + GObject *old_parent, + GdkVisual *visual) +{ + GtkWidget *toplevel; + + GTK_GL_NOTE_FUNC_PRIVATE (); + + /* + * Try to install visual to the top-level window. + */ + + toplevel = gtk_widget_get_toplevel (widget); + if (gtk_widget_is_toplevel (toplevel) && !gtk_widget_get_realized (toplevel)) + { + GTK_GL_NOTE (MISC, + g_message (" - Install visual to the top-level window.")); + + gtk_widget_set_visual (toplevel, visual); + } +} + +static void +gtk_gl_widget_style_set (GtkWidget *widget, + GtkStyle *previous_style, + gpointer user_data) +{ + GdkWindow *window; + + GTK_GL_NOTE_FUNC_PRIVATE (); + + /* + * Set a background of "None" on window to avoid AIX X server crash. + */ + + if (gtk_widget_get_realized (widget)) + { + window = gtk_widget_get_window (widget); + + GTK_GL_NOTE (MISC, + g_message (" - window->bg_pixmap = %p", + (void*)gdk_window_get_background_pattern(window))); + + gdk_window_set_background_pattern (window, NULL); + + GTK_GL_NOTE (MISC, + g_message (" - window->bg_pixmap = %p", + (void*)gdk_window_get_background_pattern(window))); + } +} + +static void +gl_widget_private_destroy (GLWidgetPrivate *private) +{ + GTK_GL_NOTE_FUNC_PRIVATE (); + + g_object_unref (G_OBJECT (private->glconfig)); + + if (private->share_list != NULL) + g_object_unref (G_OBJECT (private->share_list)); + + g_free (private); +} + +/** + * gtk_widget_set_gl_capability: + * @widget: the #GtkWidget to be used as the rendering area. + * @glconfig: a #GdkGLConfig. + * @share_list: (allow-none): the #GdkGLContext with which to share display lists and texture + * objects. NULL indicates that no sharing is to take place. + * @direct: whether rendering is to be done with a direct connection to + * the graphics system. + * @render_type: GDK_GL_RGBA_TYPE. + * + * Set the OpenGL-capability to the @widget. + * This function prepares the widget for its use with OpenGL. + * + * Return value: TRUE if it is successful, FALSE otherwise. + **/ +gboolean +gtk_widget_set_gl_capability (GtkWidget *widget, + GdkGLConfig *glconfig, + GdkGLContext *share_list, + gboolean direct, + int render_type) +{ + GdkVisual *visual; + GLWidgetPrivate *private; + + GTK_GL_NOTE_FUNC (); + + g_return_val_if_fail (GTK_IS_WIDGET (widget), FALSE); + g_return_val_if_fail (gtk_widget_get_has_window (widget), FALSE); + g_return_val_if_fail (!gtk_widget_get_realized (widget), FALSE); + g_return_val_if_fail (GDK_IS_GL_CONFIG (glconfig), FALSE); + + /* + * Init quark. + */ + + if (quark_gl_private == 0) + quark_gl_private = g_quark_from_static_string (quark_gl_private_string); + + /* + * Already OpenGL-capable? + */ + + if (gtk_widget_is_gl_capable (widget)) + return TRUE; + + /* + * Set OpenGL-capable colormap. + */ + + visual = gdk_gl_config_get_visual (glconfig); + + gtk_widget_set_visual (widget, visual); + + /* Install visual to the top-level window. */ + if (_gtk_gl_widget_install_toplevel_visual) + { + /* + * If window manager doesn't watch the WM_COLORMAP_WINDOWS property on + * the top-level window, we have to set OpenGL window's colormap to the + * top-level window, especially in color index mode (color index mode + * uses own private colormap). This is achieved by setting the window's + * visual. + */ + + /* Signal handler to set colormap to the top-level window. */ + g_signal_connect (G_OBJECT (widget), "parent_set", + G_CALLBACK (gtk_gl_widget_parent_set), + visual); + + /* If given widget has the top-level window, visual is set here. */ + gtk_gl_widget_parent_set (widget, NULL, visual); + } + + /* + * Disable backing store feature of the widget. + */ + + gtk_widget_set_double_buffered (widget, FALSE); + + /* + * "style_set" signal handler to set a background of "None" on window. + * (relates AIX X server crash) + */ + + g_signal_connect_after (G_OBJECT (widget), "style_set", + G_CALLBACK (gtk_gl_widget_style_set), + NULL); + + /* + * Set GL widget's private data. + */ + + private = g_new (GLWidgetPrivate, 1); + + private->glconfig = glconfig; + g_object_ref (G_OBJECT (private->glconfig)); + + if (share_list != NULL && GDK_IS_GL_CONTEXT (share_list)) + { + private->share_list = share_list; + g_object_ref (G_OBJECT (private->share_list)); + } + else + { + private->share_list = NULL; + } + + private->direct = direct; + private->render_type = render_type; + + private->glcontext = NULL; + + private->unrealize_handler = 0; + + private->is_realized = FALSE; + + g_object_set_qdata_full (G_OBJECT (widget), quark_gl_private, private, + (GDestroyNotify) gl_widget_private_destroy); + + /* + * Connect signal handlers to realize OpenGL-capable widget. + */ + + g_signal_connect (G_OBJECT (widget), "realize", + G_CALLBACK (gtk_gl_widget_realize), + private); + + /* gtk_drawing_area sends configure_event when it is realized. */ + g_signal_connect (G_OBJECT (widget), "configure_event", + G_CALLBACK (gtk_gl_widget_configure_event), + private); + + /* + * Connect "size_allocate" signal handler to synchronize OpenGL and + * window resizing request streams. + */ + + g_signal_connect (G_OBJECT (widget), "size_allocate", + G_CALLBACK (gtk_gl_widget_size_allocate), + private); + + return TRUE; +} + +/** + * gtk_widget_is_gl_capable: + * @widget: a #GtkWidget. + * + * Returns whether the @widget is OpenGL-capable. + * + * Return value: TRUE if the @widget is OpenGL-capable, FALSE otherwise. + **/ +gboolean +gtk_widget_is_gl_capable (GtkWidget *widget) +{ + g_return_val_if_fail (GTK_IS_WIDGET (widget), FALSE); + + return (g_object_get_qdata (G_OBJECT (widget), quark_gl_private) != NULL); +} + +/** + * gtk_widget_get_gl_config: + * @widget: a #GtkWidget. + * + * Returns the #GdkGLConfig referred by the @widget. + * + * Return value: the #GdkGLConfig. + **/ +GdkGLConfig * +gtk_widget_get_gl_config (GtkWidget *widget) +{ + GLWidgetPrivate *private; + + g_return_val_if_fail (GTK_IS_WIDGET (widget), NULL); + + private = g_object_get_qdata (G_OBJECT (widget), quark_gl_private); + if (private == NULL) + return NULL; + + return private->glconfig; +} + +/** + * gtk_widget_create_gl_context: + * @widget: a #GtkWidget. + * @share_list: (allow-none): the #GdkGLContext with which to share display lists and texture + * objects. NULL indicates that no sharing is to take place. + * @direct: whether rendering is to be done with a direct connection to + * the graphics system. + * @render_type: GDK_GL_RGBA_TYPE. + * + * Creates a new #GdkGLContext with the appropriate #GdkGLDrawable + * for this widget. The GL context must be freed when you're + * finished with it. See also gtk_widget_get_gl_context(). + * + * Return value: the new #GdkGLContext. + **/ +GdkGLContext * +gtk_widget_create_gl_context (GtkWidget *widget, + GdkGLContext *share_list, + gboolean direct, + int render_type) +{ + GdkGLDrawable *gldrawable; + GdkGLContext *glcontext; + + GTK_GL_NOTE_FUNC (); + + g_return_val_if_fail (GTK_IS_WIDGET (widget), NULL); + g_return_val_if_fail (gtk_widget_get_realized (widget), NULL); + + gldrawable = gdk_window_get_gl_drawable (gtk_widget_get_window (widget)); + if (gldrawable == NULL) + return NULL; + + /* + * Create OpenGL rendering context. + */ + + glcontext = gdk_gl_context_new (gldrawable, + share_list, + direct, + render_type); + if (glcontext == NULL) + { + g_warning ("cannot create GdkGLContext\n"); + return NULL; + } + + return glcontext; +} + +/** + * gtk_widget_get_gl_context: + * @widget: a #GtkWidget. + * + * Returns the #GdkGLContext with the appropriate #GdkGLDrawable + * for this widget. Unlike the GL context returned by + * gtk_widget_create_gl_context(), this context is owned by the widget. + * + * #GdkGLContext is needed for the function gdk_gl_drawable_begin, + * or for sharing display lists (see gtk_widget_set_gl_capability()). + * + * Return value: the #GdkGLContext. + **/ +GdkGLContext * +gtk_widget_get_gl_context (GtkWidget *widget) +{ + GLWidgetPrivate *private; + + g_return_val_if_fail (GTK_IS_WIDGET (widget), NULL); + g_return_val_if_fail (gtk_widget_get_realized (widget), NULL); + + private = g_object_get_qdata (G_OBJECT (widget), quark_gl_private); + if (private == NULL) + return NULL; + + if (private->glcontext == NULL) + private->glcontext = gtk_widget_create_gl_context (widget, + private->share_list, + private->direct, + private->render_type); + + return private->glcontext; +} + +/** + * gtk_widget_get_gl_window: + * @widget: a #GtkWidget. + * + * Returns the #GdkGLWindow owned by the @widget. + * + * Return value: the #GdkGLWindow. + **/ +GdkGLWindow * +gtk_widget_get_gl_window (GtkWidget *widget) +{ + g_return_val_if_fail (GTK_IS_WIDGET (widget), NULL); + g_return_val_if_fail (gtk_widget_get_realized (widget), NULL); + + return gdk_window_get_gl_window (gtk_widget_get_window (widget)); +} + +gboolean +gtk_widget_begin_gl(GtkWidget *widget) +{ + GdkGLContext *glcontext; + GdkGLWindow *glwindow; + + g_return_val_if_fail (GTK_IS_WIDGET (widget), FALSE); + + glcontext = gtk_widget_get_gl_context (widget); + glwindow = gtk_widget_get_gl_window (widget); + + return gdk_gl_context_make_current(glcontext, GDK_GL_DRAWABLE (glwindow), GDK_GL_DRAWABLE (glwindow)); +} + +void +gtk_widget_end_gl(GtkWidget *widget, gboolean do_swap) +{ + GdkGLDrawable *gldrawable; + + g_return_if_fail (GTK_IS_WIDGET (widget)); + + gldrawable = GDK_GL_DRAWABLE (gtk_widget_get_gl_window (widget)); + + if (do_swap) + { + if (gdk_gl_drawable_is_double_buffered (gldrawable)) + gdk_gl_drawable_swap_buffers (gldrawable); + else + glFlush (); + } + + gdk_gl_context_release_current(); +} diff --git a/plugins/gtkui/gtkglext-gtk3/gtk/gtkglwidget.h b/plugins/gtkui/gtkglext-gtk3/gtk/gtkglwidget.h new file mode 100644 index 00000000..b23b433d --- /dev/null +++ b/plugins/gtkui/gtkglext-gtk3/gtk/gtkglwidget.h @@ -0,0 +1,61 @@ +/* GtkGLExt - OpenGL Extension to GTK+ + * Copyright (C) 2002-2004 Naofumi Yasufuku + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +#if !defined (__GTKGL_H_INSIDE__) && !defined (GTK_GL_COMPILATION) +#error "Only <gtk/gtkgl.h> can be included directly." +#endif + +#ifndef __GTK_GL_WIDGET_H__ +#define __GTK_GL_WIDGET_H__ + +#include <gdk/gdk.h> +#include <gdk/gdkgl.h> +#include <gtk/gtk.h> + +G_BEGIN_DECLS + +gboolean gtk_widget_set_gl_capability (GtkWidget *widget, + GdkGLConfig *glconfig, + GdkGLContext *share_list, + gboolean direct, + int render_type); + +gboolean gtk_widget_is_gl_capable (GtkWidget *widget); + + +GdkGLConfig *gtk_widget_get_gl_config (GtkWidget *widget); + +GdkGLContext *gtk_widget_create_gl_context (GtkWidget *widget, + GdkGLContext *share_list, + gboolean direct, + int render_type); + +GdkGLContext *gtk_widget_get_gl_context (GtkWidget *widget); + +GdkGLWindow *gtk_widget_get_gl_window (GtkWidget *widget); + +#define gtk_widget_get_gl_drawable(widget) \ + GDK_GL_DRAWABLE (gtk_widget_get_gl_window (widget)) + +gboolean gtk_widget_begin_gl(GtkWidget *widget); + +void gtk_widget_end_gl(GtkWidget *widget, gboolean do_swap); + +G_END_DECLS + +#endif /* __GTK_GL_WIDGET_H__ */ |