//------------------------------------------------------------------------------ static byte* Decode(WEBP_CSP_MODE mode, byte* data, uint data_size, int* width, int* height, WebPDecBuffer* keep_info) { WebPDecParams params; WebPDecBuffer output; WebPInitDecBuffer(&output); WebPResetDecParams(¶ms); params.output = &output; output.colorspace = mode; // Retrieve (and report back) the required dimensions from bitstream. if (!WebPGetInfo(data, data_size, &output.width, &output.height)) { return null; } if (width != null) *width = output.width; if (height != null) *height = output.height; // Decode if (DecodeInto(data, data_size, ¶ms) != VP8_STATUS_OK) { return null; } if (keep_info != null) { // keep track of the side-info WebPCopyDecBuffer(&output, keep_info); } // return decoded samples (don't clear 'output'!) return (mode >= MODE_YUV) ? output.u.YUVA.y : output.u.RGBA.rgba; }
/// <summary> /// Returns true if the given mode is RGB(A) /// </summary> /// <param name="mode"></param> /// <returns></returns> public static bool WebPIsRGBMode(WEBP_CSP_MODE mode) { return(mode < WEBP_CSP_MODE.MODE_YUV); }
// Some useful macros: /// <summary> /// Returns true if the specified mode uses a premultiplied alpha /// </summary> /// <param name="mode"></param> /// <returns></returns> public static bool WebPIsPremultipliedMode(WEBP_CSP_MODE mode) { return(mode == WEBP_CSP_MODE.MODE_rgbA || mode == WEBP_CSP_MODE.MODE_bgrA || mode == WEBP_CSP_MODE.MODE_Argb || mode == WEBP_CSP_MODE.MODE_rgbA_4444); }
/// <summary> /// Loads an image from webp into a byte array in RGBA format. /// </summary> /// <returns>The RGBA from web p.</returns> /// <param name="lData">L data.</param> /// <param name="lWidth">L width.</param> /// <param name="lHeight">L height.</param> /// <param name="lMipmaps">If set to <c>true</c> l mipmaps.</param> /// <param name="lError">L error.</param> /// <param name="scalingFunction">Scaling function.</param> public static Status DecodeWebP(byte[] lInput, ref int lWidth, ref int lHeight, ref WEBP_CSP_MODE lColorSpace, bool lMipmaps, out byte[] lOutput, bool lReducedColorRange = false, bool lReducedScale = false) { Status lStatus = 0; int lLength = lInput.Length; int lBytesPerTexel = 4; GCHandle lHandle = GCHandle.Alloc(lInput, GCHandleType.Pinned); { IntPtr lDataPtr = lHandle.AddrOfPinnedObject(); WebPDecoderConfig config = new WebPDecoderConfig(); if (NativeBindings.WebPInitDecoderConfig(ref config) == 0) { throw new Exception("WebPInitDecoderConfig failed. Wrong version?"); } if (lReducedScale == true) { lWidth /= 2; lHeight /= 2; } // Set up decode options config.options.use_threads = 0; if (lReducedScale == true) { config.options.use_scaling = 1; config.options.scaled_width = lWidth; config.options.scaled_height = lHeight; } // read the .webp input file information VP8StatusCode result = NativeBindings.WebPGetFeatures((IntPtr)lDataPtr, (UIntPtr)lLength, ref config.input); if (result != VP8StatusCode.VP8_STATUS_OK) { throw new Exception(string.Format("Failed WebPGetFeatures with error {0}.", result.ToString())); } // confirm colorspace. if (config.input.has_alpha > 0) { if (lReducedColorRange == true) { lColorSpace = WEBP_CSP_MODE.MODE_RGBA_4444; lBytesPerTexel = 2; } else { lColorSpace = WEBP_CSP_MODE.MODE_RGBA; lBytesPerTexel = 4; } } else { if (lReducedColorRange == true) { lColorSpace = WEBP_CSP_MODE.MODE_RGB_565; lBytesPerTexel = 2; } else { lColorSpace = WEBP_CSP_MODE.MODE_RGB; lBytesPerTexel = 3; } } // Bytes per texel can only be calculated at this point... int lStride = lBytesPerTexel * lWidth; // If mipmaps are requested we need to create 1/3 more memory for the mipmaps to be generated in. int lSize = lHeight * lStride; if (lMipmaps) // don't do this here.. { // bit shift instead of this crude approach.,... lSize += Mathf.CeilToInt((float)lSize / 3.0f); } lOutput = new byte[lSize]; GCHandle lOutHandle = GCHandle.Alloc(lOutput, GCHandleType.Pinned); IntPtr lOutputPtr = lOutHandle.AddrOfPinnedObject(); { // As we have to reverse the y order of the data, we pass through a negative stride and // pass through a pointer to the last line of the data. IntPtr lTmpDataPtr = new IntPtr(lOutputPtr.ToInt64() + (lSize - lStride)); // specify the output format config.output.colorspace = lColorSpace; config.output.u.RGBA.rgba = lTmpDataPtr; config.output.u.RGBA.stride = -lStride; config.output.u.RGBA.size = (UIntPtr)lSize; config.output.height = lHeight; config.output.width = lWidth; config.output.is_external_memory = 1; // Decode result = NativeBindings.WebPDecode((IntPtr)lDataPtr, (UIntPtr)lLength, ref config); if (result != VP8StatusCode.VP8_STATUS_OK) { throw new Exception(string.Format("Failed WebPDecode with error {0}.", result.ToString())); } } lOutHandle.Free(); lStatus = Status.SUCCESS; } lHandle.Free(); return(lStatus); }
public static extern IntPtr WebPINewRGB(WEBP_CSP_MODE csp, IntPtr output_buffer, UIntPtr output_buffer_size, int output_stride);
public static int WebPIsRGBMode(WEBP_CSP_MODE mode) { return(((int)mode < (int)(MODE_YUV)) ? 1 : 0); }
public static int WebPIsAlphaMode(WEBP_CSP_MODE mode) { return((mode == MODE_RGBA || mode == MODE_BGRA || mode == MODE_ARGB || mode == MODE_RGBA_4444 || mode == MODE_YUVA || (WebPIsPremultipliedMode(mode)) != 0) ? 1 : 0); }
public static extern WebPIDecoder *WebPINewRGB(WEBP_CSP_MODE csp, [NativeTypeName("uint8_t *")] byte *output_buffer, [NativeTypeName("size_t")] UIntPtr output_buffer_size, int output_stride);
/// <summary> /// Returns true if the given mode is RGB(A) /// </summary> /// <param name="mode"></param> /// <returns></returns> public static bool WebPIsRGBMode(WEBP_CSP_MODE mode) { return (mode < WEBP_CSP_MODE.MODE_YUV); }
// Check that webp_csp_mode is within the bounds of WEBP_CSP_MODE. // Convert to an integer to handle both the unsigned/signed enum cases // without the need for casting to remove type limit warnings. static bool IsValidColorspace(WEBP_CSP_MODE webp_csp_mode) { return (((int)webp_csp_mode >= (int)WEBP_CSP_MODE.MODE_RGB) && ((int)webp_csp_mode < (int)WEBP_CSP_MODE.MODE_LAST)); }
// Some useful macros: /// <summary> /// Returns true if the specified mode uses a premultiplied alpha /// </summary> /// <param name="mode"></param> /// <returns></returns> public static bool WebPIsPremultipliedMode(WEBP_CSP_MODE mode) { return (mode == WEBP_CSP_MODE.MODE_rgbA || mode == WEBP_CSP_MODE.MODE_bgrA || mode == WEBP_CSP_MODE.MODE_Argb || mode == WEBP_CSP_MODE.MODE_rgbA_4444); }
/// <summary> /// Returns true if the given mode has an alpha channel /// </summary> /// <param name="mode"></param> /// <returns></returns> public static bool WebPIsAlphaMode(WEBP_CSP_MODE mode) { return (mode == WEBP_CSP_MODE.MODE_RGBA || mode == WEBP_CSP_MODE.MODE_BGRA || mode == WEBP_CSP_MODE.MODE_ARGB || mode == WEBP_CSP_MODE.MODE_RGBA_4444 || mode == WEBP_CSP_MODE.MODE_YUVA || WebPIsPremultipliedMode(mode)); }
// Helpers static byte* DecodeIntoRGBABuffer(WEBP_CSP_MODE colorspace, byte* data, uint data_size, byte* rgba, int stride, int size) { WebPDecParams params; WebPDecBuffer buf; if (rgba == null) { return null; } WebPInitDecBuffer(&buf); WebPResetDecParams(¶ms); params.output = &buf; buf.colorspace = colorspace; buf.u.RGBA.rgba = rgba; buf.u.RGBA.stride = stride; buf.u.RGBA.size = size; buf.is_external_memory = 1; if (DecodeInto(data, data_size, ¶ms) != VP8_STATUS_OK) { return null; } return rgba; }
/// <summary> /// Returns true if the given mode has an alpha channel /// </summary> /// <param name="mode"></param> /// <returns></returns> public static bool WebPIsAlphaMode(WEBP_CSP_MODE mode) { return(mode == WEBP_CSP_MODE.MODE_RGBA || mode == WEBP_CSP_MODE.MODE_BGRA || mode == WEBP_CSP_MODE.MODE_ARGB || mode == WEBP_CSP_MODE.MODE_RGBA_4444 || mode == WEBP_CSP_MODE.MODE_YUVA || WebPIsPremultipliedMode(mode)); }
public static int WebPIsPremultipliedMode(WEBP_CSP_MODE mode) { return((mode == MODE_rgbA || mode == MODE_bgrA || mode == MODE_Argb || mode == MODE_rgbA_4444) ? 1 : 0); }
static int IsAlphaMode(WEBP_CSP_MODE mode) { return (mode == MODE_RGBA || mode == MODE_BGRA || mode == MODE_ARGB || mode == MODE_RGBA_4444 || mode == MODE_YUVA); }