Est-il possible que le flux d'origine sauvegardant l'image originale ait été fermé? Si le flux derrière un bitmap a été fermé, vous commencez à recevoir des erreurs GDI +. J'ai beaucoup couru quand nous avons ajouté le traitement d'image sur notre site Web.
Si vous ouvrez l'objet Bitmap dans le débogueur Visual Studio, voyez-vous des exceptions au lieu des valeurs des propriétés? Si c'est le cas, ce n'est pas un problème avec l'opération de sauvegarde, mais la couche GDI + a perdu la capacité de traiter l'objet, période. Ce que j'ai trouvé était nécessaire pour garder une trace des MemoryStreams appartenant à mes Bitmaps et les garder tous ensemble. Le redimensionnement d'une image a donné lieu à un nouveau MemoryStream avec une nouvelle image Bitmap.
Je fini par la création de cette classe simple (coupé quelques propriétés supplémentaires inutiles ici):
public class UploadedImage : IDisposable
{
private Bitmap _img = null;
private Stream _baseStream = null;
/// <summary>
/// The image object. This must always belong to BaseStream, or weird things can happen.
/// </summary>
public Bitmap Img
{
[DebuggerStepThrough]
get { return _img; }
[DebuggerStepThrough]
set { _img = value; }
}
/// <summary>
/// The stream that stores the image. This must ALWAYS belong to Img, or weird things can happen.
/// </summary>
public Stream BaseStream
{
[DebuggerStepThrough]
get { return _baseStream; }
[DebuggerStepThrough]
set { _baseStream = value; }
}
[DebuggerStepThrough]
public void Dispose()
{
if (Img != null)
Img.Dispose();
if (BaseStream != null)
BaseStream.Close();
_attached = false;
}
}
Maintenant, je traitais des images téléchargées sur notre site Web, et ce que j'ai trouvé que lorsque Asp.Net recyclé le flux attaché à la demande, toutes les opérations d'image soudaines ont commencé à flipper. Donc, ma solution, que ce soit la meilleure façon de le faire ou non, était de copier les données du flux de téléchargement vers mon propre MemoryStream, charger l'image à partir de cela, et coller les deux dans ce conteneur. Et partout où j'ai créé une nouvelle image à partir d'un ancien, j'ai toujours gardé le flux et l'image ensemble.
J'espère que cela aide.
EDIT: Je suis également intéressé de voir comment vous faites le redimensionnement de l'image. Ceci est un extrait de la façon dont je l'ai fait la nôtre:
temp = new Bitmap(newWidth, newHeight, PIXEL_FORMAT);
temp.SetResolution(newHorizontalRes, newVerticalRes);
gr = Graphics.FromImage(temp);
//
// This copies the active frame from 'img' to the new 'temp' bitmap.
// Also resizes it and makes it super shiny. Sparkle on, mr image dude.
//
Rectangle rect = new Rectangle(0, 0, newWidth, newHeight);
gr.InterpolationMode = InterpolationMode.HighQualityBicubic;
gr.SmoothingMode = SmoothingMode.HighSpeed;
gr.PageUnit = GraphicsUnit.Pixel;
gr.DrawImage(img, rect);
//
// Image copied onto the new bitmap. Save the bitmap to a fresh memory stream.
//
retval = new UploadedImage();
retval.BaseStream = (Stream)(new MemoryStream());
temp.Save(retval.BaseStream, ImageFormat.Jpeg);
retval.Img = temp;
Vous pouvez améliorer cela en utilisant Path.GetExtension au lieu de IndexOf ('.'), Bien que vous deviez modifier légèrement le commutateur http://msdn.microsoft.com/en-us/library/system.io.path .getextension.aspx – RichardOD
Merci RichardOD ..... –
Remarque important (http://msdn.microsoft.com/en-us/library/system.drawing.aspx)> Les classes dans l'espace de noms System.Drawing ne sont pas prises en charge pour utiliser dans un service Windows ou ASP.NET. –