Cześć,
Mam metodę która kompresuje zdjęcie i je zwraca, używam do tego również strumienia MemmoryStream. Problem pojawia się taki, że jeżeli zwracam zdjęcie i zamknę strumie to wyskakuje error przy zapisie zdjęcia poza metodą "System.Runtime.InteropServices.ExternalException: „A generic error occurred in GDI+.”". Jedni mówią, że strumienia zamykać nie trzeba, lecz niestety mam taki wymóg aby go zamknąć. Jeżeli zdjęcie zapiszę do bitmapy to wszystko działa, lecz jest większy rozmiar niż jakbym samo zdjęcie zwrócił. Czy ma ktoś jakąś wskazówkę aby lepiej to zrobić?
Cała metoda odpowiedzialna za kompresje(w której zwracam obraz i występuje error przy zapisie poza metodą)
public static Image Compress(this Image img, string format, long compression)
{
if (compression <= 0 || compression > 100)
{
throw new ArgumentException("Wartość kompresji wykracza poza skalę <1-100>", nameof(compression));
}
Encoder enc;
EncoderParameters encoderParameters;
EncoderParameter encoderParameter;
Image compressedImg;
ImageCodecInfo ImgFormat;
using (Bitmap bmp = new Bitmap(img))
{
switch (format)
{
case "tiff":
case "tif":
enc = Encoder.Compression;
encoderParameters = new EncoderParameters(1);
encoderParameter = new EncoderParameter(enc, (long)EncoderValue.CompressionLZW);
encoderParameters.Param[0] = encoderParameter;
ImgFormat = GetEncoder(ImageFormat.Tiff);
break;
default:
enc = Encoder.Quality;
encoderParameters = new EncoderParameters(1);
encoderParameter = new EncoderParameter(enc, compression);
encoderParameters.Param[0] = encoderParameter;
ImgFormat = GetEncoder(ImageFormat.Jpeg);
break;
}
var flipTypeValue = img.PropertyItems.SingleOrDefault(x => x.Id == 0x0112)?.Value;
if (flipTypeValue != null && flipTypeValue.Length > 0)
{
var flipType = DecodeImageRotateFlipType(flipTypeValue[0]);
bmp.RotateFlip(flipType);
}
MemoryStream ms = new MemoryStream();
if (format.Equals("png"))
{
bmp.Save(ms, ImageFormat.Png);
}
else
{
bmp.Save(ms, ImgFormat, encoderParameters);
}
compressedImg = Image.FromStream(ms);
ms.Dispose();
return compressedImg;
}
}
Jeżeli końcówkę zamienię na coś takiego, to wszystko działa ale niestety obrazy są kompresowane ale wyniki są większe niż przy zwracaniu jak wyżej (pewnie bitmapa zajmuje miejsce)
MemoryStream ms = new MemoryStream();
if (format.Equals("png"))
{
Console.WriteLine("test3");
bmp.Save(ms, ImageFormat.Png);
}
else
{
Console.WriteLine("test4");
bmp.Save(ms, ImgFormat, encoderParameters);
}
compressedImg = Image.FromStream(ms);
Bitmap bm = new Bitmap(compressedImg);
ms.Dispose();
return bm;
}
}