OSDN Git Service

Implement support for separate minification/magnification filters.
authorNicolas Capens <capn@google.com>
Mon, 15 Feb 2016 15:31:49 +0000 (10:31 -0500)
committerNicolas Capens <capn@google.com>
Wed, 24 Feb 2016 16:48:11 +0000 (16:48 +0000)
Bug 22373253

Change-Id: Iaa30a341e5eaa58c2ef531fce503631828c5ee9d
Reviewed-on: https://swiftshader-review.googlesource.com/4757
Reviewed-by: Alexis Hétu <sugoi@google.com>
Reviewed-by: Nicolas Capens <capn@google.com>
Tested-by: Nicolas Capens <capn@google.com>
src/OpenGL/libGL/utilities.cpp
src/Shader/SamplerCore.cpp
src/Shader/SamplerCore.hpp

index e80b630..d8b2a8b 100644 (file)
@@ -620,27 +620,19 @@ namespace es2sw
                        return sw::FILTER_ANISOTROPIC;\r
                }\r
 \r
-               sw::FilterType magFilterType = sw::FILTER_POINT;\r
-               switch(magFilter)\r
-               {\r
-               case GL_NEAREST: magFilterType = sw::FILTER_POINT;  break;\r
-               case GL_LINEAR:  magFilterType = sw::FILTER_LINEAR; break;\r
-               default: UNREACHABLE(magFilter);\r
-               }\r
-\r
                switch(minFilter)\r
                {\r
                case GL_NEAREST:\r
                case GL_NEAREST_MIPMAP_NEAREST:\r
                case GL_NEAREST_MIPMAP_LINEAR:\r
-                       return (magFilterType == sw::FILTER_POINT) ? sw::FILTER_POINT : sw::FILTER_MIN_POINT_MAG_LINEAR;\r
+                       return (magFilter == GL_NEAREST) ? sw::FILTER_POINT : sw::FILTER_MIN_POINT_MAG_LINEAR;\r
                case GL_LINEAR:\r
                case GL_LINEAR_MIPMAP_NEAREST:\r
                case GL_LINEAR_MIPMAP_LINEAR:\r
-                       return (magFilterType == sw::FILTER_POINT) ? sw::FILTER_MIN_LINEAR_MAG_POINT : sw::FILTER_LINEAR;\r
+                       return (magFilter == GL_NEAREST) ? sw::FILTER_MIN_LINEAR_MAG_POINT : sw::FILTER_LINEAR;\r
                default:\r
                        UNREACHABLE(minFilter);\r
-                       return (magFilterType == sw::FILTER_POINT) ? sw::FILTER_POINT : sw::FILTER_MIN_POINT_MAG_LINEAR;\r
+                       return sw::FILTER_LINEAR;\r
                }\r
        }\r
 \r
@@ -698,7 +690,7 @@ namespace es2sw
                case GL_RGB8_EXT:             return sw::FORMAT_X8R8G8B8;\r
                case GL_DEPTH_COMPONENT16:\r
         case GL_DEPTH_COMPONENT24:\r
-               case GL_STENCIL_INDEX8:       \r
+               case GL_STENCIL_INDEX8:\r
                case GL_DEPTH24_STENCIL8_EXT: return sw::FORMAT_D24S8;\r
                default: UNREACHABLE(format); return sw::FORMAT_A8R8G8B8;\r
                }\r
index 3973d1d..82a6644 100644 (file)
@@ -556,26 +556,37 @@ namespace sw
                mask = As<Int4>(CmpLT(Abs(coordinates - Float4(0.5f)), Float4(0.5f)));
        }
 
