我想将50按钮的点击事件设置为private void buttonOnOff(object sender,EventArgs e)。
当我这样写代码时,它就起作用了:
public Form1()
{
InitializeComponent();
button1.Click += button_Click;
button2.Click += button_Click;
button3.Click += button_Click;
.......
}
但是,使用for循环可以做到这一点吗。当我尝试时,我得到了以下错误:对象引用没有设置为对象的实例。
错误出现在这行代码上:Controls[buttonName].Click+=buttonOnOff;
这是我目前使用的代码:
public Form1()
{
InitializeComponent();
string buttonName;
for (int i = 1; i < 51; i++) // Does a check for each button.
{
buttonName = "button" + i;
Controls[buttonName].Click += buttonOnOff;
}
}
您可以迭代表单控件(甚至是使用Linq的按钮),如下所示:
foreach (Button b in this.Controls.OfType<Button>())
{
// here, you could check the name, if necessary
// and add your handler
b.Click += buttonOnOff;
}
提出一些好的评论以添加到答案中:
正如@mars-red和@donboitnott所指出的,不要允许此代码执行多次。在您当前的示例中,您是在Form的构造函数中执行的,所以这很好。
此外,@mars-red提到了按钮的Tag属性。如果你的表单上有其他按钮,并且不想弄清楚哪些按钮,你可以在每个按钮的标签上添加一个特定的值,然后检查一下——所以,类似这样的东西:
foreach (Button b in this.Controls.OfType<Button>())
{
if (b.Tag.ToString() == "SomeIndicator")
{
b.Click += buttonOnOff;
}
}
当然,您也可以在按钮的名称中查找特定的模式。
如果您正在使用此代码,那么您的"对象引用"问题就没有意义了。迭代器为您提供了特定的按钮实例,因此"b"应该始终是循环中的一个按钮。
最终更新:
主要问题是表单不是按钮控件的"容器"(它们在一个面板中)。因此,用户不应该使用表单的控件,而应该使用面板的控件(类似于这样):
SomePanel.Controls[buttonName].Click += buttonOnOff;
首先声明一个控制数组变量并向其添加按钮。
Control[] B_list = new Control[] { Button1, Button2, Button3, ...... }
然后在for循环中,像一样串行使用这些
Button btn;
for(int index = 0; index < 50; index++)
{
btn = (Button)B_list[index];
btn.Click += new EventHandler(buttonOnOff);
}
好的,在@Servy的请求中取消删除:
在循环中,您将从控件列表中按名称获取按钮控件。您的异常"对象引用未设置为对象的实例"只是意味着列表中没有具有此名称的对象。
因此,在1-50的集合中,要么缺少一个按钮,要么命名为其他按钮。
如果你正在使用@snow_FFFFFFF的解决方案,而错误仍然存在,那真的很奇怪。
尽管如此,正如我已经建议的:调试循环!检查它崩溃的按钮名称/实例,检查Controls
的内容(你必须在私人成员中往下走一点)等等