2011-08-13 84 views
11

Tôi đang viết chương trình gửi email cho người dùng có nhiều hình ảnh (biểu đồ) được nhúng trong nội dung Thư email (HTML).Cách nhúng nhiều hình ảnh trong phần thân email bằng cách sử dụng .NET

Khi tôi thử mẫu ở đây..đã hoạt động tốt khi tôi chỉ nhúng một hình ảnh http://www.systemnetmail.com/faq/4.4.aspx.

Tuy nhiên, khi tôi cố gắng nhúng nhiều hình ảnh bằng cách sử dụng mã bên dưới, không có hình ảnh nào được nhúng, thay vào đó chúng được gửi dưới dạng tệp đính kèm.

public MailMessage MailMessage(Metric metric, DateTime date) 
{ 
    MailMessage msg = new MailMessage(); 
    msg.From = new MailAddress("[email protected]", "User1"); 
    msg.To.Add(new MailAddress("[email protected]")); 
    msg.Subject = "Trend for metric: " + metric.Name; 
    msg.IsBodyHtml = true; 

    // Generate the charts for the given metric 
    var charts = this.GenerateCharts(metric, date); 
    int i = 0; 
    string htmlBody = "<html><body>"; 
    List<LinkedResource> resources = new List<LinkedResource>(); 
    foreach (var chart in charts) 
    { 
     string imageTag = string.Format("<img src=cid:chart{0} /><br>", i); 
     htmlBody += imageTag; 
     LinkedResource graph = new LinkedResource(chart.Value, "image/jpeg"); 
     graph.ContentId = "chart" + i; 
     resources.Add(graph); 
     i++; 
    } 

    htmlBody += "</body></html>"; 

    // Alternate view for embedded images 
    AlternateView avText = AlternateView.CreateAlternateViewFromString(metric.Name, null, MediaTypeNames.Text.Html); 
    AlternateView avImages = AlternateView.CreateAlternateViewFromString(htmlBody, null, MediaTypeNames.Text.Html); 

    // Add all the images as linked resources 
    resources.ForEach(x => avImages.LinkedResources.Add(x)); 

    // Add the views for image 
    msg.AlternateViews.Add(avText); 
    msg.AlternateViews.Add(avImages); 


    return msg; 
} 

Mọi manh mối như những gì tôi bị thiếu? Tôi đã kiểm tra các tập tin .htm đó cũng được gửi như tập tin đính kèm với email, và nguồn html trông như sau:

<html>><body><img src=cid:chart0 /><br><img src=cid:chart1 /><br><img src=cid:chart2/><br><img src=cid:chart3 /><br><img src=cid:chart4 /><br></body></html> 

Vì vậy, Q là làm thế nào để gửi nhiều hình ảnh trong phần nội dung html, không phải là tập tin đính kèm.

+1