-       Short4 SamplerCore::offsetSample(Short4 &uvw, Pointer<Byte> &mipmap, int halfOffset, bool wrap, int count)
+       Short4 SamplerCore::offsetSample(Short4 &uvw, Pointer<Byte> &mipmap, int halfOffset, bool wrap, int count, Float &lod)
        {
+               Short4 offset = *Pointer<Short4>(mipmap + halfOffset);
+
+               if(state.textureFilter == FILTER_MIN_LINEAR_MAG_POINT)
+               {
+                       offset &= Short4(CmpNLE(Float4(lod), Float4(0.0f)));
+               }
+               else if(state.textureFilter == FILTER_MIN_POINT_MAG_LINEAR)
+               {
+                       offset &= Short4(CmpLE(Float4(lod), Float4(0.0f)));
+               }
+
                if(wrap)
                {
                        switch(count)
                        {
-                       case -1: return uvw - *Pointer<Short4>(mipmap + halfOffset);
+                       case -1: return uvw - offset;
                        case  0: return uvw;
-                       case +1: return uvw + *Pointer<Short4>(mipmap + halfOffset);
-                       case  2: return uvw + *Pointer<Short4>(mipmap + halfOffset) + *Pointer<Short4>(mipmap + halfOffset);
+                       case +1: return uvw + offset;
+                       case  2: return uvw + offset + offset;
                        }
                }
                else   // Clamp or mirror
                {
                        switch(count)
                        {
-                       case -1: return SubSat(As<UShort4>(uvw), *Pointer<UShort4>(mipmap + halfOffset));
+                       case -1: return SubSat(As<UShort4>(uvw), As<UShort4>(offset));
                        case  0: return uvw;
-                       case +1: return AddSat(As<UShort4>(uvw), *Pointer<UShort4>(mipmap + halfOffset));
-                       case  2: return AddSat(AddSat(As<UShort4>(uvw), *Pointer<UShort4>(mipmap + halfOffset)), *Pointer<UShort4>(mipmap + halfOffset));
+                       case +1: return AddSat(As<UShort4>(uvw), As<UShort4>(offset));
+                       case  2: return AddSat(AddSat(As<UShort4>(uvw), As<UShort4>(offset)), As<UShort4>(offset));
                        }
                }
 
@@ -760,7 +771,7 @@ namespace sw
                Short4 vvvv = address(v, state.addressingModeV, mipmap);
                Short4 wwww = address(w, state.addressingModeW, mipmap);
 
-               if(state.textureFilter == FILTER_POINT || state.textureFilter == FILTER_MIN_POINT_MAG_LINEAR)
+               if(state.textureFilter == FILTER_POINT)
                {
                        sampleTexel(c, uuuu, vvvv, wwww, mipmap, buffer);
                }
@@ -771,10 +782,10 @@ namespace sw
                        Vector4s c2;
                        Vector4s c3;
 
-                       Short4 uuuu0 = offsetSample(uuuu, mipmap, OFFSET(Mipmap,uHalf), state.addressingModeU == ADDRESSING_WRAP, gather ? 0 : -1);
-                       Short4 vvvv0 = offsetSample(vvvv, mipmap, OFFSET(Mipmap,vHalf), state.addressingModeV == ADDRESSING_WRAP, gather ? 0 : -1);
-                       Short4 uuuu1 = offsetSample(uuuu, mipmap, OFFSET(Mipmap,uHalf), state.addressingModeU == ADDRESSING_WRAP, gather ? 2 : +1);
-                       Short4 vvvv1 = offsetSample(vvvv, mipmap, OFFSET(Mipmap,vHalf), state.addressingModeV == ADDRESSING_WRAP, gather ? 2 : +1);
+                       Short4 uuuu0 = offsetSample(uuuu, mipmap, OFFSET(Mipmap,uHalf), state.addressingModeU == ADDRESSING_WRAP, gather ? 0 : -1, lod);
+                       Short4 vvvv0 = offsetSample(vvvv, mipmap, OFFSET(Mipmap,vHalf), state.addressingModeV == ADDRESSING_WRAP, gather ? 0 : -1, lod);
+                       Short4 uuuu1 = offsetSample(uuuu, mipmap, OFFSET(Mipmap,uHalf), state.addressingModeU == ADDRESSING_WRAP, gather ? 2 : +1, lod);
+                       Short4 vvvv1 = offsetSample(vvvv, mipmap, OFFSET(Mipmap,vHalf), state.addressingModeV == ADDRESSING_WRAP, gather ? 2 : +1, lod);
 
                        sampleTexel(c0, uuuu0, vvvv0, wwww, mipmap, buffer);
                        sampleTexel(c1, uuuu1, vvvv0, wwww, mipmap, buffer);
@@ -965,7 +976,7 @@ namespace sw
                Short4 vvvv = address(v_, state.addressingModeV, mipmap);
                Short4 wwww = address(w_, state.addressingModeW, mipmap);
 
-               if(state.textureFilter <= FILTER_POINT || state.textureFilter == FILTER_MIN_POINT_MAG_LINEAR)
+               if(state.textureFilter == FILTER_POINT)
                {
                        sampleTexel(c_, uuuu, vvvv, wwww, mipmap, buffer);
                }
@@ -983,9 +994,9 @@ namespace sw
                                {
                                        for(int k = 0; k < 2; k++)
                                        {
-                                               u[i][j][k] = offsetSample(uuuu, mipmap, OFFSET(Mipmap,uHalf), state.addressingModeU == ADDRESSING_WRAP, i * 2 - 1);
-                                               v[i][j][k] = offsetSample(vvvv, mipmap, OFFSET(Mipmap,vHalf), state.addressingModeV == ADDRESSING_WRAP, j * 2 - 1);
-                                               s[i][j][k] = offsetSample(wwww, mipmap, OFFSET(Mipmap,wHalf), state.addressingModeW == ADDRESSING_WRAP, k * 2 - 1);
+                                               u[i][j][k] = offsetSample(uuuu, mipmap, OFFSET(Mipmap,uHalf), state.addressingModeU == ADDRESSING_WRAP, i * 2 - 1, lod);
+                                               v[i][j][k] = offsetSample(vvvv, mipmap, OFFSET(Mipmap,vHalf), state.addressingModeV == ADDRESSING_WRAP, j * 2 - 1, lod);
+                                               s[i][j][k] = offsetSample(wwww, mipmap, OFFSET(Mipmap,wHalf), state.addressingModeW == ADDRESSING_WRAP, k * 2 - 1, lod);
                                        }
                                }
                        }
