diff --git a/library/lcd/lcd_comm.py b/library/lcd/lcd_comm.py index faffcfaa..11297c62 100644 --- a/library/lcd/lcd_comm.py +++ b/library/lcd/lcd_comm.py @@ -420,6 +420,29 @@ def DisplayLineGraph(self, x: int, y: int, width: int, height: int, self.DisplayPILImage(graph_image, x, y) + def DrawRadialDecoration(self, draw: ImageDraw, angle: float, radius: float, width: float, color: Tuple[int, int, int] = (0, 0, 0)): + i_cos = math.cos(angle*math.pi/180) + i_sin = math.sin(angle*math.pi/180) + x_f = (i_cos * (radius - width/2)) + radius + if math.modf(x_f) == 0.5: + if i_cos > 0: + x_f = math.floor(x_f) + else: + x_f = math.ceil(x_f) + else: + x_f = math.floor(x_f + 0.5) + + y_f = (i_sin * (radius - width/2)) + radius + if math.modf(y_f) == 0.5: + if i_sin > 0: + y_f = math.floor(y_f) + else: + y_f = math.ceil(y_f) + else: + y_f = math.floor(y_f + 0.5) + draw.ellipse([x_f - width/2, y_f - width/2, x_f + width/2, y_f - 1 + width/2 - 1], outline=color, fill=color, width=1) + + def DisplayRadialProgressBar(self, xc: int, yc: int, radius: int, bar_width: int, min_value: int = 0, max_value: int = 100, @@ -436,7 +459,12 @@ def DisplayRadialProgressBar(self, xc: int, yc: int, radius: int, bar_width: int font_color: Tuple[int, int, int] = (0, 0, 0), bar_color: Tuple[int, int, int] = (0, 0, 0), background_color: Tuple[int, int, int] = (255, 255, 255), - background_image: str = None): + background_image: str = None, + custom_bbox: Tuple[int, int, int, int] = (0, 0, 0, 0), + text_offset: Tuple[int, int] = (0,0), + bar_background_color: Tuple[int, int, int] = (0, 0, 0), + draw_bar_background: bool = False, + bar_decoration: str = ""): # Generate a radial progress bar and display it # Provide the background image path to display progress bar with transparent background @@ -449,6 +477,9 @@ def DisplayRadialProgressBar(self, xc: int, yc: int, radius: int, bar_width: int if isinstance(font_color, str): font_color = tuple(map(int, font_color.split(', '))) + if isinstance(bar_background_color, str): + bar_background_color = tuple(map(int, bar_background_color.split(', '))) + if angle_start % 361 == angle_end % 361: if clockwise: angle_start += 0.1 @@ -500,6 +531,23 @@ def DisplayRadialProgressBar(self, xc: int, yc: int, radius: int, bar_width: int ecart = 360 - angle_start + angle_end else: ecart = angle_end - angle_start + + # draw bar background + if draw_bar_background: + if angle_end < angle_start: + angleE = angle_start + ecart + angleS = angle_start + else: + angleS = angle_start + angleE = angle_start + ecart + draw.arc([0, 0, diameter - 1, diameter - 1], angleS, angleE, fill=bar_background_color, width=bar_width) + + # draw bar decoration + if bar_decoration == "Ellipse": + self.DrawRadialDecoration(draw = draw, angle = angle_end, radius = radius, width = bar_width, color = bar_background_color) + self.DrawRadialDecoration(draw = draw, angle = angle_start, radius = radius, width = bar_width, color = bar_color) + self.DrawRadialDecoration(draw = draw, angle = angle_start + pct * ecart, radius = radius, width = bar_width, color = bar_color) + # # solid bar case if angle_sep == 0: @@ -533,6 +581,25 @@ def DisplayRadialProgressBar(self, xc: int, yc: int, radius: int, bar_width: int ecart = angle_start - angle_end else: ecart = 360 - angle_end + angle_start + + # draw bar background + if draw_bar_background: + if angle_end < angle_start: + angleE = angle_start + angleS = angle_start - ecart + else: + angleS = angle_start - ecart + angleE = angle_start + draw.arc([0, 0, diameter - 1, diameter - 1], angleS, angleE, fill=bar_background_color, width=bar_width) + + + # draw bar decoration + if bar_decoration == "Ellipse": + self.DrawRadialDecoration(draw = draw, angle = angle_end, radius = radius, width = bar_width, color = bar_background_color) + self.DrawRadialDecoration(draw = draw, angle = angle_start, radius = radius, width = bar_width, color = bar_color) + self.DrawRadialDecoration(draw = draw, angle = angle_start - pct * ecart, radius = radius, width = bar_width, color = bar_color) + + # # solid bar case if angle_sep == 0: if angle_end < angle_start: @@ -568,10 +635,14 @@ def DisplayRadialProgressBar(self, xc: int, yc: int, radius: int, bar_width: int font = ImageFont.truetype("./res/fonts/" + font, font_size) left, top, right, bottom = font.getbbox(text) w, h = right - left, bottom - top - draw.text((radius - w / 2, radius - top - h / 2), text, + draw.text((radius - w / 2 + text_offset[0], radius - top - h / 2 + text_offset[1]), text, font=font, fill=font_color) - self.DisplayPILImage(bar_image, xc - radius, yc - radius) + if custom_bbox[0] != 0 or custom_bbox[1] != 0 or custom_bbox[2] != 0 or custom_bbox[3] != 0: + bar_image = bar_image.crop(box=custom_bbox) + + self.DisplayPILImage(bar_image, xc - radius + custom_bbox[0], yc - radius + custom_bbox[1]) + # self.DisplayPILImage(bar_image, xc - radius, yc - radius) # Load image from the filesystem, or get from the cache if it has already been loaded previously def open_image(self, bitmap_path: str) -> Image: diff --git a/library/stats.py b/library/stats.py index 0617ff2e..191fa0cb 100644 --- a/library/stats.py +++ b/library/stats.py @@ -177,7 +177,12 @@ def display_themed_radial_bar(theme_data, value, min_size=0, unit='', custom_tex font_size=theme_data.get("FONT_SIZE", 10), font_color=theme_data.get("FONT_COLOR", (0, 0, 0)), background_color=theme_data.get("BACKGROUND_COLOR", (0, 0, 0)), - background_image=get_theme_file_path(theme_data.get("BACKGROUND_IMAGE", None)) + background_image=get_theme_file_path(theme_data.get("BACKGROUND_IMAGE", None)), + custom_bbox=theme_data.get("CUSTOM_BBOX", (0, 0, 0, 0)), + text_offset=theme_data.get("TEXT_OFFSET", (0, 0)), + bar_background_color = theme_data.get("BAR_BACKGROUND_COLOR", (0, 0, 0)), + draw_bar_background = theme_data.get("DRAW_BAR_BACKGROUND", False), + bar_decoration = theme_data.get("BAR_DECORATION", "") ) @@ -313,8 +318,8 @@ def temperature(cls): cpu_temp_line_graph_data['SHOW'] = False display_themed_temperature_value(cpu_temp_text_data, temperature) - display_themed_progress_bar(cpu_temp_radial_data, temperature) - display_themed_temperature_radial_bar(cpu_temp_graph_data, temperature) + display_themed_progress_bar(cpu_temp_graph_data, temperature) + display_themed_temperature_radial_bar(cpu_temp_radial_data, temperature) display_themed_line_graph(cpu_temp_line_graph_data, cls.last_values_cpu_temperature) @classmethod diff --git a/res/themes/Advanced Radials Test/Credits.md b/res/themes/Advanced Radials Test/Credits.md new file mode 100644 index 00000000..06895998 --- /dev/null +++ b/res/themes/Advanced Radials Test/Credits.md @@ -0,0 +1,4 @@ +### Credits for graphical resources used from freepik + +Acknowledgements for resources : + diff --git a/res/themes/Advanced Radials Test/background.png b/res/themes/Advanced Radials Test/background.png new file mode 100644 index 00000000..fbfa2943 Binary files /dev/null and b/res/themes/Advanced Radials Test/background.png differ diff --git a/res/themes/Advanced Radials Test/preview.png b/res/themes/Advanced Radials Test/preview.png new file mode 100644 index 00000000..f7b668a8 Binary files /dev/null and b/res/themes/Advanced Radials Test/preview.png differ diff --git a/res/themes/Advanced Radials Test/theme.yaml b/res/themes/Advanced Radials Test/theme.yaml new file mode 100644 index 00000000..318a287c --- /dev/null +++ b/res/themes/Advanced Radials Test/theme.yaml @@ -0,0 +1,306 @@ +author: "@hicwic" + +display: + # Specify the display size in inch for this theme: 3.5" (default) or 5" + DISPLAY_SIZE: 3.5" + + # Specify the display orientation for this theme: portrait or landscape (reverse orientation is managed in config.yaml) + DISPLAY_ORIENTATION: landscape + + # Backplate RGB LED color (for HW revision 'flagship' devices only), set one that match your theme dominant color + DISPLAY_RGB_LED: 255, 0, 0 + +static_images: + BACKGROUND: + PATH: background.png + X: 0 + Y: 0 + WIDTH: 480 + HEIGHT: 320 + + + + +STATS: + CPU: + PERCENTAGE: + INTERVAL: 1 + RADIAL: + SHOW: True + X: 120 + Y: 100 + RADIUS: 80 + WIDTH: 26 + MIN_VALUE: 0 + MAX_VALUE: 100 + ANGLE_START: 110 + ANGLE_END: 250 + ANGLE_STEPS: 10 + ANGLE_SEP: 0 + CLOCKWISE: True + BAR_COLOR: 0, 250, 0 + BAR_BACKGROUND_COLOR: 0, 50, 0 + DRAW_BAR_BACKGROUND: True + BAR_DECORATION: Ellipse + SHOW_TEXT: True + SHOW_UNIT: True + FONT: roboto/Roboto-Bold.ttf + FONT_SIZE: 20 + FONT_COLOR: 0, 250, 0 + #BACKGROUND_COLOR: 200, 200, 200 + BACKGROUND_IMAGE: background.png + CUSTOM_BBOX: [0, 0, 80, 160] + TEXT_OFFSET: [-30, 0] + TEMPERATURE: + INTERVAL: 5 + RADIAL: + SHOW: True + X: 300 + Y: 180 + RADIUS: 80 + WIDTH: 26 + MIN_VALUE: 0 + MAX_VALUE: 100 + ANGLE_START: 200 + ANGLE_END: 340 + ANGLE_STEPS: 10 + ANGLE_SEP: 0 + CLOCKWISE: True + BAR_COLOR: 0, 250, 0 + BAR_BACKGROUND_COLOR: 0, 50, 0 + DRAW_BAR_BACKGROUND: True + BAR_DECORATION: Ellipse + SHOW_TEXT: True + SHOW_UNIT: True + FONT: roboto/Roboto-Bold.ttf + FONT_SIZE: 20 + FONT_COLOR: 0, 250, 0 + #BACKGROUND_COLOR: 200, 200, 200 + BACKGROUND_IMAGE: background.png + CUSTOM_BBOX: [0, 0, 160, 80] + TEXT_OFFSET: [-10, -20] + FAN_SPEED: + RADIAL: + SHOW: True + X: 173 + Y: 230 + RADIUS: 31 + WIDTH: 13 + MIN_VALUE: 0 + MAX_VALUE: 100 + ANGLE_START: 220 + ANGLE_END: 210 + ANGLE_STEPS: 20 + ANGLE_SEP: 0 + CLOCKWISE: True + BAR_COLOR: 200, 100, 50 + BAR_BACKGROUND_COLOR: 50, 0, 0 + DRAW_BAR_BACKGROUND: True + SHOW_TEXT: True + SHOW_UNIT: True + FONT: roboto/Roboto-Bold.ttf + FONT_SIZE: 15 + FONT_COLOR: 248, 177, 51 + #BACKGROUND_COLOR: 200, 200, 200 + BACKGROUND_IMAGE: background.png + MEMORY: + INTERVAL: 1 + VIRTUAL: + #RADIAL: + # SHOW: FALSE + # X: 66 + # Y: 151 + # RADIUS: 31 + # WIDTH: 13 + # MIN_VALUE: 0 + # MAX_VALUE: 100 + # ANGLE_START: 20 + # ANGLE_END: 20 + # ANGLE_STEPS: 1 + # ANGLE_SEP: 25 + # CLOCKWISE: True + # BAR_COLOR: 200, 100, 50 + # SHOW_TEXT: True + # SHOW_UNIT: True + # FONT: roboto/Roboto-Bold.ttf + # FONT_SIZE: 13 + # FONT_COLOR: 248, 177, 51 + # BACKGROUND_COLOR: 0, 0, 0 + # BACKGROUND_IMAGE: background.png + RADIAL: + SHOW: True + X: 87 + Y: 240 + RADIUS: 39 + WIDTH: 15 + MIN_VALUE: 0 + MAX_VALUE: 100 + ANGLE_START: 20 + ANGLE_END: 20 + ANGLE_STEPS: 1 + ANGLE_SEP: 25 + CLOCKWISE: True + BAR_COLOR: 0, 0, 200 + BAR_BACKGROUND_COLOR: 0, 0, 50 + DRAW_BAR_BACKGROUND: True + SHOW_TEXT: True + SHOW_UNIT: True + FONT: roboto/Roboto-Bold.ttf + FONT_SIZE: 13 + FONT_COLOR: 248, 177, 51 + # BACKGROUND_COLOR: 0, 0, 0 + BACKGROUND_IMAGE: background.png + GPU: + INTERVAL: 1 + PERCENTAGE: + RADIAL: + SHOW: True + X: 120 + Y: 100 + RADIUS: 80 + WIDTH: 26 + MIN_VALUE: 0 + MAX_VALUE: 100 + ANGLE_START: 70 + ANGLE_END: 290 + ANGLE_STEPS: 10 + ANGLE_SEP: 0 + CLOCKWISE: False + BAR_COLOR: 255, 0, 0 + BAR_BACKGROUND_COLOR: 50, 0, 0 + DRAW_BAR_BACKGROUND: True + BAR_DECORATION: Ellipse + SHOW_TEXT: True + SHOW_UNIT: True + FONT: roboto/Roboto-Bold.ttf + FONT_SIZE: 20 + FONT_COLOR: 255, 0, 0 + # BACKGROUND_COLOR: 0, 0, 0 + BACKGROUND_IMAGE: background.png + CUSTOM_BBOX: [80, 0, 160, 160] + TEXT_OFFSET: [30, 0] + MEMORY_PERCENT: + GRAPH: + SHOW: False + X: 349 + Y: 48 + WIDTH: 102 + HEIGHT: 9 + MIN_VALUE: 0 + MAX_VALUE: 100 + BAR_COLOR: 255, 0, 0 + BAR_OUTLINE: False + # BACKGROUND_COLOR: 0, 0, 0 + BACKGROUND_IMAGE: background.png + TEXT: + SHOW: False + SHOW_UNIT: True + X: 295 + Y: 46 + FONT: jetbrains-mono/JetBrainsMono-Bold.ttf + FONT_SIZE: 20 + FONT_COLOR: 21, 176, 231 + #BACKGROUND_COLOR: 132, 154, 165 + BACKGROUND_IMAGE: background.png + TEMPERATURE: + RADIAL: + SHOW: True + X: 300 + Y: 180 + RADIUS: 80 + WIDTH: 26 + MIN_VALUE: 0 + MAX_VALUE: 100 + ANGLE_START: 160 + ANGLE_END: 20 + ANGLE_STEPS: 10 + ANGLE_SEP: 0 + CLOCKWISE: False + BAR_COLOR: 255, 0, 0 + BAR_BACKGROUND_COLOR: 50, 0, 0 + DRAW_BAR_BACKGROUND: True + BAR_DECORATION: Ellipse + SHOW_TEXT: True + SHOW_UNIT: True + FONT: roboto/Roboto-Bold.ttf + FONT_SIZE: 20 + FONT_COLOR: 255, 0, 0 + #BACKGROUND_COLOR: 200, 200, 200 + BACKGROUND_IMAGE: background.png + CUSTOM_BBOX: [0, 80, 160, 160] + TEXT_OFFSET: [10, 20] + FAN_SPEED: + RADIAL: + SHOW: True + X: 430 + Y: 68 + RADIUS: 31 + WIDTH: 13 + MIN_VALUE: 0 + MAX_VALUE: 100 + ANGLE_START: 320 + ANGLE_END: 320 + ANGLE_STEPS: 20 + ANGLE_SEP: 0 + CLOCKWISE: False + BAR_COLOR: 200, 100, 50 + BAR_BACKGROUND_COLOR: 100, 50, 25 + DRAW_BAR_BACKGROUND: True + SHOW_TEXT: True + SHOW_UNIT: True + FONT: roboto/Roboto-Bold.ttf + FONT_SIZE: 15 + FONT_COLOR: 248, 177, 51 + #BACKGROUND_COLOR: 200, 200, 200 + BACKGROUND_IMAGE: background.png + FPS: + TEXT: + SHOW: False + SHOW_UNIT: False + X: 46 + Y: 279 + MIN_SIZE: 4 + FONT: jetbrains-mono/JetBrainsMono-Bold.ttf + FONT_SIZE: 27 + FONT_COLOR: 255, 255, 255 + #BACKGROUND_COLOR: 100, 100, 100 + BACKGROUND_IMAGE: background.png + LINE_GRAPH: + SHOW: False + X: 180 + Y: 220 + WIDTH: 133 + HEIGHT: 82 + MIN_VALUE: 0 + MAX_VALUE: 144 + HISTORY_SIZE: 100 + AUTOSCALE: True + LINE_COLOR: 255, 255, 255 + AXIS: True + BACKGROUND_IMAGE: background.png + NET: + INTERVAL: 1 + ETH: + UPLOAD: + TEXT: + SHOW: False + X: 344 + Y: 263 + FONT: jetbrains-mono/JetBrainsMono-Bold.ttf + FONT_SIZE: 10 + FONT_COLOR: 255, 255, 255 + # BACKGROUND_COLOR: 132, 154, 165 + BACKGROUND_IMAGE: background.png + DOWNLOAD: + TEXT: + SHOW: False + X: 390 + Y: 232 + FONT: jetbrains-mono/JetBrainsMono-Bold.ttf + FONT_SIZE: 10 + FONT_COLOR: 255, 255, 255 + # BACKGROUND_COLOR: 132, 154, 165 + BACKGROUND_IMAGE: background.png + + +