在一般的公司專屬應用程式開發中都會涉及到報表的產生,且一般報表的格式都是產生Excel格式的。對於各種報表的產生一直是程式員心中永遠的痛,因為對於很多程式員來說每寫一個報表都意味著要寫一大斷代碼來實現,而且有的報表可能極其複雜以及不規範,這時就會浪費程式員大量的時間來編寫和調試這些代碼,那到底有沒有一種方法能使代碼盡量少寫,且又能實現各種Excel報表的產生呢,下面我們就轉入正題。
我們要產生Excel報表,其實我們只需要兩樣東西:
1.報表的樣式,也就是哪個欄位應該填在哪裡,哪一列應該填什麼,字型大小,顏色,儲存格高度,寬度,儲存格是否合并,是否跨行,是否跨列,是橫向報表(所謂橫向報表,我自訂為:一張Excel報表就是有一條記錄或者有一條記錄以及其關聯記錄而產生的報表,如一張訂單報表通常就是有一個訂單頭和其相關的訂單明細所產生,這個就是我自訂的橫向報表)還是縱向報表(所謂縱向報表,我自訂為:一張報表就是有一個記錄集所產生的,如要產生一張記錄某個班級學生情況的報表,則要把這個班級的學生記錄都要匯出到這張報表中,這種報表基本上就是統計報表,一張報表可能會有幾萬條記錄或者更多,這個就是我自訂的縱向報表)等等報表樣式。
2.報表的資料,對於我們而言有了報表樣式,我們就知道在哪個或者哪幾個儲存格應該填哪些資料,具體的資料,我們則可以以DataTable的形式來表現,也可以以DataSet的形式來表現,至於用怎麼樣的資料格式可以隨自己喜歡,自己來定義。
現在我們知道了產生Excel報表只要有了樣式和資料,就可以產生一張自己想要的報表了,資料的產生並不困難,但是我們的困難就是這個報表的樣式用什麼來描述,怎麼來描述。
對於樣式的描述我們可以用兩種方法來實現:
1.直接用XML來描述,這個xml描述檔案的主要描述的內容可以如下(舉個列子說明一下,現在描述的還不是很規範):
<?xml version="1.0" encoding="UTF-8"?>
<Style>
<ExcelStyle Sort="縱向" Space="1">
<Ranges>
<RangeStyle>
<Range CellWidth="2.0" CellHeight="20" CellBord="1" CellBackColor=""></Range>
<TitleCell TitleName="組件編號" TitleStartxPos="1" TitleEndxPos="1" TitleStartyPos="1" TitleEndyPos="1"></TitleCell>
<DataCell DataName="PartNo" DataStartxPos="2" DataEndxPos="14" DataStartyPos="34" DataEndyPos="34"IsMerger="False" Align="XlHAlign.xlHAlignLeft" IsToArray="True" IsDateTime="False" Interval="1">
</DataCell>
<TitleFont TitleFontName="宋體" TitleFontSize="9" TitleFontColor="Black" TitleFontBold="False" TitleFontItatic="False" TitleFontPosition="Center"> </TitleFont>
<DataFont DataFontName="宋體" DataFontSize="11" DataFontColor="Black" DataFontBold="True" DataFontItatic="False" DataFontHyperLink="False" DataFontPosition="Center">
</DataFont>
</RangeStyle>
</Ranges>
</ExcelStyle>
</Style>
這個XML中結點Excelstyle的屬性Sort描述了整個Excel的格式是縱向的還是橫向的(所謂縱向還是橫向,我上面已有所說明),而屬性Space則描述了報表每個記錄的行與行之間空多少行。Ranges則是下面的所有子節點RangeStyle的父節點,對於一張報表通常會有很多的RangeStyle結點。RangeStyle其實就開始真正來描述哪個或哪些儲存格來填寫哪些欄位,如結點Range 就定義了儲存格高度,寬度,邊框寬度,顏色這些屬性。TitleCell就是定義了報表(因為我這張是縱向報表,所以有Title)Title的屬性,如Title的名稱,哪個儲存格來填寫這個名稱。節點DataCell則定義了要幫定資料中的哪個欄位,從哪個單元開始填寫,儲存格是否要合并,對齊,還有這個欄位行與行之間的間隔。結點Title Font定義了Title字型屬性,如大小,顏色,是否斜體,是否粗體,對齊。結點DataFont則定義了資料字型的屬性,如大小,顏色,是否斜體,是否粗體,對齊。一個RangeStyle結點其實也就定義了一個欄位的填寫,如果你的報表要填寫很多欄位的話,就會有很多個RangeStyle結點來描述。這個xml樣式定義檔案可以自己寫個工具來產生,我有現成的自己寫的產生工具叫ExcelStyle,不過還很簡陋,用起來還不方便,不過能產生我需要的樣式,哪位需要我可以發給你們(我不知道怎麼提供下載)。
2. XML描述檔案和Excel模板相結合的方法,對於有些報表會很複雜,特別是那些橫向的報表,有時候會極其複雜,這時就需要現成的Excel模板,有了Excel模板我們就可以參照著模板來產生xml樣式定義檔案,在具體產生報表的時候,我們只要知道用到的Excel模版是哪個,XML樣式檔案是哪個,再綁上我們的資料,那麼即使再複雜的報表也同樣能簡單產生了。
具體使用,可參照如下測試用列代碼(聲明ExcelOperate,XmlOperate是我自己寫的幾個通用的組件,如有需要我可發郵件給你們,其中資料我是以DataTable的形式來描述的):
sing System;
using NUnit.Framework;
using ExcelOperate;
using XmlOperate;
using System.Data;
using System.Data.SqlClient;
namespace TestExcel
{
/// <summary>
/// </summary>
///
[TestFixture]
public class ExcelExport
{
[Test]
public void Export()//不用Excel模板的資料匯出
{
string Sql ="Select top 100* from customers ";
//取出100條資料
ExcelFactory _factory = new ExcelFactory();
//定義一個沒有參數的ExcelFactory
_factory.CreateExcelwithoutTemplate("c://bbbbbbb.xml",GetDataTable(Sql ));
//載入定義的樣式檔案bbbbbbb.xml和剛取出來的資料GetDataTable(Sql )
_factory.SaveExcel("c://bbbbbbbbbbbbbbbb.xls");
//儲存匯出的檔案即可
}
[Test]
public void ExportWithTemplate()//用到了Excel模版的資料匯出
{
string Sql ="Select top 1* from customers ";
//取出一條資料
ExcelFactory _factory = new ExcelFactory("c://QStandardCustomer.xls");
//匯入模版QStandardCustomer.xls
_factory.CreateExcel("c://QStandardCustomer.xml",GetDataTable(Sql ));
//載入定義的樣式檔案QStandadrCustomer.xml和剛取出來的資料GetDataTable(Sql )
_factory.SaveExcel("c://Qreportstr.xls");
//最後儲存匯出的Excel檔案即可
}
private DataTable GetDataTable(string Sql)
{
string myConnectionString = "packet size=4096;user id=sa;data source=172.28.200.98;initial catalog=Northwind";
SqlConnection myConnection = new SqlConnection(myConnectionString);
myConnection.Open();
SqlDataAdapter myAdapter = new SqlDataAdapter();
SqlCommand myCommand = new SqlCommand(Sql,myConnection);
myCommand.CommandType = CommandType.Text;
myAdapter.SelectCommand = myCommand;
DataSet ds = new DataSet();
myAdapter.Fill(ds);
myConnection.Close();
return ds.Tables[0];
}
}
}
由上面代碼可見,一般的報表產生都是三句代碼,即使對於報表的某些行,某些格式要調整我們也不需要在去修改程式,只要改xml描述檔案即可,這樣就可以使我們大大的在報表的產生上來節省時間,而可以把更多的時間放在商務邏輯的處理上了。