diff --git a/src/interface/desktop/__init__.py b/src/interface/desktop/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/src/interface/desktop/configure_window.py b/src/interface/desktop/configure_window.py new file mode 100644 index 00000000..d99cd0c3 --- /dev/null +++ b/src/interface/desktop/configure_window.py @@ -0,0 +1,70 @@ +# External Packages +from PyQt6 import QtWidgets +from PyQt6.QtCore import Qt + + +class ConfigureWindow(QtWidgets.QMainWindow): + """Create Window to Configure Khoj + Allow user to + 1. Enable/Disable search on 1. org-mode, 2. markdown, 3. beancount or 4. image content types + 2. Configure the server host and port + 3. Save the configuration to khoj.yml and start the server + """ + + def __init__(self): + super().__init__() + + # Initialize Configure Window + self.setWindowTitle("Khoj - Configure") + self.layout = QtWidgets.QVBoxLayout() + + # Org Mode Settings + orgmode_settings = QtWidgets.QWidget() + self.orgmode_layout = QtWidgets.QVBoxLayout(orgmode_settings) + enable_orgmode_search = QtWidgets.QCheckBox("Search Org-Mode Files") + enable_orgmode_search.stateChanged.connect(self.show_orgmode_search_options) + self.orgmode_layout.addWidget(enable_orgmode_search) + self.layout.addWidget(orgmode_settings) + + # Ledger Settings + ledger_settings = QtWidgets.QWidget() + self.ledger_layout = QtWidgets.QVBoxLayout(ledger_settings) + enable_ledger_search = QtWidgets.QCheckBox("Search Beancount Files") + enable_ledger_search.stateChanged.connect(self.show_ledger_search_options) + self.ledger_layout.addWidget(enable_ledger_search) + self.layout.addWidget(ledger_settings) + + # Button to Save Settings + action_bar = QtWidgets.QWidget() + action_bar_layout = QtWidgets.QHBoxLayout(action_bar) + save_button = QtWidgets.QPushButton("Start", clicked=self.save_settings) + action_bar_layout.addWidget(save_button) + self.layout.addWidget(action_bar) + + # Set the central widget of the Window. Widget will expand + # to take up all the space in the window by default. + self.config_window = QtWidgets.QWidget() + self.config_window.setLayout(self.layout) + + self.setCentralWidget(self.config_window) + + def save_settings(self, s): + # Save the settings to khoj.yml + pass + + def show_orgmode_search_options(self, s): + if Qt.CheckState(s) == Qt.CheckState.Checked: + self.orgmode_layout.layout().addWidget(QtWidgets.QLabel("Search Org-Mode Notes")) + self.orgmode_layout.layout().addWidget(QtWidgets.QLineEdit()) + else: + self.orgmode_layout.layout().removeWidget(self.orgmode_layout.layout().itemAt(1).widget()) + self.orgmode_layout.layout().removeWidget(self.orgmode_layout.layout().itemAt(1).widget()) + + def show_ledger_search_options(self, s): + if Qt.CheckState(s) == Qt.CheckState.Checked: + self.ledger_layout.layout().addWidget(QtWidgets.QLabel("Search Beancount Transactions")) + self.ledger_layout.layout().addWidget(QtWidgets.QLineEdit()) + else: + self.ledger_layout.layout().removeWidget(self.ledger_layout.layout().itemAt(1).widget()) + self.ledger_layout.layout().removeWidget(self.ledger_layout.layout().itemAt(1).widget()) + \ No newline at end of file diff --git a/src/interface/desktop/system_tray.py b/src/interface/desktop/system_tray.py new file mode 100644 index 00000000..52f45dd2 --- /dev/null +++ b/src/interface/desktop/system_tray.py @@ -0,0 +1,43 @@ +# Standard Packages +import webbrowser + +# External Packages +from PyQt6 import QtGui, QtWidgets + +# Internal Packages +from src.utils import constants + + +def create_system_tray(gui: QtWidgets.QApplication, window: QtWidgets.QMainWindow): + """Create System Tray with Menu + Menu Actions should contain + 1. option to open search page at localhost:8000/ + 2. option to open config page at localhost:8000/config + 3. to quit + """ + + # Create the system tray with icon + icon_path = constants.web_directory / 'assets/icons/favicon-144x144.png' + icon = QtGui.QIcon(f'{icon_path.absolute()}') + tray = QtWidgets.QSystemTrayIcon(icon) + tray.setVisible(True) + + # Create the menu and menu actions + menu = QtWidgets.QMenu() + menu_actions = [ + ('Search', lambda: webbrowser.open('http://localhost:8000/')), + ('Configure', window.show), + ('Quit', gui.quit), + ] + + # Add the menu actions to the menu + for action_text, action_function in menu_actions: + menu_action = QtGui.QAction(action_text, menu) + menu_action.triggered.connect(action_function) + menu.addAction(menu_action) + + # Add the menu to the system tray + tray.setContextMenu(menu) + + return tray + diff --git a/src/main.py b/src/main.py index a7c7a38a..780c9d61 100644 --- a/src/main.py +++ b/src/main.py @@ -1,19 +1,20 @@ # Standard Packages import sys -import webbrowser # External Packages import uvicorn from fastapi import FastAPI from fastapi.staticfiles import StaticFiles -from PyQt6 import QtGui, QtWidgets -from PyQt6.QtCore import Qt, QThread +from PyQt6 import QtWidgets +from PyQt6.QtCore import QThread # Internal Packages from src.configure import configure_server from src.router import router from src.utils import constants from src.utils.cli import cli +from src.interface.desktop.configure_window import ConfigureWindow +from src.interface.desktop.system_tray import create_system_tray # Initialize the Application Server @@ -75,107 +76,5 @@ class ServerThread(QThread): uvicorn.run(app, host=self.host, port=self.port) -class ConfigureWindow(QtWidgets.QMainWindow): - """Create Window to Configure Khoj - Allow user to - 1. Enable/Disable search on 1. org-mode, 2. markdown, 3. beancount or 4. image content types - 2. Configure the server host and port - 3. Save the configuration to khoj.yml and start the server - """ - - def __init__(self): - super().__init__() - - # Initialize Configure Window - self.setWindowTitle("Khoj - Configure") - self.layout = QtWidgets.QVBoxLayout() - - # Org Mode Settings - orgmode_settings = QtWidgets.QWidget() - self.orgmode_layout = QtWidgets.QVBoxLayout(orgmode_settings) - enable_orgmode_search = QtWidgets.QCheckBox( - "Search Org-Mode Files", - stateChanged = self.show_orgmode_search_options) - self.orgmode_layout.addWidget(enable_orgmode_search) - self.layout.addWidget(orgmode_settings) - - # Ledger Settings - ledger_settings = QtWidgets.QWidget() - self.ledger_layout = QtWidgets.QVBoxLayout(ledger_settings) - enable_ledger_search = QtWidgets.QCheckBox( - "Search Beancount Files", - state_changed=self.show_ledger_search_options) - self.ledger_layout.addWidget(enable_ledger_search) - self.layout.addWidget(ledger_settings) - - # Button to Save Settings - action_bar = QtWidgets.QWidget() - action_bar_layout = QtWidgets.QHBoxLayout(action_bar) - save_button = QtWidgets.QPushButton("Start", clicked=self.save_settings) - action_bar_layout.addWidget(save_button) - self.layout.addWidget(action_bar) - - # Set the central widget of the Window. Widget will expand - # to take up all the space in the window by default. - self.config_window = QtWidgets.QWidget() - self.config_window.setLayout(self.layout) - - self.setCentralWidget(self.config_window) - - def save_settings(self, s): - # Save the settings to khoj.yml - pass - - def show_orgmode_search_options(self, s): - if Qt.CheckState(s) == Qt.CheckState.Checked: - self.orgmode_layout.layout().addWidget(QtWidgets.QLabel("Search Org-Mode Files")) - self.orgmode_layout.layout().addWidget(QtWidgets.QLineEdit()) - else: - self.orgmode_layout.layout().removeWidget(self.orgmode_layout.layout().itemAt(1).widget()) - self.orgmode_layout.layout().removeWidget(self.orgmode_layout.layout().itemAt(1).widget()) - - def show_ledger_search_options(self, s): - if Qt.CheckState(s) == Qt.CheckState.Checked: - self.ledger_layout.layout().addWidget(QtWidgets.QLabel("Search Ledger Files")) - self.ledger_layout.layout().addWidget(QtWidgets.QLineEdit()) - else: - self.ledger_layout.layout().removeWidget(self.ledger_layout.layout().itemAt(1).widget()) - self.ledger_layout.layout().removeWidget(self.ledger_layout.layout().itemAt(1).widget()) - - -def create_system_tray(gui: QtWidgets.QApplication, window: QtWidgets.QMainWindow): - """Create System Tray with Menu - Menu Actions should contain - 1. option to open search page at localhost:8000/ - 2. option to open config page at localhost:8000/config - 3. to quit - """ - - # Create the system tray with icon - icon_path = constants.web_directory / 'assets/icons/favicon-144x144.png' - icon = QtGui.QIcon(f'{icon_path.absolute()}') - tray = QtWidgets.QSystemTrayIcon(icon) - tray.setVisible(True) - - # Create the menu and menu actions - menu = QtWidgets.QMenu() - menu_actions = [ - ('Search', lambda: webbrowser.open('http://localhost:8000/')), - ('Configure', window.show), - ('Quit', gui.quit), - ] - - # Add the menu actions to the menu - for action_text, action_function in menu_actions: - menu_action = QtGui.QAction(action_text, menu) - menu_action.triggered.connect(action_function) - menu.addAction(menu_action) - - # Add the menu to the system tray - tray.setContextMenu(menu) - - return tray - - if __name__ == '__main__': run()