Files
Artemis/themes.py

166 lines
8.6 KiB
Python

from functools import partial
import os
from PyQt5.QtWidgets import QAction
from PyQt5.QtCore import pyqtSlot
from PyQt5.QtGui import QPixmap
import constants
from utilities import (throwable_message,
is_valid_html_color,)
class ThemeConstants(object):
FOLDER = "themes"
EXTENSION = ".qss"
ICONS_FOLDER = "icons"
DEFAULT = "1-system"
CURRENT = ".current_theme"
COLORS = "colors.txt"
COLOR_SEPARATOR = "="
DEFAULT_ACTIVE_COLOR = "#39eaff"
DEFAULT_INACTIVE_COLOR = "#9f9f9f"
THEME_NOT_FOUND = "Theme not found"
MISSING_THEME = "Missing theme in " + FOLDER + " folder."
class Theme(object):
def __init__(self, parent):
self.__parent = parent
self.__parent.active_color = ThemeConstants.DEFAULT_ACTIVE_COLOR
self.__parent.inactive_color = ThemeConstants.DEFAULT_INACTIVE_COLOR
self.__theme_path = ThemeConstants.DEFAULT
self.__parent.default_images_folder = os.path.join(ThemeConstants.FOLDER,
ThemeConstants.DEFAULT,
ThemeConstants.ICONS_FOLDER)
self.__detect_themes()
def __refresh_range_labels(self):
self.__parent.set_acf_interval_label()
self.__parent.set_band_filter_label(self.__parent.activate_low_band_filter_btn,
self.__parent.lower_band_spinbox,
self.__parent.lower_band_filter_unit,
self.__parent.lower_band_confidence,
self.__parent.activate_up_band_filter_btn,
self.__parent.upper_band_spinbox,
self.__parent.upper_band_filter_unit,
self.__parent.upper_band_confidence,
self.__parent.band_range_lbl)
self.__parent.set_band_filter_label(self.__parent.activate_low_freq_filter_btn,
self.__parent.lower_freq_spinbox,
self.__parent.lower_freq_filter_unit,
self.__parent.lower_freq_confidence,
self.__parent.activate_up_freq_filter_btn,
self.__parent.upper_freq_spinbox,
self.__parent.upper_freq_filter_unit,
self.__parent.upper_freq_confidence,
self.__parent.freq_range_lbl)
@pyqtSlot()
def __apply(self, theme_path):
self.__theme_path = theme_path
self.__change()
self.__parent.display_specs(self.__parent.result_list.currentItem(), None)
self.__refresh_range_labels()
self.__parent.audio_widget.refresh_btns_colors(self.__parent.active_color, self.__parent.inactive_color)
def __detect_themes(self):
themes = []
for theme_folder in os.listdir(ThemeConstants.FOLDER):
relative_folder = os.path.join(ThemeConstants.FOLDER, theme_folder)
if os.path.isdir(os.path.abspath(relative_folder)):
relative_folder = os.path.join(ThemeConstants.FOLDER, theme_folder)
themes.append(relative_folder)
for theme_path in themes:
theme_name = '&' + ' '.join(
map(lambda s: s.capitalize(),
os.path.basename(theme_path).split('-')[1].split('_')
)
)
new_theme = QAction(theme_name, self.__parent)
self.__parent.menu_themes.addAction(new_theme)
new_theme.triggered.connect(partial(self.__apply, theme_path))
def __change(self):
try:
with open(os.path.join(
self.__theme_path,
os.path.basename(self.__theme_path).split('-')[1] + ThemeConstants.EXTENSION)) as stylesheet:
style = stylesheet.read()
self.__parent.setStyleSheet(style)
self.__parent.download_window.setStyleSheet(style)
except FileNotFoundError:
throwable_message(self.__parent, title = ThemeConstants.THEME_NOT_FOUND,
text = ThemeConstants.MISSING_THEME).show()
else:
icons_path = os.path.join(self.__theme_path, ThemeConstants.ICONS_FOLDER)
default_icons_path = os.path.join(ThemeConstants.FOLDER,
ThemeConstants.DEFAULT,
ThemeConstants.ICONS_FOLDER)
if os.path.exists(os.path.join(icons_path, constants.NOT_SELECTED)) and \
os.path.exists(os.path.join(icons_path, constants.NOT_AVAILABLE)):
self.__parent.default_images_folder = icons_path
else:
self.__parent.default_images_folder = default_icons_path
path_to_search_label = os.path.join(icons_path, constants.SEARCH_LABEL_IMG)
default_search_label = os.path.join(default_icons_path, constants.SEARCH_LABEL_IMG)
if os.path.exists(path_to_search_label):
self.__parent.search_label.setPixmap(QPixmap(path_to_search_label))
self.__parent.modulation_search_label.setPixmap(QPixmap(path_to_search_label))
self.__parent.location_search_label.setPixmap(QPixmap(path_to_search_label))
else:
self.__parent.search_label.setPixmap(QPixmap(default_search_label))
self.__parent.modulation_search_label.setPixmap(QPixmap(default_search_label))
self.__parent.location_search_label.setPixmap(QPixmap(default_search_label))
self.__parent.search_label.setScaledContents(True)
self.__parent.modulation_search_label.setScaledContents(True)
self.__parent.location_search_label.setScaledContents(True)
path_to_volume_label = os.path.join(icons_path, constants.VOLUME_LABEL_IMG)
default_volume_label = os.path.join(default_icons_path, constants.VOLUME_LABEL_IMG)
if os.path.exists(path_to_volume_label):
self.__parent.volume_label.setPixmap(QPixmap(path_to_volume_label))
else:
self.__parent.volume_label.setPixmap(QPixmap(default_volume_label))
self.__parent.volume_label.setScaledContents(True)
path_to_colors = os.path.join(self.__theme_path, ThemeConstants.COLORS)
active_color_ok = False
inactive_color_ok = False
valid_format = False
valid_file = False
if os.path.exists(path_to_colors):
valid_file = True
with open(path_to_colors, "r") as colors_file:
for line in colors_file:
if ThemeConstants.COLOR_SEPARATOR in line:
valid_format = True
quality, color = line.split(ThemeConstants.COLOR_SEPARATOR)
color = color.rstrip()
if quality.lower() == constants.ACTIVE and is_valid_html_color(color):
self.__parent.active_color = color
active_color_ok = True
if quality.lower() == constants.INACTIVE and is_valid_html_color(color):
self.__parent.inactive_color = color
inactive_color_ok = True
if not all([valid_file, valid_format, active_color_ok, inactive_color_ok]):
self.__parent.active_color = ThemeConstants.DEFAULT_ACTIVE_COLOR
self.__parent.inactive_color = ThemeConstants.DEFAULT_INACTIVE_COLOR
try:
with open(os.path.join(ThemeConstants.FOLDER,
ThemeConstants.CURRENT), "w") as current_theme:
current_theme.write(self.__theme_path)
except:
pass
def initialize(self):
current_theme_file = os.path.join(ThemeConstants.FOLDER, ThemeConstants.CURRENT)
if os.path.exists(current_theme_file):
with open(current_theme_file) as current_theme_path:
theme_path = current_theme_path.read()
if theme_path != ThemeConstants.DEFAULT:
self.__apply(theme_path)