You are on page 1of 10

Thistutorialispartofaset.FindoutmoreaboutdataaccesswithASP.

NETintheWorkingwith
DatainASP.NET2.0sectionoftheASP.NETsiteathttp://www.asp.net/learn/dataaccess/default.aspx.

WorkingwithDatainASP.NET2.0::Using
TemplateFieldsintheDetailsViewControl
Introduction
TheTemplateFieldoffersahigherdegreeofflexibilityinrenderingdatathantheBoundField,CheckBoxField,
HyperLinkField,andotherdatafieldcontrols.Intheprevioustutorial welookedatusingtheTemplateFieldina
GridViewto:
l

Displaymultipledatafieldvaluesinonecolumn.Specifically,boththeFirstName andLastName fields


werecombinedintooneGridViewcolumn.
UseanalternateWebcontroltoexpressadatafieldvalue.WesawhowtoshowtheHiredDate value
usingaCalendarcontrol.
Showstatusinformationbasedontheunderlyingdata.WhiletheEmployees tabledoesnotcontaina
columnthatreturnsthenumberofdaysanemployeehasbeenonthejob,wewereabletodisplaysuch
informationintheGridViewexampleintheprevioustutorialwiththeuseofaTemplateFieldand
formattingmethod.

ThesameTemplateFieldscapabilitiesavailablewiththeGridViewarealsoavailablewiththeDetailsView
control.Inthistutorialwe'lldisplayoneproductatatimeusingaDetailsViewthatcontainstwo
TemplateFields.ThefirstTemplateFieldwillcombinetheUnitPrice,UnitsInStock,andUnitsOnOrder data
fieldsintooneDetailsViewrow.ThesecondTemplateFieldwilldisplaythevalueoftheDiscontinued field,
butwilluseaformattingmethodtodisplay"YES"ifDiscontinued is true,and"NO"otherwise.

Figure1:TwoTemplateFieldsareUsedtoCustomizetheDisplay
Let'sgetstarted!

1 of10

Step1:BindingtheDatatotheDetailsView
Asdiscussedintheprevioustutorial,whenworkingwithTemplateFieldsit'softeneasiesttostartbycreating
theDetailsViewcontrolthatcontainsjustBoundFieldsandthenaddnewTemplateFieldsorconverttheexisting
BoundFieldstoTemplateFieldsasneeded.Therefore,startthistutorialbyaddingaDetailsViewtothepage
throughtheDesignerandbindingittoanObjectDataSourcethatreturnsthelistofproducts.Thesestepswill
createaDetailsViewwithBoundFieldsforeachoftheproduct'snonBooleanvaluefieldsandaCheckBoxField
fortheoneBooleanvaluefield(Discontinued).
OpentheDetailsViewTemplateField.aspx pageanddragaDetailsViewfromtheToolboxontothe
Designer.FromtheDetailsView'ssmarttagchoosetoaddanewObjectDataSourcecontrolthatinvokesthe
ProductsBLL class's GetProducts() method.