@@ -1237,7 +1248,7 @@ namespace sw
                Short4 vvvv = address(v, state.addressingModeV, mipmap);
                Short4 wwww = address(w, state.addressingModeW, mipmap);
 
-               if(state.textureFilter == FILTER_POINT || state.textureFilter == FILTER_MIN_POINT_MAG_LINEAR)
+               if(state.textureFilter == FILTER_POINT)
                {
                        sampleTexel(c, uuuu, vvvv, wwww, w, mipmap, buffer);
                }
@@ -1248,10 +1259,10 @@ namespace sw
                        Vector4f c2;
                        Vector4f c3;
 
-                       Short4 uuuu0 = offsetSample(uuuu, mipmap, OFFSET(Mipmap,uHalf), state.addressingModeU == ADDRESSING_WRAP, gather ? 0 : -1);
-                       Short4 vvvv0 = offsetSample(vvvv, mipmap, OFFSET(Mipmap,vHalf), state.addressingModeV == ADDRESSING_WRAP, gather ? 0 : -1);
-                       Short4 uuuu1 = offsetSample(uuuu, mipmap, OFFSET(Mipmap,uHalf), state.addressingModeU == ADDRESSING_WRAP, gather ? 2 : +1);
-                       Short4 vvvv1 = offsetSample(vvvv, mipmap, OFFSET(Mipmap,vHalf), state.addressingModeV == ADDRESSING_WRAP, gather ? 2 : +1);
+                       Short4 uuuu0 = offsetSample(uuuu, mipmap, OFFSET(Mipmap,uHalf), state.addressingModeU == ADDRESSING_WRAP, gather ? 0 : -1, lod);
+                       Short4 vvvv0 = offsetSample(vvvv, mipmap, OFFSET(Mipmap,vHalf), state.addressingModeV == ADDRESSING_WRAP, gather ? 0 : -1, lod);
+                       Short4 uuuu1 = offsetSample(uuuu, mipmap, OFFSET(Mipmap,uHalf), state.addressingModeU == ADDRESSING_WRAP, gather ? 2 : +1, lod);
+                       Short4 vvvv1 = offsetSample(vvvv, mipmap, OFFSET(Mipmap,vHalf), state.addressingModeV == ADDRESSING_WRAP, gather ? 2 : +1, lod);
 
                        sampleTexel(c0, uuuu0, vvvv0, wwww, w, mipmap, buffer);
                        sampleTexel(c1, uuuu1, vvvv0, wwww, w, mipmap, buffer);
