Example #1
0
    //-----------------------------------------------------------------------
    void ILUtil::toOgre(const PixelBox &dst) 
    {
		if(!dst.isConsecutive())
			OGRE_EXCEPT( Exception::ERR_NOT_IMPLEMENTED,
                "Destination must currently be consecutive",
                "ILUtil::ilToOgre" ) ;
		if(dst.getWidth() != static_cast<size_t>(ilGetInteger( IL_IMAGE_WIDTH )) ||
        	dst.getHeight() != static_cast<size_t>(ilGetInteger( IL_IMAGE_HEIGHT )) ||
        	dst.getDepth() != static_cast<size_t>(ilGetInteger( IL_IMAGE_DEPTH )))
			OGRE_EXCEPT( Exception::ERR_INVALIDPARAMS,
                "Destination dimensions must equal IL dimension",
                "ILUtil::ilToOgre" ) ;
        
        int ilfmt = ilGetInteger( IL_IMAGE_FORMAT );
        int iltp = ilGetInteger( IL_IMAGE_TYPE );

		// Check if in-memory format just matches
		// If yes, we can just copy it and save conversion
		ILFormat ifmt = OgreFormat2ilFormat( dst.format );
		if(ifmt.format == ilfmt && ILabs(ifmt.type) == ILabs(iltp)) {
            memcpy(dst.data, ilGetData(), ilGetInteger( IL_IMAGE_SIZE_OF_DATA )); 
            return;
        }
		// Try if buffer is in a known OGRE format so we can use OGRE its
		// conversion routines
		PixelFormat bufFmt = ilFormat2OgreFormat((int)ilfmt, (int)iltp);
		
		ifmt = OgreFormat2ilFormat( bufFmt );
		if(ifmt.format == ilfmt && ILabs(ifmt.type) == ILabs(iltp))
		{
			// IL format matches another OGRE format
			PixelBox src(dst.getWidth(), dst.getHeight(), dst.getDepth(), bufFmt, ilGetData());
			PixelUtil::bulkPixelConversion(src, dst);
			return;
		}
		
        // Thee extremely slow method
        if(iltp == IL_UNSIGNED_BYTE || iltp == IL_BYTE) 
        {
            ilToOgreInternal(static_cast<uint8*>(dst.data), dst.format, (uint8)0x00,(uint8)0x00,(uint8)0x00,(uint8)0xFF);
        } 
        else if(iltp == IL_FLOAT)
        {
            ilToOgreInternal(static_cast<uint8*>(dst.data), dst.format, 0.0f,0.0f,0.0f,1.0f);          
        }
		else if(iltp == IL_SHORT || iltp == IL_UNSIGNED_SHORT)
        {
			ilToOgreInternal(static_cast<uint8*>(dst.data), dst.format, 
				(uint16)0x0000,(uint16)0x0000,(uint16)0x0000,(uint16)0xFFFF); 
        }
        else 
        {
            OGRE_EXCEPT( Exception::ERR_NOT_IMPLEMENTED,
                "Cannot convert this DevIL type",
                "ILUtil::ilToOgre" ) ;
        }
    }
    //-----------------------------------------------------------------------------  
    void GLES2TextureBuffer::download(const PixelBox &data)
    {
#if 0 || defined(GL_NV_get_tex_image)
        if(data.getWidth() != getWidth() ||
            data.getHeight() != getHeight() ||
            data.getDepth() != getDepth())
            OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS, "only download of entire buffer is supported by GL",
                "GLTextureBuffer::download");
        glBindTexture( mTarget, mTextureID );
        if(PixelUtil::isCompressed(data.format))
        {
            if(data.format != mFormat || !data.isConsecutive())
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS, 
                "Compressed images must be consecutive, in the source format",
                "GLTextureBuffer::download");
            // Data must be consecutive and at beginning of buffer as PixelStorei not allowed
            // for compressed formate
            glGetCompressedTexImageNV(mFaceTarget, mLevel, data.data);
        } 
        else
        {
            if((data.getWidth()*PixelUtil::getNumElemBytes(data.format)) & 3) {
                // Standard alignment of 4 is not right
                glPixelStorei(GL_PACK_ALIGNMENT, 1);
            }
            // We can only get the entire texture
            glGetTexImageNV(mFaceTarget, mLevel, 
                GLES2PixelUtil::getGLOriginFormat(data.format), GLES2PixelUtil::getGLOriginDataType(data.format),
                data.data);
            // Restore defaults
            glPixelStorei(GL_PACK_ALIGNMENT, 4);
        }
