สร้างภาพขนาดย่อ


99

ฉันต้องการแสดงภาพขนาดย่อในมุมมองตารางจากตำแหน่งไฟล์ จะสร้าง.jpegไฟล์ได้อย่างไร? ฉันใช้C#ภาษากับasp.net.


6
ImageResizerเป็นไลบรารีที่ปลอดภัยสำหรับเซิร์ฟเวอร์ที่ออกแบบมาเพื่อทำสิ่งที่คุณต้องการ ไม่เหมือนกับ GetThumbnailImage ซึ่งให้ผลลัพธ์ที่มีคุณภาพสูงและแตกต่างจากตัวอย่างโค้ดคือหน่วยความจำไม่รั่วไหลเหมือนตะแกรง คุณอาจไม่สนใจในตอนนี้ แต่คุณจะอยู่ในอีกไม่กี่เดือนเมื่อคุณจมลึกลงไปในแกนกลาง
Lilith River



ImageResizer นั้นยอดเยี่ยม แต่ก็ไม่ฟรี
Boban Stojanovski

คำตอบ:


224

คุณต้องใช้GetThumbnailImageวิธีการในImageคลาส:

https://msdn.microsoft.com/en-us/library/8t23aykb%28v=vs.110%29.aspx

นี่คือตัวอย่างคร่าวๆที่ใช้ไฟล์ภาพและสร้างภาพขนาดย่อจากนั้นบันทึกกลับไปที่ดิสก์

Image image = Image.FromFile(fileName);
Image thumb = image.GetThumbnailImage(120, 120, ()=>false, IntPtr.Zero);
thumb.Save(Path.ChangeExtension(fileName, "thumb"));

มันอยู่ในเนมสเปซ System.Drawing (ใน System.Drawing.dll)

พฤติกรรม:

หากรูปภาพมีภาพขนาดย่อที่ฝังไว้วิธีนี้จะดึงภาพขนาดย่อที่ฝังไว้และปรับขนาดตามขนาดที่ร้องขอ หากรูปภาพไม่มีภาพขนาดย่อที่ฝังไว้วิธีนี้จะสร้างภาพขนาดย่อโดยการปรับขนาดภาพหลัก


สำคัญ:ส่วนข้อสังเกตของลิงค์ Microsoft ด้านบนเตือนถึงปัญหาที่อาจเกิดขึ้น:

GetThumbnailImageวิธีการทำงานได้ดีเมื่อได้รับการร้องขอภาพมีขนาดประมาณ 120 x 120 พิกเซล ถ้าคุณขอภาพขนาดใหญ่ (เช่น 300 x 300) จากภาพที่มีรูปเล็กที่ฝังตัวที่อาจจะมีการสูญเสียที่เห็นได้ชัดของคุณภาพในภาพ

การปรับขนาดภาพหลักอาจจะดีกว่า (แทนการปรับขนาดภาพขนาดย่อที่ฝังไว้) โดยเรียกใช้DrawImageเมธอด


5
สามารถใช้ได้กับภาพ JPG โดยทั่วไปเท่านั้น หากคุณพยายามปรับขนาดภาพ PNG เป็นแบบนี้คุณจะได้รับข้อผิดพลาดนี้
HBlackorby

จริงๆแล้วใช้สิ่งนี้เพื่อรับภาพขนาดย่อ 400x225 ของภาพถ่าย Full HD และขนาดของ "ภาพขนาดย่อ" ที่ได้คือ 200 kB (ดั้งเดิม 350 kB) วิธีนี้เป็นสิ่งที่ควรหลีกเลี่ยง
Vojtěch Dohnal

1
@NathanaelJones เอาจริงเหรอ? ImageResizer ไม่ฟรีสำหรับธุรกิจ
Ciaran Gallagher

26

โค้ดต่อไปนี้จะเขียนรูปภาพตามสัดส่วนของการตอบกลับคุณสามารถแก้ไขโค้ดตามวัตถุประสงค์

