After a long practice and consulting the internet I have been able to differentiate
keyboard input from scanned input successfully.
I have 2 textboxes (txtScannedInput and txtKeyboardInput) and
1 label (lblDisplayScannedInput) to display the scanned input.
Everything works perfectly when the txtScannedInput textbox has focus before
a barcode is scanned.
My only problem is when the txtKeyboardInput has focus before
a barcode is scanned the first 2 characters of the barcode stays in the txtKeyboardInput
while the rest of the charcters move to the txtScannedInput.
(I know it is because my calculations to differentiate keyboard input from
scanned input is based on keypress, so by the time it get to know that the input is a scanned
one 2 of the characters have already been entered in the txtKeyboardInput and it moves to rest to the txtScannedInput.)
Can anyone help me to improve on my code or is there a better way of doing this?
Public Class frmFinalBarCode
Dim datLastTimePress As DateTime = Date.Now
Private Sub frmFinalBarCode_KeyPress(ByVal sender As Object, ByVal e As System.Windows.Forms.KeyPressEventArgs) Handles Me.KeyPress
If (DateTime.Now.Subtract(datLastTimePress).Milliseconds > 50) Then
Me.Text = "This is a keyboard input"
Else
Me.Text = "This is a Scanner input"
datLastTimePress = DateTime.Now ' Initialize the timer for the first character
txtScannedInput.Focus()
End If
End Sub
Private Sub frmFinalBarCode_KeyUp(ByVal sender As Object, ByVal e As System.Windows.Forms.KeyEventArgs) Handles Me.KeyUp
datLastTimePress = Date.Now
End Sub
Private Sub txtScannedInput_KeyPress(ByVal sender As Object, ByVal e As System.Windows.Forms.KeyPressEventArgs) Handles txtScannedInput.KeyPress
lblDisplayScannedInput.ResetText()
lblDisplayScannedInput.Text = txtScannedInput.Text
End Sub
End Class
Related
I have the following:
a listbox called ListBox1 with a couple of random values in it
a couple of rich textboxs called Rit11 up to Rit 154
a button
When I click a rich textbox, I want to set the a variable to the number that the box is called. After this I select a value from the listbox, and when I press the button, I want this value to move to the selected textbox, and be removed from the listview. I made the following code, but it gives an error.
Private Sub Rit12_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Rit12.Click
SelBox = "12"
End Sub
Private Sub Button3_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button3.Click
Dim BoxName
BoxName = ("Rit" & SelBox)
Me.Controls(BoxName).Text = ListBox1.SelectedItem
ListBox1.Items.RemoveAt(ListBox1.SelectedIndex)
End Sub
It worked fine, till I tried using the variable name. This rule seems to give the problem:
Me.Controls(BoxName).Text = ListBox1.SelectedItem
I have four textbox for an IP Address. Each textbox is for each of the octate.
When the control loses focus or when user presses ENTER, it will check if the value is greater than 255.
Private Sub txtParametersIpFirst_KeyPress(sender As Object, e As KeyPressEventArgs) Handles txtParametersIpFirst.KeyPress
If e.KeyChar = Microsoft.VisualBasic.ChrW(Keys.Return) Then
'Check if Value is more than 255
End If
End Sub
Private Sub txtParametersIpFirst_LostFocus(sender As Object, e As EventArgs) Handles txtParametersIpFirst.LostFocus
'Check if Value is more than 255
End Sub
Is there something that these two events be combined?
The best way to combine two events is by calling a method..
Private Sub Logic()
'Check if Value is more than 255
End Sub
Private Sub txtParametersIpFirst_KeyPress(sender As Object, e As KeyPressEventArgs) Handles txtParametersIpFirst.KeyPress
If e.KeyChar = Microsoft.VisualBasic.ChrW(Keys.Return) Then
Logic()
End If
End Sub
Private Sub txtParametersIpFirst_LostFocus(sender As Object, e As EventArgs) Handles txtParametersIpFirst.LostFocus
Logic()
End Sub
However, if you're to combine two same events, for example two Lostfocus event of two different textboxes, then you can just add handles;
Private Sub txtText1_LostFocus(sender As Object, e As EventArgs) Handles txtText1.LostFocus, txtText2.LostFocus,
' Code similar for both textbox
' You can use the Sender param to verify who's triggering the event
End Sub
Why dont you go for masking like this ###.###.###.### and use the Validation event to confirm that the value entered is a valid IP address.By this way there is no need for four different text boxes
There is some good material on This link.and MSDN
I'm Visual Basic beginner, yesterday i wrote a dictionary that give you the opposite of the entered word, so i designed the form to look like this
[url]http://img651.imageshack.us/img651/6115/errorbp.jpg[url]
by the way i made a two list boxes as databases so the code will compare if the textbox1.text = listbox1.text then it will command textbox2 to append the value of the listbox : textbox2.appendtext(listbox2.text) but nothing happens
my code:
Public Class Form1
Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
End Sub
Private Sub TnsBtn_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
If TextBox1.Text = TextBox3.ToString Then
TextBox2.AppendText(ListBox2.Text)
ElseIf TextBox1.Text = TextBox4.Text Then
TextBox2.AppendText(ListBox1.ToString)
End If
End Sub
Private Sub AddBtn_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click
ListBox1.Items.Add(TextBox3.Text)
ListBox2.Items.Add(TextBox4.Text)
End Sub
End Class
the point of the code is ok cuz yesterday i finished the coding and the programs works fine but i forget to save it so i coded again and every thing above happens
this is the yesterday program
http://www.mediafire.com/?tavne7xjyth7y7v
virustotal link:
https://www.virustotal.com/file/1d39429ae1498a744e1556188b7e8914526b7e2fbb2d4904c2b4ea22fb278dc7/analysis/1346676641/
Initially you are setting the textbox text to "ListBox" without choosing anything specific so it is calling ToString() on the listbox which is why you get that.
I would change the method so that you have a Dictionary variable like so:
Public Sub Translate(input As String)
TextBox2.Text = OppositeDictionaires(input)
End Sub
Public OppositeDictionary As New Dictionary(Of String, String)
'Call as Add(TextBox3.Text, TextBox4.Text)
Public Sub Add(input As String, opposite As String)
OppositeDictionary.Add(input, opposite)
End Sub
Call add from your event and then Translate from your translate event. You should then get your output as intended, still add them to the listboxes if you want to display to the user but handle the translation in the code behind through a dictionairy object.
http://msdn.microsoft.com/en-us/library/xfhwa508.aspx
I'm trying to make an application that can read a 12 byte hex string from the serial port and display it into a text box, the source is a RFID module that is connected to my USB port using a RS232-USB converter.
My first problem was accessing the text box in the datarecieved event due to invalid cross-threaded operation. Upon googling that, I copy/pasted the code I needed to get it work, these are all the cross threading functions.
The OpenPort function and Datarecieved event are my own code, the rest I got off google.
The application then worked, but I would get an incomplete code, the first swipe I would get all 12 digits, and at every other swipe, the first byte would vanish. Upon some more reading, I decided to make an array, the size of the incoming data (shown in the code below), but now I get the cross-threading error again.
I know there's something wrong with the way I'm using the array. This is way beyond my VB knowledge, and I'm in over my head here, could use some expert help. I'm an electronics engineer and self taught myself a little programming to create some apps for my hardware.
Thanks.
Updated code:
Public Class Form3
Dim msg As String
Private Sub Form3_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
For Each s In System.IO.Ports.SerialPort.GetPortNames()
lstPorts.Items.Add(s)
Next s
End Sub
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
If lstPorts.SelectedIndex = -1 Then
MessageBox.Show("Please select a port")
Exit Sub
Else
SerialPort1.BaudRate = 9600
SerialPort1.DataBits = 8
SerialPort1.Parity = IO.Ports.Parity.None
SerialPort1.StopBits = IO.Ports.StopBits.One
SerialPort1.PortName = lstPorts.SelectedItem.ToString
SerialPort1.Open()
End If
End Sub
Private Sub SerialPort1_DataReceived(ByVal sender As System.Object, ByVal e As System.IO.Ports.SerialDataReceivedEventArgs) Handles SerialPort1.DataReceived
msg = SerialPort1.ReadExisting
Me.Invoke(New Action(
Sub()
txtReceived.Clear()
txtReceived.Text += msg
End Sub))
End Sub
Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click
SerialPort1.Close()
txtReceived.Text = ""
End Sub
End Class
Anything you read here:
If SerialPort1.IsOpen Then
msg = SerialPort1.ReadExisting()
End If
You will lose when you overwrite it here:
msg = enc.GetString(bytesarray)
I don't generally recommend trying to read strings directly from serial ports (or TCP/IP connections either for that matter). Stick with the array approach only and get rid of ReadExisting. Only when you know you have a whole "message" would I convert the bytes to a string.
Some generic tips (though this varies by protocol):
Define a buffer to read your messages into that is large enough to hold your entire message, and don't make it a local variable.
Keep track of the offset into that buffer.
When you first read, your offset will be 0 and lets say you read 2 bytes. Your offset will then be +2 for a value of 1.
Upon your second (and third, etc) read you insert starting at that offset, effectively appending the new bytes.
After each read you must inspect your buffer to see if you have received a whole message. You can do this by the total amount read (if you have fixed-length messages), or by some info in thebuffer (like a length prefix). Once you read your message you need to remove it from the buffer.
I suggest starting with a simple approach and after removing the message you reset your offset back to zero and continue the process. If the data you had received was LONGER than the message you had removed, you need to shift those extra bytes to the "left" so that they start at position 0. (A more efficient approach is to use a circular buffer, but KISS for now).
In your DataRecv event you should do something like this to update your UI:
Me.Invoke(New Action(
Sub()
'this code runs on the GUI thread, update textboxes!
Me.Text += msg
End Sub))
I'm still not a fan of ReadExisting, but if you are sure you are always getting prinatble characters out of your device then try something like this:
Public Class Form3
Private pendingMsg As New StringBuffer()
Private Sub Form3_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
For Each s In System.IO.Ports.SerialPort.GetPortNames()
lstPorts.Items.Add(s)
Next s
End Sub
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
If lstPorts.SelectedIndex = -1 Then
MessageBox.Show("Please select a port")
Exit Sub
Else
SerialPort1.BaudRate = 9600
SerialPort1.DataBits = 8
SerialPort1.Parity = IO.Ports.Parity.None
SerialPort1.StopBits = IO.Ports.StopBits.One
SerialPort1.PortName = lstPorts.SelectedItem.ToString
SerialPort1.Open()
End If
End Sub
Private Sub SerialPort1_DataReceived(ByVal sender As System.Object, ByVal e As System.IO.Ports.SerialDataReceivedEventArgs) Handles SerialPort1.DataReceived
Dim completedMsg As String
completedMsg = String.Empty
pendingMsg.Append(SerialPort1.ReadExisting())
If pendingMsg.Length >= 24 Then '12 bytes in hex is 24 chars
completedMsg = pendingMsg.ToString(0, 24) '1st 24 bytes are a msg
pendingMsg.Remove(0, 24) 'pop off the msg from our buffer
Me.Invoke(New Action(
Sub()
txtReceived.Text = completedMsg
End Sub))
End If
End Sub
Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click
SerialPort1.Close()
txtReceived.Text = ""
End Sub
End Class
Could someone show some guidance(am not asking to do my homework) with validating a form with multiple text boxes? User would be informed what was the problematic field.
The source of the form:
Private Sub btnNewUser_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnNewUser.Click
'If txtEmail.Text.Contains(" "c) Or Not(InStr(txtEmail.Text, "#")) Then
'txtEmail.Clear()
'ElseIf txtPassword.Text.Contains(" "c) Then
'txtPassword.Clear()
'ElseIf txtPIN.Text ''#uh
aryUserRecord(0) = txtEmail.Text
aryUserRecord(1) = txtPassword.Text
aryUserRecord(2) = txtPIN.Text ''#consists of a letter then two numbers then another addNewUser = Join(aryUserData, ",")
''#more source
Me.DialogResult = DialogResult.OK
End Sub
You can use an ErrorProvider to mark the problematic fields. You'll want to hook up with the validating event for each TextBox. Something like this:
Private Sub TextBox1_Validating(ByVal sender As System.Object, ByVal e As System.ComponentModel.CancelEventArgs) Handles TextBox1.Validating
If TextBox1.Text = "" Then
ErrorProvider1.SetError(TextBox1, "Text cannot be empty")
e.Cancel = True
End If
End Sub
Then when the Textbox does actually validate, you can hook up to the Validated event to clear out the ErrorProvider:
Private Sub TextBox1_Validated(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles TextBox1.Validated
ErrorProvider1.SetError(TextBox1, "")
End Sub
Try reading up on RegularExpressionValidator.
You could have one assigned for each textbox to validate user input client side using regular expressions, which based on your comments to the question seem like a good choice.
with winforms you'll need to implement Validating and Validated events
http://msdn.microsoft.com/en-us/library/system.windows.forms.control.causesvalidation.aspx
in the link above an example is provided for e-mail. This should give you a reference to start