【发布时间】:2017-07-05 18:13:34
【问题描述】:
我有一个复选框绑定到包装 timer.Enabled 状态的属性。
主窗体:
chbTimer.DataBindings.Add(new Binding("Checked", _inactividadController, "TimerEnabled")
{
DataSourceUpdateMode = DataSourceUpdateMode.OnPropertyChanged,
ControlUpdateMode = ControlUpdateMode.OnPropertyChanged
});
_inactividadController:
public bool TimerEnabled
{
get { return _timer.Enabled; }
set
{
_timer.Enabled = value;
InvokePropertyChanged(new PropertyChangedEventArgs("TimerEnabled"));
}
}
_timer.Elapsed:
private void Test(object sender, ElapsedEventArgs e)
{
TimerEnabled = false;
}
这里发生异常:
public event PropertyChangedEventHandler PropertyChanged;
public void InvokePropertyChanged(PropertyChangedEventArgs e)
{
PropertyChangedEventHandler handler = PropertyChanged;
if (handler != null)
handler(this, e); //<-- BOOM
}
我完全理解这里发生了什么:Timer 在另一个线程上工作并尝试更新主线程上的 chbTimer,这是一个非法操作。但我不知道如何解决这个问题。
尝试了this 方法但不起作用,因为来自 UI 的更改不会反映在绑定上(当用户选中复选框时,计时器不会更改状态)。
有什么建议吗?谢谢
【问题讨论】:
-
你也可以显示你的处理程序代码吗?
-
您需要将调用编组到 UI 线程。不知道如何在 Windows 窗体中执行此操作,而不是使用 Control.Invoke,这在这里不会真正起作用(没有 hacky af)。也许在 UI 线程上创建一个 SynchronizationContext(从而捕获它)然后在您的绑定代码中使用该 SC?
-
@vendettamit 对不起什么?
PropertyChangedEventHandler就在那里。不确定您指的是哪个处理程序。 -
@Will 我不知道那门课,我现在就去读一点
-
@我会使用 SynchronizationContext 让它工作吗?非常感谢您,现在发布答案