By Michael A. Kittel, Geoffrey T. LeBlond
Cover | Table of Contents | Colophon
DataGrid control in mere
minutes using relatively few lines of code. Alternatively, if
you're more inclined to control nearly every aspect
of the tabular display, you can shape and mold the template-driven
Repeater and DataList controls
nearly beyond recognition, and still not step very far outside a
well-trodden path. But like everything else in ASP.NET, you have to
know where to start and what the trade-offs are. For instance,
it's helpful to know how and when the
DataGrid control begins to fall short of the mark.
That knowledge will save you having to retrace your steps later to
implement another tabular control altogether, something
we've had to do ourselves at an inopportune moment
during a hot project. The recipes in this chapter ought to get you
well down the curve with displaying your tabular data and prevent you
having to revisit some of our same mistakes.Repeater, DataList, or
DataGrid control. Always
choose
the smallest and fastest control that meets your needs, which
invariably will be influenced by other criteria. For example:DataGrid.Repeater.DataGrid control in mere
minutes using relatively few lines of code. Alternatively, if
you're more inclined to control nearly every aspect
of the tabular display, you can shape and mold the template-driven
Repeater and DataList controls
nearly beyond recognition, and still not step very far outside a
well-trodden path. But like everything else in ASP.NET, you have to
know where to start and what the trade-offs are. For instance,
it's helpful to know how and when the
DataGrid control begins to fall short of the mark.
That knowledge will save you having to retrace your steps later to
implement another tabular control altogether, something
we've had to do ourselves at an inopportune moment
during a hot project. The recipes in this chapter ought to get you
well down the curve with displaying your tabular data and prevent you
having to revisit some of our same mistakes.Repeater, DataList, or
DataGrid control. Always
choose
the smallest and fastest control that meets your needs, which
invariably will be influenced by other criteria. For example:DataGrid.Repeater.Repeater (lightest) or
DataList (lighter).Repeater or DataList.DataList or a DataGrid.DataGrid.Repeater, DataList,
and DataGrid—but each comes with trade-offs.
For instance, the DataGrid control is particularly
versatile, but you can pay a heavy price in terms of performance. On
the flip side, the Repeater control is lighter
weight, but is for read-only display; if you later decide you need to
edit your data, you must rework your code to use the
DataGrid control and bind the data to it.DataGridcontrol responsible for displaying the
data.DataGrid control and
bind it.DataGrid in a browser. Example 1-1 through Example 1-3 show the
.aspx and VB and C# code-behind files for the
application that produces this result.
DataGrid requires very
little coding. You must first add a DataGrid tag
to the .aspx file for your application and set a
few of its attributes, as shown in Example 1-1. The
DataGrid tag has many attributes you can use to
control the creation of a DataGrid object, but
only three are required: the id,
runat, and AutoGenerateColumns
attributes. The id and runat
attributes are required by all server controls. When the
AutoGenerateColumns attribute is set to
True, it causes the DataGrid to
automatically create the required columns along with their headings
from the data source.DataGrid goes into the code-behind class
associated with the .aspx file, as shown in
Example 1-2 (VB) and Example 1-3
(C#). In our example, this code is placed in the
DataGrid
control's default tabular display. Selecting and
editing the data are not important, nor is navigating through the
data.Repeater control with
templates and then bind the data
to the control.Repeater control and the associated templates for
displaying the data.OleDbCommand and
OleDbDataReader.Repeater control and
bind it.Repeater in a browser. Example 1-4 through Example 1-6 show the
.aspx and code-behind files for an application
that produces this result.
DataGrid
control's default tabular display, the
Repeater control is a good choice because, unlike
a DataGrid, it has associated templates that allow
you to use virtually any HTML to format the displayed data. It also
has the advantage of being relatively lightweight and easy to use.
When using Repeater, however, there are a handful
of nuances you should know about that can make life easier and, in
one instance, enhance performance.DataGrid control and
the
ReadXml method of the DataSet
class.DataGridcontrol for displaying the data.ReadXml
method of the DataSet class.DataSet to the
DataGrid control.DataGrid in a browser. Example 1-7 shows the XML used for the recipe. Examples
Example 1-8 through Example 1-10
show the .aspx and code-behind files for an
application that produces this result.
Page_Load method
in
the code-behind, shown in Example 1-9 (VB) and Example 1-10 (C#), reads the data from the XML file using
the ReadXml method of the
DataSet class, binds the
DataSet to the DataGrid
control, and then performs the necessary cleanup.DataSet will automatically load the XML data into
a table named Book. When binding the data to the
DataGrid, you must reference the desired table if
the DataSet contains more than one table. It is
always best to reference the table by name instead of by index
because the index value can change if the structure of the data
changes.DataGridCheckBoxList control and bind the array to
it.CheckBoxList control to the
.aspx file.CheckBoxList control.CheckBoxList in a browser, with a couple of
checkboxes preselected. Example 1-11 through
Example 1-13 show the .aspx and
code-behind files for an application that produces this result.
CheckBoxList control makes the job of
generating a list of checkboxes extremely easy.
Here's a rundown of some of the attributes that
control the checkbox display. In the example that we developed for
this recipe, we have placed a CheckBoxList control
in a Table cell to control its position on the form, as shown in
Example 1-11.RepeatColumns attribute of the
CheckBoxList control is used to set the number of
columns in which the checkboxes are to be displayed.RepeatDirection attribute is set to
Horizontal, which displays the checkboxes in rows
from left-to-right and then top-to-bottom. This attribute can also be
set to Vertical to display the checkboxes in
columns from top-to-bottom and then left-to-right.RepeatLayout attribute is set to
Table, which causes the
CheckBoxList control to output an HTML table that
contains the checkboxes. Using Table ensures the
checkboxes are aligned vertically. This attribute can also be set to
Flow, which causes the
CheckBoxList control to output a
<span> element for the checkboxes with
<br> elements, thus placing the checkboxes
in rows. In this case, unless all of your data is the same size, the
checkboxes will not be aligned vertically.Hashtable, a class that
provides
the ability to store a collection of key/value pairs, and you want to
display the data in a columnar table.DataList control
and bind the
Hashtable to it.DataList control to the
.aspx file, being careful to place it in a Table
cell in order to control its position on the form.Hashtable as the data source for the
DataList control.Hashtable to the
DataList control.DataList within a browser that has been bound to a
Hashtable filled with, in our case, book data.
Example 1-14 through Example 1-16 show the .aspx and
code-behind files for an application that produces this result.
DataList control can display almost any type
of data in a variety of ways using its available templates and
styles. Templates are available for the header, footer, items,
alternating items, separators, selected items, and edit items to
define and organize the data to output. Styles are available for each
of the templates to define how the content appears.asp:DataList tag is placed in
a Table cell to control its position on the form, as shown in Example 1-14. The RepeatColumns
attribute of the control defines the number of columns that should be
output, which in this case is 4. The
RepeatDirection attribute indicates that the data
should be output horizontally, which displays the data in rows from
left-to-right and then top-to-bottom. The
DataGrid control, enable its built-in
pagination features, and then bind the data to it.DataGrid control to the
.aspx file, and use its
AllowPaging and other related attributes to enable
pagination.DataSet to the
DataGrid in the usual fashion.PageIndexChanged
event for the DataGrid—and rebinds the data.DataGrid within a browser with next/previous
navigation. Example 1-17 through Example 1-19 show the .aspx and
code-behind files for an application that produces this result.
DataGrid control includes the ability to
perform pagination of the data that is displayed in the grid, and
using the built-in pagination requires very little code. Pagination
is enabled and configured by the attributes of the
DataGrid element:AllowPaging="True" PageSize="5" PagerStyle-Mode="NextPrev" PagerStyle-Position="Bottom" PagerStyle-HorizontalAlign="Center" PagerStyle-NextPageText="Next" PagerStyle-PrevPageText="Prev">
AllowPaging attribute to
True enables paging for the
DataGrid, and the PageSize
attribute defines the number of rows that will be displayed in a
single page. Setting the PageStyle-ModeDataGrid control, add first/last and
next/previous buttons (with event handlers for each one), and then
bind the data to it.DataGrid control to the
.aspx file.DataGrid with first/last and
next/previous buttons for navigation.DataGrid in the usual fashion.DataGrid within a browser with first/last and
next/previous buttons for navigation. Example 1-20 through Example 1-22 show the
.aspx and code-behind files for an application
that produces this result.
DataGrid control's default
pagination controls and, at the same time, handle the custom paging.
Setting the PagerStyle-Visible attribute to
False makes the pager invisible in a
DataGrid control, allowing you to implement your
own user interface for the pagination controls. (The
pager is the element on the
DataGridDataGrid control
and its PagerStyle-Mode and
PagerStyle-PageButton attributes to enable page
selection. This approach produces output like that shown in Figure 1-9. To create an application that employs this
approach, start by implementing Recipe 1.7 with the changes to the
DataGrid tag shown here:PagerStyle-Mode="NumericPages" PagerStyle-PageButtonCount="5"
DataGrid control and implement your own user
interface for the pagination controls. This approach allows the user
to, for example, input a page number in a text box and then click a
button to display the data, as shown in Figure 1-10.
Example 1-23 through Example 1-25 show the .aspx and
code-behind files for an application that produces this result.
PagerStyle-Mode attribute to
NumericPages causes the
DataGrid to be rendered with page number buttons
for navigating through the grid. The
PagerStyle-ButtonCount attribute defines the
number of "page buttons" that are
output. If more pages are available than can be displayed, an
ellipsis (...) is displayed at the end(s) of the page buttons
containing additional pages. As shown in Figure 1-9, additional pages of data are available beyond
page 5. Clicking on the ellipsis will update the data in the
DataGrid, yet the user must be able to page
through it quickly. This approach is beneficial anytime you have to
navigate through thousands of records.DataGrid and, using a
stored procedure, read from the database only the data that is needed
for a given page. An example of the output that can be achieved with
this approach is shown in Figure 1-11. Examples
Example 1-27 through Example 1-29
show the .aspx and code-behind files for an
application that illustrates this approach; the application uses the
stored procedure shown in Example 1-26 to retrieve
the data to display.
DataGrid's
AllowPaging and
AllowCustomPaging attributes
must be set to
True. When AllowCustomPaging is
set to False (the default), the
DataGrid assumes that all of the data that can be
displayed in all pages is present in the data source, and it
calculates the group of records to display from the
CurrentPageIndex and PageSize
attributes. When AllowCustomPaging is set to
True, the DataGrid expects only
one page (as defined by the PageSize attribute) to
be present in the data source and you are responsible for filling the
data source with the proper page of data.<asp:DataGrid
id="dgBooks"
runat="server"
BorderColor="000080"
BorderWidth="2px"
AutoGenerateColumns="False"
width="100%"
AllowPaging="True"
DataGrid by clicking on its column headers.DataGrid control's
sorting features, and create a routine that binds the appropriate
data to the control when it is initially displayed and whenever the
user clicks a column header.DataGrid control's sorting
features.bindData in our
example) that performs the actual sorting based on the value of a
sortExpression parameter and binds a dataset to
the DataGrid (this parameter is used in the
ORDER BY clause of the SQL statement).Page_Load
method (to support the initial display of the grid) and from the
event that is fired when the user clicks on a column header (the
dgBooks_SortCommand event in our example).DataGrid sorted by title, the information in the
first column. Example 1-30 through Example 1-32 show the .aspx and
code-behind files for an example application that produces this
result.
DataGrid control provides the basic plumbing
required to support sorting. It will generate the links for the
column headers that will raise the SortCommand
server-side event when a column header is clicked. The
DataGrid does not provide the code required to
perform the actual sorting, but very little code is required to
complete that job.AllowSorting attribute of
the
DataGrid, and you want to let the user sort
the data and change the sort order by clicking on the column headers.DataGrid
control and add custom coding to support the sorting along
with an indication of the current sort column and order. An example
of the output that is possible with this approach is shown in Figure 1-15. Example 1-33 through
Example 1-35 show the .aspx file
and code-behind files for an application that produces this output.
DataGrid control, you must
first enable its sorting features by setting the
AllowSorting attribute of the
DataGrid element to True. In
addition, set the SortExpression attribute of the
asp:BoundColumn element to the expression that
will be used in your code to perform the sorting. See Recipe 1.11 for details on these steps.HeadingText attribute in the
asp:BoundColumn element. You will want to set the
heading text in the code-behind, so it is not needed in the
.aspx file.enuSortOrder enumeration defines the available
sort orders that are used to store and compare sort order data. The
DataGrid with both
sorting and pagination, and you are having trouble making the two
features work together.DataGrid
control, and add custom code to support the sorting along with an
indication of the current sort column and order (see Recipe 1.12 for details). Next, with pagination
enabled, add a small amount of custom code to track the sort column
and sort order so that they can be maintained between client round
trips and used any time rebinding is required. Figure 1-16 shows a typical DataGrid
with this solution implemented. Example 1-36
through Example 1-38 show the
.aspx file and code-behind files for an
application that produces this output.
DataGrid. The key to
making it all work is to track the sort column and sort order so that
they can be used any time rebinding is required, whether because of a
page change or a sort command. Likewise, it is useful to put the sort
column and sort order data in the view state so that they are
properly maintained between client round trips.DataGrid provides the basic plumbing for
sorting and paging the data displayed in the grid. The
DataGrid also provides a property
(CurrentPageIndex) that is always available to
indicate which page is to be displayed. Unfortunately, the
DataGrid provides no information regarding the
sort column or the sort order, forcing you, as a programmer, to track
this information outside of the DataGrid so it
will be available when performing pagination operations.DataGrid.EditCommandColumn column type
to
the
DataGrid control's display to
enable editing of the data fields of each record. A typical example
of normal display mode output is shown in Figure 1-17, and an example of edit mode output is shown
in Figure 1-18. Example 1-39 through Example 1-41 show the
.aspx and code-behind files for the application
that produces this result.
DataGrid control, in particular the
EditCommandColumn column type, which provides Edit
command buttons for editing data items in each row of a
DataGrid. The EditText,
CancelText, and UpdateText
properties define the text to be output for the Edit command
button's Edit, Cancel, and Update hyperlinks,
respectively.<asp:EditCommandColumn ButtonType="LinkButton" EditText="Edit" CancelText="Cancel" UpdateText="Update" />
ButtonType attribute defines the type of
button to output. You can specify LinkButton,
which provides hyperlinked text, or PushButton,
which outputs an HTML button.EditText, CancelText, and
UpdateText properties can also be set to HTML. For
example, to output an image for the links, you can use
<img src="images/buttons/editButton.gif"
border="0">.DataGrid controls.DataFormatString attribute
of the
asp:BoundColumn tag.DataGrid control, add a
BoundColumn tag with the appropriate
DataFormatString attribute for each column you
want to format.DataFormatString does not provide the
flexibility you need to format your data, use the
ItemDataBound event instead to gain greater
flexibility.DataGrid with the Publish Date and List Price
columns formatted for dates and currency, respectively. Examples
Example 1-42 through Example 1-44
show the .aspx and code-behind files for an
application that produces this result.
DataGrid
is performed with the DataFormatString attribute
of the asp:BoundColumn element. The general format
of the formatting string is
{
A:B
},
where A is the zero-based index number of
the property the format applies to (this is generally
0) and B specifies the
format.|
Format character
|
|
|---|
DataGrid that
requires selection of a row, but you do
not want to have a Select button in every row of your
DataGrid. What you really want is to allow the
user to click anywhere within a row, like in a classic Windows
application.DataGrid add a hidden Select
button along with an onclick event that performs
the same action as if the hidden Select button were clicked.ButtonColumn to the
DataGrid.ButtonType attribute to
"LinkButton" so that a hidden
hyperlinked Select button is rendered in every row.ItemDataBound event, add an
onclick event to the DataGrid
row that performs the same action as clicking the hidden Select
button.
DataGrid in the usual fashion but add a
hidden ButtonColumn. The
ButtonType attribute is set to
"LinkButton", and the
CommandName attribute is set to
"Select". This causes the
DataGrid to be rendered with a hidden hyperlinked
Select button in every row.<Columns> <asp:ButtonColumn ButtonType="LinkButton" Visible="False" CommandName="Select" /> ... </Columns>
DataGrid
control's ItemDataBound event
handler (dgProblems_ItemDataBound) is used to
expand the functionality of the hidden Select button to encompass the
entire row. This method is called for every row of the
DataGrid row a
confirmation pop
up that appears whenever a user tries to delete a row in the
DataGrid.DataGrid
and a Delete button below the DataGrid. Whenever
the Delete button is clicked, execute some client-side script that
displays the confirmation pop up, followed by some server-side code
that performs the actual deletion.DataGrid to
display a Select button.DataGrid.DataGrid with
this solution implemented. Example 1-48
through Example 1-50 show the
.aspx and code-behind files for the application
that produces this result.
DataGrid in the same way
you have done so throughout this chapter, except that you add a
button column to allow for row selection. Setting the
ButtonType to "LinkButton"
outputs a hyperlink for selecting the row. (The
ButtonType can instead be set to
"PushButton" to output an HTML button.) The
CommandName defines the action to be taken when
the button is clicked, and the DataGrid using a pop-up window.Datagrid.
When the user clicks the button, open a new browser window, obtain
the information from the server, and then display the detailed
information in a pop-up window. An example of the output that is
possible with this approach is shown in Figure 1-22
(sample DataGrid) and Figure 1-23
(sample pop-up window output). As with the other recipes in this
book, we've implemented a complete application that
illustrates this approach. The form and code-behind for the page
containing the sample DataGrid is shown in
Example 1-51 through Example 1-53, and the form and code-behind for the sample
pop-up window is shown in Example 1-54
through Example 1-56.
DataGrid in
the normal fashion, but add a link button column to display a Details
link. The idea is that when the user clicks the Details link within a
row of the DataGrid, the browser opens a new
window and requests the appropriate page from the server. In the
context of our example that implements this solution, a book details
page is requested. From here on, the recipe's
remaining steps are described in the context of our example because
we use techniques that you are likely to find helpful in implementing
your own application.DataGrid containing numeric
information and you need to display a
total of the data in the last row of the grid.DataGrid,
accumulate the total for the data in the
ItemDataBound event handler, and then output the
total in the DataGrid footer.ShowFooter attribute of the
asp:DataGrid element to True.DataGrid in the normal fashion.ItemDataBound event handler, add the values
for each data row to the accumulated totals.ItemDataBound event handler, set the total
values in the footer when the footer is data bound.
DataGrid is by example. In this recipe,
you'll want to create the
DataGrid a little differently than normal. In the
asp:DataGrid element, set the
ShowFooter attribute to True to
cause a footer to be output when the control is rendered. You then
place the totals data in the footer.<asp:DataGrid id="dgBooks" runat="server" BorderColor="000080" BorderWidth="2px" AutoGenerateColumns="False" width="100%" ShowFooter="True">
FooterStyle element to format all of
the columns in the footer with a stylesheet class, background color,
and horizontal alignment:MinimumValue or MaximumValue,
which specify the minimum and maximum values of a validation range).
ASP.NET does all the rest. You can also combine validators to provide
multiple validations on a single input, such as a
RequiredFieldValidator and a
RangeValidator, which perform as their names
imply.postback in server code. However, if the user has
a browser that supports DHTML and client-side validation is enabled,
validators can also perform their validation using client script.
Client-side validation is handy whenever you want to avoid a round
trip to the server for server-side validation, such as when you want
to make sure an entry is provided in a text box. Regardless of
whether client-side validation is performed, server-side validation
is always a good idea, if only to ensure that validation always takes
place, even when the user's browser
doesn't support DHTML.MinimumValue or MaximumValue,
which specify the minimum and maximum values of a validation range).
ASP.NET does all the rest. You can also combine validators to provide
multiple validations on a single input, such as a
RequiredFieldValidator and a
RangeValidator, which perform as their names
imply.postback in server code. However, if the user has
a browser that supports DHTML and client-side validation is enabled,
validators can also perform their validation using client script.
Client-side validation is handy whenever you want to avoid a round
trip to the server for server-side validation, such as when you want
to make sure an entry is provided in a text box. Regardless of
whether client-side validation is performed, server-side validation
is always a good idea, if only to ensure that validation always takes
place, even when the user's browser
doesn't support DHTML.RequiredFieldValidator control to the
.aspx file,
and
use the event handler of the control that completes the
user's entry for the page to verify that validation
was successful.RequiredFieldValidator control for each text
box in which data must be entered.CausesValidation attribute to
True to have validation performed when the button
is clicked (set it to False for the Cancel
button).Page.IsValid property
and verifies that all validation was successful.