Cara mengunduh gambar dari url

105

Apakah ada cara untuk mengunduh gambar langsung dari url di c # jika url tidak memiliki format gambar di akhir tautan? Contoh url:

https://fbcdn-sphotos-h-a.akamaihd.net/hphotos-ak-xpf1/v/t34.0-12/10555140_10201501435212873_1318258071_n.jpg?oh=97ebc03895b7acee9aebbde7d6b002bf&oe=53C9ABB0&__gda__=1405685729_110e04e71d969d392b63b27ec4f4b24a

Saya tahu cara mengunduh gambar ketika url diakhiri dengan format gambar. Misalnya:

http://img1.wikia.nocookie.net/__cb20101219155130/uncyclopedia/images/7/70/Facebooklogin.png
Ifwat Ibrahim
sumber

Jawaban:

136

Cukup Anda dapat menggunakan metode berikut.

using (WebClient client = new WebClient()) 
{
    client.DownloadFile(new Uri(url), @"c:\temp\image35.png");
    // OR 
    client.DownloadFileAsync(new Uri(url), @"c:\temp\image35.png");
}

Metode ini hampir sama dengan DownloadString (..) dan DownloadStringAsync (...). Mereka menyimpan file di Direktori daripada di string C # dan tidak perlu ekstensi Format di URi

Jika Anda tidak mengetahui Format (.png, .jpeg dll) dari Gambar

public void SaveImage(string filename, ImageFormat format)
{    
    WebClient client = new WebClient();
    Stream stream = client.OpenRead(imageUrl);
    Bitmap bitmap;  bitmap = new Bitmap(stream);

    if (bitmap != null)
    {
        bitmap.Save(filename, format);
    }

    stream.Flush();
    stream.Close();
    client.Dispose();
}

Menggunakannya

try
{
    SaveImage("--- Any Image Path ---", ImageFormat.Png)
}
catch(ExternalException)
{
    // Something is wrong with Format -- Maybe required Format is not 
    // applicable here
}
catch(ArgumentNullException)
{   
    // Something wrong with Stream
}
Charlie
sumber
4
@Arsman Ahmad itu pertanyaan yang sama sekali berbeda yang harus dicari atau ditanyakan di tempat lain. Utas ini untuk mengunduh satu gambar.
AzNjoE
79

Bergantung apakah Anda mengetahui format gambar atau tidak, berikut ini cara melakukannya:

Unduh Gambar ke file, mengetahui format gambar

using (WebClient webClient = new WebClient()) 
{
   webClient.DownloadFile("http://yoururl.com/image.png", "image.png") ; 
}

Unduh Gambar ke file tanpa mengetahui format gambar

Anda dapat menggunakan Image.FromStreamuntuk memuat semua jenis bitmap biasa (jpg, png, bmp, gif, ...), ini akan mendeteksi secara otomatis jenis file dan Anda bahkan tidak perlu memeriksa ekstensi url (yang tidak terlalu baik praktek). Misalnya:

using (WebClient webClient = new WebClient()) 
{
    byte [] data = webClient.DownloadData("https://fbcdn-sphotos-h-a.akamaihd.net/hphotos-ak-xpf1/v/t34.0-12/10555140_10201501435212873_1318258071_n.jpg?oh=97ebc03895b7acee9aebbde7d6b002bf&oe=53C9ABB0&__gda__=1405685729_110e04e71d9");

   using (MemoryStream mem = new MemoryStream(data)) 
   {
       using (var yourImage = Image.FromStream(mem)) 
       { 
          // If you want it as Png
           yourImage.Save("path_to_your_file.png", ImageFormat.Png) ; 

          // If you want it as Jpeg
           yourImage.Save("path_to_your_file.jpg", ImageFormat.Jpeg) ; 
       }
   } 

}

Catatan: ArgumentException dapat dijalankan Image.FromStreamjika konten yang didownload bukan tipe gambar yang dikenal.

Periksa referensi ini di MSDN untuk menemukan semua format yang tersedia. Berikut adalah referensi untuk WebClientdan Bitmap.

Sempurna 28
sumber
2
Perhatikan bahwa Anda perlu "menggunakan System.Drawing;" untuk Image.FromStream ()
dlchambers
3
Perhatikan bahwa alih-alih meminta pustaka gambar untuk mendeteksi format gambar, Anda juga dapat melihat header respons untuk melihat format apa yang menurut sumber gambar tersebut digunakanwebClient.ResponseHeaders["Content-Type"]
bikeman868
Ini juga akan jauh lebih hemat memori daripada memperluas gambar yang dikompresi menjadi objek Bitmap yang tidak dikompresi, dan akan memungkinkan Anda untuk menyimpan gambar dalam format aslinya dengan kompresi aslinya, dll.
bikeman868
20

Untuk siapa saja yang ingin mendownload gambar TANPA menyimpannya ke file:

Image DownloadImage(string fromUrl)
{
    using (System.Net.WebClient webClient = new System.Net.WebClient())
    {
        using (Stream stream = webClient.OpenRead(fromUrl))
        {
            return Image.FromStream(stream);
        }
    }
}
Brian Cryer
sumber
11

Ini tidak perlu digunakan System.Drawinguntuk menemukan format gambar dalam URI. System.Drawingtidak tersedia .NET Corekecuali Anda mengunduh paket System.Drawing.Common NuGet dan oleh karena itu saya tidak melihat jawaban lintas platform yang baik untuk pertanyaan ini.

Selain itu, contoh saya tidak digunakan System.Net.WebClientkarena Microsoft secara eksplisit melarang penggunaanSystem.Net.WebClient .

Kami tidak menyarankan Anda menggunakan WebClientkelas untuk pengembangan baru. Sebagai gantinya, gunakan kelas System.Net.Http.HttpClient .

