how to use multiple timers using vb.net - vb.net

I am using vb.net
I am using 2 timers in a single form. Form contains many textboxes, labels and gridview.
One timer is for refresh the gridview and second timer is for print the crystal report I used threading concept but it gives error for labels and other controls.
my code is
Private Sub cmdstart_Click(ByVal sender As System.Object, ByVal e As system.EventArgs) Handles cmdstart.Click
Dim timer2 As New System.Windows.Forms.Timer
AddHandler timer2.Tick, AddressOf mytimer2_tick
timer2.Enabled = True
timer2.Interval = 100
timer2.Start()
End Sub
Public Sub mytimer2_tick(ByVal sender As Object,ByVal e As System.EventArgs)
' my printing code
DirectCast(sender, System.Windows.Forms.Timer).Enabled = True
End Sub
Private Sub frmList_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
dim timer1 As New System.Windows.Forms.Timer
AddHandler timer1.Tick, AddressOf mytimer1_tick
timer1.Enabled = True
timer1.Interval = 10000
End Sub
Public Sub mytimer1_tick(ByVal sender As Object,ByVal e As System.EventArgs)
RefreshGrid()
DirectCast(sender, System.Windows.Forms.Timer).Enabled = True
End Sub
please help me
thanks in advance

Related

Emgu.CV on VB.Net Slow PictureBox Image

Using Emgu.CV Version 2.2.1.1150
I'm trying to query frames and display on picture box and the code works well on desktop computer with a Microsoft LifeCam 720p Picturebox is smooth and fluid but when I try the program in a Windows 10 tablet (CHUWI HI10X) the image is lagging.
If I test the tablet camera in the Win10 camera app they work very well and the video is HD and smooth.
I updated the drivers of these cameras to check if it was that but no luck.
Public Class frmCamera
Dim imgFrame As Image(Of Bgr, Byte)
Dim vidCapture As Capture
Private Sub frmMain_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
vidCapture = New Capture(1)
vidCapture.QueryFrame()
AddHandler Application.Idle, AddressOf AppIdle
End Sub
Public Sub AppIdle(ByVal sender As System.Object, ByVal e As System.EventArgs)
imgFrame = vidCapture.QueryFrame().Resize(800, 600, Emgu.CV.CvEnum.INTER.CV_INTER_LINEAR)
PictureBox1.Image = imgFrame.ToBitmap()
End Sub
Private Sub Button3_Click(sender As Object, e As EventArgs) Handles Button3.Click
frmMain.Show()
RemoveHandler Application.Idle, AddressOf AppIdle
vidCapture.Dispose()
Me.Close()
End Sub
End Class
I've tried multiple frame sizes and different interpolation types with no luck. Also changed from using a imageBoxFrameGrabber to PictureBox converting to Bitmap but still same results. Also tried using a Timer but that looks worse.
Thanks!
Edit:
Using a Timer my code ends up like this with no luck.
Public Class frmCamera
Dim imgFrame As Image(Of Bgr, Byte)
Dim vidCapture As Capture
Private Sub frmMain_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
Timer1.Interval = Timer1.Interval
RichTextBox1.Text = "Interval:" + Convert.ToString(Timer1.Interval)
Timer1.Start()
vidCapture = New Capture(1)
End Sub
Private Sub Button3_Click(sender As Object, e As EventArgs) Handles Button3.Click
frmMain.Show()
vidCapture.Dispose()
Me.Close()
End Sub
Private Sub Timer1_Tick(sender As Object, e As EventArgs) Handles Timer1.Tick
imgFrame = vidCapture.QueryFrame().Resize(800, 600, Emgu.CV.CvEnum.INTER.CV_INTER_LINEAR)
' PictureBox1.Image.Dispose()
PictureBox1.Image = imgFrame.ToBitmap()
End Sub
Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
Timer1.Stop()
Timer1.Interval = Timer1.Interval + 2
RichTextBox1.Text = "Interval:" + Convert.ToString(Timer1.Interval)
Timer1.Start()
End Sub
Private Sub Button2_Click(sender As Object, e As EventArgs) Handles Button2.Click
Timer1.Stop()
Timer1.Interval = Timer1.Interval - 2
RichTextBox1.Text = "Interval:" + Convert.ToString(Timer1.Interval)
Timer1.Start()
End Sub
End Class
Tried disposing the image in the picture box as suggested and end up with a:
System.NullReferenceException: 'Object reference not set to an instance of an object.'
At the moment of dispose.
Thanks again Jimi!

Auto refresh form every 30 seconds vb.net

