2012-03-20 23 views
8

我需要能够以HTML数据传递到Outlook这样创建HTML:从数据表使用C#

MailMessage message = new MailMessage(); 
message.Body = myBody; 

起初,我以为我可以纯文本传递给它,并使用PadLeft这样的:

somestring.PadLeft(100); 

但它没有正确对齐所有内容,因为即使|||||MMMMM都只有5个字符的长度,它们在屏幕上物理上占用更多空间。

我的解决方案是将数据表中的数据转换为HTML表格,然后将其传递到Outlook。

  1. 如何将数据表转换为html表?
  2. 有没有更好的解决我的问题?

非常感谢您的帮助。

+2

迭代DataTable的Rows和Columns集合,并根据单个单元格值构建一个html字符串。 – mservidio 2012-03-20 18:38:49

+1

他们占用不同数量的空间,因为您使用的字体不是等宽字体。也许一个等宽字体是一个解决方案。 – 2012-03-20 18:40:05

+0

@DJQuimby非常感谢!什么是等宽字体的例子? – 2012-03-20 18:44:38

回答

16

循环访问DataTable并构建html字符串。 IE:

DataTable dt = new DataTable(); 

dt.Columns.Add("col1"); 
dt.Columns.Add("col2"); 
dt.Columns.Add("col3"); 
dt.Rows.Add(new object[] { "a", "b", "c" }); 
dt.Rows.Add(new object[] { "d", "e", "f" }); 

string tab = "\t"; 

StringBuilder sb = new StringBuilder(); 

sb.AppendLine("<html>"); 
sb.AppendLine(tab + "<body>"); 
sb.AppendLine(tab + tab + "<table>"); 

// headers. 
sb.Append(tab + tab + tab + "<tr>"); 

foreach (DataColumn dc in dt.Columns) 
{   
    sb.AppendFormat("<td>{0}</td>", dc.ColumnName);   
} 

sb.AppendLine("</tr>"); 

// data rows 
foreach (DataRow dr in dt.Rows) 
{ 
    sb.Append(tab + tab + tab + "<tr>"); 

    foreach (DataColumn dc in dt.Columns) 
    { 
     string cellValue = dr[dc] != null ? dr[dc].ToString() : ""; 
     sb.AppendFormat("<td>{0}</td>", cellValue); 
    } 

    sb.AppendLine("</tr>"); 
} 

sb.AppendLine(tab + tab + "</table>"); 
sb.AppendLine(tab + "</body>"); 
sb.AppendLine("</html>"); 
+0

非常感谢!对不起,我的HTML并不好。我如何将标签包裹在那里? – 2012-03-20 18:58:20

+0

我已更新代码片段以显示如何将其包装在标签中。看到这个关于使用HTML表格的网址:http://www.w3schools.com/html/html_tables.asp – mservidio 2012-03-20 19:14:11

+0

谢谢你啊!!!!!!!!令人惊叹的工作 – 2012-03-20 19:51:39

3

代码可能很长,我写在这里,我同意@mservidio。请按照此链接查看您需要执行的示例:this link

+0

备注:检查你的数据,如果他们不是数字他们可能包含HTML的无效字符,所以原始的ToString()不起作用(例如“<”)。 – 2012-03-20 18:49:36

2

如何转换数据表到HTML表?

唯一的方法是编写遍历每一行的代码,并以您需要的方式构建HTML字符串。

有没有更好的解决我的问题?

你可以使用等宽字体(如Courier)wihch可以让你通过简单地输出的空间权数正确对齐的一切,但你仍然需要发送的电子邮件中的HTML格式的设置适当的字体在文件上。

+0

谢谢!你能帮助这一个http://stackoverflow.com/questions/9793160/getting-the-innerhtml-of-an-htmltable-c-sharp – 2012-03-20 19:07:02

1

有很多方法可以输出HTML。