#else
        OGRE_EXCEPT(Exception::ERR_NOT_IMPLEMENTED, 
                    "Downloading texture buffers is not supported by OpenGL ES",
                    "GLES2TextureBuffer::download");
#endif
    }
    void GLESTextureBuffer::upload(const PixelBox &data, const Image::Box &dest)
    {
        glBindTexture(mTarget, mTextureID);
        GL_CHECK_ERROR;

        if (PixelUtil::isCompressed(data.format))
        {
            if(data.format != mFormat || !data.isConsecutive())
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                            "Compressed images must be consecutive, in the source format",
                            "GLESTextureBuffer::upload");

            GLenum format = GLESPixelUtil::getClosestGLInternalFormat(mFormat);
            // Data must be consecutive and at beginning of buffer as PixelStorei not allowed
            // for compressed formats
            if (dest.left == 0 && dest.top == 0)
            {
                glCompressedTexImage2D(mFaceTarget, mLevel,
                                       format,
                                       dest.getWidth(),
                                       dest.getHeight(),
                                       0,
                                       data.getConsecutiveSize(),
                                       data.data);
                GL_CHECK_ERROR;
            }
            else
            {
                glCompressedTexSubImage2D(mFaceTarget, mLevel,
                                          dest.left, dest.top,
                                          dest.getWidth(), dest.getHeight(),
                                          format, data.getConsecutiveSize(),
                                          data.data);

                GL_CHECK_ERROR;
            }
        }
        else if (mSoftwareMipmap)
        {
            if (data.getWidth() != data.rowPitch)
            {
                // TODO
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                            "Unsupported texture format",
                            "GLESTextureBuffer::upload");
            }

            if (data.getHeight() * data.getWidth() != data.slicePitch)
            {
                // TODO
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                            "Unsupported texture format",
                            "GLESTextureBuffer::upload");
            }

            glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
            GL_CHECK_ERROR;
            buildMipmaps(data);
        }
        else
        {
            if(data.getWidth() != data.rowPitch)
            {
                // TODO
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                            "Unsupported texture format",
                            "GLESTextureBuffer::upload");
            }

            if(data.getHeight()*data.getWidth() != data.slicePitch)
            {
                // TODO
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                            "Unsupported texture format",
                            "GLESTextureBuffer::upload");
            }

            if ((data.getWidth() * PixelUtil::getNumElemBytes(data.format)) & 3) {
                // Standard alignment of 4 is not right
                glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
                GL_CHECK_ERROR;
            }

//            LogManager::getSingleton().logMessage("GLESTextureBuffer::upload - ID: " + StringConverter::toString(mTextureID) +
//                                                  " Format: " + PixelUtil::getFormatName(data.format) +
//                                                  " Origin format: " + StringConverter::toString(GLESPixelUtil::getGLOriginFormat(data.format, 0, ' ', std::ios::hex)) +
//                                                  " Data type: " + StringConverter::toString(GLESPixelUtil::getGLOriginDataType(data.format, 0, ' ', std::ios::hex))
//                                                  );
            glTexSubImage2D(mFaceTarget,
                            mLevel,
                            dest.left, dest.top,
                            dest.getWidth(), dest.getHeight(),
                            GLESPixelUtil::getGLOriginFormat(data.format),
                            GLESPixelUtil::getGLOriginDataType(data.format),
                            data.data);
            GL_CHECK_ERROR;
        }

        glPixelStorei(GL_UNPACK_ALIGNMENT, 4);
        GL_CHECK_ERROR;
    }