I want to have a form opened all day but I want to auto refresh it every 30 seconds.
I am using this code:
Private Sub tempo(sender As System.Object, e As System.EventArgs) Handles MyBase.Load
Dim timer = New Timer
timer.Interval = 30 * 1000
AddHandler timer.Tick, AddressOf Form12_Load
timer.Start()
End Sub
Private Sub Form12_Load(sender As Object, e As EventArgs) Handles MyBase.Load
...
End sub
But it isn't working. Do you know what I am doing wrong?
Thank you.
My 0.02, should not need much explanation:
Private WithEvents clock As New Timers.Timer
Private Sub Form12_Load(sender As Object, e As EventArgs) Handles MyBase.Load
With clock
.Interval = 30000
.AutoReset = True
.Enabled = True
.Start()
End With
End Sub
Private Sub clock_tick() Handles clock.Elapsed
Me.BeginInvoke(Sub()
Me.Refresh()
End Sub)
End Sub
Firsly you need to take timer. after that you select time interval. how much time you want to refresh from load page. in my case im creating one function form load in side formload function is nothing you just type your commands. want to update on load page ===**
MyBase.Update()** im using that.
'Private Sub Timer3_Tick(sender As Object, e As EventArgs) Handles Timer3.Tick
' formload()
' ref_screen()
'End Sub
Hi you have to call the form_load event from the tick-timer event:
Private Sub Form12_Load(sender As Object, e As EventArgs) Handles MyBase.Load
Dim timer = New Timer
timer.Interval = 30 * 1000
AddHandler timer.Tick, AddressOf timer_Tick
timer.Start()
End sub
Private Sub timer_Tick(ByVal sender As Object, ByVal e As EventArgs)
Form12_Load(me,nothing)
End Sub

Late Binding Issue with BackgroundWorker in VB.Net

I am running a BackgroundWorker, and want to report its progress. In the example below I create a test list which the BackgroundWorker then iterates through. The problem lies in the line 'sender.ReportProgress(i)'. If I have Option Strict on, it does not like my use of 'i' due to Late Binding issues. Is there any alternative way to code this and avoid that issue?
Public Class Form1
Private Sub Form1_Load(sender As System.Object, e As System.EventArgs) Handles MyBase.Load
' Configuring for Background Workers
Control.CheckForIllegalCrossThreadCalls = False
Dim MyList As New List(Of String)
For a As Integer = 0 To 100
MyList.Add(CStr(a))
Next
End Sub
Private Sub Button1_Click(sender As System.Object, e As System.EventArgs) Handles Button1.Click
Dim bgw As New System.ComponentModel.BackgroundWorker
bgw.WorkerReportsProgress = True
bgw.WorkerSupportsCancellation = True
AddHandler bgw.DoWork, AddressOf bgw_DoWork
' I create a BackgroundWorker here rather than add one in the toolbox so that I can specify the Handler and use different Handler routines for different part of a large program.
Button1.Enabled = False
Dim progress As New Progress(bgw)
progress.ShowDialog()
Button1.Enabled = True
End Sub
Private Sub bgw_DoWork(sender As System.Object, e As System.ComponentModel.DoWorkEventArgs)
For i = 0 To MyList.Count -1
Label1.Text = MyList(i)
sender.ReportProgress(i)
System.Threading.Thread.Sleep(200)
Label1.Refresh()
Next
End Sub
End Class
Public Class Progress
Private WithEvents _BGW As System.ComponentModel.BackgroundWorker
Public Sub New(ByVal BGW As System.ComponentModel.BackgroundWorker)
_BGW = BGW
InitializeComponent()
End Sub
Private Sub frmProgress_Shown(sender As Object, e As System.EventArgs) Handles Me.Shown
If Not IsNothing(_BGW) Then
_BGW.RunWorkerAsync()
End If
End Sub
Private Sub _BGW_ProgressChanged(sender As Object, e As System.ComponentModel.ProgressChangedEventArgs) Handles _BGW.ProgressChanged
ProgressBar1.Value = e.ProgressPercentage
Label1.Text = e.ProgressPercentage
End Sub
Private Sub _BGW_RunWorkerCompleted(sender As Object, e As System.ComponentModel.RunWorkerCompletedEventArgs) Handles _BGW.RunWorkerCompleted
Me.Close()
End Sub
End Class
CType(sender, BackgroundWorker).ReportProgress(i)
Also, if you want to do multiple actions with it, then create a local reference variable like this:
Private Sub bgw_DoWork(sender As System.Object, e As System.ComponentModel.DoWorkEventArgs)
Dim bgw As System.ComponentModel.BackgroundWorker = DirectCast(sender, System.ComponentModel.BackgroundWorker)
' ... now you can use "bgw" multiple times below instead of casting each time ...
For i = 0 To MyList.Count -1
Label1.Text = MyList(i)
bgw.ReportProgress(i)
bgw.SomethingElse()
bgw.MoreStuff()
System.Threading.Thread.Sleep(200)
Label1.Refresh()
Next
End Sub
Obviously this isn't necessary in your case, just an FYI...

Button Click Event Within Another

