我正在使用ObjectDataProvider来调用IObservableCollection的类:
<ObjectDataProvider x:Key="WaitingPatientDS"
ObjectType="{x:Type local:clsPatients}">
<ObjectDataProvider.ConstructorParameters>
<sys:Boolean>True</sys:Boolean>
</ObjectDataProvider.ConstructorParameters>
</ObjectDataProvider>
clsPatient抓取数据并填充集合。它还使用计时器以间隔轮询重新查询数据库。
问题:如何在clsPatient中为StartPoll和EndPoll创建一个事件,更重要的是,如何将这些事件冒充到我的WPF窗口的代码隐藏?
答案 0 :(得分:0)
我不清楚什么是与谁以及如何联系,所以让我告诉你我是如何做到的。
ODP构造clsPatients的一个实例,其中包含一个填充了“data”的“集合”。
public class clsPatients, INotifyPropertyChanged
{
public IBindingList Data {get;private set;}
private DispatcherTimer _timer;
public ClsPatients()
{
_timer = new DispatcherTimer();
_timer.Interval = TimeSpan.FromMilliseconds(someInterval);
_timer.Tick += DispatcherTimerTick;
_timer.Start();
}
/* etc etc */
}
clsPatients还有一个DispatcherTimer,它定期更新Data属性并触发PropertyChanged
public void DispatcherTimerTick(object sender, EventArgs e)
{
Data = new BindingList(Repository.GetMyDataLol());
// standard event firing method here, move along:
OnPropertyChanged("Data");
}
在用户界面中,我会这样绑定这个集合(这可能是没有错误的,或者可能没有错误):
<ItemsControl
ItemsSource="{Binding Data Source={StaticResource WaitingPatientDS}}">
<ItemsControl.Resources>
<DataTemplate>
<!-- yadda -->
更新数据时如何更新UI:
要显示指示正在加载的动画,请向clsPatient添加另一个名为Loading的属性:
public Visibility Loading{get;private set}
并更新计时器刻度事件:
public void DispatcherTimerTick(object sender, EventArgs e)
{
Loading = Visibility.Visible;
OnPropertyChanged("Loading");
Data = new BindingList(Repository.GetMyDataLol());
OnPropertyChanged("Data");
Loading = Visibility.Hidden;
OnPropertyChanged("Loading");
}
然后,在ui中,将指标的Visibility属性绑定到Loading:
<Grid DataContext="{Binding Data Source={StaticResource WaitingPatientDS}}">
<ItemsControl
ItemsSource="{Binding Data}">
<ItemsControl.Resources>
<DataTemplate>
<!-- yadda -->
</ItemsControl>
<Image Source="hurf.jpg" Visibility="{Binding Loading}"
HorizontalAlignment="Center" VerticalAlignment="Center"/>
</Grid>
当“加载”设置为“可见”时,将显示“图像”(或您要使用的任何其他控件),当“加载”设置为“隐藏”时,它将消失。因此,您可以在加载数据时显示图像。
如果UI未更新,则该过程可能会阻止UI在UI线程中执行。
要解决此问题,请运行System.Threading.Timer而不是DispatcherTimer。 STT在除UI之外的后台线程上运行。在timer的回调方法中,使用调度程序更新ui(Invoke方法可能有错误;检查Dispatcher.Invoke上的文档):
public void UpdateData(Object stateInfo)
{
var disp = Dispatcher.CurrentDispatcher();
Loading = Visibility.Visible;
disp.Invoke(() => { OnPropertyChanged("Loading");});
// optional sleep here
Data = new BindingList(Repository.GetMyDataLol());
disp.Invoke(() => { OnPropertyChanged("Data");});
Loading = Visibility.Hidden;
disp.Invoke(() => { OnPropertyChanged("Loading");});
}