コード例 #1
0
        protected override void PlatformCompressTexture(
            ContentProcessorContext context, TextureContent content,
            TextureProcessorOutputFormat format, bool isSpriteFont)
        {
            format = GetTextureFormatForPlatform(format, context.TargetPlatform);

            // Make sure we're in a floating point format
            content.ConvertBitmapType(typeof(PixelBitmapContent <RgbaVector>));

            switch (format)
            {
            case TextureProcessorOutputFormat.AtcCompressed:
                GraphicsUtil.CompressAti(content, isSpriteFont);
                break;

            case TextureProcessorOutputFormat.Color16Bit:
                GraphicsUtil.CompressColor16Bit(content);
                break;

            case TextureProcessorOutputFormat.DxtCompressed:
                GraphicsUtil.CompressDxt(context, content, isSpriteFont);
                break;

            case TextureProcessorOutputFormat.Etc1Compressed:
                GraphicsUtil.CompressEtc1(context, content, isSpriteFont);
                break;

            case TextureProcessorOutputFormat.PvrCompressed:
                GraphicsUtil.CompressPvrtc(context, content, isSpriteFont);
                break;
            }
        }
コード例 #2
0
        public static void CompressDxt(ContentProcessorContext context, TextureContent content, bool isSpriteFont)
        {
            var face = content.Faces[0][0];

            if (context.TargetProfile == GraphicsProfile.Reach)
            {
                if (!IsPowerOfTwo(face.Width) || !IsPowerOfTwo(face.Height))
                {
                    throw new PipelineException(
                              "DXT compression requires width and height must " +
                              "be powers of two in Reach graphics profile.");
                }
            }

            // Test the alpha channel to figure out if we have alpha.
            var alphaRange = CalculateAlphaRange(face);

            // TODO: This isn't quite right.
            //
            // We should be generating DXT1 textures for cutout alpha
            // as DXT1 supports 1bit alpha and it uses less memory.
            //
            // XNA never generated DXT3 for textures... it always picked
            // between DXT1 for cutouts and DXT5 for fractional alpha.
            //
            // DXT3 however can produce better results for high frequency
            // alpha like a chain link fence where is DXT5 is better for
            // low frequency alpha like clouds. I don't know how we can
            // pick the right thing in this case without a hint.

            if (isSpriteFont)
            {
                CompressFontDXT3(content);
            }
            else if (alphaRange == AlphaRange.Opaque)
            {
                content.ConvertBitmapType(typeof(Dxt1BitmapContent));
            }
            else if (alphaRange == AlphaRange.Cutout)
            {
                content.ConvertBitmapType(typeof(Dxt3BitmapContent));
            }
            else
            {
                content.ConvertBitmapType(typeof(Dxt5BitmapContent));
            }
        }
コード例 #3
0
        public static void CompressColor16Bit(TextureContent content)
        {
            var face       = content.Faces[0][0];
            var alphaRange = CalculateAlphaRange(face);

            if (alphaRange == AlphaRange.Opaque)
            {
                content.ConvertBitmapType(typeof(PixelBitmapContent <Bgr565>));
            }
            else if (alphaRange == AlphaRange.Cutout)
            {
                content.ConvertBitmapType(typeof(PixelBitmapContent <Bgra5551>));
            }
            else
            {
                content.ConvertBitmapType(typeof(PixelBitmapContent <Bgra4444>));
            }
        }
コード例 #4
0
        public static void CompressAti(TextureContent content, bool isSpriteFont)
        {
            // If sharp alpha is required (for a font texture page), use 16-bit color instead of PVR
            if (isSpriteFont)
            {
                CompressColor16Bit(content);
                return;
            }

            var face       = content.Faces[0][0];
            var alphaRange = CalculateAlphaRange(face);

            if (alphaRange == AlphaRange.Full)
            {
                content.ConvertBitmapType(typeof(AtcExplicitBitmapContent));
            }
            else
            {
                content.ConvertBitmapType(typeof(AtcInterpolatedBitmapContent));
            }
        }