Unduh gambar dan tulis ke file tanpa mengetahui ekstensi (lintas platform) *

* Tanpa tua System.Net.WebClientdan System.Drawing.

Metode ini akan mengunduh gambar secara asinkron (atau file apa pun selama URI memiliki ekstensi file) menggunakan System.Net.Http.HttpClientdan kemudian menulisnya ke file, menggunakan ekstensi file yang sama seperti gambar di URI.

Mendapatkan ekstensi file

Bagian pertama untuk mendapatkan ekstensi file adalah menghapus semua bagian yang tidak diperlukan dari URI.
Kami menggunakan Uri.GetLeftPart () dengan UriP Partial.Path untuk mendapatkan semuanya mulai dari yang Schemeatas hingga Path.
Dengan kata lain, https://www.example.com/image.png?query&with.dotsmenjadi https://www.example.com/image.png.

Setelah itu, kami menggunakan Path.GetExtension () untuk hanya mendapatkan ekstensi (dalam contoh saya sebelumnya, .png).

var uriWithoutQuery = uri.GetLeftPart(UriPartial.Path);
var fileExtension = Path.GetExtension(uriWithoutQuery);

Mendownload gambar

Dari sini harus lurus ke depan. Unduh gambar dengan HttpClient.GetByteArrayAsync , buat jalur, pastikan direktori ada dan kemudian tulis byte ke jalur dengan File.WriteAllBytesAsync () (atau File.WriteAllBytesjika Anda menggunakan .NET Framework)

private async Task DownloadImageAsync(string directoryPath, string fileName, Uri uri)
{
    using var httpClient = new HttpClient();

    // Get the file extension
    var uriWithoutQuery = uri.GetLeftPart(UriPartial.Path);
    var fileExtension = Path.GetExtension(uriWithoutQuery);

    // Create file path and ensure directory exists
    var path = Path.Combine(directoryPath, $"{fileName}{fileExtension}");
    Directory.CreateDirectory(directoryPath);

    // Download the image and write to the file
    var imageBytes = await _httpClient.GetByteArrayAsync(uri);
    await File.WriteAllBytesAsync(path, imageBytes);
}

Perhatikan bahwa Anda memerlukan yang berikut menggunakan arahan.

using System;
using System.IO;
using System.Threading.Tasks;
using System.Net.Http;

Contoh penggunaan

var folder = "images";
var fileName = "test";
var url = "https://cdn.discordapp.com/attachments/458291463663386646/592779619212460054/Screenshot_20190624-201411.jpg?query&with.dots";

await DownloadImageAsync(folder, fileName, new Uri(url));

Catatan

  • Merupakan praktik yang buruk untuk membuat yang baru HttpClientuntuk setiap pemanggilan metode. Itu seharusnya digunakan kembali di seluruh aplikasi. Saya menulis contoh singkat ImageDownloader(50 baris) dengan lebih banyak dokumentasi yang menggunakan kembali dengan HttpClientbenar dan membuangnya dengan benar yang dapat Anda temukan di sini .
MarcusOtter
sumber
5

.net Framework memungkinkan Kontrol PictureBox untuk Memuat Gambar dari url

dan Simpan gambar di Acara Lengkap Laod

protected void LoadImage() {
 pictureBox1.ImageLocation = "PROXY_URL;}

void pictureBox1_LoadCompleted(object sender, AsyncCompletedEventArgs e) {
   pictureBox1.Image.Save(destination); }
Ali Humayun
sumber
4

Coba ini berhasil untuk saya

Tuliskan ini di Controller Anda

public class DemoController: Controller

        public async Task<FileStreamResult> GetLogoImage(string logoimage)
        {
            string str = "" ;
            var filePath = Server.MapPath("~/App_Data/" + SubfolderName);//If subfolder exist otherwise leave.
            // DirectoryInfo dir = new DirectoryInfo(filePath);
            string[] filePaths = Directory.GetFiles(@filePath, "*.*");
            foreach (var fileTemp in filePaths)
            {
                  str= fileTemp.ToString();
            }
                return File(new MemoryStream(System.IO.File.ReadAllBytes(str)), System.Web.MimeMapping.GetMimeMapping(str), Path.GetFileName(str));
        }

Ini pandangan saya

<div><a href="/DemoController/GetLogoImage?Type=Logo" target="_blank">Download Logo</a></div>
Chandan Kumar
sumber
1

Sebagian besar posting yang saya temukan akan habis setelah iterasi kedua. Terutama jika Anda mengulang-ulang banyak gambar seperti yang saya lakukan. Jadi untuk meningkatkan saran di atas, inilah seluruh metode:

public System.Drawing.Image DownloadImage(string imageUrl)
    {
        System.Drawing.Image image = null;

        try
        {
            System.Net.HttpWebRequest webRequest = (System.Net.HttpWebRequest)System.Net.HttpWebRequest.Create(imageUrl);
            webRequest.AllowWriteStreamBuffering = true;
            webRequest.Timeout = 30000;
            webRequest.ServicePoint.ConnectionLeaseTimeout = 5000;
            webRequest.ServicePoint.MaxIdleTime = 5000;

            using (System.Net.WebResponse webResponse = webRequest.GetResponse())
            {

                using (System.IO.Stream stream = webResponse.GetResponseStream())
                {
                    image = System.Drawing.Image.FromStream(stream);
                }
            }

            webRequest.ServicePoint.CloseConnectionGroup(webRequest.ConnectionGroupName);
            webRequest = null; 
        }
        catch (Exception ex)
        {
            throw new Exception(ex.Message, ex);

        }


        return image;
    }
Be05x5
sumber