Asp.net程序中生成Excel报表

 

   在后台调用excel组件,生成Excel,虽然可以Excel文件进行完全控制,可以生成任何复杂的格式,但是有个很大的缺点,这种方式会产生很多Excel进程很难完全清掉,特别是在出错的时候,可能会使整个服务器崩溃。本文为大家介绍一个C#写的开源组件,并简单说下office2003和以上版本支持的XML格式。

 操作Excel二进制格式

    OpenOffice.org发布过的俩个文档Excel File Format (BIFF8)SpecificationMicrosoft CompoundDocument (OLE2) Format SpecificationExcel的二进制格式做了一个比较详细的说明,依靠这些信息,我们可以直接操作Office二进制格式文档。

  MyXls是一个C#写的开源组件,可以用来生成具有很多表格且包含格式的Excel文件。它提供了一套基于对象的API,非常容易使用。

1,生成一个空的表格

       

1 XlsDocument xls = new XlsDocument(); //创建一个空的Excel文档
2        
3 xls.Send(); //将文档发送到浏览器。

2, 创建一个复杂点表格
 XlsDocument xls = new XlsDocument();
            xls.FileName 
= "Wacky.xls";

            
//添加文件属性
            xls.SummaryInformation.Author = "Tim Erickson"//作者
            xls.SummaryInformation.Subject = "A wacky display of Excel file generation";
            xls.DocumentSummaryInformation.Company 
= "in2bits.org";

            
for (int sheetNumber = 1; sheetNumber <= 5; sheetNumber++)
            
{
                
string sheetName = "Sheet " + sheetNumber;
                
int rowMin = sheetNumber;
                
int rowCount = sheetNumber + 10;
                
int colMin = sheetNumber;
                
int colCount = sheetNumber + 10;
                
//创建5个表格
                Worksheet sheet = xls.Workbook.Worksheets.AddNamed(sheetName);
                Cells cells 
= sheet.Cells;
                
for (int r = 0; r < rowCount; r++)
                
{
                    
if (r == 0)
                    
{
                        
for (int c = 0; c < colCount; c++)
                        
{
                            
//在一行内创建colCount个单元格
                            cells.Add(rowMin + r, colMin + c, "Fld" + (c + 1)).Font.Bold = true;
                        }

                    }

                    
else
                    
{
                        
for (int c = 0; c < colCount; c++)
                        
{
                            
int val = r + c;
                            Cell cell 
= cells.Add(rowMin + r, colMin + c, val);
                            
if (val % 2 != 0)
                            
{
                                cell.Font.FontName 
= "Times New Roman";
                                cell.Font.Underline 
= UnderlineTypes.Double;//给文字下方加一个双下划线
                                cell.Rotation = 45;//单元格文字旋转45度
                            }

                        }

                    }

                }

            }

效果图,一个Excel文件包含五个表格

二 XML格式

office2003或以上版本才支持xml格式,这样可以直接通过一些模板将内容转化为Office可以识别的xml,限于时间,下次再与大家讨论:-)
标签: asp.net , excel
posted @ 2008-04-14 22:22 心利 阅读(8099) 评论(55) 编辑 收藏

 回复 引用 查看   
#1楼 2008-04-14 22:38 | willieQ      
不错。。。学习,收藏
 回复 引用 查看   
#2楼 2008-04-14 23:04 | peace      
这个处理很好
 回复 引用 查看   
#3楼[楼主] 2008-04-14 23:10 | 汉广      
@peace
这俩天正好也在做导出到Excel,看了你的文章才想到写这个的。。。。


 回复 引用 查看   
#4楼 2008-04-14 23:10 | jillzhang      
这样的事情很有意义
 回复 引用 查看   
#5楼[楼主] 2008-04-14 23:16 | 汉广      
@jillzhang
试用了 MyXls,觉的很好用,而且开源的也可靠,
发现SourceForge这个东西下载量非常小,所以拿来介绍下:-)
 回复 引用   
