Как получить как можно больше информации о контексте OpenGL
Привет мир и спасибо, что нашли время, чтобы прочитать это!
Я пишу программу на GTK2 / 3 + OpenGL, у меня запущены две версии программы:
(а) GTK + 2 + GtkGlext Extention -> отлично работает!(б) GTK + 3 + LibX11 -> работает просто отлично!Все выглядит хорошо, за исключением того, что рендеринг в (а) значительно быстрее, чем рендеринг в (б) ... и я понятия не имею, почему. Вот несколько примеров частей кода, используемых для создания контекста OpenGL:
(А)
// To create the context, and the associated GtkWidget
GdkGLConfig * glconfig = gdk_gl_config_new_by_mode (GDK_GL_MODE_RGBA | GDK_GL_MODE_DEPTH | GDK_GL_MODE_DOUBLE);
GtkWidget * drawing_area = gtk_drawing_area_new ();
gtk_widget_set_gl_capability (drawing_area, glconfig, NULL, TRUE, GDK_GL_RGBA_TYPE);
g_signal_connect (G_OBJECT (drawing_area), "expose-event", G_CALLBACK (on_expose), data);
// And later on to draw using the OpenGL context:
gboolean on_expose (GtkWidget * widg, GdkEvent * event, gpointer data)
{
GdkGLContext * glcontext = gtk_widget_get_gl_context (widg);
GdkGLDrawable * gldrawable = gtk_widget_get_gl_drawable (widg);
if (gdk_gl_drawable_gl_begin (gldrawable, glcontext))
{
// OpenGL instructions to draw here !
gdk_gl_drawable_swap_buffers (view -> gldrawable);
gdk_gl_drawable_gl_end (view -> gldrawable);
}
return TRUE;
}
(Б)
// To create the GtkWidget
GtkWidget * drawing_area = gtk_drawing_area_new ();
// Next line is required to avoid background flickering
gtk_widget_set_double_buffered (drawing_area, FALSE);
g_signal_connect (G_OBJECT (drawing_area), "realize", G_CALLBACK(on_realize), data);
g_signal_connect (G_OBJECT (drawing_area), "draw", G_CALLBACK(on_expose), data);
// To create the OpenGL context
GLXContext glcontext;
G_MODULE_EXPORT void on_realize (GtkWidget * widg, gpointer data)
{
GdkWindow * xwin = gtk_widget_get_window (widg);
GLint attr_list[] = {GLX_DOUBLEBUFFER,
GLX_RGBA,
GLX_DEPTH_SIZE, 16,
GLX_RED_SIZE, 8,
GLX_GREEN_SIZE, 8,
GLX_BLUE_SIZE, 8,
None};
XVisualInfo * visualinfo = glXChooseVisual (GDK_WINDOW_XDISPLAY (xwin), gdk_screen_get_number (gdk_window_get_screen (xwin)), attr_list);
glcontext = glXCreateContext (GDK_WINDOW_XDISPLAY (xwin), visualinfo, NULL, TRUE);
xfree (visualinfo);
}
// To Draw using the OpenGL context
G_MODULE_EXPORT gboolean on_expose (GtkWidget * widg, cairo_t * cr, gpointer data)
{
GdkWindow * win = gtk_widget_get_window (widg);
if (glXMakeCurrent (GDK_WINDOW_XDISPLAY (xwin), GDK_WINDOW_XID (xwin), glcontext))
{
// OpenGL instructions to draw here !
glXSwapBuffers (GDK_WINDOW_XDISPLAY (win), GDK_WINDOW_XID (win));
}
return TRUE;
}
Пытаясь понять, почему (а) было быстрее, чем (б), я скачал исходники библиотеки GtkGLext, прочитал их и обнаружил, что команды были точно такими же, как и при вызове X11. Теперь мои мысли либо следующие строки в (б)
gtk_widget_set_double_buffered (drawing_area, FALSE);
Возиться с рендерингом, и тогда я ничего не могу сделать ... или есть (-ы) разница (-ы) между контекстами OpenGL, которые могут объяснить поведение, которое я заметил, если я продолжу в этом направлении, мне нужно сравнить оба контекстов с максимально возможной детализацией ... пока что я выбрал наиболее привычный способ получения информации:
OpenGL Version : 3.0 Mesa 12.0.3
OpenGL Vendor : nouveau
OpenGL Renderer : Gallium 0.4 on NVCF
OpenGL Shading Version : 1.30
Color Bits (R,G,B,A) : 8, 8, 8, 0
Depth Bits : 24
Stencil Bits : 0
Max. Lights Allowed : 8
Max. Texture Size : 16384
Max. Clipping Planes : 8
Max. Modelview Matrix Stacks : 32
Max. Projection Matrix Stacks : 32
Max. Attribute Stacks : 16
Max. Texture Stacks : 10
Total number of OpenGL Extensions : 227
Extensions list:
N°1 : GL_AMD_conservative_depth
N°2 : GL_AMD_draw_buffers_blend
...
Но оба контекста возвращают одну и ту же информацию ...
Спасибо за то, что вы уже там ... теперь мой вопрос:
Есть ли способ вывести как можно больше информации о контексте OpenGL и как?
Я приветствую любые другие предложения о том, что я делаю!
С.
PS: я работаю над использованием GtkGLArea Widget для GTK3, но, как указаноВот Я еще не там.
[EDIT] Некоторые инструкции OpenGL:
// OpenGL instructions to draw here !
glLoadIdentity ();
glPushMatrix ();
// d is the depth ... calculated somewhere else
glTranslated (0.0, 0.0, -d);
// Skipping the rotation part for clarity, I am using a quaternion
rotate_camera ();
// r, g, b and a are GLFloat values
glClearColor (r,g,b,a);
glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
glDisable (GL_LIGHTING);
int i;
// nbds is the number of chemical bonds
GLfloat * lineVertices;
// This is "roughly" what I do to draw chemical bonds, to give you an idea
for (i=0; i<nbds;i++)
{
// get_bonds (i) gives backs a 6 float array
lineVertices = get_bonds(i);
glPushMatrix();
glLineWidth (1.0);
glEnableClientState (GL_VERTEX_ARRAY);
glVertexPointer (3, GL_FLOAT, 0, lineVertices);
glDrawArrays (GL_LINES, 0, 2);
glDisableClientState (GL_VERTEX_ARRAY);
glPopMatrix();
}
glEnable (GL_LIGHTING);
[/РЕДАКТИРОВАТЬ]