纽威
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

284 lines
12 KiB

3 years ago
  1. using NPOI.HSSF.UserModel;
  2. using NPOI.SS.UserModel;
  3. using NPOI.SS.Util;
  4. using System;
  5. using System.Collections.Generic;
  6. using System.Data;
  7. using System.IO;
  8. using System.Text;
  9. namespace NFine.Code.Excel
  10. {
  11. public class NPOIExcel
  12. {
  13. private string _title;
  14. private string _sheetName;
  15. private string _filePath;
  16. /// <summary>
  17. /// 导出到Excel
  18. /// </summary>
  19. /// <param name="table"></param>
  20. /// <returns></returns>
  21. public bool ToExcel(DataTable table)
  22. {
  23. FileStream fs = new FileStream(this._filePath, FileMode.OpenOrCreate, FileAccess.ReadWrite);
  24. IWorkbook workBook = new HSSFWorkbook();
  25. this._sheetName = this._sheetName.IsEmpty() ? "sheet1" : this._sheetName;
  26. ISheet sheet = workBook.CreateSheet(this._sheetName);
  27. //处理表格标题
  28. IRow row = sheet.CreateRow(0);
  29. row.CreateCell(0).SetCellValue(this._title);
  30. sheet.AddMergedRegion(new CellRangeAddress(0, 0, 0, table.Columns.Count - 1));
  31. row.Height = 500;
  32. ICellStyle cellStyle = workBook.CreateCellStyle();
  33. IFont font = workBook.CreateFont();
  34. font.FontName = "微软雅黑";
  35. font.FontHeightInPoints = 17;
  36. cellStyle.SetFont(font);
  37. cellStyle.VerticalAlignment = VerticalAlignment.Center;
  38. cellStyle.Alignment = HorizontalAlignment.Center;
  39. row.Cells[0].CellStyle = cellStyle;
  40. //处理表格列头
  41. row = sheet.CreateRow(1);
  42. for (int i = 0; i < table.Columns.Count; i++)
  43. {
  44. row.CreateCell(i).SetCellValue(table.Columns[i].ColumnName);
  45. row.Height = 350;
  46. sheet.AutoSizeColumn(i);
  47. }
  48. //处理数据内容
  49. for (int i = 0; i < table.Rows.Count; i++)
  50. {
  51. row = sheet.CreateRow(2 + i);
  52. row.Height = 250;
  53. for (int j = 0; j < table.Columns.Count; j++)
  54. {
  55. row.CreateCell(j).SetCellValue(table.Rows[i][j].ToString());
  56. sheet.SetColumnWidth(j, 256 * 15);
  57. }
  58. }
  59. //写入数据流
  60. workBook.Write(fs);
  61. fs.Flush();
  62. fs.Close();
  63. return true;
  64. }
  65. /// <summary>
  66. /// 导出到Excel
  67. /// </summary>
  68. /// <param name="table"></param>
  69. /// <param name="title"></param>
  70. /// <param name="sheetName"></param>
  71. /// <returns></returns>
  72. public bool ToExcel(DataTable table, string title, string sheetName, string filePath)
  73. {
  74. this._title = title;
  75. this._sheetName = sheetName;
  76. this._filePath = filePath;
  77. return ToExcel(table);
  78. }
  79. /// <summary>
  80. /// 组装workbook.
  81. /// </summary>
  82. /// <param name="dictionary">列头</param>
  83. /// <param name="dt">dataTable数据</param>
  84. /// <param name="columnHeader">表头</param>
  85. /// <returns></returns>
  86. public HSSFWorkbook BuildWorkbook(Dictionary<string, string> dictionary, DataTable dt, string columnHeader = "")
  87. {
  88. var workbook = new HSSFWorkbook();
  89. ISheet sheet = workbook.CreateSheet(string.IsNullOrWhiteSpace(dt.TableName) ? "Sheet1" : dt.TableName);
  90. var dateStyle = workbook.CreateCellStyle();
  91. var format = workbook.CreateDataFormat();
  92. dateStyle.DataFormat = format.GetFormat("yyyy-mm-dd");
  93. //取得列宽
  94. // var arrColWidth = new int[dt.Columns.Count];
  95. var arrColWidth = new int[dictionary.Count + 1];
  96. int itemCoutn = 0;//需要导出的列的数量.
  97. foreach (DataColumn item in dt.Columns)
  98. {
  99. //判断需要导出的 “列”
  100. if (dictionary.ContainsKey(item.ColumnName))
  101. {
  102. arrColWidth[itemCoutn] = Encoding.GetEncoding(936).GetBytes(item.ColumnName.ToString()).Length;
  103. itemCoutn++;
  104. }
  105. }
  106. itemCoutn = 0;
  107. for (var i = 0; i < dt.Rows.Count; i++)
  108. {
  109. for (var j = 0; j < dt.Columns.Count; j++)
  110. {
  111. //判断需要导出的 “列”
  112. if (dictionary.ContainsKey(dt.Rows[i][j].ToString()))
  113. {
  114. int intTemp = Encoding.GetEncoding(936).GetBytes(dt.Rows[i][j].ToString()).Length;
  115. if (intTemp > arrColWidth[j])
  116. {
  117. arrColWidth[j] = intTemp;
  118. }
  119. }
  120. }
  121. }
  122. int rowIndex = 0;//行索引,第一行为:表头(列头)
  123. foreach (DataRow row in dt.Rows)
  124. {
  125. #region 表头 列头
  126. if (rowIndex == 65535 || rowIndex == 0)
  127. {
  128. if (rowIndex != 0)
  129. {
  130. sheet = workbook.CreateSheet();
  131. }
  132. #region 表头及样式
  133. {
  134. IRow headerRow = sheet.CreateRow(0);
  135. headerRow.HeightInPoints = 19.5F;
  136. headerRow.Height = 40 * 20;
  137. headerRow.CreateCell(0).SetCellValue(columnHeader);
  138. //CellStyle
  139. ICellStyle headStyle = workbook.CreateCellStyle();
  140. headStyle.Alignment = NPOI.SS.UserModel.HorizontalAlignment.Center;// 左右居中
  141. headStyle.VerticalAlignment = VerticalAlignment.Center;// 上下居中
  142. // 设置单元格的背景颜色(单元格的样式会覆盖列或行的样式)
  143. headStyle.FillForegroundColor = (short)11;
  144. //定义font
  145. IFont font = workbook.CreateFont();
  146. font.FontHeightInPoints = 20;
  147. font.Boldweight = 700;
  148. headStyle.SetFont(font);
  149. headerRow.GetCell(0).CellStyle = headStyle;
  150. //根据表的列数计算
  151. //sheet.AddMergedRegion(new NPOI.SS.Util.CellRangeAddress(0, 0, 0, dt.Columns.Count - 1));
  152. sheet.AddMergedRegion(new NPOI.SS.Util.CellRangeAddress(0, 0, 0, dictionary.Count));
  153. #endregion
  154. }
  155. {
  156. #region 列头及样式
  157. var headerRow = sheet.CreateRow(1);
  158. //CellStyle
  159. ICellStyle headStyle = workbook.CreateCellStyle();
  160. headStyle.Alignment = NPOI.SS.UserModel.HorizontalAlignment.Center;// 左右居中
  161. headStyle.VerticalAlignment = VerticalAlignment.Center;// 上下居中
  162. //定义font
  163. IFont font = workbook.CreateFont();
  164. font.FontHeightInPoints = 10;
  165. font.Boldweight = 700;
  166. headStyle.SetFont(font);
  167. int columnCount = 0;
  168. foreach (var dic in dictionary)
  169. {
  170. foreach (DataColumn column in dt.Columns)
  171. {
  172. //判断需要导出的 “列”
  173. if (dic.Key.ToLower() == column.ColumnName.ToLower())
  174. {
  175. //headerRow.CreateCell(column.Ordinal).SetCellValue(column.ColumnName);
  176. //headerRow.GetCell(column.Ordinal).CellStyle = headStyle;
  177. //sheet.SetColumnWidth(column.Ordinal, (arrColWidth[column.Ordinal] + 1) * 256);
  178. headerRow.CreateCell(columnCount).SetCellValue(dic.Value);//column.ColumnName
  179. headerRow.GetCell(columnCount).CellStyle = headStyle;
  180. sheet.SetColumnWidth(columnCount, (arrColWidth[columnCount]) * 256);
  181. columnCount++;
  182. continue;
  183. }
  184. }
  185. }
  186. #endregion
  187. }
  188. rowIndex = 2;
  189. }
  190. #endregion
  191. #region 内容
  192. var dataRow = sheet.CreateRow(rowIndex);
  193. int columnContentCount = 0; //column.Ordinal
  194. foreach (var dicKey in dictionary)
  195. {
  196. foreach (DataColumn column in dt.Columns)
  197. {
  198. //判断需要导出的 “列”
  199. if (dicKey.Key.ToLower() == column.ColumnName.ToLower())
  200. {
  201. var newCell = dataRow.CreateCell(columnContentCount);
  202. string drValue = row[column].ToString();
  203. switch (column.DataType.ToString())
  204. {
  205. case "System.String"://字符串类型
  206. newCell.SetCellValue(drValue);
  207. break;
  208. case "System.DateTime"://日期类型
  209. DateTime dateV;
  210. DateTime.TryParse(drValue, out dateV);
  211. newCell.SetCellValue(dateV);
  212. newCell.CellStyle = dateStyle;//格式化显示
  213. break;
  214. case "System.Boolean"://布尔型
  215. bool boolV = false;
  216. bool.TryParse(drValue, out boolV);
  217. newCell.SetCellValue(boolV);
  218. break;
  219. case "System.Int16"://整型
  220. case "System.Int32":
  221. case "System.Int64":
  222. case "System.Byte":
  223. int intV = 0;
  224. int.TryParse(drValue, out intV);
  225. newCell.SetCellValue(intV);
  226. break;
  227. case "System.Decimal"://浮点型
  228. case "System.Double":
  229. double doubV = 0;
  230. double.TryParse(drValue, out doubV);
  231. newCell.SetCellValue(doubV);
  232. break;
  233. case "System.DBNull"://空值处理
  234. newCell.SetCellValue("");
  235. break;
  236. default:
  237. newCell.SetCellValue("");
  238. break;
  239. }
  240. columnContentCount++;//列索引
  241. continue;
  242. }
  243. }
  244. }
  245. #endregion
  246. rowIndex++;
  247. }
  248. //自动列宽
  249. for (int i = 0; i <= dictionary.Count; i++)
  250. sheet.AutoSizeColumn(i, true);
  251. return workbook;
  252. }
  253. }
  254. }