Differences

This shows you the differences between two versions of the page.

Link to this comparison view

atmel:gpslcdsource [2009/11/27 17:53] (current)
Line 1: Line 1:
 +<code vb>
 +'​********************************************************************
 +'* GPS Coordinate display on LCD
 +'* uP:          AT89S8313
 +'* Language: ​   BASCOM-AVR 1.11.7.4
 +'* Date:        2005.Jan.22
 +'* Version: ​    V2.00
 +'* Author: ​     Brett England
 +'​********************************************************************
 +$regfile = "​2313def.dat"​
 +$crystal = 8000000
 +$baud = 4800
  
 +' condition compilation flag
 +Const Debug = 0
 +
 +#if Debug
 +  Dim Temp_i As Byte
 +#endif
 +
 +Dim Rs232_exit As Byte                            ' Sec count for RS232 timeout
 +Dim Read_ok As Bit                                ' Valid GPS frame found
 +Dim Data_ok As Bit                                ' Start of GPS frame
 +Dim Read_num As Byte                              ' RS232 character count
 +
 +Dim S2 As String * 16                             '​ LCD output buffer
 +
 +Dim Gps_state As Bit
 +Dim Gps_date As String * 7                        ' DDMMYY + comma
 +Dim Gps_time As String * 6                        ' HHMMSS
 +Dim Latitude As String * 9
 +Dim Longitude As String * 10
 +Dim North_south As Byte                           '​ N/S
 +Dim East_west As Byte                             '​ E/W
 +
 +Dim Spin_c As Bit                                 '​ Toggles when no data Rx
 +
 +Dim Temp_j As Byte
 +
 +Dim Time1_count As Byte                           '​ Second ticker
 +Dim Time1_store As Byte
 +Dim Time1_ok As Bit                               '​ Internal timer overflow ind
 +Dim Eventime As Bit                               '​ Set every other second
 +
 +Config Lcdpin = Pin , Db4 = Portb.4 , Db5 = Portb.5 , Db6 = Portb.6 , Db7 = Portb.7 , E = Portb.3 , Rs = Portb.2
 +Config Lcd = 16 * 1                               '​configure lcd screen
 +
 +
 +' Once enabled, the timer counts each clock period (or you can select a
 +' divided down input clock if you prefer). When the timer overflows (65536
 +' counts) you get an interrupt. With a 8MHz clock, this doesn'​t work out to
 +' anything very useful. At 8MHz, each clock pulse is 125nS and 65536 of them
 +' is 8.192 milliseconds.
 +
 +' I want a timer that resolves to 1000mS, so the first step is to divide down
 +' the input clock .  Input clock to divide by 256, so now each clock pulse is
 +' worth (8.192/​256)=32uS.
 +
 +' The trick is to preload the counter with a value that will cause it to count
 +' for 1000mS. Each time the counter expires, you can force the new number back
 +' into the timer register. We need 1/.000032 or 31250 counts. However, the
 +' counter expires at 65536, so the correct number to preload is 65536-31250 or
 +' 34285 This way, the timer will count up 31250 counts (1 second) and
 +' expire.
 +
 +Const 1000ms = 34285
 +Config Timer1 = Timer , Prescale = 256
 +
 +On Timer1 Timer1_int ​                             ' Timer Overflow ISR
 +On Urxc Rec_rs232 ​                                '​ Serial Rx ISR
 +
 +Cls
 +Cursor Off Noblink
 +
 +Time1_count = 0 : Timer1 = 1000ms : Time1_ok = 0 : Spin_c = 0
 +
 +Start Timer1
 +Enable Timer1
 +Enable Interrupts
 +
 +' Main Program LOOP
 +' ​  ​Screen updates rotate every 2 seconds
 +' ​     T+1 - Latitude
 +' ​     T+3 - Longitude
 +' ​     T+5 - Date/Time
 +' ​  GPS unit polling occurs at
 +' ​     T+0,T+2,T+4
 +Do
 +  If Time1_ok = 1 Then
 +      Read_ok = 0 : Read_num = 0 : Data_ok = 0
 +
 +      Stop Timer1
 +      ' Every even second check GPS
 +      If Eventime = 0 Then
 +         ​Gps_date = ""​ : Gps_time = ""​ : Latitude = ""​ : Longitude = ""​
 +         ​Gps_state = 0
 +         Gosub Rs232_r
 +      Else
 +        ' Odd duty cycle tasks (2sec spacing)
 +        If Time1_count = 1 Then
 +           If North_south = 78 Then               '​ "​N"​ -> 78
 +              S2 = "North "
 +           Else
 +              S2 = "South "
 +           End If
 +           S2 = S2 + Latitude
 +         ​Elseif Time1_count = 3 Then
 +           If East_west = 69 Then                 '​ "​E"​ -> 69
 +              S2 = "East "
 +           Else
 +              S2 = "West "
 +           End If
 +           S2 = S2 + Longitude
 +         ​Elseif Time1_count = 5 Then
 +           S2 = Gps_date + " " + Gps_time
 +         End If
 +      End If
 +
 +' Animate symbol to show activity when no valid GPS data found
 +      If Gps_state = 0 Then
 +         S2 = "No GPS Frame "
 +         If Spin_c = 0 Then
 +            S2 = S2 + "​*"​
 +            Set Spin_c
 +         Else
 +            S2 = S2 + "​+"​
 +            Reset Spin_c
 +         End If
 +      End If
 +
 +      Cls
 +      Lcd S2
 +
 +      Reset Time1_ok
 +      Start Timer1
 +   End If
 +Loop
 +
 +' Timer interrupt handler
 +Timer1_int:
 +   ​Timer1 = 1000ms
 +   Set Time1_ok
 +   Incr Time1_count
 +   Incr Rs232_exit
 +   If Time1_count > 5 Then Time1_count = 0        ' 6sec wrap - 0..5
 +   ​Eventime = Time1_count.0
 +   ​Return
 +
 +' Decode the following string from an Etrex GPS receiver
 +'​$GPRMC,​103044,​A,​5125.5210,​N,​00012.3645,​W,​0.0,​304.9,​290105,​2.6,​W,​A*1E
 +'​12345678901234567890123456789012345678901234567890123456789012345678
 +' ​        ​11111111112222222222333333333344444444445555555555666666666
 +Rec_rs232:
 +   Incr Read_num
 +
 +   If Udr = 36 Then                               '"​$"​-->​36
 +      Read_num = 1 : Data_ok = 1 : Temp_j = 0
 +   ​Elseif Data_ok = 1 Then
 +      Select Case Read_num
 +         Case 6:
 +            If Udr <> 67 Then Data_ok = 0         '"​C"​-->​67
 +         Case 8 To 13:
 +            Gps_time = Gps_time + Chr(udr)
 +         Case 15:
 +            If Udr = 65 Then Gps_state = 1        '"​A"​-->​65
 +         Case 17 To 25:
 +            Latitude = Latitude + Chr(udr)
 +         Case 27:
 +             ​North_south = Udr                    ' N/S indicator
 +         Case 29 To 38:
 +            Longitude = Longitude + Chr(udr)
 +         Case 40:
 +             ​East_west = Udr                      ' E/W indicator
 +' The next two parameters after E/W indicator are:
 +' Speed over ground, Course over ground - They vary dynamically in size.
 +         Case Is > 40:
 +' Note: The gps_date var will contain the date plus the trailing comma.
 +' Start on 3rd comma after E/W indicator
 +            If Temp_j = 3 Then Gps_date = Gps_date + Chr(udr)
 +            If Udr = 44 Then Incr Temp_j ​                   '","​-->​44
 +            If Temp_j >= 4 Then Read_ok = 1
 +      End Select
 +   End If
 +
 +   #if Debug
 +       '​ Display 1st 16 characters after $ (should be a GPS message)
 +       '​ Note: With this code enabled the interrupt may take too long
 +       ' ​      to service URXC and characters can be dropped.
 +       If Data_ok = 1 And Read_num < 17 Then
 +         ​Locate 1 , Read_num
 +         Lcd Chr(udr)
 +       End If
 +   #​endif
 +
 +   ​Rs232_exit = 0
 +   ​Return
 +
 +Rs232_r:
 +#if Debug
 +   ​Locate 1 , 1
 +   Lcd "​Reading GPS"
 +#endif
 +   Reset Usr.7
 +   Reset Ucr.7
 +   ​Enable Urxc
 +   ​Rs232_exit = 0
 +   '​ Don't let the RS232 timeout code affect the next task in the main loop.
 +   ​Time1_store = Time1_count
 +   Start Timer1
 +   Do
 +   '​ The GPS unit sends data every 2secs, so on the 3rd sec if no data has
 +   '​ been received then stop waiting.
 +      If Rs232_exit > 2 Then Exit Do
 +   Loop Until Read_ok = 1
 +   ​Disable Urxc                                   '​disable receive ISR
 +   Stop Timer1
 +   ​Time1_count = Time1_store
 +   ​Return
 +</​code>​
 +{{tag>​bascom programming avr}}