如果这是一个相对简单的格式(没有太多的格式,样式等),我一定会去@ mservidio的建议。

如果输出比较复杂,并且您有ASP.NET经验,您可以使用UserControl的路径,这样可以更灵活地管理输出。然后,您可以将控件的输出呈现为HTML,如下所示:

StringBuilder sb = new StringBuilder(); 
StringWriter tw = new StringWriter(sb); 
HtmlTextWriter hw = new HtmlTextWriter(tw); 

ctrl.RenderControl(hw); 
return sb.ToString(); 
+0

谢谢你!很简单。你能指点我一些你认为可能会起作用的代码吗? – 2012-03-20 18:57:43

+0

shai你能帮忙吗?http://stackoverflow.com/questions/9793160/getting-the-innerhtml-of-an-htmltable-c-sharp – 2012-03-20 19:07:15

+0

如果它很简单,我会选择@mservidio提供的答案 – 2012-03-20 19:22:46

6

我只是想分享我所做的。我希望这会有所帮助。

using System.Web.UI; 
using System.Web.UI.WebControls; 
using System.Data; 
using System.IO; 

public void Build(DataSet ds) 
{ 
    StringWriter sw = new StringWriter(); 
    HtmlTextWriter w = new HtmlTextWriter(sw); 

    foreach (DataTable dt in ds.Tables) 
    { 
     //Create a table 
     Table tbl = new Table(); 

     //Create column header row 
     TableHeaderRow thr = new TableHeaderRow(); 
     foreach (DataColumn col in dt.Columns) { 
      TableHeaderCell th = new TableHeaderCell(); 
      th.Text = col.Caption; 
      thr.Controls.Add(th); 
     } 
     tbl.Controls.Add(thr); 

     //Create table rows 
     foreach (DataRow row in dt.Rows) 
     { 
      TableRow tr = new TableRow(); 
      foreach (var value in row.ItemArray) 
      { 
       TableCell td= new TableCell(); 
       td.Text = value.ToString(); 
       tr.Controls.Add(td); 
      } 
      tbl.Controls.Add(tr); 
     } 

     tbl.RenderControl(w); 

    } 

    Response.Write(sw.ToString()); 
} 
0
public string toHTML_Table(DataTable dt) 
     { 
      if (dt.Rows.Count == 0) 
       return ""; 

      StringBuilder builder = new StringBuilder(); 
      builder.Append("<html>"); 
      builder.Append("<head>"); 
      builder.Append("<title>"); 
      builder.Append("Page-"); 
      builder.Append(Guid.NewGuid().ToString()); 
      builder.Append("</title>"); 
      builder.Append("</head>"); 
      builder.Append("<body>"); 
      builder.Append("<table border='1px' cellpadding='5' cellspacing='0' "); 
      builder.Append("style='border: solid 1px Silver; font-size: x-small;'>"); 
      builder.Append("<tr align='left' valign='top'>"); 
      foreach (DataColumn c in dt.Columns) 
      { 
       builder.Append("<td align='left' valign='top'><b>"); 
       builder.Append(c.ColumnName); 
       builder.Append("</b></td>"); 
      } 
      builder.Append("</tr>"); 
      foreach (DataRow r in dt.Rows) 
      { 
       builder.Append("<tr align='left' valign='top'>"); 
       foreach (DataColumn c in dt.Columns) 
       { 
        builder.Append("<td align='left' valign='top'>"); 
        builder.Append(r[c.ColumnName]); 
        builder.Append("</td>"); 
       } 
       builder.Append("</tr>"); 
      } 
      builder.Append("</table>"); 
      builder.Append("</body>"); 
      builder.Append("</html>"); 

      return builder.ToString(); 
     } 
