Как проверять каждые 30 секунд с диспетчером без влияния на пользовательский интерфейс в C#?
Я пробовал приведенный ниже код для проверки отчетов с сервера каждые 30 секунд, но после 30 секунд, приложение зависает на несколько секунд. Как избежать проблемы с зависанием. Приведенный ниже код пробовал, какие изменения хотите дать в этом?
System.Windows.Threading.DispatcherTimer dispatcherTimer2 = new System.Windows.Threading.DispatcherTimer();
dispatcherTimer2.Tick += new EventHandler(dispatcherTimer2_Tick);
dispatcherTimer2.Interval = new TimeSpan(0, 0, 30);
Public void dispatcherTimer2_Tick(object sender, EventArgs e)
{
dispatcherTimer2.start();
//code for function call autoreport();
}
3 ответа
Решение
Обратный вызов DispatcherTimer выполняется в основном потоке пользовательского интерфейса и блокирует его. Используйте System.Threading.Timer, и если вам нужно обновить пользовательский интерфейс с помощью обратного вызова таймера, используйте одну из перегрузок Dispatcher.Invoke. В коде что-то вроде этого
public partial class MainWindow : Window
{
System.Threading.Timer timer;
public MainWindow()
{
InitializeComponent();
timer = new System.Threading.Timer(OnCallBack, null, 0, 30 * 1000);
}
private void OnCallBack(object state)
{
//code to check report
Dispatcher.Invoke(() =>
{
//code to update ui
this.Label.Content = string.Format("Fired at {0}", DateTime.Now);
});
}
}
var timer = new System.Threading.Timer(
delegate
{
//--update functions here (large operations)
var value = Environment.TickCount;
//--run update using interface thread(UI Thread)
//--for WinForms
Invoke(
new Action(() =>
{
//--set the value to UI Element
}));
//--for WPF
Dispatcher.Invoke(
new Action(() =>
{
//--set the value to UI Element
}), null);
});
var period = TimeSpan.FromSeconds(30);
timer.Change(period, period);
Я надеюсь, что это помогает.
Это работает для меня
public Form1()
{
InitializeComponent();
var timer = new System.Timers.Timer(500);
// Hook up the Elapsed event for the timer.
timer.Elapsed += timer_Elapsed;
timer.Enabled = true;
}
void timer_Elapsed(object sender, System.Timers.ElapsedEventArgs e)
{
Invoke(
new Action(() =>
{
label1.Text += "Test Label";
Application.DoEvents();
}));
}