có thể trùng lặp [Gửi email có hình ảnh được nhúng trong nội dung từ C#] (http://stackoverflow.com/questions/1921275/sending-an-email-with-an-image-embedded-in-the- body-from-c) –

Trả lời

6

Vì vậy, tôi nghĩ rằng đã tìm ra những gì các vấn đề thực tế là của nó trong dòng này

// Alternate view for embedded images 
    AlternateView avText = AlternateView.CreateAlternateViewFromString(metric.Name, null, MediaTypeNames.Text.Html); 
    AlternateView avImages = AlternateView.CreateAlternateViewFromString(htmlBody, null, MediaTypeNames.Text.Html); 

Như bạn có thể thấy, cả hai quan điểm của tôi được quy định như Text.Html, nên chắc chắn một 1st được trọng kế tiếp và vì vậy tôi chỉ nhìn thấy văn bản và hình ảnh được gửi dưới dạng file đính kèm

tôi thực hiện thay đổi sau đây và nó làm việc như mong đợi

AlternateView avText = AlternateView.CreateAlternateViewFromString(metric.Name, null, **MediaTypeNames.Text.Plain**); 
AlternateView avImages = AlternateView.CreateAlternateViewFromString(htmlBody, null, MediaTypeNames.Text.Html); 
+0

Tôi đã có vấn đề chính xác. Đây chính xác là những gì tôi đang tìm kiếm! Tuy nhiên, nếu tôi kết thúc bằng cách sử dụng hơn 2 hình ảnh, tôi không hoàn toàn chắc chắn làm thế nào để tạo ra mỗi AlternateView. Tôi giả sử tôi sẽ có thể làm tất cả chúng nhưng cuối cùng là Text.Plain – roshambo

5

Đầu tiên, bạn có thể thử sử dụng URI tuyệt đối cho hình ảnh được nhúng. Dưới đây là ví dụ từ RFC-2557:

From: [email protected] 
    To: [email protected] 
    Subject: A simple example 
    Mime-Version: 1.0 
    Content-Type: multipart/related; boundary="boundary-example"; 
      type="text/html"; start="<[email protected]@bar.net>" 

    --boundary-example 
    Content-Type: text/html;charset="US-ASCII" 
    Content-ID: <[email protected]@bar.net> 

    ... text of the HTML document, which might contain a URI 
    referencing a resource in another body part, for example 
    through a statement such as: 
    <IMG SRC="http://www.ietf.cnri.reston.va.us/images/ietflogo.gif" ALT="IETF logo"> 

    --boundary-example 
    Content-Location: 
    http://www.ietf.cnri.reston.va.us/images/ietflogo.gif 
    Content-Type: IMAGE/GIF 
    Content-Transfer-Encoding: BASE64 

    R0lGODlhGAGgAPEAAP/////ZRaCgoAAAACH+PUNvcHlyaWdodCAoQykgMTk5 
    NSBJRVRGLiBVbmF1dGhvcml6ZWQgZHVwbGljYXRpb24gcHJvaGliaXRlZC4A 
    etc... 

    --boundary-example-- 

Bạn chỉ cần chỉ định LinkedResource.ContentLink property thay vì ContentId.

Thứ hai, bạn có thể nhúng hình ảnh trực tiếp vào html của mình với the "data" URL scheme.

<IMG 
    SRC="data:image/gif;base64,R0lGODdhMAAwAPAAAAAAAP///ywAAAAAMAAw 
    AAAC8IyPqcvt3wCcDkiLc7C0qwyGHhSWpjQu5yqmCYsapyuvUUlvONmOZtfzgFz 
    ByTB10QgxOR0TqBQejhRNzOfkVJ+5YiUqrXF5Y5lKh/DeuNcP5yLWGsEbtLiOSp 
    a/TPg7JpJHxyendzWTBfX0cxOnKPjgBzi4diinWGdkF8kjdfnycQZXZeYGejmJl 
    ZeGl9i2icVqaNVailT6F5iJ90m6mvuTS4OK05M0vDk0Q4XUtwvKOzrcd3iq9uis 
    F81M1OIcR7lEewwcLp7tuNNkM3uNna3F2JQFo97Vriy/Xl4/f1cf5VWzXyym7PH 
    hhx4dbgYKAAA7" 
    ALT="Larry"> 

BTW, đánh dấu html của bạn không được định dạng đúng. Bạn cũng có thể quan tâm đến “foreach” vs “ForEach”

+0

cách thức (html) không được định dạng tốt? bạn có thể giải thích? – user330612

+0

tôi tìm thấy giải pháp cho pblm của tôi, như đã nói dưới đây – user330612

+0

URI tuyệt đối để nhúng hình ảnh giải quyết vấn đề của tôi cảm ơn bạn ... –

1

nếu bạn có hình ảnh trực tuyến, có nghĩa là gửi từ một trang web lưu trữ, tôi đề nghị bạn chỉ cần tham khảo những hình ảnh đơn giản bằng cách đặt url của họ trong src.

<!-- using artplastika examples --> 
<IMG SRC="http://www.ietf.cnri.reston.va.us/images/ietflogo.gif" ALT="IETF logo" /> 

hầu hết các bản tin sử dụng phương pháp này và tôi tin rằng nó nhẹ hơn và có thể tiêu thụ ít tài nguyên hơn là tự nhúng.

hy vọng điều này giúp

19

Một cách khác để chèn hình ảnh vào trong E-mail khi sử dụng System.Net.Mail

Đính kèm hình ảnh từ ổ đĩa cục bộ để gửi email và chỉ định một contentID với nó và sau đó sử dụng contentID này trong hình ảnh URL.

này có thể được thực hiện bằng cách:

var contentID = "Image"; 
var inlineLogo = new Attachment(@"C:\Desktop\Image.jpg"); 
inlineLogo.ContentId = contentID; 
inlineLogo.ContentDisposition.Inline = true; 
inlineLogo.ContentDisposition.DispositionType = DispositionTypeNames.Inline; 

msg.IsBodyHtml = true; 
msg.Attachments.Add(inlineLogo); 
msg.Body = "<htm><body> <img src=\"cid:" + contentID + "\"> </body></html>"; 
+0

Xin vui lòng thực hiện không đăng câu trả lời chính xác cho nhiều câu hỏi: nó không phù hợp cho tất cả hoặc các câu hỏi là bản sao nên được gắn cờ/đóng cửa như vậy. – kleopatra

+0

Phương pháp của bạn đã hoạt động đối với tôi. Tôi đã thử các tài nguyên được liên kết, nhưng nó không hoạt động. Hầu hết mọi nơi tôi nhìn, mọi người dường như đã có hình ảnh được hiển thị trong ứng dụng email của họ bằng cách sử dụng các tài nguyên được liên kết. Kỳ dị! –

+0

Hoạt động hoàn hảo. Tôi không thực sự hiểu nhu cầu làm việc với các tài nguyên được liên kết. Điều này là sạch hơn và thanh lịch hơn trong khẩu vị của tôi. –

2

alternatie của tôi:

Trước hết, một chút mở rộng:

public static class RegexExtensions 
{ 
    public static string GetPattern(this IEnumerable<string> valuesToSearch) 
    { 
     return string.Format("({0})", string.Join("|", valuesToSearch)); 
    } 
} 

sau đó nhận được tên hình ảnh từ thư mục:

private string[] GetFullNamesOfImages() 
    { 
     string images = Path.Combine(_directoryName, "Images"); 
     if (!Directory.Exists(images)) 
      return new string[0]; 
     return Directory.GetFiles(images); 
    } 

rồi thay thế i tên pháp sư bởi cid:

private string InsertImages(string body) 
    { 
     var images = GetFullNamesOfImages().Select(Path.GetFileName).ToArray(); 
     return Regex.Replace(body, "(Images/)?" + images.GetPattern(), "cid:$2", RegexOptions.IgnoreCase | RegexOptions.Compiled); 
    } 

nơi cơ thể - được HTML cơ thể, và ví dụ, <img src="Images/logo_shadow.png" alt="" style="width: 100%;" /> sẽ được thay thế bởi <img src="cid:logo_shadow.png" alt="" style="width: 100%;" />

hành động sau đó lần cuối: thêm hình ảnh itselfs để mail:

private MailMessage CreateMail(SmtpClient smtp, string toAddress, string body) 
    { 
     var images = GetFullNamesOfImages(); 

     string decodedBody = WebUtility.HtmlDecode(body); 
     var text = AlternateView.CreateAlternateViewFromString(decodedBody, null, MediaTypeNames.Text.Plain); 
     var html = AlternateView.CreateAlternateViewFromString(body, null, MediaTypeNames.Text.Html); 
     foreach (var image in images) 
     { 
      html.LinkedResources.Add(new LinkedResource(image, new ContentType("image/png")) 
            { 
             ContentId = Path.GetFileName(image) 
            }); 
     } 


     var credentials = (NetworkCredential) smtp.Credentials; 

     var message = new MailMessage(new MailAddress(credentials.UserName), new MailAddress(toAddress)) 
         { 
          Subject = "Some subj", 
          Body = decodedBody 
         }; 
     message.AlternateViews.Add(text); 
     message.AlternateViews.Add(html); 
     return message; 
    } 
1
 AlternateView avHtml = AlternateView.CreateAlternateViewFromString(body, null, MediaTypeNames.Text.Html); 
     LinkedResource inline = new LinkedResource(System.Web.HttpContext.Current.Server.MapPath("~/Images/e1.jpg"), MediaTypeNames.Image.Jpeg); 
     inline.ContentId = "1"; 
     inline.TransferEncoding = System.Net.Mime.TransferEncoding.Base64; 
     avHtml.LinkedResources.Add(inline); 

     LinkedResource inline1 = new LinkedResource(System.Web.HttpContext.Current.Server.MapPath("~/CImages/2.jpg"), MediaTypeNames.Image.Jpeg); 
     inline1.ContentId = "2"; 
     inline1.TransferEncoding = System.Net.Mime.TransferEncoding.Base64; 
     avHtml.LinkedResources.Add(inline1); 

     LinkedResource inline2 = new LinkedResource(System.Web.HttpContext.Current.Server.MapPath("~/Images/3.jpg"), MediaTypeNames.Image.Jpeg); 
     inline2.ContentId = "3"; 
     inline2.TransferEncoding = System.Net.Mime.TransferEncoding.Base64; 
     avHtml.LinkedResources.Add(inline2); 

     LinkedResource inline3 = new LinkedResource(System.Web.HttpContext.Current.Server.MapPath("~/Content/Images/4.jpg"), MediaTypeNames.Image.Jpeg); 
     inline3.ContentId = "4"; 
     inline3.TransferEncoding = System.Net.Mime.TransferEncoding.Base64; 
     avHtml.LinkedResources.Add(inline3); 

     MailMessage mail = new MailMessage(); 
     mail.AlternateViews.Add(avHtml); 

HTML:

 <img src="cid:1" alt="" /> 
     <img src="cid:2" alt="" /> 
     <img src="cid:3" alt="" /` 
     <img src="cid:4" alt="" /> 
Các vấn đề liên quan