AJAX 扩展控件:与弹出窗口中的控件列表进行交互






4.17/5 (3投票s)
创建带弹出窗口的 AJAX 扩展控件
引言
Microsoft 的 AJAX 扩展控件增强了标准 ASP.NET Web 服务器控件的客户端功能。在上一篇文章中,我描述了一个与弹出窗口的简单内容交互的 AJAX 扩展控件。本文提供了一个示例,其中 AJAX 扩展控件“tbox”与弹出窗口中的 HTML DOM “select”元素列表进行交互。扩展控件是在 Visual Studio 2005 中开发的。
该应用程序创建了两个自定义扩展控件“tbox”的实例,并将它们与 TextBox ASP.NET 服务器控件关联起来,这些控件能够从弹出窗口的 <select>
元素中选择内容到 HTML DOM <input>
元素(由 TextBox 控件渲染)。弹出窗口是动态创建的,包含 HTML <div>
、<select>
和 <option>
元素。为了简化示例,<select>
元素的数据位于一个三维数组 string[][][] string_array
中。第一维决定了数据列表的数量。第二维 - 数据列表中的 <select>
元素数量。第三维 - <select>
元素中“选项”的数量。第一维是显式指定的,第二维和第三维由数据量决定。扩展控件“tbox”的属性可以在 Default.aspx 页面中设置,也可以在代码中动态设置。
该示例展示了从汽车制造商列表中选择汽车品牌,以及从调色板列表中选择颜色。
Using the Code
应用程序由以下部分组成:
- AJAX 扩展控件“tbox”,文件:/App_Code/tbox.cs,/JavaScripts/tbox.js
- Java Script 函数
- 服务函数,文件:/JavaScripts/funclib.js
- 用户函数,文件:/JavaScripts/user_functions.js
- 外部样式表,文件:/App_Themes/Basic/Default.css
- 默认页面“Default.aspx”
AJAX 扩展控件“tbox”
扩展控件是一个 Web 服务器控件,它继承自 System.Web.UI 命名空间中的 extender control 抽象类,并封装了客户端和服务器端代码。控件的主要目的是通过包装现有控件来提供新功能 - 在本例中是 TextBox Web 服务器控件。相关的 HTML DOM 元素作为参数传递给“tbox”扩展控件的构造函数。
下面简要介绍扩展控件“tbox”的客户端和服务器端代码。
客户端
客户端行为类
文件 /JavaScripts/tbox.js 描述了“tbox”扩展控件在“Demo”命名空间下的客户端行为类。属性
list_number
- 指示在弹出窗口中使用的字符串数组。winheight
- 弹出窗口的高度。winwidth
- 弹出窗口的宽度。backgroundcolor
- HTML 元素 <div> 的背景颜色。fontcolor
- HTML 元素 <select> 的字体颜色。fontsize
- HTML 元素 <select> 的字体大小。
事件和委托
- select - 客户端事件。事件处理程序由服务器端属性“
ClientFunction
”确定。 _selectDelegate
- HTML DOM 事件“mouseover
”的委托。_selectDelegate1
- HTML DOM 事件“mouseout
”的委托。
_selectHandler: function(event) {
var h = this.get_events().getHandler('select');
if (h) h(this);
}
当鼠标指针移动到 TextBox 元素上时,会触发 HTML DOM“mouseover
”事件。事件处理程序“_selectHandler
”会触发客户端事件“select”。客户端事件“select”的事件处理程序由“tbox”扩展控件的服务器端属性“ClientFunction
”确定。
Java Script 函数
文件 /JavaScripts/user_functions.js 包含用户函数 onSelect(_this)
。
函数接受 1 个参数:
_this
- 指向客户端行为类对象的指针。
function onSelect(_this)
{
var list_number = _this._listnumber - 1;
var xname = "divContext" + _this._listnumber;
var element = _this.get_element();
var xdiv=document.getElementById(xname);
if (xdiv === null)
{
alert("Property: ListNumber=\"" + list_number + "\" - number is out of range!");
return;
}
showDropDown(element, xdiv);
}
此函数是客户端事件“select”的事件处理程序。该函数的主要目的是调用“showDropDown()
”函数,该函数为 TextBox 元素创建弹出窗口,但也可以添加其他功能。函数名“onSelect
”是在 Default.aspx 页面中作为“tbox
”扩展控件的服务器端属性“ClientFunction
”确定的。弹出窗口的隐藏内容由函数“create_WinContent()
”动态创建,该函数位于页面“Default.aspx.cs”中。此函数根据数组“string_array[][][]
”中的数据创建多个 HTML 元素:<div>
、<select>
、<option>
,其中“汽车品牌”和“颜色”的数据由用户定义。每个 <select>
元素封装了一组数据。数据组中的第一个元素代表“组名”。对于汽车组,它是“制造商”;对于颜色组,它是“调色板”。
文件“/JavaScripts/funclib.js”包含函数“showDropDown()
”,该函数在 HTML DOM <input>
元素(由 TextBox 服务器控件渲染)的底部创建一个弹出窗口,并动态地将客户端函数“get_selected_value()
”作为每个 HTML DOM <select>
元素的“onchange
”事件的处理器。
函数“get_selected_value
”接受 2 个参数:
- this - Select 对象的指针。对于表单中的每个 HTML
<select>
标签实例,都会自动创建一个 Select 对象。 element.id
- “TextBox”服务器控件的 ID。
function showDropDown(element, win_content)
{
var oPopup = window.createPopup();
oPopup.document.body.innerHTML = win_content.innerHTML;
var list = oPopup.document.getElementsByTagName('select');
for(var i = 0; i < list.length; i++)
{
list[i].onchange = new Function("get_selected_value(this," + "\"" +
element.id + "\");");
}
var xdiv = oPopup.document.getElementsByTagName('div');
var str_divheight = xdiv[0].style.height;
var win_height = (str_divheight.substr(0,str_divheight.length -2))*1;
var str_divwidth = xdiv[0].style.width;
var divwidth = (str_divwidth.substr(0,str_divwidth.length -2))*1;
var srcollbar_width = getScrollBarWidth();
var win_width = divwidth + srcollbar_width;
var xheight = element.offsetHeight ;
oPopup.show(0, xheight, win_width, win_height, element);
}
函数“get_selected_value(selected_element,txtbox)
”在用户从弹出窗口中的 HTML <select>
元素中选择值时,将该值赋给 HTML DOM <input>
元素。如果选定的值是一种属于颜色调色板的颜色,该值还将为 HTML DOM <input>
元素设置背景颜色和字体颜色。字体颜色根据背景颜色设置为黑色或白色。“<select>
”元素的“选定值”被赋给“组名”值。这可以防止用户选择“组名”值,因为这种操作无法触发 <select>
元素的“onchange”事件。
function get_selected_value(selected_element,txtbox)
{
var idx = selected_element.selectedIndex;
var selected_value = selected_element.options[idx].value;
document.getElementById(txtbox).setAttribute("value",selected_value);
var opt = selected_element.options[0].value;
if (opt.indexOf("Palette") >= 0)
{
document.getElementById(txtbox).style.color='black';
document.getElementById(txtbox).style.backgroundColor=selected_value;
if ((selected_value.indexOf("dark") >= 0) ||
(selected_value.indexOf("black")>= 0) ||
(selected_value.indexOf("gray")>= 0) ||
(selected_value.indexOf("brown")>= 0) ||
(selected_value.indexOf("red")>= 0) ||
(selected_value.indexOf("blue")>= 0))
{
document.getElementById(txtbox).style.color='white';
}
}
selected_element.setAttribute("selectedIndex",0);
}
服务器端
文件 /App_Code/tbox.cs 以类“tbox”的形式描述了“tbox”扩展控件的服务器端代码,它位于“Demo.CS”命名空间中。类“tbox”继承自 System.Web.UI
命名空间中的 ExtenderControl
抽象类。
属性
ListNumber
- 指示在弹出窗口中使用的字符串数组。WinHeight
- 弹出窗口的高度。WinWidth
- 弹出窗口的宽度。FontColor
- HTML 元素 <select> 的字体颜色。FontSize
- HTML 元素 <select> 的字体大小。BackgroundColor
- HTML 元素 <div> 的背景颜色。ClientFunction
- 作为客户端事件“select”处理程序的 Java Script 客户端函数名称。TargetControlID
- 应用了扩展控件的 Web 服务器控件的 ID。此属性是从基类ExtenderControl
抽象类继承的。
ExtenderControl
抽象类的 GetScriptReferences()
方法返回一个 ScriptReference
对象集合,其中包含有关要包含在控件中的客户端脚本库的信息。
protected override IEnumerable<ScriptReference> GetScriptReferences()
{
ScriptReference reference = new ScriptReference();
reference.Path = ResolveClientUrl("~/JavaScripts/tbox.js");
return new ScriptReference[] { reference };
}
ExtenderControl
抽象类的 GetScriptDescriptors()
方法定义了客户端行为类型的实例。此方法用于确定客户端行为的属性值,这些值从服务器上的扩展控件属性中获取。它还添加客户端事件“select”,并提供客户端函数名作为事件处理程序。
protected override IEnumerable<ScriptDescriptor> GetScriptDescriptors(
Control targetControl)
{
ScriptBehaviorDescriptor descriptor = new ScriptBehaviorDescriptor("Demo.tbox",
targetControl.ClientID);
descriptor.AddProperty("list_number", this.ListNumber);
descriptor.AddProperty("winheight", this.WinHeight);
descriptor.AddProperty("winwidth", this.WinWidth);
descriptor.AddProperty("fontcolor", this.FontColor);
descriptor.AddProperty("fontsize", this.FontSize);
descriptor.AddProperty("backgroundcolor", this.BackgroundColor);
descriptor.AddEvent("select", this.ClientFunction);
return new ScriptDescriptor[] { descriptor };
}
默认页面“Default.aspx”
在“Default.aspx”页面上:- 指示“Theme”类型,注册命名空间和扩展控件的标签前缀。
<%@ Page Language="C#" AutoEventWireup="true" CodeFile="Default.aspx.cs" Inherits="_Default" Theme="Basic" %> <%@ Register Namespace="Demo.CS" TagPrefix="sample" %>
- 通过注册 ScriptReference 对象将 JavaScript 文件包含在页面中。
<asp:ScriptManager ID="ScriptManager1" runat="server" > <Scripts> <asp:ScriptReference Path="~\JavaScripts\funclib.js" /> <asp:ScriptReference Path="~\JavaScripts\user_functions.js" /> </Scripts> </asp:ScriptManager>
- 为每个控件指示属性值。例如:
<sample:tbox runat="server" ListNumber="0" WinHeight = "140" WinWidth = "230" FontColor = "#000000" FontSize = "11" BackgroundColor = "#e4e4e4" ClientFunction="onSelect" TargetControlID="TextBox1" ID="Tbox1" />
- 创建弹出窗口的隐藏内容,文件:“Default.aspx.cs”,函数:“
create_WinContent()
”。