Example #4
0
    //-----------------------------------------------------------------------
    void ILUtil::fromOgre(const PixelBox &src)
    {
		// ilTexImage http://openil.sourceforge.net/docs/il/f00059.htm
		ILFormat ifmt = OgreFormat2ilFormat( src.format );
		if(src.isConsecutive() && ifmt.isValid()) 
		{
			// The easy case, the buffer is laid out in memory just like 
			// we want it to be and is in a format DevIL can understand directly
			// We could even save the copy if DevIL would let us
			ilTexImage(static_cast<ILuint>(src.getWidth()), 
				static_cast<ILuint>(src.getHeight()), 
				static_cast<ILuint>(src.getDepth()), ifmt.numberOfChannels,
				ifmt.format, ifmt.type, src.data);
		} 
		else if(ifmt.isValid()) 
		{
			// The format can be understood directly by DevIL. The only 
			// problem is that ilTexImage expects our image data consecutively 
			// so we cannot use that directly.
			
			// Let DevIL allocate the memory for us, and copy the data consecutively
			// to its memory
			ilTexImage(static_cast<ILuint>(src.getWidth()), 
				static_cast<ILuint>(src.getHeight()), 
				static_cast<ILuint>(src.getDepth()), ifmt.numberOfChannels,
				ifmt.format, ifmt.type, 0);
			PixelBox dst(src.getWidth(), src.getHeight(), src.getDepth(), src.format, ilGetData());
			PixelUtil::bulkPixelConversion(src, dst);
		} 
		else 
		{
			// Here it gets ugly. We're stuck with a pixel format that DevIL
			// can't do anything with. We will do a bulk pixel conversion and
			// then feed it to DevIL anyway. The problem is finding the best
			// format to convert to.
			
			// most general format supported by OGRE and DevIL
			PixelFormat fmt = PixelUtil::hasAlpha(src.format)?PF_FLOAT32_RGBA:PF_FLOAT32_RGB; 

			// Make up a pixel format
			// We don't have to consider luminance formats as they have
			// straight conversions to DevIL, just weird permutations of RGBA an LA
			int depths[4];
			PixelUtil::getBitDepths(src.format, depths);
			
			// Native endian format with all bit depths<8 can safely and quickly be 
			// converted to 24/32 bit
			if(PixelUtil::isNativeEndian(src.format) && 
				depths[0]<=8 && depths[1]<=8 && depths[2]<=8 && depths[3]<=8) {
				if(PixelUtil::hasAlpha(src.format)) {
					fmt = PF_A8R8G8B8;
				} else {
					fmt = PF_R8G8B8;
				}
			}
			
			// Let DevIL allocate the memory for us, then do the conversion ourselves
			ifmt = OgreFormat2ilFormat( fmt );
			ilTexImage(static_cast<ILuint>(src.getWidth()), 
				static_cast<ILuint>(src.getHeight()), 
				static_cast<ILuint>(src.getDepth()), ifmt.numberOfChannels,
				ifmt.format, ifmt.type, 0);
			PixelBox dst(src.getWidth(), src.getHeight(), src.getDepth(), fmt, ilGetData());
			PixelUtil::bulkPixelConversion(src, dst);
		}
    }
    void GLES2TextureBuffer::upload(const PixelBox &data, const Image::Box &dest)
    {
        OGRE_CHECK_GL_ERROR(glBindTexture(mTarget, mTextureID));

        if (PixelUtil::isCompressed(data.format))
        {
            if(data.format != mFormat || !data.isConsecutive())
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                            "Compressed images must be consecutive, in the source format",
                            "GLES2TextureBuffer::upload");

            GLenum format = GLES2PixelUtil::getClosestGLInternalFormat(mFormat);
            // Data must be consecutive and at beginning of buffer as PixelStorei not allowed
            // for compressed formats
            if (dest.left == 0 && dest.top == 0)
            {
                OGRE_CHECK_GL_ERROR(glCompressedTexImage2D(mFaceTarget, mLevel,
                                       format,
                                       dest.getWidth(),
                                       dest.getHeight(),
                                       0,
                                       data.getConsecutiveSize(),
                                       data.data));
            }
            else
            {
                OGRE_CHECK_GL_ERROR(glCompressedTexSubImage2D(mFaceTarget, mLevel,
                                          dest.left, dest.top,
                                          dest.getWidth(), dest.getHeight(),
                                          format, data.getConsecutiveSize(),
                                          data.data));
            }
        }
        else if (mSoftwareMipmap)
        {
            if (data.getWidth() != data.rowPitch)
            {
#if OGRE_NO_GLES3_SUPPORT == 0
                OGRE_CHECK_GL_ERROR(glPixelStorei(GL_UNPACK_ROW_LENGTH, data.rowPitch));
#else
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                            "Unsupported texture format",
                            "GLES2TextureBuffer::upload");
#endif
            }

            if (data.getHeight() * data.getWidth() != data.slicePitch)
            {
#if OGRE_NO_GLES3_SUPPORT == 0
                OGRE_CHECK_GL_ERROR(glPixelStorei(GL_UNPACK_IMAGE_HEIGHT, (data.slicePitch/data.getWidth())));
#else
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                            "Unsupported texture format",
                            "GLES2TextureBuffer::upload");
