Browse Source

Changes to support offscreen-buffers that match the main window

Josh Yelon 20 years ago
parent
commit
4bb6fd3f1b

+ 1 - 0
doc/makepanda/makepanda.py

@@ -1893,6 +1893,7 @@ if (SLAVEBUILD==0):
         CopyFile('built/bin/', 'thirdparty/win-python/python24.dll')
         CopyFile('built/bin/', 'thirdparty/win-python/python24.dll')
         if (OMIT.count("PYTHON")==0):
         if (OMIT.count("PYTHON")==0):
             CopyTree('built/python', 'thirdparty/win-python')
             CopyTree('built/python', 'thirdparty/win-python')
+            ConditionalWriteFile('built/python/panda.pth',"..\n../bin\n")
 
 
 ########################################################################
 ########################################################################
 ##
 ##

+ 1 - 1
doc/makepanda/makepanda71.vcproj

@@ -18,7 +18,7 @@
 			<Tool
 			<Tool
 				Name="VCNMakeTool"
 				Name="VCNMakeTool"
 				BuildCommandLine="cd .. &amp; makepanda\makepanda --everything"
 				BuildCommandLine="cd .. &amp; makepanda\makepanda --everything"
-				Output="..\built\bin\test_interrogate.exe"/>
+				Output="..\built\python\python.exe"/>
 		</Configuration>
 		</Configuration>
 	</Configurations>
 	</Configurations>
 	<References>
 	<References>

+ 150 - 19
panda/src/display/graphicsOutput.cxx

@@ -32,6 +32,10 @@
 #include "perspectiveLens.h"
 #include "perspectiveLens.h"
 #include "pointerTo.h"
 #include "pointerTo.h"
 #include "compassEffect.h"
 #include "compassEffect.h"
+#include "geom.h"
+#include "geomNode.h"
+#include "geomTristrips.h"
+#include "geomVertexWriter.h"
 
 
 TypeHandle GraphicsOutput::_type_handle;
 TypeHandle GraphicsOutput::_type_handle;
 
 
