summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--FL/Fl_Gl_Window.H20
-rw-r--r--FL/glut.H8
-rw-r--r--Makefile7
-rw-r--r--documentation/Fl_Gl_Window.html17
-rw-r--r--src/Fl_Gl_Choice.H76
-rw-r--r--src/Fl_Gl_Choice.cxx68
-rw-r--r--src/Fl_Gl_Overlay.cxx157
-rw-r--r--src/Fl_Gl_Window.cxx117
-rw-r--r--src/Fl_compose.cxx6
-rw-r--r--src/fl_file_chooser.cxx6
-rw-r--r--src/gl_draw.cxx16
-rw-r--r--src/gl_start.cxx33
-rw-r--r--test/cube.cxx14
13 files changed, 293 insertions, 252 deletions
diff --git a/FL/Fl_Gl_Window.H b/FL/Fl_Gl_Window.H
index 0951f3a10..8a7a0af74 100644
--- a/FL/Fl_Gl_Window.H
+++ b/FL/Fl_Gl_Window.H
@@ -1,5 +1,5 @@
//
-// "$Id: Fl_Gl_Window.H,v 1.7.2.3 2001/01/22 15:13:37 easysw Exp $"
+// "$Id: Fl_Gl_Window.H,v 1.7.2.4 2001/03/14 17:20:01 spitzak Exp $"
//
// OpenGL header file for the Fast Light Tool Kit (FLTK).
//
@@ -27,6 +27,10 @@
#include "Fl_Window.H"
+#ifndef GLContext
+typedef void* GLContext; // actually a GLXContext or HGLDC
+#endif
+
class Fl_Gl_Choice; // structure to hold result of glXChooseVisual
class Fl_Gl_Window : public Fl_Window {
@@ -34,7 +38,7 @@ class Fl_Gl_Window : public Fl_Window {
int mode_;
const int *alist;
Fl_Gl_Choice *g;
- void * context; // actually a GLXContext
+ GLContext context_;
char valid_;
char damage1_; // damage() of back buffer
virtual FL_EXPORT void draw_overlay();
@@ -66,14 +70,16 @@ public:
int mode(int a) {return mode(a,0);}
int mode(const int *a) {return mode(0, a);}
+ void* context() const {return context_;}
+ FL_EXPORT void context(void*, int destroy_flag = false);
+ FL_EXPORT void make_current();
+ FL_EXPORT void swap_buffers();
+ FL_EXPORT void ortho();
+
FL_EXPORT int can_do_overlay();
FL_EXPORT void redraw_overlay();
FL_EXPORT void hide_overlay();
-
- FL_EXPORT void make_current();
FL_EXPORT void make_overlay_current();
- FL_EXPORT void swap_buffers();
- FL_EXPORT void ortho();
FL_EXPORT ~Fl_Gl_Window();
Fl_Gl_Window(int W, int H, const char *l=0) : Fl_Window(W,H,l) {init();}
@@ -84,5 +90,5 @@ public:
#endif
//
-// End of "$Id: Fl_Gl_Window.H,v 1.7.2.3 2001/01/22 15:13:37 easysw Exp $".
+// End of "$Id: Fl_Gl_Window.H,v 1.7.2.4 2001/03/14 17:20:01 spitzak Exp $".
//
diff --git a/FL/glut.H b/FL/glut.H
index 8f8b2b446..193e6f498 100644
--- a/FL/glut.H
+++ b/FL/glut.H
@@ -1,5 +1,5 @@
//
-// "$Id: glut.H,v 1.6.2.9 2001/01/22 15:13:38 easysw Exp $"
+// "$Id: glut.H,v 1.6.2.10 2001/03/14 17:20:01 spitzak Exp $"
//
// GLUT emulation header file for the Fast Light Tool Kit (FLTK).
//
@@ -45,7 +45,7 @@
#define __glut_h__
#include <FL/gl.h>
-#include <GL/glu.h>
+//#include <GL/glu.h>
////////////////////////////////////////////////////////////////
// Glut is emulated using this window class and these static variables
@@ -431,7 +431,7 @@ extern "C" {
extern int APIENTRY glutExtensionSupported(char *name);
/* Stroke font constants (use these in GLUT program). */
-#if defined(_WIN32) || defined(WIN32)
+#ifdef WIN32
# define GLUT_STROKE_ROMAN ((void*)0)
# define GLUT_STROKE_MONO_ROMAN ((void*)1)
#else
@@ -470,5 +470,5 @@ extern void APIENTRY glutSolidIcosahedron();
#endif /* __glut_h__ */
//
-// End of "$Id: glut.H,v 1.6.2.9 2001/01/22 15:13:38 easysw Exp $".
+// End of "$Id: glut.H,v 1.6.2.10 2001/03/14 17:20:01 spitzak Exp $".
//
diff --git a/Makefile b/Makefile
index 27c9491b3..3dd595203 100644
--- a/Makefile
+++ b/Makefile
@@ -1,5 +1,5 @@
#
-# "$Id: Makefile,v 1.12.2.5 2001/01/22 15:13:37 easysw Exp $"
+# "$Id: Makefile,v 1.12.2.6 2001/03/14 17:20:01 spitzak Exp $"
#
# Top-level makefile for the Fast Light Tool Kit (FLTK).
#
@@ -68,6 +68,9 @@ distclean: clean
makeinclude: configure configh.in makeinclude.in
./configure
+configure: configure.in
+ autoconf
+
#
-# End of "$Id: Makefile,v 1.12.2.5 2001/01/22 15:13:37 easysw Exp $".
+# End of "$Id: Makefile,v 1.12.2.6 2001/03/14 17:20:01 spitzak Exp $".
#
diff --git a/documentation/Fl_Gl_Window.html b/documentation/Fl_Gl_Window.html
index 6e5ad96be..079fc5eec 100644
--- a/documentation/Fl_Gl_Window.html
+++ b/documentation/Fl_Gl_Window.html
@@ -41,6 +41,7 @@ very well for single-buffered. </P>
</UL>
</TD><TD align=left valign=top>
<UL>
+<LI><A href=#Fl_Gl_Window.context>context</A></LI>
<LI><A href=#Fl_Gl_Window.draw>draw</A></LI>
<LI><A href=#Fl_Gl_Window.draw_overlay>draw_overlay</A></LI>
<LI><A href=#Fl_Gl_Window.handle>handle</A></LI>
@@ -120,6 +121,22 @@ window a child of another window if you wish to do this! </P>
<BR> int Fl_Gl_Window::can_do() const</A></H4>
Returns non-zero if the hardware supports the given or current OpenGL
mode.
+
+<h4><a name=Fl_Gl_Window.context>void* Fl_Gl_Window::context() const;
+<br>void Fl_Gl_Window::context(void*, int destroy_flag = false);</a></h4>
+
+Return or set a pointer to the GLContext that this window is
+using. This is a system-dependent structure, but it is portable to copy
+the context from one window to another. You can also set it to NULL,
+which will force FLTK to recreate the context the next time <a
+href=#make_current><tt>make_current()</tt></a> is called, this is
+useful for getting around bugs in OpenGL implementations.
+
+<p>If <i>destroy_flag</i> is true the context will be destroyed by
+fltk when the window is destroyed, or when the <a
+href=#mode><tt>mode()</tt></a> is changed, or the next time
+<tt>context(x)</tt> is called.
+
<H4><A name=Fl_Gl_Window.valid>char Fl_Gl_Window::valid() const
<BR> void Fl_Gl_Window::valid(char i)</A></H4>
<TT>Fl_Gl_Window::valid()</TT> is turned off when FLTK creates a new
diff --git a/src/Fl_Gl_Choice.H b/src/Fl_Gl_Choice.H
index 986ee5d65..2fd10c967 100644
--- a/src/Fl_Gl_Choice.H
+++ b/src/Fl_Gl_Choice.H
@@ -1,5 +1,5 @@
//
-// "$Id: Fl_Gl_Choice.H,v 1.4.2.5 2001/01/22 15:13:39 easysw Exp $"
+// "$Id: Fl_Gl_Choice.H,v 1.4.2.6 2001/03/14 17:20:01 spitzak Exp $"
//
// OpenGL definitions for the Fast Light Tool Kit (FLTK).
//
@@ -20,42 +20,49 @@
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
// USA.
//
-// Please report all bugs and problems to "fltk-bugs@fltk.org".
+// Please report all bugs and problems to "fltk-bugs@easysw.com".
//
// Internal interface to set up OpenGL.
//
-// A "Fl_Gl_Choice" is used to cache results of calling the
-// OpenGL code for system-specific information needed to
-// implement a "mode".
-// For X this is a visual, and this must be called *before*
-// the X window is created.
-// For win32 this can be delayed to a more convienent time,
-// as it only returns information for modifying a device
-// context.
-// This is used by Fl_Gl_Window, gl_start(), and gl_visual()
+// A "Fl_Gl_Choice" is created from an OpenGL mode and holds information
+// necessary to create a window (on X) and to create an OpenGL "context"
+// (on both X and Win32).
+//
+// fl_create_gl_context takes a window (necessary only on Win32) and an
+// Fl_Gl_Choice and returns a new OpenGL context. All contexts share
+// display lists with each other.
+//
+// On X another fl_create_gl_context is provided to create it for any
+// X visual.
+//
+// fl_set_gl_context makes the given OpenGL context current and makes
+// it draw into the passed window. It tracks the current one context
+// to avoid calling the context switching code when the same context
+// is used, though it is a mystery to me why the GLX/WGL libraries
+// don't do this themselves...
+//
+// fl_no_gl_context clears that cache so the next fl_set_gl_context is
+// guaranteed to work.
+//
+// fl_delete_gl_context destroys the context.
+//
+// This code is used by Fl_Gl_Window, gl_start(), and gl_visual()
#ifndef Fl_Gl_Choice_H
#define Fl_Gl_Choice_H
+// Warning: whatever GLContext is defined to must take exactly the same
+// space in a structure as a void*!!!
#ifdef WIN32
-# include <windows.h>
# include <FL/gl.h>
-# define GLXContext HGLRC
-# define GLX_BUFFER_SIZE 1
-# define GLX_RGBA 2
-# define GLX_GREEN_SIZE 3
-# define GLX_ALPHA_SIZE 4
-# define GLX_ACCUM_GREEN_SIZE 5
-# define GLX_ACCUM_ALPHA_SIZE 6
-# define GLX_DOUBLEBUFFER 7
-# define GLX_DEPTH_SIZE 8
-# define GLX_STENCIL_SIZE 9
+# define GLContext HGLRC
#else
# include <GL/glx.h>
+# define GLContext GLXContext
#endif
-// one of these structures is returned:
+// Describes crap needed to create a GLContext.
class Fl_Gl_Choice {
int mode;
const int *alist;
@@ -68,28 +75,35 @@ public:
XVisualInfo *vis; // the visual to use
Colormap colormap; // a colormap for that visual
#endif
- uchar r,d,o; // rgb mode, double buffered, overlay flags
// Return one of these structures for a given gl mode.
// The second argument is a glX attribute list, and is used if mode is
// zero. This is not supported on Win32:
static Fl_Gl_Choice *find(int mode, const int *);
};
-extern GLXContext fl_first_context; // used to make all contexts share
-extern GLXContext fl_current_context;
-
class Fl_Window;
#ifdef WIN32
-// This must be called before fl_set_gl_context works:
-HDC fl_private_dc(Fl_Window*, int, Fl_Gl_Choice **gp);
+
+GLContext fl_create_gl_context(Fl_Window*, const Fl_Gl_Choice*, int layer=0);
+
+#else
+
+GLContext fl_create_gl_context(XVisualInfo* vis);
+
+static inline
+GLContext fl_create_gl_context(Fl_Window*, const Fl_Gl_Choice* g) {
+ return fl_create_gl_context(g->vis);
+}
+
#endif
-void fl_set_gl_context(Fl_Window*, GLXContext);
+void fl_set_gl_context(Fl_Window*, GLContext);
void fl_no_gl_context();
+void fl_delete_gl_context(GLContext);
#endif
//
-// End of "$Id: Fl_Gl_Choice.H,v 1.4.2.5 2001/01/22 15:13:39 easysw Exp $".
+// End of "$Id: Fl_Gl_Choice.H,v 1.4.2.6 2001/03/14 17:20:01 spitzak Exp $".
//
diff --git a/src/Fl_Gl_Choice.cxx b/src/Fl_Gl_Choice.cxx
index 31285e9c6..420367348 100644
--- a/src/Fl_Gl_Choice.cxx
+++ b/src/Fl_Gl_Choice.cxx
@@ -1,5 +1,5 @@
//
-// "$Id: Fl_Gl_Choice.cxx,v 1.5.2.5 2001/01/22 15:13:39 easysw Exp $"
+// "$Id: Fl_Gl_Choice.cxx,v 1.5.2.6 2001/03/14 17:20:01 spitzak Exp $"
//
// OpenGL visual selection code for the Fast Light Tool Kit (FLTK).
//
@@ -20,7 +20,7 @@
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
// USA.
//
-// Please report all bugs and problems to "fltk-bugs@fltk.org".
+// Please report all bugs and problems to "fltk-bugs@easysw.com".
//
#include <config.h>
@@ -32,7 +32,6 @@
#include "Fl_Gl_Choice.H"
static Fl_Gl_Choice *first;
-GLXContext fl_first_context;
// this assummes one of the two arguments is zero:
// We keep the list system in Win32 to stay compatible and interpret
@@ -143,16 +142,8 @@ Fl_Gl_Choice *Fl_Gl_Choice::find(int mode, const int *alist) {
#ifdef WIN32
g->pixelformat = pixelformat;
g->pfd = chosen_pfd;
- g->d = ((mode&FL_DOUBLE) != 0);
- g->r = (mode & FL_INDEX);
- g->o = 0; // not an overlay
#else
g->vis = vis;
- g->colormap = 0;
- int i;
- glXGetConfig(fl_display, vis, GLX_DOUBLEBUFFER, &i); g->d = i;
- glXGetConfig(fl_display, vis, GLX_RGBA, &i); g->r = i;
- glXGetConfig(fl_display, vis, GLX_LEVEL, &i); g->o = i;
if (/*MaxCmapsOfScreen(ScreenOfDisplay(fl_display,fl_screen))==1 && */
vis->visualid == fl_visual->visualid &&
@@ -166,36 +157,50 @@ Fl_Gl_Choice *Fl_Gl_Choice::find(int mode, const int *alist) {
return g;
}
+static GLContext first_context;
+
#ifdef WIN32
-HDC fl_private_dc(Fl_Window* w, int mode, Fl_Gl_Choice **gp) {
- Fl_X* i = Fl_X::i(w);
- if (!i->private_dc) {
- i->private_dc = GetDCEx(i->xid, 0, DCX_CACHE);
- Fl_Gl_Choice *g = Fl_Gl_Choice::find(mode, 0);
- if (gp) *gp = g;
+GLContext fl_create_gl_context(Fl_Window* window, const Fl_Gl_Choice* g, int layer) {
+ Fl_X* i = Fl_X::i(window);
+ HDC hdc = i->private_dc;
+ if (!hdc) {
+ hdc = i->private_dc = GetDCEx(i->xid, 0, DCX_CACHE);
SetPixelFormat(i->private_dc, g->pixelformat, &g->pfd);
#if USE_COLORMAP
if (fl_palette) SelectPalette(i->private_dc, fl_palette, FALSE);
#endif
}
- return i->private_dc;
+ GLContext context =
+ layer ? wglCreateLayerContext(hdc, layer) : wglCreateContext(hdc);
+ if (context) {
+ if (first_context) wglShareLists(first_context, context);
+ else first_context = context;
+ }
+ return context;
}
-#endif
+#else
-static GLXContext cached_context;
+GLContext fl_create_gl_context(XVisualInfo* vis) {
+ GLContext context = glXCreateContext(fl_display, vis, first_context, 1);
+ if (!first_context) first_context = context;
+ return context;
+}
+
+#endif
+static GLContext cached_context;
static Fl_Window* cached_window;
-void fl_set_gl_context(Fl_Window* w, GLXContext c) {
- if (c != cached_context || w != cached_window) {
- cached_context = c;
+void fl_set_gl_context(Fl_Window* w, GLContext context) {
+ if (context != cached_context || w != cached_window) {
+ cached_context = context;
cached_window = w;
#ifdef WIN32
- wglMakeCurrent(Fl_X::i(w)->private_dc, c);
+ wglMakeCurrent(Fl_X::i(w)->private_dc, context);
#else
- glXMakeCurrent(fl_display, fl_xid(w), c);
+ glXMakeCurrent(fl_display, fl_xid(w), context);
#endif
}
}
@@ -210,8 +215,19 @@ void fl_no_gl_context() {
#endif
}
+void fl_delete_gl_context(GLContext context) {
+ if (cached_context == context) fl_no_gl_context();
+ if (context != first_context) {
+#ifdef WIN32
+ wglDeleteContext(context);
+#else
+ glXDestroyContext(fl_display, context);
+#endif
+ }
+}
+
#endif
//
-// End of "$Id: Fl_Gl_Choice.cxx,v 1.5.2.5 2001/01/22 15:13:39 easysw Exp $".
+// End of "$Id: Fl_Gl_Choice.cxx,v 1.5.2.6 2001/03/14 17:20:01 spitzak Exp $".
//
diff --git a/src/Fl_Gl_Overlay.cxx b/src/Fl_Gl_Overlay.cxx
index fd040abb0..1272c11a2 100644
--- a/src/Fl_Gl_Overlay.cxx
+++ b/src/Fl_Gl_Overlay.cxx
@@ -1,5 +1,5 @@
//
-// "$Id: Fl_Gl_Overlay.cxx,v 1.5.2.14 2001/01/22 15:13:39 easysw Exp $"
+// "$Id: Fl_Gl_Overlay.cxx,v 1.5.2.15 2001/03/14 17:20:01 spitzak Exp $"
//
// OpenGL overlay code for the Fast Light Tool Kit (FLTK).
//
@@ -20,21 +20,25 @@
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
// USA.
//
-// Please report all bugs and problems to "fltk-bugs@fltk.org".
+// Please report all bugs and problems to "fltk-bugs@easysw.com".
//
#include <config.h>
#if HAVE_GL
#include <FL/Fl.H>
-#include <FL/Fl_Gl_Window.H>
#include <FL/x.H>
#include "Fl_Gl_Choice.H"
+#include <FL/Fl_Gl_Window.H>
#include <stdlib.h>
-#if HAVE_GL_OVERLAY
+#if !HAVE_GL_OVERLAY
+
+int Fl_Gl_Window::can_do_overlay() {return 0;}
+
+void Fl_Gl_Window::make_overlay() {overlay = this;}
-#if !defined(_WIN32) && !defined(WIN32)
+#else
// Methods on Fl_Gl_Window that create an overlay window. Because
// many programs don't need the overlay, this is seperated into this
@@ -51,11 +55,14 @@
// "faked" by drawing into the main layers. This is indicated by
// setting overlay == this.
+#ifndef WIN32
+////////////////////////////////////////////////////////////////
+// X version
+
extern XVisualInfo *fl_find_overlay_visual();
extern XVisualInfo *fl_overlay_visual;
extern Colormap fl_overlay_colormap;
extern unsigned long fl_transparent_pixel;
-static Fl_Gl_Choice overlay_choice;
extern uchar fl_overlay;
class _Fl_Gl_Overlay : public Fl_Gl_Window {
@@ -65,12 +72,6 @@ public:
_Fl_Gl_Overlay(int x, int y, int w, int h) :
Fl_Gl_Window(x,y,w,h) {
set_flag(INACTIVE);
- overlay_choice.vis = fl_overlay_visual;
- overlay_choice.colormap = fl_overlay_colormap;
- overlay_choice.r = 0;
- overlay_choice.d = 0;
- overlay_choice.o = 1;
- g = &overlay_choice;
}
};
@@ -88,91 +89,87 @@ void _Fl_Gl_Overlay::draw() {
}
void _Fl_Gl_Overlay::show() {
- if (shown()) {Fl_Gl_Window::show(); return;}
- fl_background_pixel = int(fl_transparent_pixel);
+ if (!shown()) {
+ fl_background_pixel = int(fl_transparent_pixel);
+ Fl_X::make_xid(this, fl_overlay_visual, fl_overlay_colormap);
+ fl_background_pixel = -1;
+ // find the outermost window to tell wm about the colormap:
+ Fl_Window *w = window();
+ for (;;) {Fl_Window *w1 = w->window(); if (!w1) break; w = w1;}
+ XSetWMColormapWindows(fl_display, fl_xid(w), &(Fl_X::i(this)->xid), 1);
+ context(fl_create_gl_context(fl_overlay_visual), 1);
+ valid(0);
+ }
Fl_Gl_Window::show();
- fl_background_pixel = -1;
- // find the outermost window to tell wm about the colormap:
- Fl_Window *w = window();
- for (;;) {Fl_Window *w1 = w->window(); if (!w1) break; w = w1;}
- XSetWMColormapWindows(fl_display, fl_xid(w), &(Fl_X::i(this)->xid), 1);
}
int Fl_Gl_Window::can_do_overlay() {
return fl_find_overlay_visual() != 0;
}
-#else // _WIN32:
-
-int Fl_Gl_Window::can_do_overlay() {
- Fl_Gl_Choice* choice = Fl_Gl_Choice::find(0,0);
- return (choice && (choice->pfd.bReserved & 15));
+void Fl_Gl_Window::make_overlay() {
+ if (overlay) return;
+ if (can_do_overlay()) {
+ _Fl_Gl_Overlay* o = new _Fl_Gl_Overlay(0,0,w(),h());
+ overlay = o;
+ add(*o);
+ o->show();
+ } else {
+ overlay = this; // fake the overlay
+ }
}
-extern int fl_overlay_depth;
-
-#endif
-
#else
+////////////////////////////////////////////////////////////////
+// WIN32 version:
-int Fl_Gl_Window::can_do_overlay() {return 0;}
-
-#endif
+//static COLORREF *palette;
+extern int fl_overlay_depth;
void Fl_Gl_Window::make_overlay() {
- if (!overlay) {
-#if HAVE_GL_OVERLAY
-#if defined(_WIN32) || defined(WIN32)
- HDC hdc = fl_private_dc(this, mode_,&g);
- GLXContext context = wglCreateLayerContext(hdc, 1);
- if (context) { // we found a usable overlay context
- if (fl_first_context) wglShareLists(fl_first_context, context);
- else fl_first_context = context;
- overlay = context;
- LAYERPLANEDESCRIPTOR pfd;
- wglDescribeLayerPlane(hdc, g->pixelformat, 1, sizeof(pfd), &pfd);
- if (!pfd.iPixelType) {
- ; // full-color overlay
- } else {
- fl_overlay_depth = pfd.cColorBits; // used by gl_color()
- if (fl_overlay_depth > 8) fl_overlay_depth = 8;
- COLORREF palette[256];
- int n = (1<<fl_overlay_depth)-1;
- // copy all colors except #0 into the overlay palette:
- for (int i = 0; i <= n; i++) {
- uchar r,g,b; Fl::get_color((Fl_Color)i,r,g,b);
- palette[i] = RGB(r,g,b);
- }
- // always provide black & white in the last 2 pixels:
- if (fl_overlay_depth < 8) {
- palette[n-1] = RGB(0,0,0);
- palette[n] = RGB(255,255,255);
- }
- // and use it:
- wglSetLayerPaletteEntries(hdc, 1, 1, n, palette+1);
- wglRealizeLayerPalette(hdc, 1, TRUE);
- }
- valid(0);
- return;
+ if (overlay) return;
+
+ GLContext context = fl_create_gl_context(this, g, 1);
+ if (!context) {overlay = this; return;} // fake the overlay
+
+ HDC hdc = Fl_X::i(this)->private_dc;
+ overlay = context;
+ LAYERPLANEDESCRIPTOR pfd;
+ wglDescribeLayerPlane(hdc, g->pixelformat, 1, sizeof(pfd), &pfd);
+ if (!pfd.iPixelType) {
+ ; // full-color overlay
+ } else {
+ fl_overlay_depth = pfd.cColorBits; // used by gl_color()
+ if (fl_overlay_depth > 8) fl_overlay_depth = 8;
+ COLORREF palette[256];
+ int n = (1<<fl_overlay_depth)-1;
+ // copy all colors except #0 into the overlay palette:
+ for (int i = 0; i <= n; i++) {
+ uchar r,g,b; Fl::get_color((Fl_Color)i,r,g,b);
+ palette[i] = RGB(r,g,b);
}
-#else
- if (can_do_overlay()) {
- _Fl_Gl_Overlay* o = new _Fl_Gl_Overlay(0,0,w(),h());
- overlay = o;
- add(*o);
- o->show();
- return;
+ // always provide black & white in the last 2 pixels:
+ if (fl_overlay_depth < 8) {
+ palette[n-1] = RGB(0,0,0);
+ palette[n] = RGB(255,255,255);
}
-#endif
-#endif
- overlay = this; // fake the overlay
+ // and use it:
+ wglSetLayerPaletteEntries(hdc, 1, 1, n, palette+1);
+ wglRealizeLayerPalette(hdc, 1, TRUE);
}
+ valid(0);
+ return;
}
+////////////////////////////////////////////////////////////////
+#endif
+
+#endif
+
void Fl_Gl_Window::redraw_overlay() {
if (!shown()) return;
make_overlay();
-#if !defined(_WIN32) && !defined(WIN32)
+#ifndef WIN32
if (overlay != this)
((Fl_Gl_Window*)overlay)->redraw();
else
@@ -184,8 +181,8 @@ void Fl_Gl_Window::make_overlay_current() {
make_overlay();
#if HAVE_GL_OVERLAY
if (overlay != this) {
-#if defined(_WIN32) || defined(WIN32)
- fl_set_gl_context(this, (GLXContext)overlay);
+#ifdef WIN32
+ fl_set_gl_context(this, (GLContext)overlay);
// if (fl_overlay_depth)
// wglRealizeLayerPalette(Fl_X::i(this)->private_dc, 1, TRUE);
#else
@@ -198,7 +195,7 @@ void Fl_Gl_Window::make_overlay_current() {
void Fl_Gl_Window::hide_overlay() {
#if HAVE_GL_OVERLAY
-#if defined(_WIN32) || defined(WIN32)
+#ifdef WIN32
// nothing needs to be done? Or should it be erased?
#else
if (overlay && overlay!=this) ((Fl_Gl_Window*)overlay)->hide();
@@ -209,5 +206,5 @@ void Fl_Gl_Window::hide_overlay() {
#endif
//
-// End of "$Id: Fl_Gl_Overlay.cxx,v 1.5.2.14 2001/01/22 15:13:39 easysw Exp $".
+// End of "$Id: Fl_Gl_Overlay.cxx,v 1.5.2.15 2001/03/14 17:20:01 spitzak Exp $".
//
diff --git a/src/Fl_Gl_Window.cxx b/src/Fl_Gl_Window.cxx
index 87806a54a..70d46ab68 100644
--- a/src/Fl_Gl_Window.cxx
+++ b/src/Fl_Gl_Window.cxx
@@ -1,5 +1,5 @@
//
-// "$Id: Fl_Gl_Window.cxx,v 1.12.2.20 2001/01/22 15:13:39 easysw Exp $"
+// "$Id: Fl_Gl_Window.cxx,v 1.12.2.21 2001/03/14 17:20:01 spitzak Exp $"
//
// OpenGL window code for the Fast Light Tool Kit (FLTK).
//
@@ -28,8 +28,8 @@
#include <FL/Fl.H>
#include <FL/x.H>
-#include <FL/Fl_Gl_Window.H>
#include "Fl_Gl_Choice.H"
+#include <FL/Fl_Gl_Window.H>
#include <stdlib.h>
#include <string.h>
@@ -63,66 +63,65 @@ int Fl_Gl_Window::can_do(int a, const int *b) {
}
void Fl_Gl_Window::show() {
-#if !defined(_WIN32) && !defined(WIN32)
if (!shown()) {
if (!g) {
g = Fl_Gl_Choice::find(mode_,alist);
if (!g) {Fl::error("Insufficient GL support"); return;}
}
+#ifndef WIN32
Fl_X::make_xid(this, g->vis, g->colormap);
if (overlay && overlay != this) ((Fl_Gl_Window*)overlay)->show();
- }
#endif
+ }
Fl_Window::show();
}
void Fl_Gl_Window::invalidate() {
valid(0);
-#if !defined(_WIN32) && !defined(WIN32)
+#ifndef WIN32
if (overlay) ((Fl_Gl_Window*)overlay)->valid(0);
#endif
}
int Fl_Gl_Window::mode(int m, const int *a) {
if (m == mode_ && a == alist) return 0;
+#ifndef WIN32
+ int oldmode = mode_;
+ Fl_Gl_Choice* oldg = g;
+#endif
+ context(0);
mode_ = m; alist = a;
-#if defined(_WIN32) || defined(WIN32)
- // destroy context and g:
- if (shown()) {hide(); show();}
-#else
- // under X, if the visual changes we must make a new X window (!):
if (shown()) {
- Fl_Gl_Choice *g1 = g;
- g = Fl_Gl_Choice::find(mode_,alist);
- if (!g || g->vis->visualid != g1->vis->visualid || g->d != g1->d) {
- hide(); show();
+ g = Fl_Gl_Choice::find(m, a);
+#ifndef WIN32
+ // under X, if the visual changes we must make a new X window (yuck!):
+ if (!g || g->vis->visualid!=oldg->vis->visualid || (oldmode^m)&FL_DOUBLE) {
+ hide();
+ show();
}
- }
#endif
+ } else {
+ g = 0;
+ }
return 1;
}
+#define NON_LOCAL_CONTEXT 0x80000000
+
void Fl_Gl_Window::make_current() {
- if (!context) {
-#if defined(_WIN32) || defined(WIN32)
- context = wglCreateContext(fl_private_dc(this, mode_,&g));
- if (fl_first_context) wglShareLists(fl_first_context, (GLXContext)context);
- else fl_first_context = (GLXContext)context;
-#else
- context = glXCreateContext(fl_display, g->vis, fl_first_context, 1);
- if (!fl_first_context) fl_first_context = (GLXContext)context;
-#endif
+ if (!context_) {
+ mode_ &= ~NON_LOCAL_CONTEXT;
+ context_ = fl_create_gl_context(this, g);
valid(0);
}
- fl_set_gl_context(this, (GLXContext)context);
-#if (defined(_WIN32) || defined(WIN32)) && USE_COLORMAP
+ fl_set_gl_context(this, context_);
+#if defined(WIN32) && USE_COLORMAP
if (fl_palette) {
fl_GetDC(fl_xid(this));
SelectPalette(fl_gc, fl_palette, FALSE);
RealizePalette(fl_gc);
}
#endif // USE_COLORMAP
- if (g->d) glDrawBuffer(GL_BACK);
current_ = this;
}
@@ -142,7 +141,7 @@ void Fl_Gl_Window::ortho() {
}
void Fl_Gl_Window::swap_buffers() {
-#if defined(_WIN32) || defined(WIN32)
+#ifdef WIN32
#if HAVE_GL_OVERLAY
// Do not swap the overlay, to match GLX:
wglSwapLayerBuffers(Fl_X::i(this)->private_dc, WGL_SWAP_MAIN_PLANE);
@@ -154,25 +153,25 @@ void Fl_Gl_Window::swap_buffers() {
#endif
}
-#if HAVE_GL_OVERLAY && defined(_WIN32)
+#if HAVE_GL_OVERLAY && defined(WIN32)
uchar fl_overlay; // changes how fl_color() works
int fl_overlay_depth = 0;
#endif
void Fl_Gl_Window::flush() {
uchar save_valid = valid_;
-#if defined(_WIN32) || defined(WIN32)
+
+#if HAVE_GL_OVERLAY && defined(WIN32)
+
// SGI 320 messes up overlay with user-defined cursors:
bool fixcursor =
Fl_X::i(this)->cursor && Fl_X::i(this)->cursor != fl_default_cursor;
if (fixcursor) SetCursor(0);
-#endif
-#if HAVE_GL_OVERLAY && (defined(_WIN32) || defined(WIN32))
// Draw into hardware overlay planes:
if (overlay && overlay != this
&& (damage()&(FL_DAMAGE_OVERLAY|FL_DAMAGE_EXPOSE) || !save_valid)) {
- fl_set_gl_context(this, (GLXContext)overlay);
+ fl_set_gl_context(this, (GLContext)overlay);
if (fl_overlay_depth)
wglRealizeLayerPalette(Fl_X::i(this)->private_dc, 1, TRUE);
glDisable(GL_SCISSOR_TEST);
@@ -191,7 +190,9 @@ void Fl_Gl_Window::flush() {
make_current();
- if (g->d) {
+ if (mode_ & FL_DOUBLE) {
+
+ glDrawBuffer(GL_BACK);
if (!SWAP_TYPE) {
SWAP_TYPE = UNDEFINED;
@@ -224,16 +225,10 @@ void Fl_Gl_Window::flush() {
if (damage1_ || damage() != FL_DAMAGE_OVERLAY || !save_valid) draw();
// we use a seperate context for the copy because rasterpos must be 0
// and depth test needs to be off:
- static GLXContext ortho_context = 0;
+ static GLContext ortho_context = 0;
static Fl_Gl_Window* ortho_window = 0;
int init = !ortho_context;
- if (init) {
-#if defined(_WIN32) || defined(WIN32)
- ortho_context = wglCreateContext(Fl_X::i(this)->private_dc);
-#else
- ortho_context =glXCreateContext(fl_display,g->vis,fl_first_context,1);
-#endif
- }
+ if (init) ortho_context = fl_create_gl_context(this, g);
fl_set_gl_context(this, ortho_context);
if (init || !save_valid || ortho_window != this) {
glDisable(GL_DEPTH_TEST);
@@ -274,7 +269,7 @@ void Fl_Gl_Window::flush() {
}
-#if defined(_WIN32) || defined(WIN32)
+#if HAVE_GL_OVERLAY && defined(WIN32)
if (fixcursor) SetCursor(Fl_X::i(this)->cursor);
#endif
valid(1);
@@ -283,7 +278,7 @@ void Fl_Gl_Window::flush() {
void Fl_Gl_Window::resize(int X,int Y,int W,int H) {
if (W != w() || H != h()) {
valid(0);
-#if !defined(_WIN32) && !defined(WIN32)
+#ifndef WIN32
if (!resizable() && overlay && overlay != this)
((Fl_Gl_Window*)overlay)->resize(0,0,W,H);
#endif
@@ -291,26 +286,18 @@ void Fl_Gl_Window::resize(int X,int Y,int W,int H) {
Fl_Window::resize(X,Y,W,H);
}
+void Fl_Gl_Window::context(void* v, int destroy_flag) {
+ if (context_ && !(mode_&NON_LOCAL_CONTEXT)) fl_delete_gl_context(context_);
+ context_ = (GLContext)v;
+ if (destroy_flag) mode_ &= ~NON_LOCAL_CONTEXT;
+ else mode_ |= NON_LOCAL_CONTEXT;
+}
+
void Fl_Gl_Window::hide() {
- if (context) {
- fl_no_gl_context();
- if (context != fl_first_context) {
-#if defined(_WIN32) || defined(WIN32)
- wglDeleteContext((GLXContext)context);
-#else
- glXDestroyContext(fl_display, (GLXContext)context);
-#endif
- }
-// This causes incompatibility with some OpenGL libraries
-// I don't think this is not necessary in any case, right?
-//#ifdef GLX_MESA_release_buffers
-// glXReleaseBuffersMESA(fl_display, fl_xid(this));
-//#endif
- context = 0;
- }
-#if HAVE_GL_OVERLAY && (defined(_WIN32) || defined(WIN32))
- if (overlay && overlay != this && (GLXContext)overlay != fl_first_context) {
- wglDeleteContext((GLXContext)overlay);
+ context(0);
+#if HAVE_GL_OVERLAY && defined(WIN32)
+ if (overlay && overlay != this) {
+ fl_delete_gl_context((GLContext)overlay);
overlay = 0;
}
#endif
@@ -327,7 +314,7 @@ void Fl_Gl_Window::init() {
box(FL_NO_BOX);
mode_ = FL_RGB | FL_DEPTH | FL_DOUBLE;
alist = 0;
- context = 0;
+ context_ = 0;
g = 0;
overlay = 0;
}
@@ -337,5 +324,5 @@ void Fl_Gl_Window::draw_overlay() {}
#endif
//
-// End of "$Id: Fl_Gl_Window.cxx,v 1.12.2.20 2001/01/22 15:13:39 easysw Exp $".
+// End of "$Id: Fl_Gl_Window.cxx,v 1.12.2.21 2001/03/14 17:20:01 spitzak Exp $".
//
diff --git a/src/Fl_compose.cxx b/src/Fl_compose.cxx
index 8fa620be5..5b9a9f619 100644
--- a/src/Fl_compose.cxx
+++ b/src/Fl_compose.cxx
@@ -1,5 +1,5 @@
//
-// "$Id: Fl_compose.cxx,v 1.1.2.6 2001/01/22 15:13:40 easysw Exp $"
+// "$Id: Fl_compose.cxx,v 1.1.2.7 2001/03/14 17:20:01 spitzak Exp $"
//
// Character compose processing for the Fast Light Tool Kit (FLTK).
//
@@ -30,7 +30,7 @@ static const char* const compose_pairs =
"`A'A^A~A:A*AAE,C`E'E^E:E`I'I^I:I-D~N`O'O^O~O:Ox O/`U'U^U:U'YTHss"
"`a'a^a~a:a*aae,c`e'e^e:e`i'i^i:i-d~n`o'o^o~o:o-:o/`u'u^u:u'yth:y";
-#if !defined(_WIN32) && !defined(WIN32) // X only
+#ifndef WIN32 // X only
// X dead-key lookup table. This turns a dead-key keysym into the
// first of two characters for one of the compose sequences. These
// keysyms start at 0xFE50.
@@ -113,7 +113,7 @@ int Fl::compose(int& del) {
return 1;
}
-#if !defined(_WIN32) && !defined(WIN32) // X only
+#ifndef WIN32 // X only
// See if they typed a dead key. This gets it into the same state as
// typing prefix+accent:
if (i >= 0xfe50 && i <= 0xfe5b) {
diff --git a/src/fl_file_chooser.cxx b/src/fl_file_chooser.cxx
index 70987668e..1e6b463e3 100644
--- a/src/fl_file_chooser.cxx
+++ b/src/fl_file_chooser.cxx
@@ -1,5 +1,5 @@
//
-// "$Id: fl_file_chooser.cxx,v 1.10.2.8 2001/01/22 15:13:41 easysw Exp $"
+// "$Id: fl_file_chooser.cxx,v 1.10.2.9 2001/03/14 17:20:02 spitzak Exp $"
//
// File chooser widget for the Fast Light Tool Kit (FLTK).
//
@@ -231,7 +231,7 @@ int FCB::get(char* buf) {
for (dirent** r = q+1; n && r < last; r++) {
if (!item_height(*r, 0)) continue;
int i;
-#if defined(_WIN32) || defined(WIN32)
+#ifdef WIN32
for (i=0; i<n && tolower((*q)->d_name[i])==tolower((*r)->d_name[i]); i++) {}
#else
for (i=0; i<n && (*q)->d_name[i]==(*r)->d_name[i]; i++) {}
@@ -632,5 +632,5 @@ char* fl_file_chooser(const char* message, const char* pat, const char* fname)
}
//
-// End of "$Id: fl_file_chooser.cxx,v 1.10.2.8 2001/01/22 15:13:41 easysw Exp $".
+// End of "$Id: fl_file_chooser.cxx,v 1.10.2.9 2001/03/14 17:20:02 spitzak Exp $".
//
diff --git a/src/gl_draw.cxx b/src/gl_draw.cxx
index c24463c5d..2b0348c60 100644
--- a/src/gl_draw.cxx
+++ b/src/gl_draw.cxx
@@ -1,5 +1,5 @@
//
-// "$Id: gl_draw.cxx,v 1.7.2.4 2001/01/22 15:13:41 easysw Exp $"
+// "$Id: gl_draw.cxx,v 1.7.2.5 2001/03/14 17:20:02 spitzak Exp $"
//
// OpenGL drawing support routines for the Fast Light Tool Kit (FLTK).
//
@@ -37,14 +37,14 @@
#include "Fl_Font.H"
#include <string.h>
-void gl_font(int fontid, int size) {fl_font(fontid, size);}
int gl_height() {return fl_height();}
int gl_descent() {return fl_descent();}
double gl_width(const char* s) {return fl_width(s);}
double gl_width(const char* s, int n) {return fl_width(s,n);}
double gl_width(uchar c) {return fl_width(c);}
-void gl_draw(const char* str, int n) {
+void gl_font(int fontid, int size) {
+ fl_font(fontid, size);
if (!fl_fontsize->listbase) {
#ifdef WIN32
int base = fl_fontsize->metr.tmFirstChar;
@@ -60,11 +60,11 @@ void gl_draw(const char* str, int n) {
glXUseXFont(fl_xfont->fid, base, size, fl_fontsize->listbase+base);
#endif
}
+ glListBase(fl_fontsize->listbase);
+}
- glPushAttrib(GL_LIST_BIT);
- glListBase(fl_fontsize->listbase);
- glCallLists(n, GL_UNSIGNED_BYTE, str);
- glPopAttrib();
+void gl_draw(const char* str, int n) {
+ glCallLists(n, GL_UNSIGNED_BYTE, str);
}
void gl_draw(const char* str, int n, int x, int y) {
@@ -155,5 +155,5 @@ void gl_draw_image(const uchar* b, int x, int y, int w, int h, int d, int ld) {
#endif
//
-// End of "$Id: gl_draw.cxx,v 1.7.2.4 2001/01/22 15:13:41 easysw Exp $".
+// End of "$Id: gl_draw.cxx,v 1.7.2.5 2001/03/14 17:20:02 spitzak Exp $".
//
diff --git a/src/gl_start.cxx b/src/gl_start.cxx
index 3438fc464..f0274eaf4 100644
--- a/src/gl_start.cxx
+++ b/src/gl_start.cxx
@@ -1,5 +1,5 @@
//
-// "$Id: gl_start.cxx,v 1.6.2.4 2001/01/22 15:13:41 easysw Exp $"
+// "$Id: gl_start.cxx,v 1.6.2.5 2001/03/14 17:20:02 spitzak Exp $"
//
// OpenGL context routines for the Fast Light Tool Kit (FLTK).
//
@@ -20,7 +20,7 @@
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
// USA.
//
-// Please report all bugs and problems to "fltk-bugs@fltk.org".
+// Please report all bugs and problems to "fltk-bugs@easysw.com".
//
// You MUST use gl_visual() to select the default visual before doing
@@ -42,35 +42,27 @@
#include <FL/Fl_Window.H>
#include <FL/x.H>
#include <FL/fl_draw.H>
-
#include "Fl_Gl_Choice.H"
-extern GLXContext fl_first_context; // in Fl_Gl_Choice.C
extern int fl_clip_state_number; // in fl_rect.C
-static GLXContext context;
+static GLContext context;
static int clip_state_number=-1;
static int pw, ph;
#ifdef WIN32
-static int default_mode;
+static Fl_Gl_Choice* gl_choice;
#endif
Region XRectangleRegion(int x, int y, int w, int h); // in fl_rect.C
void gl_start() {
-#ifdef WIN32
- HDC hdc = fl_private_dc(Fl_Window::current(), default_mode,0);
-#endif
if (!context) {
#ifdef WIN32
- context = wglCreateContext(hdc);
- if (!fl_first_context) fl_first_context = context;
- else wglShareLists(fl_first_context, context);
+ if (!gl_choice) Fl::gl_visual(0);
+ context = fl_create_gl_context(Fl_Window::current(), gl_choice);
#else
- context = glXCreateContext(fl_display, fl_visual, fl_first_context, 1);
- if (!context) Fl::fatal("OpenGL does not support this visual");
- if (!fl_first_context) fl_first_context = context;
+ context = fl_create_gl_context(fl_visual);
#endif
}
fl_set_gl_context(Fl_Window::current(), context);
@@ -100,19 +92,18 @@ void gl_start() {
}
void gl_finish() {
-#ifdef WIN32
glFlush();
-#else
+#ifndef WIN32
glXWaitGL();
#endif
}
int Fl::gl_visual(int mode, int *alist) {
-#ifdef WIN32
- default_mode = mode;
-#else
Fl_Gl_Choice *c = Fl_Gl_Choice::find(mode,alist);
if (!c) return 0;
+#ifdef WIN32
+ gl_choice = c;
+#else
fl_visual = c->vis;
fl_colormap = c->colormap;
#endif
@@ -122,5 +113,5 @@ int Fl::gl_visual(int mode, int *alist) {
#endif
//
-// End of "$Id: gl_start.cxx,v 1.6.2.4 2001/01/22 15:13:41 easysw Exp $".
+// End of "$Id: gl_start.cxx,v 1.6.2.5 2001/03/14 17:20:02 spitzak Exp $".
//
diff --git a/test/cube.cxx b/test/cube.cxx
index 0236b3ba7..58d9d7579 100644
--- a/test/cube.cxx
+++ b/test/cube.cxx
@@ -1,5 +1,5 @@
//
-// "$Id: cube.cxx,v 1.4.2.4 2001/01/22 15:13:41 easysw Exp $"
+// "$Id: cube.cxx,v 1.4.2.5 2001/03/14 17:20:02 spitzak Exp $"
//
// Another forms test program for the Fast Light Tool Kit (FLTK).
//
@@ -152,6 +152,16 @@ int main(int argc, char **argv) {
form->show(argc,argv);
cube->show();
cube2->show();
+#if 0
+ // This demonstrates how to manipulate OpenGL contexts.
+ // In this case the same context is used by multiple windows (I'm not
+ // sure if this is allowed on Win32, can somebody check?).
+ // This fixes a bug on the XFree86 3.0 OpenGL where only one context
+ // per program seems to work, but there are probably better uses for
+ // this!
+ cube->make_current(); // causes context to be created
+ cube2->context(cube->context()); // share the contexts
+#endif
for (;;) {
if (form->visible() && speed->value())
{if (!Fl::check()) break;} // returns immediately
@@ -169,5 +179,5 @@ int main(int argc, char **argv) {
}
//
-// End of "$Id: cube.cxx,v 1.4.2.4 2001/01/22 15:13:41 easysw Exp $".
+// End of "$Id: cube.cxx,v 1.4.2.5 2001/03/14 17:20:02 spitzak Exp $".
//