I have two buttons Start button and Stop button .I run my program by clicking on start button. I want to stop the program during the start button . But the program will not responde until the start buttun finish its job. How i can do check the stop buttun during the start. i heard about threading but i do not know how i can do it.
Private Sub Button_Start (ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
//my code
//check always if the user push stop if no continue if yes go to this sub
//my code
end sub
Private Sub Button_Stop (ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button3.Click
stopClick = True
Dim Response As Integer
Response = MessageBox.Show("Do you really want to exit?", "", MessageBoxButtons.YesNo, MessageBoxIcon.Question)
If Response = vbYes Then
Me.Close()
End If
End Sub
you can use threading put button1 code in a function and use the thread .
you can refer to this example
'Thread created to handle the Background process for start_function
Dim t As System.Threading.Thread
Private Sub start_function()
While True
'your code here for Eg:
Dim i As Integer
i = i + 1
End While
End Sub
Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
t = New System.Threading.Thread(AddressOf Me.start_function)
t.Start()
End Sub
Private Sub Button2_Click(sender As Object, e As EventArgs) Handles Button2.Click
t.Abort()
End Sub
Drag a backgroundworker component onto your form.
Imports System.ComponentModel
Public Class Form1
Private Sub btnStart_Click(sender As Object, e As EventArgs) Handles btnStart.Click
Me.Text = "Busy Doing Work"
BackgroundWorker1.WorkerSupportsCancellation = True
BackgroundWorker1.RunWorkerAsync()
End Sub
Private Sub btnStop_Click(sender As Object, e As EventArgs) Handles btnStop.Click
Me.Text = "Asking to Cancel"
BackgroundWorker1.CancelAsync()
End Sub
Private Sub BackgroundWorker1_DoWork(sender As Object, e As System.ComponentModel.DoWorkEventArgs) Handles BackgroundWorker1.DoWork
While Not BackgroundWorker1.CancellationPending
System.Threading.Thread.Sleep(1000)
End While
End Sub
Private Sub BackgroundWorker1_RunWorkerCompleted(sender As Object, e As System.ComponentModel.RunWorkerCompletedEventArgs) Handles BackgroundWorker1.RunWorkerCompleted
Me.Text = "Cancelled"
End Sub
End Class

How to use timer for for next loop in visual basic 2008

I have a case where i need to generate millions of unique codes. For this I have created a generate function where the random number is generated. I call this function from a for loop and add the generated number on a list box. my code is as follow
for i=1 to val(txtnumber.txt)
mynum=generate()
next
I have created a lable on form where i wanted to display the no of secs elapsed while processing the loop. I used timer control as
timer1.start()
for i=1 to val(txtnumber.text)
mynum=generate()
listbox1.items.add(mynum)
next
timer1.stop
and on timer1_tick function
Private Sub Timer1_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer1.Tick
Label1.Text = Val(Label1.Text) + 1
End Sub
but when i click generate button, all numbers are generated, but timer doesnot shows time elapsed.
I may have missed something, so please help me out
This is probably best handled in a BackgroundWorker. Place one on the form and set its WorkerReportsProgress=True. Also, placing a million numbers in a ListBox probably isn't a good idea, so I omitted that.
Private Sub Button1_Click(ByVal sender As Object, ByVal e As EventArgs) Handles Button1.Click
Button1.Enabled = False
BackgroundWorker1.RunWorkerAsync()
End Sub
Private Sub BackgroundWorker1_DoWork(ByVal sender As Object, ByVal e As DoWorkEventArgs) Handles BackgroundWorker1.DoWork
Dim started As DateTime = Now
For i As Integer = 1 To val(txtnumber.txt)
mynum=generate()
BackgroundWorker1.ReportProgress(i, Nothing)
Next
Dim ended As TimeSpan = Now.Subtract(started)
BackgroundWorker1.ReportProgress(0, ended.TotalSeconds.ToString)
End Sub
Private Sub BackgroundWorker1_ProgressChanged(ByVal sender As Object, ByVal e As ProgressChangedEventArgs) Handles BackgroundWorker1.ProgressChanged
If e.UserState IsNot Nothing Then
Label1.Text = e.UserState.ToString()
Else
Label1.Text = e.ProgressPercentage.ToString
End If
End Sub
Private Sub BackgroundWorker1_RunWorkerCompleted(ByVal sender As Object, ByVal e As RunWorkerCompletedEventArgs) Handles BackgroundWorker1.RunWorkerCompleted
Button1.Enabled = True
End Sub
Your label should be updating correctly when the worker reports the ProgressChanged event.
What you're encountering is a threading issue. The work you are doing to generate the numbers is being executing by the UI thread, so it never gets a chance to update the screen. Take a look here: How to prevent UI from freezing during lengthy process?
This one might also have good information for you: Updating UI from another thread
Try this:
Private _Counter As Integer = 0
Private _StartTime As Date = Now
Private Sub Button1_Click(sender As System.Object, e As System.EventArgs) Handles Button1.Click
_StartTime = Now
_Counter = CInt(Val(txtnumber.Text))
ListBox1.Items.Clear()
Label1.Text = "0"
Timer1.Interval = 50
Timer1.Start()
End Sub
Private Sub Timer1_Tick(sender As System.Object, e As System.EventArgs) Handles Timer1.Tick
ListBox1.Items.Add(generate())
Label1.Text = New Date((Now - _StartTime).Ticks).ToString("HH:mm:ss.ff")
_Counter -= 1
If (_Counter <= 0) Then
Timer1.Stop()
End If
End Sub
Or you can research actual Threading.