diff --git a/.ide/vim-views/index.yaws.view b/.ide/vim-views/index.yaws.view index d626383..5d0f577 100644 --- a/.ide/vim-views/index.yaws.view +++ b/.ide/vim-views/index.yaws.view @@ -95,12 +95,12 @@ setlocal nowinfixwidth setlocal wrap setlocal wrapmargin=0 silent! normal! zE -let s:l = 1 - ((0 * winheight(0) + 36) / 72) +let s:l = 104 - ((59 * winheight(0) + 35) / 71) if s:l < 1 | let s:l = 1 | endif exe s:l normal! zt -1 -normal! 0 +104 +normal! 038l lcd /mnt/secure/projects/jdb-labs/timestamper/web-app/www let &so = s:so_save | let &siso = s:siso_save doautoall SessionLoadPost diff --git a/.ide/vim-views/ts-screen.scss.view b/.ide/vim-views/ts-screen.scss.view index 9ef293d..8238af8 100644 --- a/.ide/vim-views/ts-screen.scss.view +++ b/.ide/vim-views/ts-screen.scss.view @@ -1,6 +1,6 @@ let s:so_save = &so | let s:siso_save = &siso | set so=0 siso=0 argglobal -edit ~/projects/jdb-labs/timestamper/web-app/www/css/ts-screen.scss +edit /mnt/secure/projects/jdb-labs/timestamper/web-app/www/css/ts-screen.scss setlocal keymap= setlocal noarabic setlocal autoindent @@ -26,8 +26,8 @@ setlocal nodiff setlocal equalprg= setlocal errorformat= setlocal expandtab -if &filetype != 'scss' -setlocal filetype=scss +if &filetype != '' +setlocal filetype= endif setlocal foldcolumn=0 setlocal foldenable @@ -83,8 +83,8 @@ setlocal statusline= setlocal suffixesadd= setlocal swapfile setlocal synmaxcol=3000 -if &syntax != 'scss' -setlocal syntax=scss +if &syntax != 'sass' +setlocal syntax=sass endif setlocal tabstop=4 setlocal tags= @@ -95,12 +95,12 @@ setlocal nowinfixwidth setlocal wrap setlocal wrapmargin=0 silent! normal! zE -let s:l = 120 - ((39 * winheight(0) + 23) / 46) +let s:l = 392 - ((46 * winheight(0) + 35) / 71) if s:l < 1 | let s:l = 1 | endif exe s:l normal! zt -120 -normal! 012l +392 +normal! 022l let &so = s:so_save | let &siso = s:siso_save doautoall SessionLoadPost " vim: set ft=vim : diff --git a/db/test/DECISION_TAB.LOG b/db/test/DECISION_TAB.LOG index ad60397..e20ccce 100644 Binary files a/db/test/DECISION_TAB.LOG and b/db/test/DECISION_TAB.LOG differ diff --git a/db/test/LATEST.LOG b/db/test/LATEST.LOG index 6625cd8..a04c530 100644 Binary files a/db/test/LATEST.LOG and b/db/test/LATEST.LOG differ diff --git a/db/test/id_counter.DCD b/db/test/id_counter.DCD index b009917..a8453cb 100644 Binary files a/db/test/id_counter.DCD and b/db/test/id_counter.DCD differ diff --git a/db/test/id_counter.DCL b/db/test/id_counter.DCL new file mode 100644 index 0000000..053704f Binary files /dev/null and b/db/test/id_counter.DCL differ diff --git a/db/test/ts_entry.DCD b/db/test/ts_entry.DCD index 1141c0b..2a952c8 100644 Binary files a/db/test/ts_entry.DCD and b/db/test/ts_entry.DCD differ diff --git a/db/test/ts_entry.DCL b/db/test/ts_entry.DCL new file mode 100644 index 0000000..23a3c9d Binary files /dev/null and b/db/test/ts_entry.DCL differ diff --git a/db/test/ts_ext_data.DCD b/db/test/ts_ext_data.DCD index 836eebb..feea703 100644 Binary files a/db/test/ts_ext_data.DCD and b/db/test/ts_ext_data.DCD differ diff --git a/db/test/ts_ext_data.DCL b/db/test/ts_ext_data.DCL deleted file mode 100644 index 2a0dcfa..0000000 Binary files a/db/test/ts_ext_data.DCL and /dev/null differ diff --git a/db/test/ts_user.DCD b/db/test/ts_user.DCD index ae33bb4..72948c8 100644 Binary files a/db/test/ts_user.DCD and b/db/test/ts_user.DCD differ diff --git a/db/test/ts_user.DCL b/db/test/ts_user.DCL deleted file mode 100644 index b061d25..0000000 Binary files a/db/test/ts_user.DCL and /dev/null differ diff --git a/doc/issues/desktop/0003tn3.rst b/doc/issues/desktop/0003ts3.rst similarity index 68% rename from doc/issues/desktop/0003tn3.rst rename to doc/issues/desktop/0003ts3.rst index 4e68438..fa9d5b0 100644 --- a/doc/issues/desktop/0003tn3.rst +++ b/doc/issues/desktop/0003ts3.rst @@ -4,7 +4,12 @@ Generate day seperators. When generating EventViews in the EventListView, we need to automatically create and insert day seperators (see prototype). +Resolution +---------- + +Day separators are added to the timeline by EntryListView.render. + ========= ========== Created: 2011-05-15 -Resolved: YYYY-MM-DD +Resolved: 2011-05-17 ========= ========== \ No newline at end of file diff --git a/doc/issues/desktop/0009tn3.rst b/doc/issues/desktop/0009tn3.rst index 07d4856..cd6ad74 100644 --- a/doc/issues/desktop/0009tn3.rst +++ b/doc/issues/desktop/0009tn3.rst @@ -2,6 +2,9 @@ Implement correct start time editor. ==================================== The start time input field needs to look the same as the start time view. +Alternatively, use a date picker. + +---- ========= ========== Created: 2011-05-15 diff --git a/doc/issues/desktop/0021tn5.rst b/doc/issues/desktop/0021ts5.rst similarity index 88% rename from doc/issues/desktop/0021tn5.rst rename to doc/issues/desktop/0021ts5.rst index 81aaf2f..4d7fd24 100644 --- a/doc/issues/desktop/0021tn5.rst +++ b/doc/issues/desktop/0021ts5.rst @@ -3,5 +3,5 @@ Constrain width of notes fields to width of mark. ========= ========== Created: 2011-06-10 -Resolved: YYYY-MM-DD +Resolved: 2011-06-17 ==================== \ No newline at end of file diff --git a/doc/issues/desktop/0022bn5.rst b/doc/issues/desktop/0022bn5.rst index cecafa7..9e90f28 100644 --- a/doc/issues/desktop/0022bn5.rst +++ b/doc/issues/desktop/0022bn5.rst @@ -4,6 +4,8 @@ Deleting an entry should cascade delete extended data. Currently the data remains in the database. It should not cause any problems, but it is wasting space. +---- + ========= ========== Created: 2011-06-15 Resolved: YYYY-MM-DD diff --git a/doc/issues/desktop/0024tn5.rst b/doc/issues/desktop/0024tn5.rst new file mode 100644 index 0000000..9505e35 --- /dev/null +++ b/doc/issues/desktop/0024tn5.rst @@ -0,0 +1,11 @@ +Hide day separators when all entries that day are excluded. +=========================================================== + +We should hide headings when there is no visible data. + +---- + +========= ========== +Created: 2011-06-17 +Resolved: YYYY-MM-DD +========= ========== \ No newline at end of file diff --git a/doc/issues/desktop/0025tn5.rst b/doc/issues/desktop/0025tn5.rst new file mode 100644 index 0000000..2088fe6 --- /dev/null +++ b/doc/issues/desktop/0025tn5.rst @@ -0,0 +1,21 @@ +Never animate excluded entries. +=============================== + +We need to have some visible indication when a user enters an +exlucded item that it was added, but it looks ugly and dirty when +we first render the list. + +Part of this is motivated by the fact that entering an excluded +entry is the excpected way for a user to stop the timer on an item +without having an explicit next item. + +If we choose to implement *D0026* this would free up the UI a bit. +In that case, we could gently flash the 'Show/Hide Excluded Items' +button (*D0027*). + +---- + +========= ========== +Created: 2011-06-17 +Resolved: YYYY-MM-DD +========= ========== \ No newline at end of file diff --git a/doc/issues/desktop/0026fn4.rst b/doc/issues/desktop/0026fn4.rst new file mode 100644 index 0000000..24985b8 --- /dev/null +++ b/doc/issues/desktop/0026fn4.rst @@ -0,0 +1,16 @@ +Add a default 'stop' behaviour. +=============================== + +It might be more natural to allow the user to hit a button on +the current entry to stop the timer on it than to explicitly +create a new excluded entry. + +Maybe have a default exclusion for all users, "ENTRY STOP" for example, +and have the button automatically add this entry. + +---- + +========= ========== +Created: 2011-06-17 +Resolved: YYYY-MM-DD +========= ========== \ No newline at end of file diff --git a/doc/issues/desktop/0027fn4.rst b/doc/issues/desktop/0027fn4.rst new file mode 100644 index 0000000..83e7b5e --- /dev/null +++ b/doc/issues/desktop/0027fn4.rst @@ -0,0 +1,12 @@ +Create a way to unhide excluded entries. +======================================== + +A button somewhere would be a good way to allow users to +show/hide excluded entries. + +---- + +========= ========== +Created: 2011-06-17 +Resolved: YYYY-MM-DD +========= ========== \ No newline at end of file diff --git a/www/css/ts-screen.css b/www/css/ts-screen.css index e2e1601..319656a 100644 --- a/www/css/ts-screen.css +++ b/www/css/ts-screen.css @@ -297,7 +297,8 @@ input { font-family: Cantarell; font-size: small; margin: 0; - padding: 0 0 0 1em; } + padding: 0 0 0 1em; + width: 70%; } #entry-list .entry .notes :first-child { margin-top: 0; } #entry-list .entry .notes .notes-input, #entry-list .entry .notes pre, #entry-list .entry .notes code { diff --git a/www/css/ts-screen.scss b/www/css/ts-screen.scss index c0526c4..2d7f4e0 100644 --- a/www/css/ts-screen.scss +++ b/www/css/ts-screen.scss @@ -389,6 +389,7 @@ input { font-size: small; margin: 0; padding: 0 0 0 1em; + width: 70%; :first-child { margin-top: 0; } diff --git a/www/index.yaws b/www/index.yaws index 62dab6f..d0caebb 100644 --- a/www/index.yaws +++ b/www/index.yaws @@ -99,6 +99,14 @@ out(YArg) -> + + @@ -145,11 +153,6 @@ out(YArg) ->
-
-

