如何防止/取消 C# 中组合框的值更改?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/314503/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-03 22:48:52  来源:igfitidea点击:

How to prevent/cancel a combobox's value change in c#?

c#winformscombobox

提问by

I have a combobox at the top of a form that loads editable data into fields below. If the user has made changes, but not saved, and tries to select a different option from the combobox, I want to warn them and give them a chance to cancel or save.

我在表单顶部有一个组合框,可将可编辑数据加载到下面的字段中。如果用户进行了更改但未保存,并尝试从组合框中选择不同的选项,我想警告他们并给他们取消或保存的机会。

I am in need of a "BeforeValueChange" event with a cancelable event argument.

我需要一个带有可取消事件参数的“BeforeValueChange”事件。

Any advice on how to accomplish?

关于如何完成的任何建议?

回答by Simon

You could use a message filterto intercept clicks and key presses, which would allow you to prevent the combo box's normal behaviour. But I think you'd be better off disabling the combo box when the user makes a change, and require them to either save or revert their changes.

您可以使用消息过滤器来拦截点击和按键,这将允许您阻止组合框的正常行为。但我认为最好在用户进行更改时禁用组合框,并要求他们保存或还原更改。

回答by Daniel M

You don't get an appropriate event by default. You could cache the previous value and set it back to that if the user wants to cancel.

默认情况下,您不会获得适当的事件。如果用户想要取消,您可以缓存先前的值并将其设置回该值。

回答by Vincent Van Den Berghe

Save the current value on the Enterevent. Implement the BeforeValueChangelogic in the ValueChangedevent, before the actual ValueChangedlogic. If the user cancels, set the stored value and don't continue in the method (return).

保存Enter事件的当前值。在实际逻辑之前BeforeValueChange,在ValueChanged事件中实现ValueChanged逻辑。如果用户取消,设置存储值,不要在方法(return)中继续。

If you're going to use this system a lot, I'd suggest inheriting ComboBox and implementing your BeforeValuechangeevent there.

如果您要经常使用这个系统,我建议您继承 ComboBox 并在BeforeValuechange那里实现您的事件。

回答by configurator

How about using the Validating / Validated events?
It works well, if the event happening on LostFocus instead of Change is ok with you.

如何使用 Validating / Validated 事件?
如果在 LostFocus 而不是 Change 上发生的事件对您没问题,那么它运行良好。

Otherwise, how about

不然怎么办

public void Combobox_ValueChanged(object sender, EventArgs e) {
    if (!AskUserIfHeIsSureHeWantsToChangeTheValue())
    {
        // Set previous value
        return;
    }

    // perform rest of onChange code
}

回答by Denis Biondic

Save the ComboBox's SelectedIndex when to box if first entered, and then restore it's value when you need to cancel the change.

如果第一次输入,则保存 ComboBox 的 SelectedIndex when to box,然后在需要取消更改时恢复它的值。

cbx_Example.Enter += cbx_Example_Enter;
cbx_Example.SelectionChangeCommitted += cbx_Example_SelectionChangeCommitted;

...

private int prevExampleIndex = 0;
private void cbx_Example_Enter(object sender, EventArgs e)
{
    prevExampleIndex = cbx_Example.SelectedIndex;
}

private void cbx_Example_SelectionChangeCommitted(object sender, EventArgs e)
{
    // some custom flag to determine Edit mode
    if (mode == FormModes.EDIT) 
    {
        cbx_Example.SelectedIndex = prevExampleIndex;
    }
}

回答by Kushal Waikar

Here is the simplest fix:-

这是最简单的修复:-

        bool isSelectionHandled = true;

        void CmbBx_SelectionChanged(object sender, SelectionChangedEventArgs e)
        {
            if (isSelectionHandled)
            {
                MessageBoxResult result = MessageBox.Show("Do you wish to continue selection change?", this.Title, MessageBoxButton.YesNo, MessageBoxImage.Question);
                if (result == MessageBoxResult.No)
                {
                    ComboBox combo = (ComboBox)sender;
                    isSelectionHandled = false;
                    if (e.RemovedItems.Count > 0)
                        combo.SelectedItem = e.RemovedItems[0];
                    return;
                }
            }
            isSelectionHandled = true;
        }

回答by Tates

You can't really prevent it, but you can change it back to the old value if certain requirements aren't met:

您无法真正阻止它,但如果不满足某些要求,您可以将其改回旧值:

private SomeObject = selectedSomeObject=null;

private void cbxTemplates_SelectionChangeCommitted(object sender, EventArgs e)
{
  if (!(sender is ComboBox cb)) return;
  if (!(cb.SelectedItem is SomeObject tem)) return;
  if (MessageBox.Show("You sure?", "??.",
        MessageBoxButtons.OKCancel) != DialogResult.OK)
    cb.SelectedItem = selectedSomeObject;
  else
  {
    selectedSomeObject = tem;
  }
}