示例#1
0
        private unsafe void uploadATFTextureFromByteArray(ByteArray data, uint byteArrayOffset)
        {
            data.position = byteArrayOffset;

            // read atf signature
            string signature = data.readUTFBytes(3);

            if (signature != "ATF")
            {
                throw new InvalidDataException("ATF signature not found");
            }

            // read atf length
            uint length = readUInt24(data);

            if ((byteArrayOffset + length) > data.length)
            {
                throw new InvalidDataException("ATF length exceeds byte array length");
            }

            // get format
            uint    tdata = data.readUnsignedByte( );
            AtfType type  = (AtfType)(tdata >> 7);

            if (type != AtfType.NORMAL)
            {
                throw new NotImplementedException("ATF Cube maps are not supported");
            }

//			Removing ATF format limitation to allow for multiple format support.
//			AtfFormat format = (AtfFormat)(tdata & 0x7f);
//			if (format != AtfFormat.Block) {
//				throw new NotImplementedException("Only ATF block compressed textures are supported");
//			}

            // get dimensions
            int width  = (1 << (int)data.readUnsignedByte());
            int height = (1 << (int)data.readUnsignedByte());

            if (width != mWidth || height != mHeight)
            {
                throw new InvalidDataException("ATF Width and height dont match");
            }

            // get mipmap count
            int mipCount = (int)data.readUnsignedByte();

            // read all mipmap levels
            for (int level = 0; level < mipCount; level++)
            {
                // read all gpu formats
                for (int gpuFormat = 0; gpuFormat < 3; gpuFormat++)
                {
                    // read block length
                    uint blockLength = readUInt24(data);
                    if ((data.position + blockLength) > data.length)
                    {
                        throw new System.IO.InvalidDataException("Block length exceeds ATF file length");
                    }

                    if (blockLength > 0)
                    {
                        // handle PVRTC on iOS
                        if (gpuFormat == 1)
                        {
                                                        #if PLATFORM_MONOTOUCH
                            OpenTK.Graphics.ES20.PixelInternalFormat pixelFormat = (OpenTK.Graphics.ES20.PixelInternalFormat) 0x8C02;
                            fixed(byte *ptr = data.getRawArray())
                            {
                                // upload from data position
                                var address = new IntPtr(ptr + data.position);

                                GL.CompressedTexImage2D(textureTarget, level, pixelFormat, width, height, 0, (int)blockLength, address);
                                mAllocated = true;
                            }

                            trackCompressedMemoryUsage((int)blockLength);
                                                        #endif
                        }
                        else if (gpuFormat == 2)
                        {
                                                        #if PLATFORM_MONODROID
                            int textureLength = width * height / 2;
                            fixed(byte *ptr = data.getRawArray())
                            {
                                var address = new IntPtr(ptr + data.position);

                                GL.CompressedTexImage2D(textureTarget, level, All.Etc1Rgb8Oes, width, height, 0, (int)textureLength, address);

                                GLUtils.CheckGLError();

                                mAllocated = true;
                                if (textureLength < blockLength)
                                {
                                    mAlphaTexture = new Texture(mContext, width, height, mFormat, mOptimizeForRenderToTexture, mStreamingLevels);
                                    var alphaAddress = new IntPtr(ptr + data.position + textureLength);

                                    GL.BindTexture(mAlphaTexture.textureTarget, mAlphaTexture.textureId);
                                    GLUtils.CheckGLError();
                                    GL.CompressedTexImage2D(mAlphaTexture.textureTarget, level, All.Etc1Rgb8Oes, width, height, 0, textureLength, alphaAddress);
                                    GLUtils.CheckGLError();
                                    GL.BindTexture(mAlphaTexture.textureTarget, 0);
                                    GLUtils.CheckGLError();
                                    mAllocated = true;
                                }
                                else
                                {
                                    mAlphaTexture = new Texture(mContext, 1, 1, mFormat, mOptimizeForRenderToTexture, mStreamingLevels);
                                    var clearData = new BitmapData(width, height, true, 0xFFFFFFFF);

                                    GL.BindTexture(mAlphaTexture.textureTarget, mAlphaTexture.textureId);
                                    GLUtils.CheckGLError();
                                    GL.TexImage2D(mAlphaTexture.textureTarget, level, (int)PixelInternalFormat.Rgba, 1, 1, 0, PixelFormat.Rgba, PixelType.UnsignedByte, clearData.getRawData());
                                    GLUtils.CheckGLError();
                                    GL.BindTexture(mAlphaTexture.textureTarget, 0);
                                    GLUtils.CheckGLError();

                                    mAllocated = true;
                                    clearData.dispose();
                                }
                            }

                            trackCompressedMemoryUsage((int)blockLength);
                                                        #endif
                        }

                        // TODO handle other formats/platforms
                    }

                    // next block data
                    data.position += blockLength;
                }
            }
        }
示例#2
0
        private unsafe void uploadATFTextureFromByteArray(ByteArray data, uint byteArrayOffset)
        {
            data.position = byteArrayOffset;

            // read atf signature
            string signature = data.readUTFBytes(3);

            if (signature != "ATF")
            {
                throw new InvalidDataException("ATF signature not found");
            }

            // read atf length
            uint length = readUInt24(data);

            if ((byteArrayOffset + length) > data.length)
            {
                throw new InvalidDataException("ATF length exceeds byte array length");
            }

            // get format
            uint    tdata = data.readUnsignedByte( );
            AtfType type  = (AtfType)(tdata >> 7);

            if (type != AtfType.NORMAL)
            {
                throw new NotImplementedException("ATF Cube maps are not supported");
            }

//			Removing ATF format limitation to allow for multiple format support.
//			AtfFormat format = (AtfFormat)(tdata & 0x7f);
//			if (format != AtfFormat.Block) {
//				throw new NotImplementedException("Only ATF block compressed textures are supported");
//			}

            // get dimensions
            int width  = (1 << (int)data.readUnsignedByte());
            int height = (1 << (int)data.readUnsignedByte());

            if (width != mWidth || height != mHeight)
            {
                throw new InvalidDataException("ATF Width and height dont match");
            }

            // get mipmap count
            int mipCount = (int)data.readUnsignedByte();

            // read all mipmap levels
            for (int level = 0; level < mipCount; level++)
            {
                // read all gpu formats
                for (int gpuFormat = 0; gpuFormat < 3; gpuFormat++)
                {
                    // read block length
                    uint blockLength = readUInt24(data);
                    if ((data.position + blockLength) > data.length)
                    {
                        throw new System.IO.InvalidDataException("Block length exceeds ATF file length");
                    }

                    if (blockLength > 0)
                    {
#if PLATFORM_MONOTOUCH
                        // handle PVRTC on iOS
                        if (gpuFormat == 1)
                        {
                            OpenTK.Graphics.ES20.PixelInternalFormat pixelFormat = (OpenTK.Graphics.ES20.PixelInternalFormat) 0x8C02;

                            fixed(byte *ptr = data.getRawArray())
                            {
                                // upload from data position
                                var address = new IntPtr(ptr + data.position);

                                GL.CompressedTexImage2D(textureTarget, level, pixelFormat, width, height, 0, (int)blockLength, address);
                            }
                        }
#endif
                        // TODO handle other formats/platforms
                    }

                    // next block data
                    data.position += blockLength;
                }
            }
        }