Stefan Dösinger : wined3d: Emulate R16G16F and R32G32F if GL_ARB_texture_rg is not supported.

Alexandre Julliard julliard at winehq.org
Tue Apr 28 07:53:01 CDT 2009


Module: wine
Branch: master
Commit: 8513f64a0117ee7a6a15cb174a3c0c76e2f2b071
URL:    http://source.winehq.org/git/wine.git/?a=commit;h=8513f64a0117ee7a6a15cb174a3c0c76e2f2b071

Author: Stefan Dösinger <stefan at codeweavers.com>
Date:   Mon Apr  6 15:05:27 2009 +0200

wined3d: Emulate R16G16F and R32G32F if GL_ARB_texture_rg is not supported.

Nvidia doesn't offer it on geforce 7 and earlier cards, but some games need
it. This is surprising because the extension was made specifically for
compatibility purposes for older cards.

---

 dlls/wined3d/directx.c         |   11 ++---------
 dlls/wined3d/surface.c         |   40 ++++++++++++++++++++++++++++++++++++++++
 dlls/wined3d/wined3d_private.h |    2 ++
 3 files changed, 44 insertions(+), 9 deletions(-)

diff --git a/dlls/wined3d/directx.c b/dlls/wined3d/directx.c
index 6a15a48..2b4520c 100644
--- a/dlls/wined3d/directx.c
+++ b/dlls/wined3d/directx.c
@@ -2391,6 +2391,7 @@ static BOOL CheckTextureCapability(struct WineD3DAdapter *adapter,
 
             /* Floating point formats */
         case WINED3DFMT_R16_FLOAT:
+        case WINED3DFMT_R16G16_FLOAT:
         case WINED3DFMT_R16G16B16A16_FLOAT:
             if(GL_SUPPORT(ARB_TEXTURE_FLOAT) && GL_SUPPORT(ARB_HALF_FLOAT_PIXEL)) {
                 TRACE_(d3d_caps)("[OK]\n");
@@ -2400,6 +2401,7 @@ static BOOL CheckTextureCapability(struct WineD3DAdapter *adapter,
             return FALSE;
 
         case WINED3DFMT_R32_FLOAT:
+        case WINED3DFMT_R32G32_FLOAT:
         case WINED3DFMT_R32G32B32A32_FLOAT:
             if (GL_SUPPORT(ARB_TEXTURE_FLOAT)) {
                 TRACE_(d3d_caps)("[OK]\n");
@@ -2408,15 +2410,6 @@ static BOOL CheckTextureCapability(struct WineD3DAdapter *adapter,
             TRACE_(d3d_caps)("[FAILED]\n");
             return FALSE;
 
-        case WINED3DFMT_R16G16_FLOAT:
-        case WINED3DFMT_R32G32_FLOAT:
-            if(GL_SUPPORT(ARB_TEXTURE_RG)) {
-                TRACE_(d3d_caps)("[OK]\n");
-                return TRUE;
-            }
-            TRACE_(d3d_caps)("[FAILED]\n");
-            return FALSE;
-
         /* ATI instancing hack: Although ATI cards do not support Shader Model 3.0, they support
          * instancing. To query if the card supports instancing CheckDeviceFormat with the special format
          * MAKEFOURCC('I','N','S','T') is used. Should a (broken) app check for this provide a proper return value.
diff --git a/dlls/wined3d/surface.c b/dlls/wined3d/surface.c
index 35ba9a4..9e9d55c 100644
--- a/dlls/wined3d/surface.c
+++ b/dlls/wined3d/surface.c
@@ -1795,6 +1795,22 @@ HRESULT d3dfmt_get_conv(IWineD3DSurfaceImpl *This, BOOL need_alpha_ck, BOOL use_
             *target_bpp = 6;
             break;
 
+        case WINED3DFMT_R16G16_FLOAT:
+            *convert = CONVERT_R16G16F;
+            *format = GL_RGB;
+            *internal = GL_RGB16F_ARB;
+            *type = GL_HALF_FLOAT_ARB;
+            *target_bpp = 6;
+            break;
+
+        case WINED3DFMT_R32G32_FLOAT:
+            *convert = CONVERT_R32G32F;
+            *format = GL_RGB;
+            *internal = GL_RGB32F_ARB;
+            *type = GL_FLOAT;
+            *target_bpp = 12;
+            break;
+
         default:
             break;
     }
@@ -2123,6 +2139,7 @@ static HRESULT d3dfmt_convert_surface(const BYTE *src, BYTE *dst, UINT pitch, UI
         }
 
         case CONVERT_G16R16:
+        case CONVERT_R16G16F:
         {
             unsigned int x, y;
             const WORD *Source;
@@ -2136,6 +2153,9 @@ static HRESULT d3dfmt_convert_surface(const BYTE *src, BYTE *dst, UINT pitch, UI
                     WORD red = (*Source++);
                     Dest[0] = green;
                     Dest[1] = red;
+                    /* Strictly speaking not correct for R16G16F, but it doesn't matter because the
+                     * shader overwrites it anyway
+                     */
                     Dest[2] = 0xffff;
                     Dest += 3;
                 }
@@ -2143,6 +2163,26 @@ static HRESULT d3dfmt_convert_surface(const BYTE *src, BYTE *dst, UINT pitch, UI
             break;
         }
 
+        case CONVERT_R32G32F:
+        {
+            unsigned int x, y;
+            const float *Source;
+            float *Dest;
+            for(y = 0; y < height; y++) {
+                Source = (const float *)(src + y * pitch);
+                Dest = (float *) (dst + y * outpitch);
+                for (x = 0; x < width; x++ ) {
+                    float green = (*Source++);
+                    float red = (*Source++);
+                    Dest[0] = green;
+                    Dest[1] = red;
+                    Dest[2] = 1.0;
+                    Dest += 3;
+                }
+            }
+            break;
+        }
+
         default:
             ERR("Unsupported conversation type %d\n", convert);
     }
diff --git a/dlls/wined3d/wined3d_private.h b/dlls/wined3d/wined3d_private.h
index 9040ac0..5809cb9 100644
--- a/dlls/wined3d/wined3d_private.h
+++ b/dlls/wined3d/wined3d_private.h
@@ -1824,6 +1824,8 @@ typedef enum {
     CONVERT_V16U16,
     CONVERT_A4L4,
     CONVERT_G16R16,
+    CONVERT_R16G16F,
+    CONVERT_R32G32F,
 } CONVERT_TYPES;
 
 HRESULT d3dfmt_get_conv(IWineD3DSurfaceImpl *This, BOOL need_alpha_ck, BOOL use_texturing, GLenum *format, GLenum *internal, GLenum *type, CONVERT_TYPES *convert, int *target_bpp, BOOL srgb_mode);




More information about the wine-cvs mailing list