0
public string ConvertDataTableToHTMLTableInOneLine(DataTable dt) 
    { 
     //Convert DataTable To HTML Table in one line 
     return "<table>\n<tr>" + string.Join("", dt.Columns.Cast<DataColumn>().Select(dc => "<td>" + dc.ColumnName + "</td>")) + "</tr>\n" + 
     "<tr>" + string.Join("</tr>\n<tr>", dt.AsEnumerable().Select(row => "<td>" + string.Join("</td><td>", row.ItemArray) + "</td>").ToArray()) + "</tr>\n<\table>"; 

    } 
-1
public string MakeJPGFromDataTable(DataTable dt) 
    { 
     Font fnt = new System.Drawing.Font("verdana", 10,FontStyle.Bold); 
     string strPath = Path.GetTempPath(); 
     string strJPG = ""; 
     strPath += "Publisher"; 
     Directory.CreateDirectory(strPath); 
     Graphics grfx = CreateGraphics(); 
     float nWdBMP = 0; 
     float nHtBMP = 0; 

     var TalleststringLength = dt.AsEnumerable().Max(row => row.ItemArray.Max(x => grfx.MeasureString(x.ToString(), fnt).Height)); 
     var longeststringLength = dt.AsEnumerable().Max(row => row.ItemArray.Max(x => grfx.MeasureString(x.ToString(), fnt).Width)); 
     //string ss = dt.Columns[1].ToString(); 
     //int[] nColHeaderLengths = (from z in new int[7] { 0, 1, 2, 3, 4, 5, 6 } select dt.Columns.Cast<DataColumn>().Max(dc => (int)grfx.MeasureString(dt.Columns[z].ToString(), fnt).Width)).ToArray(); 
     //int[] nColWidths = (from z in new int[7] { 0, 1, 2, 3, 4, 5, 6 } select dt.AsEnumerable().Max(row => (int)grfx.MeasureString(row.ItemArray[z].ToString(), fnt).Width)).ToArray(); 
     var xx = (from x in dt.Columns.Cast<DataColumn>() select x.Ordinal).ToArray(); 
     var nColWidths = (from z in (xx) 
          select dt.AsEnumerable().Max(row => 
           (grfx.MeasureString(row.ItemArray[z].ToString(), fnt).Width > 
           grfx.MeasureString(dt.Columns[z].ToString(), fnt).Width) 
           ? grfx.MeasureString(row.ItemArray[z].ToString(), fnt).Width 
           : grfx.MeasureString(dt.Columns[z].ToString(), fnt).Width) 
      ).ToArray(); 

     nWdBMP = nColWidths.Sum(); 
     nHtBMP = TalleststringLength * (dt.Rows.Count + 1); 
     int xPos = 0; 
     int yPos = 0; 
     int nMargin = 10; 

     Bitmap mapMem = new Bitmap((int)nWdBMP + (nMargin * (dt.Columns.Count + 1)), (int)nHtBMP); 
     Graphics grfxMem = Graphics.FromImage(mapMem); 
     grfxMem.SmoothingMode = SmoothingMode.HighQuality; 
     grfxMem.InterpolationMode = InterpolationMode.HighQualityBicubic; 
     grfxMem.PixelOffsetMode = PixelOffsetMode.HighQuality; 
     grfxMem.CompositingQuality = CompositingQuality.GammaCorrected; 

     grfxMem.FillRectangle(lgBackgroundBrush,0,0,mapMem.Width,mapMem.Height); 

     for (int j = 0; j < dt.Columns.Count; j++) 
     { 
      grfxMem.DrawString(dt.Columns[j].ToString(), fnt, lgFontBrush, xPos, yPos); 
      //xPos += (int)grfx.MeasureString(dt.Columns[j].ToString(), fnt).Width; 
      xPos += (int)nColWidths[j] + nMargin; 
     } 
     xPos = 0; 
     yPos += (int)TalleststringLength; 
     grfxMem.DrawLine(pen, new Point(0, yPos), new Point((int)mapMem.Width, yPos)); 
     //foreach (DataRow dr in dt.Rows) 
     //{ 
     // for (int j = 0; j < dt.Columns.Count; j++) 
     // { 
     //  grfxMem.DrawString(dr[j].ToString(), fnt, Brushes.Blue, xPos, yPos); 
     //  xPos += (int)nColWidths[j] + nMargin; 
     // } 
     // xPos = 0; 
     // yPos += (int)TalleststringLength; 
     //} 
     int s = 0; 
     Func<object, bool> too_much_where = delegate(object itemCurrent) 
     { 
      grfxMem.DrawString(itemCurrent.ToString(), fnt, lgFontBrush, xPos, yPos); 
      xPos += (int)nColWidths[s++] + nMargin; 
      if (s >= dt.Columns.Count) 
      { 
       //Know what this determines the end of every row 
       s = 0; 
       xPos = 0; 
       yPos += (int)TalleststringLength; 
       grfxMem.DrawLine(pen, new Point(0, yPos), new Point((int)mapMem.Width, yPos)); 
      } 
      return false; 
     }; 
     //var sizzeler = (from dr in dt.AsEnumerable() 
     //    let drItems = (from itemCurrent in dr.ItemArray select itemCurrent) 
     //        from item in drItems 
     //        where too_much_where(item) 
     //     select new 
     //     { 
     //      z = true, 
     //     } 
     //    ).ToArray(); 
     var sizzeler = (from dr in dt.AsEnumerable() 
         where (dr.ItemArray.Where(itemCurrent => too_much_where(itemCurrent)).Count() == 0) 
         select new 
         { 
          z = true, 
         } 
         ).ToArray(); 
     s = 0; 
     for (int j = 0; j < nColWidths.Length; j ++) 
     { 
      grfxMem.DrawLine(pen, new Point(s, 0), new Point(s, (int)mapMem.Height)); 
      s += (int)(nColWidths[j] + nMargin); 
     } 
     s = mapMem.Width-1; 
     grfxMem.DrawRectangle(pen, new Rectangle(0, 0, mapMem.Width - 1, mapMem.Height - 1)); 
     s = 0; 
     grfx.DrawImage(mapMem, (float)10.0, (float)10.0); 
     grfx.Dispose(); 
     return strJPG; 
    } 
