当前位置: 首页 > 图文教程 > 网络编程 > ASP.NET > ASP.NET2.0服务器控件之创建复杂属性

ASP.NET
Asp.net利用JQuery弹出层加载数据代码
asp.net dataview做无限极分类的又一用法
asp.net ckeditor编辑器的使用方法
告别ADO.NET实现应用系统无缝切换的烦恼(总结篇)
asp.net 实现动态显示当前时间(不用javascript不考虑开销)
.net动态显示当前时间(客户端javascript)
asp.net 结合YUI 3.0小示例
asp.net 取消缓存相关问题说明
asp.net 计划任务管理程序实现,多线程任务加载
ASP.NET 跨页面传值方法
asp.net中url地址传送中文参数时的两种解决方案
Asp.net 菜单控件简洁版
asp.net jQuery Ajax用户登录功能的实现
asp.net SharpZipLib的压缩与解压问题
asp.net url重写后页面回传问题
asp.net与Discuz!NT整合集成实例教程
Discuz!NT 3与asp.net 整合的实例教程
测试控制台使用方法
.net 动态标题实现方法
asp.net *.ashx类型的文件使用说明

ASP.NET2.0服务器控件之创建复杂属性


出处:互联网   整理: 软晨网(RuanChen.com)   发布: 2009-08-14   浏览: 87 ::
收藏到网摘: n/a

本文详细讲解了一个利用ASP.NET 2.0技术创建复杂属性的示例。

1、示例应用

本文所实现的示例很简单,其核心是通过实现自定义服务器控件的连字符形式复杂属性来说明复杂属性的实现方法,其中使用了上一篇文章中介绍的内容。

页面显示了公司所在城市、姓名、性别和职务信息。这些内容是定义服务器控件呈现的结果,其中公司所在城市由简单属性City设置,姓名、性别和职务由复杂属性Employee设置,其中包括子属性Name,Sex和Title设置。下面列举了示例应用程序的Default.aspx文件源代码。

以下为引用的内容:
<%@ Page Language="C#" AutoEventWireup="true" CodeFile="Default.aspx.cs" Inherits="_Default" %>
<%@ Register Namespace="WebControlLibrary" Assembly="WebControlLibrary" TagPrefix="Cp" %>
<!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>实现连字符形式复杂属性</title>
</head>
<body>
<form id="form1" runat="server">
<div>
<Cp:Company ID="demo1" runat="server" City="重庆" Employee-Name="小李" Employee-Sex="男" Employee-Title="销售经理" />
</div>
</form>
</body>
</html>

如上代码所示,主要设置了@ Register指令和自定义服务器控件Company。前者用于为页面引入自定义服务器控件Company,从而实现控件在页面中的应用。在自定义服务器控件Company中主要设置了City、Employee-Name、Employee-Sex和Employee-Title。同时,在开发人员编码过程中将会发现,以上4个属性均为Visual Studio 2005的智能感知功能所支持。

另外,读者还可以以另一种非连字符形式设置Company控件属性。具体代码如下所示:

以下为引用的内容:
<Cp:Company ID="Company1" runat="server" City="重庆">
<Employee Name="小李" Sex="男" Title="销售经理">
</Employee>
</Cp:Company>

实际上,以上设置Company控件属性的方法与前文利用连字符设置属性的方法是完全一致的。对于所有连字符形式属性,可以任意使用二者之一。如果是基于代码可读性的角度而言,后者比前者的可读性更强一些。

2、实现方法

上一小节中的Default.aspx页面所包含的Company控件具有3个连字符形式复杂属性。它们是如何实现的呢?实际上,实现这种形式的复杂属性关键是,在自定义服务器控件实现过程中,对复杂属性及其子属性设置特定的设计时元数据。

对于复杂属性而言,主要在该属性实现前设置两个设计时元数据:DesignerSerializationVisibility和NotifyParentProperty。DesignerSerializationVisibility用于指定在设计时序列化组件上的属性时,所使用的持久性类型。NotifyParentProperty可使得属性浏览器中对子属性的修改通知一直上传到对象模型,并在被修改了子属性的控件中产生修改通知。对于子属性的设计时元数据设置比较简单,只需在子属性实现前设置一个NotifyParentProperty即可。

