private static void CompressPvrtc(TextureContent content, bool generateMipmaps, bool premultipliedAlpha)
        {
            // TODO: Once uncompressed mipmap generation is supported, first use NVTT to generate mipmaps,
            // then compress them withthe PVRTC tool, so we have the same implementation of mipmap generation
            // across platforms.

            // Calculate number of mip levels
            var width             = content.Faces[0][0].Height;
            var height            = content.Faces[0][0].Width;
            var numberOfMipLevels = 1;

            if (generateMipmaps)
            {
                while (height != 1 || width != 1)
                {
                    height = Math.Max(height / 2, 1);
                    width  = Math.Max(width / 2, 1);
                    numberOfMipLevels++;
                }
            }

            IntPtr dataSizesPtr = IntPtr.Zero;
            var    texDataPtr   = ManagedPVRTC.ManagedPVRTC.CompressTexture(content.Faces[0][0].GetPixelData(),
                                                                            content.Faces[0][0].Height,
                                                                            content.Faces[0][0].Width,
                                                                            numberOfMipLevels,
                                                                            premultipliedAlpha,
                                                                            true,
                                                                            ref dataSizesPtr);

            // Store the size of each mip level
            var dataSizesArray = new int[numberOfMipLevels];

            Marshal.Copy(dataSizesPtr, dataSizesArray, 0, dataSizesArray.Length);

            var levelSize = 0;

            byte[] levelData;
            var    sourceWidth  = content.Faces[0][0].Width;
            var    sourceHeight = content.Faces[0][0].Height;

            content.Faces[0].Clear();

            for (int x = 0; x < numberOfMipLevels; x++)
            {
                levelSize = dataSizesArray[x];
                levelData = new byte[levelSize];

                Marshal.Copy(texDataPtr, levelData, 0, levelSize);

                var levelWidth  = Math.Max(sourceWidth >> x, 1);
                var levelHeight = Math.Max(sourceHeight >> x, 1);

                var bmpContent = new PvrtcBitmapContent(4, sourceWidth, sourceHeight);
                bmpContent.SetPixelData(levelData);
                content.Faces[0].Add(bmpContent);

                texDataPtr = IntPtr.Add(texDataPtr, levelSize);
            }
        }
Exemple #2
0
        private static void CompressPvrtc(TextureContent content, bool generateMipmaps, bool premultipliedAlpha)
        {
            // TODO: Once uncompressed mipmap generation is supported, first use NVTT to generate mipmaps,
            // then compress them withthe PVRTC tool, so we have the same implementation of mipmap generation
            // across platforms.

            // Calculate number of mip levels
            var width = content.Faces[0][0].Height;
            var height = content.Faces[0][0].Width;

			if (!IsPowerOfTwo(width) || !IsPowerOfTwo(height))
				throw new PipelineException("PVRTC Compressed textures width and height must be powers of two.");

			if (width != height)
				throw new PipelineException("PVRTC Compressed textures must be square. i.e width == height.");

            var numberOfMipLevels = 1;
            if (generateMipmaps)
            {
                while (height != 1 || width != 1)
                {
                    height = Math.Max(height / 2, 1);
                    width = Math.Max(width / 2, 1);
                    numberOfMipLevels++;
                }
            }

            IntPtr dataSizesPtr = IntPtr.Zero;
            var texDataPtr = ManagedPVRTC.ManagedPVRTC.CompressTexture(content.Faces[0][0].GetPixelData(),
                                            content.Faces[0][0].Height,
                                            content.Faces[0][0].Width,
                                            numberOfMipLevels,
                                            premultipliedAlpha,
                                            true,
                                            ref dataSizesPtr);

            // Store the size of each mip level
            var dataSizesArray = new int[numberOfMipLevels];
            Marshal.Copy(dataSizesPtr, dataSizesArray, 0, dataSizesArray.Length);

            var levelSize = 0;
            byte[] levelData;
            var sourceWidth = content.Faces[0][0].Width;
            var sourceHeight = content.Faces[0][0].Height;

            content.Faces[0].Clear();

            for (int x = 0; x < numberOfMipLevels; x++)
            {
                levelSize = dataSizesArray[x];
                levelData = new byte[levelSize];

                Marshal.Copy(texDataPtr, levelData, 0, levelSize);

                var levelWidth = Math.Max(sourceWidth >> x, 1);
                var levelHeight = Math.Max(sourceHeight >> x, 1);

                var bmpContent = new PvrtcBitmapContent(4, sourceWidth, sourceHeight);
                bmpContent.SetPixelData(levelData);
                content.Faces[0].Add(bmpContent);

                texDataPtr = IntPtr.Add(texDataPtr, levelSize);
            }
        }