+0

他没有说JPG而是HTML。 – 2017-03-15 12:27:01

0

这是我的版本的话,添加了基于通用规则(rowHighlightRule参数)的可能性为 “亮点” 一些行。

public static string ToHTML(this DataTable dt, Func<DataRow, bool> rowHiglithRule) 
    { 

     if (dt == null) throw new ArgumentNullException("dt"); 

     string tab = "\t"; 

     StringBuilder sb = new StringBuilder(); 
     sb.AppendLine(tab + tab + "<table>"); 

     // headers. 
     sb.Append(tab + tab + tab + "<thead><tr>"); 

     foreach (DataColumn dc in dt.Columns) 
     { 
      sb.AppendFormat("<td>{0}</td>", dc.ColumnName); 
     } 

     sb.AppendLine("</thead></tr>"); 

     // data rows 
     foreach (DataRow dr in dt.Rows) 
     { 
      if (rowHiglithRule != null) 
      { 

       if (rowHiglithRule(dr)) 
       { 
        sb.Append(tab + tab + tab + "<tr class=\"highlightedRow\">"); 
       } 
       else 
       { 
        sb.Append(tab + tab + tab + "<tr>"); 
       } 
      } 
      else 
      { 
       //Non ho alcuna regola, quindi caso normale. 
       sb.Append(tab + tab + tab + "<tr>"); 
      } 

      foreach (DataColumn dc in dt.Columns) 
      { 
       string cellValue = dr[dc] != null ? dr[dc].ToString() : ""; 
       sb.AppendFormat("<td>{0}</td>", cellValue); 
      } 

      sb.AppendLine("</tr>"); 
     } 

     sb.AppendLine(tab + tab + "</table>"); 


     return sb.ToString(); 
    }