我向你展示了一个小小的谜......以下控件的目的是每次都无法验证,无论如何,但它不会:
public class Test : CompositeControl
{
protected override void CreateChildControls()
{
Controls.Clear();
CreateControlHierachy();
ClearChildViewState();
}
void CreateControlHierachy()
{
var validator = new CustomValidator
{
ErrorMessage = "Can't do that!"
};
validator.ServerValidate += (sender, e) =>
{
e.IsValid = false;
};
Controls.Add(validator);
}
}
要“修复”此问题,请将以下行添加到CreateControlHierachy,并且所有内容都按预期工作:
Controls.Add(new TextBox());
该控件已在web.config中注册,并放在一个简单的页面上,如下所示:
<uc:Test runat="server" />
在回发事件上使用调试器会显示以下内容:
TextBox对验证器有什么影响以及解决此问题的正确方法是什么?
答案 0 :(得分:1)
我找到了可能的解释。 TextBox的存在为您的控件添加了一个子控件,即IPostbackDataHandler。为了加载发布数据,页面必须首先通过调用FindControl来找到控件,当然这是控件。当FindControl做它的事情时,它最终会访问你的控件的Controls集合。因为您的控件是CompositeControl,所以它调用EnsureChildControls调用CreateChildControls。
所有这些都在验证之前发生。取出TextBox并且在验证之前不再访问Controls集合,因此在验证之后才会创建验证器(很可能在预渲染期间)
由于您的验证器在验证阶段不存在,因此不会调用它。我建议在验证发生之前添加对EnsureChildControls的调用。
protected override void OnLoad(EventArgs e)
{
EnsureChildControls();
base.OnLoad(e);
}