[.NET] Qualitätsverlust bei Bild-Resize

Dieses Thema im Forum "Programmierung & Entwicklung" wurde erstellt von foxi, 11. September 2008 .

Schlagworte:
Status des Themas:
Es sind keine weiteren Antworten möglich.
  1. 11. September 2008
    Qualitätsverlust bei Bild-Resize

    Mein Problem besteht dadrin, dass bei einem Resize von größeren Bildern (z.B. über 2000 Pixeln) ein wirklich sichtbarer Qualitätsverlust zu sehen ist.

    Ich poste hier mal das Programm, mit welchem ich die Bilder verkleiner. Das ganze ist eine Konsolenanwendung.

    Code:
    using System;
    using System.Collections.Generic;
    using System.Text;
    using System.IO;
    
    namespace ResizeIt
    {
     class Program
     {
     // Methode um die Strings zu bauen / lesen zu können
     private static string GetArg(string[] args, string sArgName)
     {
     for (int i = 0; i < args.Length; i++)
     {
     if (args[i] == "-" + sArgName && args.Length >= i)
     {
     return args[i + 1];
     }
     }
    
     return "";
     }
    
     // Methode um Endung (.jpg) abzuschneiden
     private static string RemoveExtension(string sFilename)
     {
     return sFilename.Substring(0, sFilename.IndexOf('.'));
     }
    
     // Methode um nur die Endung (.jpg) zu bekommen
     private static string GetExtension(string sFilename)
     {
     return sFilename.Substring(sFilename.IndexOf('.') + 1);
     }
    
     // Hauptroutine
     static void Main(string[] args)
     {
     // Falls alle Parameter vollständig sind
     if (GetArg(args, "x") != "" && GetArg(args, "dir") != "" && GetArg(args, "dest") != "")
     {
     // Lese alle (.jpg) Dateien aus dem Stammverzeichnis ein
     string[] folder_item = Directory.GetFiles(GetArg(args, "dir"), "*.jpg");
    
     // Versuch die Bilder neu zu skalieren
     try
     {
     // Durchlaufe solange (.jpg) Dateien vorhanden sind
     foreach (string files in folder_item)
     {
     // neue Bitmaps für files
     System.Drawing.Bitmap bmpTemp = new System.Drawing.Bitmap(files);
     
     // Berechnung der Seitenverhältnisse
     double item_x = bmpTemp.Width;
     double item_y = bmpTemp.Height;
     double dimension = (item_y / item_x);
    
     // Seitenverhältnisse an neue Breite anpassen
     double new_item_x = Convert.ToDouble(GetArg(args, "x"));
     double new_item_y = (new_item_x * dimension);
    
     System.Drawing.Image.GetThumbnailImageAbort myCallback = new System.Drawing.Image.GetThumbnailImageAbort(ThumbnailCallback);
     System.Drawing.Image imgTemp = bmpTemp.GetThumbnailImage(Convert.ToInt32(GetArg(args, "x")), Convert.ToInt32(new_item_y), myCallback, IntPtr.Zero);
     
    
     // Zielpfad
     string sPath = GetArg(args, "dest") + RemoveExtension(Path.GetFileName(files)) + "." + GetExtension(files);
    
     // Speichern
     imgTemp.Save(@sPath, bmpTemp.RawFormat);
    
     // Temporäre Dateien entsorgen
     bmpTemp.Dispose();
     imgTemp.Dispose();
    
     // Ausgabe der bereits fertig skalierten Dateien
     Console.WriteLine(RemoveExtension(files) + " wurde neu skaliert...");
    
     }
     }
    
     // Falls Skalieren nicht erfolgreich war: Fehlermeldung
     catch
     {
     Console.WriteLine("Fehler: Bilder konnten nicht skaliert werden.");
     Console.Read();
     }
     }
     }
    
     private static bool ThumbnailCallback()
     {
     return false;
     }
     }
    }

    Es sind ja letztenendes nur zwei / drei Zeilen, in denen wirklich was mit dem Bild an sich gemacht wird. Hat da jemand einen besseren Vorschlag? So dass das Bild später nicht ganz entstellt aussieht?

    Ich danke schonmal allen hilfsbereiten Leuten!
     
  2. 11. September 2008
    AW: Qualitätsverlust bei Bild-Resize

    durch das verkleinern erreichst du logischerweise ein schlechteres bild da 1 pixel ja immernoch nicht größer ist und du versuchst den gesamten inhalt mit weniger dazurstellen. versuch es mal irgendwie ein wenig zu verwischen damit solltest du eventuell das ganze hin bekommen bin mir aber nicht sicher kannst ja erst nen bild resisen und mit photoshop oder sonstiges mal versuchen auf ein besseres ergebniss zu beokmmen dann weißt du was dir in deinem code noch fehlt
     
  3. 11. September 2008
    AW: Qualitätsverlust bei Bild-Resize

    Da ich an sich kein Grafiker bin stellt sich das Ganze etwas schwierig dar für mich. Es gibt ja Programme, die diesen Resize hinbekommen, ohne riesigen Qualitätsverlust. Zudem sei noch gesagt, dass dieses Programm zum VERKLEINERN gedacht ist und nicht zum vergrößern.

    Trotzdem Danke für deinen Hinweis
     
  4. 11. September 2008
    AW: Qualitätsverlust bei Bild-Resize

    ich meine ja verkleinern. wenn du überlegst du hast 10000 pixel und willst daraus ein bild mit 500 pixel machen ist doch logisch das das kleinere bild verbixelt wirkt da viele pixel quasi gelöscht werden müssen. deshalb würde ich das auf anhieb mal mit verwischen versuchen
     
  5. 11. September 2008
    AW: Qualitätsverlust bei Bild-Resize

    Wie gesagt, kein Grafiker, daher weiß ich auch nicht, ob es da eine Methode in C# für gibt um die Dateien anschließend weich zu zeichnen :/
     
  6. 11. September 2008
    AW: Qualitätsverlust bei Bild-Resize

    Nun einen fertigen "Filter" für .Net gibt es meines wissens nach nicht. Viele Programme, die zum Verkleinern/Vergrößern gedacht sind haben auch ihren eigenen Algo um ein halbwegs passables Resultat zu erziehlen.
     
  7. 11. September 2008
    AW: Qualitätsverlust bei Bild-Resize

    Sowas in der Art dacht ich mir schon :/
     
  8. 11. September 2008
    AW: Qualitätsverlust bei Bild-Resize

    ich hatte es mal so gelöst

    Code:
    Bitmap Bild = Bitmap.FromFile(wo_liegt_das_bild);
    
    Image.GetThumbnailImageAbort myCallback = new Image.GetThumbnailImageAbort(ThumbnailCallback);
    Image Thumb = Bild.GetThumbnailImage(breite, hoehe, myCallback, System.IntPtr.Zero);
    Thumb.Save(@Speicherort + DateiName + ".jpg", System.Drawing.Imaging.ImageFormat.Jpeg);
    
     
  9. 11. September 2008
    AW: Qualitätsverlust bei Bild-Resize

    Code:
    System.Drawing.Bitmap bmpTemp = System.Drawing.Bitmap.FromFile(files);
    Diese Zeile liefert folgenden Fehler:

    Code:
    Fehler 1 Der Typ "System.Drawing.Image" kann nicht implizit in "System.Drawing.Bitmap" konvertiert werden. Es ist bereits eine explizite Konvertierung vorhanden. (Möglicherweise fehlt eine Umwandlung.) C:\Programmierung\C#\resizeit_advanced\resizeit\Program.cs 63 57 resizeit
     
  10. 11. September 2008
    AW: Qualitätsverlust bei Bild-Resize


    in der Zeile wandelst du garnix in ein Image um..
     
  11. 11. September 2008
    AW: Qualitätsverlust bei Bild-Resize

    du siehst doch deinen Quellcode oben, wo wird dann wohl der Fehler herkommen?

    Wahrscheinlich doch aus:
    Code:
    imgTemp.Save(@sPath, System.Drawing.Imaging.ImageFormat.Jpeg);
    Sobald ich das hier:
    System.Drawing.Bitmap bmpTemp = System.Drawing.Bitmap.FromFile(files);

    in das hier umwandel, dann funktioniert es wieder einwandfrei (nur eben schlechte Qualität)
    System.Drawing.Bitmap bmpTemp = new System.Drawing.Bitmap(files);
     
  12. 11. September 2008
    AW: Qualitätsverlust bei Bild-Resize

    using System.Drawing;
    using System.Drawing.Imaging;

    drin?
     
  13. 11. September 2008
    AW: Qualitätsverlust bei Bild-Resize

    ich hab des ma ausprobiert

    allein dein quellcode funktioniert iwie nicht lässt sich zwar compilieren wirft aber nen error beim testen

    es gibt auch zwischen deinem code und icq-lights code nur einen kleinen unterschied der nicht ausschlaggebend ist. Bei dir ist der output immer in dem Format wie es vorm Resizen war bei icq.light immer jpeg
     
  14. 11. September 2008
    AW: Qualitätsverlust bei Bild-Resize

    du willst ein bild resamplen.

    hier gibts ne demo in c# (asp.net)
    Scaling/Resizing/Resampling an Image in ASP.NET - Scott Hanselman
     
  15. 11. September 2008
    AW: Qualitätsverlust bei Bild-Resize

    bitteschön:

    Code:
    using System;
    using System.Drawing;
    using System.IO;
    
    namespace resize_advanced
    {
     class Program
     {
     // Methode um die Strings zu bauen / lesen zu können
     private static string GetArg(string[] args, string sArgName)
     {
     for (int i = 0; i < args.Length; i++)
     {
     if (args[i] == "-" + sArgName && args.Length >= i)
     {
     return args[i + 1];
     }
     }
    
     return "";
     }
    
     // Methode um Endung (.jpg) abzuschneiden
     private static string RemoveExtension(string sFilename)
     {
     return sFilename.Substring(0, sFilename.IndexOf('.'));
     }
    
     // Methode um nur die Endung (.jpg) zu bekommen
     private static string GetExtension(string sFilename)
     {
     return sFilename.Substring(sFilename.IndexOf('.') + 1);
     }
    
     public static Image GetThumbnail(Image pImage, int pSize)
     {
     int x, y;
    
     if (pImage.Width > pImage.Height)
     {
     x = pSize;
     y = Convert.ToInt32(((float)pImage.Height / (float)pImage.Width * pSize));
     }
     else
     {
     y = pSize;
     x = Convert.ToInt32(((float)pImage.Width / (float)pImage.Height * pSize));
     }
     Image ret = new Bitmap(x, y);
     Graphics g = Graphics.FromImage(ret);
     g.InterpolationMode = System.Drawing.Drawing2D.InterpolationMode.HighQualityBicubic;
     g.DrawImage(pImage, 0, 0, x, y);
     g.Dispose();
     return ret;
     }
    
     // Hauptroutine
     static void Main(string[] args)
     {
     // Falls alle Parameter vollständig sind
     if (GetArg(args, "x") != "" && GetArg(args, "dir") != "" && GetArg(args, "dest") != "")
     {
     // Speicher alle (.jpg) Dateien aus dem Stammverzeichnis
     string[] folder_item = Directory.GetFiles(GetArg(args, "dir"), "*.jpg");
    
     // Versuch die Bilder neu zu skalieren
     try
     {
     // Durchlaufe solange (.jpg) Dateien vorhanden sind
     foreach (string files in folder_item)
     {
     // Lege neue Bitmap mit Drawzone an
     System.Drawing.Bitmap bmpTemp = new Bitmap(files);
    
     Image bildchen = GetThumbnail(bmpTemp, Convert.ToInt32(GetArg(args,"x")));
    
     // Zielpfad
     string sPath = GetArg(args, "dest") + RemoveExtension(Path.GetFileName(files)) + "_scaled." + GetExtension(files);
    
     bildchen.Save(@sPath,System.Drawing.Imaging.ImageFormat.Jpeg);
    
     // Ausgabe der bereits fertig skalierten Dateien
     Console.WriteLine(RemoveExtension(files) + " wurde neu skaliert...");
    
     }
     }
    
     // Falls Skalieren nicht erfolgreich war: Fehlermeldung
     catch
     {
     Console.WriteLine("Fehler: Bilder konnten nicht skaliert werden.");
     Console.Read();
     }
     }
     }
     }
    }
    besser gehts nun auch nicht wirklich mehr mit so wenig aufwand
     
  16. 11. September 2008
    AW: Qualitätsverlust bei Bild-Resize

    Danke für die Tipps und Lösungen =)
     
  17. 11. September 2008
    AW: Qualitätsverlust bei Bild-Resize

    damit erledigt
     
  18. Video Script

    Videos zum Themenbereich

    * gefundene Videos auf YouTube, anhand der Überschrift.