第一章 建立ASP.NET页面
第一章 建立ASP.NET页面
主要内容:
l ASPNET和.NET框架
l ASPNET控件简介
l 向ASPNET页面中添加应用逻辑
l ASP.NET页面的结构
何为”表单”?
Web表单页面能够做的事情远远不只是显示标准的HTML表单,可以用它创建具有交互式、动态或数据库驱动的内容的页面。
Web表单页面构件
页面是有两个构件组成.
首先,使用ASP.NET控件组装用户界面的动态部分.
第二个构件是应用逻辑.(包括执行代码,或数据库操作代码)
1. ASPNET和.NET框架
ASPNET是.NET框架的一部分,
1.1. .NET框架类库
1.2. 理解命名空间
.NET的类由(命名空间)组成层次结构.
(相对的,ASP只能访问五个标准类[Response/Request/Session/Application/Server])
名称空间是类的逻辑分组.
名称空间组织成一个层次结构(逻辑树).树根是System名称控件(包含基本数据类型,随机数,日期和时间的类).
1.3. 标准的ASP.Net名称空间
ASPNET页面可以默认地使用一些名称空间(其中包含最常使用的类)中包含的类,其他名称空间必须显示导入.
名称空间 |
说明 |
System |
包含所有基本数据类型,和其他常用类,如随机数,日期和时间相关类. |
System.Collections |
用于操作标准集合类型的类(比如散列表和数组列表) |
System.Collections.Specialized |
包含特殊化集合的类(链表和字符串集合) |
System.Configuration |
包含用于操作配置文件[Web.config]的类 |
System.Text |
包含用于编码、解码和操作字符串内容的类。 |
System.Text.RegularExpressions |
包含用于执行正则表达式匹配和替换操作的类 |
System.Web |
包含用于使用WWW的基本类,包括表示浏览器请求和服务器响应的类 |
System.Web.Cache |
用于缓存页面内容的类和用于执行自定义缓存操作的类 |
System.Web.Security |
用于实现身份验证和授权的类 |
System.Web.SessionState |
实现会话状态的类 |
System.Web.UI |
建立ASPNET页面的用户界面的基本类 |
System.Web.UI.HTMLControls |
HTML控件的类 |
System.Web.UI.WebControls |
ASPNET控件的类 |
1.4. 与.NET框架兼容的语言
可以使用“支持NET通用语言运行时CLR的任何语言创建ASP.NET页面.
不管使用何种语言,都要认识到:”ASP.NET页面在执行前需要编译.”
在第一次请求ASP.NET页面时,页面被编译成.NET类,产生的类文件保存在服务器的特定目录中(Temporary ASP.NET Files,此文件位于你的.NET Framework文件夹的对应版本,例如.NET 2.0下位于这里C:"WINDOWS"Microsoft.NET"Framework"v2.0.50727)
对于每一个每一个ASPNET页面,在Temporary ASP.NET Files中都有一个对应的类.对页面的请求,会执行对应的类文件.
ASPNET页面被编译为IL代码.此代码会由即时编译器JIT编译(其实就是在Temporary ASP.NET Files目录中的类文件),并执行它.这个过程是后台自动发生的.
ASPNET不支持VBScript.Visual Basic具备VBScript的全部功能.
2. ASP.NET控件简介
2.1. 简单的ASP.NET页面
首先展示一个简单的HTML页面.(可以使用记事本程序)
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" >
<head>
<title>Simple HTML Page</title>
</head>
<body>
<form method="post" action="SimpleHTML.htm">
<b>UserName:</b>
<br /><input name="username" type="text" size="30" />
<p></p>
<b>Comments:</b>
<br /><textarea name="comments" cols="60" rows="10"></textarea>
<p></p>
<input type="submit" value="Add Comment" />
</form>
</body>
</html>
以上页面包含一个简单的HTML表单,其中有一个用户名文本域和一个注释文本域.
这个表单提交到它本身(<form method="post" action="SimpleHTML.htm">)
表单中不包含ASPNET控件.
下面,将页面修改为使用ASPNET控件,将表单域转换为”智能”服务器端表单域.
<%@ Page Language="VB" AutoEventWireup="false" CodeFile="SimpleASPX.aspx.vb" Inherits="SimpleASPX" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
<title>Simple ASPX Page</title>
</head>
<body>
<form id="form1" runat="server">
<div>
<b>UserName:</b>
<br /><input id="username" type="text" size="30" runat="server" />
<p></p>
<b>Comments:
</b>
<br /><textarea id="comments" cols="60" rows="10" runat="server"></textarea>
<p></p>
<input type="submit" value="Add Comment" runat="server" />
</div>
</form>
</body>
</html>
比较两端代码,我们应该注意到有四处修改.
首先,页面的扩展名改为aspx.这样Web服务器才能按照ASP.NET页面加载.
其次,所有表单标记中都添加了[runat=”server”]属性.此属性将标准HTML标记转换为”智能”服务器端HTML标记.在服务器中打开页面时,有此属性的表单标记现(在服务器上执行),然后在浏览器中显示.
第三,不再使用NAME属性为(表单域命名),而是使用[ID属性为表单域分配一个惟一标识符].使用ID属性是因为不再将表单域看成简单的HTML标记;而是将其转换为服务器端对象.
最后,是form标记的修改.必须[在表单域的开始就使用runat=”server”
注意:表单标记转换为ASP.NET时,不要使用Method属性,因为此属性是自动包含的.
注意:在[默认]情况下,标准HTML表单标记的Method属性值为GET. Method=”GET”的表单提交时,表单数据作为[查询字符串变量]提交.(不能在查询字符串中传递大量表单数据-具体受限于浏览器,一般不超过1000到2000个字符. 一般在创建HTML表单时,在表单标记中添加[Method=”POST”属性] ASP.NET中的表单标记,[默认]时,Method=”POST”. |
如果不指定Action属性,ASP.NET表单控件自动发送回相同页面.
要将标准HTML转换为ASP.NET页面,需要对页面做四处修改: 1) 将文件重命名,扩展名.aspx 2) 每个表单标记添加runat=”server”属性 3) 不使用表单标记的NAME属性,而是使用[ID属性] 4) 将<form>标记改为<form runat=”server”> |
ASP.NET页面在后台做了大量复杂的工作,还带来了几种令人兴奋的编程方式.
2.2. ASP.NET控件的优点
使用ASP.NET控件有四个重要的优点: l ASP.NET控件在[一个直观的对象模型中表达HTML元素] l ASPNET控件通过[参与视图状态自动保留它们的属性值] l ASP.NET控件[允许你清晰的分隔页面的设计内容和应用逻辑] l ASP.NET控件[能够维持浏览器兼容性,同时支持高级的浏览器特性,如JavaScript] |
1. 直观的对象模型
一般情况下,web服务器忽略页面中的HTML标记.从Web服务器角度看,这些标记是发送到Web浏览器的无意义字符串;(分析执行页面标记)的工作将由浏览器完成.如<b>bold</b>
但是,将HTML标记转换为ASP.NET控件后,对于Web服务器来说,这些标记变成[服务器端对象],它具有可以在程序中操作的属性、方法、集合和事件。
HTML标记转为服务器端对象有很多好处。比如:可以通过服务器端代码操作对象的属性;可以编写应用逻辑来读取或修改对象属性;可以通过程序向页面添加新对象或隐藏现有对象。
注意:传统的ASP只能编写从上到下执行的页面;而ASP.NET允许编写代码来响应有某些用户动作引发的事件(事件驱动的编程模型) |
2. 视图状态
提交ASP.NET控件所建立的表单时,所有表单域中输入的数据在表单再次出现时都会(保留)。Microsoft将这种自动保留数据的特性称为视图状态(View State)。
ASP.NET控件自动地保留视图状态。
标准的HTML表单,每次都会得到空的表单域。
所有的ASP.NET控件都会自动的保留视图状态。 |
<%@ Page Language="VB" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<script runat="server">
Sub Button_Click(ByVal s As Object, ByVal e As EventArgs)
entries.InnerHtml = "<hr>" & username.Value & "<p>" & comments.Value & entries.InnerHtml
End Sub
</script>
<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
<title>清单1-4 GuestBook.aspx</title>
</head>
<body>
<form id="form1" runat="server">
<div>
<b>UserName:</b>
<br /><input id="username" type="text" size="30" runat="server" />
<p></p>
<b>Comments:</b>
<br /><textarea id="comments" cols="60" rows="10" runat="server"></textarea>
<p></p>
<input type="submit" onserverclick="Button_Click" value="增加注释" runat="server" />
<p></p>
<span id="entries" runat="server"></span>
</div>
</form>
</body>
</html>
通过<span>标记的innerHTML属性,将用户名和注释域的内容添加到<span>标记显示的文本中。
<span>标记的视图状态被保留了下来。(可以通过浏览器查看源码功能查看)
视图状态有什么用?
视图状态最重要的作用就是(表单检验)。
3. 将代码与内容分离
4. 浏览器兼容性
ASP.NET页面在服务器上执行,而不是在浏览器。
当浏览器请求ASP.NET页面是,会获得标准的HTML页面。
ASP.NET页面可以与任何浏览器兼容。
2.3. ASP.NET控件概述
向Web表单添加的ASPNET控件多达50多种。分为两类:
l HTML控件
l Web控件
1. ASPNET HTML控件
HTML控件是标准HTML标记的服务器端复制品。
l 对于每一个最常见的HTML标记,有一个服务器端HTML控件与之对应。(只需在标记末尾添加runat=”server”属性)
l 另外,任何不由特殊服务器控件代表的HTML控件可以用HtmlGenericControl表示。
HTML控件如何处理新的或者含义模糊的HTML属性? 例如:在标准的HtmlInputText控件中添加名为myAttribute的属性,如下 <input id=”username” type=”text” myAttribute=”39” runat=”server”/> 【这个属性不会造成错误】
而如果你在HTML控件中添加一个奇怪的属性,那么显示时,控件只是将此属性的值【原封不动】地传递给Web浏览器。 |
1) HtmlAnchor
用来创建一个服务器端(HTML锚标记)
<a href=”somepage.aspx” runat=”server”>点此</a>
2) HtmlButton
用来创建一个服务器端HTML4.0按钮标记。(一个兼容HTML4.0的<button>标记)
【不要将HtmlButton与HTMLInputButton混淆】后者用于创建(表单按钮)。
<button runat=”server”>click Here</button>
3) HtmlForm
用于创建一个服务器端HTML <form>标记。
<form runat=”server”>
4) HtmlGenericControl
为没有HTML控件与之直接对应的HTML标记创建一个服务器控件。
例如:如果使用具有runat=”server”属性的<span>、<body>或<marquee>标记,那么就会创建HtmlGenericControl的一个示例:
<span runat=”server”>Hello World!</span>
5) HtmlImage
用于创建一个服务器端<img>标记
<img id=”myImage” src=”smile.gif” runat=”server”/>
6) HtmlInputButton
用于创建一个服务器端<input type=”submit”>、<input type=“reset”>或<input type=”button”>标记
<input type=”submit” value=”提交” runat=”server”/>
7) HtmlInputCheckBox
用于创建一个服务器端<input type=”checkbox”>标记
<input type=”checkbox” runat=”server”>Do you like this Web Site?
8) HtmlInputFile
用于创建一个服务器端<input type=”file”>标记(接受文件上传)
<input type=”file” runat=”server”>
9) HtmlInputHidden
用于创建一个服务器端<input type=”hidden”>标记
<input type=”hidden” runat=”server”>
10) HtmlInputImage
创建一个服务器端<input type=”image”>标记
<input type=”image” runat=”server”>
11) HtmlInputRadioButton
创建一个服务器端表单单选按钮
Geneder?
<br/><input type=”radio” runat=”server”>Male
<br/><input type=”radio” runat=”server”>Female
12) HtmlInputText
创建一个服务器端<input type=”text”>或<input type=”password”>标记
Please Login:
UserName:
<input id=”username” type=”text” runat=”server”/>
<p/>
Password:
<input id=”password” type=”password” runat=”server”/>
13) HtmlSelect
创建一个服务器端HTML <select>标记(用于创建【下拉列表】或【列表框】)
Select your favorite movie:
<select runat=”server”>
<option>Star Wars</option>
<option>Citizen Kane</option>
<option>The Princess Bride</option>
</select>
14) HtmlTable
创建一个服务器端HTML <table>标记
<table border=1 cellspacing=0 cellpadding=4 runat=”server”/>
15) HtmlTableCell
创建服务器端Html表格<td>标记(用于创建HTML表格单元格)
<td runat=”server”>Table Data</td>
16) HtmlTableRow
创建HTML表格<tr>标记(HTML表格行)
<tr runat=”server”>
<td runat=”server”>Table Data1</td>
<td runat=”server”>Table Data 2</td>
</tr>
17) HtmlTextArea
创建服务器端HTML<textarea>标记(多行的文本输入域)
<textarea cols=”60” rows=”10” runat=”server”></textarea>
2. Web控件
所有最常用的HTML标记都可以用HTML控件或Web控件来表达。
注意: n HTML控件都在〖System.Web.UI.HTMLControls名称空间〗中; n 而Web控件都在〖System.Web.UI.WebControls名称空间〗中。 |
Web控件是标准HTML标记的『更合理』的版本。(标准HTML标记不是处于最合理的状态)
注意:在Web控件结尾必须明确添加结束标记(前向斜线 / )
<asp:TextBox id=”username” columns=”30” Runat=”server”></asp:TextBox>
或者,可以这样写:
<asp:TextBox id=”username” columns=”30” runat=”server”/>
Web控件种类比HTML控件多。可分为五类:
u 基本的Web控件。大致对应于现有HTML标记。包括TextBox、DropDownList和ListBox控件。第一组控件如下:
n Button
n CheckBox
n CheckBoxList
n DropDownList
n HyperLink
n Image
n ImageButton
n Label
n ListBox
n LinkButton
n Panel
n PlaceHolder
n RadioButton
n RadioButtonList
n Table
n TableCell
n TableRow
n TextBox
u 检验web控件。包含用于进行表单验证的控件。这些控件不对应现有的任何HTML标记。
n CompareValidator
n CustomValidator
n RangeValidator
n RegularExpressionValidator
n RequiredFieldValidator
n ValidationSummary
u 数据控件。用于显示数据库数据,跟ADO.NET有关。
n DataGrid
n DataList
n Repeater
u 复杂的Web控件。Microsoft提供的两个复杂控件:其一,Calendar控件(显示交互式日历);第二,AdRotator控件(用于显示广告条)
u 可移动(移动设备)控件。支持移动电话或者PDA。
3. 向ASP.NET页面添加应用逻辑
3.1 处理控件事件
通过将一个子例程(sub)与事件相关联,可以处理控件引发的事件。
<%@ Page Language="VB" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<script runat="server">
Sub btnSubmit_Click(ByVal o As Object, ByVal e As EventArgs)
lblMessage.Text = "你好啊,ASP.NET!"
End Sub
</script>
<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
<title>无标题页</title>
</head>
<body>
<form id="form1" runat="server">
<div>
<b>程序清单1-5 DisplayMessage.aspx</b>
<p></p>
<h1>Click on the button to View the Message:</h1>
<p></p>
<asp:Button ID="btnSubmit" Text="click Here" OnClick="btnSubmit_Click" runat="server" />
<p></p>
<asp:Label ID="lblMessage" runat="server"></asp:Label>
</div>
</form>
</body>
</html>
在ASPNET页面中声明子例程的方式如下:
Sub btnSubmit_Click(s As Object, e As EventArgs)
End Sub
l 可以使用第一个参数(Object类型)判断触发子例程的是哪个对象?并且做出相应的响应。
l 第二个参数是EventArgs类型,其中可以包含被引发的事件所特有的信息。(对于Button,它没有任何属性)
ImageButton控件就能传递有意义的EventArgs参数。
<%@ Page Language="VB" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<script runat="server">
Protected Sub ImageButton1_Click(ByVal sender As Object, ByVal e As System.Web.UI.ImageClickEventArgs)
Label1.Text = e.X
Label2.Text = e.Y
If (e.X > 59 And e.X < 80) And (e.Y > 59 And e.X < 80) Then
lblMsg.Text = "打中靶心"
Else
lblMsg.Text = "笨死了"
End If
End Sub
</script>
<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
<title>无标题页</title>
</head>
<body>
<form id="form1" runat="server">
<div>
<asp:ImageButton ID="ImageButton1" runat="server" ImageUrl="~/Img/i1.JPG" OnClick="ImageButton1_Click" /><br />
<br />
x位置:<asp:Label ID="Label1" runat="server" Text="Label"></asp:Label><br />
<br />
y位置:<asp:Label ID="Label2" runat="server" Text="Label"></asp:Label></div>
<p></p>
<asp:Label ID="lblMsg" runat="server"></asp:Label>
</form>
</body>
</html>
3.2. 处理页面事件
在『请求ASP.NET页面时』,页面本身会引发几个事件。
<%@ Page Language="VB" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<script runat="server">
Sub Page_Init()
lblMessage.Text &= "<li> Init Event"
End Sub
Sub Page_Load()
lblMessage.Text &= "<li> Load Event"
End Sub
Sub page_prerender()
lblMessage.Text &= "<li> PreRender Event"
End Sub
Sub Page_Unload()
lblMessage.Text &= "<li> Unload Event"
End Sub
</script>
<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
<title>清单1-8 PageEvent.aspx</title>
</head>
<body>
<form id="form1" runat="server">
<div>
<asp:Label ID="lblMessage" runat="server"></asp:Label>
</div>
</form>
</body>
</html>
注意:Page_Unload子例程的消息不被显示的原因是【Unload事件在浏览器显示完所有内容之后才发生。】 |
最有用的页面事件是Load事件。(可以在这里对页面中的变量和控件状态,进行初始化。
注意:Random类是System名称空间的一部分。(可参考.NET Framework SDK文档)
Dim ran_num As New Random
Dim i As Integer
For i = 0 To 10
lblMessage.Text &= ran_num.Next(1, 11) & ", "
Next
其中ran_num.Next(1, 11)会返回1到10之间的随机数。
Load事件在引发任何控件事件之前被引发。
PreRender事件在引发任何控件事件之后被引发。
l IsPostBack属性
使用Page.IsPostBack属性,表示Load事件仅在第一次装载页面时执行代码。
Page控件对象在页面中是默认的。
4. ASP.NET页面的结构
下面列出ASP.NET页面的重要元素的列表:
u 指令
u 代码声明块
u ASP.NET控件
u 代码显示块
u 服务器端注释
u 服务器端包含指令
u 文本和HTML标记
4.1 指令directive
指令控制如何编译ASP.NET页面。(编译指令?)
指令:以<%@开头,以%>结尾。
可以出现在页面任何位置。(但是按惯例,一般在页面的顶部。)
指令分两类:即【页面指令】和【导入指令】
1. 页面指令
功能包括:指定默认的编程语言;为页面启用跟踪和调试。
指定页面语言:<%@ Page Language=”C#” %>
上面指令中的Page关键字是可选的(没有也可以)
跟踪指令Trace:
启用跟踪功能<%@ Page Trace=”True” %>之后,你可以使用Trace类的两个方法(Write和Warn)来跟踪信息。
<%@ Page Language="VB" Debug="true" trace="true" %><%--只能有一个Page指令--%>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<script runat="server">
Sub page_load()
Dim strTraceMessage As String
Trace.Warn("Page_load Event Executing!")
strTraceMessage = "Hello world!"
Trace.Write("the value of strTraceMessage is " & strTraceMessage)
End Sub
</script>
<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
<title>Trace.aspx</title>
</head>
<body>
<form id="form1" runat="server">
<div>
<h2>Testing Page Trace</h2>
</div>
<% Trace.Warn("Rendering Page Content!")%>
<% Trace.Write("Hello")%>
</form>
</body>
</html>
注意:要在页面上显示【运行时错误消息】,需要用到Debug指令(Page的一部分)。 |
在Asp.NET页面中包含以下指令:
<%@ Page Debug=”true” %>(注意值true用引号包裹)
要想启用跟踪功能则要包含Trace指令,如下:
<%@ Page Trace=”true”%>
最好,要注意的是,一个页面只能有一个Page指令,但是以上指令可以组合在一句。
2.导入指令
默认时,ASP.NET页面只能自动导入几个常用名称空间。
或者,也可以对类使用完全限定名称。
4.2 代码声明块
代码声明块,包含ASP.NET页面的所有应用逻辑和所有全局变量声明、子例程和函数。
必须出现在<Script Runat=”server”>标记中。
<Script Runat=”server”>标记接受两个可选的属性。
首先,可以指定使用的语言:<Scipt Language=”C#” runat=”server”>(默认语言是VB)
第二个可选属性是SRC。用来指定包含代码块的外部文件。<Script runat=”server” SRC=”d.aspx”/>
4.3 ASP.NET控件
控件可以随意地散步在页面的(文本和HTML内容之间)。但是要求【控件应该出现在<form runat=“server”>标记内】。
对于某些标记(如<span runat=”server”>和<ASP:Label runat=”server”/>)可以不出现在【form】段。
ASP.NET限定『一个页面只能包括一个form』
4.4 代码显示块(code render block)
用于『在ASP.NET页面的HTML或文本内容中执行代码』
有两种:内嵌代码(inline code)和内嵌表达式(inline expression)
内嵌代码:执行一个或一系列语句。语句开头是字符<%,结尾是%>
内嵌表达式:显示变量或方法的值。(这种代码是Response.Write的缩写形式),开头是<%=,结尾是%>
注意:可以在【代码显示块】内使用代码声明块来声明变量。但是,此变量是被限定了使用范围的。
4.5 服务器端注释
通过服务器端注释(server-side comment)向页面添加注释。
注释的开头字符<%--,结尾--%>
目的是对代码进行说明。
注意:不能用浏览器的View source来查看此注释。
4.6 服务器端包含指令
使用服务器端包含指令(server-side include directive)可以将一个文件包含在ASP.NET页面中。
指令有两种形式:在当前目录或子目录<!--#INCLUDE file=”includefile.aspx”-->
或者提供完整路径<!--#INCLUDE virtual=”/mydir/include.aspx”-->
不能使用变量来指定要包含的文件路径。(这是错误的)<!-- #INCLUDE file”<%=myval%>” -->
如果不使用包含指令,可以用【用户控件】来代替。
4.7 文本和HTML标记
可以包含在ASP.NET中的元素还有HTML内容。
一般的HTML标记和文本构成了页面的静态部分。
页面中的HTML内容会【随其他元素一起编译】。页面中的HTML内容由【LiternalControl类】表示。
可以使用LiternalControl类的Text属性操作页面中的纯HTML部分。