class Window(QtGui.QDialog): ''' ''' def __init__(self): super(Window, self).__init__() self.INTERVAL = 300000 # update interval in milliseconds # Container lists for shift widgets and timeslots. self.shiftWidgets = [] self.timeslotObjects = {} self.viewport = Viewport(self) self.scrollArea = ScrollArea(self.viewport) self.progressbar = Progressbar(self) # Regex for grabbing room names from shift summaries. self.pattern = re.compile("(\D*) \d*") # Initialize a schedule object and related timeslot objects. self.getSchedule() self.getTimeslots() # Create a QThread object for the webscrape. self.worker = Worker(self.timeslotObjects) # Connect QThread objects signals. self.worker.started.connect(self.starting) self.worker.finished.connect(self.finished) self.worker.signal.connect(self.updateDisplay) self.worker.start() self.timeslotTimer() self.mainLayout() self.createActions() self.createTrayIcon() self.setIcon() self.trayIcon.show() self.setWindowTitle("RoomWhen") self.setFixedHeight(500) def starting(self): self.progressbar.show() print("Starting thread!") def finished(self): self.progressbar.hide() print("Finished thread!") def updateDisplay(self, data): ''' If first run create widgets and layout, else update widgets information. ''' if data: self.createShiftWidgets() else: self.updateTimeslotStatus() def getSchedule(self): ''' Pull the current schedule, requires .icalURL file in same directory ''' url = '' try: with open('.icalURL', 'r') as icalURL: url = icalURL.readline().replace('\n', '') except IOError: pass # No pre made url file, so create dialogue for creating one. self.schedule = Schedule(url) self.schedule.events = self.schedule.sortEventsByDatetime() def getTimeslots(self): ''' Initiate timeslot objects, requires an already initialized schedule object. ''' # Schedule.listRooms() returns a dict of room:week for us to # create a timeslot for each room and only fetch important weeks. roomList = self.schedule.listRooms() for room in roomList: self.timeslotObjects[room] = Timeslots(room, roomList[room]) def timeslotTimer(self): ''' Method to start the worker thread at given interval. ''' self.timer = QtCore.QTimer() self.timer.setSingleShot(False) self.timer.timeout.connect(self.worker.start) self.timer.start(self.INTERVAL) def setIcon(self): ''' ''' icon = QtGui.QIcon('images/drink.png') self.trayIcon.setIcon(icon) self.setWindowIcon(icon) self.trayIcon.setToolTip("Placeholder") def mainLayout(self): ''' Create the main layout ''' self.layout = QtGui.QVBoxLayout(self) self.layout.addWidget(self.scrollArea) self.layout.addWidget(self.progressbar) self.setLayout(self.layout) def createShiftLayout(self): ''' Create a layout for a single shift. ''' for widget in self.shiftsWidgets: self.viewport.layout.addWidget(widget) def createActions(self): self.minimizeAction = QtGui.QAction("Mi&nimize", self, triggered=self.hide) self.restoreAction = QtGui.QAction("&Restore", self, triggered=self.showNormal) self.quitAction = QtGui.QAction("&Quit", self, triggered=QtGui.qApp.quit) def createTrayIcon(self): ''' ''' self.trayIconMenu = QtGui.QMenu(self) self.trayIconMenu.addAction(self.minimizeAction) self.trayIconMenu.addAction(self.restoreAction) self.trayIconMenu.addAction(self.quitAction) self.trayIcon = QtGui.QSystemTrayIcon(self) self.trayIcon.setContextMenu(self.trayIconMenu) def showMessage(self, titel, body): ''' ''' icon = QtGui.QSystemTrayIcon.MessageIcon(1) self.trayIcon.showMessage( titel, body, icon, 5000 ) def createShiftWidgets(self): ''' Create a widget with shift information for each shift. Requires already initialized schedule and timeslot objects.''' # For each shift create QWidget and set it's layout. for shift in self.schedule.events: # Use regex to get nice room name for our widget. patternMatch = re.match(self.pattern, shift['summary']) roomNiceName = patternMatch.group(1) start = shift['timeStart'] end = shift['timeEnd'] + datetime.timedelta(minutes=5) room = self.schedule.getRoom(shift) shiftWidget = ShiftWidget( roomNiceName, start.strftime("%Y-%m-%d"), self.timeslotObjects[room].findGames(start, end), room, start, end, parent = self.viewport ) self.shiftWidgets.append(shiftWidget) self.viewport.layout.addWidget(shiftWidget) def updateTimeslotStatus(self): ''' Iterate through all widgets and update any changes. ''' for widget in self.shiftWidgets: # Query timeslot for given widget room, about all games during it. timeslots = self.timeslotObjects[widget.room].findGames(widget.start, widget.end) for timeslot in timeslots: # Check if there has been any change if timeslot['Status'] != widget.statuses[timeslot['Timestamp']].text(): # Compose notification message. titel = widget.titel + ' ' + widget.date + " status changed" body = "The " + widget.titel + " at the " + widget.date + \ " had it's status change from " + \ widget.statuses[timeslot['Timestamp']].text() + \ " to " + timeslot['Status'] self.showMessage(titel, body) # Update widget with the change. widget.statuses[timeslot['Timestamp']].setText(timeslot['Status']) else: pass