[Cogl] [PATCH 3/3] Support retrieving depth textures from framebuffers

Damien Lespiau damien.lespiau at gmail.com
Wed May 23 10:23:47 PDT 2012


From: Damien Lespiau <damien.lespiau at intel.com>

This commit introduces two new funtions on framebuffers to be able to
retrieve the depth buffer as a texture for further usage, say, to
implement shadow mapping.

The proposed API works as follow:
  * Before the framebuffer is allocated, you can request that a depth
    texture is created with cogl_framebuffer_enable_depth_texture()
  * cogl_framebuffer_get_depth_texture() can then be used to grab a
    CoglTexture
---
 cogl/cogl-bitmap-conversion.c               |    5 +
 cogl/cogl-bitmap-packing.h                  |   10 ++
 cogl/cogl-context.h                         |    3 +
 cogl/cogl-framebuffer-private.h             |    3 +
 cogl/cogl-framebuffer.c                     |  170 +++++++++++++++++++++------
 cogl/cogl-framebuffer.h                     |   42 +++++++
 cogl/cogl-types.h                           |   28 ++++-
 cogl/driver/gl/cogl-gl.c                    |    7 +
 cogl/driver/gl/cogl-texture-driver-gl.c     |   27 +++++
 cogl/driver/gles/cogl-gles.c                |    6 +
 cogl/driver/gles/cogl-texture-driver-gles.c |   27 +++++
 examples/cogl-info.c                        |    6 +
 12 files changed, 289 insertions(+), 45 deletions(-)

