Resize with minimal loss of quality

I need to resize the image, but the image quality cannot be affected by this, the images will be from 10x10 to 1000x1000, it will have some basic clusters and a few empty times it has to scale both up and down "potentially losing some image quality". ok, but it should be at least all with bitmap graphics No libraries or other external binaries.

+2


a source to share


3 answers


Here is a link showing how to resize an image:



http://snippets.dzone.com/posts/show/4336

+4


a source


Whenever you resize images, you will have some loss of quality - there is no way around this, but you can help minimize it by using the highest quality settings for the graphics context.

Here I am using simple GDI + functions:

public static Bitmap ResizeImage(Bitmap bmp, int width, int height, 
                                 InterpolationMode mode = InterpolationMode.HighQualityBicubic)                                         
{
    Bitmap bmpOut = null;

    try
    {                                
        decimal ratio;
        int newWidth = 0;
        int newHeight = 0;

        // If the image is smaller than a thumbnail just return original size
        if (bmp.Width < width && bmp.Height < height)
        {
            newWidth = bmp.Width;
            newHeight = bmp.Height;
        }
        else
        {
            if (bmp.Width == bmp.Height)
            {
                if (height > width)
                {
                    newHeight = height;
                    newWidth = height;
                }
                else
                {
                    newHeight = width;
                    newWidth = width;                         
                }
            }
            else if (bmp.Width >= bmp.Height)
            {
                ratio = (decimal) width/bmp.Width;
                newWidth = width;
                decimal lnTemp = bmp.Height*ratio;
                newHeight = (int) lnTemp;
            }
            else
            {
                ratio = (decimal) height/bmp.Height;
                newHeight = height;
                decimal lnTemp = bmp.Width*ratio;
                newWidth = (int) lnTemp;
            }
        }

        //bmpOut = new Bitmap(bmp, new Size( newWidth, newHeight));                     
        bmpOut = new Bitmap(newWidth, newHeight);                
        bmpOut.SetResolution(bmp.HorizontalResolution, bmp.VerticalResolution);

        Graphics g = Graphics.FromImage(bmpOut);
        g.InterpolationMode = mode;

        g.SmoothingMode = SmoothingMode.HighQuality;
        g.PixelOffsetMode = PixelOffsetMode.HighQuality;

        g.FillRectangle(Brushes.White, 0, 0, newWidth, newHeight);
        g.DrawImage(bmp, 0, 0, newWidth, newHeight);                
    }
    catch
    {
        return null;
    }

    return bmpOut;
}

      

This reduces the size of the image to its largest or width or height - you can modify this algorithm to suit your resizing needs.



If you want to work with files, you can add another helper that wraps the code above:

public static bool ResizeImage(string filename, string outputFilename, 
                                int width, int height, 
                                InterpolationMode mode = InterpolationMode.HighQualityBicubic)
{

    using (var bmpOut = ResizeImage(filename, width, height, mode) )
    {
        var imageFormat = GetImageFormatFromFilename(filename);
        if (imageFormat == ImageFormat.Emf)
            imageFormat = bmpOut.RawFormat; 

        bmpOut.Save(outputFilename, imageFormat);
    }

    return true;
}

      

GDI + is generally not the best solution for high quality image processing - it is decent, but if you want high quality, better performance, and thread safety in web applications, you need to look at other options.

Bertrand LeRoy had a great article on Image Resizing some time ago that offers some alternatives using the mainstream .NET frameworks. http://weblogs.asp.net/bleroy/state-of-net-image-resizing-how-does-imageresizer-do

0


a source


What do you need to scale your images. I would recommend using the XML format to store your images as XML is very scalable. For instance:

<Image Width="640" Height="480">
  <Pixel X="0" Y="0">
    <Red>20</Red>
    <Green>80</Green>
    <Blue>0</Blue>
    <Alpha>255</Alpha>
  </Pixel>
  <Pixel X="1" Y="0">
    ...

      

If you're worried about memory, I'm sure this will compress very well :-).

-2


a source







All Articles