#6楼 2008-04-15 00:29 | Ricky81[未注册用户]
我记得MS已经正式官方发布了Office的二进制文档格式说明。
 回复 引用 查看   
#7楼 2008-04-15 00:36 | 簡簡單單..      
不错不错
 回复 引用 查看   
#8楼 2008-04-15 07:07 | 生鱼片      
MyXLS记住了
 回复 引用 查看   
#9楼 2008-04-15 07:26 | 新程金锣      
挺好的
 回复 引用 查看   
#10楼 2008-04-15 08:15 | OneCool      
ushort fontIndex = BitConverter.ToUInt16(recordData.Get(0, 2).ByteArray, 0);
ushort formatIndex = BitConverter.ToUInt16(recordData.Get(2, 2).ByteArray, 0);
//ushort styleIndex = BitConverter.ToUInt16(recordData.Get(4, 2))
Font font = fonts[fontIndex];

以前看到过,在读EXCEL文件的时候有错误。
 回复 引用 查看   
#11楼 2008-04-15 08:23 | 李战      
路过,学习!

 回复 引用 查看   
#12楼 2008-04-15 09:01 | 心悦      
不错,学习之
 回复 引用 查看   
#13楼 2008-04-15 09:09 | 狼Robot      
学习
 回复 引用   
#14楼 2008-04-15 09:33 | liu ray[未注册用户]
非常好
 回复 引用 查看   
#15楼 2008-04-15 09:36 | 小龙3      
一直苦恼.NET下没有类似于JAVA下的JExcelApi,现在好了!!

谢谢博主!!!!
 回复 引用 查看   
#16楼 2008-04-15 09:44 | 天生俪姿      
8错8错
呱叽呱叽
 回复 引用 查看   
#17楼 2008-04-15 09:48 | 鹏鹏_Lovely      
期待你的XML哦。谢啦。
 回复 引用 查看   
#18楼 2008-04-15 10:00 | 鹏鹏_Lovely      
MyXls————C#写的开源组件。可以给我一份吗,我想要个MyXls组件。
 回复 引用 查看   
#19楼[楼主] 2008-04-15 10:48 | 汉广      
@鹏鹏_Lovely
文章里有链接的:-)
@所有人
谢谢大家支持
 回复 引用 查看   
#20楼 2008-04-15 19:09 | 恋恋风尘      
没个文档,没个性能测试数据,实在不放心用在自己的项目中
 回复 引用 查看   
#21楼[楼主] 2008-04-15 19:44 | 汉广      
@恋恋风尘
感觉性能还行,可以自己测试下
 回复 引用 查看   
#22楼 2008-04-15 22:47 | Jim~      
果然够简单的~~~支持下
 回复 引用   
#23楼 2008-04-16 10:01 | nine425[未注册用户]
请问楼主:
1 XlsDocument xls = new XlsDocument(); //创建一个空的Excel文档
2
3 xls.Send(); //将文档发送到浏览器。

请问xls.Send();如何将文档只发送到IE浏览器中?我试了一下,只提示下载还是打开,可不可以不显示提示直接在IE中打开?
 回复 引用   
#24楼 2008-04-16 11:07 | nine425[未注册用户]
我又查了一下MyXls的源码,可以这样发送到浏览器:
xls.Send(XlsDocument.SendMethods.Inline);
 回复 引用   
#25楼 2008-04-16 11:11 | nine425[未注册用户]
再问楼主:
通过MyXls如何打开一个已存在的xls文档呢?
 回复 引用   
#26楼 2008-04-16 11:15 | nine425[未注册用户]
如果我这样写:
XlsDocument xls = new XlsDocument(@"D:\My Net\WebSite1\xls\test.xls");
运行时提示错误如下:

“/WebSite1”应用程序中的服务器错误。
--------------------------------------------------------------------------------

value already exists
参数名: name
说明: 执行当前 Web 请求期间,出现未处理的异常。请检查堆栈跟踪信息,以了解有关该错误以及代码中导致错误的出处的详细信息。