diff --git a/cogl/cogl-bitmap-conversion.c b/cogl/cogl-bitmap-conversion.c
index 6a57dbf..6e918da 100644
--- a/cogl/cogl-bitmap-conversion.c
+++ b/cogl/cogl-bitmap-conversion.c
@@ -306,6 +306,11 @@ _cogl_bitmap_needs_short_temp_buffer (CoglPixelFormat format)
      floats */
   switch (format)
     {
+    case COGL_PIXEL_FORMAT_DEPTH_ANY:
+    case COGL_PIXEL_FORMAT_DEPTH_16:
+    case COGL_PIXEL_FORMAT_DEPTH_24:
+    case COGL_PIXEL_FORMAT_DEPTH_32:
+    case COGL_PIXEL_FORMAT_DEPTH_24_STENCIL_8:
     case COGL_PIXEL_FORMAT_ANY:
     case COGL_PIXEL_FORMAT_YUV:
       g_assert_not_reached ();
diff --git a/cogl/cogl-bitmap-packing.h b/cogl/cogl-bitmap-packing.h
index 6c0a985..b12986f 100644
--- a/cogl/cogl-bitmap-packing.h
+++ b/cogl/cogl-bitmap-packing.h
@@ -370,6 +370,11 @@ G_PASTE (_cogl_unpack_, component_type) (CoglPixelFormat format,
     case COGL_PIXEL_FORMAT_ABGR_2101010_PRE:
       G_PASTE (_cogl_unpack_abgr_2101010_, component_type) (src, dst, width);
       break;
+    case COGL_PIXEL_FORMAT_DEPTH_ANY:
+    case COGL_PIXEL_FORMAT_DEPTH_16:
+    case COGL_PIXEL_FORMAT_DEPTH_24:
+    case COGL_PIXEL_FORMAT_DEPTH_32:
+    case COGL_PIXEL_FORMAT_DEPTH_24_STENCIL_8:
     case COGL_PIXEL_FORMAT_ANY:
     case COGL_PIXEL_FORMAT_YUV:
       g_assert_not_reached ();
@@ -711,6 +716,11 @@ G_PASTE (_cogl_pack_, component_type) (CoglPixelFormat format,
     case COGL_PIXEL_FORMAT_ABGR_2101010_PRE:
       G_PASTE (_cogl_pack_abgr_2101010_, component_type) (src, dst, width);
       break;
+    case COGL_PIXEL_FORMAT_DEPTH_ANY:
+    case COGL_PIXEL_FORMAT_DEPTH_16:
+    case COGL_PIXEL_FORMAT_DEPTH_24:
+    case COGL_PIXEL_FORMAT_DEPTH_32:
+    case COGL_PIXEL_FORMAT_DEPTH_24_STENCIL_8:
     case COGL_PIXEL_FORMAT_ANY:
     case COGL_PIXEL_FORMAT_YUV:
       g_assert_not_reached ();
diff --git a/cogl/cogl-context.h b/cogl/cogl-context.h
index e2120d7..f4b1950 100644
--- a/cogl/cogl-context.h
+++ b/cogl/cogl-context.h
@@ -203,6 +203,8 @@ cogl_is_context (void *object);
  * @COGL_FEATURE_ID_SWAP_BUFFERS_EVENT:
  *     Available if the window system supports reporting an event
  *     for swap buffer completions.
+ * @COGL_FEATURE_ID_DEPTH_TEXTURE: Whether #CoglFramebuffer support rendering
+ *     the depth buffer to a texture.
  *
  * All the capabilities that can vary between different GPUs supported
  * by Cogl. Applications that depend on any of these features should explicitly
@@ -230,6 +232,7 @@ typedef enum _CoglFeatureID
   COGL_FEATURE_ID_MAP_BUFFER_FOR_WRITE,
   COGL_FEATURE_ID_MIRRORED_REPEAT,
   COGL_FEATURE_ID_SWAP_BUFFERS_EVENT,
+  COGL_FEATURE_ID_DEPTH_TEXTURE,
 
   /*< private > */
   _COGL_N_FEATURE_IDS
diff --git a/cogl/cogl-framebuffer-private.h b/cogl/cogl-framebuffer-private.h
index 0081a2f..f2643f5 100644
--- a/cogl/cogl-framebuffer-private.h
+++ b/cogl/cogl-framebuffer-private.h
@@ -49,6 +49,7 @@ typedef enum _CoglFramebufferType {
 typedef struct
 {
   CoglSwapChain *swap_chain;
+  gboolean need_depth_texture;
   gboolean need_stencil;
   int samples_per_pixel;
   gboolean swap_throttled;
@@ -166,6 +167,8 @@ struct _CoglOffscreen
   int             texture_level_width;
   int             texture_level_height;
 
+  CoglTexture    *depth_texture;
+
   /* FIXME: _cogl_offscreen_new_to_texture_full should be made to use
    * fb->config to configure if we want a depth or stencil buffer so
    * we can get rid of these flags */
diff --git a/cogl/cogl-framebuffer.c b/cogl/cogl-framebuffer.c
index 30613f7..c219ab4 100644
--- a/cogl/cogl-framebuffer.c
+++ b/cogl/cogl-framebuffer.c
@@ -881,52 +881,125 @@ try_creating_fbo (CoglOffscreen *offscreen,
 
   if (flags & _TRY_DEPTH24_STENCIL8)
     {
-      /* Create a renderbuffer for depth and stenciling */
-      GE (ctx, glGenRenderbuffers (1, &gl_depth_stencil_handle));
-      GE (ctx, glBindRenderbuffer (GL_RENDERBUFFER, gl_depth_stencil_handle));
-      if (n_samples)
-        GE (ctx, glRenderbufferStorageMultisampleIMG (GL_RENDERBUFFER,
-                                                      n_samples,
-                                                      GL_DEPTH24_STENCIL8,
-                                                      width, height));
+      if (fb->config.need_depth_texture)
+        {
+          /* We need a depth texture, so let's attatch a newly created
+           * GL_DEPTH24_STENCIL8 texture to the GL_DEPTH_ATTACHMENT and
+           * GL_STENCIL_ATTACHMENT attachement points */
+          CoglTexture2D *depth_texture;
+          int width, height;
+
+          width = cogl_texture_get_width (offscreen->texture);
+          height = cogl_texture_get_height (offscreen->texture);
+
+          depth_texture =
+            cogl_texture_2d_new_with_size (ctx,
+                                           width, height,
+                                           COGL_PIXEL_FORMAT_DEPTH_24_STENCIL_8,
+                                           NULL);
+
+          cogl_texture_get_gl_texture (COGL_TEXTURE (depth_texture),
+                                       &tex_gl_handle, &tex_gl_target);
+
+          GE (ctx, glFramebufferTexture2D (GL_DRAW_FRAMEBUFFER,
+                                           GL_DEPTH_ATTACHMENT,
+                                           tex_gl_target, tex_gl_handle,
+                                           0));
+          GE (ctx, glFramebufferTexture2D (GL_DRAW_FRAMEBUFFER,
+                                           GL_STENCIL_ATTACHMENT,
+                                           tex_gl_target, tex_gl_handle,
+                                           0));
+
+          offscreen->depth_texture = COGL_TEXTURE (depth_texture);
+          _cogl_texture_associate_framebuffer (offscreen->depth_texture, fb);
+        }
       else
-        GE (ctx, glRenderbufferStorage (GL_RENDERBUFFER, GL_DEPTH24_STENCIL8,
-                                        width, height));
-      GE (ctx, glBindRenderbuffer (GL_RENDERBUFFER, 0));
-      GE (ctx, glFramebufferRenderbuffer (GL_FRAMEBUFFER,
-                                          GL_STENCIL_ATTACHMENT,
-                                          GL_RENDERBUFFER,
-                                          gl_depth_stencil_handle));
-      GE (ctx, glFramebufferRenderbuffer (GL_FRAMEBUFFER,
-                                          GL_DEPTH_ATTACHMENT,
-                                          GL_RENDERBUFFER,
-                                          gl_depth_stencil_handle));
-      offscreen->renderbuffers =
-        g_slist_prepend (offscreen->renderbuffers,
-                         GUINT_TO_POINTER (gl_depth_stencil_handle));
+        {
+          /* renderbuffer for depth and stenciling */
+          GE (ctx, glGenRenderbuffers (1, &gl_depth_stencil_handle));
+          GE (ctx, glBindRenderbuffer (GL_RENDERBUFFER, gl_depth_stencil_handle));
+
+          if (n_samples)
+            GE (ctx, glRenderbufferStorageMultisampleIMG (GL_RENDERBUFFER,
+                                                          n_samples,
+                                                          GL_DEPTH24_STENCIL8,
+                                                          width, height));
+          else
+            GE (ctx, glRenderbufferStorage (GL_RENDERBUFFER,
+                                            GL_DEPTH24_STENCIL8,
+                                            width, height));
+
+          GE (ctx, glBindRenderbuffer (GL_RENDERBUFFER, 0));
+          GE (ctx, glFramebufferRenderbuffer (GL_FRAMEBUFFER,
+                                              GL_STENCIL_ATTACHMENT,
+                                              GL_RENDERBUFFER,
+                                              gl_depth_stencil_handle));
+
+          GE (ctx, glFramebufferRenderbuffer (GL_FRAMEBUFFER,
+                                              GL_DEPTH_ATTACHMENT,
+                                              GL_RENDERBUFFER,
+                                              gl_depth_stencil_handle));
+          offscreen->renderbuffers =
+            g_slist_prepend (offscreen->renderbuffers,
+                             GUINT_TO_POINTER (gl_depth_stencil_handle));
+        }
     }
 
   if (flags & _TRY_DEPTH)
     {
-      GE (ctx, glGenRenderbuffers (1, &gl_depth_handle));
-      GE (ctx, glBindRenderbuffer (GL_RENDERBUFFER, gl_depth_handle));
       /* For now we just ask for GL_DEPTH_COMPONENT16 since this is all that's
        * available under GLES */
-      if (n_samples)
-        GE (ctx, glRenderbufferStorageMultisampleIMG (GL_RENDERBUFFER,
-                                                      n_samples,
-                                                      GL_DEPTH_COMPONENT16,
-                                                      width, height));
+
+      if (fb->config.need_depth_texture)
+        {
+          /* We need a depth texture, so let's attatch a newly created
+           * GL_DEPTH_COMPONENT16 texture to the GL_DEPTH_ATTACHMENT
+           * attachement point */
+          CoglTexture2D *depth_texture;
+          int width, height;
+
+          width = cogl_texture_get_width (offscreen->texture);
+          height = cogl_texture_get_height (offscreen->texture);
+
+          depth_texture =
+            cogl_texture_2d_new_with_size (ctx,
+                                           width, height,
+                                           COGL_PIXEL_FORMAT_DEPTH_16,
+                                           NULL);
+
+          cogl_texture_get_gl_texture (COGL_TEXTURE (depth_texture),
+                                       &tex_gl_handle, &tex_gl_target);
+
+          GE (ctx, glFramebufferTexture2D (GL_DRAW_FRAMEBUFFER,
+                                           GL_DEPTH_ATTACHMENT,
+                                           tex_gl_target, tex_gl_handle,
+                                           0));
+
+          offscreen->depth_texture = COGL_TEXTURE (depth_texture);
+          _cogl_texture_associate_framebuffer (offscreen->depth_texture, fb);
+        }
       else
-        GE (ctx, glRenderbufferStorage (GL_RENDERBUFFER, GL_DEPTH_COMPONENT16,
-                                        width, height));
-      GE (ctx, glBindRenderbuffer (GL_RENDERBUFFER, 0));
-      GE (ctx, glFramebufferRenderbuffer (GL_FRAMEBUFFER,
-                                          GL_DEPTH_ATTACHMENT,
-                                          GL_RENDERBUFFER, gl_depth_handle));
-      offscreen->renderbuffers =
-        g_slist_prepend (offscreen->renderbuffers,
-                         GUINT_TO_POINTER (gl_depth_handle));
+        {
+          /* renderbuffer for depth and stenciling */
+          GE (ctx, glGenRenderbuffers (1, &gl_depth_handle));
+          GE (ctx, glBindRenderbuffer (GL_RENDERBUFFER, gl_depth_handle));
+          if (n_samples)
+            GE (ctx, glRenderbufferStorageMultisampleIMG (GL_RENDERBUFFER,
+                                                          n_samples,
+                                                          GL_DEPTH_COMPONENT16,
+                                                          width, height));
+          else
+            GE (ctx, glRenderbufferStorage (GL_RENDERBUFFER,
+                                            GL_DEPTH_COMPONENT16,
+                                            width, height));
+          GE (ctx, glBindRenderbuffer (GL_RENDERBUFFER, 0));
+          GE (ctx, glFramebufferRenderbuffer (GL_FRAMEBUFFER,
+                                              GL_DEPTH_ATTACHMENT,
+                                              GL_RENDERBUFFER, gl_depth_handle));
+          offscreen->renderbuffers =
+            g_slist_prepend (offscreen->renderbuffers,
+                             GUINT_TO_POINTER (gl_depth_handle));
+        }
     }
 
   if (flags & _TRY_STENCIL)
@@ -1792,6 +1865,27 @@ cogl_framebuffer_get_color_format (CoglFramebuffer *framebuffer)
   return framebuffer->format;
 }
 
+void
+cogl_framebuffer_enable_depth_texture (CoglFramebuffer *framebuffer,
+                                       gboolean         enabled)
+{
+  _COGL_RETURN_IF_FAIL (!framebuffer->allocated);
+
+  framebuffer->config.need_depth_texture = enabled;
+}
+
+CoglTexture *
+cogl_framebuffer_get_depth_texture (CoglFramebuffer *framebuffer)
+{
+  _COGL_RETURN_VAL_IF_FAIL (cogl_is_offscreen (framebuffer),
+                            COGL_INVALID_HANDLE);
+
+  if (!cogl_framebuffer_allocate (framebuffer, NULL))
+    return COGL_INVALID_HANDLE;
+
+  return COGL_OFFSCREEN(framebuffer)->depth_texture;
+}
+
 int
 cogl_framebuffer_get_samples_per_pixel (CoglFramebuffer *framebuffer)
 {
diff --git a/cogl/cogl-framebuffer.h b/cogl/cogl-framebuffer.h
index 07886db..7a568f1 100644
--- a/cogl/cogl-framebuffer.h
+++ b/cogl/cogl-framebuffer.h
@@ -43,6 +43,7 @@
 #include <cogl/cogl-pipeline.h>
 #include <cogl/cogl-indices.h>
 #include <cogl/cogl-bitmap.h>
+#include <cogl/cogl-texture.h>
 
 G_BEGIN_DECLS
 
@@ -774,6 +775,47 @@ CoglPixelFormat
 cogl_framebuffer_get_color_format (CoglFramebuffer *framebuffer);
 
 /**
+ * cogl_framebuffer_enable_depth_texture:
+ * @framebuffer: A #CoglFramebuffer
+ * @enabled: TRUE or FALSE
+ *
+ * If @enabled is #TRUE, the depth buffer used when rendering to @framebuffer
+ * is available as a texture. You can retrieve the texture with
+ * cogl_framebuffer_get_depth_texture().
+ *
+ * <note>It's possible that your GPU does not support depth textures. You
+ * should check the COGL_FEATURE_ID_DEPTH_TEXTURE feature before using this
+ * function.</note>
+ * <note>It's not valid to call this function after the framebuffer has been
+ * allocated as the creation of the depth texture is done at allocation time.
+ * </note>
+ *
+ * Since: 2.0
+ */
+void
+cogl_framebuffer_enable_depth_texture (CoglFramebuffer *framebuffer,
+                                       gboolean         enabled);
+
+/**
+ * cogl_framebuffer_get_depth_texture:
+ * @framebuffer: A #CoglFramebuffer
+ *
+ * Retrieves the depth buffer of @framebuffer as a #CoglTexture. You need to
+ * call cogl_framebuffer_get_depth_texture(fb, TRUE); before using this
+ * function.
+ *
+ * <note>Calling this function implicitely allocates the framebuffer.</note>
+ * <note>The texture returned stays valid as long as the framebuffer stays
+ * valid.</note>
+ *
+ * Returns: (transfer none): the depth texture
+ *
+ * Since: 2.0
+ */
+CoglTexture *
+cogl_framebuffer_get_depth_texture (CoglFramebuffer *framebuffer);
+
+/**
  * cogl_framebuffer_set_samples_per_pixel:
  * @framebuffer: A #CoglFramebuffer framebuffer
  * @samples_per_pixel: The minimum number of samples per pixel
diff --git a/cogl/cogl-types.h b/cogl/cogl-types.h
index 92c5e9a..73dd9bb 100644
--- a/cogl/cogl-types.h
+++ b/cogl/cogl-types.h
@@ -167,18 +167,22 @@ typedef struct _CoglTextureVertex       CoglTextureVertex;
 #define COGL_BGR_BIT            (1 << 5)
 #define COGL_AFIRST_BIT         (1 << 6)
 #define COGL_PREMULT_BIT        (1 << 7)
+#define COGL_DEPTH_BIT          (1 << 8)
+#define COGL_STENCIL_BIT        (1 << 9)
 
 /* XXX: Notes to those adding new formats here...
  *
  * First this diagram outlines how we allocate the 32bits of a
  * CoglPixelFormat currently...
  *
- *                             4 bits for flags
- *                             |--|
+ *                            6 bits for flags
+ *                          |-----|
  *  enum        unused             4 bits for the bytes-per-pixel
  *                                 and component alignment info
- *  |------| |---------------|     |--|
- *  00000000 xxxxxxxx xxxxxxxx PFBA0000
+ *  |------| |-------------|       |--|
+ *  00000000 xxxxxxxx xxxxxxSD PFBA0000
+ *                          ^ stencil
+ *                           ^ depth
  *                             ^ premult
  *                              ^ alpha first
  *                               ^ bgr order
@@ -200,7 +204,7 @@ typedef struct _CoglTextureVertex       CoglTextureVertex;
  * 4-6   = 2 bpp, not aligned (e.g. 565, 4444, 5551)
  * 7     = YUV: undefined bpp, undefined alignment
  * 9     = 2 bpp, aligned
- * 10    = undefined
+ * 10    = depth, aligned (8, 16, 24, 32, 32f)
  * 11    = undefined
  * 12    = 3 bpp, not aligned
  * 13    = 4 bpp, not aligned (e.g. 2101010)
@@ -318,7 +322,14 @@ typedef enum { /*< prefix=COGL_PIXEL_FORMAT >*/
   COGL_PIXEL_FORMAT_RGBA_1010102_PRE = (COGL_PIXEL_FORMAT_RGBA_1010102 | COGL_PREMULT_BIT),
   COGL_PIXEL_FORMAT_BGRA_1010102_PRE = (COGL_PIXEL_FORMAT_BGRA_1010102 | COGL_PREMULT_BIT),
   COGL_PIXEL_FORMAT_ARGB_2101010_PRE = (COGL_PIXEL_FORMAT_ARGB_2101010 | COGL_PREMULT_BIT),
-  COGL_PIXEL_FORMAT_ABGR_2101010_PRE = (COGL_PIXEL_FORMAT_ABGR_2101010 | COGL_PREMULT_BIT)
+  COGL_PIXEL_FORMAT_ABGR_2101010_PRE = (COGL_PIXEL_FORMAT_ABGR_2101010 | COGL_PREMULT_BIT),
+
+  COGL_PIXEL_FORMAT_DEPTH_ANY = (0 | COGL_DEPTH_BIT),
+  COGL_PIXEL_FORMAT_DEPTH_16  = (9 | COGL_DEPTH_BIT),
+  COGL_PIXEL_FORMAT_DEPTH_24  = (2 | COGL_DEPTH_BIT),
+  COGL_PIXEL_FORMAT_DEPTH_32  = (3 | COGL_DEPTH_BIT),
+
+  COGL_PIXEL_FORMAT_DEPTH_24_STENCIL_8 = (3 | COGL_DEPTH_BIT | COGL_STENCIL_BIT) 
 } CoglPixelFormat;
 
 /**
@@ -361,6 +372,8 @@ typedef enum { /*< prefix=COGL_PIXEL_FORMAT >*/
  *     supported with CoglBufferAccess including read support.
  * @COGL_FEATURE_MAP_BUFFER_FOR_WRITE: Whether cogl_buffer_map() is
  *     supported with CoglBufferAccess including write support.
+ * @COGL_FEATURE_DEPTH_TEXTURE: Whether #CoglFramebuffer support rendering the
+ *     depth buffer to a texture.
  *
  * Flags for the supported features.
  *
@@ -390,7 +403,8 @@ typedef enum
   COGL_FEATURE_SHADERS_ARBFP          = (1 << 20),
   COGL_FEATURE_MAP_BUFFER_FOR_READ    = (1 << 21),
   COGL_FEATURE_MAP_BUFFER_FOR_WRITE   = (1 << 22),
-  COGL_FEATURE_ONSCREEN_MULTIPLE      = (1 << 23)
+  COGL_FEATURE_ONSCREEN_MULTIPLE      = (1 << 23),
+  COGL_FEATURE_DEPTH_TEXTURE          = (1 << 24)
 } CoglFeatureFlags;
 
 /**
diff --git a/cogl/driver/gl/cogl-gl.c b/cogl/driver/gl/cogl-gl.c
index b35ddbe..7bcee59 100644
--- a/cogl/driver/gl/cogl-gl.c
+++ b/cogl/driver/gl/cogl-gl.c
@@ -216,6 +216,13 @@ _cogl_gl_update_features (CoglContext *context,
                       COGL_FEATURE_ID_OFFSCREEN_MULTISAMPLE, TRUE);
     }
 
+  if (COGL_CHECK_GL_VERSION (gl_major, gl_minor, 3, 0) ||
+      _cogl_check_extension ("GL_ARB_depth_texture", gl_extensions))
+    {
+      flags |= COGL_FEATURE_DEPTH_TEXTURE;
+      COGL_FLAGS_SET (ctx->features, COGL_FEATURE_ID_DEPTH_TEXTURE, TRUE);
+    }
+
   if (COGL_CHECK_GL_VERSION (gl_major, gl_minor, 2, 1) ||
       _cogl_check_extension ("GL_EXT_pixel_buffer_object", gl_extensions))
     private_flags |= COGL_PRIVATE_FEATURE_PBOS;
diff --git a/cogl/driver/gl/cogl-texture-driver-gl.c b/cogl/driver/gl/cogl-texture-driver-gl.c
index 3d46ccb..66b247d 100644
--- a/cogl/driver/gl/cogl-texture-driver-gl.c
+++ b/cogl/driver/gl/cogl-texture-driver-gl.c
@@ -517,6 +517,33 @@ _cogl_texture_driver_pixel_format_to_gl (CoglPixelFormat  format,
       gltype = GL_UNSIGNED_SHORT_5_5_5_1;
       break;
 
+    case COGL_PIXEL_FORMAT_DEPTH_ANY:
+      glintformat = GL_DEPTH_COMPONENT;
+      glformat = GL_DEPTH_COMPONENT;
+      gltype = GL_UNSIGNED_BYTE;
+      break;
+    case COGL_PIXEL_FORMAT_DEPTH_16:
+      glintformat = GL_DEPTH_COMPONENT16;
+      glformat = GL_DEPTH_COMPONENT;
+      gltype = GL_UNSIGNED_SHORT;
+      break;
+    case COGL_PIXEL_FORMAT_DEPTH_24:
+      glintformat = GL_DEPTH_COMPONENT24;
+      glformat = GL_DEPTH_COMPONENT;
+      gltype = GL_UNSIGNED_INT;
+      break;
+    case COGL_PIXEL_FORMAT_DEPTH_32:
+      glintformat = GL_DEPTH_COMPONENT32;
+      glformat = GL_DEPTH_COMPONENT;
+      gltype = GL_UNSIGNED_INT;
+      break;
+
+    case COGL_PIXEL_FORMAT_DEPTH_24_STENCIL_8:
+      glintformat = GL_DEPTH24_STENCIL8;
+      glformat = GL_DEPTH_STENCIL;
+      gltype = GL_UNSIGNED_INT_24_8;
+      break;
+
     case COGL_PIXEL_FORMAT_ANY:
     case COGL_PIXEL_FORMAT_YUV:
       g_assert_not_reached ();
diff --git a/cogl/driver/gles/cogl-gles.c b/cogl/driver/gles/cogl-gles.c
index 8087ae0..8ba0cc6 100644
--- a/cogl/driver/gles/cogl-gles.c
+++ b/cogl/driver/gles/cogl-gles.c
@@ -120,6 +120,12 @@ _cogl_gles_update_features (CoglContext *context,
                       COGL_FEATURE_ID_UNSIGNED_INT_INDICES, TRUE);
     }
 
+  if (_cogl_check_extension ("GL_OES_depth_texture"))
+    {
+      flags |= COGL_FEATURE_DEPTH_TEXTURE;
+      COGL_FLAGS_SET (ctx->features, COGL_FEATURE_ID_DEPTH_TEXTURE, TRUE);
+    }
+
   if (_cogl_check_extension ("GL_OES_texture_npot", gl_extensions))
     {
       flags |= (COGL_FEATURE_TEXTURE_NPOT |
diff --git a/cogl/driver/gles/cogl-texture-driver-gles.c b/cogl/driver/gles/cogl-texture-driver-gles.c
index 21cfb61..5bee0e6 100644
--- a/cogl/driver/gles/cogl-texture-driver-gles.c
+++ b/cogl/driver/gles/cogl-texture-driver-gles.c
@@ -478,6 +478,33 @@ _cogl_texture_driver_pixel_format_to_gl (CoglPixelFormat  format,
       gltype = GL_UNSIGNED_SHORT_5_5_5_1;
       break;
 
+    case COGL_PIXEL_FORMAT_DEPTH_ANY:
+      glintformat = GL_DEPTH_COMPONENT;
+      glformat = GL_DEPTH_COMPONENT;
+      gltype = GL_UNSIGNED_BYTE;
+      break;
+    case COGL_PIXEL_FORMAT_DEPTH_16:
+      glintformat = GL_DEPTH_COMPONENT16;
+      glformat = GL_DEPTH_COMPONENT;
+      gltype = GL_UNSIGNED_SHORT;
+      break;
+    case COGL_PIXEL_FORMAT_DEPTH_24:
+      glintformat = GL_DEPTH_COMPONENT24;
+      glformat = GL_DEPTH_COMPONENT;
+      gltype = GL_UNSIGNED_INT;
+      break;
+    case COGL_PIXEL_FORMAT_DEPTH_32:
+      glintformat = GL_DEPTH_COMPONENT32;
+      glformat = GL_DEPTH_COMPONENT;
+      gltype = GL_UNSIGNED_INT;
+      break;
+
+    case COGL_PIXEL_FORMAT_DEPTH_24_STENCIL_8:
+      glintformat = GL_DEPTH24_STENCIL8;
+      glformat = GL_DEPTH_STENCIL;
+      gltype = GL_UNSIGNED_INT_24_8;
+      break;
+
     case COGL_PIXEL_FORMAT_ANY:
     case COGL_PIXEL_FORMAT_YUV:
       g_assert_not_reached ();
diff --git a/examples/cogl-info.c b/examples/cogl-info.c
index 988e991..808f3ed 100644
--- a/examples/cogl-info.c
+++ b/examples/cogl-info.c
@@ -103,6 +103,12 @@ struct {
     COGL_FEATURE_ID_MIRRORED_REPEAT,
     "Mirrored repeat wrap modes",
     "Mirrored repeat wrap modes"
+  },
+  {
+    COGL_FEATURE_ID_DEPTH_TEXTURE,
+    "Depth Textures",
+    "CoglFramebuffers can be configured to render their depth buffer into "
+    "a texture"
   }
 };
 
-- 
1.7.7.5



More information about the Cogl mailing list