【问题标题】:How to override button click in c# (winForms)?如何覆盖 c# (winForms) 中的按钮单击?
【发布时间】:2018-07-25 05:37:39
【问题描述】:

让我从示例开始: 我有一个 Form 和一个名为 "btnTest" 的按钮,并为它添加了 _click 事件。

private void btnTest_Click(object sender, EventArgs e)
        {
            MessageBox.Show("button click");
        }

现在我想使用Control 类为这个button 动态生成另一个_click 事件,因此覆盖现有的event_hendler,所以我的表单看起来像这样:

 public partial class Form1 : Form
{
    public Form1()
    {
        InitializeComponent();
        Control[] controls = Controls.Find("btnTest", true); //find control by name
        controls[0].Click += Form1_Click; //generate button click
    }

    private void Form1_Click(object sender, EventArgs e)
    {
        MessageBox.Show("control click"); //want to be displayed
    }

    private void btnTest_Click(object sender, EventArgs e)
    {       
        MessageBox.Show("button click");  //don't want to be displayed
    }
}

所以我的目标是启用 Form1_Click忽略 btnTest_Click 并在代码中动态执行此操作。 完成someresearch,但无法得到答案。

我为什么要这样做?

我的主要目标是使用 ENTER 关键字而不是 TAB 来浏览控件,所以当我偶然发现按钮时,我只想在不触发原始事件的情况下继续前进。

请注意,btnTest_Click 事件是在 Form1_Click 事件之前触发的,而且不好的解决方案是直接在btnTest_Click 中执行某些操作,因为我想使用 ENTER导航的控件数量有限> 并且帽子是可变的,所以我想忽略的按钮将在 controls 数组中。

任何建议都有帮助,感谢您的宝贵时间。

【问题讨论】:

  • 我会尝试取消按钮上的 13 on keydown 事件,因此单击只会在您点击空格或用鼠标单击或点击时触发。因为您肯定不想让按钮完全无法点击。
  • 这是一个 XY 问题。您设置了一个奇怪的解决方案来解决实际上不需要任何启用和禁用这些功能的问题,只需小心调用。相当肯定你需要去 KeyDown 这个。
  • @dlatikay 谢谢你的建议,你是对的,不想让按钮无法点击
  • @MarkBenningfield 谢谢,但它不是重复的,因为我不是从一开始就构建导航,我只是在修复已经编写的代码中的现有问题

标签: c# winforms events button


【解决方案1】:

试试这个:

controls[0].Click += Form1_Click;
controls[0].Click -= btnTest_Click;

【讨论】:

  • 不能这样做,因为它需要是动态的,我不能使用btnTest_Click,除非我找到了像 buban 提议的名称控制
  • 好的,如果我理解你的目标,你需要使用 enterKey 而不是 TabKey 导航,但是你有一个点击事件句柄,所以,我相信你可以使用 PreviewKeyDown 事件句柄并创建一个标志来检测是否按下 Enter 键,然后在其他事件上验证标志并根据标志的状态执行操作,请查看示例代码:
  • 这个想法很好,谢谢你的努力,但它对我不起作用,它需要是动态的,让我试着解释一下,考虑以下场景:我有 17 个按钮用于今天导航,所以我需要去添加这个if (e.KeyCode == Keys.Enter)到al 17,第二天我有不同的17个导航按钮,所以我需要再次这样做if (e.KeyCode == Keys.Enter)并从前17删除。
  • 如何生成17个按钮?我要修改 answere 上的代码,我尝试在运行时添加 5 个按钮,并为 Preview 按键和 Form1.Click 添加句柄,检查一下。
【解决方案2】:

您如何看待这种方法

Control control = Controls.Find("btnTest", true).FirstOrDefault(); //find control by name
if(control != null)
{
  btnTest.Click -= btnTest_Click; //Remove Default Event Handler.
  control.Click += Form1_Click; //generate button click
}

【讨论】:

  • 感谢您的建议,但它不起作用,我可以使用 btnTest_Click ,如果我能以某种方式动态找到 btnTest_Click 名称,那么这将起作用,这将是我的逻辑,但它需要要动态,我已经找到解决方案并将发布并回答,请注意我已经尝试过controls[0].Click+=null; controls[0].Click += Form1_Click;,但它不会工作
【解决方案3】:

经过一番努力和研究,我设法找到了解决方案。 我的逻辑是删除controls[0].Click += Form1_Click; 之前的所有事件处理程序,这将是覆盖原始事件的方法。 试过这样的东西

 controls[0].Click += null;
 controls[0].Click += Form1_Click;

但它不起作用,所以我找到了基于this 答案的解决方案,我的论坛看起来像这样:

        public Form1()
        {
            InitializeComponent();
            InitializeComponent();
            Control[] controls = Controls.Find("btnTest", true); //find control by name
            Button btn = controls[0] as Button;    //safe cast as Button     
            RemoveClickEvent(btn); 
            controls[0].Click += Form1_Click; //generate button click
        }
        private void Form1_Click(object sender, EventArgs e)
        {
            MessageBox.Show("control click"); 
        }
        private void btnTest_Click(object sender, EventArgs e)
        {
            MessageBox.Show("button click"); 
        }

        //remove all event hendlers for button 
        private void RemoveClickEvent(Button b)
        {
            FieldInfo f1 = typeof(Control).GetField("EventClick",
                BindingFlags.Static | BindingFlags.NonPublic);
            object obj = f1.GetValue(b);
            PropertyInfo pi = b.GetType().GetProperty("Events",
                BindingFlags.NonPublic | BindingFlags.Instance);
            EventHandlerList list = (EventHandlerList)pi.GetValue(b, null);
            list.RemoveHandler(obj, list[obj]);
        }

【讨论】:

  • 这个解决方案有效,但有一个不小的问题,因为点击事件被删除,按钮失去了它的功能,所以鼠标点击不起作用。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2019-01-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-07-29
  • 1970-01-01
相关资源
最近更新 更多