Continue to Site

Welcome to our site!

Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

  • Welcome to our site! Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

Assembly project with pic16f887 lcd and special character generation

Status
Not open for further replies.

runman_up

New Member
does anyone know the assembly code for pic 16f that can generate the special CGRAM character codes - I suspect it is fairly straightforward - I just don't know it - -

thanks

Richard
 
This should be all you need to get started.
For the LCD commands, check Nigel's site;

Code:
UDG					;User defined graphics
	call	LCD_Init
	movlw	0x40	;CGRAM Address
	call	LCD_Cmd
		
;----------User defined bit------

;-------------0x00---------------First character
movlw	 0x0E
call	LCD_Char
movlw	 0x11
call	LCD_Char
movlw	 0x11
call	LCD_Char
movlw	 0x11
call	LCD_Char
movlw	 0x1F
call	LCD_Char
movlw	 0x1B
call	LCD_Char
movlw	 0x1B
call	LCD_Char
movlw	 0x1F
call	LCD_Char

;-------------0x01---------------Second character
movlw	 0x0E
call	LCD_Char
movlw	 0x11
call	LCD_Char
movlw	 0x10
call	LCD_Char
movlw	 0x10
call	LCD_Char
movlw	 0x1F
call	LCD_Char
movlw	 0x1B
call	LCD_Char
movlw	 0x1B
call	LCD_Char
movlw	 0x1F	
call	LCD_Char

;-------------0x02---------------Third character
movlw	 0x0A
call	LCD_Char
movlw	  0x0A
call	LCD_Char
movlw	  0x0A
call	LCD_Char
movlw	 0x1F
call	LCD_Char
movlw	 0x1F
call	LCD_Char
movlw	 0x0E
call	LCD_Char
movlw	 0x0E
call	LCD_Char
movlw	 0x04	
call	LCD_Char

;-------------0x03---------------Forth character
movlw	 0x10
call	LCD_Char
movlw	 0x10
call	LCD_Char
movlw	 0x10
call	LCD_Char
movlw	 0x10
call	LCD_Char
movlw	 0x10
call	LCD_Char
movlw	 0x10
call	LCD_Char
movlw	 0x10
call	LCD_Char
movlw	 0x10	
call	LCD_Char

;-------------0x04---------------Fifth character
movlw	 0x18
call	LCD_Char
movlw	 0x18
call	LCD_Char
movlw	 0x18
call	LCD_Char
movlw	 0x18
call	LCD_Char
movlw	 0x18
call	LCD_Char
movlw	 0x18
call	LCD_Char
movlw	 0x18
call	LCD_Char
movlw	 0x18	
call	LCD_Char

;-------------0x05---------------Sixth character
movlw	 0x1C
call	LCD_Char
movlw	 0x1C
call	LCD_Char
movlw	 0x1C
call	LCD_Char
movlw	 0x1C
call	LCD_Char
movlw	 0x1C
call	LCD_Char
movlw	 0x1C
call	LCD_Char
movlw	 0x1C
call	LCD_Char
movlw	 0x1C	
call	LCD_Char

;-------------0x06---------------Seventh character
movlw	 0x1E	
call	LCD_Char
movlw	 0x1E
call	LCD_Char
movlw	 0x1E
call	LCD_Char
movlw	 0x1E
call	LCD_Char
movlw	 0x1E
call	LCD_Char
movlw	 0x1E
call	LCD_Char
movlw	 0x1E
call	LCD_Char
movlw	 0x1E	
call	LCD_Char

;-------------0x07---------------Eigth character
movlw	 0x1F
call	LCD_Char
movlw	 0x1F
call	LCD_Char
movlw	 0x1F
call	LCD_Char
movlw	 0x1F
call	LCD_Char
movlw	 0x1F
call	LCD_Char
movlw	 0x1F
call	LCD_Char
movlw	 0x1F
call	LCD_Char
movlw	 0x1F	
call	LCD_Char




	movlw	0x80		;move to 1st row, first column
	call	LCD_Cmd

			;Display characters.
							