#endif
            }

#if OGRE_NO_GLES3_SUPPORT == 0
            if(data.left > 0 || data.top > 0 || data.front > 0)
                OGRE_CHECK_GL_ERROR(glPixelStorei(GL_UNPACK_SKIP_PIXELS, data.left + data.rowPitch * data.top + data.slicePitch * data.front));
#endif
            OGRE_CHECK_GL_ERROR(glPixelStorei(GL_UNPACK_ALIGNMENT, 1));
            buildMipmaps(data);
        }
        else
        {
            if (data.getWidth() != data.rowPitch)
            {
#if OGRE_NO_GLES3_SUPPORT == 0
                OGRE_CHECK_GL_ERROR(glPixelStorei(GL_UNPACK_ROW_LENGTH, data.rowPitch));
#else
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                            "Unsupported texture format",
                            "GLES2TextureBuffer::upload");
#endif
            }

            if (data.getHeight() * data.getWidth() != data.slicePitch)
            {
#if OGRE_NO_GLES3_SUPPORT == 0
                OGRE_CHECK_GL_ERROR(glPixelStorei(GL_UNPACK_IMAGE_HEIGHT, (data.slicePitch/data.getWidth())));
#else
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                            "Unsupported texture format",
                            "GLES2TextureBuffer::upload");
#endif
            }

#if OGRE_NO_GLES3_SUPPORT == 0
            if(data.left > 0 || data.top > 0 || data.front > 0)
                OGRE_CHECK_GL_ERROR(glPixelStorei(GL_UNPACK_SKIP_PIXELS, data.left + data.rowPitch * data.top + data.slicePitch * data.front));
#endif

            if ((data.getWidth() * PixelUtil::getNumElemBytes(data.format)) & 3) {
                // Standard alignment of 4 is not right
                OGRE_CHECK_GL_ERROR(glPixelStorei(GL_UNPACK_ALIGNMENT, 1));
            }

//            LogManager::getSingleton().logMessage("GLES2TextureBuffer::upload - ID: " + StringConverter::toString(mTextureID) +
//                                                  " Format: " + PixelUtil::getFormatName(data.format) +
//                                                  " Origin format: " + StringConverter::toString(GLES2PixelUtil::getGLOriginFormat(data.format), 0, std::ios::hex) +
//                                                  " Data type: " + StringConverter::toString(GLES2PixelUtil::getGLOriginDataType(data.format), 0, ' ', std::ios::hex));
            OGRE_CHECK_GL_ERROR(glTexSubImage2D(mFaceTarget,
                            mLevel,
                            dest.left, dest.top,
                            dest.getWidth(), dest.getHeight(),
                            GLES2PixelUtil::getGLOriginFormat(data.format),
                            GLES2PixelUtil::getGLOriginDataType(data.format),
                            data.data));
        }

