Code:
'------------------------------ General 18F2620 configuration --------------------------
#CONFIG
__CONFIG _CONFIG1H, _OSC_INTIO67_1H & _FCMEN_OFF_1H & _IESO_OFF_1H
__CONFIG _CONFIG2L, _PWRT_OFF_2L & _BOREN_OFF_2L
__CONFIG _CONFIG2H, _WDT_OFF_2H
__CONFIG _CONFIG3H, _PBADEN_OFF_3H & _LPT1OSC_OFF_3H & _MCLRE_OFF_3H
__CONFIG _CONFIG4L, _STVREN_OFF_4L & _LVP_OFF_4L & _XINST_OFF_4L & _DEBUG_OFF_4L
#ENDCONFIG
DEFINE OSC 32 'Set PicBasic Pro processor speed to 8 Mhz (Must change this if run at 32mhz mode)
OSCCON = %01110000 'Internal 8 mhz Osc and stable
OSCTUNE= %11000000 'Pllen Frequency Multiplier Enabled for 8mhz Clock enables 32mhz Clock!!
CMCON = %00000111 'Comparators Off
CVRCON = %00000000 'CvRef Powered Down
CCP1CON= %00001100 'CCP1 Module PWM Mode
CCP2CON= %00000000 'CCP2 Module Disabled
HLVDCON= %00000000 'HLVCON Disabled
T1CON = %00110000 '$30 = Prescaler 1:8, TMR1 OFF
TRISA = %00001011 'SET PORTA0, A1 & A3 AS INPUTS, REST AS OUTPUTS
TRISB = %00000000 'SET PORTB AS OUTPUTS
TRISC = %11010000 'SET PORTC AS OUTPUTS EXCEPT PORT C4 & C6,C7
ADCON0 = %00000001 'SETUP ADC & ENABLE ADC MODULE on AN0
ADCON1 = %00001110 'SETUP ADC SET REFV to VDD & VSS AN0
ADCON2 = %00100010 'SETUP ADC FOSC/32 LEFT JUSTIFY TAD 8
DEFINE LCD_DREG PORTB 'PORTB is LCD data port
DEFINE LCD_DBIT 0 'PORTB.0 is the data LSB
DEFINE LCD_RSREG PORTC 'RS is connected to PORTC.0
DEFINE LCD_RSBIT 0
DEFINE LCD_EREG PORTC 'EN is connected to PORTC.1
DEFINE LCD_EBIT 1
DEFINE LCD_BITS 8 '8 lines of data are used
DEFINE LCD_LINES 4 'It is a 4-line display
DEFINE LCD_COMMANDUS 2000 'Use 2000uS command delay
DEFINE LCD_DATAUS 50 'Use 50uS data delay
DEFINE ADC_BITS 8 'Set number of bits in result
DEFINE ADC_CLOCK 3 'Set Clock source (3 = rc)
DEFINE ADC_SAMPLEUS 50 'Set sampling time in uS
DEFINE CCP1_REG PORTC 'HPWM channel 1 pin Port C Backlight PWM Driver
DEFINE CCP1_BIT 2 'HPWM channel 1 pin Bit 2
'Setup the hardware USART for 9600 baud
DEFINE HSER_BAUD 9600 'Set Baud rate to 9600bps
DEFINE HSER_BITS 9 'Set to 9 bit mode
DEFINE HSER_EVEN 1 'Set Even Parity
DEFINE HSER_CLROERR 1 'Clear overflow error automatically
'Button var PORTA.0 'Joy Button Input
HLineIn var PORTA.1 'H Line In
HLineOut var PORTA.2 'H Line Out
KLineIn var PORTA.3 'K Line In
KLineOut var PORTA.4 'K Line Out
GreenLed var PORTA.5 'Green Led Out
Scs var PORTA.6 'SCS Line Out
Piezo var PORTA.7 'Piezo Buzzer Out
Lcd0 var PORTB.0 'Parallel Lcd0
Lcd1 var PORTB.1 'Parallel Lcd1
Lcd2 var PORTB.2 'Parallel Lcd2
Lcd3 var PORTB.3 'Parallel Lcd3
Lcd4 var PORTB.4 'Parallel Lcd4
Lcd5 var PORTB.5 'Parallel Lcd5
Lcd6 var PORTB.6 'Parallel Lcd6
Lcd7 var PORTB.7 'Parallel Lcd7
LcdRS var PORTC.0 'Parallel LcdRS Line
LcdEN var PORTC.1 'Parallel LcdEN Line
LcdLight var PORTC.2 'Parallel Lcd Backlight Control
I2CClock var PORTC.3 'I2CClock Line
I2CData var PORTC.4 'I2CData Line
RedLed var PORTC.5 'Red Led Out
'Txd var PORTC.6 'Usart Logger Txd
'Rxd var PORTC.7 'Usart Logger Rxd
'*******************************************************************************
'Variables Constants and I/O definitions
'------------------------ Variables 16bit --------------------------------------
'------------------- Variables 8bit --------------------------------------------
IChkSum var BYTE 'MotA Line rolling Checksum Byte
AssistLevel var byte 'Shows level of Ima Assist
RegenLevel var byte 'Shows level of Ima Regen
FlagBits var BYTE 'Flag Bits Byte (0-7)
DutyCycle var BYTE 'PWM DutyCycle for Lcd backlight [127 = 50% duty]
Key var BYTE 'Returned Button Value (0-5) 5 = No key pressed
Gen var BYTE 'Gen is a General Use Byte variable (0-255)
ImaCtrl var BYTE 'Ima Control Byte 0-8 (0-3 = Regen) 4 = Off (5-8 = Assist)
LCM VAR BYTE 'Lcd Command Code 254
LCL VAR BYTE 'Lcd Control Code Clear Lcd
L12 VAR BYTE 'Lcd Control Code Line 1 Column 0
L22 VAR BYTE 'Lcd Control Code Line 2 Column 0
L32 VAR BYTE 'Lcd Control Code Line 3 Column 0
L42 VAR BYTE 'Lcd Control Code Line 4 Column 0
L52 VAR BYTE 'Lcd Control Code Line 1 Column 10
L62 VAR BYTE 'Lcd Control Code Line 2 Column 10
L72 VAR BYTE 'Lcd Control Code Line 3 Column 10
L82 VAR BYTE 'Lcd Control Code Line 4 Column 10
'------------------- Variables 1bit --------------------------------------------
AssistBit var FlagBits.Bit1 'Assist Bit Shows when Ima Assist in operation.
RegenBit var FlagBits.Bit2 'Regen Bit Show when Ima Regen in operation.
'------------------------------ Main Program -----------------------------------
EEPROM 1014, [254,1,128,192,148,212,138,202,158,222] '20x4 Lcd Control Codes
'**************************************************************************************************************
'Alias & Vars
RCIF VAR PIR1.5 'Receive interrupt flag (1=full , 0=empty)
TXIF VAR PIR1.4 'Transmit interrupt flag (1=empty, 0=full)
OERR VAR RCSTA.1 'Alias OERR (USART Overrun Error Flag)
CREN VAR RCSTA.4 'Alias CREN (USART Continuous Receive Enable)
Ptr_in VAR BYTE 'Pointer - next empty location in buffer
ErrFlag VAR BYTE 'Holds error flags
ptr_in = 0 'Clear buffer pointer (in)
Errflag = 0 'Clear error flag
Char var byte 'Define Char as the data byte being sent
RCSTA.7 = 1 'Configue PortC 6 & 7 as Usart
BAUDCON.4 = 1 'Invert USART Output for use with Transistor driver TXCKP
'-----------------------------------------------------------------------------
INCLUDE "DT_INTS-18.bas"
INCLUDE "ReEnterPBP-18.bas" 'Include if using PBP interrupts
ASM
INT_LIST macro ;IntSource, Label, Type, ResetFlag?
INT_Handler RX_INT, _INT_Serin, PBP, no
endm
INT_CREATE ;Creates the interrupt processor
ENDASM
@ INT_ENABLE RX_INT ;Enable external (INT) interrupts
'-----------------------------------------------------------------------------
'***********************************************************************
'Skip over the interupt handler & subroutines
goto Start
'***********************************************************************
'-------------------------------------
' INTERUPT HANDLER
'-------------------------------------
INT_Serin: 'Serial Interrupt routine
IF OERR Then usart_error 'Check for USART errors
HSerin [Char] 'Read USART
if Char = $B3 then 'Start of 9 byte packet
Ptr_In = 0 'Reset Ptr_In to 0
IChkSum = 0 'Clear Checksum Byte
else
Ptr_In = Ptr_In + 1 'Increment pointer
endif
If Ptr_In = 1 then 'If Byte is 1 then check if assist or regen requested
If AssistBit = 1 then Char = %00010000 'Modify byte 1 for Ima Assist Control = 16 Normal
if RegenBit = 1 then Char = %00100000 'Modify byte 1 for Ima Regen Control = 32 Normal
endif
If Ptr_In = 2 then 'If Byte is 2 then check if assist or regen requested
if AssistBit = 1 then Char = AssistLevel 'Load Char byte 2 with Ima Assist Value 0-127 = 0-100%
if RegenBit = 1 then Char = RegenLevel 'Load Char byte 2 with Ima Regen Value 127-0 = 0-100%
endif
If Ptr_In = 5 then 'If Byte is 5 then check if Regen requested
If AssistBit = 1 then Char = %00100001 'Modify byte 5 for Ima Assist Control = 33
if RegenBit = 1 then Char = %00000001 'Modify byte 5 for Ima Regen Control = 1
endif
if Ptr_In = 8 then 'Calculate IChkSum Byte
IChkSum = ~ IChkSum 'NOT CheckSum
IChkSum = IChkSum + 1 'Add 1 to CheckSum
Char = IChkSum & $7F 'AND $7F
else
IChkSum = IChkSum + Char 'Add Char to accumulated data
endif
hserout [Char] 'Sends data
IF RCIF = 1 Then INT_Serin 'Check for another character while we're here
Toggle RedLed 'Flash the Red Led
@ INT_RETURN 'Return to program
USART_Error: 'Error - USART has overrun (data too fast?)
errflag.0 = 1 'Set the error flag for hardware
CREN = 0 'Disable continuous receive to clear overrun flag
CREN = 1 'Enable continuous receive
@ INT_RETURN 'Return to program
'**************************************************************************************************************
'OBDII Gauge Main Program
Start: 'Start of Program
ImaCtrl = 4 'Ima Control Byte = 4 (No Assist or Regen)
Gosub SetIma 'Gosub Set Ima Routine
Read 1014,LCM,LCL,L12,L22,L32,L42,L52,L62,L72,L82 'Load 20x4 Lcd Control Codes from EEprom adr
HPWM 1, 255, 500 'Change/Start 500hz HPWM 'Set Backlight Duty 0 = Off 255 = FullOn
Pause 2000 'Pause for 2.0 seconds
LCDOUT LCM,LCL
'**************************************************************************************************************
DispLoop: 'Main Loop goes here
Toggle GreenLed 'Flashes Green Led
'***************************** Key Functions KeyBit 0 ****************************************
'*Key Check*
Gosub KeyPress 'Gosub KeyPress Routine 5 = No Key Pressed
'*Key Bit Toggle* Press
if Key = 0 then 'If Key = 0 (Press) then
ImaCtrl = 4 'Ima Control Byte = 4 (No Assist or Regen)
Gosub SetIma 'Gosub Set Ima Routine
endif
'*Assist Up / Regen Down* Button Right
if Key = 2 then 'If Key = 2 (Right) and KeyBit = 0 then (Toggle Assist Bit)
If ImaCtrl < 8 then ImaCtrl = ImaCtrl + 1 'Increment ImaCtrl Byte if < 8
Gosub SetIma 'Gosub Set Ima Routine
endif
'* Assist Down / Regen Up* Button Left
if Key = 4 then 'If Key = 4 (Left) and KeyBit = 0 then (Toggle Regen Bit)
If ImaCtrl > 0 then ImaCtrl = ImaCtrl - 1 'Decrement ImaCtrl Byte if > 0
Gosub SetIma 'Gosub Set Ima Routine
endif
'* Display Assist/Regen Status on Screen
LCDOUT LCM,146 'Set Display to Line 1, Column 19
if AssistBit = 1 then LCDOUT "A",#4 - (8-ImaCtrl) 'Display Assist Data on screen if active
if RegenBit = 1 then LCDOUT "R",#4 - ImaCtrl 'Display Regen Data on screen if active
if AssistBit = 0 and RegenBit = 0 then LCDOUT 32,32 'Blank Assist/Regen data if not active
pause 250
goto DispLoop 'Goto Main Loop
'****************************** Set Ima Routine *******************************
SetIma: 'Set Ima Routine 4 levels of assist/regen 25,50,75,100%
If ImaCtrl = 0 then 'If ImaCtrl = 0 then set Regen 100%
RegenLevel = 0 'Set Regen to 100%
RegenBit = 1 'Set Regen Bit (Regen On)
elseif ImaCtrl = 1 then 'If ImaCtrl = 1 then set Regen 75%
RegenLevel = 64 'Set Regen to 75%
RegenBit = 1 'Set Regen Bit (Regen On)
elseif ImaCtrl = 2 then 'If ImaCtrl = 2 then set Regen 50%
RegenLevel = 96 'Set Regen to 50%
RegenBit = 1 'Set Regen Bit (Regen On)
elseif ImaCtrl = 3 then 'If ImaCtrl = 3 then set Regen 25%
RegenLevel = 116 'Set Regen to 25%
RegenBit = 1 'Set Regen Bit (Regen On)
elseif ImaCtrl = 4 then 'If ImaCtrl = 4 then set Assist & Regen to 0%
RegenLevel = 0 'Set Regen to 0%
RegenBit = 0 'Clear Regen Bit (Regen Off)
AssistLevel = 0 'Set Assist to 0%
AssistBit = 0 'Clear Assist Bit (Assist Off)
elseif ImaCtrl = 5 then 'If ImaCtrl = 5 then set Assist 25%
AssistLevel = 15 'Set Assist to 25%
AssistBit = 1 'Set Assist Bit (Assist On)
elseif ImaCtrl = 6 then 'If ImaCtrl = 6 then set Assist 50%
AssistLevel = 35 'Set Assist to 50%
AssistBit = 1 'Set Assist Bit (Assist On)
elseif ImaCtrl = 7 then 'If ImaCtrl = 7 then set Assist 75%
AssistLevel = 76 'Set Assist to 75%
AssistBit = 1 'Set Assist Bit (Assist On)
elseif ImaCtrl = 8 then 'If ImaCtrl = 8 then set Assist 100%
AssistLevel = 126 'Set Assist to 126
AssistBit = 1 'Set Assist Bit (Assist On)
endif
return 'Return to Main Program
'****************************** Buttons Routine *******************************
'Check Button is pressed > Push = 0 Up = 1 Right = 2 Down = 3 Left = 4 No Key = 5 (Count1 = Press Duration)
KeyPress: 'Decodes Joybutton Input and returns 5 values (0,1,2,3,4) in Key
ADCIN 0, Gen 'Get value 0-255
key = 5 'Set Default value for Key
If Gen > 234 then return 'If No key pressed then key = 5 return
if Gen < 235 then key = 2 'Test if button 2 pressed Right
if Gen < 192 then key = 1 'Test if button 1 pressed Up
if Gen < 150 then key = 4 'Test if button 4 pressed Left
if Gen < 107 then key = 3 'Test if button 3 pressed Down
if Gen < 64 then key = 0 'Test if button 0 pressed Press
High Piezo 'Sound Piezo
pause 75 'Pause for 0.075 seconds
low Piezo 'Stop Piezo
return 'Return to main program
Bookmarks