public void WriteImage(string path, int width, int height)
{
    Bitmap srcBmp = new Bitmap(path);
    float ratio = srcBmp.Width / srcBmp.Height;
    SizeF newSize = new SizeF(width, height * ratio);
    Bitmap target = new Bitmap((int) newSize.Width,(int) newSize.Height);
    HttpContext.Response.Clear();
    HttpContext.Response.ContentType = "image/jpeg";
    using (Graphics graphics = Graphics.FromImage(target))
    {
        graphics.CompositingQuality = CompositingQuality.HighSpeed;
        graphics.InterpolationMode = InterpolationMode.HighQualityBicubic;
        graphics.CompositingMode = CompositingMode.SourceCopy;
        graphics.DrawImage(srcBmp, 0, 0, newSize.Width, newSize.Height);
        using (MemoryStream memoryStream = new MemoryStream()) 
        {
            target.Save(memoryStream, ImageFormat.Jpeg);
            memoryStream.WriteTo(HttpContext.Response.OutputStream);
        }
    }
    Response.End();
}

ฉันให้เส้นทางไฟล์ในเครื่องของฉันในเส้นทางสตริง มันส่งคืน "ไม่รองรับรูปแบบเส้นทางที่กำหนด"
Gopal Palraj

ฉันให้แบบนี้ ... var path = @ "C: \ Users \ Gopal \ Desktop \ files.jpeg"; Bitmap srcBmp = Bitmap ใหม่ (เส้นทาง);
Gopal Palraj

สำหรับผู้ที่ใช้ HttpResponseMessage:response.Content = new ByteArrayContent(memoryStream.ToArray());
Hp93

โปรดระวังรหัสนี้จะถือว่าภาพเป็น "แนวนอน" (แนวนอน)
Alex

9

นี่คือตัวอย่างที่สมบูรณ์ของวิธีสร้างภาพขนาดเล็ก (ภาพขนาดย่อ) ตัวอย่างนี้จะปรับขนาดรูปภาพหมุนเมื่อจำเป็น (หากถือโทรศัพท์ในแนวตั้ง) และวางแผ่นรองรูปภาพหากคุณต้องการสร้างนิ้วหัวแม่มือสี่เหลี่ยม ตัวอย่างข้อมูลนี้สร้าง JPEG แต่สามารถแก้ไขได้อย่างง่ายดายสำหรับไฟล์ประเภทอื่น ๆ แม้ว่าภาพจะมีขนาดเล็กกว่าขนาดสูงสุดที่อนุญาต แต่ภาพจะยังคงถูกบีบอัดและความละเอียดจะถูกเปลี่ยนแปลงเพื่อสร้างภาพที่มี dpi และระดับการบีบอัดเดียวกัน

using System;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.Drawing.Imaging;
using System.IO;

//set the resolution, 72 is usually good enough for displaying images on monitors
float imageResolution = 72;

//set the compression level. higher compression = better quality = bigger images
long compressionLevel = 80L;


public Image resizeImage(Image image, int maxWidth, int maxHeight, bool padImage)
{
    int newWidth;
    int newHeight;

    //first we check if the image needs rotating (eg phone held vertical when taking a picture for example)
    foreach (var prop in image.PropertyItems)
    {
        if (prop.Id == 0x0112)
        {
            int orientationValue = image.GetPropertyItem(prop.Id).Value[0];
            RotateFlipType rotateFlipType = getRotateFlipType(orientationValue);
            image.RotateFlip(rotateFlipType);
            break;
        }
    }

    //apply the padding to make a square image
    if (padImage == true)
    {
        image = applyPaddingToImage(image, Color.Red);
    }

    //check if the with or height of the image exceeds the maximum specified, if so calculate the new dimensions
    if (image.Width > maxWidth || image.Height > maxHeight)
    {
        double ratioX = (double)maxWidth / image.Width;
        double ratioY = (double)maxHeight / image.Height;
        double ratio = Math.Min(ratioX, ratioY);

        newWidth = (int)(image.Width * ratio);
        newHeight = (int)(image.Height * ratio);
    }
    else
    {
        newWidth = image.Width;
        newHeight = image.Height;
    }

    //start the resize with a new image
    Bitmap newImage = new Bitmap(newWidth, newHeight);

    //set the new resolution
    newImage.SetResolution(imageResolution, imageResolution);

    //start the resizing
    using (var graphics = Graphics.FromImage(newImage))
    {
        //set some encoding specs
        graphics.CompositingMode = CompositingMode.SourceCopy;
        graphics.CompositingQuality = CompositingQuality.HighQuality;
        graphics.SmoothingMode = SmoothingMode.HighQuality;
        graphics.InterpolationMode = InterpolationMode.HighQualityBicubic;
        graphics.PixelOffsetMode = PixelOffsetMode.HighQuality;

        graphics.DrawImage(image, 0, 0, newWidth, newHeight);
    }

    //save the image to a memorystream to apply the compression level
    using (MemoryStream ms = new MemoryStream())
    {
        EncoderParameters encoderParameters = new EncoderParameters(1);
        encoderParameters.Param[0] = new EncoderParameter(Encoder.Quality, compressionLevel);

        newImage.Save(ms, getEncoderInfo("image/jpeg"), encoderParameters);

        //save the image as byte array here if you want the return type to be a Byte Array instead of Image
        //byte[] imageAsByteArray = ms.ToArray();
    }

    //return the image
    return newImage;
}