movlw	 0x00			 ;First character
call	LCD_Char

movlw	 0x01			 ;Second character			
call	LCD_Char

movlw	 0x02			 ;Third character
call	LCD_Char

movlw	 0x03			 ;Forth character
call	LCD_Char

movlw	 0x04			 ;Fifth character
call	LCD_Char

movlw	 0x05			 ;Sixth character
call	LCD_Char

movlw	 0x06			 ;Seventh character
call	LCD_Char

movlw	 0x07			 ;Eigth character
call	LCD_Char

Character generator; http://www.dinceraydin.com/lcd/charcalc.htm
Though it gives decimal values, not HEX.
 
Last edited:
What pins (data/control) do you have on the display unit? Is there a part number and/or data sheet of the display unit itself?
 
Cant quite get it to work -

I initiate the LCD and can send ASCI characters fine, I cannot get it to work with Characters I try to generate
For example I send a 'V' using

movlw 'V'
movwf temp_wr
call d_write

i send a command using LCDWriteNibble per below- how do I proceed?


;****************************************
CODE
#define LCD_D4 PORTD, 0 ; LCD data bits
#define LCD_D5 PORTD, 1
#define LCD_D6 PORTD, 2
#define LCD_D7 PORTD, 3

#define LCD_D4_DIR TRISD, 0 ; LCD data bits
#define LCD_D5_DIR TRISD, 1
#define LCD_D6_DIR TRISD, 2
#define LCD_D7_DIR TRISD, 3

;#define LCD_E PORTA, 1 ; LCD E clock
;#define LCD_RW PORTA, 2 ; LCD read/write line
;#define LCD_RS PORTA, 3 ; LCD register select line
;
;#define LCD_E_DIR TRISA, 1
;#define LCD_RW_DIR TRISA, 2
;#define LCD_RS_DIR TRISA, 3
;
#define LCD_E PORTD, 6 ; LCD E clock
#define LCD_RW PORTD, 5 ; LCD read/write line
#define LCD_RS PORTD, 4 ; LCD register select line

#define LCD_E_DIR TRISD, 6
#define LCD_RW_DIR TRISD, 5
#define LCD_RS_DIR TRISD, 4

#define LCD_INS 0
#define LCD_DATA 1



D_LCD_DATA UDATA 0x57
COUNTER res 1
delay res 1
temp_wr res 1
temp_rd res 1
pumpdel1 res 1
pumpdelh res 1
holdcnt res 1
timefast RES 1
ptemp_4l RES 1
GLOBAL temp_wr, pumpdel1, pumpdelh, holdcnt, timefast, ptemp_4l

PROG1 CODE


;***************************************************************************

LCDLine_1
banksel temp_wr
movlw 0x80
movwf temp_wr
call i_write
return
GLOBAL LCDLine_1

LCDLine_2
banksel temp_wr
movlw 0xC0
movwf temp_wr
call i_write
return
GLOBAL LCDLine_2

d_write ;write data
call LCDBusy
bsf STATUS, C
call LCDWrite
banksel TXREG ;move data into TXREG
movwf TXREG
banksel TXSTA
btfss TXSTA,TRMT ;wait for data TX
goto $-1
banksel PORTA
return
GLOBAL d_write

i_write ;write instruction
call LCDBusy
bcf STATUS, C
call LCDWrite
return
GLOBAL i_write

rlcd macro MYREGISTER
IF MYREGISTER == 1
bsf STATUS, C
call LCDRead
ELSE
bcf STATUS, C
call LCDRead
ENDIF
endm
;****************************************************************************




; *******************************************************************
LCDInit
banksel TRISD
bcf TRISD,7
banksel PORTD
bsf PORTD,7
call Delay30ms
clrf PORTA

banksel TRISA ;configure control lines
bcf LCD_E_DIR
bcf LCD_RW_DIR
bcf LCD_RS_DIR

movlw b'00001110'
banksel ADCON1
movwf ADCON1

