有选择地禁用WebControl元素

时间:2011-01-07 16:42:31

标签: asp.net web-controls

我有一个带有PlaceHolder元素的ASP.Net MasterPage。 可以通过两种模式查看PlaceHolder的内容:读写和只读。

要实现只读,我想禁用PlaceHolder中的所有输入 我决定通过递归循环遍历PlaceHolder的控件集合,查找从WebControl继承的所有内容,并设置control.Enabled = false;来完成此任务。

这是我最初写的:

private void DisableControls(Control c)
{
    if (c.GetType().IsSubclassOf(typeof(WebControl)))
    {
        WebControl wc = c as WebControl;
        wc.Enabled = false;
    }

    //Also disable all child controls.
    foreach (Control child in c.Controls)
    {
        DisableControls(child);
    }
}

这很好用,所有控件都被禁用......但随后要求改变了;)
现在,我们要禁用所有控件,除了具有某个CssClass的控件。

所以,我第一次尝试新版本:

private void DisableControls(Control c)
{
    if (c.GetType().IsSubclassOf(typeof(WebControl)))
    {
        WebControl wc = c as WebControl;
        if (!wc.CssClass.ToLower().Contains("someclass"))
            wc.Enabled = false;
    }

    //Also disable all child controls.
    foreach (Control child in c.Controls)
    {
        DisableControls(child);
    }
}

现在我遇到了问题。如果我(例如)<ASP:Panel>包含<ASP:DropDownList>,并且我想保持启用DropDownList,那么这不起作用。

我在Panel上调用DisableControls,它被禁用。然后循环遍历子节点,并在DropDownList上调用DisableControls,并使其保持启用状态(按预期)。但是,由于Panel已禁用,当页面呈现时,<div>标记内的所有内容都被禁用!

你能想到一个解决这个问题的方法吗?我考虑过将c.GetType().IsSubclassOf(typeof(WebControl))更改为c.GetType().IsSubclassOf(typeof(SomeParentClassThatAllInputElementsInheritFrom)),但我找不到合适的内容!

1 个答案:

答案 0 :(得分:2)

您只想禁用输入控件,因此您的代码过于笼统。做这样的事情:

if (IsInputControl(wc) && !wc.CssClass.ToLower().Contains("someclass"))
            wc.Enabled = false;

并创建函数IsInputControl:

bool isInputControl(WebControl ctl) {
    if (ctl is TextBox ||
      ctl is DropDownList || 
      ctl is CheckBox ||
      ...) {
      return true;
    } else {
      return false;
    }
}

我不知道WebControl的任何一般属性将其标识为输入控件,但是没有那么多类型,所以这不应该是一个太大的事情。