异常详细信息: System.ArgumentException: value already exists
参数名: name
 回复 引用 查看   
#27楼[楼主] 2008-04-16 11:42 | 汉广      
@nine425
还不支持读操作的。。。。。
 回复 引用   
#28楼 2008-04-16 12:52 | channel139[未注册用户]
不错学习之
 回复 引用   
#29楼 2008-04-16 13:15 | nine425[未注册用户]
请问:
xls.Send(XlsDocument.SendMethods.Inline); 是将内容显示在当前页面,那么如何让内容显示在另一个页面呢?
比如:左右两个框架,点击左框架某个按钮,会在右框架显示相关文件内容。
 回复 引用   
#30楼 2008-04-16 17:19 | nine425[未注册用户]
可能我问的问题太简单了点。左框架链接页面显示在右框架,这个我会。我的问题是:如果左框架显示了很多xls文件,这些文件可能分布在服务端众多的不同的目录,而我并未将这些目录在IIS中做成虚拟目录(如果做成虚拟目录,给xlls文件名写个超链接接可以了,但目录实在是太多)。现在我想实现的效果是:点击左框架xls文件名,会在右框架中(或在单独的一个页面,如果不用框架的话)显示该xls文件内容。我的xls文件内容读取方法采用MyXls的HttpContent方法。而MyXls新建xls文件后,采用xls.Send(XlsDocument.SendMethods.Inline); 只能将内容覆盖显示在当前页面,所以想请教楼主能不能让它单独显示在另一个页面呢?
谢谢!
 回复 引用 查看   
#31楼[楼主] 2008-04-16 20:21 | 汉广      
@nine425
xls.Send()方法只是把当前excel文档的二进制流写入当前的输出流,
xls.Send(XlsDocument.SendMethods.Inline)只是给Http响应加了个
“Content-Disposition: Inline” Header,它使得浏览器默认处理附件的方式为直接打开,而不是保存。
关于Content-Disposition的更多信息可以浏览RFC1806
http://www.ietf.org/rfc/rfc1806.txt

至于你说的Feature,建议可以使用Javascript监测左框架的点击事件,驱动右边框架的地址。

至于读取Excel文件,ADO.net比较好的支持Excel文件读取,可以参考
http://support.microsoft.com/kb/306572/

欢迎讨论,希望这些信息对你有用:-)
 回复 引用   
#32楼 2008-04-17 13:02 | nine425[未注册用户]
谢谢楼主!这些信息很有价值。
不过,我想要的效果很简单,将xls文档或doc文档直接显示在另一个页面即可,但不通过链接如:http://...//test.doc的方式。直接读取服务端路径的某个office文件,采用二进制流,所以我对MyXls比较感兴趣。
 回复 引用   
#33楼 2008-04-24 15:03 | Justinian[未注册用户]
不行,用不来。 使用后打开的excel里全是当前页的一些html编码,而且汉字都是乱码,也没产生5个sheet页,请教博主,我哪里出问题了?
 回复 引用 查看   
#34楼[楼主] 2008-04-25 10:56 | 汉广      
怎么可能,你把代码贴上来看看
 回复 引用 查看   
#35楼 2008-04-28 14:15 | 冷火      
我怎知道,怎么合并单元格?
 回复 引用   
#36楼 2008-04-28 16:05 | cepheus[未注册用户]
楼主,我想知道怎么设置单元格的宽度?
我用
ColumnInfo col = new ColumnInfo(xls, sheet);
sheet.AddColumnInfo(col);
col.Width = 5120;
但是这只能改变第一列的宽度,后面的就变不了了,不知道这是为什么?
 回复 引用   
#37楼 2008-04-29 13:52 | Justinian[未注册用户]
我自己使用最简单的代码都出错,

XlsDocument xls = new XlsDocument();
xls.Send();

这样子产生的文档内容为当前页的一些html编码,且汉字成了乱码。
请教博主,我哪里出问题了?
我是用vs2008在测。 不知道和这个有没有关系!
 回复 引用   
