1

Sometimes I prefer to do some work offline. I can time it and write it down and avoid starting up my computer.

I like to use a table and org-update-all-dblocks to calculate my hours for the day. It's very convenient for me, because I might spend odd numbers of minutes throughout the day doing work for a client.

If I want to quickly add my offline hours and update the table, does org-mode already have a function for this? I know that I can org-clock-in and org-clock-out to generate a clock, and then manually retype it and use org-update-all-dblocks to recalculate, but I would ideally like a single function I can call that will ask me for how many minutes I want to input. It should probably just use the current time and date as the start, even though that would seemingly conflict with work I start doing after adding the offline hours.

It would be even better if org-mode had a concept of offline hours that understood I might know the date but I probably didn't record the time of day, and so the time of day could be left out, but still calculated in a clock table.

If I have to write some quick and dirty elisp, what functions would be of use to me apart from the above? I think the pieces I'm missing is something to grab the most recent clock, something to add minutes to it, and something to request a number of minutes.

1

The following command inserts the typical org logbook entry, a time range starting from N minutes ago:

(defun org-insert-clock-range (&optional n)
  (interactive "NTime Offset (in min): ")
  (let* ((ctime (cdr (decode-time (current-time))))
         (min (car ctime))
         (start (apply 'encode-time 0 (- min n) (cdr ctime))))
    (org-insert-time-stamp start t t "CLOCK: ")
    (insert "--")
    (org-insert-time-stamp (current-time) t t)))
1

mutbuerger's answer helped me a lot. It's my first time programming in elisp other than configuration. His answer was close to the mark, but I still wanted the normal functionality of clock-in and clock-out for finding or creating the logbook under the closest heading, and adding a note.

My amended solution was this:

(defun offset-current-time (n)
  (let* ((ctime (cdr (decode-time (current-time))))
     (minutes (car ctime)))
    (apply 'encode-time 0 (- minutes n) (cdr ctime))))

(defun org-insert-clock-range (&optional n)
  (interactive "NTime Offset (in min): ")
    (org-clock-in nil (offset-current-time n))
    (org-clock-out))

(defadvice org-clock-out (after org-clock-out-after activate) (org-update-all-dblocks))

(add-hook 'org-mode-hook
    (lambda ()
    ; Keys for org mode
    ;snip
      (define-key evil-normal-state-map (kbd "gl") 'org-insert-clock-range)
    ;snip

    ))
0

I manage offline times with a toolbox of custom functions to manipulate clock logs in Org's own syntax and a script to convert a shorthand plain-text notation to Org's syntax.

Functions in https://github.com/clange/emacs/blob/master/.emacs.d/init/org-clock.el:

  • org-clock-split-current-interval (I bound this to C-c o s): if there is an interval in the current line, in which actually two tasks were done, facilitate splitting it into two intervals.
  • org-clock-change-hh-mm (bound to C-c o :): leaving the day unchanged, adapt the hours/minutes of a clock log. Typical use case: copy a clock log line from somewhere else, adapt it according to time worked offline.

Script: https://github.com/clange/scripts/blob/master/org-offline-to-clock/org-offline-to-clock.pl

My workflow of using it:

  1. record offline times in a text file e.g. on my mobile phone
  2. sync this file to my PC
  3. on the PC, run org-offline-to-clock.pl BEFORE > AFTER
  4. validate with diff BEFORE AFTER
  5. if happy, mv AFTER BEFORE
  6. move selected lines into my actual org file.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.