在ASP.NET 2.0中操作數(shù)據(jù)之十四:使用FormView 的模板
導(dǎo)言
在上兩節(jié)教程中,我們看到了如何使用TemplateField來自定義GridView和DetailsView的輸入。TemplateField使我們可以高度自主的定義某個(gè)特定的列,但不管是GridView還是DetailsView,都會(huì)有點(diǎn)太規(guī)則了,簡(jiǎn)單的說就是它們都有著四四方方的格子一樣的外觀。很多情況下這樣的格子一樣的外觀是很不錯(cuò)的,不過有的時(shí)候我們卻需要使用一個(gè)不規(guī)則的顯示外觀。當(dāng)需要顯示一個(gè)單獨(dú)的記錄時(shí),使用FormView控件就可以實(shí)現(xiàn)這種比較隨意的外觀呈現(xiàn)。
跟DetailsView不同,F(xiàn)ormView并不是由那些雜七雜八的列所組成的。你不能給一個(gè)FormView添加BoundField或是TemplateField,不過FormView是使用模板來呈現(xiàn)的。我們可以這樣來理解FormView,把它當(dāng)作只含有一個(gè)TemplateField的DetailsView控件。FormView支持以下這些模板:
· ItemTemplate – 用于在FormView種呈現(xiàn)一個(gè)特殊的記錄
· HeaderTemplate – 用于指定一個(gè)可選的頁(yè)眉行
· FooterTemplate –用于指定一個(gè)可選的頁(yè)腳行
· EmptyDataTemplate – 當(dāng)FormView的DataSource缺少記錄的時(shí)候,EmptyDataTemplate將會(huì)代替
ItemTemplate來生成控件的標(biāo)記語言
· PagerTemplate – 如果FormView啟用了分頁(yè)的話,這個(gè)模板可以用于自定義分頁(yè)的界面
· EditItemTemplate / InsertItemTemplate – 如果FormView支持編輯或插入功能,那么這兩種模板可以用于自定義相關(guān)的界面
在本節(jié)教程中,我們將解釋如何使用FormView控件來為產(chǎn)品呈現(xiàn)一個(gè)不規(guī)則的外觀。FormView的ItemTemplate將會(huì)使用一個(gè)頁(yè)眉元素和<table>的結(jié)合體來顯示名稱、分類、供應(yīng)商等等的值,而不是使用各種各樣的列(如圖一所示)。

圖一:FormView打破了DetailsView的那種格子一樣外觀
第一步:將數(shù)據(jù)綁定到FormView
打開FormView.aspx頁(yè)面,并從工具箱中拖一個(gè)FormView到設(shè)計(jì)器中。FormView剛剛添加到頁(yè)面上時(shí),它就是一個(gè)灰色的方塊,這就告訴我們它需要一個(gè)ItemTemplate。