Figure2:AddaNewObjectDataSourceControlthatInvokestheGetProducts() Method
ForthisreportremovetheProductID,SupplierID,CategoryID,andReorderLevel BoundFields.Next,
reordertheBoundFieldssothattheCategoryName andSupplierName BoundFieldsappearimmediatelyafter
theProductName BoundField.FeelfreetoadjusttheHeaderText propertiesandformattingpropertiesforthe
BoundFieldsasyouseefit.LikewiththeGridView,theseBoundFieldleveleditscanbeperformedthroughthe
Fieldsdialogbox(accessiblebyclickingontheEditFieldslinkintheDetailsView'ssmarttag)orthroughthe
declarativesyntax.Lastly,clearouttheDetailsView'sHeight andWidth propertyvaluesinordertoallowthe
DetailsViewcontroltoexpandbasedonthedatadisplayedandchecktheEnablePagingcheckboxinthesmart
tag.
Aftermakingthesechanges,yourDetailsViewcontrol'sdeclarativemarkupshouldlooksimilartothe
following:
<asp:DetailsViewID="DetailsView1"runat="server"AutoGenerateRows="False"
DataKeyNames="ProductID"DataSourceID="ObjectDataSource1"AllowPaging="True"
EnableViewState="False">
<Fields>

2 of10

<asp:BoundFieldDataField="ProductName"HeaderText="Product"
SortExpression="ProductName"/>
<asp:BoundFieldDataField="CategoryName"HeaderText="Category"
ReadOnly="True"SortExpression="CategoryName"/>
<asp:BoundFieldDataField="SupplierName"HeaderText="Supplier"
ReadOnly="True"SortExpression="SupplierName"/>
<asp:BoundFieldDataField="QuantityPerUnit"
HeaderText="Qty/Unit"SortExpression="QuantityPerUnit"/>
<asp:BoundFieldDataField="UnitPrice"HeaderText="Price"
SortExpression="UnitPrice"/>
<asp:BoundFieldDataField="UnitsInStock"
HeaderText="UnitsInStock"SortExpression="UnitsInStock"/>
<asp:BoundFieldDataField="UnitsOnOrder"
HeaderText="UnitsOnOrder"SortExpression="UnitsOnOrder"/>
<asp:CheckBoxFieldDataField="Discontinued"
HeaderText="Discontinued"SortExpression="Discontinued"/>
</Fields>
</asp:DetailsView>

Takeamomenttoviewthepagethroughabrowser.Atthispointyoushouldseeasingleproductlisted(Chai)
withrowsshowingtheproduct'sname,category,supplier,price,unitsinstock,unitsonorder,andits
discontinuedstatus.

Figure3:TheProduct'sDetailsAreShownUsingaSeriesofBoundFields

Step2:CombiningthePrice,UnitsInStock,and
UnitsOnOrderIntoOneRow
TheDetailsViewhasarowfortheUnitPrice,UnitsInStock,andUnitsOnOrder fields.Wecancombine

3 of10

thesedatafieldsintoasinglerowwithaTemplateFieldeitherbyaddinganewTemplateFieldorbyconverting
oneoftheexistingUnitPrice,UnitsInStock,andUnitsOnOrder BoundFieldsintoaTemplateField.WhileI
personallypreferconvertingexistingBoundFields,let'spracticebyaddinganewTemplateField.
StartbyclickingontheEditFieldslinkintheDetailsView'ssmarttagtobringuptheFieldsdialogbox.Next,
addanewTemplateFieldandsetitsHeaderText propertyto"PriceandInventory"andmovethenew
TemplateFieldsothatitispositionedabovetheUnitPrice BoundField.

Figure4:AddaNewTemplateFieldtotheDetailsViewControl
SincethisnewTemplateFieldwillcontainthevaluescurrentlydisplayedintheUnitPrice,UnitsInStock,and
UnitsOnOrder BoundFields,let'sremovethem.
ThelasttaskforthisstepistodefinetheItemTemplate markupforthePriceandInventoryTemplateField,
whichcanbeaccomplishedeitherthroughtheDetailsView'stemplateeditinginterfaceintheDesignerorby
handthroughthecontrol'sdeclarativesyntax.AswiththeGridView,theDetailsView'stemplateediting
interfacecanbeaccessedbyclickingontheEditTemplateslinkinthesmarttag.Fromhereyoucanselectthe
templatetoeditfromthedropdownlistandthenaddanyWebcontrolsfromtheToolbox.
Forthistutorial,startbyaddingaLabelcontroltothePriceandInventoryTemplateField'sItemTemplate.
Next,clickontheEditDataBindingslinkfromtheLabelWebcontrol'ssmarttagandbindtheText propertyto
theUnitPrice field.

4 of10

Figure5:BindtheLabel'sText PropertytotheUnitPrice DataField

FormattingthePriceasaCurrency
Withthisaddition,theLabelWebcontrolPriceandInventoryTemplateFieldwillnowdisplayjustthepricefor
theselectedproduct.Figure6showsascreenshotofourprogressthusfarwhenviewedthroughabrowser.

Figure6:ThePriceandInventoryTemplateFieldShowsthePrice
Notethattheproduct'spriceisnotformattedasacurrency.WithaBoundField,formattingispossiblebysetting
theHtmlEncode propertytofalse andtheDataFormatString propertyto{0:formatSpecifier}.Fora
TemplateField,however,anyformattinginstructionsmustbespecifiedinthedatabindingsyntaxorthroughthe
useofaformattingmethoddefinedsomewherewithintheapplication'scode(suchasintheASP.NETpage's

5 of10

codebehindclass).
TospecifytheformattingforthedatabindingsyntaxusedintheLabelWebcontrol,returntotheDataBindings
dialogboxbyclickingontheEditDataBindingslinkfromtheLabel'ssmarttag.Youcantypetheformatting
instructionsdirectlyintheFormatdropdownlistorselectoneofthedefinedformatstrings.Likewiththe
BoundField'sDataFormatString property,theformattingisspecifiedusing{0:formatSpecifier}.
FortheUnitPrice fieldusethecurrencyformattingspecifiedeitherbyselectingtheappropriatedropdownlist
valueorbytypingin{0:C} byhand.

