A thread and textbox question

G

Guest

I have a form with a text box, a thread start button, and a seperate thread.
This is a TCP listener (server) example I took out of a book. See the code
below. In the loop below, look at the two lines I have marked with a comment
of ??????? If I don't write to the text box, I have a fast response. The
value "returnedData" is written to the console in a timely manner. However,
if I try to write to the textbox, tbStatus, the response slows to about 1
time per second. Is there some problem with writing to a textbox from within
a seperate thread?? Can somesone suggest a solution.

Hamil.



Private Sub btnStart_Click(ByVal sender As System.Object, ByVal e As
System.EventArgs) Handles btnStart.Click
btnStart.Enabled = False
btnStop.Enabled = True
Dim tr As New Thread(AddressOf ListenToClients)
tr.Start()
End Sub

Sub ListenToClients()
'localhostAddress = IPAddress.Loopback
localhostAddress = IPAddress.Parse("192.168.1.5")
port = CInt(txtPort.Text)
tcpList = New TcpListener(localhostAddress, port)
tcpList.Start()
listening = True
Do While listening
Do While tcpList.Pending = False And listening = True
Thread.Sleep(10)
Loop
If Not listening Then Exit Do
Dim tcpCli As New TcpClient
tcpCli = tcpList.AcceptTcpClient()
ns = tcpCli.GetStream
sr = New StreamReader(ns)
sw = New StreamWriter(ns)
tbStatus.Text = "connected"
Do While listening = True
Thread.Sleep(10)
receivedData = sr.ReadLine
If receivedData <> Nothing Then
returnedData = ProcessInput(receivedData)

Console.WriteLine(returnedData) '???????????
tbStatus.Text = returnedData '???????????????

sw.WriteLine(returnedData)
sw.Flush()
End If
Loop
sr.Close()
sw.Close()
ns.Close()
tcpCli.Close()
tbStatus.Text = "closed"
Loop
tcpList.Stop()
End Sub
 
I

Imran Koradia

Technically, you shouldn't be accessing a control from any other thread
except the one it was created on.
http://msdn.microsoft.com/library/d...ystemwindowsformscontrolclassinvoketopic1.asp

Accessing controls from a secondary thread is not guaranteed. It might work
sometimes but you shouldn't rely on it.

Instead, you should define a delegate and use the delegate to marshal the
calls from the secondary thread to the main thread when accessing your
controls. I'm not sure if this would speed up the update but here's how you
would update a textbox's text from another thread:


Delegate Sub SetTextDelegate(ByVal sText As String)
Private SetText As New SetTextDelegate(AddressOf SetTextBoxText)


Private Sub SetTextBoxText(ByVal sText As String)
tbStatus.Text = sText
End Sub

Sub ListToClients()
...
' all your relevant code..
...
...
...
' replace tbStatus.Text = "Connected" with this..
tbStatus.Invoke(SetText, New Object() {"Connected"})
...
' all your remaining code..
...
...
End Sub


hope that helps..
Imran.
 
G

Guest

What you say works! I tried it. Thanks.

Now, if the text box I want to write into is in another form, how would I
handle this?

I would assume I would do something like..

dim RemoteTextBox as textbox

Private Sub SetTextBoxText(ByVal sText As String)
RemoteTextBox.Text = sText
End Sub

I would have to set the RemotTextBox object variable from the remote form.
Comments??

hamil.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top