Just judging from what you've provided, it looks like you're doing all the work on the UI thread, and you're queuing up items via a timer. I suspect that one job isn't completing before another is started (how fast is your timer set to fire?). So the reason your form isn't updating is that the UI thread is too busy to update the controls because it's doing the other work you're requesting.
I don't know how familiar you are with windows forms and windows forms controls, so I'll explain this as if you don't know any of it.
In windows forms, all controls are created using one thread. We call this the UI (or user interface) thread. Your controls and your forms themselves can only be updated from the UI thread. Attempting to update them from a background thread will cause a "cross thread" exception. But that doesn't mean that we should do all our work on the UI thread, or that controls can't be updated with data created or pulled on a background thread. it just means we have to pass that data to the UI thread first, and that we always need to make sure that the UI thread is free to update the user interface when we ask it to.
So:
1.) Do as little work on the UI thread as possible, unless you are actively updating the user interface (your forms / controls). This will mean creating additional threads to handle the bulk of your work.
2.) When you have data that needs to be reflected in the UI, switch to the UI thread and update your controls. Here's an easy way to do that:
private bool closing = false;
public void UI(Action action) {
if (closing) return;
if (InvokeRequired) {
Invoke((MethodInvoker)delegate () { action(); });
} else {
action();
}
}
You would use it like this:
private void GetSessionData(ParentPanel panel, int transactionId, int connectorId)
{
new Thread(()=>{
if (data != null || data.ErrorCode == ErrorCodeEnum.NoError)
{
if (data.ChargerState == ChargerStateEnum.ChargingEV || data.ChargerState == ChargerStateEnum.Available || data.ChargerState == ChargerStateEnum.None)
{
SendMeterData(data, connectorId, transactionId);
Thread.Sleep(2000);
int voltage = Int32.Parse(sessionData.PresentVoltage);
int current = Int32.Parse(sessionData.PresentCurrent);
TimeSpan ts = TimeSpan.FromMilliseconds(Double.Parse(sessionData.ElapsedChargingTime));
string timeDuration = ts.ToString("hh\\:mm");
int power = (voltage * current) / 1000;
double amount = Math.Round(power * 0.18, 2);
int num = rnd.Next();
UI(()=>{
PowerLabel.Text = num.ToString();
TimerLabel.Text = DateTime.Now.ToString();
PriceLabel.Text = amount.ToString();
});
}
}
else
{
screensData.Notify(Event.ChargerEvents.ERROR, "Faulted Charger");
}
}){ isBackground = true }.Start();
}
Handling it like this will shift all the work to background threads, leaving the UI free to update your controls.
- Pete