Visual Studio 2010, .NET Framework 4.0 尝试手动将 AjaxControlToolkit CascadingDropDown 扩展器动态添加到网页。该网页有一个占位符。当它回发时,控件会动态构建并添加到占位符中。我有想要添加 CascadingDropDown 扩展器的常规 ASP.NET 下拉列表框。
myCascadingDropDown = New AjaxControlToolkit.CascadingDropDown
myCascadingDropDown.ID = "cdd_" & myDisplayedField.ControlID
myCascadingDropDown.BehaviorID = "cdd_" & myDisplayedField.ControlID
myCascadingDropDown.TargetControlID = myDisplayedField.ControlID
myCascadingDropDown.Category = myDisplayedField.ControlID
myCascadingDropDown.PromptText = "Select " & aField.Caption
myCascadingDropDown.ServicePath = "CascadingDropDown.asmx"
myCascadingDropDown.ServiceMethod = "DropDownListBoxChanged"
myPanelForFields.Controls.Add(myCascadingDropDown)
错误是添加 CascadingDropDown 的最后一行。错误是:
值不能为空。参数:没有为扩展器
name
设置目标控制。CascadingDropDown
如果您查看 myCascadingDropDown 上的 TargetControl 属性,它为空(无)。但是你不能设置它(它是只读的)。我假设因为我设置了 TargetControlID,所以 ASP.NET 会从 TargetControlID 设置 TargetControl。
有什么想法或建议吗?
更完整的异常:
System.ArgumentNullException 未被用户代码处理 Message=Value 不能为空。
参数名称:没有为 CascadingDropDown 扩展器设置目标控件。ParamName=没有为 CascadingDropDown 扩展器设置目标控件。
Source=AjaxControlToolkit
StackTrace:
在 AjaxControlToolkit.CascadingDropDown.CascadingDropDown_ClientStateValuesLoaded(Object sender, EventArgs e)
在 AjaxControlToolkit.ExtenderControlBase.LoadClientStateValues()
在 AjaxControlToolkit.ExtenderControlBase.OnLoad(EventArgs e)
在 System.Web.UI.Control.LoadRecursive()
在 System .Web.UI.Control.AddedControl(控制控件,Int32 索引)
在 System.Web.UI.ControlCollection.Add(控制子)
VB.NET 中的答案:
Yuriy Rozhovetskiy 做到了。我在 vb.net 中编程这个应用程序,所以首先我创建了一个全局变量(我在这个类中的函数是共享/静态的):
Shared ControlToResolve As System.Web.UI.Control
然后我创建的代码是:
myCascadingDropDown = New AjaxControlToolkit.CascadingDropDown
myCascadingDropDown.ID = "cdd_" & myDisplayedField.ControlID
myCascadingDropDown.BehaviorID = "cdd_" & myDisplayedField.ControlID
myCascadingDropDown.TargetControlID = myDisplayedField.ControlID
myCascadingDropDown.Category = myDisplayedField.ControlID
myCascadingDropDown.PromptText = "Select " & aField.Caption
myCascadingDropDown.ServicePath = "CascadingDropDown.asmx"
myCascadingDropDown.ServiceMethod = "DropDownListBoxChanged"
ControlToResolve = myBSCComboBox
AddHandler myCascadingDropDown.ResolveControlID, AddressOf myCascadingDropDown_ResolveControlID
myPanelForFields.Controls.Add(myCascadingDropDown)
那么处理程序是:
Shared Sub myCascadingDropDown_ResolveControlID(sender As Object, e As ResolveControlEventArgs)
e.Control = ControlToResolve
End Sub
我将 CascadingDropDown 的 TargetControl 定义为“ControlToResolve”。在将 CascadingDropDown 添加到包含控件的面板之前,我将 ControlToResolve 设置为目标下拉列表框。当我添加 CascadingDropDown 时,它调用处理程序 myCascadingDropDown_ResolveControlID 将下拉列表框分配给 CascadingDropDown.Target
我的网络服务看起来像:
<System.Web.Services.WebService(Namespace:="http://tempuri.org/")> _
<System.Web.Services.WebServiceBinding(ConformsTo:=WsiProfiles.BasicProfile1_1)> _
<System.Web.Script.Services.ScriptService()> _
<ToolboxItem(False)> _
Public Class CascadingDropDown
Inherits System.Web.Services.WebService
<WebMethod(EnableSession:=True)> _
Public Function DropDownListBoxChanged(ByVal knownCategoryValues As String, ByVal category As String) As CascadingDropDownNameValue()
End Function
每次我需要下拉列表框中的一个值时,它都会使用我的 ControlID 调用此 Web 服务。顺便说一句 - 使用 ControlID 我可以判断哪个下拉列表框需要数据,如果它是父或子下拉列表框并且可以获取数据。