2009-10-10 9 views
0

J'ai fait une méthode à CompressImageSize selon la qualité d'image. Le code estComportement étrange de GDI +

public static Image CompressImage(string imagePath, long quality) 
{ 
    Image srcImg = LoadImage(imagePath); 
    //Image srcImg = Image.FromFile(imagePath); 

    EncoderParameters parameters = new EncoderParameters(1); 
    parameters.Param[0] = new EncoderParameter(Encoder.Quality, quality); 

    ImageCodecInfo encoder = GetCodecInfo("image/jpeg"); 

    srcImg.Save("d:\\creatives\\abcd123.jpg", encoder, parameters); 
} 

public static Image LoadImage(string filename) 
{ 
    using (FileStream fs = new FileStream(filename, FileMode.Open)) 
    { 
     return(Image.FromStream(fs)); 
    } 
} 

Maintenant, quand je lance ce code tout comme il me donne une « exception GDI générique + », tout en économisant l'srcImg (dernière ligne FunC# 1), mais quand je décommenter la 2ème ligne et chargez l'image en utilisant Image.FromFile tout fonctionne bien.

Pourquoi?

Répondre

0

Vous devez réécrire votre code:

public static Image LoadImage(string filename) 
{ 
    FileStream fs = new FileStream(filename, FileMode.Open);   
    return Image.FromStream(fs);   
} 

Construction using est faux dans ce cas parce que FileStream a besoin d'être en vie pour utiliser votre image.

0

Une conjecture sauvage ... L'image est IDisposable. Appelez-vous ceci dans une boucle ou quelque chose? Essayez de mettre votre image elle-même dans un bloc using()?

0

À la fin de LoadImage, le FileStream contenant l'image est éliminé. C'est trop tôt. le flux de fichier doit être actif pour être utilisé par la méthode appelant LoadImage.

Voir using sur MSDN.

3

Selon MSDN:

Remarques: Vous devez garder le flux ouvert pendant toute la durée de l'image.

Ici votre flux est dans un bloc d'utilisation et donc fermé avant la fin de la durée de vie de l'image.

0

Il existe plusieurs problèmes avec Image.FromFile() ...

Image srcImg = Image.FromFile(imagePath); 

La déclaration ci-dessus ne fermera pas le flux de fichiers et qui va créer des problèmes si vous souhaitez accéder à nouveau le fichier ou le supprimer. J'écrirais votre fonction de cette façon.

public static Image CompressImage(string imagePath, long quality) 
{ 
    using(FileStream fs = File.OpenRead(imagePath)){ 
     Image srcImg = Image.FromStream(fs);  

     EncoderParameters parameters = new EncoderParameters(1);  
     parameters.Param[0] = new EncoderParameter(Encoder.Quality, quality);  
     ImageCodecInfo encoder = GetCodecInfo("image/jpeg");  
     srcImg.Save("d:\\creatives\\abcd123.jpg", encoder, parameters); 
    } 
} 

Ceci garantira que mon fichier sera fermé à la fin de l'utilisation de la portée.

0

Fix, mais pour moi l'appel Dispose est un bogue dans le cadre de .net ...

public static Image CompressImage(string imagePath, long quality) 
{ 
    Image srcImg = LoadImage(imagePath); 
    //Image srcImg = Image.FromFile(imagePath); 

    EncoderParameters parameters = new EncoderParameters(1); 
    parameters.Param[0] = new EncoderParameter(Encoder.Quality, quality); 

    ImageCodecInfo encoder = GetCodecInfo("image/jpeg"); 

    srcImg.Save("d:\\creatives\\abcd123.jpg", encoder, parameters); 
srcImg.Dispose(); 
}