Figure7:FormatthePriceasaCurrency
Declaratively,theformattingspecificationisindicatedasasecondparameterintotheBind orEval methods.
ThesettingsjustmadethroughtheDesignerresultinthefollowingdatabindingexpressioninthedeclarative
markup:
<asp:LabelID="Label1"runat="server"Text='<%#Eval("UnitPrice","{0:C}")%>'/>

AddingtheRemainingDataFieldstothe
TemplateField
Atthispointwe'vedisplayedandformattedtheUnitPrice datafieldinthePriceandInventoryTemplateField,
butstillneedtodisplaytheUnitsInStock andUnitsOnOrder fields.Let'sdisplaytheseonalinebelowthe
priceandinparentheses.FromthetemplateeditinginterfaceintheDesigner,suchmarkupcanbeaddedby
positioningyourcursorwithinthetemplateandsimplytypinginthetexttobedisplayed.Alternatively,this
markupcanbeentereddirectlyinthedeclarativesyntax.
Addthestaticmarkup,LabelWebcontrols,anddatabindingsyntaxsothatthePriceandInventory
TemplateFielddisplaysthepriceandinventoryinformationlikeso:
UnitPrice

6 of10

(InStock/OnOrder: UnitsInStock/UnitsOnOrder)
AfterperformingthistaskyourDetailsView'sdeclarativemarkupshouldlooksimilartothefollowing:
<asp:DetailsViewID="DetailsView1"runat="server"AutoGenerateRows="False"
DataKeyNames="ProductID"DataSourceID="ObjectDataSource1"AllowPaging="True"
EnableViewState="False">
<Fields>
<asp:BoundFieldDataField="ProductName"
HeaderText="Product"SortExpression="ProductName"/>
<asp:BoundFieldDataField="CategoryName"HeaderText="Category"
ReadOnly="True"SortExpression="CategoryName"/>
<asp:BoundFieldDataField="SupplierName"
HeaderText="Supplier"ReadOnly="True"
SortExpression="SupplierName"/>
<asp:BoundFieldDataField="QuantityPerUnit"
HeaderText="Qty/Unit"SortExpression="QuantityPerUnit"/>
<asp:TemplateFieldHeaderText="PriceandInventory">
<ItemTemplate>
<asp:LabelID="Label1"runat="server"
Text='<%#Eval("UnitPrice","{0:C}")%>'></asp:Label>
<br/>
<strong>
(InStock/OnOrder:</strong>
<asp:LabelID="Label2"runat="server"
Text='<%#Eval("UnitsInStock")%>'></asp:Label>
<strong>/</strong>
<asp:LabelID="Label3"runat="server"
Text='<%#Eval("UnitsOnOrder")%>'>
</asp:Label><strong>)</strong>
</ItemTemplate>
</asp:TemplateField>
<asp:CheckBoxFieldDataField="Discontinued"
HeaderText="Discontinued"SortExpression="Discontinued"/>
</Fields>
</asp:DetailsView>

Withthesechangeswe'veconsolidatedthepriceandinventoryinformationintoasingleDetailsViewrow.

Figure8:ThePriceandInventoryInformationisDisplayedinaSingleRow

7 of10

Step3:CustomizingtheDiscontinuedField
Information
TheProducts table'sDiscontinued columnisabitvaluethatindicateswhethertheproducthasbeen
discontinued.WhenbindingaDetailsView(orGridView)toadatasourcecontrol,theBooleanvaluefields,
likeDiscontinued,areimplementedasCheckBoxFieldswhereasnonBooleanvaluefields,likeProductID,
ProductName,andsoon,areimplementedasBoundFields.TheCheckBoxFieldrendersasadisabledcheckbox
thatischeckedifthedatafield'svalueisTrueanduncheckedotherwise.
RatherthandisplaytheCheckBoxFieldwemaywanttoinsteaddisplaytextindicatingwhetherornotthe
productisdiscontinued.ToaccomplishthiswecouldremovetheCheckBoxFieldfromtheDetailsViewand
thenaddaBoundFieldwhoseDataField propertywassettoDiscontinued.Takeamomenttodothis.After
thischangetheDetailsViewshowsthetext"True"fordiscontinuedproductsand"False"forproductsthatare
stillactive.

Figure9:TheStringsTrueandFalseAreUsedtoDisplaytheDiscontinuedState
Imaginethatwedidn'twantthestrings"True"or"False"tobeused,but"YES"and"NO",instead.Such
customizationcanbeperformedwiththeaidofaTemplateFieldandaformattingmethod.Aformattingmethod
cantakeinanynumberofinputparameters,butmustreturntheHTML(asastring)toinjectintothetemplate.
AddaformattingmethodtotheDetailsViewTemplateField.aspx page'scodebehindclassnamed
DisplayDiscontinuedAsYESorNO thatacceptsaBooleanasaninputparameterandreturnsastring.As
discussedintheprevioustutorial,thismethodmust bemarkedas protected orpublic inordertobe
accessiblefromthetemplate.
protectedstringDisplayDiscontinuedAsYESorNO(booldiscontinued)
{
if(discontinued)
return"YES"
else
return"NO"
}