movlw 0xff ; Wait ~15ms @ 20 MHz
banksel COUNTER
movwf COUNTER
movlw 0xFF
banksel delay
movwf delay
call DelayXCycles
decfsz COUNTER, F
goto $-3
;0x02------------------
; movlw b'00110000' ;#1 Send control sequence
movlw b'00100000' ;#1 Send control sequence
movwf temp_wr
bcf STATUS,C
call LCDWriteNibble

movlw 0xff ;Wait ~4ms @ 20 MHz
movwf COUNTER
movlw 0xFF
movwf delay
call DelayXCycles
decfsz COUNTER, F
goto $-3
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;28---2
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
; movlw b'00110000' ;#2 Send control sequence
movlw b'00100000' ;#2 Send control sequence
movwf temp_wr
bcf STATUS,C
call LCDWriteNibble

movlw 0xFF ;Wait ~100us @ 20 MHz
movwf delay
call DelayXCycles
;28--08
; movlw b'0011000' ;#3 Send control sequence
movlw b'10000000'
movwf temp_wr
bcf STATUS,C
call LCDWriteNibble

;test delay
movlw 0xFF ;Wait ~100us @ 20 MHz
movwf delay
call DelayXCycles

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;0C--0
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;

; movlw b'00100000' ;#4 set 4-bit
movlw b'00000000' ;#4 set 4-bit
movwf temp_wr
bcf STATUS,C
call LCDWriteNibble
;0x0C
movlw b'11000000' ;#4 set 4-bit
movwf temp_wr
bcf STATUS,C
call LCDWriteNibble



call Delay1ms
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;0x01
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
; movlw b'00100000' ;#4 set 4-bit
movlw b'00000000' ;#4 set 4-bit
movwf temp_wr
bcf STATUS,C
call LCDWriteNibble
;0x01
movlw b'00010000' ;#4 set 4-bit
movwf temp_wr
bcf STATUS,C
call LCDWriteNibble

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
call LongDelay ;2ms
call LongDelay ;2ms
call LongDelay ;2ms
call LongDelay ;2ms
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;0x02
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
movlw b'00000000' ;#4 set 4-bit
movwf temp_wr
bcf STATUS,C
call LCDWriteNibble
;0x02
movlw b'00100000' ;#4 set 4-bit
movwf temp_wr
bcf STATUS,C
call LCDWriteNibble
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
; rcall LCDBusy ;Busy?
call LongDelay ;2ms
call LongDelay ;2ms
call LongDelay ;2ms
call LongDelay ;2ms
call LongDelay ;2ms
call LongDelay ;2ms
call LongDelay ;2ms

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;


movlw 0x4E
movwf temp_wr
call LCDBusy
bsf STATUS, C
call LCDWrite


call Delay1ms
return

GLOBAL LCDInit
; *******************************************************************

LCDWriteNibble
GLOBAL LCDWriteNibble
btfss STATUS, C ; Set the register select
bcf LCD_RS
btfsc STATUS, C
bsf LCD_RS

bcf LCD_RW ; Set write mode

banksel TRISD
bcf LCD_D4_DIR ; Set data bits to outputs
bcf LCD_D5_DIR
bcf LCD_D6_DIR
bcf LCD_D7_DIR

NOP ; Small delay
NOP

banksel PORTA
bsf LCD_E ; Setup to clock data

btfss temp_wr, 7 ; Set high nibble
bcf LCD_D7
btfsc temp_wr, 7
bsf LCD_D7
btfss temp_wr, 6
bcf LCD_D6
btfsc temp_wr, 6
bsf LCD_D6
btfss temp_wr, 5
bcf LCD_D5
btfsc temp_wr, 5
bsf LCD_D5
btfss temp_wr, 4
bcf LCD_D4
btfsc temp_wr, 4
bsf LCD_D4

NOP
NOP

bcf LCD_E ; Send the data

return
; *******************************************************************

; *******************************************************************
LCDWrite
; call LCDBusy
call LCDWriteNibble
BANKSEL temp_wr
swapf temp_wr, f
call LCDWriteNibble
banksel temp_wr
swapf temp_wr,f

