function sameDay(due, now) { return ( due.getFullYear() == now.getFullYear() && due.getMonth() == now.getMonth() && due.getDate() == now.getDate() ) } function dayDiff(due, now, stopAt) { // due and now are both Date objects // if due has the same day as now (i.e. due is today), return 0 // if due is tomorrow, return 1, the day after that 2, yesterday -1, etc. // when the absolute value of diff reaches stopAt, return stopAt let diff = 0 const step = (due > now) ? 1 : -1 while (!sameDay(due, now)) { now.setDate(now.getDate() + step) diff += step if (Math.abs(diff) >= stopAt) { return stopAt } } return diff } function humanDue(isoDue) { // converts ISO 8601 datetime string to relative time, e.g. tomorrow midnight const daysOfWeek = [ i18n("Sunday"), i18n("Monday"), i18n("Tuesday"), i18n("Wednesday"), i18n("Thursday"), i18n("Friday"), i18n("Saturday"), ] try { let due = new Date(isoDue) if (due.toString() == "Invalid Date") { console.warn(`Cannot parse due date: ${isoDue}`) return isoDue } let now = new Date() const pastDue = (due <= now) const dayDifference = dayDiff(due, now, 8) let humanDueString = "" if (dayDifference <= -2) { humanDueString = Qt.formatDate(due) } else if (dayDifference == -1) { humanDueString = i18n("Yesterday") } else if (dayDifference == 0) { humanDueString = i18n("Today") } else if (dayDifference == 1) { humanDueString = i18n("Tomorrow") } else if (dayDifference <= 6) { humanDueString = daysOfWeek[due.getDay()] } else { humanDueString = Qt.formatDate(due) } humanDueString += " " + Qt.formatTime(due) return humanDueString } catch (e) { return isoDue // screw it } } function dueLabelText() { if (type != "assignment") { return "" } if (submitted) { return i18n("Submitted") } if (!dueAt) { return i18n("Due date not announced") } return i18n("Due: ") + humanDue(dueAt) }