实现自定义服务器控件Company涉及两个文件:Company.cs和Employee.cs。前者是自定义服务器控件的实现主体,其中包括各种属性设置、控件呈现方法RenderContents等等。后者用于实现复杂属性Employee。下面首先列举了Company.cs文件源代码。

以下为引用的内容:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Text;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
namespace WebControlLibrary{
 [DefaultProperty("Text")]
 [ToolboxData("<{0}:Company runat=server></{0}:Company>")]
 public class Company : WebControl {
  private Employee employee; //实现属性City
  [ Bindable(true), Category("Appearance"), DefaultValue(""), Description("公司所在城市") ]
  public string City {
   get {
    string _city = (String)ViewState["City"];
    return ((_city == null)?String.Empty:_city);
   }
   set { ViewState["City"] = value; }
  } //实现属性Employee

  [ Bindable(true), Category("Appearance"), Description("员工信息"), DesignerSerializationVisibility( DesignerSerializationVisibility.Content), NotifyParentProperty(true) ]

  public Employee Employee {
   get {
    if (employee == null) {
     employee = new Employee();
    }
    return employee;
   }
  } // 重写RenderContents方法,自定义实现控件呈现

  protected override void RenderContents(HtmlTextWriter output) {
   output.Write("公司所在城市:");
   output.Write(City);
   output.WriteBreak();
   output.Write("姓名:");
   output.Write(Employee.Name.ToString());
   output.WriteBreak();
   output.Write("性别:");
   output.Write(Employee.Sex.ToString());
   output.WriteBreak();
   output.Write("职务:");
   output.Write(Employee.Title.ToString());
  }
 }
}

以上代码显示了自定义服务器控件Company的实现,其中主要包括了一些属性和RenderContents方法的内容。具体属性包括2个:一个是简单属性City,另一个是复杂属性Employee。简单属性City的实现使用了视图状态ViewState。复杂属性Employee则有些特别,其类型是一个类Employee。同时,该属性还设置了两个元数据属性:DesignerSerializationVisibility(DesignerSerializationVisibility.Content)和NotifyParentProperty(true)。前者可用于指定序列化程序应该序列化属性的内容即子属性,后者则可使得属性浏览器中对子属性的修改通知一直上传到对象模型,并在被修改了子属性的控件中产生修改通知。以上两个设计时元数据属性的设置是实现连字符形式复杂属性的关键之一。另一个关键之处在于为在实现复杂属性的子属性时未其设置元数据属性。

下面列举了具体实现复杂属性Employee的Employee.cs文件源代码。

以下为引用的内容:

using System;
using System.Collections;
using System.ComponentModel;
using System.Globalization;
using System.Web.UI;
namespace WebControlLibrary{
 public class Employee {
  private string _name;
  private string _sex;
  private string _title; //实现构造函数1
  public Employee() { } //实现构造函数2
  public Employee(String Name, String Sex, String Title) {
   _name = Name; _sex = Sex; _title = Title;
  } //实现属性Name
  [ Bindable(true), Category("Appearance"), DefaultValue(""), Description("员工姓名"), NotifyParentProperty(true) ]

  public String Name {
   get { return _name; }
   set { _name = value; }
  } //实现属性Sex

  [ Bindable(true), Category("Appearance"), DefaultValue(""), Description("员工性别"), NotifyParentProperty(true) ]

  public String Sex {
   get { return _sex; }
   set { _sex = value; }
  } //实现属性Title

  [ Bindable(true), Category("Appearance"), DefaultValue(""), Description("员工职务"), NotifyParentProperty(true) ]

  public String Title {
   get { return _title; }
   set { _title = value; }
  }
 }
}

以上代码实现了Employee类,其中包括构造函数和属性Name、Sex和Title。读者需要注意,为了实现连字符形式复杂属性,以上3个属性都必须设置元数据属性NotifyParentProperty(true)。这样,当子属性发生修改时,.NET框架将自动产生修改通知,并且通知到父属性Employee。

3、小结

本文通过一个典型示例介绍了创建连字符形式复杂属性的实现方法。对于其他形式的复杂属性,例如,内部嵌套形式复杂属性、内部嵌套形式默认复杂属性等,本文将不再做更多解释。实际上,实现复杂属性是有其自身规律可循的。只要读者能够按照规定的方法实现,基本上都不会出现太大的问题。