@@ -87,6 +91,7 @@ GraphicsOutput(GraphicsPipe *pipe, GraphicsStateGuardian *gsg,
   _one_shot = false;
   _one_shot = false;
   _inverted = window_inverted;
   _inverted = window_inverted;
   _delete_flag = false;
   _delete_flag = false;
+  _texture_card = 0;
 
 
   int mode = gsg->get_properties().get_frame_buffer_mode();
   int mode = gsg->get_properties().get_frame_buffer_mode();
   if ((mode & FrameBufferProperties::FM_buffer) == FrameBufferProperties::FM_single_buffer) {
   if ((mode & FrameBufferProperties::FM_buffer) == FrameBufferProperties::FM_single_buffer) {
@@ -217,31 +222,30 @@ void GraphicsOutput::
 setup_render_texture(Texture *tex, bool allow_bind, bool to_ram) {
 setup_render_texture(Texture *tex, bool allow_bind, bool to_ram) {
   MutexHolder holder(_lock);
   MutexHolder holder(_lock);
 
 
+  if (to_ram) {
+    _rtm_mode = RTM_copy_ram;
+  } else if (allow_bind) {
+    _rtm_mode = RTM_bind_or_copy;
+  } else {
+    _rtm_mode = RTM_copy_texture;
+  }
+  
   if (tex == (Texture *)NULL) {
   if (tex == (Texture *)NULL) {
     _texture = new Texture(get_name());
     _texture = new Texture(get_name());
     _texture->set_wrap_u(Texture::WM_clamp);
     _texture->set_wrap_u(Texture::WM_clamp);
     _texture->set_wrap_v(Texture::WM_clamp);
     _texture->set_wrap_v(Texture::WM_clamp);
-
   } else {
   } else {
     _texture = tex;
     _texture = tex;
     _texture->clear_ram_image();
     _texture->clear_ram_image();
   }
   }
   _texture->set_match_framebuffer_format(true);
   _texture->set_match_framebuffer_format(true);
-
+  
   // Go ahead and tell the texture our anticipated size, even if it
   // Go ahead and tell the texture our anticipated size, even if it
   // might be inaccurate (particularly if this is a GraphicsWindow,
   // might be inaccurate (particularly if this is a GraphicsWindow,
   // which has system-imposed restrictions on size).
   // which has system-imposed restrictions on size).
   _texture->set_x_size(get_x_size());
   _texture->set_x_size(get_x_size());
   _texture->set_y_size(get_y_size());
   _texture->set_y_size(get_y_size());
 
 
-  if (to_ram) {
-    _rtm_mode = RTM_copy_ram;
-  } else if (allow_bind) {
-    _rtm_mode = RTM_bind_if_possible;
-  } else {
-    _rtm_mode = RTM_copy_texture;
-  }
-
   nassertv(_gsg != (GraphicsStateGuardian *)NULL);
   nassertv(_gsg != (GraphicsStateGuardian *)NULL);
   set_inverted(_gsg->get_copy_texture_inverted());
   set_inverted(_gsg->get_copy_texture_inverted());
 }
 }
@@ -460,6 +464,110 @@ get_active_display_region(int n) const {
   return result;
   return result;
 }
 }
 
 
+////////////////////////////////////////////////////////////////////
+//     Function: create_texture_card_vdata
+//       Access: Static
+//  Description: Generates a GeomVertexData for a texture card.
+////////////////////////////////////////////////////////////////////
+static PT(GeomVertexData)
+create_texture_card_vdata(int x, int y)
+{
+  int xru = Texture::up_to_power_2(x);
+  int yru = Texture::up_to_power_2(y);
+  
+  float xhi = (x * 1.0f) / xru;
+  float yhi = (y * 1.0f) / yru;
+  
+  CPT(GeomVertexFormat) format = GeomVertexFormat::get_v3n3cpt2();
+  
+  PT(GeomVertexData) vdata = new GeomVertexData
+    ("card", format, Geom::UH_static);
+
+  GeomVertexWriter vertex(vdata, InternalName::get_vertex());
+  GeomVertexWriter texcoord(vdata, InternalName::get_texcoord());
+  GeomVertexWriter normal(vdata, InternalName::get_normal());
+    
+  vertex.add_data3f(Vertexf::rfu(-1.0f, 0.0f,  1.0f));
+  vertex.add_data3f(Vertexf::rfu(-1.0f, 0.0f, -1.0f));
+  vertex.add_data3f(Vertexf::rfu( 1.0f, 0.0f,  1.0f));
+  vertex.add_data3f(Vertexf::rfu( 1.0f, 0.0f, -1.0f));
+  
+  texcoord.add_data2f( 0.0f,  yhi);
+  texcoord.add_data2f( 0.0f, 0.0f);
+  texcoord.add_data2f(  xhi,  yhi);
+  texcoord.add_data2f(  xhi, 0.0f);
+  
+  normal.add_data3f(LVector3f::back());
+  normal.add_data3f(LVector3f::back());
+  normal.add_data3f(LVector3f::back());
+  normal.add_data3f(LVector3f::back());
+
+  return vdata;
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: GraphicsOutput::set_size_and_recalc
+//       Access: Public
+//  Description: Changes the x_size and y_size, then recalculates
+//               structures that depend on size.  The recalculation
+//               currently includes:
+//               - compute_pixels on all the graphics regions.
+//               - updating the texture card, if one is present.
+////////////////////////////////////////////////////////////////////
+void GraphicsOutput::
+set_size_and_recalc(int x, int y) {
+  _x_size = x;
+  _y_size = y;
+  _has_size = true;
+  
+  TotalDisplayRegions::iterator dri;
+  for (dri = _total_display_regions.begin(); 
+       dri != _total_display_regions.end(); 
+       ++dri) {
+    (*dri)->compute_pixels(x,y);
+  }
+
+  if (_texture_card != 0) {
+    _texture_card->set_vertex_data(create_texture_card_vdata(x, y));
+  }
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: GraphicsOutput::get_texture_card
+//       Access: Published
+//  Description: Returns a PandaNode containing a square polygon.
+//               The dimensions are (-1,0,-1) to (1,0,1). The texture
+//               coordinates are such that the texture of this
+//               GraphicsOutput is aligned properly to the polygon.
+//               The GraphicsOutput promises to surgically update
+//               the Geom inside the PandaNode if necessary to maintain
+//               this invariant.
+//
+//               Each invocation of this function returns a freshly-
+//               allocated PandaNode.  You can therefore safely modify
+//               the RenderAttribs of the PandaNode.  The
+//               PandaNode is initially textured with the texture
+//               of this GraphicOutput.
+////////////////////////////////////////////////////////////////////
+NodePath GraphicsOutput::
+get_texture_card() {
+  if (_texture_card == 0) {
+    PT(GeomVertexData) vdata = create_texture_card_vdata(_x_size, _y_size);
+    PT(GeomTristrips) strip = new GeomTristrips(Geom::UH_static);
+    strip->set_shade_model(Geom::SM_uniform);
+    strip->add_next_vertices(4);
+    strip->close_primitive();
+    _texture_card = new Geom(vdata);
+    _texture_card->add_primitive(strip);
+  }
+  
+  PT(GeomNode) gnode = new GeomNode("texture card");
+  gnode->add_geom(_texture_card);
+  NodePath path(gnode);
+  path.set_texture(get_texture(), 0);
+  return path;
+}
+
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 //     Function: GraphicsOutput::make_texture_buffer
 //     Function: GraphicsOutput::make_texture_buffer
 //       Access: Published
 //       Access: Published
@@ -509,6 +617,15 @@ make_texture_buffer(const string &name, int x_size, int y_size,
 
 
   GraphicsOutput *buffer = NULL;
   GraphicsOutput *buffer = NULL;
 
 
+  if ((x_size == 0) && (y_size == 0)) {
+    // Currently, only parasite buffers support the tracking of the
+    // host window size.  If the user requests this, we have to use a
+    // parasite buffer.
+    buffer = engine->make_parasite(host, name, sort, x_size, y_size);
+    buffer->setup_render_texture(tex, false, to_ram);
+    return buffer;
+  }
+
   if (show_buffers) {
   if (show_buffers) {
     // If show_buffers is true, just go ahead and call make_buffer(),
     // If show_buffers is true, just go ahead and call make_buffer(),
     // since it all amounts to the same thing anyway--this will
     // since it all amounts to the same thing anyway--this will
@@ -784,6 +901,9 @@ begin_frame() {
     return false;
     return false;
   }
   }
 
 
+  // Track the size of some other graphics output, if desired.
+  auto_resize();
+  
   if (needs_context()) {
   if (needs_context()) {
     if (!make_context()) {
     if (!make_context()) {
       return false;
       return false;
@@ -793,11 +913,11 @@ begin_frame() {
   // Okay, we already have a GSG, so activate it.
   // Okay, we already have a GSG, so activate it.
   make_current();
   make_current();
 
 
-  if (_rtm_mode == RTM_bind_texture) {
+  if (_rtm_mode == RTM_bind_or_copy) {
     // Release the texture so we can render into the frame buffer.
     // Release the texture so we can render into the frame buffer.
     _gsg->framebuffer_release_texture(this, get_texture());
     _gsg->framebuffer_release_texture(this, get_texture());
   }
   }
-
+  
   _cube_map_index = -1;
   _cube_map_index = -1;
   _cube_map_dr = NULL;
   _cube_map_dr = NULL;
 
 
@@ -856,10 +976,10 @@ end_frame() {
     PStatTimer timer(_copy_texture_pcollector);
     PStatTimer timer(_copy_texture_pcollector);
     nassertv(has_texture());
     nassertv(has_texture());
 
 
-    // If _rtm_mode is RTM_bind_texture, it means we should attempt to
-    // lock the framebuffer directly to the texture memory, avoiding
+    // If _rtm_mode is one of the bind-modes, it means we should attempt
+    // to lock the framebuffer directly to the texture memory, avoiding
     // the copy.
     // the copy.
-    if (_rtm_mode == RTM_bind_texture) {
+    if (_rtm_mode == RTM_bind_or_copy) {
       if (display_cat.is_debug()) {
       if (display_cat.is_debug()) {
         display_cat.debug()
         display_cat.debug()
           << "Locking texture for " << get_name() << " at frame end.\n";
           << "Locking texture for " << get_name() << " at frame end.\n";
@@ -870,8 +990,8 @@ end_frame() {
         _rtm_mode = RTM_copy_texture;
         _rtm_mode = RTM_copy_texture;
       }
       }
     }
     }
-
-    if (_rtm_mode != RTM_bind_texture) {
+    
+    if (_rtm_mode == RTM_copy_texture) {
       if (display_cat.is_debug()) {
       if (display_cat.is_debug()) {
         display_cat.debug()
         display_cat.debug()
           << "Copying texture for " << get_name() << " at frame end.\n";
           << "Copying texture for " << get_name() << " at frame end.\n";
@@ -922,7 +1042,7 @@ end_frame() {
       
       
       // If we were rendering directly to texture, we can't delete the
       // If we were rendering directly to texture, we can't delete the
       // buffer until the texture is gone too.
       // buffer until the texture is gone too.
-      if (_rtm_mode == RTM_bind_texture) {
+      if (_rtm_mode == RTM_bind_or_copy) {
         _hold_texture = _texture;
         _hold_texture = _texture;
       }
       }
     }
     }
@@ -959,7 +1079,7 @@ change_scenes(DisplayRegion *new_dr) {
     _cube_map_dr = new_dr;
     _cube_map_dr = new_dr;
 
 
     if (_rtm_mode != RTM_none) {
     if (_rtm_mode != RTM_none) {
-      if (_rtm_mode == RTM_bind_texture) {
+      if (_rtm_mode == RTM_bind_or_copy) {
         // In render-to-texture mode, switch the rendering backend to
         // In render-to-texture mode, switch the rendering backend to
         // the new cube map face, so that the subsequent frame will be
         // the new cube map face, so that the subsequent frame will be
         // rendered to the new face.
         // rendered to the new face.
@@ -1043,6 +1163,17 @@ release_gsg() {
   _gsg.clear();
   _gsg.clear();
 }
 }
 
 
+////////////////////////////////////////////////////////////////////
+//     Function: GraphicsOutput::auto_resize
+//       Access: Public, Virtual
+//  Description: Certain graphics outputs can automatically resize
+//               themselves to automatically stay the same size as
+//               some other graphics output.
+////////////////////////////////////////////////////////////////////
+void GraphicsOutput::
+auto_resize() {
+}
+
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 //     Function: GraphicsOutput::begin_flip
 //     Function: GraphicsOutput::begin_flip
 //       Access: Public, Virtual
 //       Access: Public, Virtual

+ 10 - 4
panda/src/display/graphicsOutput.h

@@ -35,6 +35,7 @@
 #include "drawMask.h"
 #include "drawMask.h"
 #include "pvector.h"
 #include "pvector.h"
 #include "weakPointerTo.h"
 #include "weakPointerTo.h"
+#include "nodePath.h"
 
 
 class PNMImage;
 class PNMImage;
 
 
@@ -122,6 +123,8 @@ PUBLISHED:
   INLINE bool save_screenshot(const Filename &filename);
   INLINE bool save_screenshot(const Filename &filename);
   INLINE bool get_screenshot(PNMImage &image);
   INLINE bool get_screenshot(PNMImage &image);
 
 
+  NodePath get_texture_card();
+
 public:
 public:
   // These are not intended to be called directly by the user.
   // These are not intended to be called directly by the user.
   INLINE bool needs_context() const;
   INLINE bool needs_context() const;
@@ -137,6 +140,8 @@ public:
   virtual void set_close_now();
   virtual void set_close_now();
   virtual void reset_window(bool swapchain);
   virtual void reset_window(bool swapchain);
 
 
+  void set_size_and_recalc(int x, int y);
+  
   // It is an error to call any of the following methods from any
   // It is an error to call any of the following methods from any
   // thread other than the draw thread.  These methods are normally
   // thread other than the draw thread.  These methods are normally
   // called by the GraphicsEngine.
   // called by the GraphicsEngine.
@@ -152,7 +157,8 @@ public:
   virtual bool make_context();
   virtual bool make_context();
   virtual void make_current();
   virtual void make_current();
   virtual void release_gsg();
   virtual void release_gsg();
-
+  virtual void auto_resize();
+  
   // These methods will be called within the app (main) thread.
   // These methods will be called within the app (main) thread.
   virtual void begin_flip();
   virtual void begin_flip();
   virtual void end_flip();
   virtual void end_flip();
@@ -165,8 +171,7 @@ public:
 protected:
 protected:
   enum RenderTextureMode {
   enum RenderTextureMode {
     RTM_none,
     RTM_none,
-    RTM_bind_texture,
-    RTM_bind_if_possible,
+    RTM_bind_or_copy,
     RTM_copy_texture,
     RTM_copy_texture,
     RTM_copy_ram,
     RTM_copy_ram,
   };
   };
@@ -180,6 +185,7 @@ protected:
   bool _needs_context;
   bool _needs_context;
   int _cube_map_index;
   int _cube_map_index;
   DisplayRegion *_cube_map_dr;
   DisplayRegion *_cube_map_dr;
+  PT(Geom) _texture_card;
 
 
 private:
 private:
   DisplayRegion *add_display_region(DisplayRegion *display_region);
   DisplayRegion *add_display_region(DisplayRegion *display_region);
@@ -188,7 +194,7 @@ private:
 
 
   INLINE void determine_display_regions() const;
   INLINE void determine_display_regions() const;
   void do_determine_display_regions();
   void do_determine_display_regions();
-
+  
   int _sort;
   int _sort;
   unsigned int _internal_sort_index;
   unsigned int _internal_sort_index;
 
 

+ 4 - 22
panda/src/display/graphicsWindow.cxx

@@ -541,18 +541,9 @@ set_properties_now(WindowProperties &properties) {
       if (open_window()) {
       if (open_window()) {
         // When the window is first opened, force its size to be
         // When the window is first opened, force its size to be
         // broadcast to its display regions.
         // broadcast to its display regions.
-        _x_size = _properties.get_x_size();
-        _y_size = _properties.get_y_size();
-        _has_size = true;
         _is_valid = true;
         _is_valid = true;
-
-        TotalDisplayRegions::iterator dri;
-        for (dri = _total_display_regions.begin(); 
-             dri != _total_display_regions.end(); 
-             ++dri) {
-          (*dri)->compute_pixels(_x_size, _y_size);
-        }
-
+        set_size_and_recalc(_properties.get_x_size(),
+                            _properties.get_y_size());
       } else {
       } else {
         // Since we can't even open the window, tag the
         // Since we can't even open the window, tag the
         // _rejected_properties with all of the window properties that
         // _rejected_properties with all of the window properties that
@@ -715,18 +706,9 @@ system_changed_size(int x_size, int y_size) {
     display_cat.debug()
     display_cat.debug()
       << "system_changed_size(" << x_size << ", " << y_size << ")\n";
       << "system_changed_size(" << x_size << ", " << y_size << ")\n";
   }
   }
-
+  
   if (x_size != _properties.get_x_size() || 
   if (x_size != _properties.get_x_size() || 
       y_size != _properties.get_y_size()) {
       y_size != _properties.get_y_size()) {
-    _x_size = x_size;
-    _y_size = y_size;
-    _has_size = true;
-
-    TotalDisplayRegions::iterator dri;
-    for (dri = _total_display_regions.begin(); 
-         dri != _total_display_regions.end(); 
-         ++dri) {
-      (*dri)->compute_pixels(_x_size, _y_size);
-    }
+    set_size_and_recalc(x_size, y_size);
   }
   }
 }
 }

+ 28 - 2
panda/src/display/parasiteBuffer.cxx

@@ -44,13 +44,20 @@ ParasiteBuffer(GraphicsOutput *host, const string &name,
       << " on " << _host->get_name() << "\n";
       << " on " << _host->get_name() << "\n";
   }
   }
 
 
+  if ((x_size == 0)&&(y_size == 0)) {
+    _track_host_size = true;
+    x_size = host->get_x_size();
+    y_size = host->get_y_size();
+  } else {
+    _track_host_size = false;
+  }
+  
   _x_size = x_size;
   _x_size = x_size;
   _y_size = y_size;
   _y_size = y_size;
   _has_size = true;
   _has_size = true;
   _default_display_region->compute_pixels(_x_size, _y_size);
   _default_display_region->compute_pixels(_x_size, _y_size);
-
   _is_valid = true;
   _is_valid = true;
-
+  
   nassertv(_x_size <= host->get_x_size() && _y_size <= host->get_y_size());
   nassertv(_x_size <= host->get_x_size() && _y_size <= host->get_y_size());
 }
 }
 
 
@@ -100,3 +107,22 @@ void ParasiteBuffer::
 make_current() {
 make_current() {
   _host->make_current();
   _host->make_current();
 }
 }
+
+////////////////////////////////////////////////////////////////////
+//     Function: ParasiteBuffer::auto_resize
+//       Access: Public, Virtual
+//  Description: This function will be called within the draw thread
+//               to make sure this buffer is the right size.  If not,
+//               it will be resized.
+////////////////////////////////////////////////////////////////////
+void ParasiteBuffer::
+auto_resize() {
+  if (_track_host_size) {
+    _host->auto_resize();
+    if ((_host->get_x_size() != _x_size)||
+        (_host->get_y_size() != _y_size)) {
+      set_size_and_recalc(_host->get_x_size(),
+                          _host->get_y_size());
+    }
+  }
+}

+ 3 - 1
panda/src/display/parasiteBuffer.h

@@ -56,7 +56,7 @@ class EXPCL_PANDA ParasiteBuffer : public GraphicsOutput {
 public:
 public:
   ParasiteBuffer(GraphicsOutput *host, const string &name,
   ParasiteBuffer(GraphicsOutput *host, const string &name,
                  int x_size, int y_size);
                  int x_size, int y_size);
-
+  
 PUBLISHED:
 PUBLISHED:
   virtual ~ParasiteBuffer();
   virtual ~ParasiteBuffer();
 
 
@@ -65,9 +65,11 @@ PUBLISHED:
 public:
 public:
   virtual GraphicsOutput *get_host();
   virtual GraphicsOutput *get_host();
   virtual void make_current();
   virtual void make_current();
+  virtual void auto_resize();
 
 
 private:
 private:
   PT(GraphicsOutput) _host;
   PT(GraphicsOutput) _host;
+  bool _track_host_size;
   
   
 public:
 public:
   static TypeHandle get_class_type() {
   static TypeHandle get_class_type() {

+ 50 - 6
panda/src/dxgsg8/dxGraphicsStateGuardian8.cxx

@@ -1321,16 +1321,19 @@ end_draw_primitives() {
 //               copy.
 //               copy.
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 void DXGraphicsStateGuardian8::
 void DXGraphicsStateGuardian8::
-framebuffer_copy_to_texture(Texture *tex, int z, const DisplayRegion *dr, const RenderBuffer &rb) {
+framebuffer_copy_to_texture(Texture *tex, int z, const DisplayRegion *dr,
+                            const RenderBuffer &rb) {
   set_read_buffer(rb);
   set_read_buffer(rb);
 
 
+  int orig_x = tex->get_x_size();
+  int orig_y = tex->get_y_size();
+
   HRESULT hr;
   HRESULT hr;
   int xo, yo, w, h;
   int xo, yo, w, h;
   dr->get_region_pixels_i(xo, yo, w, h);
   dr->get_region_pixels_i(xo, yo, w, h);
-
-  tex->set_x_size(w);
-  tex->set_y_size(h);
-
+  tex->set_x_size(Texture::up_to_power_2(w));
+  tex->set_y_size(Texture::up_to_power_2(h));
+  
   TextureContext *tc = tex->prepare_now(get_prepared_objects(), this);
   TextureContext *tc = tex->prepare_now(get_prepared_objects(), this);
   if (tc == (TextureContext *)NULL) {
   if (tc == (TextureContext *)NULL) {
     return;
     return;
@@ -1345,13 +1348,54 @@ framebuffer_copy_to_texture(Texture *tex, int z, const DisplayRegion *dr, const
   }
   }
   nassertv(dtc->get_d3d_2d_texture() != NULL);
   nassertv(dtc->get_d3d_2d_texture() != NULL);
 
 
-  IDirect3DSurface8 *tex_level_0, *render_target;
+  IDirect3DSurface8 *tex_level_0;
   hr = dtc->get_d3d_2d_texture()->GetSurfaceLevel(0, &tex_level_0);
   hr = dtc->get_d3d_2d_texture()->GetSurfaceLevel(0, &tex_level_0);
   if (FAILED(hr)) {
   if (FAILED(hr)) {
     dxgsg8_cat.error() << "GetSurfaceLev failed in copy_texture" << D3DERRORSTRING(hr);
     dxgsg8_cat.error() << "GetSurfaceLev failed in copy_texture" << D3DERRORSTRING(hr);
     return;
     return;
   }
   }
 
 
+  // If the texture is the wrong size, we need to do something about it.
+  D3DSURFACE_DESC texdesc;
+  hr = tex_level_0->GetDesc(&texdesc);
+  if (FAILED(hr)) {
+    dxgsg8_cat.error() << "GetDesc failed in copy_texture" << D3DERRORSTRING(hr);
+    SAFE_RELEASE(tex_level_0);
+    return;
+  }
+  if ((texdesc.Width != tex->get_x_size())||(texdesc.Height != tex->get_y_size())) {
+    if ((orig_x != tex->get_x_size()) || (orig_y != tex->get_y_size())) {
+      // Texture might be wrong size because we resized it and need to recreate.
+      SAFE_RELEASE(tex_level_0);
+      if (!dtc->create_texture(*_screen)) {
+        // Oops, we can't re-create the texture for some reason.
+        dxgsg8_cat.error()
+          << "Unable to re-create texture " << *dtc->_texture << endl;
+        return;
+      }
+      hr = dtc->get_d3d_2d_texture()->GetSurfaceLevel(0, &tex_level_0);
+      if (FAILED(hr)) {
+        dxgsg8_cat.error() << "GetSurfaceLev failed in copy_texture" << D3DERRORSTRING(hr);
+        return;
+      }
+      hr = tex_level_0->GetDesc(&texdesc);
+      if (FAILED(hr)) {
+        dxgsg8_cat.error() << "GetDesc 2 failed in copy_texture" << D3DERRORSTRING(hr);
+        SAFE_RELEASE(tex_level_0);
+        return;
+      }
+    }
+    if ((texdesc.Width != tex->get_x_size())||(texdesc.Height != tex->get_y_size())) {
+      // If it's still the wrong size, it's because driver can't create size
+      // that we want.  In that case, there's no helping it, we have to give up.
+      dxgsg8_cat.error()
+        << "Unable to copy to texture, texture is wrong size: " << *dtc->_texture << endl;
+      SAFE_RELEASE(tex_level_0);
+      return;
+    }
+  }
+  
+  IDirect3DSurface8 *render_target;
   hr = _d3d_device->GetRenderTarget(&render_target);
   hr = _d3d_device->GetRenderTarget(&render_target);
   if (FAILED(hr)) {
   if (FAILED(hr)) {
     dxgsg8_cat.error() << "GetRenderTgt failed in copy_texture" << D3DERRORSTRING(hr);
     dxgsg8_cat.error() << "GetRenderTgt failed in copy_texture" << D3DERRORSTRING(hr);

+ 94 - 31
panda/src/glstuff/glGraphicsStateGuardian_src.cxx

@@ -565,6 +565,51 @@ reset() {
     }
     }
   }
   }
 
 
+  _supports_framebuffer_object = false;
+  if (has_extension("GL_EXT_framebuffer_object")) {
+    _supports_framebuffer_object = true;
+    _glIsRenderbuffer = (PFNGLISRENDERBUFFEREXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "IsRenderbufferEXT");
+    _glBindRenderbuffer = (PFNGLBINDRENDERBUFFEREXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "BindRenderbufferEXT");
+    _glDeleteRenderbuffers = (PFNGLDELETERENDERBUFFERSEXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "DeleteRenderbuffersEXT");
+    _glGenRenderbuffers = (PFNGLGENRENDERBUFFERSEXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "GenRenderbuffersEXT");
+    _glRenderbufferStorage = (PFNGLRENDERBUFFERSTORAGEEXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "RenderbufferStorageEXT");
+    _glGetRenderbufferParameteriv = (PFNGLGETRENDERBUFFERPARAMETERIVEXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "GetRenderbufferParameterivEXT");
+    _glIsFramebuffer = (PFNGLISFRAMEBUFFEREXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "IsFramebufferEXT");
+    _glBindFramebuffer = (PFNGLBINDFRAMEBUFFEREXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "BindFramebufferEXT");
+    _glDeleteFramebuffers = (PFNGLDELETEFRAMEBUFFERSEXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "DeleteFramebuffersEXT");
+    _glGenFramebuffers = (PFNGLGENFRAMEBUFFERSEXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "GenFramebuffersEXT");
+    _glCheckFramebufferStatus = (PFNGLCHECKFRAMEBUFFERSTATUSEXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "CheckFramebufferStatusEXT");
+    _glFramebufferTexture1D = (PFNGLFRAMEBUFFERTEXTURE1DEXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "FramebufferTexture1DEXT");
+    _glFramebufferTexture2D = (PFNGLFRAMEBUFFERTEXTURE2DEXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "FramebufferTexture2DEXT");
+    _glFramebufferTexture3D = (PFNGLFRAMEBUFFERTEXTURE3DEXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "FramebufferTexture3DEXT");
+    _glFramebufferRenderbuffer = (PFNGLFRAMEBUFFERRENDERBUFFEREXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "FramebufferRenderbufferEXT");
+    _glGetFramebufferAttachmentParameteriv = (PFNGLGETFRAMEBUFFERATTACHMENTPARAMETERIVEXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "GetFramebufferAttachmentParameterivEXT");
+    _glGenerateMipmap = (PFNGLGENERATEMIPMAPEXTPROC)
+      get_extension_func(GLPREFIX_QUOTED, "GenerateMipmapEXT");
+  }
+
+  _glDrawBuffers = NULL;
+  if (has_extension("GL_ARB_draw_buffers")) {
+    _glDrawBuffers = (PFNGLDRAWBUFFERSARBPROC)
+      get_extension_func(GLPREFIX_QUOTED, "DrawBuffersARB");
+  }
+  
   _glBlendEquation = NULL;
   _glBlendEquation = NULL;
   bool supports_blend_equation = false;
   bool supports_blend_equation = false;
   if (is_at_least_version(1, 2)) {
   if (is_at_least_version(1, 2)) {
@@ -831,7 +876,7 @@ reset() {
 
 
 
 
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
-//     Function: GLGraphicsStateGuardian::clear
+//     Function: GLGraphicsStateGuardian::do_clear
 //       Access: Public, Virtual
 //       Access: Public, Virtual
 //  Description: Clears all of the indicated buffers to their assigned
 //  Description: Clears all of the indicated buffers to their assigned
 //               colors.
 //               colors.
@@ -2388,10 +2433,26 @@ framebuffer_copy_to_texture(Texture *tex, int z, const DisplayRegion *dr,
 
 
   int xo, yo, w, h;
   int xo, yo, w, h;
   dr->get_region_pixels(xo, yo, w, h);
   dr->get_region_pixels(xo, yo, w, h);
+  tex->set_x_size(Texture::up_to_power_2(w));
+  tex->set_y_size(Texture::up_to_power_2(h));
+  
+  // Sanity check everything.
+  if (z >= 0) {
+    if (!_supports_cube_map) {
+      return;
+    }
+    nassertv(z < 6);
+    nassertv(tex->get_texture_type() == Texture::TT_cube_map);
+    if ((w != tex->get_x_size()) ||
+        (h != tex->get_y_size()) ||
+        (w != h)) {
+      return;
+    }
+  } else {
+    nassertv(tex->get_texture_type() == Texture::TT_2d_texture);
+  }
 
 
-  tex->set_x_size(w);
-  tex->set_y_size(h);
-
+  // Match framebuffer format if necessary.
   if (tex->get_match_framebuffer_format()) {
   if (tex->get_match_framebuffer_format()) {
     const FrameBufferProperties &properties = get_properties();
     const FrameBufferProperties &properties = get_properties();
     int mode = properties.get_frame_buffer_mode();
     int mode = properties.get_frame_buffer_mode();
@@ -2414,37 +2475,39 @@ framebuffer_copy_to_texture(Texture *tex, int z, const DisplayRegion *dr,
 
 
   TextureContext *tc = tex->prepare_now(get_prepared_objects(), this);
   TextureContext *tc = tex->prepare_now(get_prepared_objects(), this);
   nassertv(tc != (TextureContext *)NULL);
   nassertv(tc != (TextureContext *)NULL);
-
   CLP(TextureContext) *gtc = DCAST(CLP(TextureContext), tc);
   CLP(TextureContext) *gtc = DCAST(CLP(TextureContext), tc);
   GLenum target = get_texture_target(tex->get_texture_type());
   GLenum target = get_texture_target(tex->get_texture_type());
-  if (target == GL_NONE) {
-    // Invalid texture, can't copy to it.
-    return;
-  }
   GLP(BindTexture)(target, gtc->_index);
   GLP(BindTexture)(target, gtc->_index);
-
-  if (z >= 0) {
-    // Copy to a cube map face.
-    nassertv(z < 6);
-    nassertv(tex->get_texture_type() == Texture::TT_cube_map);
-
-    if (_supports_cube_map) {
-      // We cleverly defined the cube map faces to fall in the same
-      // order as the GL constants are defined, so we can just make this
-      // simple addition to get to the right GL constant.
-      GLP(CopyTexImage2D)(GL_TEXTURE_CUBE_MAP_POSITIVE_X + z, 0,
-                          get_internal_image_format(tex->get_format()),
-                          xo, yo, w, h, 0);
-    }
-
-  } else {
-    // Copy to a regular texture.
-    nassertv(tex->get_texture_type() == Texture::TT_2d_texture);
-    GLP(CopyTexImage2D)(GL_TEXTURE_2D, 0,
-                        get_internal_image_format(tex->get_format()),
-                        xo, yo, w, h, 0);
+  GLint internal_format = get_internal_image_format(tex->get_format());
+  GLenum imagetarget = (z >= 0) ? (GL_TEXTURE_CUBE_MAP_POSITIVE_X + z) : GL_TEXTURE_2D;
+  
+  // If the texture has never been uploaded before, create it.
+  // We cannot use glCopyTexImage2D to create a texture that may be
+  // larger than the screen, so use glTexImage2D with arbitrary data.
+  
+  if ((gtc->_already_applied == false)||
+      (gtc->_internal_format != internal_format)||
+      (gtc->_width  != tex->get_x_size())||
+      (gtc->_height != tex->get_y_size())||
+      (gtc->_depth  != 1)) {
+
+    char *image = new char[tex->get_x_size() * tex->get_y_size()];
+    memset(image, 128, tex->get_x_size() * tex->get_y_size());
+    GLP(TexImage2D)(imagetarget, 0, internal_format, 
+                    tex->get_x_size(), tex->get_y_size(), 0,
+                    GL_LUMINANCE, GL_UNSIGNED_BYTE, image);
+    delete image;
+    
+    gtc->_already_applied = true;
+    gtc->_internal_format = internal_format;
+    gtc->_width  = tex->get_x_size();
+    gtc->_height = tex->get_y_size();
+    gtc->_depth  = 1;
   }
   }
-
+  
+  // Copy the pixel data from the frame buffer.
+  GLP(CopyTexSubImage2D)(imagetarget, 0, 0, 0, xo, yo, w, h);
+  
   report_my_gl_errors();
   report_my_gl_errors();
 
 
   // Force reload of texture state, since we've just monkeyed with it.
   // Force reload of texture state, since we've just monkeyed with it.

+ 21 - 0
panda/src/glstuff/glGraphicsStateGuardian_src.h

@@ -380,6 +380,27 @@ public:
   PFNGLBLENDEQUATIONPROC _glBlendEquation;
   PFNGLBLENDEQUATIONPROC _glBlendEquation;
   PFNGLBLENDCOLORPROC _glBlendColor;
   PFNGLBLENDCOLORPROC _glBlendColor;
 
 
+  bool _supports_framebuffer_object;
+  PFNGLISRENDERBUFFEREXTPROC _glIsRenderbuffer;
+  PFNGLBINDRENDERBUFFEREXTPROC _glBindRenderbuffer;
+  PFNGLDELETERENDERBUFFERSEXTPROC _glDeleteRenderbuffers;
+  PFNGLGENRENDERBUFFERSEXTPROC _glGenRenderbuffers;
+  PFNGLRENDERBUFFERSTORAGEEXTPROC _glRenderbufferStorage;
+  PFNGLGETRENDERBUFFERPARAMETERIVEXTPROC _glGetRenderbufferParameteriv;
+  PFNGLISFRAMEBUFFEREXTPROC _glIsFramebuffer;
+  PFNGLBINDFRAMEBUFFEREXTPROC _glBindFramebuffer;
+  PFNGLDELETEFRAMEBUFFERSEXTPROC _glDeleteFramebuffers;
+  PFNGLGENFRAMEBUFFERSEXTPROC _glGenFramebuffers;
+  PFNGLCHECKFRAMEBUFFERSTATUSEXTPROC _glCheckFramebufferStatus;
+  PFNGLFRAMEBUFFERTEXTURE1DEXTPROC _glFramebufferTexture1D;
+  PFNGLFRAMEBUFFERTEXTURE2DEXTPROC _glFramebufferTexture2D;
+  PFNGLFRAMEBUFFERTEXTURE3DEXTPROC _glFramebufferTexture3D;
+  PFNGLFRAMEBUFFERRENDERBUFFEREXTPROC _glFramebufferRenderbuffer;
+  PFNGLGETFRAMEBUFFERATTACHMENTPARAMETERIVEXTPROC _glGetFramebufferAttachmentParameteriv;
+  PFNGLGENERATEMIPMAPEXTPROC _glGenerateMipmap;
+  
+  PFNGLDRAWBUFFERSARBPROC _glDrawBuffers;
+
   GLenum _edge_clamp;
   GLenum _edge_clamp;
   GLenum _border_clamp;
   GLenum _border_clamp;
   GLenum _mirror_repeat;
   GLenum _mirror_repeat;

+ 142 - 34
panda/src/glstuff/glShaderContext_src.cxx

@@ -244,7 +244,6 @@ bind(GSG *gsg) {
 
 
     // Pass in k-parameters and transform-parameters
     // Pass in k-parameters and transform-parameters
     issue_parameters(gsg);
     issue_parameters(gsg);
-    issue_transform(gsg);
     
     
     // Bind the shaders.
     // Bind the shaders.
     cgGLEnableProfile(_cg_profile[SHADER_type_vert]);
     cgGLEnableProfile(_cg_profile[SHADER_type_vert]);
@@ -271,13 +270,62 @@ unbind()
 #endif
 #endif
 }
 }
 
 
+////////////////////////////////////////////////////////////////////
+//     Function: GLShaderContext::issue_cg_auto_bind
+//       Access: Public
+//  Description: Pass a single system parameter into the shader.
+////////////////////////////////////////////////////////////////////
+#ifdef HAVE_CGGL
+void CLP(ShaderContext)::
+issue_cg_auto_bind(const ShaderAutoBind &bind, GSG *gsg)
+{
+  LVecBase4f t;
+
+  CGparameter p = bind.parameter;
+  switch(bind.value) {
+  case SIC_mat_modelview:
+  case SIC_inv_modelview:
+  case SIC_tps_modelview:
+  case SIC_itp_modelview:
+  case SIC_mat_projection:
+  case SIC_inv_projection:
+  case SIC_tps_projection:
+  case SIC_itp_projection:
+  case SIC_mat_texture:
+  case SIC_inv_texture:
+  case SIC_tps_texture:
+  case SIC_itp_texture:
+  case SIC_mat_modelproj:
+  case SIC_inv_modelproj:
+  case SIC_tps_modelproj:
+  case SIC_itp_modelproj:
+    cgGLSetStateMatrixParameter(p, (CGGLenum)((bind.value >> 2)+4), (CGGLenum)(bind.value & 3));
+    return;
+  case SIC_sys_windowsize:
+    t[0] = gsg->_current_display_region->get_pixel_width();
+    t[1] = gsg->_current_display_region->get_pixel_height();
+    t[2] = 1;
+    t[3] = 1;
+    cgGLSetParameter4fv(p, t.get_data());
+    return;
+  case SIC_sys_pixelsize:
+    t[0] = 1.0 / gsg->_current_display_region->get_pixel_width();
+    t[1] = 1.0 / gsg->_current_display_region->get_pixel_height();
+    t[2] = 1;
+    t[3] = 1;
+    cgGLSetParameter4fv(p, t.get_data());
+    return;
+  }
+}
+#endif
+
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 //     Function: GLShaderContext::issue_parameters
 //     Function: GLShaderContext::issue_parameters
 //       Access: Public
 //       Access: Public
-//  Description: This function is to be called whenever
-//               the RenderState has changed, but the ShaderExpansion
-//               has not changed.  It loads the new input parameters
-//               into the already-bound shader.
+//  Description: This function gets called whenever the RenderState
+//               has changed, but the ShaderExpansion itself has not
+//               changed.  It loads new parameters into the
+//               already-bound shader.
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 void CLP(ShaderContext)::
 void CLP(ShaderContext)::
 issue_parameters(GSG *gsg)
 issue_parameters(GSG *gsg)
@@ -304,24 +352,27 @@ issue_parameters(GSG *gsg)
       cgGLSetMatrixParameterfc(_cg_npbind[i].parameter, dat);
       cgGLSetMatrixParameterfc(_cg_npbind[i].parameter, dat);
     }
     }
     
     
+    // Pass in system parameters
+    for (int i=0; i<(int)_cg_auto_param.size(); i++) {
+      issue_cg_auto_bind(_cg_auto_param[i], gsg);
+    }
+    
     // Pass in trans,tpose,row,col,xvec,yvec,zvec,pos parameters
     // Pass in trans,tpose,row,col,xvec,yvec,zvec,pos parameters
-    for (int i=0; i<(int)_cg_parameter_bind.size(); i++)
+    for (int i=0; i<(int)_cg_parameter_bind.size(); i++) {
       bind_cg_transform(_cg_parameter_bind[i], gsg);
       bind_cg_transform(_cg_parameter_bind[i], gsg);
-
-    // Pass in trans,tpose,row,col,xvec,yvec,zvec,pos parameters
-    for (int i=0; i<(int)_cg_transform_bind.size(); i++)
-      bind_cg_transform(_cg_transform_bind[i], gsg);
+    }
   }
   }
 #endif
 #endif
+  issue_transform(gsg);
 }
 }
 
 
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 //     Function: GLShaderContext::issue_transform
 //     Function: GLShaderContext::issue_transform
 //       Access: Public
 //       Access: Public
-//  Description: This function is to be called whenever
-//               the external_transform has changed, but the
-//               ShaderExpansion itself has not changed.  It loads the 
-//               new transform into the already-bound shader.
+//  Description: This function gets called whenever the RenderState
+//               or the TransformState has changed, but the
+//               ShaderExpansion itself has not changed.  It loads
+//               new parameters into the already-bound shader.
 ////////////////////////////////////////////////////////////////////
 ////////////////////////////////////////////////////////////////////
 void CLP(ShaderContext)::
 void CLP(ShaderContext)::
 issue_transform(GSG *gsg)
 issue_transform(GSG *gsg)
@@ -329,14 +380,13 @@ issue_transform(GSG *gsg)
 #ifdef HAVE_CGGL
 #ifdef HAVE_CGGL
   if (_cg_context != 0) {
   if (_cg_context != 0) {
     // Pass in modelview, projection, etc.
     // Pass in modelview, projection, etc.
-    for (int i=0; i<(int)_cg_autobind.size(); i++)
-      cgGLSetStateMatrixParameter(_cg_autobind[i].parameter,
-                                  _cg_autobind[i].matrix,
-                                  _cg_autobind[i].orient);
-    
+    for (int i=0; i<(int)_cg_auto_trans.size(); i++) {
+      issue_cg_auto_bind(_cg_auto_trans[i], gsg);
+    }
     // Pass in trans,tpose,row,col,xvec,yvec,zvec,pos parameters
     // Pass in trans,tpose,row,col,xvec,yvec,zvec,pos parameters
-    for (int i=0; i<(int)_cg_transform_bind.size(); i++)
+    for (int i=0; i<(int)_cg_transform_bind.size(); i++) {
       bind_cg_transform(_cg_transform_bind[i], gsg);
       bind_cg_transform(_cg_transform_bind[i], gsg);
+    }
   }
   }
 #endif
 #endif
 }
 }
@@ -513,13 +563,14 @@ update_shader_texture_bindings(CLP(ShaderContext) *prev, GSG *gsg)
 void CLP(ShaderContext)::
 void CLP(ShaderContext)::
 bind_cg_transform(const ShaderTransBind &stb, GSG *gsg)
 bind_cg_transform(const ShaderTransBind &stb, GSG *gsg)
 {
 {
+  const float *data;
   CPT(TransformState) src;
   CPT(TransformState) src;
   CPT(TransformState) rel;
   CPT(TransformState) rel;
   
   
   if (stb.src_name == InternalName::get_camera()) {
   if (stb.src_name == InternalName::get_camera()) {
     src = TransformState::make_identity();
     src = TransformState::make_identity();
   } else if (stb.src_name == InternalName::get_view()) {
   } else if (stb.src_name == InternalName::get_view()) {
-    src = gsg->_cs_transform;
+    src = gsg->_inv_cs_transform;
   } else if (stb.src_name == InternalName::get_model()) {
   } else if (stb.src_name == InternalName::get_model()) {
     src = gsg->get_transform();
     src = gsg->get_transform();
   } else if (stb.src_name == InternalName::get_world()) {
   } else if (stb.src_name == InternalName::get_world()) {
@@ -536,8 +587,8 @@ bind_cg_transform(const ShaderTransBind &stb, GSG *gsg)
 
 
   if (stb.rel_name == InternalName::get_camera()) {
   if (stb.rel_name == InternalName::get_camera()) {
     rel = TransformState::make_identity();
     rel = TransformState::make_identity();
-  } else if (stb.src_name == InternalName::get_view()) {
-    rel = gsg->_cs_transform;
+  } else if (stb.rel_name == InternalName::get_view()) {
+    rel = gsg->_inv_cs_transform;
   } else if (stb.rel_name == InternalName::get_model()) {
   } else if (stb.rel_name == InternalName::get_model()) {
     rel = gsg->get_transform();
     rel = gsg->get_transform();
   } else if (stb.rel_name == InternalName::get_world()) {
   } else if (stb.rel_name == InternalName::get_world()) {
@@ -553,13 +604,39 @@ bind_cg_transform(const ShaderTransBind &stb, GSG *gsg)
   }
   }
   
   
   CPT(TransformState) total = rel->invert_compose(src);
   CPT(TransformState) total = rel->invert_compose(src);
-  const float *data = total->get_mat().get_data();
-  //  cerr << "Input for " << cgGetParameterName(stb.parameter) << " is\n" << 
+
+  //  data = src->get_mat().get_data();
+  //  cerr << "Src for " << cgGetParameterName(stb.parameter) << " is\n" << 
+  //    data[ 0] << " " << data[ 1] << " " << data[ 2] << " " << data[ 3] << "\n" <<
+  //    data[ 4] << " " << data[ 5] << " " << data[ 6] << " " << data[ 7] << "\n" <<
+  //    data[ 8] << " " << data[ 9] << " " << data[10] << " " << data[11] << "\n" <<
+  //    data[12] << " " << data[13] << " " << data[14] << " " << data[15] << "\n";
+  //  data = rel->get_mat().get_data();
+  //  cerr << "Rel for " << cgGetParameterName(stb.parameter) << " is\n" << 
+  //    data[ 0] << " " << data[ 1] << " " << data[ 2] << " " << data[ 3] << "\n" <<
+  //    data[ 4] << " " << data[ 5] << " " << data[ 6] << " " << data[ 7] << "\n" <<
+  //    data[ 8] << " " << data[ 9] << " " << data[10] << " " << data[11] << "\n" <<
+  //    data[12] << " " << data[13] << " " << data[14] << " " << data[15] << "\n";
+  //  data = total->get_mat().get_data();
+  //  cerr << "Total for " << cgGetParameterName(stb.parameter) << " is\n" << 
+  //    data[ 0] << " " << data[ 1] << " " << data[ 2] << " " << data[ 3] << "\n" <<
+  //    data[ 4] << " " << data[ 5] << " " << data[ 6] << " " << data[ 7] << "\n" <<
+  //    data[ 8] << " " << data[ 9] << " " << data[10] << " " << data[11] << "\n" <<
+  //    data[12] << " " << data[13] << " " << data[14] << " " << data[15] << "\n";
+  //  data = gsg->_cs_transform->get_mat().get_data();
+  //  cerr << "cs_transform is\n" <<
+  //    data[ 0] << " " << data[ 1] << " " << data[ 2] << " " << data[ 3] << "\n" <<
+  //    data[ 4] << " " << data[ 5] << " " << data[ 6] << " " << data[ 7] << "\n" <<
+  //    data[ 8] << " " << data[ 9] << " " << data[10] << " " << data[11] << "\n" <<
+  //    data[12] << " " << data[13] << " " << data[14] << " " << data[15] << "\n";
+  //  data = gsg->_internal_transform->get_mat().get_data();
+  //  cerr << "internal_transform is\n" <<
   //    data[ 0] << " " << data[ 1] << " " << data[ 2] << " " << data[ 3] << "\n" <<
   //    data[ 0] << " " << data[ 1] << " " << data[ 2] << " " << data[ 3] << "\n" <<
   //    data[ 4] << " " << data[ 5] << " " << data[ 6] << " " << data[ 7] << "\n" <<
   //    data[ 4] << " " << data[ 5] << " " << data[ 6] << " " << data[ 7] << "\n" <<
   //    data[ 8] << " " << data[ 9] << " " << data[10] << " " << data[11] << "\n" <<
   //    data[ 8] << " " << data[ 9] << " " << data[10] << " " << data[11] << "\n" <<
   //    data[12] << " " << data[13] << " " << data[14] << " " << data[15] << "\n";
   //    data[12] << " " << data[13] << " " << data[14] << " " << data[15] << "\n";
 
 
+  data = total->get_mat().get_data();
   switch (stb.trans_piece) {
   switch (stb.trans_piece) {
   case SHADER_data_matrix: cgGLSetMatrixParameterfc(stb.parameter, data); break;
   case SHADER_data_matrix: cgGLSetMatrixParameterfc(stb.parameter, data); break;
   case SHADER_data_transpose:  cgGLSetMatrixParameterfr(stb.parameter, data); break;
   case SHADER_data_transpose:  cgGLSetMatrixParameterfr(stb.parameter, data); break;
@@ -894,9 +971,11 @@ compile_cg_parameter(CGparameter p)
     bind.parameter = p;
     bind.parameter = p;
     
     
     if      (pieces[0]=="wstrans") { bind.rel_name = InternalName::get_world();  bind.trans_piece = SHADER_data_matrix; }
     if      (pieces[0]=="wstrans") { bind.rel_name = InternalName::get_world();  bind.trans_piece = SHADER_data_matrix; }
+    else if (pieces[0]=="vstrans") { bind.rel_name = InternalName::get_view();   bind.trans_piece = SHADER_data_matrix; }
     else if (pieces[0]=="cstrans") { bind.rel_name = InternalName::get_camera(); bind.trans_piece = SHADER_data_matrix; }
     else if (pieces[0]=="cstrans") { bind.rel_name = InternalName::get_camera(); bind.trans_piece = SHADER_data_matrix; }
     else if (pieces[0]=="mstrans") { bind.rel_name = InternalName::get_model();  bind.trans_piece = SHADER_data_matrix; }
     else if (pieces[0]=="mstrans") { bind.rel_name = InternalName::get_model();  bind.trans_piece = SHADER_data_matrix; }
     else if (pieces[0]=="wspos")   { bind.rel_name = InternalName::get_world();  bind.trans_piece = SHADER_data_row3; }
     else if (pieces[0]=="wspos")   { bind.rel_name = InternalName::get_world();  bind.trans_piece = SHADER_data_row3; }
+    else if (pieces[0]=="vspos")   { bind.rel_name = InternalName::get_view();   bind.trans_piece = SHADER_data_row3; }
     else if (pieces[0]=="cspos")   { bind.rel_name = InternalName::get_camera(); bind.trans_piece = SHADER_data_row3; }
     else if (pieces[0]=="cspos")   { bind.rel_name = InternalName::get_camera(); bind.trans_piece = SHADER_data_row3; }
     else if (pieces[0]=="mspos")   { bind.rel_name = InternalName::get_model();  bind.trans_piece = SHADER_data_row3; }
     else if (pieces[0]=="mspos")   { bind.rel_name = InternalName::get_model();  bind.trans_piece = SHADER_data_row3; }
 
 
@@ -926,22 +1005,51 @@ compile_cg_parameter(CGparameter p)
       return false;
       return false;
     ShaderAutoBind bind;
     ShaderAutoBind bind;
     bind.parameter = p;
     bind.parameter = p;
-    if      (pieces[1] == "modelview")  bind.matrix = CG_GL_MODELVIEW_MATRIX;
-    else if (pieces[1] == "projection") bind.matrix = CG_GL_PROJECTION_MATRIX;
-    else if (pieces[1] == "texmatrix")  bind.matrix = CG_GL_TEXTURE_MATRIX;
-    else if (pieces[1] == "modelproj")  bind.matrix = CG_GL_MODELVIEW_PROJECTION_MATRIX;
+    bind.value = 0;
+    if      (pieces[1] == "modelview")  bind.value += 0;
+    else if (pieces[1] == "projection") bind.value += 4;
+    else if (pieces[1] == "texmatrix")  bind.value += 8;
+    else if (pieces[1] == "modelproj")  bind.value += 12;
     else {
     else {
       errchk_cg_output(p, "unrecognized matrix name");
       errchk_cg_output(p, "unrecognized matrix name");
       return false;
       return false;
     }
     }
-    if      (pieces[0]=="mat") bind.orient = CG_GL_MATRIX_IDENTITY;
-    else if (pieces[0]=="inv") bind.orient = CG_GL_MATRIX_INVERSE;
-    else if (pieces[0]=="tps") bind.orient = CG_GL_MATRIX_TRANSPOSE;
-    else if (pieces[0]=="itp") bind.orient = CG_GL_MATRIX_INVERSE_TRANSPOSE;
-    _cg_autobind.push_back(bind);
+    if      (pieces[0]=="mat") bind.value += 0;
+    else if (pieces[0]=="inv") bind.value += 1;
+    else if (pieces[0]=="tps") bind.value += 2;
+    else if (pieces[0]=="itp") bind.value += 3;
+    _cg_auto_trans.push_back(bind);
     return true;
     return true;
   }
   }
 
 
+  if (pieces[0] == "sys") {
+    if ((!errchk_cg_parameter_words(p,2)) ||
+        (!errchk_cg_parameter_direction(p, CG_IN)) ||
+        (!errchk_cg_parameter_variance(p, CG_UNIFORM))) {
+      return false;    
+    }
+    ShaderAutoBind bind;
+    bind.parameter = p;
+    if (pieces[1] == "pixelsize") {
+      if (!errchk_cg_parameter_type(p, CG_FLOAT2)) {
+        return false;
+      }
+      bind.value = SIC_sys_pixelsize;
+      _cg_auto_param.push_back(bind);
+      return true;
+    }
+    if (pieces[1] == "windowsize") {
+      if (!errchk_cg_parameter_type(p, CG_FLOAT2)) {
+        return false;
+      }
+      bind.value = SIC_sys_windowsize;
+      _cg_auto_param.push_back(bind);
+      return true;
+    }
+    errchk_cg_output(p,"unknown system parameter");
+    return false;
+  }
+
   if (pieces[0] == "tex") {
   if (pieces[0] == "tex") {
     if ((!errchk_cg_parameter_direction(p, CG_IN)) ||
     if ((!errchk_cg_parameter_direction(p, CG_IN)) ||
         (!errchk_cg_parameter_variance(p, CG_UNIFORM)) ||
         (!errchk_cg_parameter_variance(p, CG_UNIFORM)) ||

+ 27 - 3
panda/src/glstuff/glShaderContext_src.h

@@ -51,10 +51,32 @@ public:
 private:
 private:
 
 
 #ifdef HAVE_CGGL
 #ifdef HAVE_CGGL
+  enum ShaderAutoValue {
+    // This first batch of constants cleverly lines up
+    // with the Cg constant values.  Don't insert anything.
+    SIC_mat_modelview,
+    SIC_inv_modelview,
+    SIC_tps_modelview,
+    SIC_itp_modelview,
+    SIC_mat_projection,
+    SIC_inv_projection,
+    SIC_tps_projection,
+    SIC_itp_projection,
+    SIC_mat_texture,
+    SIC_inv_texture,
+    SIC_tps_texture,
+    SIC_itp_texture,
+    SIC_mat_modelproj,
+    SIC_inv_modelproj,
+    SIC_tps_modelproj,
+    SIC_itp_modelproj,
+    // From this point forward, it's okay to insert stuff.
+    SIC_sys_windowsize,
+    SIC_sys_pixelsize,
+  };
   struct ShaderAutoBind {
   struct ShaderAutoBind {
     CGparameter parameter;
     CGparameter parameter;
-    CGGLenum matrix;
-    CGGLenum orient;
+    int value;
   };
   };
   struct ShaderArgBind {
   struct ShaderArgBind {
     CGparameter parameter;
     CGparameter parameter;
@@ -85,7 +107,8 @@ private:
   
   
   // These arrays contain lists of "bindings." They
   // These arrays contain lists of "bindings." They
   // tell us how to fill the shader's input parameters.
   // tell us how to fill the shader's input parameters.
-  vector <ShaderAutoBind> _cg_autobind;
+  vector <ShaderAutoBind> _cg_auto_trans;
+  vector <ShaderAutoBind> _cg_auto_param;
   vector <ShaderArgBind> _cg_fbind;
   vector <ShaderArgBind> _cg_fbind;
   vector <ShaderArgBind> _cg_npbind;
   vector <ShaderArgBind> _cg_npbind;
   vector <ShaderTexBind> _cg_texbind;
   vector <ShaderTexBind> _cg_texbind;
@@ -98,6 +121,7 @@ private:
                          CLP(GraphicsStateGuardian) *gsg);
                          CLP(GraphicsStateGuardian) *gsg);
   void suggest_cg_profile(const string &vpro, const string &fpro);
   void suggest_cg_profile(const string &vpro, const string &fpro);
   CGprofile parse_cg_profile(const string &id, bool vertex);
   CGprofile parse_cg_profile(const string &id, bool vertex);
+  void issue_cg_auto_bind(const ShaderAutoBind &bind, GSG *gsg);
   bool compile_cg_parameter(CGparameter p);
   bool compile_cg_parameter(CGparameter p);
   bool errchk_cg_parameter_words(CGparameter p, int len);
   bool errchk_cg_parameter_words(CGparameter p, int len);
   bool errchk_cg_parameter_direction(CGparameter p, CGenum dir);
   bool errchk_cg_parameter_direction(CGparameter p, CGenum dir);

+ 594 - 16
panda/src/glstuff/panda_glext.h

@@ -1,10 +1,5 @@
-/* Additions by drose to re-include this glext.h even if an older
-   version has previously been included. */
-#if defined(GL_GLEXT_VERSION) && GL_GLEXT_VERSION < 21
-  #undef GL_GLEXT_VERSION
-#endif
-#ifndef GL_GLEXT_VERSION
-
+#ifndef __glext_h_
+#define __glext_h_
 
 
 #ifdef __cplusplus
 #ifdef __cplusplus
 extern "C" {
 extern "C" {
@@ -29,7 +24,7 @@ extern "C" {
 ** 
 ** 
 ** Original Code. The Original Code is: OpenGL Sample Implementation,
 ** Original Code. The Original Code is: OpenGL Sample Implementation,
 ** Version 1.2.1, released January 26, 2000, developed by Silicon Graphics,
 ** Version 1.2.1, released January 26, 2000, developed by Silicon Graphics,
-** Inc. The Original Code is Copyright (c) 1991-2002 Silicon Graphics, Inc.
+** Inc. The Original Code is Copyright (c) 1991-2004 Silicon Graphics, Inc.
 ** Copyright in any portions created by third parties is as indicated
 ** Copyright in any portions created by third parties is as indicated
 ** elsewhere herein. All Rights Reserved.
 ** elsewhere herein. All Rights Reserved.
 ** 
 ** 
@@ -57,9 +52,9 @@ extern "C" {
 /*************************************************************/
 /*************************************************************/
 
 
 /* Header file version number, required by OpenGL ABI for Linux */
 /* Header file version number, required by OpenGL ABI for Linux */
-/* glext.h last updated 2003/1/12 */
+/* glext.h last updated 2005/06/20 */
 /* Current version at http://oss.sgi.com/projects/ogl-sample/registry/ */
 /* Current version at http://oss.sgi.com/projects/ogl-sample/registry/ */
-#define GL_GLEXT_VERSION 21
+#define GL_GLEXT_VERSION 29
 
 
 #ifndef GL_VERSION_1_2
 #ifndef GL_VERSION_1_2
 #define GL_UNSIGNED_BYTE_3_3_2            0x8032
 #define GL_UNSIGNED_BYTE_3_3_2            0x8032
@@ -256,7 +251,6 @@ extern "C" {
 #define GL_NUM_COMPRESSED_TEXTURE_FORMATS 0x86A2
 #define GL_NUM_COMPRESSED_TEXTURE_FORMATS 0x86A2
 #define GL_COMPRESSED_TEXTURE_FORMATS     0x86A3
 #define GL_COMPRESSED_TEXTURE_FORMATS     0x86A3
 #define GL_CLAMP_TO_BORDER                0x812D
 #define GL_CLAMP_TO_BORDER                0x812D
-#define GL_CLAMP_TO_BORDER_SGIS           0x812D
 #define GL_COMBINE                        0x8570
 #define GL_COMBINE                        0x8570
 #define GL_COMBINE_RGB                    0x8571
 #define GL_COMBINE_RGB                    0x8571
 #define GL_COMBINE_ALPHA                  0x8572
 #define GL_COMBINE_ALPHA                  0x8572
@@ -362,7 +356,7 @@ extern "C" {
 #define GL_DYNAMIC_READ                   0x88E9
 #define GL_DYNAMIC_READ                   0x88E9
 #define GL_DYNAMIC_COPY                   0x88EA
 #define GL_DYNAMIC_COPY                   0x88EA
 #define GL_SAMPLES_PASSED                 0x8914
 #define GL_SAMPLES_PASSED                 0x8914
-#define GL_FOG_COORD_SOURCE               GL_FOG_COORDINATE_SOURCE
+#define GL_FOG_COORD_SRC                  GL_FOG_COORDINATE_SOURCE
 #define GL_FOG_COORD                      GL_FOG_COORDINATE
 #define GL_FOG_COORD                      GL_FOG_COORDINATE
 #define GL_CURRENT_FOG_COORD              GL_CURRENT_FOG_COORDINATE
 #define GL_CURRENT_FOG_COORD              GL_CURRENT_FOG_COORDINATE
 #define GL_FOG_COORD_ARRAY_TYPE           GL_FOG_COORDINATE_ARRAY_TYPE
 #define GL_FOG_COORD_ARRAY_TYPE           GL_FOG_COORDINATE_ARRAY_TYPE
@@ -378,6 +372,93 @@ extern "C" {
 #define GL_SRC2_ALPHA                     GL_SOURCE2_ALPHA
 #define GL_SRC2_ALPHA                     GL_SOURCE2_ALPHA
 #endif
 #endif
 
 
+#ifndef GL_VERSION_2_0
+#define GL_BLEND_EQUATION_RGB             GL_BLEND_EQUATION
+#define GL_VERTEX_ATTRIB_ARRAY_ENABLED    0x8622
+#define GL_VERTEX_ATTRIB_ARRAY_SIZE       0x8623
+#define GL_VERTEX_ATTRIB_ARRAY_STRIDE     0x8624
+#define GL_VERTEX_ATTRIB_ARRAY_TYPE       0x8625
+#define GL_CURRENT_VERTEX_ATTRIB          0x8626
+#define GL_VERTEX_PROGRAM_POINT_SIZE      0x8642
+#define GL_VERTEX_PROGRAM_TWO_SIDE        0x8643
+#define GL_VERTEX_ATTRIB_ARRAY_POINTER    0x8645
+#define GL_STENCIL_BACK_FUNC              0x8800
+#define GL_STENCIL_BACK_FAIL              0x8801
+#define GL_STENCIL_BACK_PASS_DEPTH_FAIL   0x8802
+#define GL_STENCIL_BACK_PASS_DEPTH_PASS   0x8803
+#define GL_MAX_DRAW_BUFFERS               0x8824
+#define GL_DRAW_BUFFER0                   0x8825
+#define GL_DRAW_BUFFER1                   0x8826
+#define GL_DRAW_BUFFER2                   0x8827
+#define GL_DRAW_BUFFER3                   0x8828
+#define GL_DRAW_BUFFER4                   0x8829
+#define GL_DRAW_BUFFER5                   0x882A
+#define GL_DRAW_BUFFER6                   0x882B
+#define GL_DRAW_BUFFER7                   0x882C
+#define GL_DRAW_BUFFER8                   0x882D
+#define GL_DRAW_BUFFER9                   0x882E
+#define GL_DRAW_BUFFER10                  0x882F
+#define GL_DRAW_BUFFER11                  0x8830
+#define GL_DRAW_BUFFER12                  0x8831
+#define GL_DRAW_BUFFER13                  0x8832
+#define GL_DRAW_BUFFER14                  0x8833
+#define GL_DRAW_BUFFER15                  0x8834
+#define GL_BLEND_EQUATION_ALPHA           0x883D
+#define GL_POINT_SPRITE                   0x8861
+#define GL_COORD_REPLACE                  0x8862
+#define GL_MAX_VERTEX_ATTRIBS             0x8869
+#define GL_VERTEX_ATTRIB_ARRAY_NORMALIZED 0x886A
+#define GL_MAX_TEXTURE_COORDS             0x8871
+#define GL_MAX_TEXTURE_IMAGE_UNITS        0x8872
+#define GL_FRAGMENT_SHADER                0x8B30
+#define GL_VERTEX_SHADER                  0x8B31
+#define GL_MAX_FRAGMENT_UNIFORM_COMPONENTS 0x8B49
+#define GL_MAX_VERTEX_UNIFORM_COMPONENTS  0x8B4A
+#define GL_MAX_VARYING_FLOATS             0x8B4B
+#define GL_MAX_VERTEX_TEXTURE_IMAGE_UNITS 0x8B4C
+#define GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS 0x8B4D
+#define GL_SHADER_TYPE                    0x8B4F
+#define GL_FLOAT_VEC2                     0x8B50
+#define GL_FLOAT_VEC3                     0x8B51
+#define GL_FLOAT_VEC4                     0x8B52
+#define GL_INT_VEC2                       0x8B53
+#define GL_INT_VEC3                       0x8B54
+#define GL_INT_VEC4                       0x8B55
+#define GL_BOOL                           0x8B56
+#define GL_BOOL_VEC2                      0x8B57
+#define GL_BOOL_VEC3                      0x8B58
+#define GL_BOOL_VEC4                      0x8B59
+#define GL_FLOAT_MAT2                     0x8B5A
+#define GL_FLOAT_MAT3                     0x8B5B
+#define GL_FLOAT_MAT4                     0x8B5C
+#define GL_SAMPLER_1D                     0x8B5D
+#define GL_SAMPLER_2D                     0x8B5E
+#define GL_SAMPLER_3D                     0x8B5F
+#define GL_SAMPLER_CUBE                   0x8B60
+#define GL_SAMPLER_1D_SHADOW              0x8B61
+#define GL_SAMPLER_2D_SHADOW              0x8B62
+#define GL_DELETE_STATUS                  0x8B80
+#define GL_COMPILE_STATUS                 0x8B81
+#define GL_LINK_STATUS                    0x8B82
+#define GL_VALIDATE_STATUS                0x8B83
+#define GL_INFO_LOG_LENGTH                0x8B84
+#define GL_ATTACHED_SHADERS               0x8B85
+#define GL_ACTIVE_UNIFORMS                0x8B86
+#define GL_ACTIVE_UNIFORM_MAX_LENGTH      0x8B87
+#define GL_SHADER_SOURCE_LENGTH           0x8B88
+#define GL_ACTIVE_ATTRIBUTES              0x8B89
+#define GL_ACTIVE_ATTRIBUTE_MAX_LENGTH    0x8B8A
+#define GL_FRAGMENT_SHADER_DERIVATIVE_HINT 0x8B8B
+#define GL_SHADING_LANGUAGE_VERSION       0x8B8C
+#define GL_CURRENT_PROGRAM                0x8B8D
+#define GL_POINT_SPRITE_COORD_ORIGIN      0x8CA0
+#define GL_LOWER_LEFT                     0x8CA1
+#define GL_UPPER_LEFT                     0x8CA2
+#define GL_STENCIL_BACK_REF               0x8CA3
+#define GL_STENCIL_BACK_VALUE_MASK        0x8CA4
+#define GL_STENCIL_BACK_WRITEMASK         0x8CA5
+#endif
+
 #ifndef GL_ARB_multitexture
 #ifndef GL_ARB_multitexture
 #define GL_TEXTURE0_ARB                   0x84C0
 #define GL_TEXTURE0_ARB                   0x84C0
 #define GL_TEXTURE1_ARB                   0x84C1
 #define GL_TEXTURE1_ARB                   0x84C1
@@ -754,6 +835,14 @@ extern "C" {
 #define GL_FLOAT_MAT2_ARB                 0x8B5A
 #define GL_FLOAT_MAT2_ARB                 0x8B5A
 #define GL_FLOAT_MAT3_ARB                 0x8B5B
 #define GL_FLOAT_MAT3_ARB                 0x8B5B
 #define GL_FLOAT_MAT4_ARB                 0x8B5C
 #define GL_FLOAT_MAT4_ARB                 0x8B5C
+#define GL_SAMPLER_1D_ARB                 0x8B5D
+#define GL_SAMPLER_2D_ARB                 0x8B5E
+#define GL_SAMPLER_3D_ARB                 0x8B5F
+#define GL_SAMPLER_CUBE_ARB               0x8B60
+#define GL_SAMPLER_1D_SHADOW_ARB          0x8B61
+#define GL_SAMPLER_2D_SHADOW_ARB          0x8B62
+#define GL_SAMPLER_2D_RECT_ARB            0x8B63
+#define GL_SAMPLER_2D_RECT_SHADOW_ARB     0x8B64
 #define GL_OBJECT_DELETE_STATUS_ARB       0x8B80
 #define GL_OBJECT_DELETE_STATUS_ARB       0x8B80
 #define GL_OBJECT_COMPILE_STATUS_ARB      0x8B81
 #define GL_OBJECT_COMPILE_STATUS_ARB      0x8B81
 #define GL_OBJECT_LINK_STATUS_ARB         0x8B82
 #define GL_OBJECT_LINK_STATUS_ARB         0x8B82
@@ -778,9 +867,11 @@ extern "C" {
 #ifndef GL_ARB_fragment_shader
 #ifndef GL_ARB_fragment_shader
 #define GL_FRAGMENT_SHADER_ARB            0x8B30
 #define GL_FRAGMENT_SHADER_ARB            0x8B30
 #define GL_MAX_FRAGMENT_UNIFORM_COMPONENTS_ARB 0x8B49
 #define GL_MAX_FRAGMENT_UNIFORM_COMPONENTS_ARB 0x8B49
+#define GL_FRAGMENT_SHADER_DERIVATIVE_HINT_ARB 0x8B8B
 #endif
 #endif
 
 
 #ifndef GL_ARB_shading_language_100
 #ifndef GL_ARB_shading_language_100
+#define GL_SHADING_LANGUAGE_VERSION_ARB   0x8B8C
 #endif
 #endif
 
 
 #ifndef GL_ARB_texture_non_power_of_two
 #ifndef GL_ARB_texture_non_power_of_two
@@ -791,6 +882,78 @@ extern "C" {
 #define GL_COORD_REPLACE_ARB              0x8862
 #define GL_COORD_REPLACE_ARB              0x8862
 #endif
 #endif
 
 
+#ifndef GL_ARB_fragment_program_shadow
+#endif
+
+#ifndef GL_ARB_draw_buffers
+#define GL_MAX_DRAW_BUFFERS_ARB           0x8824
+#define GL_DRAW_BUFFER0_ARB               0x8825
+#define GL_DRAW_BUFFER1_ARB               0x8826
+#define GL_DRAW_BUFFER2_ARB               0x8827
+#define GL_DRAW_BUFFER3_ARB               0x8828
+#define GL_DRAW_BUFFER4_ARB               0x8829
+#define GL_DRAW_BUFFER5_ARB               0x882A
+#define GL_DRAW_BUFFER6_ARB               0x882B
+#define GL_DRAW_BUFFER7_ARB               0x882C
+#define GL_DRAW_BUFFER8_ARB               0x882D
+#define GL_DRAW_BUFFER9_ARB               0x882E
+#define GL_DRAW_BUFFER10_ARB              0x882F
+#define GL_DRAW_BUFFER11_ARB              0x8830
+#define GL_DRAW_BUFFER12_ARB              0x8831
+#define GL_DRAW_BUFFER13_ARB              0x8832
+#define GL_DRAW_BUFFER14_ARB              0x8833
+#define GL_DRAW_BUFFER15_ARB              0x8834
+#endif
+
+#ifndef GL_ARB_texture_rectangle
+#define GL_TEXTURE_RECTANGLE_ARB          0x84F5
+#define GL_TEXTURE_BINDING_RECTANGLE_ARB  0x84F6
+#define GL_PROXY_TEXTURE_RECTANGLE_ARB    0x84F7
+#define GL_MAX_RECTANGLE_TEXTURE_SIZE_ARB 0x84F8
+#endif
+
+#ifndef GL_ARB_color_buffer_float
+#define GL_RGBA_FLOAT_MODE_ARB            0x8820
+#define GL_CLAMP_VERTEX_COLOR_ARB         0x891A
+#define GL_CLAMP_FRAGMENT_COLOR_ARB       0x891B
+#define GL_CLAMP_READ_COLOR_ARB           0x891C
+#define GL_FIXED_ONLY_ARB                 0x891D
+#endif
+
+#ifndef GL_ARB_half_float_pixel
+#define GL_HALF_FLOAT_ARB                 0x140B
+#endif
+
+#ifndef GL_ARB_texture_float
+#define GL_TEXTURE_RED_TYPE_ARB           0x8C10
+#define GL_TEXTURE_GREEN_TYPE_ARB         0x8C11
+#define GL_TEXTURE_BLUE_TYPE_ARB          0x8C12
+#define GL_TEXTURE_ALPHA_TYPE_ARB         0x8C13
+#define GL_TEXTURE_LUMINANCE_TYPE_ARB     0x8C14
+#define GL_TEXTURE_INTENSITY_TYPE_ARB     0x8C15
+#define GL_TEXTURE_DEPTH_TYPE_ARB         0x8C16
+#define GL_UNSIGNED_NORMALIZED_ARB        0x8C17
+#define GL_RGBA32F_ARB                    0x8814
+#define GL_RGB32F_ARB                     0x8815
+#define GL_ALPHA32F_ARB                   0x8816
+#define GL_INTENSITY32F_ARB               0x8817
+#define GL_LUMINANCE32F_ARB               0x8818
+#define GL_LUMINANCE_ALPHA32F_ARB         0x8819
+#define GL_RGBA16F_ARB                    0x881A
+#define GL_RGB16F_ARB                     0x881B
+#define GL_ALPHA16F_ARB                   0x881C
+#define GL_INTENSITY16F_ARB               0x881D
+#define GL_LUMINANCE16F_ARB               0x881E
+#define GL_LUMINANCE_ALPHA16F_ARB         0x881F
+#endif
+
+#ifndef GL_ARB_pixel_buffer_object
+#define GL_PIXEL_PACK_BUFFER_ARB          0x88EB
+#define GL_PIXEL_UNPACK_BUFFER_ARB        0x88EC
+#define GL_PIXEL_PACK_BUFFER_BINDING_ARB  0x88ED
+#define GL_PIXEL_UNPACK_BUFFER_BINDING_ARB 0x88EF
+#endif
+
 #ifndef GL_EXT_abgr
 #ifndef GL_EXT_abgr
 #define GL_ABGR_EXT                       0x8000
 #define GL_ABGR_EXT                       0x8000
 #endif
 #endif
@@ -1121,6 +1284,10 @@ extern "C" {
 #define GL_CLAMP_TO_EDGE_SGIS             0x812F
 #define GL_CLAMP_TO_EDGE_SGIS             0x812F
 #endif
 #endif
 
 
+#ifndef GL_SGIS_texture_border_clamp
+#define GL_CLAMP_TO_BORDER_SGIS           0x812D
+#endif
+
 #ifndef GL_EXT_blend_minmax
 #ifndef GL_EXT_blend_minmax
 #define GL_FUNC_ADD_EXT                   0x8006
 #define GL_FUNC_ADD_EXT                   0x8006
 #define GL_MIN_EXT                        0x8007
 #define GL_MIN_EXT                        0x8007
@@ -2664,6 +2831,11 @@ extern "C" {
 #define GL_DRAW_BUFFER15_ATI              0x8834
 #define GL_DRAW_BUFFER15_ATI              0x8834
 #endif
 #endif
 
 
+#ifndef GL_ATI_pixel_format_float
+#define GL_TYPE_RGBA_FLOAT_ATI            0x8820
+#define GL_COLOR_CLEAR_UNCLAMPED_VALUE_ATI 0x8835
+#endif
+
 #ifndef GL_ATI_texture_env_combine3
 #ifndef GL_ATI_texture_env_combine3
 #define GL_MODULATE_ADD_ATI               0x8744
 #define GL_MODULATE_ADD_ATI               0x8744
 #define GL_MODULATE_SIGNED_ADD_ATI        0x8745
 #define GL_MODULATE_SIGNED_ADD_ATI        0x8745
@@ -2750,6 +2922,11 @@ extern "C" {
 #ifndef GL_ATI_vertex_attrib_array_object
 #ifndef GL_ATI_vertex_attrib_array_object
 #endif
 #endif
 
 
+#ifndef GL_OES_read_format
+#define GL_IMPLEMENTATION_COLOR_READ_TYPE_OES 0x8B9A
+#define GL_IMPLEMENTATION_COLOR_READ_FORMAT_OES 0x8B9B
+#endif
+
 #ifndef GL_EXT_depth_bounds_test
 #ifndef GL_EXT_depth_bounds_test
 #define GL_DEPTH_BOUNDS_TEST_EXT          0x8890
 #define GL_DEPTH_BOUNDS_TEST_EXT          0x8890
 #define GL_DEPTH_BOUNDS_EXT               0x8891
 #define GL_DEPTH_BOUNDS_EXT               0x8891
@@ -2776,10 +2953,100 @@ extern "C" {
 #define GL_YCBCR_MESA                     0x8757
 #define GL_YCBCR_MESA                     0x8757
 #endif
 #endif
 
 
+#ifndef GL_EXT_pixel_buffer_object
+#define GL_PIXEL_PACK_BUFFER_EXT          0x88EB
+#define GL_PIXEL_UNPACK_BUFFER_EXT        0x88EC
+#define GL_PIXEL_PACK_BUFFER_BINDING_EXT  0x88ED
+#define GL_PIXEL_UNPACK_BUFFER_BINDING_EXT 0x88EF
+#endif
+
+#ifndef GL_NV_fragment_program_option
+#endif
+
+#ifndef GL_NV_fragment_program2
+#define GL_MAX_PROGRAM_EXEC_INSTRUCTIONS_NV 0x88F4
+#define GL_MAX_PROGRAM_CALL_DEPTH_NV      0x88F5
+#define GL_MAX_PROGRAM_IF_DEPTH_NV        0x88F6
+#define GL_MAX_PROGRAM_LOOP_DEPTH_NV      0x88F7
+#define GL_MAX_PROGRAM_LOOP_COUNT_NV      0x88F8
+#endif
+
+#ifndef GL_NV_vertex_program2_option
+/* reuse GL_MAX_PROGRAM_EXEC_INSTRUCTIONS_NV */
+/* reuse GL_MAX_PROGRAM_CALL_DEPTH_NV */
+#endif
+
+#ifndef GL_NV_vertex_program3
+/* reuse GL_MAX_VERTEX_TEXTURE_IMAGE_UNITS_ARB */
+#endif
+
+#ifndef GL_EXT_framebuffer_object
+#define GL_INVALID_FRAMEBUFFER_OPERATION_EXT 0x0506
+#define GL_MAX_RENDERBUFFER_SIZE_EXT      0x84E8
+#define GL_FRAMEBUFFER_BINDING_EXT        0x8CA6
+#define GL_RENDERBUFFER_BINDING_EXT       0x8CA7
+#define GL_FRAMEBUFFER_ATTACHMENT_OBJECT_TYPE_EXT 0x8CD0
+#define GL_FRAMEBUFFER_ATTACHMENT_OBJECT_NAME_EXT 0x8CD1
+#define GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_LEVEL_EXT 0x8CD2
+#define GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_CUBE_MAP_FACE_EXT 0x8CD3
+#define GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_3D_ZOFFSET_EXT 0x8CD4
+#define GL_FRAMEBUFFER_COMPLETE_EXT       0x8CD5
+#define GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT_EXT 0x8CD6
+#define GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT_EXT 0x8CD7
+#define GL_FRAMEBUFFER_INCOMPLETE_DUPLICATE_ATTACHMENT_EXT 0x8CD8
+#define GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS_EXT 0x8CD9
+#define GL_FRAMEBUFFER_INCOMPLETE_FORMATS_EXT 0x8CDA
+#define GL_FRAMEBUFFER_INCOMPLETE_DRAW_BUFFER_EXT 0x8CDB
+#define GL_FRAMEBUFFER_INCOMPLETE_READ_BUFFER_EXT 0x8CDC
+#define GL_FRAMEBUFFER_UNSUPPORTED_EXT    0x8CDD
+#define GL_MAX_COLOR_ATTACHMENTS_EXT      0x8CDF
+#define GL_COLOR_ATTACHMENT0_EXT          0x8CE0
+#define GL_COLOR_ATTACHMENT1_EXT          0x8CE1
+#define GL_COLOR_ATTACHMENT2_EXT          0x8CE2
+#define GL_COLOR_ATTACHMENT3_EXT          0x8CE3
+#define GL_COLOR_ATTACHMENT4_EXT          0x8CE4
+#define GL_COLOR_ATTACHMENT5_EXT          0x8CE5
+#define GL_COLOR_ATTACHMENT6_EXT          0x8CE6
+#define GL_COLOR_ATTACHMENT7_EXT          0x8CE7
+#define GL_COLOR_ATTACHMENT8_EXT          0x8CE8
+#define GL_COLOR_ATTACHMENT9_EXT          0x8CE9
+#define GL_COLOR_ATTACHMENT10_EXT         0x8CEA
+#define GL_COLOR_ATTACHMENT11_EXT         0x8CEB
+#define GL_COLOR_ATTACHMENT12_EXT         0x8CEC
+#define GL_COLOR_ATTACHMENT13_EXT         0x8CED
+#define GL_COLOR_ATTACHMENT14_EXT         0x8CEE
+#define GL_COLOR_ATTACHMENT15_EXT         0x8CEF
+#define GL_DEPTH_ATTACHMENT_EXT           0x8D00
+#define GL_STENCIL_ATTACHMENT_EXT         0x8D20
+#define GL_FRAMEBUFFER_EXT                0x8D40
+#define GL_RENDERBUFFER_EXT               0x8D41
+#define GL_RENDERBUFFER_WIDTH_EXT         0x8D42
+#define GL_RENDERBUFFER_HEIGHT_EXT        0x8D43
+#define GL_RENDERBUFFER_INTERNAL_FORMAT_EXT 0x8D44
+#define GL_STENCIL_INDEX1_EXT             0x8D46
+#define GL_STENCIL_INDEX4_EXT             0x8D47
+#define GL_STENCIL_INDEX8_EXT             0x8D48
+#define GL_STENCIL_INDEX16_EXT            0x8D49
+#define GL_RENDERBUFFER_RED_SIZE_EXT      0x8D50
+#define GL_RENDERBUFFER_GREEN_SIZE_EXT    0x8D51
+#define GL_RENDERBUFFER_BLUE_SIZE_EXT     0x8D52
+#define GL_RENDERBUFFER_ALPHA_SIZE_EXT    0x8D53
+#define GL_RENDERBUFFER_DEPTH_SIZE_EXT    0x8D54
+#define GL_RENDERBUFFER_STENCIL_SIZE_EXT  0x8D55
+#endif
+
+#ifndef GL_GREMEDY_string_marker
+#endif
+
 
 
 /*************************************************************/
 /*************************************************************/
 
 
 #include <stddef.h>
 #include <stddef.h>
+#ifndef GL_VERSION_2_0
+/* GL type for program/shader text */
+typedef char GLchar;			/* native character */
+#endif
+
 #ifndef GL_VERSION_1_5
 #ifndef GL_VERSION_1_5
 /* GL types for handling large vertex buffer objects */
 /* GL types for handling large vertex buffer objects */
 typedef ptrdiff_t GLintptr;
 typedef ptrdiff_t GLintptr;
@@ -2793,13 +3060,17 @@ typedef ptrdiff_t GLsizeiptrARB;
 #endif
 #endif
 
 
 #ifndef GL_ARB_shader_objects
 #ifndef GL_ARB_shader_objects
-/* GL types for handling shader object handles and characters */
+/* GL types for handling shader object handles and program/shader text */
 typedef char GLcharARB;		/* native character */
 typedef char GLcharARB;		/* native character */
 typedef unsigned int GLhandleARB;	/* shader object handle */
 typedef unsigned int GLhandleARB;	/* shader object handle */
 #endif
 #endif
 
 
+/* GL types for "half" precision (s10e5) float data in host memory */
+#ifndef GL_ARB_half_float_pixel
+typedef unsigned short GLhalfARB;
+#endif
+
 #ifndef GL_NV_half_float
 #ifndef GL_NV_half_float
-/* GL type for representing NVIDIA "half" floating point type in host memory */
 typedef unsigned short GLhalfNV;
 typedef unsigned short GLhalfNV;
 #endif
 #endif
 
 
@@ -3123,6 +3394,198 @@ typedef void (APIENTRYP PFNGLGETBUFFERPARAMETERIVPROC) (GLenum target, GLenum pn
 typedef void (APIENTRYP PFNGLGETBUFFERPOINTERVPROC) (GLenum target, GLenum pname, GLvoid* *params);
 typedef void (APIENTRYP PFNGLGETBUFFERPOINTERVPROC) (GLenum target, GLenum pname, GLvoid* *params);
 #endif
 #endif
 
 
+#ifndef GL_VERSION_2_0
+#define GL_VERSION_2_0 1
+#ifdef GL_GLEXT_PROTOTYPES
+GLAPI void APIENTRY glBlendEquationSeparate (GLenum, GLenum);
+GLAPI void APIENTRY glDrawBuffers (GLsizei, const GLenum *);
+GLAPI void APIENTRY glStencilOpSeparate (GLenum, GLenum, GLenum, GLenum);
+GLAPI void APIENTRY glStencilFuncSeparate (GLenum, GLenum, GLint, GLuint);
+GLAPI void APIENTRY glStencilMaskSeparate (GLenum, GLuint);
+GLAPI void APIENTRY glAttachShader (GLuint, GLuint);
+GLAPI void APIENTRY glBindAttribLocation (GLuint, GLuint, const GLchar *);
+GLAPI void APIENTRY glCompileShader (GLuint);
+GLAPI GLuint APIENTRY glCreateProgram (void);
+GLAPI GLuint APIENTRY glCreateShader (GLenum);
+GLAPI void APIENTRY glDeleteProgram (GLuint);
+GLAPI void APIENTRY glDeleteShader (GLuint);
+GLAPI void APIENTRY glDetachShader (GLuint, GLuint);
+GLAPI void APIENTRY glDisableVertexAttribArray (GLuint);
+GLAPI void APIENTRY glEnableVertexAttribArray (GLuint);
+GLAPI void APIENTRY glGetActiveAttrib (GLuint, GLuint, GLsizei, GLsizei *, GLint *, GLenum *, GLchar *);
+GLAPI void APIENTRY glGetActiveUniform (GLuint, GLuint, GLsizei, GLsizei *, GLint *, GLenum *, GLchar *);
+GLAPI void APIENTRY glGetAttachedShaders (GLuint, GLsizei, GLsizei *, GLuint *);
+GLAPI GLint APIENTRY glGetAttribLocation (GLuint, const GLchar *);
+GLAPI void APIENTRY glGetProgramiv (GLuint, GLenum, GLint *);
+GLAPI void APIENTRY glGetProgramInfoLog (GLuint, GLsizei, GLsizei *, GLchar *);
+GLAPI void APIENTRY glGetShaderiv (GLuint, GLenum, GLint *);
+GLAPI void APIENTRY glGetShaderInfoLog (GLuint, GLsizei, GLsizei *, GLchar *);
+GLAPI void APIENTRY glGetShaderSource (GLuint, GLsizei, GLsizei *, GLchar *);
+GLAPI GLint APIENTRY glGetUniformLocation (GLuint, const GLchar *);
+GLAPI void APIENTRY glGetUniformfv (GLuint, GLint, GLfloat *);
+GLAPI void APIENTRY glGetUniformiv (GLuint, GLint, GLint *);
+GLAPI void APIENTRY glGetVertexAttribdv (GLuint, GLenum, GLdouble *);
+GLAPI void APIENTRY glGetVertexAttribfv (GLuint, GLenum, GLfloat *);
+GLAPI void APIENTRY glGetVertexAttribiv (GLuint, GLenum, GLint *);
+GLAPI void APIENTRY glGetVertexAttribPointerv (GLuint, GLenum, GLvoid* *);
+GLAPI GLboolean APIENTRY glIsProgram (GLuint);
+GLAPI GLboolean APIENTRY glIsShader (GLuint);
+GLAPI void APIENTRY glLinkProgram (GLuint);
+GLAPI void APIENTRY glShaderSource (GLuint, GLsizei, const GLchar* *, const GLint *);
+GLAPI void APIENTRY glUseProgram (GLuint);
+GLAPI void APIENTRY glUniform1f (GLint, GLfloat);
+GLAPI void APIENTRY glUniform2f (GLint, GLfloat, GLfloat);
+GLAPI void APIENTRY glUniform3f (GLint, GLfloat, GLfloat, GLfloat);
+GLAPI void APIENTRY glUniform4f (GLint, GLfloat, GLfloat, GLfloat, GLfloat);
+GLAPI void APIENTRY glUniform1i (GLint, GLint);
+GLAPI void APIENTRY glUniform2i (GLint, GLint, GLint);
+GLAPI void APIENTRY glUniform3i (GLint, GLint, GLint, GLint);
+GLAPI void APIENTRY glUniform4i (GLint, GLint, GLint, GLint, GLint);
+GLAPI void APIENTRY glUniform1fv (GLint, GLsizei, const GLfloat *);
+GLAPI void APIENTRY glUniform2fv (GLint, GLsizei, const GLfloat *);
+GLAPI void APIENTRY glUniform3fv (GLint, GLsizei, const GLfloat *);
+GLAPI void APIENTRY glUniform4fv (GLint, GLsizei, const GLfloat *);
+GLAPI void APIENTRY glUniform1iv (GLint, GLsizei, const GLint *);
+GLAPI void APIENTRY glUniform2iv (GLint, GLsizei, const GLint *);
+GLAPI void APIENTRY glUniform3iv (GLint, GLsizei, const GLint *);
+GLAPI void APIENTRY glUniform4iv (GLint, GLsizei, const GLint *);
+GLAPI void APIENTRY glUniformMatrix2fv (GLint, GLsizei, GLboolean, const GLfloat *);
+GLAPI void APIENTRY glUniformMatrix3fv (GLint, GLsizei, GLboolean, const GLfloat *);
+GLAPI void APIENTRY glUniformMatrix4fv (GLint, GLsizei, GLboolean, const GLfloat *);
+GLAPI void APIENTRY glValidateProgram (GLuint);
+GLAPI void APIENTRY glVertexAttrib1d (GLuint, GLdouble);
+GLAPI void APIENTRY glVertexAttrib1dv (GLuint, const GLdouble *);
+GLAPI void APIENTRY glVertexAttrib1f (GLuint, GLfloat);
+GLAPI void APIENTRY glVertexAttrib1fv (GLuint, const GLfloat *);
+GLAPI void APIENTRY glVertexAttrib1s (GLuint, GLshort);
+GLAPI void APIENTRY glVertexAttrib1sv (GLuint, const GLshort *);
+GLAPI void APIENTRY glVertexAttrib2d (GLuint, GLdouble, GLdouble);
+GLAPI void APIENTRY glVertexAttrib2dv (GLuint, const GLdouble *);
+GLAPI void APIENTRY glVertexAttrib2f (GLuint, GLfloat, GLfloat);
+GLAPI void APIENTRY glVertexAttrib2fv (GLuint, const GLfloat *);
+GLAPI void APIENTRY glVertexAttrib2s (GLuint, GLshort, GLshort);
+GLAPI void APIENTRY glVertexAttrib2sv (GLuint, const GLshort *);
+GLAPI void APIENTRY glVertexAttrib3d (GLuint, GLdouble, GLdouble, GLdouble);
+GLAPI void APIENTRY glVertexAttrib3dv (GLuint, const GLdouble *);
+GLAPI void APIENTRY glVertexAttrib3f (GLuint, GLfloat, GLfloat, GLfloat);
+GLAPI void APIENTRY glVertexAttrib3fv (GLuint, const GLfloat *);
+GLAPI void APIENTRY glVertexAttrib3s (GLuint, GLshort, GLshort, GLshort);
+GLAPI void APIENTRY glVertexAttrib3sv (GLuint, const GLshort *);
+GLAPI void APIENTRY glVertexAttrib4Nbv (GLuint, const GLbyte *);
+GLAPI void APIENTRY glVertexAttrib4Niv (GLuint, const GLint *);
+GLAPI void APIENTRY glVertexAttrib4Nsv (GLuint, const GLshort *);
+GLAPI void APIENTRY glVertexAttrib4Nub (GLuint, GLubyte, GLubyte, GLubyte, GLubyte);
+GLAPI void APIENTRY glVertexAttrib4Nubv (GLuint, const GLubyte *);
+GLAPI void APIENTRY glVertexAttrib4Nuiv (GLuint, const GLuint *);
+GLAPI void APIENTRY glVertexAttrib4Nusv (GLuint, const GLushort *);
+GLAPI void APIENTRY glVertexAttrib4bv (GLuint, const GLbyte *);
+GLAPI void APIENTRY glVertexAttrib4d (GLuint, GLdouble, GLdouble, GLdouble, GLdouble);
+GLAPI void APIENTRY glVertexAttrib4dv (GLuint, const GLdouble *);
+GLAPI void APIENTRY glVertexAttrib4f (GLuint, GLfloat, GLfloat, GLfloat, GLfloat);
+GLAPI void APIENTRY glVertexAttrib4fv (GLuint, const GLfloat *);
+GLAPI void APIENTRY glVertexAttrib4iv (GLuint, const GLint *);
+GLAPI void APIENTRY glVertexAttrib4s (GLuint, GLshort, GLshort, GLshort, GLshort);
+GLAPI void APIENTRY glVertexAttrib4sv (GLuint, const GLshort *);
+GLAPI void APIENTRY glVertexAttrib4ubv (GLuint, const GLubyte *);
+GLAPI void APIENTRY glVertexAttrib4uiv (GLuint, const GLuint *);
+GLAPI void APIENTRY glVertexAttrib4usv (GLuint, const GLushort *);
+GLAPI void APIENTRY glVertexAttribPointer (GLuint, GLint, GLenum, GLboolean, GLsizei, const GLvoid *);
+#endif /* GL_GLEXT_PROTOTYPES */
+typedef void (APIENTRYP PFNGLBLENDEQUATIONSEPARATEPROC) (GLenum modeRGB, GLenum modeAlpha);
+typedef void (APIENTRYP PFNGLDRAWBUFFERSPROC) (GLsizei n, const GLenum *bufs);
+typedef void (APIENTRYP PFNGLSTENCILOPSEPARATEPROC) (GLenum face, GLenum sfail, GLenum dpfail, GLenum dppass);
+typedef void (APIENTRYP PFNGLSTENCILFUNCSEPARATEPROC) (GLenum frontfunc, GLenum backfunc, GLint ref, GLuint mask);
+typedef void (APIENTRYP PFNGLSTENCILMASKSEPARATEPROC) (GLenum face, GLuint mask);
+typedef void (APIENTRYP PFNGLATTACHSHADERPROC) (GLuint program, GLuint shader);
+typedef void (APIENTRYP PFNGLBINDATTRIBLOCATIONPROC) (GLuint program, GLuint index, const GLchar *name);
+typedef void (APIENTRYP PFNGLCOMPILESHADERPROC) (GLuint shader);
+typedef GLuint (APIENTRYP PFNGLCREATEPROGRAMPROC) (void);
+typedef GLuint (APIENTRYP PFNGLCREATESHADERPROC) (GLenum type);
+typedef void (APIENTRYP PFNGLDELETEPROGRAMPROC) (GLuint program);
+typedef void (APIENTRYP PFNGLDELETESHADERPROC) (GLuint shader);
+typedef void (APIENTRYP PFNGLDETACHSHADERPROC) (GLuint program, GLuint shader);
+typedef void (APIENTRYP PFNGLDISABLEVERTEXATTRIBARRAYPROC) (GLuint index);
+typedef void (APIENTRYP PFNGLENABLEVERTEXATTRIBARRAYPROC) (GLuint index);
+typedef void (APIENTRYP PFNGLGETACTIVEATTRIBPROC) (GLuint program, GLuint index, GLsizei bufSize, GLsizei *length, GLint *size, GLenum *type, GLchar *name);
+typedef void (APIENTRYP PFNGLGETACTIVEUNIFORMPROC) (GLuint program, GLuint index, GLsizei bufSize, GLsizei *length, GLint *size, GLenum *type, GLchar *name);
+typedef void (APIENTRYP PFNGLGETATTACHEDSHADERSPROC) (GLuint program, GLsizei maxCount, GLsizei *count, GLuint *obj);
+typedef GLint (APIENTRYP PFNGLGETATTRIBLOCATIONPROC) (GLuint program, const GLchar *name);
+typedef void (APIENTRYP PFNGLGETPROGRAMIVPROC) (GLuint program, GLenum pname, GLint *params);
+typedef void (APIENTRYP PFNGLGETPROGRAMINFOLOGPROC) (GLuint program, GLsizei bufSize, GLsizei *length, GLchar *infoLog);
+typedef void (APIENTRYP PFNGLGETSHADERIVPROC) (GLuint shader, GLenum pname, GLint *params);
+typedef void (APIENTRYP PFNGLGETSHADERINFOLOGPROC) (GLuint shader, GLsizei bufSize, GLsizei *length, GLchar *infoLog);
+typedef void (APIENTRYP PFNGLGETSHADERSOURCEPROC) (GLuint shader, GLsizei bufSize, GLsizei *length, GLchar *source);
+typedef GLint (APIENTRYP PFNGLGETUNIFORMLOCATIONPROC) (GLuint program, const GLchar *name);
+typedef void (APIENTRYP PFNGLGETUNIFORMFVPROC) (GLuint program, GLint location, GLfloat *params);
+typedef void (APIENTRYP PFNGLGETUNIFORMIVPROC) (GLuint program, GLint location, GLint *params);
+typedef void (APIENTRYP PFNGLGETVERTEXATTRIBDVPROC) (GLuint index, GLenum pname, GLdouble *params);
+typedef void (APIENTRYP PFNGLGETVERTEXATTRIBFVPROC) (GLuint index, GLenum pname, GLfloat *params);
+typedef void (APIENTRYP PFNGLGETVERTEXATTRIBIVPROC) (GLuint index, GLenum pname, GLint *params);
+typedef void (APIENTRYP PFNGLGETVERTEXATTRIBPOINTERVPROC) (GLuint index, GLenum pname, GLvoid* *pointer);
+typedef GLboolean (APIENTRYP PFNGLISPROGRAMPROC) (GLuint program);
+typedef GLboolean (APIENTRYP PFNGLISSHADERPROC) (GLuint shader);
+typedef void (APIENTRYP PFNGLLINKPROGRAMPROC) (GLuint program);
+typedef void (APIENTRYP PFNGLSHADERSOURCEPROC) (GLuint shader, GLsizei count, const GLchar* *string, const GLint *length);
+typedef void (APIENTRYP PFNGLUSEPROGRAMPROC) (GLuint program);
+typedef void (APIENTRYP PFNGLUNIFORM1FPROC) (GLint location, GLfloat v0);
+typedef void (APIENTRYP PFNGLUNIFORM2FPROC) (GLint location, GLfloat v0, GLfloat v1);
+typedef void (APIENTRYP PFNGLUNIFORM3FPROC) (GLint location, GLfloat v0, GLfloat v1, GLfloat v2);
+typedef void (APIENTRYP PFNGLUNIFORM4FPROC) (GLint location, GLfloat v0, GLfloat v1, GLfloat v2, GLfloat v3);
+typedef void (APIENTRYP PFNGLUNIFORM1IPROC) (GLint location, GLint v0);
+typedef void (APIENTRYP PFNGLUNIFORM2IPROC) (GLint location, GLint v0, GLint v1);
+typedef void (APIENTRYP PFNGLUNIFORM3IPROC) (GLint location, GLint v0, GLint v1, GLint v2);
+typedef void (APIENTRYP PFNGLUNIFORM4IPROC) (GLint location, GLint v0, GLint v1, GLint v2, GLint v3);
+typedef void (APIENTRYP PFNGLUNIFORM1FVPROC) (GLint location, GLsizei count, const GLfloat *value);
+typedef void (APIENTRYP PFNGLUNIFORM2FVPROC) (GLint location, GLsizei count, const GLfloat *value);
+typedef void (APIENTRYP PFNGLUNIFORM3FVPROC) (GLint location, GLsizei count, const GLfloat *value);
+typedef void (APIENTRYP PFNGLUNIFORM4FVPROC) (GLint location, GLsizei count, const GLfloat *value);
+typedef void (APIENTRYP PFNGLUNIFORM1IVPROC) (GLint location, GLsizei count, const GLint *value);
+typedef void (APIENTRYP PFNGLUNIFORM2IVPROC) (GLint location, GLsizei count, const GLint *value);
+typedef void (APIENTRYP PFNGLUNIFORM3IVPROC) (GLint location, GLsizei count, const GLint *value);
+typedef void (APIENTRYP PFNGLUNIFORM4IVPROC) (GLint location, GLsizei count, const GLint *value);
+typedef void (APIENTRYP PFNGLUNIFORMMATRIX2FVPROC) (GLint location, GLsizei count, GLboolean transpose, const GLfloat *value);
+typedef void (APIENTRYP PFNGLUNIFORMMATRIX3FVPROC) (GLint location, GLsizei count, GLboolean transpose, const GLfloat *value);
+typedef void (APIENTRYP PFNGLUNIFORMMATRIX4FVPROC) (GLint location, GLsizei count, GLboolean transpose, const GLfloat *value);
+typedef void (APIENTRYP PFNGLVALIDATEPROGRAMPROC) (GLuint program);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB1DPROC) (GLuint index, GLdouble x);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB1DVPROC) (GLuint index, const GLdouble *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB1FPROC) (GLuint index, GLfloat x);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB1FVPROC) (GLuint index, const GLfloat *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB1SPROC) (GLuint index, GLshort x);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB1SVPROC) (GLuint index, const GLshort *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB2DPROC) (GLuint index, GLdouble x, GLdouble y);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB2DVPROC) (GLuint index, const GLdouble *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB2FPROC) (GLuint index, GLfloat x, GLfloat y);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB2FVPROC) (GLuint index, const GLfloat *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB2SPROC) (GLuint index, GLshort x, GLshort y);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB2SVPROC) (GLuint index, const GLshort *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB3DPROC) (GLuint index, GLdouble x, GLdouble y, GLdouble z);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB3DVPROC) (GLuint index, const GLdouble *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB3FPROC) (GLuint index, GLfloat x, GLfloat y, GLfloat z);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB3FVPROC) (GLuint index, const GLfloat *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB3SPROC) (GLuint index, GLshort x, GLshort y, GLshort z);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB3SVPROC) (GLuint index, const GLshort *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4NBVPROC) (GLuint index, const GLbyte *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4NIVPROC) (GLuint index, const GLint *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4NSVPROC) (GLuint index, const GLshort *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4NUBPROC) (GLuint index, GLubyte x, GLubyte y, GLubyte z, GLubyte w);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4NUBVPROC) (GLuint index, const GLubyte *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4NUIVPROC) (GLuint index, const GLuint *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4NUSVPROC) (GLuint index, const GLushort *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4BVPROC) (GLuint index, const GLbyte *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4DPROC) (GLuint index, GLdouble x, GLdouble y, GLdouble z, GLdouble w);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4DVPROC) (GLuint index, const GLdouble *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4FPROC) (GLuint index, GLfloat x, GLfloat y, GLfloat z, GLfloat w);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4FVPROC) (GLuint index, const GLfloat *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4IVPROC) (GLuint index, const GLint *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4SPROC) (GLuint index, GLshort x, GLshort y, GLshort z, GLshort w);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4SVPROC) (GLuint index, const GLshort *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4UBVPROC) (GLuint index, const GLubyte *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4UIVPROC) (GLuint index, const GLuint *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIB4USVPROC) (GLuint index, const GLushort *v);
+typedef void (APIENTRYP PFNGLVERTEXATTRIBPOINTERPROC) (GLuint index, GLint size, GLenum type, GLboolean normalized, GLsizei stride, const GLvoid *pointer);
+#endif
+
 #ifndef GL_ARB_multitexture
 #ifndef GL_ARB_multitexture
 #define GL_ARB_multitexture 1
 #define GL_ARB_multitexture 1
 #ifdef GL_GLEXT_PROTOTYPES
 #ifdef GL_GLEXT_PROTOTYPES
@@ -3315,8 +3778,8 @@ typedef void (APIENTRYP PFNGLMATRIXINDEXPOINTERARBPROC) (GLint size, GLenum type
 #define GL_ARB_texture_env_dot3 1
 #define GL_ARB_texture_env_dot3 1
 #endif
 #endif
 
 
-#ifndef GL_ARB_texture_mirror_repeat
-#define GL_ARB_texture_mirror_repeat 1
+#ifndef GL_ARB_texture_mirrored_repeat
+#define GL_ARB_texture_mirrored_repeat 1
 #endif
 #endif
 
 
 #ifndef GL_ARB_depth_texture
 #ifndef GL_ARB_depth_texture
@@ -3666,6 +4129,42 @@ typedef GLint (APIENTRYP PFNGLGETATTRIBLOCATIONARBPROC) (GLhandleARB programObj,
 #define GL_ARB_point_sprite 1
 #define GL_ARB_point_sprite 1
 #endif
 #endif
 
 
+#ifndef GL_ARB_fragment_program_shadow
+#define GL_ARB_fragment_program_shadow 1
+#endif
+
+#ifndef GL_ARB_draw_buffers
+#define GL_ARB_draw_buffers 1
+#ifdef GL_GLEXT_PROTOTYPES
+GLAPI void APIENTRY glDrawBuffersARB (GLsizei, const GLenum *);
+#endif /* GL_GLEXT_PROTOTYPES */
+typedef void (APIENTRYP PFNGLDRAWBUFFERSARBPROC) (GLsizei n, const GLenum *bufs);
+#endif
+
+#ifndef GL_ARB_texture_rectangle
+#define GL_ARB_texture_rectangle 1
+#endif
+
+#ifndef GL_ARB_color_buffer_float
+#define GL_ARB_color_buffer_float 1
+#ifdef GL_GLEXT_PROTOTYPES
+GLAPI void APIENTRY glClampColorARB (GLenum, GLenum);
+#endif /* GL_GLEXT_PROTOTYPES */
+typedef void (APIENTRYP PFNGLCLAMPCOLORARBPROC) (GLenum target, GLenum clamp);
+#endif
+
+#ifndef GL_ARB_half_float_pixel
+#define GL_ARB_half_float_pixel 1
+#endif
+
+#ifndef GL_ARB_texture_float
+#define GL_ARB_texture_float 1
+#endif
+
+#ifndef GL_ARB_pixel_buffer_object
+#define GL_ARB_pixel_buffer_object 1
+#endif
+
 #ifndef GL_EXT_abgr
 #ifndef GL_EXT_abgr
 #define GL_EXT_abgr 1
 #define GL_EXT_abgr 1
 #endif
 #endif
@@ -5692,6 +6191,13 @@ GLAPI void APIENTRY glDrawBuffersATI (GLsizei, const GLenum *);
 typedef void (APIENTRYP PFNGLDRAWBUFFERSATIPROC) (GLsizei n, const GLenum *bufs);
 typedef void (APIENTRYP PFNGLDRAWBUFFERSATIPROC) (GLsizei n, const GLenum *bufs);
 #endif
 #endif
 
 
+#ifndef GL_ATI_pixel_format_float
+#define GL_ATI_pixel_format_float 1
+/* This is really a WGL extension, but defines some associated GL enums.
+ * ATI does not export "GL_ATI_pixel_format_float" in the GL_EXTENSIONS string.
+ */
+#endif
+
 #ifndef GL_ATI_texture_env_combine3
 #ifndef GL_ATI_texture_env_combine3
 #define GL_ATI_texture_env_combine3 1
 #define GL_ATI_texture_env_combine3 1
 #endif
 #endif
@@ -5881,6 +6387,10 @@ typedef void (APIENTRYP PFNGLGETVERTEXATTRIBARRAYOBJECTFVATIPROC) (GLuint index,
 typedef void (APIENTRYP PFNGLGETVERTEXATTRIBARRAYOBJECTIVATIPROC) (GLuint index, GLenum pname, GLint *params);
 typedef void (APIENTRYP PFNGLGETVERTEXATTRIBARRAYOBJECTIVATIPROC) (GLuint index, GLenum pname, GLint *params);
 #endif
 #endif
 
 
+#ifndef GL_OES_read_format
+#define GL_OES_read_format 1
+#endif
+
 #ifndef GL_EXT_depth_bounds_test
 #ifndef GL_EXT_depth_bounds_test
 #define GL_EXT_depth_bounds_test 1
 #define GL_EXT_depth_bounds_test 1
 #ifdef GL_GLEXT_PROTOTYPES
 #ifdef GL_GLEXT_PROTOTYPES
@@ -5909,6 +6419,74 @@ typedef void (APIENTRYP PFNGLBLENDEQUATIONSEPARATEEXTPROC) (GLenum modeRGB, GLen
 #define GL_MESA_ycbcr_texture 1
 #define GL_MESA_ycbcr_texture 1
 #endif
 #endif
 
 
+#ifndef GL_EXT_pixel_buffer_object
+#define GL_EXT_pixel_buffer_object 1
+#endif
+
+#ifndef GL_NV_fragment_program_option
+#define GL_NV_fragment_program_option 1
+#endif
+
+#ifndef GL_NV_fragment_program2
+#define GL_NV_fragment_program2 1
+#endif
+
+#ifndef GL_NV_vertex_program2_option
+#define GL_NV_vertex_program2_option 1
+#endif
+
+#ifndef GL_NV_vertex_program3
+#define GL_NV_vertex_program3 1
+#endif
+
+#ifndef GL_EXT_framebuffer_object
+#define GL_EXT_framebuffer_object 1
+#ifdef GL_GLEXT_PROTOTYPES
+GLAPI GLboolean APIENTRY glIsRenderbufferEXT (GLuint);
+GLAPI void APIENTRY glBindRenderbufferEXT (GLenum, GLuint);
+GLAPI void APIENTRY glDeleteRenderbuffersEXT (GLsizei, const GLuint *);
+GLAPI void APIENTRY glGenRenderbuffersEXT (GLsizei, GLuint *);
+GLAPI void APIENTRY glRenderbufferStorageEXT (GLenum, GLenum, GLsizei, GLsizei);
+GLAPI void APIENTRY glGetRenderbufferParameterivEXT (GLenum, GLenum, GLint *);
+GLAPI GLboolean APIENTRY glIsFramebufferEXT (GLuint);
+GLAPI void APIENTRY glBindFramebufferEXT (GLenum, GLuint);
+GLAPI void APIENTRY glDeleteFramebuffersEXT (GLsizei, const GLuint *);
+GLAPI void APIENTRY glGenFramebuffersEXT (GLsizei, GLuint *);
+GLAPI GLenum APIENTRY glCheckFramebufferStatusEXT (GLenum);
+GLAPI void APIENTRY glFramebufferTexture1DEXT (GLenum, GLenum, GLenum, GLuint, GLint);
+GLAPI void APIENTRY glFramebufferTexture2DEXT (GLenum, GLenum, GLenum, GLuint, GLint);
+GLAPI void APIENTRY glFramebufferTexture3DEXT (GLenum, GLenum, GLenum, GLuint, GLint, GLint);
+GLAPI void APIENTRY glFramebufferRenderbufferEXT (GLenum, GLenum, GLenum, GLuint);
+GLAPI void APIENTRY glGetFramebufferAttachmentParameterivEXT (GLenum, GLenum, GLenum, GLint *);
+GLAPI void APIENTRY glGenerateMipmapEXT (GLenum);
+#endif /* GL_GLEXT_PROTOTYPES */
+typedef GLboolean (APIENTRYP PFNGLISRENDERBUFFEREXTPROC) (GLuint renderbuffer);
+typedef void (APIENTRYP PFNGLBINDRENDERBUFFEREXTPROC) (GLenum target, GLuint renderbuffer);
+typedef void (APIENTRYP PFNGLDELETERENDERBUFFERSEXTPROC) (GLsizei n, const GLuint *renderbuffers);
+typedef void (APIENTRYP PFNGLGENRENDERBUFFERSEXTPROC) (GLsizei n, GLuint *renderbuffers);
+typedef void (APIENTRYP PFNGLRENDERBUFFERSTORAGEEXTPROC) (GLenum target, GLenum internalformat, GLsizei width, GLsizei height);
+typedef void (APIENTRYP PFNGLGETRENDERBUFFERPARAMETERIVEXTPROC) (GLenum target, GLenum pname, GLint *params);
+typedef GLboolean (APIENTRYP PFNGLISFRAMEBUFFEREXTPROC) (GLuint framebuffer);
+typedef void (APIENTRYP PFNGLBINDFRAMEBUFFEREXTPROC) (GLenum target, GLuint framebuffer);
+typedef void (APIENTRYP PFNGLDELETEFRAMEBUFFERSEXTPROC) (GLsizei n, const GLuint *framebuffers);
+typedef void (APIENTRYP PFNGLGENFRAMEBUFFERSEXTPROC) (GLsizei n, GLuint *framebuffers);
+typedef GLenum (APIENTRYP PFNGLCHECKFRAMEBUFFERSTATUSEXTPROC) (GLenum target);
+typedef void (APIENTRYP PFNGLFRAMEBUFFERTEXTURE1DEXTPROC) (GLenum target, GLenum attachment, GLenum textarget, GLuint texture, GLint level);
+typedef void (APIENTRYP PFNGLFRAMEBUFFERTEXTURE2DEXTPROC) (GLenum target, GLenum attachment, GLenum textarget, GLuint texture, GLint level);
+typedef void (APIENTRYP PFNGLFRAMEBUFFERTEXTURE3DEXTPROC) (GLenum target, GLenum attachment, GLenum textarget, GLuint texture, GLint level, GLint zoffset);
+typedef void (APIENTRYP PFNGLFRAMEBUFFERRENDERBUFFEREXTPROC) (GLenum target, GLenum attachment, GLenum renderbuffertarget, GLuint renderbuffer);
+typedef void (APIENTRYP PFNGLGETFRAMEBUFFERATTACHMENTPARAMETERIVEXTPROC) (GLenum target, GLenum attachment, GLenum pname, GLint *params);
+typedef void (APIENTRYP PFNGLGENERATEMIPMAPEXTPROC) (GLenum target);
+#endif
+
+#ifndef GL_GREMEDY_string_marker
+#define GL_GREMEDY_string_marker 1
+#ifdef GL_GLEXT_PROTOTYPES
+GLAPI void APIENTRY glStringMarkerGREMEDY (GLsizei, const GLvoid *);
+#endif /* GL_GLEXT_PROTOTYPES */
+typedef void (APIENTRYP PFNGLSTRINGMARKERGREMEDYPROC) (GLsizei len, const GLvoid *string);
+#endif
+
 
 
 #ifdef __cplusplus
 #ifdef __cplusplus
 }
 }

+ 4 - 2
panda/src/gobj/texture.h

@@ -289,12 +289,14 @@ public:
 
 
   static PT(Texture) make_texture();
   static PT(Texture) make_texture();
 
 
+public:
+  static int up_to_power_2(int value);
+  static int down_to_power_2(int value);
+
 protected:
 protected:
   virtual void reconsider_dirty();
   virtual void reconsider_dirty();
   virtual void reload_ram_image();
   virtual void reload_ram_image();
 
 
-  static int up_to_power_2(int value);
-  static int down_to_power_2(int value);
   bool reconsider_z_size(int z);
   bool reconsider_z_size(int z);
   bool reconsider_image_properties(int x_size, int y_size, int num_components,
   bool reconsider_image_properties(int x_size, int y_size, int num_components,
 				   ComponentType component_type, int z);
 				   ComponentType component_type, int z);

+ 4 - 5
panda/src/wgldisplay/wglGraphicsBuffer.cxx

@@ -235,13 +235,12 @@ open_buffer() {
     wgldisplay_cat.debug()
     wgldisplay_cat.debug()
       << "Created PBuffer " << _pbuffer << ", DC " << _pbuffer_dc << "\n";
       << "Created PBuffer " << _pbuffer << ", DC " << _pbuffer_dc << "\n";
     switch (_rtm_mode) {
     switch (_rtm_mode) {
-    case RTM_bind_texture:
+    case RTM_bind_or_copy:
       wgldisplay_cat.debug()
       wgldisplay_cat.debug()
         << "pbuffer renders directly to texture.\n";
         << "pbuffer renders directly to texture.\n";
       break;
       break;
 
 
     case RTM_copy_texture:
     case RTM_copy_texture:
-    case RTM_bind_if_possible:
       wgldisplay_cat.debug()
       wgldisplay_cat.debug()
         << "pbuffer copies indirectly into texture.\n";
         << "pbuffer copies indirectly into texture.\n";
       break;
       break;
@@ -288,7 +287,7 @@ make_pbuffer(HDC twindow_dc) {
   if (wglgsg->_supports_pixel_format) {
   if (wglgsg->_supports_pixel_format) {
     bool got_pbuffer_format = false;
     bool got_pbuffer_format = false;
 
 
-    if (_rtm_mode == RTM_bind_if_possible && 
+    if ((_rtm_mode == RTM_bind_or_copy) &&
         wglgsg->_supports_render_texture) {
         wglgsg->_supports_render_texture) {
       // First, try to get a pbuffer format that supports
       // First, try to get a pbuffer format that supports
       // render-to-texture.
       // render-to-texture.
@@ -296,12 +295,12 @@ make_pbuffer(HDC twindow_dc) {
       if (new_pbformat != 0) {
       if (new_pbformat != 0) {
         pbformat = new_pbformat;
         pbformat = new_pbformat;
         got_pbuffer_format = true;
         got_pbuffer_format = true;
-        _rtm_mode = RTM_bind_texture;
       }
       }
     }
     }
 
 
     if (!got_pbuffer_format) {
     if (!got_pbuffer_format) {
       // Failing that, just get a matching pbuffer format.
       // Failing that, just get a matching pbuffer format.
+      _rtm_mode = RTM_copy_texture;
       int new_pbformat = choose_pbuffer_format(twindow_dc, false);
       int new_pbformat = choose_pbuffer_format(twindow_dc, false);
       if (new_pbformat != 0) {
       if (new_pbformat != 0) {
         pbformat = new_pbformat;
         pbformat = new_pbformat;
@@ -323,7 +322,7 @@ make_pbuffer(HDC twindow_dc) {
   int iattrib_list[max_attrib_list];
   int iattrib_list[max_attrib_list];
   int ni = 0;
   int ni = 0;
 
 
-  if (_rtm_mode == RTM_bind_texture) {
+  if (_rtm_mode == RTM_bind_or_copy) {
     nassertr(_texture != (Texture *)NULL, false);
     nassertr(_texture != (Texture *)NULL, false);
 
 
     if (_gsg->get_properties().get_frame_buffer_mode() & FrameBufferProperties::FM_alpha) {
     if (_gsg->get_properties().get_frame_buffer_mode() & FrameBufferProperties::FM_alpha) {