6502-OS/system/lcd.h65

165 lines
5.1 KiB
Plaintext
Raw Permalink Normal View History

2023-12-23 14:18:48 +01:00
;;********************************************************************************
2024-08-08 21:11:25 +02:00
;; @file
;; @brief LCD-W164B driver
2024-08-08 20:39:25 +02:00
;; @ingroup drivers
2023-12-23 14:18:48 +01:00
;; @device ELECTRONIC ASSEMBLY - W164B-NLW
;; @details
;; The LCD must be connected to a W65C22N Interface Chip:
;; - IO.RB0-7 -> LCD.D0-7 data lines
;; - IO.RA5 -> LCD.RS register select
;; - IO.RA6 -> LCD.R/W read/write
;; - IO.RA7 -> LCD.E enable
;; @requires IO: Base Address of IO Chip
;; @depends IO-W65C22N
;;********************************************************************************
2023-12-08 22:56:35 +01:00
.ifndef INCLUDE_LCD
INCLUDE_LCD = 1
.include "system/system.h65"
;;********************************************************************************
;; @brief LCD character display
2024-08-08 20:39:25 +02:00
;; @ingroup drivers
;;********************************************************************************
2023-12-08 22:56:35 +01:00
.scope lcd
LCD_IO = IO1
2023-12-16 02:41:19 +01:00
Import lcd,init,clear,print,print_char,set_position,set_custom_char
Import lcd,_cmd,_wait_nbusy,_write_ram,_read_ram,_set_dd_ram_addr_from_charcount
Import lcd,_charcount
2024-01-15 09:19:05 +01:00
; PIN MASKS
E = %10000000
RW = %01000000
RS = %00100000
RA_MASK = %11100000
;;********************************************************************************
;; LCD Instructions
;; @details See LCD-W164B datasheet for a complete list
;;********************************************************************************
.enum CMD
CLEAR = %00000001 ;; clear display
ENTRY_MODE = %00000110 ;; auto-shift cursor
DISPLAY_ON = %00001111 ;; everything on, with blinking cursor
SHIFT_CUR_LEFT = %00101000 ;; shift the cursor to the left
SHIFT_DIS_LEFT = %00111000 ;; shift the display to the left
SHIFT_DIS_RIGHT = %00110000 ;; shift the display to the right
SHIFT_CUR_RIGHT = %00100000 ;; shift the cursor to the right
FUNCTION_SET = %00111000 ;; 8-bit, 4 lines, 5x7 font
SET_CG_ADDRESS = %01000000 ;; or this with the address
SET_ADDRESS = %10000000 ;; or this with the address
.endenum
2024-01-15 09:19:05 +01:00
; LCD Constants
LINE1 = $00
LINE2 = $40
LINE3 = $10
LINE4 = $50
.endscope
2023-12-08 22:56:35 +01:00
2023-12-21 17:27:54 +01:00
;;********************************************************************************
;; @macro Clear the screen and print a null-terminated string
;; @param message: Address of the message or string literal
;; @details
;; If message is a string literal, it will be stored in rodata
;; and the address of this segment will be used
;;********************************************************************************
2023-12-08 22:56:35 +01:00
.macro Print message
jsr lcd::clear
2023-12-21 17:27:54 +01:00
.if .match(message, "") ; message is a string literal -> store in rodata
.pushseg
.rodata
: .asciiz message
.popseg
lda #<:-
sta ARG0
lda #>:-
sta ARG1
.else ; message is not a string
lda #<message
sta ARG0
lda #>message
sta ARG1
2023-12-20 12:27:54 +01:00
.endif
2023-12-08 22:56:35 +01:00
jsr lcd::print
.endmacro
2023-12-16 02:41:19 +01:00
2023-12-21 17:27:54 +01:00
;;********************************************************************************
;; @macro Print a null-terminated string
;; @param message: Address of the message or string literal
;;********************************************************************************
2023-12-16 02:41:19 +01:00
.macro PrintNC message
2023-12-21 17:27:54 +01:00
.if .match(message, "") ; message is a string literal -> store in rodata
.pushseg
.rodata
: .asciiz message
.popseg
lda #<:-
sta ARG0
lda #>:-
sta ARG1
.else ; message is not a string
lda #<message
sta ARG0
lda #>message
sta ARG1
.endif
2023-12-16 02:41:19 +01:00
jsr lcd::print
.endmacro
2023-12-08 22:56:35 +01:00
2024-01-15 09:19:05 +01:00
;;********************************************************************************
;; @macro Set the cursor to the n-th position
;; @param n: Position [0,$40) or a register
2024-01-15 09:19:05 +01:00
;;********************************************************************************
.macro lcd_SetCursorPos n
.if .match (n, a)
.elseif .match (n, x)
txa
.elseif .match (n, y)
tya
2024-01-15 09:19:05 +01:00
.else
lda #n
2024-01-15 09:19:05 +01:00
.endif
sta lcd::_charcount
jsr lcd::_set_dd_ram_addr_from_charcount
2024-01-15 09:19:05 +01:00
.endmacro
;;********************************************************************************
;; @macro Move the cursor to the right
;; @param n: Number of characters to move n. Defaults to 1 if not provided
2024-01-15 09:19:05 +01:00
;;********************************************************************************
.macro lcd_IncrementCursor n
2024-01-15 09:19:05 +01:00
.ifblank n
inc lcd::_charcount
.elseif n = 1
inc lcd::_charcount
2024-01-15 09:19:05 +01:00
.else
lda lcd::_charcount
add #n
sta lcd::_charcount
2024-01-15 09:19:05 +01:00
.endif
jsr lcd::_set_dd_ram_addr_from_charcount
2024-01-15 09:19:05 +01:00
.endmacro
2023-12-16 02:41:19 +01:00
;;********************************************************************************
;; @macro Move the cursor to the left
;; @param n: Number of characters to move n. Defaults to 1 if not provided
;;********************************************************************************
.macro lcd_DecrementCursor n
.ifblank n
dec lcd::_charcount
.elseif n = 1
dec lcd::_charcount
.else
lda lcd::_charcount
sub #n
sta lcd::_charcount
.endif
jsr lcd::_set_dd_ram_addr_from_charcount
.endmacro
2023-12-08 22:56:35 +01:00
.endif ; guard