使用
调用方法
通过ExcelsList.fm
生成一个处理数据的方法,此处用的lambda
,ExcelsList
的构造方法里,必须传的是列名,其他的如果没有就空着,下载的文件名无所谓,前台用的时候也可以给名字
DataTable ListData = 各种获取数据;
//列的信息
List dc=new List();
ExcelsList.fm isend = (string cellname,DataRow rows) =>
{
if (rows[cellname].ToString() == "1") return "待化解";
if (rows[cellname].ToString() == "2") return "已化解";
return "";
};
ExcelsList.fm getstate= (string cellname,DataRow rows)=> {
if (rows["isend"].ToString() == "1") { // 未办结
if (DateTime.Now.AddDays(Convert.ToInt32(rows["LimitDays"])) < Convert.ToDateTime(rows[cellname]))
{
//return "超期未办结";
return "超期未办结 ";
}
else if (DateTime.Now.AddDays(Convert.ToInt32(rows["LimitDays"]) * 2 / 3) < Convert.ToDateTime(rows[cellname]))
{
//return "黄色预警";
return "黄色预警 ";
}
else
{ //化解中
return "化解中 ";
}
} else {
return "已办结";
}
};
//添加所有显示的列
dc.Add(new ExcelsList("pctime", "状态", getstate));
dc.Add(new ExcelsList("id", "排查编号"));
dc.Add(new ExcelsList("pctime", "排查时间"));
dc.Add(new ExcelsList("name", "信访人姓名"));
dc.Add(new ExcelsList("addorg", "排查单位"));
dc.Add(new ExcelsList("nowexeorg", "承办单位"));
dc.Add(new ExcelsList("handlemode", "办理方式"));
dc.Add(new ExcelsList("isend", "是否化解", isend));
//导出
HPK.Utilities.DeriveExcel.DataTableandExcelsListToExcel(Response, ListData, dc, "化解" + DateTime.Now.ToString("yyyy-MM-dd HHmmss"));
复制代码
前台
这边千变万化的,具体情况具体对待,这里先记下一种
调用写在MVC的Controller里的方法
var a = document.createElement("a");
a.href = "url";
a.download = '化解' + formatDate(new Date(), "yyyy-MM-dd-hhmmss.xls"); //如果不填就是后台默认的名字
a.click();
复制代码
实现导出的部分
封装类
用来保存真实列名、显示列名和处理内容的方法
///
/// 列的信息
///
public class ExcelsList
{
#region 封装字段
//显示名称
public string zh_name;
//所在列名
public string col_name;
//过滤方法
public fm thisfm;
#endregion
#region 方法
///
/// 导出excel列的信息
///
/// "_col">列名
/// "_zh">列备注
/// "_thisfm">处理值的方法
public ExcelsList(string _col, string _zh = null, fm _thisfm = null)
{
this.col_name = _col;
this.zh_name = _zh;
this.thisfm = _thisfm;
}
///
/// 过滤的方法
///
/// "str">输入值
/// 返回一个方法
public delegate string fm(string str,DataRow dr = null);
///
/// 获取筛选后的返回值的方法
///
/// 返回值
public string retstr(DataRow ROW)
{
string str;
///是否过滤规则
if (this.thisfm != null)
{
str = this.thisfm(this.col_name, ROW);
}
else
{
str = ROW[this.col_name].ToString();
}
///是否规定格式
if (!str.StartsWith("))
{
str = " " + str + " ";
}
///返回值
return str;
}
#endregion
}
复制代码
后台
HttpResponseBase Response
视情况可以不用传值进来,直接HttpContext.Current.Response
///
/// DataTable导出Excel
///
/// "data">数据源
/// "DataColumn">导出的字段设置
/// "fileName">文件名称&表头
public static void DataTableAndExcellistToExcel(HttpResponseBase Response, DataTable data, List DataColumn, string fileName="Excel")
{
Response.ContentType = "application/vnd.ms-excel";
Response.ContentEncoding = System.Text.Encoding.UTF8;
Response.Charset = "Utf-8";
Response.AppendHeader("Content-Disposition", "attachment;filename=" + HttpUtility.UrlEncode(fileName + ".xls", System.Text.Encoding.UTF8));//给一个默认的名字,如果前台没给名字,那下载时候就是显示这个
StringBuilder sbHtml = new StringBuilder();
sbHtml.AppendLine("");
sbHtml.AppendLine("");
sbHtml.AppendLine("");
//表头
sbHtml.AppendLine("");
sbHtml.AppendLine(" + DataColumn .Count.ToString()+ "\" style='height:37.00pt;width:942.75pt;border-right:none;border-bottom:none;' x:str>" + fileName + " ");
sbHtml.AppendLine(" ");
//写出列名
sbHtml.AppendLine("");
foreach (ExcelsList item in DataColumn)
{
sbHtml.AppendLine("" + item.zh_name ?? item.col_name + " ");
}
sbHtml.AppendLine(" ");
//写数据
foreach (DataRow row in data.Rows)
{
sbHtml.Append("");
foreach (ExcelsList item in DataColumn)
{
sbHtml.Append(item.retstr(row));
}
sbHtml.AppendLine(" ");
}
sbHtml.AppendLine("
");
Response.Write(sbHtml.ToString());
Response.End();
}
复制代码
踩过的坑
1.导出的长串数字自动转换 科学计数法 显示
例如 201805241723197
,会在excel 里显示为2.01805E+16
,这个解决方法是
· x:str属性
有时候不太好用
str = " + str + "\">" + str + " ";
复制代码
· MSO-NUMBER-FORMAT
这个可以用
str = "" + str + " ";
复制代码
或者放进css里
sbHtml.AppendLine("");
...
str = "" + str + " ";
复制代码
其他的MSO-NUMBER-FORMAT
mso-number-format:"0" NO Decimals
mso-number-format:"0\.000" 3 Decimals
mso-number-format:"\#\,\#\#0\.000" Comma with 3 dec
mso-number-format:"mm\/dd\/yy" Date7
mso-number-format:"mmmm\ d\,\ yyyy" Date9
mso-number-format:"m\/d\/yy\ h\:mm\ AM\/PM" D -T AMPM
mso-number-format:"Short Date" 01/03/1998
mso-number-format:"Medium Date" 01-mar-98
mso-number-format:"d\-mmm\-yyyy" 01-mar-1998
mso-number-format:"Short Time" 5:16
mso-number-format:"Medium Time" 5:16 am
mso-number-format:"Long Time" 5:16:21:00
mso-number-format:"Percent" Percent - two decimals
mso-number-format:"0%" Percent - no decimals
mso-number-format:"0\.E+00" Scientific Notation
mso-number-format:"\@" Text
mso-number-format:"\#\ ???\/???" Fractions - up to 3 digits (312/943)
复制代码
2.Response.End()不知道为什么总是报错
从网上搜来的内容
Response.End()是终止服务器输出,但有可能会throw出线程异常,不处理即可,ms官方对该问题进行了解释,如果你不希望throw出线程错误,则可以采用相关解决方法。
用HttpContext.Current.ApplicationInstance.CompleteRequest();
代替后解决了