private Bitmap DecodeIndexInternal(byte[] data, byte[] paletteData, Size imageSize, IProgressContext progress) { ContractAssertions.IsTrue(IsIndexed, nameof(IsIndexed)); var progresses = progress?.SplitIntoEvenScopes(2); // Prepare information and instances var paddedSize = GetPaddedSize(imageSize); var swizzle = GetPixelRemapper(_indexEncoding, paddedSize); var finalSize = GetFinalSize(paddedSize, swizzle); var colorShader = _shadeColorsFunc?.Invoke(); // Load palette var paletteColorCount = paletteData.Length * 8 / _paletteEncoding.BitsPerValue * _paletteEncoding.ColorsPerValue; var setMaxProgress = progresses?[0]?.SetMaxValue(paletteColorCount * _paletteEncoding.ColorsPerValue); var paletteEnumeration = _paletteEncoding .Load(paletteData, new EncodingLoadContext(new Size(1, paletteColorCount), _taskCount)) .AttachProgress(setMaxProgress, "Decode palette colors"); // Apply color shader on palette var palette = colorShader != null?paletteEnumeration.Select(colorShader.Read).ToArray() : paletteEnumeration.ToArray(); // Load indices setMaxProgress = progresses?[1]?.SetMaxValue(finalSize.Width * finalSize.Height); var colors = _indexEncoding .Load(data, palette, new EncodingLoadContext(finalSize, _taskCount)) .AttachProgress(setMaxProgress, "Decode colors"); return(colors.ToBitmap(imageSize, paddedSize, swizzle, _anchor)); }
private Bitmap DecodeColorInternal(byte[] data, Size imageSize, IProgressContext progress) { // Prepare information and instances var paddedSize = GetPaddedSize(imageSize); var swizzle = GetPixelRemapper(_colorEncoding, paddedSize); var finalSize = GetFinalSize(paddedSize, swizzle); var colorShader = _shadeColorsFunc?.Invoke(); // Load colors var colorCount = data.Length * 8 / _colorEncoding.BitsPerValue * _colorEncoding.ColorsPerValue; var colorCountBySize = finalSize.Width * finalSize.Height; // HINT: If the data portion does not fit with the actual image size, it will cause progress irregularities. // If the given data is shorter than what is needed for the full image, we throw. // Otherwise enough data is given and the image can be fully decoded, even if excess data is not used. if (colorCount < colorCountBySize) { throw new InvalidOperationException("Given data is too short."); } var setMaxProgress = progress?.SetMaxValue(colorCountBySize * _colorEncoding.ColorsPerValue); var colors = _colorEncoding .Load(data, new EncodingLoadContext(finalSize, _taskCount)) .AttachProgress(setMaxProgress, "Decode colors"); // Apply color shader if (colorShader != null) { colors = colors.Select(colorShader.Read); } // Create image with unpadded dimensions return(colors.ToBitmap(imageSize, paddedSize, swizzle, _anchor)); }