def showCustom_(self, sender): self.startDate = Timings.combineDateWithTime( nsDateToDatetime(self.dpkrFrom.dateValue())) self.endDate = Timings.combineDateWithTime( nsDateToDatetime(self.dpkrTo.dateValue()) + datetime.timedelta(days=1)) self.generateChart()
def currentWeekMenu_(self, sender): today = Timings.workStartDateTime() weekNumber = int(today.strftime("%w")) if weekNumber == 0: weekNumber = 7 d = today - datetime.timedelta(days=weekNumber - 1) self.setDate(d) self.updateState()
def __init__(self, fromDate, toDate): self.timings = Timings() self._fromDate = fromDate self._toDate = toDate
class Statistics(object): _avgWork = 0 _avgSlacking = 0 _maxValue = 0 def __init__(self, fromDate, toDate): self.timings = Timings() self._fromDate = fromDate self._toDate = toDate def _countAttrib(self, res): """Count basic attributes(average work, average slacking and maximum value)""" days = (self._toDate - self._fromDate).days self._avgWork = int(self.timings.spentSeconds / days) self._avgSlacking = int(self.timings.slackingSeconds / days) if res: self._maxValue = max(res) def _countObject(self, objType, targetAction): """Generic function for calculating projects data or slacking statistics""" self._data = DataManager.getByRange(self._fromDate, self._toDate) res = {} for date, task, projectName in self._data: if task == "__start__": self.timings.setPrevDate(None) objKey = projectName if objType == "project" else task spentSeconds = self.timings.count(date, Tasks.taskType(task)) if Tasks.taskType(task) != targetAction: self.timings.setPrevDate(date) continue if spentSeconds: if objKey not in res: res[objKey] = spentSeconds else: res[objKey] += spentSeconds self._countAttrib(res.values()) if res: return sorted(res.iteritems(), key=lambda item:item[1], reverse=True) else: return [] def countProjects(self): """Count project statistics""" return self._countObject("project", "work") def countSlacking(self): """Count slacking statistics""" return self._countObject("task", "slack") def countTasks(self): """Count tasks statistics divided by projects""" self._data = DataManager.getByRange(self._fromDate, self._toDate) res = {} for date, task, projectName in self._data: if task == "__start__": self.timings.setPrevDate(None) spentSeconds = self.timings.count(date, Tasks.taskType(task)) if Tasks.taskType(task) != "work": continue if spentSeconds: if projectName not in res: res[projectName] = {} if task not in res[projectName]: res[projectName][task] = spentSeconds else: res[projectName][task] += spentSeconds self._countAttrib([v for k in res for v in res[k].values()]) if res: ret = {} for k in res.keys(): ret[k] = sorted(res[k].iteritems(), key=lambda item: item[1], reverse=True) return ret else: return {} @property def maxValue(self): """Maximum value of calculated object (project /task / slackings)""" return self._maxValue @property def totalWork(self): """Total work done""" return self.timings.spentSeconds @property def avgWork(self): """Average work per day""" return self._avgWork @property def totalSlacking(self): """Total slacking""" return self.timings.slackingSeconds @property def avgSlacking(self): """Average slacking per day""" return self._avgSlacking
def setDate(self, date): self.startDate = date self.endDate = Timings.workStartDateTime() + datetime.timedelta(days=1)
class ReportsController(NSWindowController): attributeBox = objc.IBOutlet("attributeBox") graphView = objc.IBOutlet("graphView") scrollView = objc.IBOutlet("scrollView") lblWorkTotal = objc.IBOutlet("lblWorkTotal") lblAvgWork = objc.IBOutlet("lblAvgWork") lblSlackTotal = objc.IBOutlet("lblSlackTotal") lblAvgSlack = objc.IBOutlet("lblAvgSlack") sgmControl = objc.IBOutlet("sgmControl") dpkrFrom = objc.IBOutlet("dpkrFrom") dpkrTo = objc.IBOutlet("dpkrTo") btnShow = objc.IBOutlet("btnShow") startDate = Timings.workStartDateTime() endDate = Timings.workStartDateTime() + datetime.timedelta(days=1) reportType = "tasks" def init(self): return super(ReportsController, self).initWithWindowNibName_("Reports") def showWindow_(self, sender): self.window().makeKeyAndOrderFront_(sender) def awakeFromNib(self): self.window().setFrameAutosaveName_("reportsWindow") self.customControls = [self.btnShow, self.dpkrTo, self.dpkrFrom] self.dpkrTo.setDateValue_(NSDate.alloc().init()) self.dpkrFrom.setDateValue_(NSDate.alloc().init()) self.graphView.setConversionFunction(secToTimeStr) self.generateChart() def setDate(self, date): self.startDate = date self.endDate = Timings.workStartDateTime() + datetime.timedelta(days=1) def updateCustomDatePicker(self): self.dpkrTo.setDateValue_(datetimeToNSDate(self.endDate)) self.dpkrFrom.setDateValue_(datetimeToNSDate(self.startDate)) def updateState(self): self.updateCustomDatePicker() self.setCustomControlsEnabled(False) self.generateChart() def setCustomControlsEnabled(self, enabled): for control in self.customControls: control.setEnabled_(enabled) def generateChart(self): self.graphView.setScrollView(self.scrollView) stat = Statistics(self.startDate, self.endDate) if self.reportType == "tasks": self.graphView.setData(stat.countTasks(), self.reportType) elif self.reportType == "projects": self.graphView.setData(stat.countProjects(), self.reportType) elif self.reportType == "slacking": self.graphView.setData(stat.countSlacking(), self.reportType) self.graphView.setScale(stat.maxValue) self.lblWorkTotal.setStringValue_(secToTimeStr(stat.totalWork)) self.lblAvgWork.setStringValue_(secToTimeStr(stat.avgWork)) self.lblSlackTotal.setStringValue_(secToTimeStr(stat.totalSlacking)) self.lblAvgSlack.setStringValue_(secToTimeStr(stat.avgSlacking)) self.graphView.setNeedsDisplay_(True) # def windowDidBecomeMain_(self, sender): # self.generateChart() @objc.IBAction def customMenu_(self, sender): self.setCustomControlsEnabled(True) @objc.IBAction def todayMenu_(self, sender): self.setDate(Timings.workStartDateTime()) self.updateState() @objc.IBAction def yeaterdayMenu_(self, sender): self.startDate = Timings.workStartDateTime() - datetime.timedelta(days=1) self.endDate = Timings.workStartDateTime() self.updateState() @objc.IBAction def currentMonthMenu_(self, sender): today = Timings.workStartDateTime() d = today - datetime.timedelta(days=int(today.strftime("%d")) - 1) self.setDate(d) self.updateState() @objc.IBAction def currentWeekMenu_(self, sender): today = Timings.workStartDateTime() weekNumber = int(today.strftime("%w")) if weekNumber == 0: weekNumber = 7 d = today - datetime.timedelta(days=weekNumber - 1) self.setDate(d) self.updateState() @objc.IBAction def days20Menu_(self, sender): self.setDate(Timings.workStartDateTime() - datetime.timedelta(days=20)) self.updateState() @objc.IBAction def days30Menu_(self, sender): self.setDate(Timings.workStartDateTime() - datetime.timedelta(days=30)) self.updateState() @objc.IBAction def days10_(self, sender): self.setDate(Timings.workStartDateTime() - datetime.timedelta(days=10)) self.updateState() @objc.IBAction def typeChanged_(self, sender): sel = self.sgmControl.selectedSegment() if sel == 0: self.reportType = "tasks" elif sel == 1: self.reportType = "projects" elif sel == 2: self.reportType = "slacking" self.generateChart() @objc.IBAction def showCustom_(self, sender): self.startDate = Timings.combineDateWithTime( nsDateToDatetime(self.dpkrFrom.dateValue())) self.endDate = Timings.combineDateWithTime( nsDateToDatetime(self.dpkrTo.dateValue()) + datetime.timedelta(days=1)) self.generateChart()
def days10_(self, sender): self.setDate(Timings.workStartDateTime() - datetime.timedelta(days=10)) self.updateState()
def currentMonthMenu_(self, sender): today = Timings.workStartDateTime() d = today - datetime.timedelta(days=int(today.strftime("%d")) - 1) self.setDate(d) self.updateState()
def yeaterdayMenu_(self, sender): self.startDate = Timings.workStartDateTime() - datetime.timedelta(days=1) self.endDate = Timings.workStartDateTime() self.updateState()
def todayMenu_(self, sender): self.setDate(Timings.workStartDateTime()) self.updateState()