From f055a858e28255d4717baa9fdebfdb04b2c19b05 Mon Sep 17 00:00:00 2001 From: James Jackson-South Date: Tue, 8 Nov 2016 14:28:15 +1100 Subject: [PATCH] Remove lists --- src/ImageSharp/Formats/Png/PngEncoderCore.cs | 49 ++++++++------------ 1 file changed, 20 insertions(+), 29 deletions(-) diff --git a/src/ImageSharp/Formats/Png/PngEncoderCore.cs b/src/ImageSharp/Formats/Png/PngEncoderCore.cs index 03f74d5a7..275b79442 100644 --- a/src/ImageSharp/Formats/Png/PngEncoderCore.cs +++ b/src/ImageSharp/Formats/Png/PngEncoderCore.cs @@ -322,29 +322,28 @@ namespace ImageSharp.Formats private byte[] EncodePixelData() { // TODO: Use pointers - List filteredScanlines = new List(); - + byte[][] filteredScanlines = new byte[this.height][]; byte[] previousScanline = new byte[this.width * this.bytesPerPixel]; - + int length = 0; for (int y = 0; y < this.height; y++) { byte[] rawScanline = this.GetRawScanline(y); byte[] filteredScanline = this.GetOptimalFilteredScanline(rawScanline, previousScanline, this.bytesPerPixel); - - filteredScanlines.Add(filteredScanline); + length += filteredScanline.Length; + filteredScanlines[y] = filteredScanline; previousScanline = rawScanline; } - // TODO: We should be able to use a byte array when not using interlaced encoding. - List result = new List(); - - foreach (byte[] encodedScanline in filteredScanlines) + // Flatten the jagged array + byte[] result = new byte[length]; + for (int i = 0; i < this.height; i++) { - result.AddRange(encodedScanline); + int len = filteredScanlines[i].Length; + Buffer.BlockCopy(filteredScanlines[i], 0, result, i * len, len); } - return result.ToArray(); + return result; } /// @@ -357,32 +356,24 @@ namespace ImageSharp.Formats /// The private byte[] GetOptimalFilteredScanline(byte[] rawScanline, byte[] previousScanline, int byteCount) { - List> candidates = new List>(); + Tuple[] candidates = new Tuple[4]; - if (this.PngColorType == PngColorType.Palette) - { - byte[] none = NoneFilter.Encode(rawScanline); - candidates.Add(new Tuple(none, this.CalculateTotalVariation(none))); - } - else - { - byte[] sub = SubFilter.Encode(rawScanline, byteCount); - candidates.Add(new Tuple(sub, this.CalculateTotalVariation(sub))); + byte[] sub = SubFilter.Encode(rawScanline, byteCount); + candidates[0] = new Tuple(sub, this.CalculateTotalVariation(sub)); - byte[] up = UpFilter.Encode(rawScanline, previousScanline); - candidates.Add(new Tuple(up, this.CalculateTotalVariation(up))); + byte[] up = UpFilter.Encode(rawScanline, previousScanline); + candidates[1] = new Tuple(up, this.CalculateTotalVariation(up)); - byte[] average = AverageFilter.Encode(rawScanline, previousScanline, byteCount); - candidates.Add(new Tuple(average, this.CalculateTotalVariation(average))); + byte[] average = AverageFilter.Encode(rawScanline, previousScanline, byteCount); + candidates[2] = new Tuple(average, this.CalculateTotalVariation(average)); - byte[] paeth = PaethFilter.Encode(rawScanline, previousScanline, byteCount); - candidates.Add(new Tuple(paeth, this.CalculateTotalVariation(paeth))); - } + byte[] paeth = PaethFilter.Encode(rawScanline, previousScanline, byteCount); + candidates[3] = new Tuple(paeth, this.CalculateTotalVariation(paeth)); int lowestTotalVariation = int.MaxValue; int lowestTotalVariationIndex = 0; - for (int i = 0; i < candidates.Count; i++) + for (int i = 0; i < 4; i++) { if (candidates[i].Item2 < lowestTotalVariation) {