第3章 三层架构项目开发实战 第2章学习的信息管理系统可以理解为二层架构的项目,由用户(界面)直接访问数据 库,这种项目运行效率高,但是如果用户需求发生改变,那么需要改动的地方往往会很多,甚 至项目需要重新开发,也就是说,这种架构的项目不利于后续的维护。本章学习三层架构项 目,三层架构项目有利于后续维护。 学习目标 (1)能够理解三层架构的思想。 (2)能够熟练开发三层架构的项目。 思政目标及设计建议 根据新时代软件工程师应该具备的基本素养,挖掘课程思政元素,有机融入教学中,本 章思政目标及设计建议如表3-1所示。 表3-1 第3章思政目标及设计建议 思政目标思政元素及融入 培养学生职业道德和职业素养 讲解项目为什么要分层时类比到随着企业的发展壮大,也要分 层,以更好地对企业进行管理。三层架构的项目层与层之间访问 是有严格顺序的,启发学生在学习工作中有问题要先找直接领 导,一般不宜越级找领导,培养学生职业道德和职业素养 培养自主探索、敬业、专注的工匠精神通过课前自主学习,培养自主探索、敬业、专注的工匠精神 3.1 三层架构的基础知识 3.1.1 三层架构的理解和作用 在生活中经常会见到分层的现象,例如,公司人员结构会分层,楼房是分层的,甚至做包 子的笼屉都是分层的。虽然分层的目的各有不同,但都是为解决某一问题而产生的。所以, 分层架构其实是为了解决某一问题而产生的一种解决方案。 从社会的发展来看,社会分工是人类进步的表现。社会分工的优势就是让适合的人做 自己擅长的事情,使平均社会劳动时间大大缩短。 第 3 章 三层架构项目开发实战 程序三层架构就是在项目开发过程中根据代码的不同功能,分别对代码进行存储与调 用。通常分为表现层、业务逻辑层、数据访问层,这三层如何理解? 我们通过去大饭店吃饭 来形象的理解。如果到小餐馆吃饭,可能直接叫老板给我们炒菜,最后也是老板自己收钱, 这种情况可以理解为二层架构。如果到大饭店吃饭,我们就是把需求(要点的菜)告诉服务 员,由服务员将顾客的需求转交到厨房,然后由厨师做出相应的菜肴,并由服务员送到顾客 餐桌上。这一过程中,厨师、服务员和顾客这三个角色可以分别表示为数据访问层、业务逻 辑层和表现层,如图3-1所示。在这个过程中,根据顾客的需求不同,更换服务员和厨师都 不影响顾客的需求,同样在项目开发中也是这样。 表现层(UserInterfaceLayer,UIL):主要用于存放与用户交互的展示页面。主要实现 和用户的交互,接收用户请求或返回用户请求的数据结果的展现,而具体的数据处理则交给 业务逻辑层和数据访问层去处理。 业务逻辑层(BusinesLogicLayer,BLL):主要用于存放针对具体问题对数据进行逻 辑处理的代码,起到承上启下的作用。 数据访问层(DataAcesLayer,DAL):主要用于存放对原始数据进行操作的代码,它 封装了所有与数据库交互的操作,并为业务逻辑层提供数据服务。 因此,三层架构可以用图3-2表示,这也是一种最简易的三层架构。 图3- 1 三层架构形象比喻图3- 2 简易三层架构图 实际开发中,很多情况下为了复用一些共同的“东西”,会把各层都用的“东西”抽象出 来。例如,将数据对象实体分离,以便在多个层中传递,称为实体类(Model)。一些共性的 通用辅助类和工具方法,如数据校验、生成验证码、加解密处理等,为了让各个层之间复用, 也单独分离出来,作为独立的模块使用,称为通用类库(Common)。这时三层架构可以用 图3-3表示。 说明: (1)什么是业务实体(Model)? 用于封装实体类数据结构,一般用于映射数据库的数据表或视图,用以描述业务中客观 存在的对象。Model分离出来是为了更好地解耦,为了更好地发挥分层的作用,更好地进行 复用和扩展,增强灵活性。 业务实体也称为实体类或实体模型类,通常类名与映射的数据库的数据表名称一致,该 类中包含一系列属性,这些属性与数据库中的字段一一对应,从数据库中查询出来的数据都 43 ASP.NET 项目实战教程———从.NETFramework到.NETCore 44 使用该类的对象来保存,以便在程序中使用。 (2)为了使数据访问层的代码更加简洁及操作数据库的代码复用,通常数据访问层会 分离出通用数据访问类,即第2章封装的SqlHelper工具类。此时就形成了一个完整经典 的三层架构图,如图3-4所示。 图3-3 三层架构演变图 图3-4 完整经典的三层架构图 3.1.2 三层架构的优缺点 三层架构是一种通用的项目开发方式,可以极大地提高项目的可扩展性和可维护性。 但是使用三层架构也会存在一些缺陷,实际开发中根据项目的大小及客户的需求综合考虑 是否选择三层架构。三层架构的优缺点如表3-2所示。 表3-2 三层架构的优缺点 优 点缺 点 代码结构清晰增加了开发成本 耦合度降低,可维护性和可扩展性提高降低了系统的性能 适应需求的变化,降低维护的成本和 时间 在表现层中增加一个功能,为保证其设计符合分层式结构,就 需要在相应的业务逻辑层和数据访问层中都增加相应的代码 3.2 三层架构项目实战——登录设计与实现 在学习完三层架构的基础知识后,接下来根据前面所学的知识结合ADO.NET以及简 单的WebForm 窗体来实现一个三层架构的学生信息管理系统,本节来完成三层架构的登 录功能。 3.2.1 创建数据库 在ASPNETDemoDataBase数据库下创建一个名为UserLogin的用户登录表,该表的 结构设计如图3-5所示。其中,ID为自增的主键。 为了后面的测试,为UserLogin表输入一条记录,如UserName为admin,Pwd为123456。 第3 章 三层架构项目开发实战 45 图3-5 UserLogin表结构 3.2.2 搭建三层架构的基本结构 三层架构的项目数据库访问层、业务逻辑层、实体模型层项目类型都要为类库(.NET Framework),表现层根据项目的需要可以为WebForm 项目、Windows窗体应用程序等。 1.创建解决方案及数据访问层(DAL) 打开VisualStudio2022,创建新项目,项目模板选择类库(.NETFramework),如图3-6 所示。 图3-6 项目模板选择类库(.NETFramework) 单击“下一步”按钮,打开如图3-7所示的“配置新项目”窗口,在此设置解决方案名称、 项目名称,此项目作为数据库访问层,因此这里项目名称设置为DAL,实际开发中数据访问 层项目名称一般以DAL作为后缀,但是前面可以加解决方案名称之类的。 之后单击“创建”按钮,稍后即可创建好解决方案及项目DAL,如图3-8所示。 2.创建业务逻辑层(BLL) 在图3-8界面中右击解决方案,选择“添加”→“新建项目”,弹出添加新项目的模板,继 续选择“类库(.NETFramework)”,单击“下一步”按钮之后在弹出的界面中设置项目名称 为BLL,作为业务逻辑层。实际开发中,业务逻辑层项目的名称一般以BLL作为后缀,但是 前面可以加解决方案名称之类的。 ASP.NET 项目实战教程———从.k到. NETFrameworNETCore 图3- 7 设置解决方案名称及项目名称 图3- 8 创建了DAL 项目的VisualStudio界面 3. 创建实体模型层(Model) 在图3-8界面中右击解决方案,选择“添加”→“新建项目”,弹出添加新项目的模板,继 续选择“类库(NETFramework)”,单击“下一步”按钮之后在弹出的界面中设置项目名称 为Model,作为实(.) 体模型层。实际开发中,实体模型层项目的名称一般就叫Model。 4. 创建表现层(UI) 在图3-8界面中右击解决方案,选择“添加”→“新建项目”,弹出添加新项目的模板,选 ASP.NETFramewor 择“NETWeb应用程序(k)”,如图39所示。单击“下一步”按钮,配 置项目名称为UI,然后单击“下一(.) 步”按钮,打开如图3-10 所示的对话框,这里选择“空”,即 创建空的ASP. NETWeb应用程序。 46 第 3 章 三层架构项目开发实战 图3创建ASP.b应用程序(NETFaeok)模板项目 - 9 NETWe.rmwr 图3创建空的ASP.b应用程序 -10 NET We 至此,三层架构的项目基本结构就搭建好了。 47 ASP.NET 项目实战教程———从.NETFramework到.NETCore 48 3.2.3 添加各层之间的引用 三层架构各项目之间有严格的访问关系。表现层(UI)只能访问实体模型层(Model)和 业务逻辑层(BLL);业务逻辑层(BLL)只能访问实体模型层(Model)和数据访问层(DAL); 数据访问层(DAL)只能访问实体模型层(Model)。下面添加各层之间的引用。 (1)展开解决方案下面的UI层项目,右击“引用”,选择“添加引用”,弹出如图3-11所 示对话框,在左侧选择项目,然后在右侧勾选BLL和Model,就表示UI层可以访问BLL和 Model层。单击“确定”按钮之后可以看到引用下面多了对BLL和Model程序集的引用。 图3-11 为UI层添加引用 (2)同理展开解决方案下面的BLL项目,右击“引用”,选择“添加引用”,在弹出的对话 框左侧选择项目,然后在右侧勾选DAL和Model,就表示BLL可以访问DAL和Model层。 单击“确定”按钮之后可以看到引用下面多了对DAL和Model程序集的引用。 (3)同理展开解决方案下面的DAL项目,右击“引用”,选择“添加引用”,在弹出的对话 框左侧选择项目,然后在右侧勾选Model,就表示DAL可以访问Model层。单击“确定”按 钮之后可以看到引用下面多了对Model程序集的引用。 3.2.4 编写实体模型层Model 代码 实体模型层就是把数据表转换成对应的实体类,本节只用到UserLogin表,即只要把该表 转换成实体类。在Model层下添加一个类,类名一般与数据表名称相同,即UserLogin.cs。 说明:原有的默认类Class1.cs一般删除。 根据数据表UserLogin的字段在UserLogin.cs中添加对应的属性。同时把类的修饰 符改为public,方便其他项目调用。UserLogin代码如下。 public class UserLogin { public int ID { get; set; } public string UserName { get; set; } public string Pwd { get; set; } } 第3 章 三层架构项目开发实战 49 3.2.5 编写数据访问层代码 1.添加SqlHelper工具类到DAL项目下 为了提高编写代码效率及操作数据库代码的复用,从而使代码也更加简洁,数据访问层 一般需要把访问数据库操作的工具类SqlHelper.cs添加进来。直接复制第2章完成的 SqlHelper工具类到DAL项目下。之后还要做以下两个处理。 1)为SqlHelper工具类添加引用System.Configuration 即打开复制过来的SqlHelper工具类,然后安装System.Configuration.Configuration- Manager包,之后会自动添加引用System.Configuration。 2)为项目配置文件添加连接数据库信息 即打开UI层下的web.config文件,在<configuration>节中添加下面的代码。 <connectionStrings> <add name="connectionStr" connectionString="server=.;uid= sa;pwd= 123456; database=ASPNETDemoDataBase"/> </connectionStrings> 同时检查下<add>标签下的name属性值与SqlHelper工具类下加粗名称是否相同, 需要保持一致。 public static string constr =ConfigurationManager.ConnectionStrings ["connectionStr"].ConnectionString; 2.添加数据访问层类 在DAL下添加一个类,类名一般以DAL作为结尾,前面部分一般是表名称,本数据访 问层主要是针对UserLogin表进行操作,所以这里类名取名为UserLoginDAL.cs。 说明:原有的默认类Class1.cs一般删除。 接下来在该类中添加对UserLogin表进行操作的方法。因为本节要实现的是登录功 能,所以这里编写一个根据用户名去查找用户的方法,返回值为UserLogin对象,具体代码 如下。 public UserLogin SelectUserLogin(string username) { string sql ="select * from UserLogin where userName=@username"; UserLogin user =null; using ( SqlDataReader reader = SqlHelper. ExecuteReader ( sql, new SqlParameter("@username", username))) { if (reader.Read()) { user =new UserLogin(); user.ID =reader.GetInt32(0); user.UserName =reader.GetString(1); user.Pwd =reader.GetString(2); } } ASP.NET 项目实战教程———从.NETFramework到.NETCore 50 return user; } 提示:在上述类中需要添加实体类UserLogin所在命名空间,如果没有默认引用,则需 要手动引用。 3.2.6 编写业务逻辑层代码 数据访问层编写完成后,接下来编写业务逻辑层代码。在BLL项目下创建一个类,命 名为UserLoginBLL.cs,一般以BLL结尾,前面部分为数据表名,同时把默认修饰符改为 public。 由于业务逻辑层肯定需要用到数据访问层对象,所以就需要用数据库访问层类实例化 出一个数据访问层对象。然后再创建业务逻辑层的方法,该方法结构一般可以与数据访问 层下的相应方法结构保持一致,如果修改一般就是修改方法名称和返回值类型。方法体里 面一般需要用到数据访问层对象调用相应方法,具体代码如下。 public class UserLoginBLL { //实例化数据访问层对象 UserLoginDAL dal=new UserLoginDAL(); public UserLogin SelectUserLogin(string username) { return dal.SelectUserLogin(username); } } 3.2.7 实现UI 层 右击UI层项目,选择“添加”→“Web窗体”,窗体文件名取名为Login,单击“确定”按钮 之后即创建了文件名为Login.aspx的Web页面。 1.表现层界面设计 表现层运行效果如图3-12所示。 图3-12 登录效果图 通过表格布局,输入相关文字及引入相关控制,代码如下。 <form id="form1" runat="server"> <div id="divLogin"> <table id="tab"> 第3 章 三层架构项目开发实战 51 <tr> <td colspan="2" id="tdHead">管理员登录</td> </tr> <tr> <td class="td1">用户名:</td> <td > <asp:TextBox ID="txtusername" runat="server" Width= "160px" Height="20px"></asp:TextBox></td> </tr> <tr> <td class="td1">密 码:</td> <td> < asp:TextBox ID="txtpwd" runat="server" Width="160px" Height="20px" TextMode="Password"></asp:TextBox></td> </tr> <tr> <td colspan="2" class="td2"> < asp:Button ID="btnLogin" runat="server" Text="登录" Height="30px" Width="80px" /> <asp:Button ID="btnCancel" runat= "server" Text="取消" Height="30px" Width="80px" /></td> </tr> </table> </div> </form> 为了实现页面居中显示等效果,设置CSS样式如下。 <style type="text/css"> #divLogin { width:300px; height:200px; background-color:cornflowerblue; position:absolute; left:50%; top:50%; margin-top:-150px; margin-left:-100px; } #tab { width:100%; height:100%; } #tdHead{ font-family:微软雅黑; font-size:24px; color:white; ASP.NET 项目实战教程———从.NETFramework到.NETCore 52 text-align:center; } .td1 { height: 45px; width:90px; color:white; font-size:18px; font-family:微软雅黑; text-align:right; } .td2 { text-align:center; } </style> 2.表现层功能实现 UI层的界面设计好了,接下来就实现表现层的功能。单击“登录”按钮时检测用户输入 的用户名在数据库中是否存在,如果存在再看用户输入的密码是否与数据库中该用户的密 码一致,如果一致则可以进入系统,否则给出相应的提示。 由于表现层需要用到业务逻辑层对象,所以需要先实例化出业务逻辑层对象。 UserLoginBLL bll=new UserLoginBLL(); 然后编写“登录”按钮的单击事件如下。 protected void btnLogin_Click(object sender, EventArgs e) { //获取用户输入的用户名和密码 string name =txtusername.Text.Trim(); string pwd =txtpwd.Text.Trim(); if (string.IsNullOrEmpty(name) || string.IsNullOrEmpty(pwd)) { Response.Write("<script>alert('用户名或者密码不能为空!')</script>"); } else { //获取到登录对象 UserLogin user =bll.SelectUserLogin(name); if (user !=null) { //拿数据库里获取的密码与输入的密码对比 if (user.Pwd ==pwd) { //将用户名和密码写入Session 中 Session["UserName"] =user.UserName; Session["Pwd"] =user.Pwd; 第3 章 三层架构项目开发实战 53 //跳转到主页StudentList.aspx,并传递用户名过去 Response.Redirect("StudentList.aspx? UserName=" +name); } else { Response.Write("<script>alert('密码错误!')</script>"); } } else { Response.Write("<script>alert('用户名不存在!')</script>"); } } } 注意:需要导入Model和BLL命名空间。 说明: (1)Get和Post的请求方式。 Get和Post是向服务器发送请求的两种方式,其中,Get请求是将需要提交给服务器的 数据放在URL中,而Post请求则是将请求数据封装到请求报文中进行发送。 请求报文由请求行、请求头部、空行和请求数据4部分组成,其中,请求行中包括请求方 式、URL和HTTP版本三个字段;请求头部是通知服务器有关于客户端请求的信息;空行 用于通知服务器以下不再是请求头;请求数据是使用Post方式发送的数据。 (2)Response对象的使用———用于输出数据的对象。 Response对象用于将服务器响应的数据发送到客户端,此对象中包含有关该响应的信 息,并且通过Response对象的方法可以执行一些特殊操作。例如,通过该对象的Write() 方法可以向页面输出内容。如果传递的参数是普通的字符串,则会被直接输出到页面;当传 递的是“<script>alert(‘输入的内容’)</script>”等内容的字符串参数时,浏览器会将该 字符串当作脚本解析。 通过Response对象的Redirect()方法可以跳转到另一个页面,使用该方法时需要将重 定向的url作为实参传递到该方法中,跳转的url可以通过“?”来传递参数,多个参数之间使 用“&”连接,示例代码如下。 Response.Write("江西服装学院欢迎您!"); Response.Write("<script>alert('密码错误!')</script>"); Response.Redirect("http://www.jift.edu.cn"); Response.Redirect("http://www.jift.edu.cn? Username='admin'"); (3)Request对象的使用———用于接收数据的对象。 Request对象的作用是获取从客户端向服务器端发出的请求信息。根据请求方式的不同, 可以通过三种方式来接收客户端的值,当使用Get方式发送请求时可以通过QueryString 属性来获取值;当用户通过Post方式发送请求时,可以通过Form 属性来获取值;当不确定 请求方式时,可以通过Request对象直接获取值,具体示例代码如下。 ASP.NET 项目实战教程———从.NETFramework到.NETCore 54 string name=Request.QueryString["Name"]; //Get 请求 string name=Request.Form["Name"]; //Post 请求 string name=Request["Name"]; //Get 和Post 请求 接下来为“取消”按钮编写单击事件代码,只需要把两个文本框置空即可,代码如下。 protected void btnCancel_Click(object sender, EventArgs e) { txtusername.Text=string.Empty; txtpwd.Text=string.Empty; } 3.2.8 设置启动项和测试项目运行结果 由于三层架构的解决方案下肯定有很多项目,所以运行测试之前要先设置启动项,右击 解决方案,选择“设置启动项”,弹出如图3-13所示对话框,在此设置“单启动项目”为UI。 图3-13 设置解决方案下的启动项目 然后再右击UI项目下的Login.aspx,选择“设为起始页”。 设置后启动运行出现“检测到在集成的托管管道模式下不适用的ASP.NET 设置”错误 提示,只需要在项目的Web.config配置文件中添加如下代码。 <system.webServer> <validation validateIntegratedModeConfiguration="false" /> </system.webServer> 为了测试运行效果,需要在UI层添加一个名为StudentList.aspx的Web窗体,当用户 名和密码正确时进入该页面。 再次启动运行后,输入正确的用户名和密码后,能够进入主页面StudentList.aspx。其 他情况会给出相应的提示。 第3 章 三层架构项目开发实战 55 3.3 三层架构项目实战——学生信息列表展示页设计与实现 3.2节完成了三层架构的登录,进入的主页面StudentList.aspx是一个空的页面,接下 来把这个页面作为学生信息列表展示页面。所使用的数据表是student表,表结构如 图3-14所示。 图3-14 student表结构 3.3.1 在Model 层添加学生表(student)实体类 在Model层中添加一个名为Student.cs的类文件,并在该文件中创建一个与student 数据表对应的实体类,即Student类中的属性与student表中的字段一一对应。同时把类的 修饰符改为public,方便其他项目调用,具体代码如下。 public class Student { public int ID { get; set; } public string Num { get; set; } public string Name { get; set; } public string Sex { get; set; } //int? 表示可空的值类型 public int? Age { get; set; } public string Class { get; set; } public string Speciality { get; set; } public string Phone { get; set; } } 3.3.2 在数据访问层查询学生表(student)数据 在DAL中添加一个名为StudentDAL.cs的类文件,类的修饰符改为public,在该类中 封装对student表的增、删、改、查操作的代码。在该类中定义一个GetAllStudent()方法, 该方法用于查询student表中的所有数据,具体代码如下。 public List<Student> GetAllStudent() { string sql ="select * from student"; List<Student> studentList =new List<Student>(); using (SqlDataReader reader =SqlHelper.ExecuteReader(sql)) //提示:正常该方法有两个参数,即(sql,null),但可变参数为空时可以不写 ASP.NET 项目实战教程———从.NETFramework到.NETCore 56 { if (reader.HasRows) { while (reader.Read()) { Student stu =new Student(); stu.ID =reader.GetInt32(0); stu.Num =reader.GetString(1); stu.Name =reader.GetString(2); stu.Sex = Convert. IsDBNull ( reader [3]) ? null : reader. GetString(3); stu.Age = Convert. IsDBNull ( reader [4]) ? null : ( int? ) reader.GetInt32(4); stu.Class =reader.GetString(5); stu.Speciality =reader.GetString(6); stu.Phone = Convert.IsDBNull(reader[7]) ? null : reader. GetString(7); studentList.Add(stu); } } } return studentList; } 在上述代码中,GetAllStudent()方法调用了SqlHelper的ExecuteReader()方法查询 数据,并将查询到的数据封装到泛型集合List<Student>中,并作为返回值返回。其中,在 查询数据时取出数据表中可为空的类型列的数据赋给对象属性时,需要先通过Convert. IsDBNull()方法判断再赋值。 提示:int类型与null值不是同类型,在进行三元运算时需要将int类型强制转换成 int? 类型。 3.3.3 在业务逻辑层利用数据访问层查询学生表(student)数据 在BLL中添加一个名为StudentBLL.cs的类文件,类的修饰符改为public,在该类中也 是封装对student表的增、删、改、查操作的代码,但是是通过数据访问层对象调用数据访问 层的方法,只不过是在业务逻辑层对数据访问层的方法进行了一次封装。在该类中定义的 方法结构可以与数据访问层的保持一致,具体代码如下。 StudentDAL dal =new StudentDAL(); public List<Student> GetAllStudent() { return dal.GetAllStudent(); } 3.3.4 在表现层调用业务逻辑层 在UI层的StudentList.aspx.cs文件的Page_Load()事件中编写代码,该事件在页面加 载时触发,触发时将所有数据加载到页面中,具体代码如下。 第3 章 三层架构项目开发实战 57 StudentBLL bll=new StudentBLL(); protected void Page_Load(object sender, EventArgs e) { if (Session["UserName"] ==null) { Response.Redirect("/Login.aspx"); } else { List<Student> studentlist =bll.GetAllStudent(); StringBuilder sb =new StringBuilder(); //创建用于拼接表格的 //StringBuilder 对象 int count =1; //表格中的编号 sb.Append( " < div style = ' position: absolute; top: 25%; left: 50%; background-color:cornflowerblue; margin- left:- 400px;'> < table style= 'width: 800px;border- collapse:collapse; text- align:center;' border= '1px solid black'> <tr><th>编号</th><th>学号</th><th>姓名</th><th>性别</th> < th> 年龄</th> < th> 班级</th><th>专业</th><th>电话</th><th>操作</th></tr>"); foreach (var item in studentlist) { sb.Append(string.Format("< tr> < td> {0}</td> < td> {1}</td> <td> {2}</td><td>{3}</td><td>{4}</td><td>{5}</td><td>{6}</td><td>{7}</td><td> <a onclick= 'return confirm(\"确定要删除吗? \")' href= 'DeleteStudent.ashx? ID= {8}'>删除</a> < a href= 'UpdateStudent.aspx? ID= {8}'> 修改</a> </td> </tr >", count + +, item. Num, item. Name, item. Sex, item. Age, item. Class, item.Speciality, item.Phone, item.ID)); } sb.Append("< tr> < td colspan= '9' style= 'text- align:left'> < a href='AddStudent.aspx'>添加用户</a></td></tr></table></div>"); Response.Write(sb.ToString()); } } 在上述代码的Page_Load()事件中,首先通过判断Session["UserName"]是否为null, 判断用户是否登录,如果登录了,通过调用bll的GetAllStudent()方法获取数据集合,遍历 集合并将值拼接成表格输出到页面。 3.3.5 添加页面导航栏 为了使页面功能更加完整,在StudentList.aspx页面的<body>标签内添加页面导航 栏功能布局代码,包括显示登录的用户名、网站主页链接、修改密码链接和用户注销链接,具 体代码如下。 <body> <form id="form1" runat="server"> <div id="box"> <div id="left"> 您好:<%=Session ASP.NET 项目实战教程———从.NETFramework到.NETCore 58 ["UserName"].ToString() %>,欢迎使用学生信息管理系统</div> <div id="right"> <a href =" StudentList. aspx" > 网站主页</a > <a href="UpdatePassword.aspx">修改密码</a> <a href="temp.aspx">注销退出</a> </div> </div> </form> </body> 说明:“<%=%>”用于读取Session中的用户名并展示到页面上。 添加布局样式,在UI层下创建文件夹Style,再在该文件夹下创建一个样式表文件 NavigateStyle.css,并添加如下样式。 body { margin: 0px; }# box { width: 100%; background-color:cornflowerblue; height: 80px; line-height: 80px; font-family: "微软雅黑"; }# left { width: 60%; float: left; }# right { text-align: right; width: 40%; float: left; } a:link { color: #fff; text-decoration: none; font-family: 微软雅黑; } a:hover { color: #f00; text-decoration: none; font-family: 微软雅黑; } 启动运行,登录成功后看到的效果如图3-15所示。 第3 章 三层架构项目开发实战 59 图3-15 学生信息管理系统主页面效果 3.4 三层架构项目实战——添加学生信息设计与实现 本节实现三层架构的添加学生信息功能。在UI层项目下添加一个名为AddStudent.aspx 的Web窗体。 3.4.1 设计添加学生信息的界面 添加学生信息界面如图3-16所示。 图3-16 添加学生信息界面 1.导航栏部分设计 该部分设计与主页StudentList.aspx的导航栏一样,直接复制相关代码与样式即可。 2.引入添加学生信息的控件及布局 采用表格布局,从工具箱中拖入6个TextBox 控件、2个RadioButton控件和2个Button 控件,并修改ID等属性。 然后编写样式,最终参考代码如下。 (1)样式代码,其中,NavigateStyle.css样式见3.3节。 <link href="Style/NavigateStyle.css" rel="stylesheet" /> <style type="text/css"> #divLogin { background-color:cornflowerblue; ASP.NET 项目实战教程———从.NETFramework到.NETCore 60 width: 550px; height: 300px; left: 50%; margin-left: -275px; top: 50%; margin-top: -150px; position: absolute; } #tb { width: 100%; height: 100%; } #td1 { height: 70px; font-family: 微软雅黑; color: white; font-size: 28px; text-align:center; } .td2 { height: 40px; font-family: 微软雅黑; color: white; font-size: 20px; text-align: right; } #td3 { height:56px; text-align: center; } </style> (2)HTML代码。 <form id="form1" runat="server"> <div id="box"> <div id =" left " > 您好:<% = Session [ " UserName"].ToString() %>,欢迎使用学生信息管理系统</div> <div id="right"> <a href =" StudentList. aspx" > 网站主页</a > 第3 章 三层架构项目开发实战 61 <a href="UpdatePassword.aspx"> 修改密码</a> <a href="temp.aspx">注销退出</a> </div> </div> <div id="divLogin"> <table id="tb" style="border-collapse: collapse;"> <tr> <td id="td1" colspan="4">添加信息</td> </tr> <tr> <td class="td2">学号:</td> <td> <asp:TextBox ID="txtStuNum" runat="server" Width="150px"> </asp:TextBox></td> <td class="td2">姓名:</td> <td> <asp:TextBox ID="txtStuName" runat="server" Width="150px"> </asp:TextBox></td> </tr> <tr> <td class="td2">班级:</td> <td> <asp:TextBox ID="txtStuClass" runat="server" Width= "150px"></asp:TextBox></td> <td class="td2">专业:</td> <td> <asp:TextBox ID="txtSpeciality" runat="server" Width= "150px"></asp:TextBox></td> </tr> <tr> <td class="td2">年龄:</td> <td> <asp:TextBox ID="txtStuAge" runat="server" Width= "150px"></asp:TextBox></td> <td class="td2">电话:</td> <td> <asp:TextBox ID="txtStuPhone" runat="server" Width= "150px"></asp:TextBox></td> </tr> <tr> <td class="td2">性别:</td> <td colspan="2" class="td2" style="text-align: center;"> < asp:RadioButton ID="radbtnB" runat="server" Text= "男" GroupName="xb" /> < asp: RadioButton ID="radbtnG" runat="server" Text="女" GroupName="xb" /></td> <td></td> </tr> <tr>