@@ -1303,7 +1314,7 @@ namespace sw
                Short4 vvvv = address(v, state.addressingModeV, mipmap);
                Short4 wwww = address(w, state.addressingModeW, mipmap);
 
-               if(state.textureFilter <= FILTER_POINT || state.textureFilter == FILTER_MIN_POINT_MAG_LINEAR)
+               if(state.textureFilter == FILTER_POINT)
                {
                        sampleTexel(c, uuuu, vvvv, wwww, w, mipmap, buffer);
                }
@@ -1318,12 +1329,12 @@ namespace sw
                        Vector4f c6;
                        Vector4f c7;
 
-                       Short4 uuuu0 = offsetSample(uuuu, mipmap, OFFSET(Mipmap,uHalf), state.addressingModeU == ADDRESSING_WRAP, -1);
-                       Short4 vvvv0 = offsetSample(vvvv, mipmap, OFFSET(Mipmap,vHalf), state.addressingModeV == ADDRESSING_WRAP, -1);
-                       Short4 wwww0 = offsetSample(wwww, mipmap, OFFSET(Mipmap,wHalf), state.addressingModeW == ADDRESSING_WRAP, -1);
-                       Short4 uuuu1 = offsetSample(uuuu, mipmap, OFFSET(Mipmap,uHalf), state.addressingModeU == ADDRESSING_WRAP, +1);
-                       Short4 vvvv1 = offsetSample(vvvv, mipmap, OFFSET(Mipmap,vHalf), state.addressingModeV == ADDRESSING_WRAP, +1);
-                       Short4 wwww1 = offsetSample(wwww, mipmap, OFFSET(Mipmap,wHalf), state.addressingModeW == ADDRESSING_WRAP, +1);
+                       Short4 uuuu0 = offsetSample(uuuu, mipmap, OFFSET(Mipmap,uHalf), state.addressingModeU == ADDRESSING_WRAP, -1, lod);
+                       Short4 vvvv0 = offsetSample(vvvv, mipmap, OFFSET(Mipmap,vHalf), state.addressingModeV == ADDRESSING_WRAP, -1, lod);
+                       Short4 wwww0 = offsetSample(wwww, mipmap, OFFSET(Mipmap,wHalf), state.addressingModeW == ADDRESSING_WRAP, -1, lod);
+                       Short4 uuuu1 = offsetSample(uuuu, mipmap, OFFSET(Mipmap,uHalf), state.addressingModeU == ADDRESSING_WRAP, +1, lod);
+                       Short4 vvvv1 = offsetSample(vvvv, mipmap, OFFSET(Mipmap,vHalf), state.addressingModeV == ADDRESSING_WRAP, +1, lod);
+                       Short4 wwww1 = offsetSample(wwww, mipmap, OFFSET(Mipmap,wHalf), state.addressingModeW == ADDRESSING_WRAP, +1, lod);
 
                        sampleTexel(c0, uuuu0, vvvv0, wwww0, w, mipmap, buffer);
                        sampleTexel(c1, uuuu1, vvvv0, wwww0, w, mipmap, buffer);
index 3dacf16..75d8f31 100644 (file)
@@ -28,7 +28,7 @@ namespace sw
        private:\r
                void border(Short4 &mask, Float4 &coordinates);\r
                void border(Int4 &mask, Float4 &coordinates);\r
-               Short4 offsetSample(Short4 &uvw, Pointer<Byte> &mipmap, int halfOffset, bool wrap, int count);\r
+               Short4 offsetSample(Short4 &uvw, Pointer<Byte> &mipmap, int halfOffset, bool wrap, int count, Float &lod);\r
                void sampleFilter(Pointer<Byte> &texture, Vector4s &c, Float4 &u, Float4 &v, Float4 &w, Float &lod, Float &anisotropy, Float4 &uDelta, Float4 &vDelta, Int face[4], bool lodProvided);\r
                void sampleAniso(Pointer<Byte> &texture, Vector4s &c, Float4 &u, Float4 &v, Float4 &w, Float &lod, Float &anisotropy, Float4 &uDelta, Float4 &vDelta, Int face[4], bool secondLOD, bool lodProvided);\r
                void sampleQuad(Pointer<Byte> &texture, Vector4s &c, Float4 &u, Float4 &v, Float4 &w, Float &lod, Int face[4], bool secondLOD);\r