#38楼 2008-04-29 17:06 | zhangyi[未注册用户]
XlsDocument xls = new XlsDocument(path);
为什么执行到这个地方总有问题 ,我想吧本地xls文件读出来 这样不行吗
 回复 引用 查看   
#39楼 2008-04-29 17:33 | 冷火      
我知道怎合并单元格了
 回复 引用 查看   
#40楼[楼主] 2008-04-30 10:16 | 汉广      
对不起,刚看到评论。

@冷火
@cepheus
单元格长度可以这样改变
ColumnInfo col = new ColumnInfo(xls, sheet);
cInfo.ColumnIndexStart = 1;
cInfo.ColumnIndexEnd = 4;
sheet.AddColumnInfo(col);
col.Width = 5120;

@Justinian
这个程序是2.0的,可能3.5会有问题,
@zhangyi
目前不支持读操作
 回复 引用 查看   
#41楼[楼主] 2008-04-30 10:24 | 汉广      
刚才那段程序敲错了,应该这样 :-)
ColumnInfo cInfo = new ColumnInfo(xls, sheet);
cInfo.ColumnIndexStart = 1;
cInfo.ColumnIndexEnd = 4;
col.Width = 5120;
sheet.AddColumnInfo(col);

ColumnInfo类那俩个属性用来设置所要影响的列。
 回复 引用   
#42楼 2008-06-06 15:23 | LouisWang[未注册用户]
这位大哥,你提供的这个开源组件很有用,我正在为这个问题头痛,正好给我解决了,谢谢!
 回复 引用   
#43楼 2008-06-07 18:28 | dot net菜鳥[未注册用户]
好東西,有沒有技术文檔?如使用參考之類的?
 回复 引用   
#44楼 2008-09-02 10:46 | 郭斌[未注册用户]
IE6下,生成Excel文件之后,会有一个空白页,楼主知道怎么把该空白页删除掉吗。IE7下面则没有这个问题
 回复 引用 查看   
#45楼 2008-09-03 14:12 | 徐文兵      
对了 问一下 行高 怎么 设置阿
 回复 引用 查看   
#46楼 2008-09-03 15:25 | 天下鹰      
还有就是,隐藏一个不要的列怎么设置呢?

急需。。。
 回复 引用 查看   
#47楼[楼主] 2008-10-07 17:02 | 汉广      
@郭斌
@天下鹰
@徐文兵
对不起,前阵子一直没打理博客,没看到各位的留言。
 回复 引用   
#48楼 2009-03-05 18:16 | 张新[未注册用户]
MergeArea meaA = new MergeArea(1, 2, 3, 4);//一个合并单元格实例(合并第一行、第三例 到 第二行、第四例)
sheet.AddMergeArea(meaA);
加上这段代码后生成的XLS不能正常打开,如果去掉以后就可以正常打开了,这什么原因啊,3Q
 回复 引用 查看   
#49楼 2009-03-05 22:42 | 猫狼      
如何插入分页符啊
 回复 引用   
#50楼 2009-03-07 13:26 | Fy123[未注册用户]
如何单元格自动换行?
 回复 引用 查看   
#51楼 2010-04-16 11:16 | Mr Chai      
最大的缺点应该是不能打开一个文档吧。
 回复 引用 查看   
#52楼 2010-11-09 11:45 | 城市の蜗牛      
性能咋样?
 回复 引用 查看   
#53楼[楼主] 2010-12-27 22:41 | 心利      
@城市の蜗牛
很快
 回复 引用 查看   
#54楼[楼主] 2010-12-27 22:44 | 心利      
@Mr Chai
你说的是使用一个Excel模板,然后填充内容,创建一个Excel文件吧?你可以直接用ADO.NET,Insert语句就可以搞定了,性能相对很好
 回复 引用 查看   
#55楼 2011-04-01 15:52 | dotnet初行者      
请问xls.Send();怎么提示不包括send的方法