MSCOMM- RS232- FREQUENCY CAPTURE FROM ICOM IC-706MKIIG
Before you criticize this program, I think it is wise for me to have you informed that I don't have any computer training and I am not a programmer. My coding may not meet to your standard. But you can always improve it or find the shortest possible way to code it.
This program has the purpose of capturing the ICOM IC-706 MKIIG into my logbook. In that way I don't have to type the frequency anymore. You need to think how to do it in your logbook. The basic is here. Please expand it.
This program is not perfect yet. This writting is done as soon I have finished the coding.
Private Sub Form_Load()
MSComm1.CommPort = 4 'my commport is 4. There
is an alternative program for serching the commport
MSComm1.Settings = "9600,N,8,2"
MSComm1.RTSEnable = True
MSComm1.DTREnable = True
MSComm1.RThreshold = 1
MSComm1.PortOpen = True
End Sub
' chr(254) is the preamble code to be sent to your icom. It has to be sent twice. xx represent the CI-V address - for mark2G it is 88 and pro3 is 110.chr(3) is the request for display frequency and 253 is the closing bit.
Private Sub Form_Activate()
MSComm1.Output = Chr(254) & Chr(254) & Chr(xx) & Chr(224) & Chr(3) & Chr(253)
End Sub
Below is the alternative way to look for any existing port. Here I assume there is 100 commports, which is of course absurd.
Private Sub initb()
On Error GoTo kel
MSComm1.CommPort = komport
MSComm1.settings = "9600,N,8,2"
MSComm1.RTSEnable = True
MSComm1.DTREnable = True
MSComm1.RThreshold = 1
MSComm1.PortOpen = True
Exit Sub
kel:
komport = komport + 1: If komport = 100 Then komport = 0
Call klik_Click 'klik is
command button - make it invisible
End Sub
Private Sub klik_Click()
initb
End Sub
Once the shakehand takes place the radio will continue to send messages out. It may not neccesairy the request message. If you make changes to the transmission mode, the radio will also send the signal back to the rs232. You have to be smart to request and immediately capture the receive messages.
Private Sub Timer1_Timer()
On Error Resume Next
inbuff = MSComm1.Input
n = 0
For i = Len(inbuff) To 1 Step -1 'reading the output
from right to left because icom sends frequency in this manner
n = n + 1
ang(n) = Hex(Asc(Mid(inbuff, i, 2))) ' ang(1),ang(2)...capture
byte info representing frequency sent by the radio.
Next
'Please observe what happen if you eliminate the if
val(ang(n)) lines. Just try it to understand why
If Val(ang(4)) < 10 And Len(ang(4)) < 2 Then ang(4) = "0" + ang(4)
If Val(ang(5)) < 10 And Len(ang(5)) < 2 Then ang(5) = "0" + ang(5)
If Val(ang(6)) < 10 And Len(ang(6)) < 2 Then ang(6) = "0" + ang(6)
If Val(ang(2)) = 0 Then Text2 = ang(3) + "." + ang(4) + Left(ang(5), 1) + "." + Right(ang(5), 1) + ang(6): Exit Sub
Text2 = ang(2) + ang(3) + "." + ang(4) + Left(ang(5), 1) + "." + Right(ang(5), 1) + ang(6)
'text2 is the frequency
End Sub
Text2 can represent the frequency field of the logbook.
The RS232 circuits are plentiful in the web, which cost less than RM8 (USD$3). For further expansion, refer to your rigs' manual. Simpel eh! ? We all should thank to many people for making life easy for us. They cracked their head for mankind.
I don't know the algorithm in Commander and other programmers. Many a time I feel shy to let people read the codings. Let us all explore.
by 9M2AR - Abdul Rahman
Below is the modification made by 9V1CP (Leow). He put the timer1 interval to 500. You can test with different speed.
Private Sub Timer1_Timer()
On Error Resume Next
inbuff = MSComm1.Input
n = 0
For i = Len(inbuff) To 1 Step -1 'reading the output from right to left because icom sends frequency in this manner
n = n + 1
ang(n) = Hex(Asc(Mid(inbuff, i, 2))) ' ang(1),ang(2)...capture byte info representing frequency sent by the radio.
Next
'Please observe what happen if you eliminate the if val(ang(n)) lines. Just try it to understand why
Text1 = ang(1)
Text2 = ang(2)
Text3 = ang(3)
Text4 = ang(4)
Text5 = ang(5)
Text6 = ang(6)
a2 = ang(2) * 100
a4 = ang(4) / 100
a5 = ang(5) / 10000
a6 = ang(6) / 1000000
Text22 = a2 + ang(3) + a4 + a5 + a6
Text22 = Format(Text22, "0.000.00") ' Display format
End Sub
EXTRACTING MODE FROM INPUT BUFFER
Your radio does not tell you the mode by showing 'LSB','USB"
etc. When you request for mode you send decimal 4 to the radio MSComm1.Output = Chr(254) & Chr(254) &
Chr(xx) & Chr(224) & Chr(4) & Chr(253) .
In the routine below ang(3) will show you the number which represent the mode.
The mode request in my programmig was made during the choice of radio from the
combo box. The timer routine will first response to this request, for the mode.
At the end of the procedure is the requests for frequency. If you put a flag to
bypass the ang(3) I think it is better. You can always use 9V1CP's routine and
test it out.
Private Sub Timer6_Timer()
On Error GoTo kel
inbuff = MSComm1.Input
numbe = 0
For i = Len(inbuff) To 1 Step -1
'an = Hex(Asc(Mid(inbuff, i, 2))): htd
numbe = numbe + 1
'Text1 = Text1 & Hex(Asc(Mid(inbuff, i, 2))) & " "
ang(numbe) = Hex(Asc(Mid(inbuff, i, 2)))
Next
If Val(ang(4)) < 10 And Len(ang(4)) < 2 Then ang(4) = "0" + ang(4)
If Val(ang(5)) < 10 And Len(ang(5)) < 2 Then ang(5) = "0" + ang(5)
If Val(ang(6)) < 10 And Len(ang(6)) < 2 Then ang(6) = "0" + ang(6)
'put a flag to bpass the routine below. So far I don't
have problem with the routine in my logbook.
If ang(3) = "0" Then Text23 = "LSB": GoTo kel
If ang(3) = "1" Then Text23 = "USB": GoTo kel
If ang(3) = "2" Then Text23 = "AM": GoTo kel
If ang(3) = "3" Then Text23 = "CW": GoTo kel
If ang(3) = "4" Then Text23 = "RTTY": GoTo kel
If ang(3) = "5" Then Text23 = "FM": GoTo kel
If ang(3) = "6" Then Text23 = "WFM": GoTo kel
' end of flag. Text22 is the frequency display on the
logbook
Text22 = ang(2) + ang(3) + "." + ang(4) + Left(ang(5), 1) + "." + Right(ang(5), 1) + ang(6): Exit Sub
kel:
If Err = 8018 Then Exit Sub 'error trap in case of no
handshaking
MSComm1.Output = Chr(254) & Chr(254) & Chr(xx) & Chr(224) & Chr(3) & Chr(253)
'xx is the address of various transceivers.
End Sub
BASIC MEMORY MANAGEMENT
Basically the memory can be called back by your program. You need to declare nnn. You can modified lines if nnn=10 or nnn=26 .... by replacing with the formula which you can devise. As for the the down button, you can use <. Chage the + sign to - sign.
Private Sub Command25_Click() ' Place > on the button
nnn = nnn + 1:
If nnn = 10 Or nnn = 26 Or nnn = 42 Or nnn = 58 Or nnn = 74 Or nnn = 90 Then nnn = nnn + 7
'channels available
MSComm1.Output = Chr(254) & Chr(254) & Chr(xx) & Chr(224) & Chr(8) & Chr(nnn) & Chr(253)
'Memory channel
MSComm1.Output = Chr(254) & Chr(254) & Chr(xx) & Chr(224) & Chr(3) & Chr(253)
'reading back the frequency
End Sub
Notice my logbook has included the S-Meter. I don't put any scale yet. I don't know the proper way to do it. I just do it blindly. Running the S-meter command would disturb all other operations because of the continueous feedback of data from the transceiver. I use 3 timers to make it work; for the S-Meter, frequency and mode. The timer for S-Meter and frequency toggle with each other to make sure only one procedure runs at a time. Timer for mode is only activated when there is a change in frequency textbox. After reading the mode it is disabled. If you want to follow this silly idea you have to adjust the timer interval and the counter. The codes below is just my silly idea.
Private Sub Timer6_Timer()
On Error GoTo kel
nnn = nnn + 1: If nnn > 10 Then nnn = 0: Timer6.Enabled = False: Timer7.Enabled = True
MSComm1.Output = Chr(254) & Chr(254) & Chr(xx) & Chr(224) & Chr(3) & Chr(253)
' it is reading the frequency
inbuff = MSComm1.Input
numbe = 0
For i = Len(inbuff) To 1 Step -1
numbe = numbe + 1
ang(numbe) = Hex(Asc(Mid(inbuff, i, 2)))
Next
If Val(ang(4)) < 10 And Len(ang(4)) < 2 Then ang(4) = "0" + ang(4)
If Val(ang(5)) < 10 And Len(ang(5)) < 2 Then ang(5) = "0" + ang(5)
If Val(ang(6)) < 10 And Len(ang(6)) < 2 Then ang(6) = "0" + ang(6)
If InStr(ang(6), "E") > 0 Then Exit Sub 'filtering garbage - You can just put
the lines below on one line. Or choose the shortest way to do it
If InStr(ang(5), "E") > 0 Then Exit Sub 'filtering garbage
If InStr(ang(4), "E") > 0 Then Exit Sub 'filtering garbage
If InStr(ang(3), "E") > 0 Then Exit Sub 'filtering garbage
If InStr(ang(2), "E") > 0 Then Exit Sub ' filtering garbage
If InStr(ang(1), "E") > 0 Then Exit Sub 'filtering garbage
Text22 = ang(2) + ang(3) + "." + ang(4) + Left(ang(5), 1) + "." + Right(ang(5), 1) + ang(6):
End Sub
Private Sub Timer8_Timer()
On Error Resume Next
nnn = nnn + 1: If nnn > 10 Then nnn = 0: Timer8.Enabled = False: Timer7.Enabled = True
'triggering the S-Meter reading
MSComm1.Output = Chr(254) & Chr(254) & Chr(110) & Chr(224) & Chr(4) & Chr(253)
'Reading the mode
inbuff = MSComm1.Input
numbe = 0
For i = Len(inbuff) To 1 Step -1
'an = Hex(Asc(Mid(inbuff, i, 2))): htd
numbe = numbe + 1
'Text1 = Text1 & Hex(Asc(Mid(inbuff, i, 2))) & " "
ang(numbe) = Hex(Asc(Mid(inbuff, i, 2)))
Next
If InStr(ang(3), "E") > 0 Then Exit Sub 'filtering garbage. Garbage comes from
other request if timing is not accurate
If InStr(ang(3), "15") > 0 Then Exit Sub 'filtering garbage
If InStr(ang(3), "E") > 0 Then Exit Sub 'filtering garbage
If InStr(ang(3), "7") > 0 Then Exit Sub 'filtering garbage
If ang(4) <> "4" Then Exit Sub
If ang(3) = "0" And Len(ang(3)) = 1 Then Text23 = "LSB": exit sub
If ang(3) = "1" And Len(ang(3)) = 1 Then Text23 = "USB": exit sub
If ang(3) = "2" And Len(ang(3)) = 1 Then Text23 = "AM": exit sub
If ang(3) = "3" And Len(ang(3)) = 1 Then Text23 = "CW": exit sub
If ang(3) = "4" And Len(ang(3)) = 1 Then Text23 = "RTTY": exit sub
If ang(3) = "5" And Len(ang(3)) = 1 Then Text23 = "FM": exit sub
If ang(3) = "6" And Len(ang(3)) = 1 Then Text23 = "WFM":
End Sub
Private Sub Timer7_Timer()
On Error Resume Next
nnn = nnn + 1: If nnn > 20 Then nnn = 0: Timer7.Enabled = False: Timer6.Enabled = True
MSComm1.Output = Chr(254) & Chr(254) & Chr(110) & Chr(224) & Chr(21) & Chr(2) & Chr(253)
'reading S-Meter
inbuff = MSComm1.Input
numbe = 0
For i = Len(inbuff) To 1 Step -1
'an = Hex(Asc(Mid(inbuff, i, 2))): htd
numbe = numbe + 1
'Text1 = Text1 & Hex(Asc(Mid(inbuff, i, 2))) & " "
ang(numbe) = Hex(Asc(Mid(inbuff, i, 2)))
Next
'nn = Val(ang(2)) + Val(ang(3)) * 100: If nn = 0 Then nn = 1 ' look for the nn
value by your method. ang(3) is from 0 to 99
ProgressBar1.Value = nn
' if it exceeds 99 ang(2)=1. I assume ang(2) is the db gain
End Sub
' lease find a smart way to translate the s-meter reading
Private Sub Text22_Change() 'only after frequency change it will look out for
mode
Timer8.Enabled = True
End Sub
I think this programm deals more with the proper timing. Below is my last version of coding. I find it is better than the above one.
'ang(4)<>"15" is to trigger the timer7. 15 is the continueous s-meter signal. When you press the mic up/dn or move your dial the value of ang(4) temporary change. Disabling timer7 is stopping the s-meter signal.Enabling timer6 is reading the frequency. We put vv=1 because we don't line the mscomm to activate this line until all other changes has taken place, like the frequency and the mode. The s-meter reading begins again at procedure mulac which is provided by timer9 that provide the long intercval.
Private Sub MSComm1_OnComm()
If ang(4) <> "15" And vv = 0 Then Timer7.Enabled = False: Timer6.Enabled = True: vv = 1
End Sub
Private Sub Timer9_Timer() 'timer9
interval is set to 2000 providing ample delay
mm = mm + 1
If mm = 1 Then
mm = 0
mulac ' to set up timer status
End If
End Sub
Private Sub mulac()
Timer6.Enabled = False
Timer8.Enabled = False
Timer7.Enabled = True
End Sub
Private Sub Timer6_Timer()
On Error GoTo kel
MSComm1.Output = Chr(254) & Chr(254) & Chr(xx) & Chr(224) & Chr(3) & Chr(253)
inbuff = MSComm1.Input
numbe = 0
For i = Len(inbuff) To 1 Step -1
numbe = numbe + 1
ang(numbe) = Hex(Asc(Mid(inbuff, i, 2)))
Next
If Val(ang(4)) < 10 And Len(ang(4)) < 2 Then ang(4) = "0" + ang(4)
If Val(ang(5)) < 10 And Len(ang(5)) < 2 Then ang(5) = "0" + ang(5)
If Val(ang(6)) < 10 And Len(ang(6)) < 2 Then ang(6) = "0" + ang(6)
If InStr(ang(6), "E") > 0 Then Exit Sub
If InStr(ang(5), "E") > 0 Then Exit Sub
If InStr(ang(4), "E") > 0 Then Exit Sub
If InStr(ang(3), "E") > 0 Then Exit Sub
If InStr(ang(2), "E") > 0 Then Exit Sub
If InStr(ang(1), "E") > 0 Then Exit Sub
Text22 = ang(2) + ang(3) + "." + ang(4) + Left(ang(5), 1) + "." + Right(ang(5), 1) +
ang(6)
kel: 'reserving this portion for any error coding
End Sub
Private Sub Timer7_Timer()
On Error Resume Next
nnn = nnn + 1: If nnn > 20 Then nnn = 0: vv = 0
MSComm1.Output = Chr(254) & Chr(254) & Chr(110) & Chr(224) & Chr(21) & Chr(2) & Chr(253)
inbuff = MSComm1.Input
numbe = 0
For i = Len(inbuff) To 1 Step -1
numbe = numbe + 1
ang(numbe) = Hex(Asc(Mid(inbuff, i, 2)))
Next
nn = Val(ang(2)) + Val(ang(3)) * 100: If nn = 0 Then nn = 1 'you
don't need to set nn to 1 if it is 0.This line sets the s-meter value
ProgressBar1.Value = nn 's-meter display
End Sub
Private Sub Timer8_Timer()
On Error Resume Next
nnn = nnn + 1: If nnn > 5 Then nnn = 0: Timer8.Enabled = False:
MSComm1.Output = Chr(254) & Chr(254) & Chr(110) & Chr(224) & Chr(4) & Chr(253)
inbuff = MSComm1.Input
numbe = 0
For i = Len(inbuff) To 1 Step -1
numbe = numbe + 1
ang(numbe) = Hex(Asc(Mid(inbuff, i, 2)))
Next
If InStr(ang(3), "E") > 0 Then Exit Sub
If InStr(ang(3), "15") > 0 Then Exit Sub
If InStr(ang(3), "E") > 0 Then Exit Sub
If InStr(ang(3), "7") > 0 Then Exit Sub
If ang(4) <> "4" Then GoTo kel
If ang(3) = "0" And Len(ang(3)) = 1 Then Text23 = "LSB": GoTo kel
If ang(3) = "1" And Len(ang(3)) = 1 Then Text23 = "USB": GoTo kel
If ang(3) = "2" And Len(ang(3)) = 1 Then Text23 = "AM": GoTo kel
If ang(3) = "3" And Len(ang(3)) = 1 Then Text23 = "CW": GoTo kel
If ang(3) = "4" And Len(ang(3)) = 1 Then Text23 = "RTTY": GoTo kel
If ang(3) = "5" And Len(ang(3)) = 1 Then Text23 = "FM": GoTo kel
If ang(3) = "6" And Len(ang(3)) = 1 Then Text23 = "WFM": GoTo kel
kel:
Timer9.Enabled = True 'to allow delay and set
timing
End Sub
' we trigger timer8 for mode retreival only after
frequency changed
Private Sub Text22_Change()
Timer8.Enabled = True
End Sub
For non-computer people this program is OK. From time to time it will be upgraded. The coding will certainly change. Good luck.