Today

-
start
-
duration
-
diff --git a/www/js/ts.js b/www/js/ts.js index 8a9eca1..7e6f300 100644 --- a/www/js/ts.js +++ b/www/js/ts.js @@ -355,8 +355,8 @@ $(document).ready(function(){ // render the element var el = entry.view.render().el; - // add it to the container - this.entryContainer.prepend(el); + // add it to the container after the topmost separator ("Today") + this.topSeparator.after(el); // hide it if excluded if (excluded) { @@ -401,21 +401,67 @@ $(document).ready(function(){ this.entryContainer.empty(); // last day we have printed a separator for - var currentDay = null; - var today = new Date(); + var today = new Date() + var currentDay = this.collection.at(0) ? + this.collection.at(0).get("timestamp"): today; + + // add the top-most day separator + this.topSeparator = ich.daySeparatorTemplate({ + separatorLabel: this.formatDaySeparator(today, today) }); + this.entryContainer.prepend(this.topSeparator); // iterate through the collection and render the elements. for (var i = 0, len = this.collection.length; i < len; i++) { var entry = this.collection.at(i); var nextEntry = (i + 1 < len ? this.collection.at(i + 1) : null); - if (currentDay != entry.get('timestamp').getDate()) { - currentDay = entry.get('timestamp').getDate(); - + // we are rendering buttom up, which means we need to insert the + // day separator before the first entry of the *next* period + if (currentDay.getDate() != entry.get("timestamp").getDate()) { + this.topSeparator.after(ich.daySeparatorTemplate( + {separatorLabel: this.formatDaySeparator(today, currentDay)})); + currentDay = entry.get('timestamp'); } this.renderOne(entry, nextEntry); } + }, + + formatDaySeparator: function(today, labelDay) { + + var days = ['Sunday', 'Monday', 'Tuesday', 'Wednesday', 'Thursday', + 'Friday', 'Saturday']; + var months = ['January', 'February', 'March', 'April', 'May', + 'June', 'July', 'August', 'September', 'October', + 'November', 'December']; + + var yearDiff = today.getFullYear() - labelDay.getFullYear(); + var monthDiff = today.getMonth() - labelDay.getMonth(); + var dayDiff = today.getDate() - labelDay.getDate(); + + // more than a calendar year old + if (yearDiff > 0) { + + return days[labelDay.getDay()] + ", " + + months[labelDay.getMonth()] + " " + labelDay.getDate() + + ", " + labelDay.getFullYear(); } + + // same calendar year, more than a week ago + else if (monthDiff > 0 || dayDiff > 7) { + + return days[labelDay.getDay()] + ", " + + months[labelDay.getMonth()] + " " + labelDay.getDate(); } + + // less than a week ago, more than yesterday + else if (dayDiff > 1) { + return "Last " + days[labelDay.getDay()]; } + + // yesterday + else if (dayDiff == 1) { return "Yesterday"; } + + // today + else if (dayDiff == 0) { return "Today"; } + } }); @@ -757,59 +803,3 @@ function dateToJSON(d) { + pad(d.getUTCMinutes())+':' + pad(d.getUTCSeconds())+'Z'; } - -function daysApart(d1, d2) { - var daysInMonth = [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30]; - - days1 = (d1.getFullYear() * 365) + daysInMonth[d1.getMonth()] + d1.getDate(); - days2 = (d2.getFullYear() * 365) + daysInMonth[d2.getMonth()] + d2.getDate(); - - return days1 - days2; -} - -function getEnglishDate(d) { - if (typeof getEnglishDate.today == 'undefined') { - getEnglishDate.today = new Date() }; - - var yearDiff = today.getFullYear() - d.getFullYear(); - var monthDiff = today.getMonth() - d.getMonth(); - var dayDiff = today.getDate() - d.getDate(); - - if (yearDiff > 1) { return capitalize(toWords(yearDiff)) + " years ago."; } - else if (yearDiff > 0) { return "Last year"; } - else if (monthDiff > 1) { - return capitalize(toWords(monthDiff)) + "months ago."; } - else if (monthDiff > 0) { return "Last month."; } - else if (dayDiff > 0) { - // weeks as 7-day periods - var weekDiff = Math.ceil(dayDiff / 7) - - // adjust for the hard boundary of the weekend - if (today.getDay() > d.getDay()) { weekDiff--; } - - if (weekDiff > 1) { - return capitalize(toWords(weekDiff)) + " weeks ago."; } - else if (weekDiff > 0) { return "Last week."; } - else { return capitalize(toWords(dayDiff)) + " days ago."; } - - } else if (yearDiff < 0 || monthDiff < 0 || daysDiff < 0) { - return "In the future."; } - else { return "Today."; } -} - - -function toWords(i) { - if (typeof toWords.words == 'undefined') { - toWords.words = ['zero','one','two','three','four', 'five','six', - 'seven','eight','nine','ten','eleven','twelve', - 'thirteen', 'fourteen','fifteen','sixteen', - 'seventeen','eighteen','nineteen' ]; - } - - if (i < 20) { return toWords.words[i]; } - else { return i.toString(); } -} - -function capitalize(s) { - return s.slice(0, 1).toUpperCase() + s.slice(1); -}