//=== image padding
public Image applyPaddingToImage(Image image, Color backColor)
{
    //get the maximum size of the image dimensions
    int maxSize = Math.Max(image.Height, image.Width);
    Size squareSize = new Size(maxSize, maxSize);

    //create a new square image
    Bitmap squareImage = new Bitmap(squareSize.Width, squareSize.Height);

    using (Graphics graphics = Graphics.FromImage(squareImage))
    {
        //fill the new square with a color
        graphics.FillRectangle(new SolidBrush(backColor), 0, 0, squareSize.Width, squareSize.Height);

        //put the original image on top of the new square
        graphics.DrawImage(image, (squareSize.Width / 2) - (image.Width / 2), (squareSize.Height / 2) - (image.Height / 2), image.Width, image.Height);
    }

    //return the image
    return squareImage;
}


//=== get encoder info
private ImageCodecInfo getEncoderInfo(string mimeType)
{
    ImageCodecInfo[] encoders = ImageCodecInfo.GetImageEncoders();

    for (int j = 0; j < encoders.Length; ++j)
    {
        if (encoders[j].MimeType.ToLower() == mimeType.ToLower())
        {
            return encoders[j];
        }
    }

    return null;
}


//=== determine image rotation
private RotateFlipType getRotateFlipType(int rotateValue)
{
    RotateFlipType flipType = RotateFlipType.RotateNoneFlipNone;

    switch (rotateValue)
    {
        case 1:
            flipType = RotateFlipType.RotateNoneFlipNone;
            break;
        case 2:
            flipType = RotateFlipType.RotateNoneFlipX;
            break;
        case 3:
            flipType = RotateFlipType.Rotate180FlipNone;
            break;
        case 4:
            flipType = RotateFlipType.Rotate180FlipX;
            break;
        case 5:
            flipType = RotateFlipType.Rotate90FlipX;
            break;
        case 6:
            flipType = RotateFlipType.Rotate90FlipNone;
            break;
        case 7:
            flipType = RotateFlipType.Rotate270FlipX;
            break;
        case 8:
            flipType = RotateFlipType.Rotate270FlipNone;
            break;
        default:
            flipType = RotateFlipType.RotateNoneFlipNone;
            break;
    }

    return flipType;
}


//== convert image to base64
public string convertImageToBase64(Image image)
{
    using (MemoryStream ms = new MemoryStream())
    {
        //convert the image to byte array
        image.Save(ms, ImageFormat.Jpeg);
        byte[] bin = ms.ToArray();

        //convert byte array to base64 string
        return Convert.ToBase64String(bin);
    }
}

สำหรับผู้ใช้ asp.net ตัวอย่างเล็กน้อยเกี่ยวกับวิธีการอัปโหลดไฟล์ปรับขนาดและแสดงผลลัพธ์บนหน้า

