import time import os import RPi.GPIO as GPIO GPIO.setmode(GPIO.BCM) GPIO.setwarnings(False) # Define GPIO to LCD mapping LCD_RS = 4 LCD_E = 17 LCD_D4 = 18 LCD_D5 = 27 LCD_D6 = 22 LCD_D7 = 23 R1 = 5 R2 = 6 R3 = 12 R4 = 13 C1 = 16 C2 = 19 C3 = 20 C4 = 26 # Timing constants E_PULSE = 0.0005 E_DELAY = 0.0005 GPIO.setup(LCD_E, GPIO.OUT) # E GPIO.setup(LCD_RS, GPIO.OUT) # RS GPIO.setup(LCD_D4, GPIO.OUT) # DB4 GPIO.setup(LCD_D5, GPIO.OUT) # DB5 GPIO.setup(LCD_D6, GPIO.OUT) # DB6 GPIO.setup(LCD_D7, GPIO.OUT) # DB7 GPIO.setup(R1, GPIO.OUT) GPIO.setup(R2, GPIO.OUT) GPIO.setup(R3, GPIO.OUT) GPIO.setup(R4, GPIO.OUT) GPIO.setup(C1, GPIO.IN, pull_up_down=GPIO.PUD_DOWN) GPIO.setup(C2, GPIO.IN, pull_up_down=GPIO.PUD_DOWN) GPIO.setup(C3, GPIO.IN, pull_up_down=GPIO.PUD_DOWN) GPIO.setup(C4, GPIO.IN, pull_up_down=GPIO.PUD_DOWN) # Define some device constants LCD_WIDTH = 16 # Maximum characters per line LCD_CHR = True LCD_CMD = False LCD_LINE_1 = 0x80 # LCD RAM address for the 1st line LCD_LINE_2 = 0xC0 # LCD RAM address for the 2nd line def lcd_init(): # Initialise display lcd_byte(0x33,LCD_CMD) # 110011 Initialise lcd_byte(0x32,LCD_CMD) # 110010 Initialise lcd_byte(0x06,LCD_CMD) # 000110 Cursor move direction lcd_byte(0x0C,LCD_CMD) # 001100 Display On,Cursor Off, Blink Off lcd_byte(0x28,LCD_CMD) # 101000 Data length, number of lines, font size lcd_byte(0x01,LCD_CMD) # 000001 Clear display time.sleep(E_DELAY) def lcd_byte(bits, mode): GPIO.output(LCD_RS, mode) # RS # High bits GPIO.output(LCD_D4, False) GPIO.output(LCD_D5, False) GPIO.output(LCD_D6, False) GPIO.output(LCD_D7, False) if bits&0x10;==0x10: GPIO.output(LCD_D4, True) if bits&0x20;==0x20: GPIO.output(LCD_D5, True) if bits&0x40;==0x40: GPIO.output(LCD_D6, True) if bits&0x80;==0x80: GPIO.output(LCD_D7, True) # Toggle 'Enable' pin lcd_toggle_enable() # Low bits GPIO.output(LCD_D4, False) GPIO.output(LCD_D5, False) GPIO.output(LCD_D6, False) GPIO.output(LCD_D7, False) if bits&0x01;==0x01: GPIO.output(LCD_D4, True) if bits&0x02;==0x02: GPIO.output(LCD_D5, True) if bits&0x04;==0x04: GPIO.output(LCD_D6, True) if bits&0x08;==0x08: GPIO.output(LCD_D7, True) # Toggle 'Enable' pin lcd_toggle_enable() def lcd_toggle_enable(): # Toggle enable time.sleep(E_DELAY) GPIO.output(LCD_E, True) time.sleep(E_PULSE) GPIO.output(LCD_E, False) time.sleep(E_DELAY) def lcd_string(message,line): # Send string to display message = message.ljust(LCD_WIDTH," ") lcd_byte(line, LCD_CMD) for i in range(LCD_WIDTH): lcd_byte(ord(message[i]),LCD_CHR) def readRow(line, characters): GPIO.output(line, GPIO.HIGH) time.sleep(0.02) if(GPIO.input(C1) == 1): if line == R4: lcd_string('',LCD_LINE_2) time.sleep(0.01) else: lcd_string(characters[0],LCD_LINE_2) if(GPIO.input(C2) == 1): lcd_string(characters[1],LCD_LINE_2) time.sleep(0.01) if(GPIO.input(C3) == 1): lcd_string(characters[2],LCD_LINE_2) time.sleep(0.01) if(GPIO.input(C4) == 1): lcd_string(characters[3],LCD_LINE_2) time.sleep(0.01) GPIO.output(line, GPIO.LOW) time.sleep(0.02) def calculator(matrix_char): size=len(matrix_char) func='' result=0 number_before_char=[] number_after_char=[] for i in range(size): if matrix_char[i] == '+' or matrix_char[i] == '-' or matrix_char[i] == 'x' or matrix_char[i] == '/' : func=matrix_char[i] for j in range(i): number_before_char.append(matrix_char[j]) for k in range(i+1,size): number_after_char.append(matrix_char[k]) number_before_int=[float(element) for element in number_before_char] result1 = 0 for i in range(len(number_before_int)): result1 = result1 * 10 + number_before_int[i] number_after_int=[int(element) for element in number_after_char] result2 = 0 for i in range(len(number_after_int)): result2 = result2 * 10 + number_after_int[i] if func=='+': result= result1+result2 if func=='-': result= result1-result2 if func=='x': result= result1*result2 if func=='/': result=result1/result2 return result def key_pad(line, col,matrix_char): GPIO.output(line, GPIO.HIGH) time.sleep(0.01) if(GPIO.input(C1) == 1): if line == R4: lcd_string('',LCD_LINE_1) matrix_char.clear() else: lcd_string(col[0],LCD_LINE_1) matrix_char.append((col[0])) time.sleep(0.1) if(GPIO.input(C2) == 1): lcd_string(col[1],LCD_LINE_1) matrix_char.append((col[1])) time.sleep(0.1) if(GPIO.input(C3) == 1): if line == R4: a=calculator(matrix_char) lcd_string(str(a),LCD_LINE_1) matrix_char.clear() matrix_char.append(str(a)) time.sleep(0.1) else: lcd_string(col[2],LCD_LINE_1) matrix_char.append((col[2])) time.sleep(0.1) if(GPIO.input(C4) == 1): lcd_string(col[3],LCD_LINE_1) matrix_char.append((col[3])) time.sleep(0.1) GPIO.output(line, GPIO.LOW) time.sleep(0.01) # Define delay between readings lcd_init() matrix_char=[] try: while 1: key_pad(R1, ["7","8","9","/"],matrix_char) key_pad(R2, ["4","5","6","x"],matrix_char) key_pad(R3, ["1","2","3","-"],matrix_char) key_pad(R4, ["C","0","=","+"],matrix_char) finally: GPIO.cleanup()