コード例 #5
0
        public static void CompressEtc1(ContentProcessorContext context, TextureContent content, bool isSpriteFont)
        {
            // If sharp alpha is required (for a font texture page), use 16-bit color instead of PVR
            if (isSpriteFont)
            {
                CompressColor16Bit(content);
                return;
            }

            var face       = content.Faces[0][0];
            var alphaRange = CalculateAlphaRange(face);

            // Use BGRA4444 for textures with non-opaque alpha values
            if (alphaRange != AlphaRange.Opaque)
            {
                content.ConvertBitmapType(typeof(PixelBitmapContent <Bgra4444>));
            }
            else
            {
                // PVR SGX does not handle non-POT ETC1 textures.
                // https://code.google.com/p/libgdx/issues/detail?id=1310
                // Since we already enforce POT for PVR and DXT in Reach, we will also enforce POT for ETC1
                if (!IsPowerOfTwo(face.Width) || !IsPowerOfTwo(face.Height))
                {
                    context.Logger.LogWarning(
                        null, content.Identity,
                        "ETC1 compression requires width and height to be powers of two due to " +
                        "hardware restrictions on some devices. Falling back to BGR565.");

                    content.ConvertBitmapType(typeof(PixelBitmapContent <Bgr565>));
                }
                else
                {
                    content.ConvertBitmapType(typeof(Etc1BitmapContent));
                }
            }
        }
コード例 #6
0
        public static void CompressPvrtc(ContentProcessorContext context, TextureContent content, bool isSpriteFont)
        {
            // If sharp alpha is required (for a font texture page), use 16-bit color instead of PVR
            if (isSpriteFont)
            {
                CompressColor16Bit(content);
                return;
            }

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

            if (IsPowerOfTwo(width) && IsPowerOfTwo(height) && width == height)
            {
                var face       = content.Faces[0][0];
                var alphaRange = CalculateAlphaRange(face);

                if (alphaRange == AlphaRange.Opaque)
                {
                    content.ConvertBitmapType(typeof(PvrtcRgb4BitmapContent));
                }
                else
                {
                    content.ConvertBitmapType(typeof(PvrtcRgba4BitmapContent));
                }
            }
            else
            {
                context.Logger.LogWarning(
                    null, content.Identity,
                    "PVR compression requires width and height to " +
                    "be powers of two and equal. Falling back to 16-bit color.");

                CompressColor16Bit(content);
            }
        }
コード例 #7
0
        /// <summary>
        /// Performs conversion of the texture content to the correct format.
        /// </summary>
        /// <param name="context">The processor context.</param>
        /// <param name="content">The content to be compressed.</param>
        /// <param name="format">The user requested format for compression.</param>
        /// <param name="isSpriteFont">If the texture has represents a sprite font, i.e. is greyscale and has sharp black/white contrast.</param>
        public void ConvertTexture(
            ContentProcessorContext context, TextureContent content, TextureProcessorOutputFormat format, bool isSpriteFont)
        {
            // We do nothing in this case.
            if (format == TextureProcessorOutputFormat.NoChange)
            {
                return;
            }

            // If this is color just make sure the format is right and return it.
            if (format == TextureProcessorOutputFormat.Color)
            {
                content.ConvertBitmapType(typeof(PixelBitmapContent <Color>));
                return;
            }

            // Handle this common compression format.
            if (format == TextureProcessorOutputFormat.Color16Bit)
            {
                GraphicsUtil.CompressColor16Bit(content);
                return;
            }

            try
            {
                // All other formats require platform specific choices.
                PlatformCompressTexture(context, content, format, isSpriteFont);
            }
            catch (EntryPointNotFoundException ex)
            {
                context.Logger.LogImportantMessage("Could not find the entry point to compress the texture. " + ex.ToString());
                throw;
            }
            catch (DllNotFoundException ex)
            {
                context.Logger.LogImportantMessage("Could not compress texture. Required shared lib is missing. " + ex.ToString());
                throw;
            }
            catch (Exception ex)
            {
                context.Logger.LogImportantMessage("Could not convert texture. " + ex.ToString());
                throw;
            }
        }