|
@@ -1,7 +1,7 @@
|
|
|
"""
|
|
|
Author: Tobias Müller
|
|
|
Date: 30.06.2023
|
|
|
-Version: 0.5
|
|
|
+Version: 0.7
|
|
|
|
|
|
This file contains classes for LCD, Button and Led control.
|
|
|
"""
|
|
@@ -18,28 +18,38 @@ class LCD:
|
|
|
|
|
|
############################## Attributes ##############################
|
|
|
|
|
|
- __lcd_setting = {"CONTROL_BYTE": 0x80, # Set Continue Bit
|
|
|
- "LCD_PARA_FUNC1": 0x3A, # Function Set 1 (8 Bit, RE = 1, IS = 0)
|
|
|
- "LCD_PARA_EXT_FUNC": 0x09, # Extended Function
|
|
|
- "LCD_PARA_ENTRY_MODE": 0x06, # Bottom View
|
|
|
- "LCD_PARA_BIAS_SET": 0x1E, # Bias Setting
|
|
|
- "LCD_PARA_FUNC2": 0x39, # Function Set 2 (8 Bit, RE = 0, IS = 1)
|
|
|
- "LCD_PARA_INT_OSC": 0x1B, # Internal OSC (BS0 = 1, Bias = 1/6)
|
|
|
- "LCD_PARA_FOL_CON": 0x6E, # Follower Control (Devider on, Set Value)
|
|
|
- "LCD_PARA_POW_CON": 0x56, # Power Control (Booster on, Set Contrast)
|
|
|
- "LCD_PARA_CONTRAST": 0x7A, # Set Contrast
|
|
|
- "LCD_PARA_FUNC3": 0x38, # Function Set 3 (8 Bit, RE = 0, IS = 0)
|
|
|
- "LCD_PARA_DIS_CON": 0x0C, # Display on/off Control (Cursor off, Blink off)
|
|
|
- "LCD_PARA_CLR_DIS": 0x01} # Clear Display
|
|
|
-
|
|
|
- __lcd_control = {"CONTROL_BYTE": 0x80, # Set Continue Bit
|
|
|
- "CONTROL_BYTE_DCB": 0x40, # Data/Command Selection Bit set
|
|
|
- "LCD_PARA_CLR_DIS": 0x01, # Clear Display
|
|
|
- "LCD_PARA_DIS_ROW1": 0x80, # Display Row 1
|
|
|
- "LCD_PARA_DIS_ROW2": 0xA0, # Display Row 2
|
|
|
- "LCD_PARA_DIS_ROW3": 0xC0, # Display Row 3
|
|
|
- "LCD_PARA_DIS_ROW4": 0xE0, # Display Row 4
|
|
|
- "LCD_PARA_DIS_COLUMN": 0x0A} # Columns per Display Row
|
|
|
+ __lcd_setting_para = {"LCD_PARA_EXT_FUNC": 0x09, # Extended Function (4 line mode)
|
|
|
+ "LCD_PARA_BIAS_SET": 0x12, # Bias Setting (BS1 = 1)
|
|
|
+ "LCD_PARA_INT_OSC": 0x1B, # Internal OSC (BS0 = 1, Bias = 1/6)
|
|
|
+ "LCD_PARA_FOL_CON": 0x6E, # Follower Control (Devider on, Set Value)
|
|
|
+ "LCD_PARA_DIS_CON": 0x0C} # Display on/off Control (Cursor off, Blink off)
|
|
|
+
|
|
|
+ __lcd_contrast_para = {"LCD_PARA_POW_CON": 0x54, # Power Control (Booster on) and Contrast (C5, C4)
|
|
|
+ "LCD_PARA_CONTRAST": 0x70} # Contrast (C3 - C0)
|
|
|
+
|
|
|
+ __lcd_line_mode_para = {"LCD_PARA_LINES": 0x12} # Line Mode
|
|
|
+
|
|
|
+ __lcd_direction_para = {"LCD_PARA_ENTRY_MODE": 0x04} # Display direction / orientation
|
|
|
+
|
|
|
+ __lcd_control_para_priv = {"CONTROL_BYTE": 0x00, # Control Byte
|
|
|
+ "CONTROL_BYTE_C0": 0x80, # Control Byte (C0 = 1)
|
|
|
+ "CONTROL_BYTE_RS": 0x40, # Control Byte (RS = 1)
|
|
|
+ "CONTROL_BYTE_C0_RS": 0xC0, # Control Byte (C0 = 1, RS = 1)
|
|
|
+ "FUNCTION_SET": 0x38, # Function Set
|
|
|
+ "FUNCTION_SET_RE": 0x3A, # Function Set (RE = 1)
|
|
|
+ "FUNCTION_SET_IS": 0x39, # Function Set (IS = 1)
|
|
|
+ "CLEAR_DISPLAY": 0x01, # Clear Display
|
|
|
+ "DISPLAY_ROW_1": 0x80, # Display Row 1
|
|
|
+ "DISPLAY_ROW_2": 0xA0, # Display Row 2
|
|
|
+ "DISPLAY_ROW_3": 0xC0, # Display Row 3
|
|
|
+ "DISPLAY_ROW_4": 0xE0, # Display Row 4
|
|
|
+ "DISPLAY_COLUMN": 0x0A} # Columns per Display Row
|
|
|
+
|
|
|
+ __lcd_rom_para = {"LCD_PARA_ROM_SEL": 0x72}
|
|
|
+
|
|
|
+ __lcd_rom = {"ROM A": 0, "ROM B": 1, "ROM C": 2,
|
|
|
+ "A": 0, "B": 1, "C": 2,
|
|
|
+ 1: 0, 2: 1, 3: 2}
|
|
|
|
|
|
__i2c_ports = {"I2C0": {"SDA_PINS": [0, 4 ,8 ,12 ,16 ,20],
|
|
|
"SCL_PINS": [1, 5, 9, 13, 17, 21]},
|
|
@@ -47,8 +57,7 @@ class LCD:
|
|
|
"SCL_PINS": [3, 7, 11, 15, 19, 27]}}
|
|
|
|
|
|
__i2c_frequencies = {"STANDARD_MODE": 100000,
|
|
|
- "FAST_MODE": 400000,
|
|
|
- "FAST_MODE_PLUS": 1000000}
|
|
|
+ "FAST_MODE": 400000}
|
|
|
|
|
|
__i2c_address = 0x3c
|
|
|
|
|
@@ -57,20 +66,42 @@ class LCD:
|
|
|
def __init__(self,
|
|
|
i2c_sda_pin: int|str = 2,
|
|
|
i2c_scl_pin: int|str = 3,
|
|
|
- i2c_frequency: int|str = 400000,
|
|
|
+ i2c_frequency: int|str = "FAST_MODE",
|
|
|
lcd_backlight_pin: int|str = 28,
|
|
|
- lcd_brightness: int = 100):
|
|
|
+ lcd_brightness: int = 100,
|
|
|
+ lcd_contrast: int = 0x2A,
|
|
|
+ lcd_ascii_table: int|str = "ROM B",
|
|
|
+ lcd_line_mode: int = 0,
|
|
|
+ lcd_direction_top: int|bool = False):
|
|
|
|
|
|
# Check and store input values
|
|
|
- self.__I2C_Bus, self.__I2C_SDA_Pin, self.__I2C_SCL_Pin = self.__check_i2c_ports(i2c_sda_pin,
|
|
|
+ self.__i2c_bus, self.__i2c_sda_pin, self.__i2c_scl_pin = self.__check_i2c_ports(i2c_sda_pin,
|
|
|
i2c_scl_pin)
|
|
|
- self.__i2c_frequency = self.__check_i2c_speed(i2c_frequency)
|
|
|
+ self.__i2c_frequency = self.__check_i2c_frequency(i2c_frequency)
|
|
|
self.__lcd_backlight_pin = self.__check_lcd_backlight_pin(lcd_backlight_pin)
|
|
|
self.__lcd_brightness = self.__check_lcd_brightness(lcd_brightness)
|
|
|
+ self.__lcd_contrast = self.__check_lcd_contrast(lcd_contrast)
|
|
|
+ self.__lcd_ascii_table = self.__check_lcd_ascii_table(lcd_ascii_table)
|
|
|
+ self.__lcd_line_mode = self.__check_lcd_line_mode(lcd_line_mode)
|
|
|
+ self.__lcd_direction_top = self.__check_lcd_direction_top(lcd_direction_top)
|
|
|
|
|
|
# init i2c and backlight
|
|
|
self.__init_i2c()
|
|
|
self.__init_backlight_pwm()
|
|
|
+
|
|
|
+ ############################## Properties private ##############################
|
|
|
+
|
|
|
+ @property
|
|
|
+ def __lcd_control_para(self):
|
|
|
+ lcd_control_para = self.__lcd_control_para_priv.copy()
|
|
|
+ if self.__lcd_line_mode:
|
|
|
+ lcd_control_para["FUNCTION_SET"] = 0x3C
|
|
|
+ if self.__lcd_direction_top:
|
|
|
+ lcd_control_para["DISPLAY_ROW_1"] = 0x8A
|
|
|
+ lcd_control_para["DISPLAY_ROW_2"] = 0xAA
|
|
|
+ lcd_control_para["DISPLAY_ROW_3"] = 0xCA
|
|
|
+ lcd_control_para["DISPLAY_ROW_4"] = 0xEA
|
|
|
+ return lcd_control_para
|
|
|
|
|
|
############################## Properties ##############################
|
|
|
|
|
@@ -81,16 +112,101 @@ class LCD:
|
|
|
@lcd_brightness.setter
|
|
|
def lcd_brightness(self, lcd_brightness: int):
|
|
|
self.__lcd_brightness = self.__check_lcd_brightness(lcd_brightness)
|
|
|
- self.__backlight_pwm.duty_u16(round(65635 * (lcd_brightness / 100)))
|
|
|
+ self.__set_lcd_brightness()
|
|
|
+
|
|
|
+ @property
|
|
|
+ def lcd_ascii_table(self):
|
|
|
+ return self.__lcd_ascii_table
|
|
|
+
|
|
|
+ @lcd_ascii_table.setter
|
|
|
+ def lcd_ascii_table(self, lcd_ascii_table: int|str):
|
|
|
+ self.__lcd_ascii_table = self.__check_lcd_ascii_table(lcd_ascii_table)
|
|
|
+ self.__set_lcd_ascii_table()
|
|
|
+
|
|
|
+ @property
|
|
|
+ def lcd_contrast(self):
|
|
|
+ return self.__lcd_contrast
|
|
|
+
|
|
|
+ @lcd_contrast.setter
|
|
|
+ def lcd_contrast(self, lcd_contrast: int):
|
|
|
+ self.__lcd_contrast = self.__check_lcd_contrast(lcd_contrast)
|
|
|
+ self.__set_lcd_contrast()
|
|
|
+
|
|
|
+ @property
|
|
|
+ def lcd_direction_top(self):
|
|
|
+ return self.__lcd_direction_top
|
|
|
+
|
|
|
+ @lcd_direction_top.setter
|
|
|
+ def lcd_direction_top(self, lcd_direction_top: int|bool):
|
|
|
+ self.__lcd_direction_top = self.__check_lcd_direction_top(lcd_direction_top)
|
|
|
+ self.__set_lcd_direction()
|
|
|
+ self.clear()
|
|
|
+
|
|
|
+ @property
|
|
|
+ def lcd_line_mode(self):
|
|
|
+ return self.__lcd_line_mode
|
|
|
+
|
|
|
+ @lcd_line_mode.setter
|
|
|
+ def lcd_line_mode(self, lcd_line_mode: int):
|
|
|
+ self.__lcd_line_mode = self.__check_lcd_line_mode(lcd_line_mode)
|
|
|
+ self.__set_lcd_line_mode()
|
|
|
+
|
|
|
+ @property
|
|
|
+ def lcd_backlight_pin(self):
|
|
|
+ return self.__lcd_backlight_pin
|
|
|
+
|
|
|
+ @lcd_backlight_pin.setter
|
|
|
+ def lcd_backlight_pin(self, lcd_backlight_pin: int|str):
|
|
|
+ self.__check_lcd_backlight_pin(lcd_backlight_pin)
|
|
|
+ self.__deinit_backlight_pwm()
|
|
|
+ self.lcd_backlight_pin = lcd_backlight_pin
|
|
|
+ self.__init_backlight_pwm()
|
|
|
+
|
|
|
+ @property
|
|
|
+ def i2c_frequency(self):
|
|
|
+ return self.__i2c_frequency
|
|
|
+
|
|
|
+ @i2c_frequency.setter
|
|
|
+ def i2c_frequency(self, i2c_frequency: int|str):
|
|
|
+ self.__check_i2c_frequency(i2c_frequency)
|
|
|
+ self.__deinit_i2c()
|
|
|
+ self.__i2c_frequency = i2c_frequency
|
|
|
+ self.__init_i2c()
|
|
|
+
|
|
|
+ @property
|
|
|
+ def i2c_sda_pin(self):
|
|
|
+ return self.__i2c_sda_pin
|
|
|
+
|
|
|
+ @i2c_sda_pin.setter
|
|
|
+ def i2c_sda_pin(self, i2c_sda_pin: int|str):
|
|
|
+ self.__check_i2c_ports(i2c_sda_pin, self.__i2c_scl_pin)
|
|
|
+ self.__deinit_i2c()
|
|
|
+ (self.__i2c_bus,
|
|
|
+ self.__i2c_sda_pin,
|
|
|
+ self.__i2c_scl_pin) = self.__check_i2c_ports(i2c_sda_pin, self.__i2c_scl_pin)
|
|
|
+ self.__init_i2c()
|
|
|
+
|
|
|
+ @property
|
|
|
+ def i2c_scl_pin(self):
|
|
|
+ return self.__i2c_scl_pin
|
|
|
+
|
|
|
+ @i2c_scl_pin.setter
|
|
|
+ def i2c_scl_pin(self, i2c_scl_pin: int|str):
|
|
|
+ self.__check_i2c_ports(self.__i2c_sda_pin, i2c_scl_pin)
|
|
|
+ self.__deinit_i2c()
|
|
|
+ (self.__i2c_bus,
|
|
|
+ self.__i2c_sda_pin,
|
|
|
+ self.__i2c_scl_pin) = self.__check_i2c_ports(self.__i2c_sda_pin, i2c_scl_pin)
|
|
|
+ self.__init_i2c()
|
|
|
|
|
|
############################## Methods private ##############################
|
|
|
|
|
|
@staticmethod
|
|
|
- def __reset_pin(pin):
|
|
|
+ def __reset_pin(pin: int|str):
|
|
|
Pin(pin, Pin.IN, None)
|
|
|
|
|
|
@staticmethod
|
|
|
- def __check_lcd_brightness(lcd_brightness):
|
|
|
+ def __check_lcd_brightness(lcd_brightness: int):
|
|
|
if not isinstance(lcd_brightness, int):
|
|
|
raise ValueError(f"Value \"{lcd_brightness}\" of \"lcd_brightness\" is not type \"int\"!")
|
|
|
elif lcd_brightness < 0 or lcd_brightness > 100:
|
|
@@ -99,7 +215,7 @@ class LCD:
|
|
|
return lcd_brightness
|
|
|
|
|
|
@staticmethod
|
|
|
- def __check_lcd_backlight_pin(lcd_backlight_pin):
|
|
|
+ def __check_lcd_backlight_pin(lcd_backlight_pin: int|str):
|
|
|
if not isinstance(lcd_backlight_pin, int) and not isinstance(lcd_backlight_pin, str):
|
|
|
raise ValueError(f"Value \"{lcd_backlight_pin}\" of \"lcd_backlight_pin\" is not type" +
|
|
|
" \"int\" or \"str\"!")
|
|
@@ -109,7 +225,44 @@ class LCD:
|
|
|
else:
|
|
|
return lcd_backlight_pin
|
|
|
|
|
|
- def __check_i2c_ports(self, i2c_sda_pin, i2c_scl_pin):
|
|
|
+ @staticmethod
|
|
|
+ def __check_lcd_line_mode(lcd_line_mode: int):
|
|
|
+ if not isinstance(lcd_line_mode, int):
|
|
|
+ raise ValueError(f"Value \"{lcd_line_mode}\" of \"lcd_line_mode\" is not type \"int\"!")
|
|
|
+ elif lcd_line_mode < 0 or lcd_line_mode > 4:
|
|
|
+ raise ValueError(f"Value \"{lcd_line_mode}\" of \"lcd_line_mode\" is out of range!")
|
|
|
+ else:
|
|
|
+ return lcd_line_mode
|
|
|
+
|
|
|
+ @staticmethod
|
|
|
+ def __check_lcd_direction_top(lcd_direction_top: int|bool):
|
|
|
+ if not isinstance(lcd_direction_top, int) and not isinstance(lcd_direction_top, bool):
|
|
|
+ raise ValueError(f"Value \"{lcd_direction_top}\" of \"lcd_direction_top\" is not type" +
|
|
|
+ " \"int\" or \"bool\"!")
|
|
|
+ elif isinstance(lcd_direction_top, int) and (lcd_direction_top < 0 or lcd_direction_top > 1):
|
|
|
+ raise ValueError(f"Value \"{lcd_direction_top}\" of \"lcd_direction_top\" is out of range!")
|
|
|
+ else:
|
|
|
+ return lcd_direction_top
|
|
|
+
|
|
|
+ @staticmethod
|
|
|
+ def __check_lcd_contrast(lcd_contrast: int):
|
|
|
+ if not isinstance(lcd_contrast, int):
|
|
|
+ raise ValueError(f"Value \"{lcd_contrast}\" of \"lcd_contrast\" is not type \"int\"!")
|
|
|
+ elif lcd_contrast < 0 or lcd_contrast > 63:
|
|
|
+ raise ValueError(f"Value \"{lcd_contrast}\" of \"lcd_contrast\" is out of range!")
|
|
|
+ else:
|
|
|
+ return lcd_contrast
|
|
|
+
|
|
|
+ def __check_lcd_ascii_table(self, lcd_ascii_table: int|str):
|
|
|
+ if not isinstance(lcd_ascii_table, int) and not isinstance(lcd_ascii_table, str):
|
|
|
+ raise ValueError(f"Value \"{lcd_ascii_table}\" of \"lcd_ascii_table\" is not type" +
|
|
|
+ " \"int\" or \"str\"!")
|
|
|
+ elif lcd_ascii_table not in self.__lcd_rom.keys():
|
|
|
+ raise ValueError(f"Value \"{lcd_ascii_table}\" of \"lcd_ascii_table\" is not supported!")
|
|
|
+ else:
|
|
|
+ return lcd_ascii_table
|
|
|
+
|
|
|
+ def __check_i2c_ports(self, i2c_sda_pin: int|str, i2c_scl_pin: int|str):
|
|
|
if not isinstance(i2c_sda_pin, int) and not isinstance(i2c_sda_pin, str):
|
|
|
raise ValueError(f"Value \"{i2c_sda_pin}\" of \"i2c_sda_pin\" is not type \"int\"" +
|
|
|
" or \"str\"!")
|
|
@@ -162,7 +315,7 @@ class LCD:
|
|
|
else:
|
|
|
return 1, i2c_sda_pin, i2c_scl_pin
|
|
|
|
|
|
- def __check_i2c_speed(self, i2c_frequency):
|
|
|
+ def __check_i2c_frequency(self, i2c_frequency: int|str):
|
|
|
if not isinstance(i2c_frequency, int) and not isinstance(i2c_frequency, str):
|
|
|
raise ValueError(f"Value \"{i2c_frequency}\" of \"i2c_frequency\" is not type \"int\"" +
|
|
|
" or \"str\"!")
|
|
@@ -174,53 +327,151 @@ class LCD:
|
|
|
|
|
|
|
|
|
def __init_i2c(self):
|
|
|
- self.__i2c = I2C(self.__I2C_Bus,
|
|
|
- sda=Pin(self.__I2C_SDA_Pin),
|
|
|
- scl=Pin(self.__I2C_SCL_Pin),
|
|
|
+ self.__i2c = I2C(self.__i2c_bus,
|
|
|
+ sda=Pin(self.__i2c_sda_pin),
|
|
|
+ scl=Pin(self.__i2c_scl_pin),
|
|
|
freq=(self.__i2c_frequency if isinstance(self.__i2c_frequency, int) else
|
|
|
self.__i2c_frequencies[self.__i2c_frequency]))
|
|
|
- self.__i2c.writeto(self.__i2c_address, bytes(self.__lcd_setting.values()))
|
|
|
+ buffer = (self.__lcd_control_para["CONTROL_BYTE"],
|
|
|
+ self.__lcd_control_para["FUNCTION_SET_RE"],
|
|
|
+ self.__lcd_setting_para["LCD_PARA_EXT_FUNC"],
|
|
|
+ self.__lcd_setting_para["LCD_PARA_BIAS_SET"],
|
|
|
+ self.__lcd_control_para["FUNCTION_SET_IS"],
|
|
|
+ self.__lcd_setting_para["LCD_PARA_INT_OSC"],
|
|
|
+ self.__lcd_setting_para["LCD_PARA_FOL_CON"],
|
|
|
+ self.__lcd_control_para["FUNCTION_SET"],
|
|
|
+ self.__lcd_setting_para["LCD_PARA_DIS_CON"])
|
|
|
+ self.__i2c.writeto(self.__i2c_address, bytes(buffer))
|
|
|
+ self.__set_lcd_line_mode()
|
|
|
+ self.__set_lcd_ascii_table()
|
|
|
+ self.__set_lcd_contrast()
|
|
|
+ self.__set_lcd_direction()
|
|
|
+ self.clear()
|
|
|
|
|
|
def __deinit_i2c(self):
|
|
|
- self.__reset_pin(self.__I2C_SCL_Pin)
|
|
|
- self.__reset_pin(self.__I2C_SDA_Pin)
|
|
|
+ self.__reset_pin(self.__i2c_scl_pin)
|
|
|
+ self.__reset_pin(self.__i2c_sda_pin)
|
|
|
|
|
|
def __init_backlight_pwm(self):
|
|
|
self.__backlight_pwm = PWM(Pin(self.__lcd_backlight_pin))
|
|
|
self.__backlight_pwm.freq(1000)
|
|
|
- self.__backlight_pwm.duty_u16(round(65635 * (self.lcd_brightness / 100)))
|
|
|
+ self.__set_lcd_brightness()
|
|
|
|
|
|
def __deinit_backlight_pwm(self):
|
|
|
self.__backlight_pwm.deinit()
|
|
|
self.__reset_pin(self.__lcd_backlight_pin)
|
|
|
|
|
|
+ def __set_lcd_brightness(self):
|
|
|
+ self.__backlight_pwm.duty_u16(round(65635 * (self.__lcd_brightness / 100)))
|
|
|
+
|
|
|
+ def __set_lcd_ascii_table(self):
|
|
|
+ buffer = (self.__lcd_control_para["CONTROL_BYTE_C0"],
|
|
|
+ self.__lcd_control_para["FUNCTION_SET_RE"],
|
|
|
+ self.__lcd_control_para["CONTROL_BYTE_C0"],
|
|
|
+ self.__lcd_rom_para["LCD_PARA_ROM_SEL"],
|
|
|
+ self.__lcd_control_para["CONTROL_BYTE_C0_RS"],
|
|
|
+ self.__lcd_rom[self.__lcd_ascii_table] << 0x02,
|
|
|
+ self.__lcd_control_para["CONTROL_BYTE"],
|
|
|
+ self.__lcd_control_para["FUNCTION_SET"])
|
|
|
+ self.__i2c.writeto(self.__i2c_address, bytes(buffer))
|
|
|
+
|
|
|
+ def __set_lcd_contrast(self):
|
|
|
+ buffer = (self.__lcd_control_para["CONTROL_BYTE"],
|
|
|
+ self.__lcd_control_para["FUNCTION_SET_IS"],
|
|
|
+ self.__lcd_contrast_para["LCD_PARA_POW_CON"] | (self.__lcd_contrast >> 0x04),
|
|
|
+ self.__lcd_contrast_para["LCD_PARA_CONTRAST"] | (self.__lcd_contrast & 0x0F),
|
|
|
+ self.__lcd_control_para["FUNCTION_SET"])
|
|
|
+ self.__i2c.writeto(self.__i2c_address, bytes(buffer))
|
|
|
+
|
|
|
+ def __set_lcd_direction(self):
|
|
|
+ buffer = [self.__lcd_control_para["CONTROL_BYTE"],
|
|
|
+ self.__lcd_control_para["FUNCTION_SET_RE"]]
|
|
|
+ if self.__lcd_direction_top:
|
|
|
+ buffer.append(self.__lcd_direction_para["LCD_PARA_ENTRY_MODE"] | 0x01)
|
|
|
+ else:
|
|
|
+ buffer.append(self.__lcd_direction_para["LCD_PARA_ENTRY_MODE"] | 0x02)
|
|
|
+ buffer.append(self.__lcd_control_para["FUNCTION_SET"])
|
|
|
+ self.__i2c.writeto(self.__i2c_address, bytes(buffer))
|
|
|
+
|
|
|
+ def __set_lcd_line_mode(self):
|
|
|
+ buffer = [self.__lcd_control_para["CONTROL_BYTE"],
|
|
|
+ self.__lcd_control_para["FUNCTION_SET_RE"]]
|
|
|
+ if self.__lcd_line_mode:
|
|
|
+ buffer.append(self.__lcd_line_mode_para["LCD_PARA_LINES"] |
|
|
|
+ ((self.__lcd_line_mode - 1) << 0x02))
|
|
|
+ else:
|
|
|
+ buffer.append(self.__lcd_line_mode_para["LCD_PARA_LINES"])
|
|
|
+ buffer.append(self.__lcd_control_para["FUNCTION_SET"])
|
|
|
+ self.__i2c.writeto(self.__i2c_address, bytes(buffer))
|
|
|
+
|
|
|
############################## Methods public ##############################
|
|
|
|
|
|
def change_i2c_port(self, i2c_sda_pin: int|str, i2c_scl_pin: int|str):
|
|
|
- self.__I2C_Bus, i2c_sda_pin, i2c_scl_pin = self.__check_i2c_ports(i2c_sda_pin, i2c_scl_pin)
|
|
|
+ self.__check_i2c_ports(i2c_sda_pin, i2c_scl_pin)
|
|
|
self.__deinit_i2c()
|
|
|
- self.__I2C_SCL_Pin = i2c_scl_pin
|
|
|
- self.__I2C_SDA_Pin = i2c_sda_pin
|
|
|
+ (self.__i2c_bus,
|
|
|
+ self.__i2c_sda_pin,
|
|
|
+ self.__i2c_scl_pin) = self.__check_i2c_ports(i2c_sda_pin, i2c_scl_pin)
|
|
|
self.__init_i2c()
|
|
|
|
|
|
def print(self, text: str, **keywords):
|
|
|
- if not isinstance(text, str):
|
|
|
- raise ValueError(f"Value \"{text}\" of \"text\" is not type \"str\"!")
|
|
|
- elif len(keywords) == 0:
|
|
|
- self.clear()
|
|
|
- buffer = [self.__lcd_control["CONTROL_BYTE"]]
|
|
|
- buffer.append(self.__lcd_control["LCD_PARA_DIS_ROW1"])
|
|
|
- buffer.append(self.__lcd_control["CONTROL_BYTE_DCB"])
|
|
|
- for i in range(0, self.__lcd_control["LCD_PARA_DIS_COLUMN"] if
|
|
|
- len(text) > self.__lcd_control["LCD_PARA_DIS_COLUMN"] else len(text)):
|
|
|
- buffer.append(ord(text[i]))
|
|
|
- print(bytes(buffer))
|
|
|
- self.__i2c.writeto(self.__i2c_address, bytes(buffer))
|
|
|
-
|
|
|
- def clear(self):
|
|
|
- buffer = [self.__lcd_control["CONTROL_BYTE"], self.__lcd_control["LCD_PARA_CLR_DIS"]]
|
|
|
+ def check_text(text: str):
|
|
|
+ if not isinstance(text, str):
|
|
|
+ raise ValueError(f"Value \"{text}\" of \"text\" is not type \"str\"!")
|
|
|
+ elif len(text) == 0:
|
|
|
+ raise ValueError(f"Value \"{text}\" of \"text\" is out of range!")
|
|
|
+
|
|
|
+ def check_keywords(keywords):
|
|
|
+ pass
|
|
|
+
|
|
|
+ buffer = []
|
|
|
+ char=0
|
|
|
+ linefeed = ("\n","\r")
|
|
|
+ column = 0
|
|
|
+ line = 1
|
|
|
+ lines = 4 if self.__lcd_line_mode == 0 else 2 if self.__lcd_line_mode == 3 else 3
|
|
|
+
|
|
|
+ if len(keywords) == 0:
|
|
|
+ check_text(text)
|
|
|
+ for row in range(line,lines + 1):
|
|
|
+ print(len(text))
|
|
|
+ if len(text) == 0:
|
|
|
+ break
|
|
|
+ buffer.append(self.__lcd_control_para["CONTROL_BYTE_C0"])
|
|
|
+ buffer.append(self.__lcd_control_para["DISPLAY_ROW_" + str(row)])
|
|
|
+ for char in range(0, self.__lcd_control_para["DISPLAY_COLUMN"] if
|
|
|
+ len(text) > self.__lcd_control_para["DISPLAY_COLUMN"] else
|
|
|
+ len(text)):
|
|
|
+ if text[char] in linefeed:
|
|
|
+ text = text[char + 1:]
|
|
|
+ break
|
|
|
+ buffer.append(self.__lcd_control_para["CONTROL_BYTE_C0_RS"])
|
|
|
+ buffer.append(ord(text[char]))
|
|
|
+ else:
|
|
|
+ text = text[self.__lcd_control_para["DISPLAY_COLUMN"]:]
|
|
|
+ else:
|
|
|
+ check_text(text)
|
|
|
+ check_keywords(keywords)
|
|
|
+ print(keywords)
|
|
|
+ self.__i2c.writeto(self.__i2c_address, bytes(buffer))
|
|
|
+
|
|
|
+ def clear(self, **keywords):
|
|
|
+ buffer = (self.__lcd_control_para["CONTROL_BYTE"],
|
|
|
+ self.__lcd_control_para["CLEAR_DISPLAY"])
|
|
|
self.__i2c.writeto(self.__i2c_address, bytes(buffer))
|
|
|
|
|
|
if __name__ == "__main__":
|
|
|
- lcd = LCD(i2c_scl_pin="GP3", i2c_sda_pin=2, i2c_frequency=100000)
|
|
|
- lcd.print("Hallo")
|
|
|
+ lcd = LCD(i2c_scl_pin="GP1",
|
|
|
+ i2c_sda_pin=0,
|
|
|
+ i2c_frequency=400000,
|
|
|
+ lcd_backlight_pin=5,
|
|
|
+ lcd_direction_top=False,
|
|
|
+ lcd_line_mode=0,
|
|
|
+ lcd_contrast=40,
|
|
|
+ lcd_brightness=100,
|
|
|
+ lcd_ascii_table="B")
|
|
|
+ lcd.print("Hallöle")
|
|
|
+ sleep_us(2000000)
|
|
|
+ lcd.clear()
|
|
|
+ sleep_us(2000000)
|
|
|
+ lcd.print("Hallüüüüü")
|