#if OGRE_NO_GLES3_SUPPORT == 0
        OGRE_CHECK_GL_ERROR(glPixelStorei(GL_UNPACK_ROW_LENGTH, 0));
        OGRE_CHECK_GL_ERROR(glPixelStorei(GL_UNPACK_IMAGE_HEIGHT, 0));
        OGRE_CHECK_GL_ERROR(glPixelStorei(GL_UNPACK_SKIP_PIXELS, 0));
#endif
        OGRE_CHECK_GL_ERROR(glPixelStorei(GL_UNPACK_ALIGNMENT, 4));
    }
    void GLES2TextureBuffer::upload(const PixelBox &data, const Image::Box &dest)
    {
        glBindTexture(mTarget, mTextureID);
        GL_CHECK_ERROR;

        if (PixelUtil::isCompressed(data.format))
        {
            if(data.format != mFormat || !data.isConsecutive())
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                            "Compressed images must be consecutive, in the source format",
                            "GLES2TextureBuffer::upload");

            GLenum format = GLES2PixelUtil::getClosestGLInternalFormat(mFormat);
            // Data must be consecutive and at beginning of buffer as PixelStorei not allowed
            // for compressed formats
            if (dest.left == 0 && dest.top == 0)
            {
                glCompressedTexImage2D(mFaceTarget, mLevel,
                                       format,
                                       dest.getWidth(),
                                       dest.getHeight(),
                                       0,
                                       data.getConsecutiveSize(),
                                       data.data);
                GL_CHECK_ERROR;
            }
            else
            {
                glCompressedTexSubImage2D(mFaceTarget, mLevel,
                                          dest.left, dest.top,
                                          dest.getWidth(), dest.getHeight(),
                                          format, data.getConsecutiveSize(),
                                          data.data);

                GL_CHECK_ERROR;
            }
        }
        else if (mSoftwareMipmap)
        {
            if (data.getWidth() != data.rowPitch)
            {
                // TODO
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                            "Unsupported texture format",
                            "GLES2TextureBuffer::upload");
            }

            if (data.getHeight() * data.getWidth() != data.slicePitch)
            {
                // TODO
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                            "Unsupported texture format",
                            "GLES2TextureBuffer::upload");
            }

            glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
            GL_CHECK_ERROR;
            buildMipmaps(data);
        }
        else
        {
            if(data.getWidth() != data.rowPitch)
            {
                // TODO
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                            "Unsupported texture format",
                            "GLES2TextureBuffer::upload");
            }

            if(data.getHeight()*data.getWidth() != data.slicePitch)
            {
                // TODO
                OGRE_EXCEPT(Exception::ERR_INVALIDPARAMS,
                    "Unsupported texture format",
                    "GLES2TextureBuffer::upload");
            }

            if ((data.getWidth() * PixelUtil::getNumElemBytes(data.format)) & 3) {
                // Standard alignment of 4 is not right
                glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
                GL_CHECK_ERROR;
            }

            glTexSubImage2D(mFaceTarget,
                            mLevel,
                            dest.left, dest.top,
                            dest.getWidth(), dest.getHeight(),
                            GLES2PixelUtil::getGLOriginFormat(data.format),
                            GLES2PixelUtil::getGLOriginDataType(data.format),
                            data.data);
        }
        
        if ((mUsage & TU_AUTOMIPMAP) && !mSoftwareMipmap && (mLevel == 0))
        {
            glGenerateMipmap(mFaceTarget);
            GL_CHECK_ERROR;
        }

        glPixelStorei(GL_UNPACK_ALIGNMENT, 4);
        GL_CHECK_ERROR;
    }