Session 1 - UW Faculty Web Server

Download Report

Transcript Session 1 - UW Faculty Web Server

Advanced Web Development using C#
Session 1
Last Update: 1/12
David Figge
[email protected]
Page 1
Copyright (C) 2012 by David Figge. All Rights Reserved.
Welcome
Advanced Web Development using C#
Last Update: 1/12
Page 2
Copyright (C) 2012 by David Figge. All Rights Reserved.
Advanced Web Development using C#

This is the 2nd in a 3 part series designed
to introduce you to Web Development
using C# and ASP.Net



Class 1 introduced you to the basics of Web
development using ASP and C#, just finishing
off with things like Data Binding
In Class 2 we will delve into several
specialized controls, play a bit with File
Streams and LINQ, work with CSS, and finish
up with a brief tutorial in deploying your site.
In Class 3 you complete the picture with
security, web services, and some Ajax.
Last Update: 1/12
Page 3
Copyright (C) 2012 by David Figge. All Rights Reserved.
Class Format

This class is designed around the lecture/lab
format



We will discuss a subject in class in detail,
Then YOU will experience that subject with one
or more labs
Feel free to ask questions any time




Even stupid ones, like “How is Ajax different than SOAP?
It’s critical that you understand as we encounter the
material, because we build on this knowledge
If it’s appropriate to defer the question until later, I will
Questions between sessions?


Contact me at [email protected]
I’ll try to get back to you in a timely manner
Last Update: 1/12
Page 4
Copyright (C) 2012 by David Figge. All Rights Reserved.
Slides

Over the years, I’ve found that the best
system for me is to have a series of
I also like to make use of these “speech
PowerPoint slides
“lead”
our
discussion
bubbles”.
They help
me make
a point


Show”) in order to make the bubbles
move out of the way until appropriate.
I also make these slides available to you


