vbnewbie
vbnewbie

Reputation: 226

How to run multiple timer in a form?

I have a panel with 50 button and 1 label in my form

Private Sub flp_table_paint(sender As Object, e As PaintEventArgs) Handles flp_table.Paint

        Dim i As Integer
        For i = 1 To 50
            Dim btn_tableNo As New Button
            btn_tableNo.Width = 40
            btn_tableNo.Height = 40
            btn_tableNo.Text = i
            AddHandler btn_tableNo.Click, AddressOf TableButtonClicked

            Dim timer As New Timer
            timer.Tag = i

            Me.flp_table.Controls.Add(btn_tableNo)
        Next

End Sub

What I try to do is, for every single button that i clicked they will start their own timer and show on the label.

Example:

11:00:00PM - Clicked on Button1 , lb_timer will show 1,2,3,4...

11:00:30PM - Clicked on Button2 , lb_timer will show 1,2,3,4...

11:00:45PM - Clicked on Button1 again, lb_timer will show 45,46,47,48...

11:00:50PM - Clicked on Button2 again, lb_timer will show 20,21,22,23...

Here is what i try so far, but fail...

Private Sub TableButtonClicked(ByVal sender As Object, ByVal e As EventArgs)
    Dim currButton As Button = sender
    selectedTable = currButton

    For Each timer As Timer In Me.Controls
        If timer.Tag = selectedTable.Text Then
            timer.Start()
            lb_timer.Text = timer.ToString
        End If
    Next
End Sub

I have no idea how to make it work, please help me...

Upvotes: 0

Views: 706

Answers (2)

Fabio
Fabio

Reputation: 32445

Here asynchronous approach without Timer and one eventhandler for all buttons

' In constructor
AddHandler button1.Click, AddressOf Button_Click
AddHandler button2.Click, AddressOf Button_Click
AddHandler button3.Click, AddressOf Button_Click
' ... rest of buttons


' variable will keep name of the button which number is showing
Private _selectedButtonName As String

Private Async Sub Button_Click(sender As object, e As EventArgs)
    Dim button As Button = DirectCast(sender, Button)
    _selectedButtonName = button.Name

    Dim isRunning As Boolean = (button.Tag IsNot Nothing)
    If isRunning = True Then return

    await StartCounterAsync(button)
End Sub

Private Async Function StartCounterAsync(Button button) As Task
    button.Tag = new object()
    Dim number As Integer = 0
    While True
        await Task.Delay(1000)
        number += 1

        If _selectedButtonName.Equals(button.Name)
            lb_timer.Text = $"{button.Name}: {number}"
        End If
    End While
End Function

You can add CancellationToken in case you want reset counters.

Upvotes: 1

djalonso
djalonso

Reputation: 765

Sadly the timer doesn't show elapsed time. An easier control to use for your purpose would be the StopWatch control. Its quite similar and will show a running time.

Dim StopWatchTest As New Stopwatch
StopWatchTest.Start()
Dim EllapsedTime As String = StopWatchTest.ElapsedMilliseconds / 1000

However since you want to continually update the label with the ellapsed time, you would need a timer to update the label at every tick.

Dim UpdateLabelTimer As New Timer()
UpdateLabelTimer.Interval = 1000 'How often to update your label (in milliseconds)
AddHandler UpdateLabelTimer.Tick, AddressOf Tick
UpdateLabelTimer.Start()

----------

Private Sub Tick()
    lblLabel.text = StopWatchTest.ElapsedMilliseconds
End Sub

Upvotes: 0

Related Questions