圖二:FormView在添加一個(gè)ItemTemplate之前是不會(huì)在設(shè)計(jì)器中呈現(xiàn)出來的
可以手工編寫代碼(在源視圖中)來添加ItemTemplate,也可以通過在設(shè)計(jì)器中將FormView綁定到一個(gè)數(shù)據(jù)源控件上來實(shí)現(xiàn)自動(dòng)添加。這個(gè)自動(dòng)生成的ItemTemplate包含了用于顯示各字段的名稱的HTML代碼,還有用于顯示各字段的值的Label控件,當(dāng)然了,這些Label控件的Text屬性都已經(jīng)綁定到了各相應(yīng)的字段上。這個(gè)操作也同時(shí)生成了InsertItemTemplate和EditItemTemplate,它們?yōu)閿?shù)據(jù)源控件的每一個(gè)字段都呈現(xiàn)了一個(gè)輸入控件。
如果你想要自動(dòng)生成模板,首先應(yīng)該使用ProductsBLL類的GetProducts()方法來給FormView添加一個(gè)ObjectDataSource控件,通過FormView的智能標(biāo)簽?zāi)憔涂梢宰龅缴厦娴倪@個(gè)操作。這樣就可以創(chuàng)建一個(gè)帶有ItemTemplate、InsertItemTemplate和EditItemTemplate的FormView了。在源視圖中,刪除InsertItemTemplate和EditItemTemplate,因?yàn)槲覀儸F(xiàn)在對(duì)創(chuàng)建一個(gè)可編輯和可插入的FormView并不感興趣。然后,清空ItemTemplate中的標(biāo)記語言代碼,這樣我才可以工作于一個(gè)干凈的環(huán)境上。
如果你喜歡手工建立ItemTemplate,你可以從工具箱中拖一個(gè)ObjectDataSource到設(shè)計(jì)器中并配置它,這里可不要在設(shè)計(jì)器中為FormView添加數(shù)據(jù)源。我們應(yīng)該到源視圖中手工的將ForView的DataSourceID屬性設(shè)置為ObjectDataSource的ID,然后再手工添加ItemTemplate。不管你決定使用哪種方式,反正最后你的FormView的聲明標(biāo)記代碼應(yīng)該像下面這個(gè)樣子:
<asp:FormView ID="FormView1" runat="server" DataSourceID="ObjectDataSource1"> <ItemTemplate> </ItemTemplate> </asp:FormView>
花點(diǎn)兒時(shí)間到FormView的智能標(biāo)簽中勾上“啟用分頁(yè)(Enable Paging)”復(fù)選框,這樣可以在FormView的聲明標(biāo)記代碼中加上AllowPaging="True"這么一個(gè)屬性(attribute)。另外,把EnableViewState屬性設(shè)置為false。
第二步:定義ItemTemplate的標(biāo)記代碼(MarkUp)
在將FormView綁定到ObjectDataSource控件并且將其配置為支持分頁(yè)之后,我們就準(zhǔn)備指定ItemTemplate的內(nèi)容了。在本教程中,讓我們將產(chǎn)品名稱顯示在一個(gè)<h3>中。跟著讓我們使用<table>將余下的產(chǎn)品屬性顯示在一個(gè)四列的表中,其中第一列和第三列用于顯示產(chǎn)品屬性的名稱,第二列和第四列用于顯示產(chǎn)品屬性的值。
在設(shè)計(jì)器中通過FormView的模板編輯界面或是在源視圖中手工輸入代碼都可以添加上面所說的這些標(biāo)記代碼。使用模板的時(shí)候,我發(fā)現(xiàn)直接在源視圖中編代碼會(huì)來得比較快,不過你可以使用任何一種讓你覺得夠爽的方式。下面的聲明標(biāo)記代碼展示了FormView在完成了ItemTemplate的結(jié)構(gòu)之后所應(yīng)該有的樣子:
<asp:FormView ID="FormView1" runat="server" DataSourceID="ObjectDataSource1"
AllowPaging="True" EnableViewState="False">
<ItemTemplate>
<hr />
<h3><%# Eval("ProductName") %></h3>
<table border="0">
<tr>
<td class="ProductPropertyLabel">Category:</td>
<td class="ProductPropertyValue">
<%# Eval("CategoryName") %></td>
<td class="ProductPropertyLabel">Supplier:</td>
<td class="ProductPropertyValue">
<%# Eval("SupplierName")%></td>
</tr>
<tr>
<td class="ProductPropertyLabel">Price:</td>
<td class="ProductPropertyValue"><%# Eval("UnitPrice",
"{0:C}") %></td>
<td class="ProductPropertyLabel">Units In Stock:</td>
<td class="ProductPropertyValue">
<%# Eval("UnitsInStock")%></td>
</tr>
<tr>
<td class="ProductPropertyLabel">Units On Order:</td>
<td class="ProductPropertyValue">
<%# Eval("UnitsOnOrder") %></td>
<td class="ProductPropertyLabel">Reorder Level:</td>
<td class="ProductPropertyValue">
<%# Eval("ReorderLevel")%></td>
</tr>
<tr>
<td class="ProductPropertyLabel">Qty/Unit</td>
<td class="ProductPropertyValue">
<%# Eval("QuantityPerUnit") %></td>
<td class="ProductPropertyLabel">Discontinued:</td>
<td class="ProductPropertyValue">
<asp:CheckBox runat="server" Enabled="false"
Checked='<%# Eval("Discontinued") %>' />
</td>
</tr>
</table>
<hr />
</ItemTemplate>
</asp:FormView>
注意這個(gè)數(shù)據(jù)綁定語法——以<%# Eval("ProductName") %>為例——可以直接插入到模板的輸出中。那是因?yàn)樗鼪]有必要綁定到一個(gè)Label控件的Text屬性上。舉個(gè)例子,比如我們要將ProductName的值使用<h3><%# Eval("ProductName") %></h3>來顯示在一個(gè)<h3>元素中,那么產(chǎn)品“Chai”將被輸出為<h3>Chai</h3>。
CSS類ProductPropertyLabel和ProductPropertyValue用于指定<table>中的產(chǎn)品屬性的名稱和值的樣式。這些CSS類定義在Styles.css中,它們使產(chǎn)品屬性的名稱粗體顯示并且右對(duì)齊,它們還給產(chǎn)品屬性的值加上一個(gè)右填充。
由于FormView沒有CheckBoxField,要將Discontinued的值顯示為一個(gè)CheckBox的話,我們就必須自己添加一個(gè)CheckBox控件。將這個(gè)CheckBox控件的Enabled屬性設(shè)置為false以使其只讀,并將其Checked屬性綁定到Discontinued字段上去。
完成了ItemTemplate之后,產(chǎn)品信息就以一種更加不規(guī)則的方式來顯示了。來比較一下上一節(jié)中的DetailsView的輸出(圖三)和本節(jié)所討論的FormView的輸出(圖四)。

