本帖只是把前一篇文章「ASP.NET 資料分頁第三篇 - 結合 Custom Control 處理 GridView 的 UI 呈現」裡面,提供給大家下載的 Custom Control,也就是加強「分頁」功能的 GridView,再改寫了一些細部功能。新功能如下:
* 這個 WizardGridView 所需要的 CSS、JavaScript,都已嵌入至 dll 裡。如此一來,引用 WizardGridView 的頁面即不必再引用外部的 CSS 檔。
* 新增了 5 個「屬性」,程式員可從 VS 2005/2008 的「屬性」視窗,以圖形介面直接做設定,如 1 右側所示。
* 新增的「CustomFontSize」屬性,可控制整個 GridView 裡字型的大小 (預設為 Small),且不會受到引用頁面中 HTML 設定的影響。
* 新增的屬性中,有三個是開放讓程式員自訂「單數行、雙數行、滑鼠置於其上的資料行」的背景顏色。
* 加入了 icon 小圖示。把 WizardGridView 加入 VS 2005/2008 的「工具箱」中時,會有我自訂的小圖示。
* 為了搭配一些用來製作 chm 檔案的軟體,加入了可讓 Sandcastle 軟體可辨識的批註文字。
* 有寫過自訂控制項的人應知道,當一個 class 直接繼承自微軟原生的 GridView class,會造成引用的 ASPX 頁面裡,此自訂 GridView 的 "Columns" tag 中的 IntelliSense 功能失效。因此我加入了 WizardTemplateField、WizardBoundField 兩個 class,用來取代微軟原生的 TemplateField、BoundField class。如此一來,當程式員在頁面中引用 WizardGridView 控制項時,在 "Columns" tag 中的 IntelliSense 即又會生效。請參考 2。
圖 1 新增的 5 個屬性,已集中在 Visual Studio「屬性」視窗的同一個 Index Tab 裡
圖 2 在 WizardGridView 的 "Columns" tag 中的 IntelliSense 仍會生效
本帖的範例程式碼下載點:
http://files.cnblogs.com/WizardWu/080928.zip
(執行本樣本,需要 SQL Server 的 Northwind 資料庫)
您只要直接以 VS 2005 開啟「方案檔 (.sln)」即可,裡面的「WizardGridView」檔案夾為 Custom Control 的 source code。用來 Demo 的網站範例有兩個,一個是「SqlDataSource」檔案夾,另一個是「ObjectDataSource」檔案夾,前者會自動連結您原生 SQL Server 2000/2005 的 Northwind 資料庫,後者必須要您先在 SQL Server 2005 的 Northwind 裡,先建立用來做「資料分頁」的 Stored Procedure (亦附於本帖的下載代碼裡),才能正確連結您原生 SQL Server 2005 的 Northwind 資料庫。
本帖的下載代碼裡,所附的新版的「資料分頁」Stored Procedure,加上了可處理 DISTINCT 需求的功能 (實際上是用 GROUP BY 取代 DISTINCT 去做處理)。在本系列的前兩篇文章「ASP.NET 資料分頁第一篇 - 探討分頁原理及 SQL Server 2005 的 ROW_NUMBER 函數」、「ASP.NET 資料分頁第二篇 - 範例下載」裡曾提到,若我們沒有用 Stored Procedure 去做「資料分頁」的處理,當資料表中有一百萬筆記錄時,則 ASP.NET 預設的行為,是使用者每次單擊頁碼換頁時,都是一百萬筆全部重新擷取,此舉會造成系統記憶體大量浪費、performance 大大降低,甚至造成當機。
在本系列前幾篇文章裡, 我們用來在 SQL Server 2005 中處理「資料分頁」的 Stored Procedure,主要是用 SQL Server 2005 內建的一個 ROW_NUMBER 函數去做處理。但 ROW_NUMBER 函數有一個缺點,就是會造成 DISTINCT 語句的功能失效;因此在本帖中的新版 Stored Procedure,是以 GROUP BY 取代 DISTINCT。在本帖下載代碼的「ObejctDataSource」Demo 網站裡,App_Code 檔案夾裡的 DAL 層、DAL2 層,也都會多傳 一個 strGroupBy 參數,給這個專門用來做「資料分頁」的 Stored Procedure。
引用此 Custom Control 頁面的代碼
<%@ Register Assembly="WizardGridView" Namespace="WizardGridView" TagPrefix="Wizard" %>
<Wizard:WizardGridView ID="WizardGridView1" runat="server" AllowPaging="True" AllowSorting="True"
AutoGenerateColumns="False" DataKeyNames="OrderID" DataSourceID="SqlDataSource1"
WizardCustomPager="True">
<Columns>
<asp:BoundField DataField="OrderID" HeaderText="OrderID" InsertVisible="False" ReadOnly="True"
SortExpression="OrderID" />
<asp:BoundField DataField="CustomerID" HeaderText="CustomerID" SortExpression="CustomerID" />
<asp:BoundField DataField="OrderDate" HeaderText="OrderDate" SortExpression="OrderDate" />
<asp:BoundField DataField="ShipName" HeaderText="ShipName" SortExpression="ShipName" />
<asp:BoundField DataField="ShipCity" HeaderText="ShipCity" SortExpression="ShipCity" />
</Columns>
</Wizard:WizardGridView>
<asp:SqlDataSource ID="SqlDataSource1" runat="server" ConnectionString="<%$ ConnectionStrings:ConnString_SqlClient %>"
SelectCommand="SELECT [OrderID], [CustomerID], [OrderDate], [ShipName], [ShipCity] FROM [Orders]">
</asp:SqlDataSource>
or with IntelliSense like this:
<Wizard:WizardGridView ID="WizardGridView1" runat="server" AllowPaging="True" AllowSorting="True"
AutoGenerateColumns="False" DataKeyNames="OrderID" DataSourceID="SqlDataSource1"
WizardCustomPager="True">
<Columns>
<asp:WizardBoundField DataField="OrderID" HeaderText="OrderID" InsertVisible="False" ReadOnly="True"
SortExpression="OrderID" />
<asp:WizardTemplateField />