Question

I recently updated my loading code for textures and also added some new features like mipmap loading ( the last application has been only 2D so i didn't need them ). But the loaded PVRTC textures stay black when using mipmaps, without mipmaps everything works like expected and also mipmaps are working when using textures like RGBA8888 textures.

Loading of the compressed data:

for (int i = 0; i < source.MipmapCount; i++)
{
    data = source.GetData(i);
    GLTextures.CompressedTexImage2D(TextureType.TEXTURE_2D, i, Format.CompressedFormat.Value, Width >> i, Height >> i, data.Length, data);
    Debug.WriteGLError("Texture2D->CompressedTexImage2D", "MipmapLevel={0}", i);
}

Setup of the filtering:

if (source.MipmapCount == 0)
{
    switch (filterQuality)
    {
        case FilterQuality.Nearest:
            GLTextures.TexParameteri(TextureType.TEXTURE_2D, TexParameter.TEXTURE_MIN_FILTER, (Int32)TextureMinFilterParams.NEAREST);
            GLTextures.TexParameteri(TextureType.TEXTURE_2D, TexParameter.TEXTURE_MAG_FILTER, (Int32)TextureMagFilterParams.NEAREST);
            break;
        case FilterQuality.Linear:
            GLTextures.TexParameteri(TextureType.TEXTURE_2D, TexParameter.TEXTURE_MIN_FILTER, (Int32)TextureMinFilterParams.LINEAR);
            GLTextures.TexParameteri(TextureType.TEXTURE_2D, TexParameter.TEXTURE_MAG_FILTER, (Int32)TextureMagFilterParams.LINEAR);
            break;
    }
    Debug.WriteGLError("Texture2D->TexParameteri without mipmaps");
}
else
{
    switch (filterQuality)
    {
        case FilterQuality.Nearest:
            GLTextures.TexParameteri(TextureType.TEXTURE_2D, TexParameter.TEXTURE_MIN_FILTER, (Int32)TextureMinFilterParams.NEAREST_MIPMAP_LINEAR);
            GLTextures.TexParameteri(TextureType.TEXTURE_2D, TexParameter.TEXTURE_MAG_FILTER, (Int32)TextureMagFilterParams.NEAREST);
            break;
        case FilterQuality.Linear:
            GLTextures.TexParameteri(TextureType.TEXTURE_2D, TexParameter.TEXTURE_MIN_FILTER, (Int32)TextureMinFilterParams.LINEAR_MIPMAP_LINEAR);
            GLTextures.TexParameteri(TextureType.TEXTURE_2D, TexParameter.TEXTURE_MAG_FILTER, (Int32)TextureMagFilterParams.LINEAR);
            break;
    }

    Debug.WriteGLError("Texture2D->TexParameteri with mipmaps");

    if (anisotropicQuality > 1f && GL.IsExtensionSupported(Extension.GL_EXT_texture_filter_anisotropic))
    {
        // GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT 
        GLTextures.TexParameter(TextureType.TEXTURE_2D, 0x84FF, Mathf.Clamp(anisotropicQuality, 1f, GL.GetFloat(GetFloatName.TEXTURE_MAX_ANISOTROPY)));
        Debug.WriteGLError("Texture2D->Anisotropy");
    }
}

Loading of the texture The loading is done with a modified reference-loader for PVR files. I checked the length of the bytes of each mipmap and the last few arrays have the size of 32 bytes ( minimum size of PVRTC ). What could cause the issue?

Edit

The method "GLTextures.CompressedTexImage2D".

public static void CompressedTexImage2D(TextureType target, Int32 level, CompressedFormats internalFormat, Int32 width, Int32 height, Int32 imageSize, Byte[] pixels)
{
    /* Used for mobile apps for debugging purposes */
    Debug.CheckMethodLoaded(glCompressedTexImage2D);
    Profiler.IncreaseCallCount("glCompressedTexImage2D");
    glCompressedTexImage2D(target, level, internalFormat, width, height, 0, imageSize, pixels);
}

Image formats definition:

PVRTC2RGB = new ImageFormat("PVRTC2RGB", CompressedFormats.COMPRESSED_RGB_PVRTC_2BPPV1_IMG, 16, 8, bitsPerPixel: 2, requiredExtension:Extension.GL_IMG_texture_compression_pvrtc);
PVRTC2RGBA = new ImageFormat("PVRTC2RGBA", CompressedFormats.COMPRESSED_RGBA_PVRTC_2BPPV1_IMG, 16, 8, bitsPerPixel: 2, requiredExtension: Extension.GL_IMG_texture_compression_pvrtc);
PVRTC4RGB = new ImageFormat("PVRTC4RGB", CompressedFormats.COMPRESSED_RGB_PVRTC_4BPPV1_IMG, 8, 8, bitsPerPixel: 4, requiredExtension: Extension.GL_IMG_texture_compression_pvrtc);
PVRTC4RGBA = new ImageFormat("PVRTC4RGBA", CompressedFormats.COMPRESSED_RGBA_PVRTC_4BPPV1_IMG, 8, 8, bitsPerPixel: 4, requiredExtension: Extension.GL_IMG_texture_compression_pvrtc);
Was it helpful?

Solution 2

edit: correction.

I believe your texture min/mag filters must be:

  • GL_LINEAR_MIPMAP_NEAREST for the min filter
  • GL_LINEAR for the mag filter

when using mipmaps with PVRTC. See the header file at: http://ne3d.googlecode.com/svn-history/r3/trunk/Lib/SRC/Tools/OGLES/PVRTTextureAPI.h

OTHER TIPS

I just came across a similar issue using cocos2d-x. After a lot of debugging I finally figured it out : make sure you are supplying a complete mipmap chain (down to 1x1) or set Apple's GL_TEXTURE_MAX_LEVEL_APPLE texture parameter to the correct number of mipmaps. Unfortunately, Apple's own TextureTool output only down to 8x8 (with was supposed to be the lower limit but it's not anymore). Even PVRTextureLoader sample code from Apple doesn't works out of the box.

Be sure your "imageSize" in glCompressedTexImage2D is bigger than 32 at any mipmap level.

To achieve mipmap "effect" on PVRTC texture, you should use:

  • use filter GL_LINEAR.
  • fetch texture color using texture2DLod(EXT) with lod value calculated by yourself.
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top