8 of10

Thismethodcheckstheinputparameter(discontinued)andreturns"YES"ifitistrue,"NO"otherwise.
Note:Intheformattingmethodexaminedintheprevioustutorialrecallthatwewerepassinginadatafieldthat
mightcontainNULLsandthereforeneededtocheckiftheemployee'sHiredDate propertyvaluehadadatabase
NULL valuebeforeaccessingtheEmployeesRow'sHiredDate property.Suchacheckisnotneededheresince
theDiscontinued columncanneverhavedatabaseNULL valuesassigned.Moreover,thisiswhythemethod
canacceptaBooleaninputparameterratherthanhavingtoacceptaProductsRow instanceoraparameterof
typeobject.
Withthisformattingmethodcomplete,allthatremainsistocallitfromtheTemplateField's ItemTemplate.To
createtheTemplateFieldeitherremovetheDiscontinued BoundFieldandaddanewTemplateFieldorconvert
theDiscontinued BoundFieldintoaTemplateField.Then,fromthedeclarativemarkupview,editthe
TemplateFieldsothatitcontainsjustanItemTemplatethatinvokestheDisplayDiscontinuedAsYESorNO
method,passinginthevalueofthecurrentProductRow instance's Discontinued property.Thiscanbe
accessedviatheEval method.Specifically,theTemplateField'smarkupshouldlooklike:
<asp:TemplateFieldHeaderText="Discontinued"SortExpression="Discontinued">
<ItemTemplate>
<%#DisplayDiscontinuedAsYESorNO((bool)
Eval("Discontinued"))%>
</ItemTemplate>
</asp:TemplateField>

ThiswillcausetheDisplayDiscontinuedAsYESorNO methodtobeinvokedwhenrenderingtheDetailsView,
passingintheProductRow instance'sDiscontinued value.SincetheEval methodreturnsavalueoftype
object,buttheDisplayDiscontinuedAsYESorNO methodexpectsaninputparameteroftype bool,wecast
theEval methodsreturnvaluetobool.TheDisplayDiscontinuedAsYESorNO methodwillthenreturn"YES"
or"NO"dependingonthevalueitreceives.ThereturnedvalueiswhatisdisplayedinthisDetailsViewrow
(seeFigure10).

Figure10:YESorNOValuesareNowShownintheDiscontinuedRow

Summary
9 of10

TheTemplateFieldintheDetailsViewcontrolallowsforahigherdegreeofflexibilityindisplayingdatathanis
availablewiththeotherfieldcontrolsandareidealforsituationswhere:
l
l
l

MultipledatafieldsneedtobedisplayedinoneGridViewcolumn
ThedataisbestexpressedusingaWebcontrolratherthanplaintext
Theoutputdependsontheunderlyingdata,suchasdisplayingmetadataorinreformattingthedata

WhileTemplateFieldsallowforagreaterdegreeofflexibilityintherenderingoftheDetailsView'sunderlying
data,theDetailsViewoutputstillfeelsabitboxyaseachfieldisrenderedasarowinanHTML<table>.
TheFormViewcontroloffersagreaterdegreeofflexibilityinconfiguringtherenderedoutput.TheFormView
doesnotcontainfieldsbutratherjustaseriesoftemplates(ItemTemplate,EditItemTemplate,
HeaderTemplate,andsoon).We'llseehowtousetheFormViewtoachieveevenmorecontroloftherendered
layoutinournexttutorial.
HappyProgramming!

AbouttheAuthor
ScottMitchell,authorofsixASP/ASP.NETbooksandfounderof4GuysFromRolla.com,hasbeenworking
withMicrosoftWebtechnologiessince1998.Scottworksasanindependentconsultant,trainer,andwriter,
recentlycompletinghislatestbook, SamsTeachYourselfASP.NET2.0in24Hours.Hecanbereachedat
mitchell@4guysfromrolla.comorviahisblog,whichcanbefoundathttp://ScottOnWriting.NET.

SpecialThanksTo
Thistutorialserieswasreviewedbymanyhelpfulreviewers.LeadreviewerforthistutorialwasDanJagers.
InterestedinreviewingmyupcomingMSDNarticles?Ifso,dropmealineat mitchell@4GuysFromRolla.com.

10 of10

You might also like