return

GLOBAL LCDWrite
; *******************************************************************





; *******************************************************************
; _____ _____________________________________________________
; RS _____>--<_____________________________________________________
; ____________________________________________________
; RW _________/
; ____________________ ____________________
; E ____________/ \____/ \__
; _________________ __________ ___
; DB _________________>--------------<__________>--------------<___
;
LCDRead
banksel TRISD
bsf LCD_D4_DIR ; Set data bits to inputs
bsf LCD_D5_DIR
bsf LCD_D6_DIR
bsf LCD_D7_DIR

BANKSEL PORTA
btfss STATUS, C ; Set the register select
bcf LCD_RS
btfsc STATUS, C
bsf LCD_RS

bsf LCD_RW ;Read = 1

NOP
NOP

bsf LCD_E ; Setup to clock data

NOP
NOP
NOP
NOP

btfss LCD_D7 ; Get high nibble
bcf temp_rd, 7
btfsc LCD_D7
bsf temp_rd, 7
btfss LCD_D6
bcf temp_rd, 6
btfsc LCD_D6
bsf temp_rd, 6
btfss LCD_D5
bcf temp_rd, 5
btfsc LCD_D5
bsf temp_rd, 5
btfss LCD_D4
bcf temp_rd, 4
btfsc LCD_D4
bsf temp_rd, 4

bcf LCD_E ; Finished reading the data

NOP
NOP
NOP
NOP
NOP
NOP
NOP
NOP

bsf LCD_E ; Setup to clock data

NOP
NOP

btfss LCD_D7 ; Get low nibble
bcf temp_rd, 3
btfsc LCD_D7
bsf temp_rd, 3
btfss LCD_D6
bcf temp_rd, 2
btfsc LCD_D6
bsf temp_rd, 2
btfss LCD_D5
bcf temp_rd, 1
btfsc LCD_D5
bsf temp_rd, 1
btfss LCD_D4
bcf temp_rd, 0
btfsc LCD_D4
bsf temp_rd, 0

bcf LCD_E ; Finished reading the data

FinRd
return
; *******************************************************************






; *******************************************************************
LCDBusy
call LongDelayLast
; call LongDelay
return
; Check BF
rlcd LCD_INS
btfsc temp_rd, 7
goto LCDBusy
return

GLOBAL LCDBusy
; *******************************************************************






; *******************************************************************
DelayXCycles
decfsz delay, F
goto DelayXCycles
return
; *******************************************************************

Delay1ms ;Approxiamtely at 4Mhz
banksel delay
clrf delay
Delay_1
nop
banksel delay
decfsz delay
goto Delay_1
return




Delay30ms ;more than 30 at 4 Mhz
GLOBAL Delay30ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms

call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms

call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
return
GLOBAL Delay30ms
LongDelay:
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
call Delay1ms
return

LongDelayLast
call Delay1ms
call Delay1ms
call Delay1ms
return
 
I can't see any generated characters in your code... you need to send them to the screen's CGRam and store them in locations 0 - 63,
Then display them by printing 0 through 7... there are 8 bytes per character ( lower 5 bits ).

What characters are you generating?
 
Response

I tried to generate and write a custom character using the below code - but I could not get it to work-------

call LCD_Init
movlw 0x40 ;CGRAM Address
call LCDWriteNibble

movlw 0x0E
movwf temp_wr
call d_write

movlw 0x11
movwf temp_wr
call d_write

movlw 0x11
movwf temp_wr
call d_write

movlw 0x11
movwf temp_wr
call d_write

movlw 0x1F
movwf temp_wr
call d_write

movlw 0x1B
movwf temp_wr
call d_write

movlw 0x1B
movwf temp_wr
call d_write

movlw 0x1F
movwf temp_wr
call d_write

movlw 0x80 ;move to 1st row, first column
call LCDWriteNibble
;Display characters.

movlw 0x00 ;First character
call movwf temp_wr
call d_write
 
Status
Not open for further replies.

Latest threads

New Articles From Microcontroller Tips

Back
Top