Я наткнулся на этот пост после желания реализовать что-то подобное некоторое время. Я регулярно использую Measurement Studio от National Instruments, и их элементы управления WinForms, у которых событие StateChanging или StateChanged передают параметр типа ActionEventArgs, у которого есть свойство Action, которое может принимать три значения: ByKeyboard, ByMouse и Programatic. Это очень полезно при определении причин изменения состояния элемента управления. Я хотел повторить это в стандартном флажке WinForms.
Вот мой код:
public enum ControlSource
{
Programatic,
ByKeyboard,
ByMouse
}
public class AwareCheckBox : Checkbox
{
public AwareCheckBox()
: base()
{
this.MouseDown += AwareCheckbox_MouseDown;
this.KeyDown += AwareCheckbox_KeyDown;
}
private ControlSource controlSource = ControlSource.Programatic;
void AwareCheckbox_KeyDown(object sender, KeyEventArgs e)
{
controlSource = ControlSource.ByKeyboard;
}
void AwareCheckbox_MouseDown(object sender, MouseEventArgs e)
{
controlSource = ControlSource.ByMouse;
}
public new event AwareControlEventHandler CheckedChanged;
protected override void OnCheckedChanged(EventArgs e)
{
var handler = CheckedChanged;
if (handler != null)
handler(this, new AwareControlEventArgs(controlSource));
controlSource = ControlSource.Programatic;
}
}
public delegate void AwareControlEventHandler(object source, AwareControlEventArgs e);
public class AwareControlEventArgs : EventArgs
{
public ControlSource Source { get; private set; }
public AwareControlEventArgs(ControlSource s)
{
Source = s;
}
}
Я уверен, что есть улучшения, но мое элементарное тестирование показало, что это работает. Я написал здесь просто на тот случай, если другие натолкнутся на эту проблему и захотят более четкого определения того, где было инициировано изменение. Любые комментарии приветствуются.