使用C#从DataTable创建HTML

我需要能够将HTML数据传递到Outlook,如下所示:

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

最初我以为我可以将纯文本传递给它并像这样使用PadLeft

 somestring.PadLeft(100); 

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

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

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

非常感谢你的帮助。

循环遍历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(""); sb.AppendLine(tab + ""); sb.AppendLine(tab + tab + ""); // headers. sb.Append(tab + tab + tab + ""); foreach (DataColumn dc in dt.Columns) { sb.AppendFormat("", dc.ColumnName); } sb.AppendLine(""); // data rows foreach (DataRow dr in dt.Rows) { sb.Append(tab + tab + tab + ""); foreach (DataColumn dc in dt.Columns) { string cellValue = dr[dc] != null ? dr[dc].ToString() : ""; sb.AppendFormat("", cellValue); } sb.AppendLine(""); } sb.AppendLine(tab + tab + "
{0}
{0}
"); sb.AppendLine(tab + ""); sb.AppendLine("");

我只想分享我的所作所为。 我希望这会有所帮助。

 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()); } 

如何将数据表转换为html表?

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

我的问题有更好的解决方案吗?

您可以使用等宽字体(例如Courier ),只需输出正确数量的空格,您就可以正确对齐所有内容,但仍需要以HTML格式发送电子邮件,在文档上设置正确的字体。

在这里写代码可能很长,我同意@mservidio。 请点击此链接查看您必须执行的操作的示例: 此链接

有许多方法可以输出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(); 
 public string ConvertDataTableToHTMLTableInOneLine(DataTable dt) { //Convert DataTable To HTML Table in one line return "\n" + string.Join("", dt.Columns.Cast().Select(dc => "")) + "\n" + "" + string.Join("\n", dt.AsEnumerable().Select(row => "").ToArray()) + "\n<\table>"; }
" + dc.ColumnName + "
" + string.Join("", row.ItemArray) + "
 public string toHTML_Table(DataTable dt) { if (dt.Rows.Count == 0) return ""; StringBuilder builder = new StringBuilder(); builder.Append(""); builder.Append(""); builder.Append(""); builder.Append("Page-"); builder.Append(Guid.NewGuid().ToString()); builder.Append(""); builder.Append(""); builder.Append(""); builder.Append(""); builder.Append(""); foreach (DataColumn c in dt.Columns) { builder.Append(""); } builder.Append(""); foreach (DataRow r in dt.Rows) { builder.Append(""); foreach (DataColumn c in dt.Columns) { builder.Append(""); } builder.Append(""); } builder.Append("
"); builder.Append(c.ColumnName); builder.Append("
"); builder.Append(r[c.ColumnName]); builder.Append("
"); builder.Append(""); builder.Append(""); return builder.ToString(); }

这是我的版本,增加了基于通用规则(rowHighlightRule参数)“突出显示”某些行的可能性。

  public static string ToHTML(this DataTable dt, Func rowHiglithRule) { if (dt == null) throw new ArgumentNullException("dt"); string tab = "\t"; StringBuilder sb = new StringBuilder(); sb.AppendLine(tab + tab + ""); // headers. sb.Append(tab + tab + tab + ""); foreach (DataColumn dc in dt.Columns) { sb.AppendFormat("", dc.ColumnName); } sb.AppendLine(""); // data rows foreach (DataRow dr in dt.Rows) { if (rowHiglithRule != null) { if (rowHiglithRule(dr)) { sb.Append(tab + tab + tab + ""); } else { sb.Append(tab + tab + tab + ""); } } else { //Non ho alcuna regola, quindi caso normale. sb.Append(tab + tab + tab + ""); } foreach (DataColumn dc in dt.Columns) { string cellValue = dr[dc] != null ? dr[dc].ToString() : ""; sb.AppendFormat("", cellValue); } sb.AppendLine(""); } sb.AppendLine(tab + tab + "
{0}
{0}
"); return sb.ToString(); }
  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().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() 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 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; }