圖三:生硬的DetailsView輸出

圖四:柔和的FormView輸出
總結(jié)
雖然GridView和DetailsView控件可以使用TemplateField來自定義它們的輸出,不過它們都呈現(xiàn)為一種格子一樣的四四方方的樣子。在那些需要使用一種不規(guī)則的外觀來顯示一個(gè)單獨(dú)的記錄的時(shí)候,F(xiàn)ormView就是一個(gè)理想的選擇。跟DetailsView一樣,F(xiàn)ormView從它的DataSource中顯示一個(gè)單獨(dú)的記錄。不過它也有跟DetailsView不同的地方,它僅由模板組成,而且它根本不支持字段(fields。譯者注:比如說CheckBoxField)。
就像我們?cè)诒竟?jié)中看到的那樣,在顯示一個(gè)單獨(dú)的記錄的時(shí)候,F(xiàn)ormView提供了一種更加復(fù)雜的的呈現(xiàn)方式。在今后的教程中我們將解釋一下DataList和Repeater控件,它們可以提供跟FormView一樣復(fù)雜的呈現(xiàn),不過它們可以顯示多列(就像GridView那樣)。
編程愉快!
關(guān)于作者
Scott Mitchell,著有六本ASP/ASP.NET方面的書,是4GuysFromRolla.com的創(chuàng)始人,自1998年以來一直應(yīng)用微軟Web技術(shù)。Scott是個(gè)獨(dú)立的技術(shù)咨詢顧問,培訓(xùn)師,作家,最近完成了將由Sams出版社出版的新作,24小時(shí)內(nèi)精通ASP.NET 2.0。他的聯(lián)系電郵為mitchell@4guysfromrolla.com,也可以通過他的博客http://ScottOnWriting.NET與他聯(lián)系。
- asp.net GridView 刪除時(shí)彈出確認(rèn)對(duì)話框(包括內(nèi)容提示)
- asp.net操作javascript:confirm返回值的兩種方式
- 在ASP.NET 2.0中操作數(shù)據(jù)之十五:在GridView的頁(yè)腳中顯示統(tǒng)計(jì)信息
- 在ASP.NET 2.0中操作數(shù)據(jù)之十六:概述插入、更新和刪除數(shù)據(jù)
- 在ASP.NET 2.0中操作數(shù)據(jù)之十七:研究插入、更新和刪除的關(guān)聯(lián)事件
- 在ASP.NET 2.0中操作數(shù)據(jù)之十八:在ASP.NET頁(yè)面中處理BLL/DAL層的異常
- 在ASP.NET 2.0中操作數(shù)據(jù)之十九:給編輯和新增界面增加驗(yàn)證控件
- 在ASP.NET 2.0中操作數(shù)據(jù)之二十:定制數(shù)據(jù)修改界面
- 在ASP.NET 2.0中操作數(shù)據(jù)之二十一:實(shí)現(xiàn)開放式并發(fā)
- 在ASP.NET 2.0中操作數(shù)據(jù)之二十二:為刪除數(shù)據(jù)添加客戶端確認(rèn)
相關(guān)文章
Mac中體驗(yàn)ASP.NET 5 beta2的K gen代碼生成
這篇文章主要介紹了Mac中體驗(yàn)ASP.NET 5 beta2的K gen代碼生成,需要的朋友可以參考一下。2016-06-06
在ASP.NET 2.0中操作數(shù)據(jù)之六十五:在TableAdapters中創(chuàng)建新的存儲(chǔ)過程
本文主要講解使用TableAdapter設(shè)置向?qū)ё詣?dòng)創(chuàng)建增刪改查的存儲(chǔ)過程,雖然自動(dòng)創(chuàng)建存儲(chǔ)過程可以節(jié)省時(shí)間,但他們會(huì)包含一些無用的參數(shù),下節(jié)我們會(huì)介紹TableAdapter使用現(xiàn)有的存儲(chǔ)過程。2016-05-05
解讀ASP.NET 5 & MVC6系列教程(11):Routing路由
這篇文章主要介紹了ASP.NET 5 Routing路由的用法,雖然ASP.NET 5 和MVC6的路由使用方式很簡(jiǎn)單,但是相關(guān)的使用規(guī)則卻很復(fù)雜,大家使用的時(shí)候需要多加注意。2016-06-06
在ASP.NET 2.0中操作數(shù)據(jù)之五:聲明參數(shù)
為了使用帶輸入?yún)?shù)的方法,我們需要在ObjectDataSource的SelectParameters集合里指定參數(shù)的值。本文主要介紹使用一個(gè)硬編碼參數(shù)值的方法,和使用設(shè)置Web控件的屬性作為參數(shù)源的方法。2016-04-04
在MacOS+Linux+Nginx中發(fā)布和部署Asp.Net?Core
這篇文章介紹了在MacOS+Linux+Nginx中發(fā)布和部署Asp.Net?Core,對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2021-12-12
在ASP.NET 2.0中操作數(shù)據(jù)之六十六:在TableAdapters中使用現(xiàn)有的存儲(chǔ)過程
雖然通過TableAdapter向?qū)Э梢宰詣?dòng)的生成存儲(chǔ)過程,但是在某些時(shí)候我們需要使用現(xiàn)有的存儲(chǔ)過程。本文將講解如何在Visual Studio環(huán)境里手動(dòng)添加存儲(chǔ)過程,并引導(dǎo)TableAdapter的方法使用這些存儲(chǔ)過程。2016-05-05
解讀ASP.NET 5 & MVC6系列教程(9):日志框架
這篇文章主要介紹了ASP.NET 5 日志框架,通過基于接口的編程機(jī)制和DI依賴注入機(jī)制,我們可以很容易實(shí)現(xiàn)第三方日志provider的擴(kuò)展,從而將日志記錄到我們想記錄的任意地方,需要的朋友可以參考下2016-06-06

