Add base functionality: Show agenda.

This commit is contained in:
Sergio Martínez Portela 2021-04-03 01:13:41 +02:00
parent 97a63380c6
commit 6a71f342f0
3 changed files with 163 additions and 23 deletions

1
.gitignore vendored
View File

@ -1 +1,2 @@
__pycache__ __pycache__
.idea

106
doc_manager.py Normal file
View File

@ -0,0 +1,106 @@
import logging
import os
import sys
from datetime import datetime
from typing import List
import org_rw
from org_rw import OrgTime
def is_today(ot: OrgTime):
now = datetime.now()
return (
(ot.time.year == now.year)
and (ot.time.month == now.month)
and (ot.time.day == now.day)
)
class Agenda:
def __init__(self, /,
with_hour: List[org_rw.Headline],
no_hour: List[org_rw.Headline],
):
self.with_hour = with_hour
self.no_hour = no_hour
def print(self):
for item in self.with_hour:
print(item.scheduled.time, item.state, item.title)
if len(self.with_hour) > 0:
print("--------")
for item in self.no_hour:
print(item.scheduled.time, item.state, item.title)
class DocumentManager:
def __init__(self, basepath):
self.basepath = basepath
def load(self):
top = os.path.abspath(self.basepath)
docs = []
for root, dirs, files in os.walk(top):
for name in files:
if ".org" not in name:
continue
path = os.path.join(root, name)
try:
doc = org_rw.load(open(path), extra_cautious=True)
docs.append(doc)
except Exception as err:
import traceback
traceback.print_exc()
print(f"== On {path}")
sys.exit(1)
logging.info("Loaded {} files".format(len(docs)))
self.docs = docs
def get_agenda(self) -> Agenda:
headline_count = 0
items_in_agenda = []
now = datetime.now()
for doc in self.docs:
for hl in doc.getAllHeadlines():
headline_count += 1
if hl.scheduled and isinstance(hl.scheduled, OrgTime):
if is_today(hl.scheduled):
items_in_agenda.append(hl)
elif (hl.scheduled.time.to_datetime() < now) and hl.is_todo:
items_in_agenda.append(hl)
logging.info("Read {} items".format(headline_count))
logging.info("{} items in agenda today".format(len(items_in_agenda)))
items_with_hour = [
item
for item in items_in_agenda
if item.scheduled and is_today(item.scheduled) and item.scheduled.time.hour
]
other_items = [
item
for item in items_in_agenda
if not (
item.scheduled and is_today(item.scheduled) and item.scheduled.time.hour
)
]
logging.info("{} items today for a specific hour".format(len(items_with_hour)))
return Agenda(
with_hour=sorted(items_with_hour, key=lambda x: x.scheduled.time),
no_hour=other_items
)

73
main.py
View File

@ -8,31 +8,25 @@ import time
from PySide2.QtCore import QObject, QThread, Signal, Slot from PySide2.QtCore import QObject, QThread, Signal, Slot
from PySide2.QtWidgets import (QApplication, QDialog, QGroupBox, QHBoxLayout, from PySide2.QtWidgets import (QApplication, QDialog, QGroupBox, QHBoxLayout,
QLabel, QLineEdit, QProgressBar, QPushButton, QLabel, QLineEdit, QProgressBar, QPushButton,
QScrollArea, QTabBar, QVBoxLayout) QScrollArea, QTabBar, QVBoxLayout, QSplitter, QFrame)
ORG_PATH = os.environ['ORG_PATH'] import doc_manager
DOCS_PATH = os.environ['ORG_PATH']
class LoadDoneSignal(QObject): class LoadDoneSignal(QObject):
sig = Signal(str) sig = Signal(doc_manager.DocumentManager)
class DocumentLoader(QThread): class DocumentLoader(QThread):
def __init__(self, parent = None): def __init__(self, manager):
QThread.__init__(self, parent) QThread.__init__(self, None)
self.exiting = False self.manager = manager
self.signal = LoadDoneSignal() self.signal = LoadDoneSignal()
def run(self): def run(self):
end = time.time() + 3 self.manager.load()
while self.exiting==False: self.signal.sig.emit(self.manager)
sys.stdout.write('*')
sys.stdout.flush()
time.sleep(1)
now = time.time()
if now >= end:
self.exiting = True
self.signal.sig.emit('OK')
class Dialog(QDialog): class Dialog(QDialog):
@ -40,6 +34,7 @@ class Dialog(QDialog):
super(Dialog, self).__init__() super(Dialog, self).__init__()
self.loader = None self.loader = None
self.manager = doc_manager.DocumentManager(DOCS_PATH)
layout = QVBoxLayout() layout = QVBoxLayout()
@ -53,7 +48,7 @@ class Dialog(QDialog):
layout.setSpacing(0) layout.setSpacing(0)
self.results = QScrollArea() self.results = QScrollArea(widgetResizable=True)
layout.addWidget(self.results) layout.addWidget(self.results)
# Options # Options
@ -81,26 +76,61 @@ class Dialog(QDialog):
def startLoad(self): def startLoad(self):
self.edit.setDisabled(True) self.edit.setDisabled(True)
self.edit.setVisible(False)
self.tabBar.setDisabled(True) self.tabBar.setDisabled(True)
self.progressBar.setVisible(True) self.progressBar.setVisible(True)
self.loader = DocumentLoader() self.loader = DocumentLoader(self.manager)
self.loader.signal.sig.connect(self.longoperationcomplete) self.loader.signal.sig.connect(self.longoperationcomplete)
self.loading_start_time = time.time()
self.loader.start() self.loader.start()
def endLoad(self): def endLoad(self):
self.edit.setDisabled(False) self.edit.setDisabled(False)
self.edit.setVisible(True)
self.tabBar.setDisabled(False) self.tabBar.setDisabled(False)
self.progressBar.setVisible(False) self.progressBar.setVisible(False)
self.update_tab() self.update_tab()
def longoperationcomplete(self, data): def longoperationcomplete(self, data):
print("Complete with", data) logging.info("Loading complete in {:.3f}s".format(time.time() - self.loading_start_time))
self.endLoad() self.endLoad()
def loadAgenda(self): def loadAgenda(self):
logging.warning("loadAgenda not yet implemented") agenda = self.manager.get_agenda()
old = self.results.layout()
if old:
print("Deleting old")
old.deleteLater()
layout = QVBoxLayout()
for item in agenda.with_hour:
text = "{} {} {}".format(
item.scheduled.time,
item.state,
item.title,
)
label = QLabel(text=text)
layout.addWidget(label)
# if len(agenda.with_hour) > 0 and len(agenda.no_hour) > 0:
# layout.addWidget(QSplitter())
for item in agenda.no_hour:
text = "{} {} {}".format(
item.scheduled.time,
item.state,
item.title,
)
label = QLabel(text=text)
layout.addWidget(label)
frame = QFrame(self.results)
frame.setLayout(layout)
self.results.setWidget(frame)
def loadNotes(self): def loadNotes(self):
logging.warning("loadNotes not yet implemented") logging.warning("loadNotes not yet implemented")
@ -109,6 +139,9 @@ class Dialog(QDialog):
logging.warning("loadTasks not yet implemented") logging.warning("loadTasks not yet implemented")
# Create the Qt Application # Create the Qt Application
if __name__ == '__main__':
logging.basicConfig(level=logging.INFO, format="%(levelname)-8s %(message)s")
app = QApplication(sys.argv) app = QApplication(sys.argv)
dialog = Dialog() dialog = Dialog()