#!/usr/bin/env python3 import sys import signal from functools import partial from PySide2 import QtCore, QtGui, QtWidgets from PySide2.QtWidgets import QMessageBox from data import Tasks, Log from exceptions import FimeFrackingException from new_task import NewTask from task_edit import TaskEdit from report import Report class App: def __init__(self): self.app = QtWidgets.QApplication(sys.argv) self.tasks = Tasks() self.log = Log() self.active_task = self.log.last_log() or "Nothing" icon = QtGui.QIcon.fromTheme("appointment-new") self.menu = QtWidgets.QMenu() self.new_task = NewTask(None) self.new_task.accepted.connect(self.new_task_selected) self.taskEdit = TaskEdit(None) self.taskEdit.accepted.connect(self.tasks_edited) self.reportDialog = Report(None) self.reportDialog.accepted.connect(self.report_done) self.tray = QtWidgets.QSystemTrayIcon() self.tray.setIcon(icon) self.tray.setContextMenu(self.menu) self.tray.show() self.tray.setToolTip("fimefracking") self.update_tray_menu() @QtCore.Slot() def new_task_selected(self): print(f"dialog input: {self.new_task.task_text}") @QtCore.Slot() def tasks_edited(self): self.tasks.tasks = self.taskEdit.tasks self.update_tray_menu() @QtCore.Slot() def report_done(self): self.active_task = self.log.last_log() or "Nothing" self.update_tray_menu() def change_task(self, task): self.active_task = task if task == "Nothing": return self.log.log(task) self.update_tray_menu() def update_tray_menu(self): self.menu.clear() tasks = list(self.tasks.tasks) tasks.append("Pause") if self.active_task == "Nothing": tasks.append("Nothing") for t in tasks: a = self.menu.addAction(t) a.triggered.connect(partial(self.change_task, t)) if t == self.active_task: a.setIcon(QtGui.QIcon.fromTheme("go-next")) self.menu.addSeparator() new_action = self.menu.addAction("New task") new_action.triggered.connect(self.new_task.show) new_action = self.menu.addAction("Edit tasks") new_action.triggered.connect(self.edit_tasks) report_action = self.menu.addAction("Report") report_action.triggered.connect(self.report) self.menu.addSeparator() exit_action = self.menu.addAction("Close") exit_action.triggered.connect(self.app.quit) def sigterm_handler(self, _signo, _frame): self.app.quit() def run(self): timer = QtCore.QTimer() # interrupt event loop regularly for signal handling timer.timeout.connect(lambda: None) timer.start(500) signal.signal(signal.SIGTERM, self.sigterm_handler) signal.signal(signal.SIGINT, self.sigterm_handler) self.app.exec_() @QtCore.Slot() def report(self): self.reportDialog.set_data(self.log.report()) self.reportDialog.show() @QtCore.Slot() def edit_tasks(self): self.taskEdit.tasks = self.tasks.tasks self.taskEdit.show() if __name__ == "__main__": try: app = App() app.run() except FimeFrackingException as e: QMessageBox.critical(None, "Error", str(e), QMessageBox.Ok)