#!/usr/bin/python3 import notify2 from time import sleep from playsound import playsound import os from pystray import MenuItem as item import pystray from PIL import Image import argparse import threading NAME = 'Eye Strain Reminder' MESSAGE = 'Friendly reminder to observe the 20-20-20 rule' MESSAGE_MISSED = 'Missed notification(s), resuming countdown' TIMEOUT = 20 MILLISECOND = 1000 MINUTE = 60 DIR = os.path.dirname(os.path.abspath(__file__)) icon = None mute = False disable_notifications = False invert_icons = False notify_thread = None def init(): print("Initializing EyeStrainReminder...") notify2.init(NAME) def create_tray_icon(): global icon image = get_image() icon = pystray.Icon(NAME, image, NAME, generate_menu_items()) icon.run() def update_icon(): global icon image = get_image() icon.icon = image def get_image(): theme = [[f"{DIR}/files/eye_light.png", f"{DIR}/files/eye_dark.png"], [f"{DIR}/files/eye_dark.png", f"{DIR}/files/eye_light.png"]] return Image.open(theme[invert_icons][disable_notifications]) def generate_menu_items(): menu_items = [] menu_items.append(item('Mute' if not mute else 'Unmute', toggle_mute)) menu_items.append(item('Do Not Disturb' if not disable_notifications else 'Enable Notifications', toggle_notifications)) return menu_items def toggle_mute(): global mute mute = not mute update_menu() def toggle_notifications(): global disable_notifications disable_notifications = not disable_notifications update_menu() update_icon() def update_menu(): global icon icon.menu = generate_menu_items() icon.update_menu() def uninit(): notify2.uninit() def wait(): sleep(TIMEOUT*MINUTE) #pass def send_notification(): if not disable_notifications: notify(MESSAGE) else: print("Notifications are disabled, waiting for an enable...") while disable_notifications: sleep(10) notify(MESSAGE_MISSED) def notify(message): print(message) notification = notify2.Notification(NAME, message, "notification-device-eject") notification.set_timeout(TIMEOUT * MILLISECOND) notification.set_urgency(notify2.URGENCY_LOW) notification.show() play_sound() sleep(TIMEOUT) notification.close() play_sound() def play_sound(): if not mute: playsound(f"{DIR}/files/default.wav") def main(): init() while 1: wait() send_notification() uninit() if __name__ == '__main__': notify_thread = threading.Thread(target=main, name="Notify Thread") notify_thread.start() create_tray_icon() notify_thread.join()