Serial controller Help

Hi,

I am using Serial Controller to get the output into a listbox form a weighing scale machine,

I put two button with the same code in Data Available Event

while me.BytesAvailable > 0
dim s as string = me.ReadAll
Listbox1.AddRow s
me.poll
wend

the problem is , when I press the button 1 to receive the output, is working.
but it wont work for the second button press

Button 1 code (worked)

l_input.text="Auto"
lkt.Text="1"
Listbox1.DeleteAllRows
dim g as new date
txtjam_masuk.text=""
txtjam_masuk.text=str(g.ShortTime)

If Me.Caption = "Stop" Then // Disconnect from the serial port
SerialController.Close
Me.Caption = "KG"
SerialPortsPopupMenu.Enabled = True
PortListUpdater.Mode = Timer.ModeMultiple // turn the PortListUpdater timer back on
Else // Connect to the serial port
SerialController.SerialPort = System.SerialPort(SerialPortsPopupMenu.ListIndex) // Set the serial port to the index of the one chosen in the popup menu
If SerialController.Open Then
Me.Caption = "Stop"
SerialPortsPopupMenu.Enabled = False
PortListUpdater.Mode = Timer.ModeOff
Else
Beep
Label1.text="The selected serial port could not be opened."
End If
End If


if cmbStatus.ListIndex=1 then 'kirim
dim a,b,c as double
a=CDbl(Label9.text)
b=CDbl(Label2.text)
c=a-b
label11.text= Format(c , "###,##0") 

dim a1,b1,c1 as Double
a1=CDbl(label11.text)
b1=CDbl(txtpalet.text)
c1=a1-b1
label24.text= Format(c1 , "###,##0") 
end if

if cmbStatus.ListIndex=2 then 'terima
dim a,b,c as double
a=CDbl(Label9.text)
b=CDbl(Label2.text)
c=b-a

label11.text= Format(c , "###,##0") 

dim a1,b1,c1 as Double
a1=CDbl(label11.text)
b1=CDbl(txtpalet.text)
c1=a1-b1

label24.text= Format(c1 , "###,##0") 

end if
if btnbatal.text="1" then
Update_data
end if

if cmbStatus.ListIndex=0 then
 label1.Text="Silahkan pilih statusnya, kirim apa terima"
else
label1.Text="Connected to local server"
end if

and this the button 2 code,

l_input.text="Auto"
lkt.Text="2"
Listbox1.DeleteAllRows
dim g as new date
txtjam_keluar.text=""
txtjam_keluar.text=str(g.ShortTime)

If Me.Caption = "Stop" Then // Disconnect from the serial port
SerialController.Close
Me.Caption = "KG"
SerialPortsPopupMenu.Enabled = True
PortListUpdater.Mode = Timer.ModeMultiple // turn the PortListUpdater timer back on
Else // Connect to the serial port
SerialController.SerialPort = System.SerialPort(SerialPortsPopupMenu.ListIndex) // Set the serial port to the index of the one chosen in the popup menu
If SerialController.Open Then
Me.Caption = "Stop"
SerialPortsPopupMenu.Enabled = False
PortListUpdater.Mode = Timer.ModeOff
Else
Beep
Label1.text="The selected serial port could not be opened."
End If
End If


if cmbStatus.ListIndex=1 then 'kirim
dim a,b,c as double
a=CDbl(Label9.text)
b=CDbl(Label2.text)
c=a-b
label11.text= Format(c , "###,##0") 

dim a1,b1,c1 as Double
a1=CDbl(label11.text)
b1=CDbl(txtpalet.text)
c1=a1-b1

label24.text= Format(c1 , "###,##0") 
end if

if cmbStatus.ListIndex=2 then 'terima
dim a,b,c as double
a=CDbl(Label9.text)
b=CDbl(Label2.text)
c=b-a

label11.text= Format(c , "###,##0") 

dim a1,b1,c1 as Double
a1=CDbl(label11.text)
b1=CDbl(txtpalet.text)
c1=a1-b1

label24.text= Format(c1 , "###,##0") 

end if

if btnbatal.text="1" then
Update_data
end if

if cmbStatus.ListIndex=0 then label1.Text="please select the status"

any help ?

thanks
regards,
Arief

Best practice is to put as little code as possible in the DataAvailable event. Doing more in the DataAvailable event (like adding a row to a ListBox) can result in missed bytes. In the DataAvailable event, append the received bytes to a buffer string and start a timer with a short delay. Handle the data in the timer’s Action event.

The net result is that you’ve moved the data handling to a different thread from the one that the serial controller is running on (I think).

1 Like

Amen to that.

I recognize the code from the sample project since I usually start there myself when working with serial ports.
Because each button tries to manage the serial device open/close, the second press either closes the port or fails to open because it is already open.

Try this:
Create a new button to connect to the serial port. Put the Open/Close code in the action event of that button.
Remove all of the code that does not actually read the data from the other 2 buttons. Those should only read the data into the listbox.

Button 2 is trying to open the port while it is still open (having been opened, but not closed, by button 1). Create a boolean window property and set it whenever the port opens or closes. Use that property to only open the port when it is closed.

Hi,
yes, I choose to add the result into a listbox, because I want to remove unwanted character there.

the output from the machine is loop, here is the result,
ÌCÓ˜˜00000
.kg0
G0000000
L0000000

so, if I put the output in a listbox, will be easier to manage unwanted rows using regex.

the original example file in xojo bundle put the result into textarea. I dont know if regex will work to remove it and get the last proper result.

thanks
Arief

hi,
so its mean, I just use the original code for the example, only to open and close right.
okay, will give it a try.

thanks
arief

Sure, you can put the data in a ListBox and do whatever you want with it, just don’t do it in the DataAvailable event - do it in the Action event of a timer instead.

1 Like

I just realized that I have made some change in serial.data event.
the original from the example was using lookahead property.

what is the difference between,

If InStr(Me.LookAhead(Encodings.ASCII)) > 0 Then
Listbox1.AddRow Me.ReadAll(Encodings.UTF8)
End If

with

while me.BytesAvailable > 0
dim s as string = me.ReadAll
Listbox1.AddRow s
me.poll
wend

thanks
regards,
arief

Forum for Xojo Programming Language and IDE. Copyright © 2021 Xojo, Inc.