Getting incorrect timings while execution using dispatcher timer + stopwatch using VB.NET
-
02-07-2021 - |
Question
Here I initialize the time variables to 0 and use StopWatch
to count milliseconds and DispatcherTimer
to update UI
Imports System.Threading
Imports Windows.UI.Xaml
Dim dt As DispatcherTimer = New DispatcherTimer
Dim dd As Integer = 0
Dim mm As Integer = 0
Dim hh As Integer = 0
Dim ss As Integer = 0
Dim ms As Integer = 0
Dim stopwatch As System.Diagnostics.Stopwatch = New System.Diagnostics.Stopwatch
Private Sub ontimertick()
ms = stopwatch.ElapsedMilliseconds
ss = ms / 1000
ms = ms Mod 1000
mm = ss / 60
ss = ss Mod 60
hh = mm / 60
mm = mm Mod 60
dd = hh / 24
hh = hh Mod 24
MicroSeconds.Text = ms.ToString("00")
Seconds.Text = ss.ToString("00")
Minutes.Text = mm.ToString("00")
Hours.Text = hh.ToString("00")
End Sub
Private Sub StartButton_Click(sender As Object, e As RoutedEventArgs) Handles StartButton.Click
dt.Interval = New TimeSpan(0, 0, 0, 0, 100)
AddHandler dt.Tick, AddressOf ontimertick
stopwatch.Start()
dt.Start()
End Sub
The problem is that the very first instance of all variables increment in 1/2 of the time than the actual time I expect.
e.g. seconds.text is updated to 1 on 500th ms and the next onwards after 1000ms
Similarly Minutes.text is updated to 1 after 30th second and after that it increments after 60 seconds as normal
Same with the hour and day but only for the very 1st instance after that it increments after the normal intervals
So can anyone help me finding out the logical error?
I am Wondering how can I Reverse the process and countdown the time?
Can you guys help me with Idea/Logic that i can implement?
Solution
I think you're doing more work than you need to. The Stopwatch.Elapsed
property returns a TimeSpan
, which has all of the individual parts of the elapsed time.
Your ontimertick()
could look like this:
Private Sub ontimertick()
TimeSpan e = stopwatch.Elapsed
MicroSeconds.Text = e.Milliseconds.ToString("00")
Seconds.Text = e.Seconds.ToString("00")
Minutes.Text = e.Minutes.ToString("00")
Hours.Text = e.Hours.ToString("00")
End Sub
OTHER TIPS
ss = ms / 1000
The /
operator performs a floating point division, producing a Double result. You then assign it to an Integer, that will round the value instead of truncate it like you hope. So 500/1000 becomes 1.
The fix is to use the integer division operator:
ss = ms \ 1000
Also for the other divisions.