//== the button click method
protected void Button1_Click(object sender, EventArgs e)
{
    //check if there is an actual file being uploaded
    if (FileUpload1.HasFile == false)
    {
        return;
    }

    using (Bitmap bitmap = new Bitmap(FileUpload1.PostedFile.InputStream))
    {
        try
        {
            //start the resize
            Image image = resizeImage(bitmap, 256, 256, true);

            //to visualize the result, display as base64 image
            Label1.Text = "<img src=\"data:image/jpg;base64," + convertImageToBase64(image) + "\">";

            //save your image to file sytem, database etc here
        }
        catch (Exception ex)
        {
            Label1.Text = "Oops! There was an error when resizing the Image.<br>Error: " + ex.Message;
        }
    }
}

ฉันชอบตัวอย่างโค้ดนี้และเลือกใช้ อย่างไรก็ตามไม่ว่าฉันจะเปลี่ยนแปลงอะไรกับตัวเลือกต่างๆ (imageResolution, compressionLevel, CompositingMode, CompositingQuality, SmoothingMode, InterpolationMode, PixelOffsetMode) ขนาดไฟล์ภาพก็ลดลงเพียงเล็กน้อยเท่านั้น และฉันไม่เคยเห็นความแตกต่างใด ๆ ในภาพที่สร้างขึ้น สุดท้ายฉันเลือกที่จะบันทึกภาพลงในไฟล์แทนสตรีมหน่วยความจำและสามารถเห็นการเปลี่ยนแปลงที่รุนแรงได้ สำหรับใครก็ตามที่ใช้สิ่งนี้ดูเหมือนว่าการบันทึกลงในสตรีมหน่วยความจำจะไม่มีผลกับภาพที่ส่งคืน
BLaminack

2

นี่คือตัวอย่างการแปลงภาพความละเอียดสูงเป็นขนาดย่อ -

protected void Button1_Click(object sender, EventArgs e)
{
    //----------        Getting the Image File
    System.Drawing.Image img = System.Drawing.Image.FromFile(Server.MapPath("~/profile/Avatar.jpg"));

    //----------        Getting Size of Original Image
    double imgHeight = img.Size.Height;
    double imgWidth = img.Size.Width;

    //----------        Getting Decreased Size
    double x = imgWidth / 200;
    int newWidth = Convert.ToInt32(imgWidth / x);
    int newHeight = Convert.ToInt32(imgHeight / x);

    //----------        Creating Small Image
    System.Drawing.Image.GetThumbnailImageAbort myCallback = new System.Drawing.Image.GetThumbnailImageAbort(ThumbnailCallback);
    System.Drawing.Image myThumbnail = img.GetThumbnailImage(newWidth, newHeight, myCallback, IntPtr.Zero);

    //----------        Saving Image
    myThumbnail.Save(Server.MapPath("~/profile/NewImage.jpg"));
}
public bool ThumbnailCallback()
{
    return false;
}

ที่มา - http://iknowledgeboy.blogspot.in/2014/03/c-creating-thumbnail-of-large-image-by.html


0

นี่คือรหัสที่ฉันใช้ ใช้ได้กับ.NET Core> 2.0 โดยใช้System.Drawing.CommonNuGet

https://www.nuget.org/packages/System.Drawing.Common/

using System;
using System.Drawing;

class Program
{
    static void Main()
    {
        const string input = "C:\\background1.png";
        const string output = "C:\\thumbnail.png";

        // Load image.
        Image image = Image.FromFile(input);

        // Compute thumbnail size.
        Size thumbnailSize = GetThumbnailSize(image);

        // Get thumbnail.
        Image thumbnail = image.GetThumbnailImage(thumbnailSize.Width,
            thumbnailSize.Height, null, IntPtr.Zero);

        // Save thumbnail.
        thumbnail.Save(output);
    }

    static Size GetThumbnailSize(Image original)
    {
        // Maximum size of any dimension.
        const int maxPixels = 40;

        // Width and height.
        int originalWidth = original.Width;
        int originalHeight = original.Height;

        // Compute best factor to scale entire image based on larger dimension.
        double factor;
        if (originalWidth > originalHeight)
        {
            factor = (double)maxPixels / originalWidth;
        }
        else
        {
            factor = (double)maxPixels / originalHeight;
        }

        // Return thumbnail size.
        return new Size((int)(originalWidth * factor), (int)(originalHeight * factor));
    }
}

ที่มา:

https://www.dotnetperls.com/getthumbnailimage

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.