without
losing the
focusmaterial
of the slide. in an
This allows me
to
present
the
So when
you
use the slides,
remember
Don’t let these throw you off.
to
‘run’
the
presentation (“View Slide
organized way
This way, you can use them for notes or for a
reference in the future
Because they're used as a reference, I try
to make sure they're complete

This may make them 'busier' than many slide
presentations, but I think it's worth it
Last Update: 1/12
Page 5
Copyright (C) 2012 by David Figge. All Rights Reserved.
Facility Basics


Restrooms, etc.
I usually try to take a 15 minute break every
hour or so

If you feel I've gone "too long", let me know.
Last Update: 1/12
Page 6
Copyright (C) 2012 by David Figge. All Rights Reserved.
Environment Basics

You should assume that all data will be wiped off the disk
between sessions

It may not be, but don’t take chances

You can also copy it to a USB drive or email to yourself

Or you can save it to the network
Last Update: 1/12
Page 7
Copyright (C) 2012 by David Figge. All Rights Reserved.
People Basics


Mostly for my benefit
Let’s introduce ourselves with






Your name
What you do
Any courses you’ve taken here before
Why you are taking this course
Are there any specific things you were hoping to learn
What do you like to do in your spare time?
Last Update: 1/12
Page 8
Copyright (C) 2012 by David Figge. All Rights Reserved.
Questions
Questions before we go forth?
Last Update: 1/12
Page 9
Copyright (C) 2012 by David Figge. All Rights Reserved.
Course Overview
Advanced Web Development using C#
Last Update: 1/12
Page 10
Copyright (C) 2012 by David Figge. All Rights Reserved.
Class 2: Course Objectives

Understand of the Philosophy of the C# Language

Utilize Structured Methodology in Constructing C# Modules

Create, Compile, Debug ASP.Net programs using C# elements


Variables, functions, arrays, classes, .Net framework elements
Understand how to use the core controls including GridView and
ListView

Understand how to create your own custom User Controls

Understand the basics of Caching, File Streams, and XML

Understand how to use LINQ in web applications

Understand how to use Cascading Style Sheets and Themes to
provide a consistent look and feel to your site

Understand the basics of deploying a Web Site
Last Update: 1/12
Page 11
Copyright (C) 2012 by David Figge. All Rights Reserved.
Class 2 Schedule





Session 1:

Introductions, Overview

Gridviews Controls
Session 2:

More on GridView Controls
Session 3:

GridView Once Again

ListViews
Session 4:

The DetailsView and FormView

Caching
Session 5:

File Streams

Using XML
Last Update: 1/12
Page 12



Session 6:

User Controls
Session 7:

CSS and Themes
Session 8:

LINQ




Linq with DataSets
Linq with Entities
Session 9:

Deployment
Session 10:

Final Lab
Copyright (C) 2012 by David Figge. All Rights Reserved.
Course Textbook

Text is Pro ASP.NET 4
in C# 2010


I chose this because:






Good text
Reasonable to read
Great reference book to
have in the future
My exercises are typically not
directly from the book


Matthew MacDonald, et. Al.
This way you can have more exercises available to you
Use it as a source to augment my lectures
Our discussions will be chapters 10-18
If you can’t find associated reading, let me know
Questions before we
get started?
Last Update: 1/12
Page 13
Copyright (C) 2012 by David Figge. All Rights Reserved.
Let’s Get Started…
Starting Project
Last Update: 1/12
Page 14
Copyright (C) 2012 by David Figge. All Rights Reserved.
Starting Project

We’re going to start by creating a base
project on which to build and experiment


We’re going to build program called
“Reservations” to keep track of table
reservations for a restaurant


We’ll be building on this project throughout
the classes
Not surprisingly, the Web app will be
driven from a database


Further, it can act as a good “review”
Which is a reasonable place to start
The database that supports this program
will look like this...
Last Update: 1/12
Page 15
Copyright (C) 2012 by David Figge. All Rights Reserved.
Reservations Database
When you have one table have a
reference to Customers
a row inTable
another table,
the best way to do that is through a
CustomerID*
Integer
Unique ID for customer
Foreign Key relationship. We will
LastName
String
Customer’s Last Name
establish one for both the
FirstName
StringTwo key
Customer’s
First Name
pieces
CustomerTable-DiningReservation,
ReservationID
is a address
Address
Stringof information
Customer’s street
and the
DiningTableunique
identifier
City
String
Customer’s
cityfor
for
a
DiningReservation
relationships.
each
row
in the
State
String[2]
Customer’s
State
reservation
table.Customer’s
All
Zip
String[9] are
Zip
thetables
should
haveand
a way
customer
Phone
String[14]
Customer’s
Phone
to uniquely
identify
theCustomer’s
table Email
Email
String
eachassigned
row. This
tois the
We Primary
also
need
to and
know
Key,
is when
them.
These
FK: Customers
Table
the
customer
willSQL
arrive,
maintained
are bothby
departreferences
(assume
The CustomerID
is aServer.
link 90
totoaminutes
row in to
eat), and
the which
total
number
of
the
Customers
table,
keeps
rows
otherSite,
We’ll
build our
baseinWeb
and
guests.
information
aboutour
each
customer
of
tables.
use VS to create
database.
Then
thedata
restaurant.
we’ll display
in our Web Page…
Ready?
DiningTable Table
TableID*
Integer
Unique ID for dining table
Capacity
Integer
Seats at the table
The table reservations portion of the
program will be driven by a table
called DiningReservation.
And
the TableID is a link to a
FK: DiningTable
Table
DiningTable row, which keeps track of
the table ID and the number of seats
DiningReservation
at the table.Table
ReservationID*
Integer
Unique ID for reservation
CustomerID
Integer
Customer’s ID
TableID
Integer
Table’s ID
StartTime
DateTime
Reservation Start Time
EndTime
DateTime
Reservation End Time
Guests
Integer
Number of Guests
*Unique Identifier: Indentity, Auto-Increment
Last Update: 1/12
Page 16
Copyright (C) 2012 by David Figge. All Rights Reserved.
Reservations Database

Steps to Creating the Reservations
Database
1.
Create the Base Web Site
1.
2.
Open Server Explorer from the View
Menu
1.
2.
3.
Last Update: 1/12
File/New Project/Web/New ASP.Net Web
Application, named Reservations
Create new SQL Server Database
Call it Reservations
Create the tables as shown here…
Page 17
Copyright (C) 2012 by David Figge. All Rights Reserved.
Reservations Database
Customers Table
DiningTable Table
CustomerID
Integer
No nulls, Identity, AutoIncrement, Primary Key
TableID
Integer
No nulls, Identity, Auto-Increment,
Primary Key
LastName
nvarchar(50)
No Nulls
Capacity
Integer
No Nulls
FirstName
nvarchar(50)
Address
nvarchar(50)
City
nvarchar(50)
State
nchar(2)
Zip
nchar(10)
Phone
Email


DiningReservation Table
ReservationID
Integer
No nulls, Identity, AutoIncrement, Primary Key
CustomerID
Integer
No Nulls
TableID
Integer
No Nulls
nchar(14)
StartTime
DateTime
No Nulls
nvarchar(50)
EndTime
DateTime
No Nulls
Guests
Integer
No Nulls
Establish the foreign key relationships
DiningReservation-Customers and
DiningReservation-DiningTable.
When you’re ready, we'll add some data…
Last Update: 1/12
Page 18
Copyright (C) 2012 by David Figge. All Rights Reserved.
Reservations Database

Some Data…

Add Customer Names


Use “Show Table Data” from the table in Server
Explorer.
Add the names: Amanda Jones, Byron Barnes, Carl
Moore, Chris Johnston, Jay Carlton, Sam Preston, Sarah
Smith, Wendy Walters


Just add the names for now. We’ll add the other data later
Add DiningTable Data


Add 20 tables with various capacities from 2-10
Add Reservations Data

Add 3 for now (we’ll add more later). Make sure the
capacity of the table (in blue) you give them supports
the number of guests (in purple).



Last Update: 1/12
1,1, 7:30 PM, 9:00 PM, 4 (today’s date is fine)
2, 2, 6:30 PM, 8:00 PM, 6
3, 4, 6:30 PM, 8:00 PM, 4
Page 19
Copyright (C) 2012 by David Figge. All Rights Reserved.
Our First Page



Let’s create a
page to display
the reservation
data we just
entered.
In Site.Master,
change the
header to read “Restaurant Reservation System”
We’ll start with a GridView to show the basic
reservation information

So go back to Default.aspx (design mode) and drag
a GridView control from the toolbox onto it
Last Update: 1/12
Page 20
Copyright (C) 2012 by David Figge. All Rights Reserved.
Setting the Data Source

Click on the Smart Tab (“>”) and where it
says Choose Data Source, select:



<New Data Source>
SQL Database (called ReservationData)
Create a new connection to the Reservations
database


The SQL statement should come out as
“SELECT * FROM [DiningReservation] ORDER BY
[StartTime]”
When you run the program, you should see
data in the GridView
Last Update: 1/12
Page 21
Copyright (C) 2012 by David Figge. All Rights Reserved.
But It’s Not Pretty…




So it’s not very professional right out of
the box, is it?
So let’s set some elements to make
things look better
To begin with, let’s set some of the
column headings and format of the
displays
Go to the “Source” mode of the
Default.aspx file and we’ll fix some of
these things in code

Let’s look at this…
Last Update: 1/12
Page 22
Copyright (C) 2012 by David Figge. All Rights Reserved.
Default.aspx Columns
Locate this section in the source code. As you can
Asthis
youdefines
can see,the
there's
one control we're using.
see,
GridView
BoundField element defined for each
<asp:GridView ID="GridView1"
row.runat="server"
That's where we can customize
AutoGenerateColumns="False” DataKeyNames="ReservationID“
how things look…
DataSourceID="ReservationData">
<Columns>
<asp:BoundField DataField="ReservationID"
HeaderText="ReservationID" InsertVisible="False"
This section defines
the individual
ReadOnly="True"
SortExpression="ReservationID"
/>
columns within
the GridView. That's
<asp:BoundField
DataField="CustomerID"
what's not quite looking good
yet…
HeaderText="CustomerID"
SortExpression="CustomerID"
/>
<asp:BoundField DataField="TableID" HeaderText="TableID"
SortExpression="TableID" />
<asp:BoundField DataField="StartTime“
HeaderText="StartTime" SortExpression="StartTime" />
<asp:BoundField DataField="EndTime" HeaderText="EndTime“
SortExpression="EndTime" />
So modify this
section of code so it
<asp:BoundField DataField="Guests"
HeaderText="Guests“
SortExpression="Guests" /> looks like this next page…
</Columns>
</asp:GridView>
Last Update: 1/12
Page 23
Copyright (C) 2012 by David Figge. All Rights Reserved.
Default.aspx Columns Revisited
<asp:GridView ID="GridView1" runat="server" AutoGenerateColumns="False"
DataKeyNames="ReservationID" DataSourceID="ReservationData">
<Columns>
<asp:BoundField DataField="ReservationID" HeaderText="Reservation Number"
InsertVisible="False" ReadOnly="True" SortExpression="ReservationID" />
<asp:BoundField DataField="CustomerID"
HeaderText="Customer Number" SortExpression="CustomerID" />
<asp:BoundField DataField="TableID" HeaderText="Table Number"
SortExpression="TableID" />
<asp:BoundField DataField="StartTime" HeaderText="Arrive"
DataFormatString="{0:t}" SortExpression="StartTime" />
<asp:BoundField DataField="EndTime" HeaderText="Depart"
DataFormatString="{0:t}" SortExpression="EndTime" />
<asp:BoundField DataField="Guests" HeaderText="Guests"
So it'sSortExpression="Guests"
looking much better now!
/>
Before
we
go
on,
I
don't
want
to
</Columns>
gloss over this very important
</asp:GridView>
DataFormatString property. Let's take
a closer look at that…
Last Update: 1/12
Page 24
Everything in gray is already there
and doesn't need to change. Black
sections are ones that change, red
indicates the actual change itself… It
should run (and look better!)
Copyright (C) 2012 by David Figge. All Rights Reserved.
DataFormatString

The DataFormatString is used to
format the data in a form that is more
appropriate for the data you're
displaying


In our case, displaying the full date and
time was too much data. The {0:t} says
"Display a short version of the time"
There are many options in the format
string. Let's look at a few of them…
Last Update: 1/12
Page 25
Copyright (C) 2012 by David Figge. All Rights Reserved.
DataFormatString Options
Type
Format String
Description/Example
Currency
{0:C}
$1,234.56
Scientific Notation
{0:E}
1.23456E+003
Percentage
{0:P}
53%
Decimal
{0:F2}
45.23 (# is decimal places)
Short Date
{0:d}
7/4/1776
Long Date
{0:D}
Thursday, July 4, 1776
Time
{0:T}
10:00:00 AM
Short Time
{0:t}
10:00 AM
This is a (very) short portion of a very long list. Check in
help for many more options…
Last Update: 1/12
Page 26
Copyright (C) 2012 by David Figge. All Rights Reserved.
Reservations Gridview




So now we're getting closer
Now let's format the ID and Guest columns so that
they're centered in the column
Many of properties that you set in code can also be done
via the Properties window in the "Design" mode
So let's go back to the Design mode, click on the
GridView, and make sure that the Properties window is
displayed.


Note that the properties we set in code are reflected in the
properties window
Now let's center the ID and Guest columns


Select Columns from the property window, press …
Now select the column to change and find the ItemStyle



Open it up, and change the HorizontalAlign to Center.
Do this for the Reservation Number, Customer Number,
Table Number, and Guests columns
Look in the source code to see how it changed when you
set these properties…
Last Update: 1/12
Page 27
Copyright (C) 2012 by David Figge. All Rights Reserved.
A Better SQL Statement

It's looking better, but still isn't where a
professional product should be



We don't want customer IDs and separate
columns for first and last. Let's fix that.
From the Design window, click on the
SqlDataSource and click on the Task Menu tab
Hit NEXT, then tell it we want to specify a
custom SQL statement



This allows us the flexibility to mix, match, and
combine our data via SQL
The table just reflects the resulting SQL Table
from the SQL query
Hit NEXT. Here's the custom SQL Statement:
Last Update: 1/12
Page 28
Copyright (C) 2012 by David Figge. All Rights Reserved.
A Better SQL Statement




SELECT
DR.ReservationID, DR.CustomerID, DR.TableID,
DR.StartTime, DR.EndTime, DR.Guests,
CUST.LastName, CUST.FirstName, DT.Capacity,
CUST.LastName + ', ' + CUST.FirstName AS Fullname
FROM
DiningTable AS DT INNER JOIN
DiningReservation AS DR INNER JOIN
Customers AS CUST
ON DR.CustomerID = CUST.CustomerID
ON DT.TableID = DR.TableID
ORDER BY
DR.StartTime
Copy and Paste should work, but let's talk about the statement…
When asked if you want the system to regenerate the table, say YES.
I think you'll agree that we've made an improvement…
Last Update: 1/12
Page 29
Copyright (C) 2012 by David Figge. All Rights Reserved.
Time to Play A Bit…

Your turn. Make the
table look as it does here

I added a few more
names for realism


You do that, too…
Notes:







Start by removing
unwanted columns
This can all be done via
the Columns property or via code (your choice)
All fields are centered except Customer Name
Be sure to change the header text of the columns
The Customer Name field is a field created by the SQL
statement called FullName
Header text is set by the control's HeaderStyle property
Alternating colors is set by the control's AlternatingRowStyle
property.
40 Minutes
Last Update: 1/12
Page 30
Copyright (C) 2012 by David Figge. All Rights Reserved.
Auto Formatting




All right. We're looking pretty good here.
As you can probably see, formatting the
visuals for lots of tables could be a bit of
a bother
You can also use the Auto Formatting
function from the "Smart Tag" (aka task
menu)
Let's see how that works

If you like yours as it is, just watch me…
Last Update: 1/12
Page 31
Copyright (C) 2012 by David Figge. All Rights Reserved.
Who's There?




What we have is a pretty
good system for showing
how things are for the
day.
What we need is a system
that changes as people
arrive.
To do that, we need to
keep track of whether
a party has arrived or not.
To implement this:




Add a field HasArrived to the DiningReservation table (make it a 'bit'
data type, which holds True or False)
Initialize the new field in the records, setting the first record to TRUE
(so we have one party that has arrived), the rest to FALSE
Add the new column to the SQL statement request
Add the column tothe GridView display so it shows like this example.
20 Minutes
Last Update: 1/12
Page 32
Copyright (C) 2012 by David Figge. All Rights Reserved.
More Formatting…


We'll get to changing the record when
the party arrives in just a few minutes
But first, let's look at another
formatting option


This one allows you to change the
formatting of one row based on the data
displayed
In our case, to allow us to visually change
rows where people have arrived

Last Update: 1/12
We'll de-emphasize the row. The data should
still be shown, but it's not nearly as important
as people who haven't arrived.
Page 33
Copyright (C) 2012 by David Figge. All Rights Reserved.
Data-driven Formatting

To do this, we'll add a handler to the
RowDataBound event of the GridView





This event is triggered as each row is being
drawn up
During this event, you have access to the
data being displayed – in our case the
HasArrived flag
So we'll look to see if that flag is true, and if it
is, we'll change the default formatting of the
row.
Start by adding the RowDataBound Handler
In the method, put this code…
Last Update: 1/12
Page 34
Copyright (C) 2012 by David Figge. All Rights Reserved.
The RowDataBound Handler
protected void GridView1_RowDataBound(...)
{
if (e.Row.RowType == DataControlRowType.DataRow)
{
if ((bool)DataBinder.Eval(e.Row.DataItem, "HasArrived") == true)
{
e.Row.BackColor = System.Drawing.Color.LightGray;
Also notice this line. Because not all rows
e.Row.ForeColor = System.Drawing.Color.DarkGray;
contain data (like the header row), we need to
}
Notice
howonly
we to
access
the data from
for the
row.that
We
be careful
request
a row
}
Here's where
call
wethe
look
DataBinder.Eval
at data!
the "HasArrived"
in
actually
HAS
That's method,
what data
thispassing
line does.
}
column.
e.Row.DataItem
If it's true (they've
(essentially
arrived)…
the record), asking
wetext
change
the That's
row's
Notice
in Gray.
already beencolor to
forThen
thethe
HasArrived
field
in it. background
light
the foreground
color
(the text)
added
by gray,
Visualand
Studio.
It's just here
to show
darkthe
gray.
Stillgoes.
readable,
as obvious
you to
where
code
Also, but
the not
… shows
as people
haven't
arrived.
that there's more
codewho
on the
line, but
it's not
important to what we're doing. When it's all
in, it should run.
Does this all
make sense?
Last Update: 1/12
Page 35
Type it in, then we’ll look at it…
Copyright (C) 2012 by David Figge. All Rights Reserved.
Row Selection


Okay. Now that we have the grid responding
properly when someone has arrived, let's add the
ability to change that setting from the GridView.
To do this, we're going to start by adding a
column to the GridView with a "Here!" button
(one for each row)





From the Design mode, highlight the GridView and
open the Columns settings from the Properties
window
In the top window, open the CommandField branch
and select the item that says "Select"
Add it to the displayed columns by clicking the Add
button. Move it to the top of the list.
From the bottom window, highlight the new element
and change the SelectText to read "Here!"
Give it a try (run it)!
Last Update: 1/12
Page 36
Copyright (C) 2012 by David Figge. All Rights Reserved.
Row Selection

Okay, not much happens yet



Although the row did "highlight"
Not much happened because we don't have
any code to cause those changes to occur.
When you press the Here button, it selects the
row.

When you select a row, several things occur:

SelectedIndexChanging is fired



The SelectedIndex property is set to the new row
The SelectedIndexChanged event is fired


Last Update: 1/12
You can catch this and cancel the row change if needed (set
the e.Cancel flag to true and return)
This is where you can trap the event and update the
database based on the button click. Let's do that
Add a SelectedIndexChanged handler via Properties, then…
Page 37
Copyright (C) 2012 by David Figge. All Rights Reserved.
SelectedIndexChanged
There are two key fields in the GridView we need
here. First, the DataKeyNames must be set. This
defines the primary key for the database table. In our
protected void GridView1_SelectedIndexChanged(...)
it's the
ReservationID (since the data comes
Then we createcase,
our SQL
statement
{
int thisRow = GridView1.SelectedIndex;
fromtothat
table,
(setting HasArrived
'true')
for the
our DataSource sets this for us).
int ReservationID = (int)GridView1.SelectedDataKey.Value;
this record.
SqlConnection connection = new SqlConnection(ReservationData.ConnectionString);
connection.Open();
Then we need to trigger a redraw of the GridView. Since
string newValuewe'll
= "true";
need that several places, we'll create a method to
SqlCommand cmd = new SqlCommand("UPDATE [DiningReservation] SET [HasArrived] = '" +
do that
called
Refresh()
The
key element is the SelectedDataKey.
newValue + "' WHERE [ReservationID]
= "second
+ ReservationID.ToString(),connection);
Based on
we can
the HasArrived
cmd.ExecuteNonQuery();
It'sthat
thekey,
primary
keynow
(viaset
DataKeyNames)
for the
Refresh();
field to 'true' for the selected row. We'll do that
currently selected row. So, in our case, it's the
}
through a standard
SQL statement.
we create
a
ReservationID
of the rowHere
we just
selected.
void Refresh()
SQLConnection object, using the connection string
{
Then we execute the statement.
that's in ReservationData.
Response.Redirect("Default.aspx");
}
…which simply causes our page
to redraw itself.
Have I lost
anyone?
Last Update: 1/12
Page 38
Once again, type it in, then we'll talk about it…
Copyright (C) 2012 by David Figge. All Rights Reserved.
Lookin' Better!



Alright. Now we're looking a bit better.
Before we go any further, I want to
give you a chance to play a bit with
what we've learned up to now.
So…
Last Update: 1/12
Page 39
Copyright (C) 2012 by David Figge. All Rights Reserved.
The Customer Screen

Add a second screen, linked to by the
home page, that

Uses a GridView to display the contents of
the Customers table

Don't display the Customer ID



But that should be the DataKeyNames parameter so we
can use it when we add editing
Remember there isn't much data in there yet, but
have it display all the columns anyway.
Extra – Add a column to the grid that
indicates whether the customer currently
has a reservation in the system.
40 Minutes
Last Update: 1/12
Page 40
Copyright (C) 2012 by David Figge. All Rights Reserved.
Row Selection Revisited

Let's revisit our Table Reservations page



Let's turn the "little too obvious" button into something
more subtle: a link
You can use any data field as a link also, and that's how
we'll implement this
Start by adding a ButtonField



Set the ButtonType to Link
Set the HeaderText to ID
Set the CommandName to Select


Set the DataTextField to ReservationID



This causes the row to be selected, thus invoking the
SelectedIndexChanged event where our code is
This tells the system to use this row as the data (so we click on the record
ID to select the row).
Note that we're still setting the record in the row to "Arrived", like
the buttons. Just another way of selecting rows.
Once it's working, we can remove the button-based column
Last Update: 1/12
Page 41
Copyright (C) 2012 by David Figge. All Rights Reserved.
Toggling the Selection


Okay, I admit that it's getting a little
annoying that we only set the
customer record to "Arrived"
Let's change the link processing so it's
a toggle instead


It changes it's True/False state back and
forth every time you select it.
To do that, we just have to get the
existing state of the record field and
select its opposite…

Here's the code changes…
Last Update: 1/12
Page 42
Copyright (C) 2012 by David Figge. All Rights Reserved.
SelectedIndexChanged
protected void GridView1_SelectedIndexChanged(...)
{
int thisRow = GridView1.SelectedIndex;
A pretty direct way to determine the current
int ReservationID = (int)GridView1.SelectedDataKey.Value;
setting of the HasArrived flag is to ask the
SqlConnection connection = new
database. So here we create a SQL statement
SqlConnection(ReservationData.ConnectionString);
connection.Open(); that does that.
string newValue = "true";
The=rest
ofSqlCommand("SELECT
thelooking
code already
setsHasArrived
the
table
column
Because
we're
for a single
return
value,
we to
can
SqlCommand cmd
new
FROM
" +
whatever
newValue
is,
so
there's
no
need
to
change
use ExecuteScalar,
casting the results
"[DiningReservation]
WHERE [ReservationID]
= "to bool.
anything else…
+ ReservationID.ToString(),connection);
bool result = (bool)cmd.ExecuteScalar();
if (result == true) newValue = "false";
cmd = new SqlCommand("UPDATE [DiningReservation] SET [HasArrived] = '" +
newValue + "' WHERE [ReservationID] = " +
ReservationID.ToString(),connection);
cmd.ExecuteNonQuery();
We originally set the newValue to true.
Refresh();
}
Last Update: 1/12
Now we look to see if we should really be
setting it to false (e.g. if the 'HasArrived'
value already says true).
Page 43
Any questions
on this?
You know the drill… Type first, then talk…
Copyright (C) 2012 by David Figge. All Rights Reserved.
Simple Editing


We're looking pretty good now, but an
obvious thing to add is the ability to
edit a record.
This is actually pretty easy



Enable Editing within the GridView
Provide an SQL statement as an Update
Command in the SqlDataSource.
Let's try that…
Last Update: 1/12
Page 44
Copyright (C) 2012 by David Figge. All Rights Reserved.
Simple Editing

Using the GridView's "Smart Tab", turn on Enable
Editing


This turns on a link saying Edit.
Let's move that to a more appropriate location


the parameter
for that
column
is
Use the "ConfigureColumn
Dataname,
Source"
option
from
the
automatically
created.Command
Nice, huh?
DataSource object to set
the Update
field
to:


Put it to the right of Guests, and put "Change" as the column
heading
By making the parameter name be the same as the SQL
UPDATE DiningReservation
SET TableID =@TableID, StartTime =@StartTime,
EndTime =@EndTime, Guests =@Guests
WHERE ReservationID=@ReservationID
You should be able to edit at this point. Give it a try…
Last Update: 1/12
Page 45
Copyright (C) 2012 by David Figge. All Rights Reserved.
Using Templates




We've been able to control the look and feel
of a GridView pretty well with the basic
formatting functions it has built in
However, we unleash another level of options
when we use GridView Templates.
By inserting a Template Field as a column, you
have the full control of the underlying HTML
to determine the look, feel, and function of
the field
Let's look at simple example


Add a column to the right end of your GridView
using the TemplateField type, making the
HeaderText be "Summary"
Go into the source mode, and find the last
column and insert this code…
Last Update: 1/12
Page 46
Copyright (C) 2012 by David Figge. All Rights Reserved.
The Summary Column
Recall that the <%# … %> tag
indicates that we're using
<asp:TemplateField
Data Binding. HeaderText="Summary">
<ItemTemplate>
<%# Eval("FirstName") %> <%# Eval("LastName") %>
will arrive at <%# Eval("StartTime") %>
with <%# Eval("Guests") %> guests.
In the Binding Tag we use the static
</ItemTemplate>
function Eval(), which gives us the
</asp:TemplateField>
value of the database column for the
current record.
So we're combining the first name, last
name, start time, and guests to create an
HTML text line, all within a GridView
column. Templates provide us with options
that are almost limitless.
Last Update: 1/12
Page 47
Once you get it in, we'll discuss it…
Copyright (C) 2012 by David Figge. All Rights Reserved.
Checking the Arrival

As an example of what we can do, let's take
the first two columns of our GridView (the
record ID and the "Arrived" status) and
replace them with a simple checkbox.


Then we'll trap the CheckChanged event
and use it to toggle the arrival status


Templates allow us to insert controls into
columns!
Similar to how we did it when we selected the
row
Ready?
Last Update: 1/12
Page 48
Copyright (C) 2012 by David Figge. All Rights Reserved.
Adding the CheckBox


Start by removing the first two columns
Add a TemplateField as the first column


Make the HeadingText be "Arrived" and the
positioning centered
Using the "smart tag", select "Edit
Templates"


Our new column should be at the top of the list
and currently displayed
Drag a CheckBox from the toolbox onto it


Pretty easy to add controls, huh?
Now go into the Source mode and enter this
ASP code…
Last Update: 1/12
Page 49
Copyright (C) 2012 by David Figge. All Rights Reserved.
Adding the CheckBox
<asp:TemplateField HeaderText="Arrived">
<ItemTemplate>
<asp:CheckBox ID="CheckBox1" runat="server"
AutoPostBack = "true"
OnCheckedChanged="ArrivedCheckChanged"
Checked='<%# Eval("HasArrived") %>'
Text="Arrived" />
</ItemTemplate>
<ItemStyle HorizontalAlign="Center"
/>
Here we're saying to set the checkmark
based on the record's HasArrived field,
</asp:TemplateField>
and when the check mark changes, to call
the method ArrivedCheckChanged.
Let's look at that function now…
Last Update: 1/12
Page 50
Once you get it in, we'll discuss it…
Copyright (C) 2012 by David Figge. All Rights Reserved.
Adding the CheckBox
Every event gets two parameters: the
triggering object and EventArgs
Here we take the triggering objectSo
(the
checkbox)
and store
it into a
there's
a gives
lot going
on
here.
The
control's
NamingContainer
property
you
the
Now
we us
getthe
thecheckbox
indexsender,
(row
number)
public
void cb.
ArrivedCheckChanged(object
EventArgs
e)clicked row's
Weobject
can
get
thewas
database
variable
This
gives
that
Let's
break
it
down…by the user.
row
where
it
sits
within
the
GridView.
{
of the row. With that information…
(which
is what
we
Now it becomes aprimary
simple key
matter
(similar
to how
CheckBox cb = (CheckBox)sender;
need to update the
table).the
GridViewRow row = (GridViewRow)cb.NamingContainer;
we did it in SelectedIndexChanged)
to update
int GridViewRowNum =table
row.DataItemIndex;
row based on the checkmark's on/off status.
int ReservationID = (int)GridView1.DataKeys[GridViewRowNum].Value;
string newValue = "true";
if (cb.Checked == false) newValue = "false";
SqlConnection connection = new SqlConnection(ReservationData.ConnectionString);
connection.Open();
SqlCommand cmd = new SqlCommand("UPDATE [DiningReservation] SET [HasArrived] = '" +
newValue + "' WHERE [ReservationID] = " + ReservationID.ToString(), connection);
cmd.ExecuteNonQuery();
Refresh();
}
Questions on what we've done here?
Last Update: 1/12
Page 51
Go ahead and get it typed in before we talk…
Copyright (C) 2012 by David Figge. All Rights Reserved.
Advanced Editing

As you know, we can now edit a record
from the GridView

However, it's pretty limited editing

Text boxes aren't always the best way to edit




No validation
It often looks amateurish


For example, our Table # can't just take any value
A Drop-Down list box would be more appropriate
Like, well, you just turned editing on with the
GridView 
Now that we know about Templates, we
have the skills to use more advanced
editing tools…
Last Update: 1/12
Page 52
Copyright (C) 2012 by David Figge. All Rights Reserved.
Advanced Editing


So to see how this works, let's put the
Table Number field into a Drop-Down
List Box (e.g. Combo box)
We will do this by
1.
2.
Last Update: 1/12
Using templates in the ASP file to display
the box, fill it, and set the right value for
the record, and store it to the database
when the value changes
Add the functions to the code-behind
page to support this
Page 53
Copyright (C) 2012 by David Figge. All Rights Reserved.
Advanced Editing: ASP
<asp:BoundField DataField="Fullname" HeaderText="Customer
Name" ReadOnly="True"
Here we use the TemplateField tag, setting
SortExpression="Fullname">
Now weSo
have
a
template
we're usingthe
a
the
header
textthe drop
Identifying
value
within
<ItemStyle Font-Bold="True"
/> index
specific
to
this
item.
DropDownList
with
an
ID ofnumber in the record is a
down
of
the
table
</asp:BoundField>
This causes events to trigger
TableNum
bit
complex.
We'll
do that in the Code
<asp:TemplateField HeaderText="Table
#">
when
the
item
is changed
Finally,
we're
"When
thethe
selection
We'll
dosaying
the
same
get
Behind
page.
This
is how
weto'call'
<ItemTemplate>
changes,
callpassing
this
function
in the
Code
appropriate
table
numbers,
only
function
there,
the
TableID
<asp:DropDownList runat="server"
ID="TableNum"
Behind
page"
which
willa update
the
this time
we're
using
property.
AutoPostBack = "true"database record and refresh the display.
SelectedIndex='<%# GetTableIndex(Eval("TableID")) %>'
DataSource='<%# TableNumbers %>'
OnSelectedIndexChanged="TableSelectionChanged" />
</ItemTemplate>
</asp:TemplateField>
Questions so far…?
<asp:BoundField DataField="Capacity" HeaderText="Table Size"
SortExpression="Capacity">
Replace the existing BoundField entry for the
TableID with this code (it won't work yet)…
Last Update: 1/12
Page 54
Copyright (C) 2012 by David Figge. All Rights Reserved.
Advanced Editing: CS Part 1
The TableNumbers
method returns an
protected string[] TableNumbers
We start by executing
(in a way that
arraynow)
of legal
table
numbers. We grab
{
should be familiar
a SQL
Request.
get
this from the database.
{
SqlConnection connection = new
Because we need multiple values back,
SqlConnection(ReservationData.ConnectionString);
we use a DataReader object
We create an empty List object, then
connection.Open();
SqlCommand cmd = new
use the reader to fill it with the contents
SqlCommand("SELECT TableID FROM
DiningTable",connection);
of each
data row returned
SqlDataReader tableList = cmd.ExecuteReader();
List<String> tables = new List<String>();
while (tableList.Read())
Finally, we return the list object values
{
converted to an array.
The GetTableIndex returns the location within the array of
tables.Add(tableList["TableID"].ToString());
}
tableIDs where the passed-in tableID is located. This
The
Array.IndexOf
searches
through
the
the index
on
this
property
before
we move
on?
return tables.ToArray();
makes
it display Questions
the
right value
when
thearray,
box
isreturning
displayed.
}
of the specified object (which is what we need). Make sense?
}
protected int GetTableIndex(object tableNumber)
{
return Array.IndexOf(this.TableNumbers, tableNumber.ToString());
}
Last Update: 1/12
Page 55
Add this code to your Code Behind page…
Copyright (C) 2012 by David Figge. All Rights Reserved.
Advanced Editing: CS Part 2
Like we did with the checkbox, here
we're gettingsender,
the ReservationID
based
public void TableSelectionChanged(object
EventArgs
e)
on the row that the list box is in…
{
DropDownList ddl = (DropDownList)sender;
GridViewRow row = (GridViewRow)ddl.NamingContainer;
int GridViewRowNum = row.DataItemIndex;
int ReservationID =
Then we create a new SQL statement
(int)GridView1.DataKeys[GridViewRowNum].Value;
SqlConnection connection =that
newupdates the DiningReservation
table to use the selected table.
SqlConnection(ReservationData.ConnectionString);
connection.Open();
SqlCommand cmd = new SqlCommand("UPDATE [DiningReservation] "+
Finally,
we +callddl.SelectedValue
our Refresh method to+ "' WHERE " +
"SET [TableID]
= '"
redisplay
database values.
"[ReservationID]
= the
" +updated
ReservationID.ToString(),
connection);
cmd.ExecuteNonQuery();
Refresh();
}
Last Update: 1/12
So this method is called when the user
changes the value in the drop-down box.
Page 56
Add this code to your Code Behind page too…
Copyright (C) 2012 by David Figge. All Rights Reserved.
Exercise

Use a DropDownList to display the
Arrival times of the customers (so they
can be changed if they're late)



Arrival times are on the ½ hour, from 5:00
PM to 10:00 PM
When changed, modify the departure time
to be 90 minutes past the arrival time
Extra Credit:

Modify the TableNumbers property to not
list any tables currently in use during during
that time slot (a worthy challenge!)
45 Minutes
Last Update: 1/12
Page 57
Copyright (C) 2012 by David Figge. All Rights Reserved.
End of Session 1
Advanced Web Development using C#
Last Update: 1/12
Page 58
Copyright (C) 2012 by David Figge. All Rights Reserved.