Mercurial > emacs
comparison lisp/org/org-timer.el @ 100269:032aa24b2125
Checking in the correct versions of the files, sorry, I hade used the files
from an experimental branch.....
author | Carsten Dominik <dominik@science.uva.nl> |
---|---|
date | Sun, 07 Dec 2008 18:45:03 +0000 |
parents | |
children | cea079b68b76 |
comparison
equal
deleted
inserted
replaced
100268:b1b9e6c5c96c | 100269:032aa24b2125 |
---|---|
1 ;;; org-clock.el --- The time clocking code for Org-mode | |
2 | |
3 ;; Copyright (C) 2008 Free Software Foundation, Inc. | |
4 | |
5 ;; Author: Carsten Dominik <carsten at orgmode dot org> | |
6 ;; Keywords: outlines, hypermedia, calendar, wp | |
7 ;; Homepage: http://orgmode.org | |
8 ;; Version: 6.14 | |
9 ;; | |
10 ;; This file is part of GNU Emacs. | |
11 ;; | |
12 ;; GNU Emacs is free software: you can redistribute it and/or modify | |
13 ;; it under the terms of the GNU General Public License as published by | |
14 ;; the Free Software Foundation, either version 3 of the License, or | |
15 ;; (at your option) any later version. | |
16 | |
17 ;; GNU Emacs is distributed in the hope that it will be useful, | |
18 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of | |
19 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
20 ;; GNU General Public License for more details. | |
21 | |
22 ;; You should have received a copy of the GNU General Public License | |
23 ;; along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. | |
24 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; | |
25 ;; | |
26 ;;; Commentary: | |
27 | |
28 ;; This file contains the relative timer code for Org-mode | |
29 | |
30 (require 'org) | |
31 | |
32 (defvar org-timer-start-time nil | |
33 "t=0 for the running timer.") | |
34 | |
35 (defconst org-timer-re "\\([-+]?[0-9]+\\):\\([0-9]\\{2\\}\\):\\([0-9]\\{2\\}\\)" | |
36 "Regular expression used to match timer stamps.") | |
37 | |
38 (defcustom org-timer-format "%s " | |
39 "The format to insert the time of the timer. | |
40 This format must contain one instance of \"%s\" which will be replaced by | |
41 the value of the relative timer." | |
42 :group 'org-time | |
43 :type 'string) | |
44 | |
45 ;;;###autoload | |
46 (defun org-timer-start (&optional offset) | |
47 "Set the starting time for the relative timer to now. | |
48 When called with prefix argument OFFSET, prompt the user for an offset time, | |
49 with the default taken from a timer stamp at point, if any. | |
50 If OFFSET is a string or an integer, it is directly taken to be the offset | |
51 without user interaction. | |
52 When called with a double prefix arg, all timer strings in the active | |
53 region will be shifted by a specific amount. You will be prompted for | |
54 the amount, with the default to make the first timer string in | |
55 the region 0:00:00." | |
56 (interactive "P") | |
57 (if (equal offset '(16)) | |
58 (call-interactively 'org-timer-change-times-in-region) | |
59 (let (delta def s) | |
60 (if (not offset) | |
61 (setq org-timer-start-time (current-time)) | |
62 (cond | |
63 ((integerp offset) (setq delta offset)) | |
64 ((stringp offset) (setq delta (org-timer-hms-to-secs offset))) | |
65 (t | |
66 (setq def (if (org-in-regexp org-timer-re) | |
67 (match-string 0) | |
68 "0:00:00") | |
69 s (read-string | |
70 (format "Restart timer with offset [%s]: " def))) | |
71 (unless (string-match "\\S-" s) (setq s def)) | |
72 (setq delta (org-timer-hms-to-secs (org-timer-fix-incomplete s))))) | |
73 (setq org-timer-start-time | |
74 (seconds-to-time | |
75 (- | |
76 (time-to-seconds (current-time)) | |
77 (org-timer-hms-to-secs s))))) | |
78 (message "Timer start time set to %s, current value is %s" | |
79 (format-time-string "%T" org-timer-start-time) | |
80 (org-timer-secs-to-hms (or delta 0)))))) | |
81 | |
82 ;;;###autoload | |
83 (defun org-timer (&optional restart) | |
84 "Insert a H:MM:SS string from the timer into the buffer. | |
85 The first time this command is used, the timer is started. When used with | |
86 a `C-u' prefix, force restarting the timer. | |
87 When used with a double prefix arg `C-u C-u', change all the timer string | |
88 in the region by a fixed amount. This can be used to recalibrate a timer | |
89 that was not started at the correct moment." | |
90 (interactive "P") | |
91 (if (equal restart '(4)) (org-timer-start)) | |
92 (or org-timer-start-time (org-timer-start)) | |
93 (insert (format | |
94 org-timer-format | |
95 (org-timer-secs-to-hms | |
96 (floor | |
97 (- (time-to-seconds (current-time)) | |
98 (time-to-seconds org-timer-start-time))))))) | |
99 | |
100 ;;;###autoload | |
101 (defun org-timer-change-times-in-region (beg end delta) | |
102 "Change all h:mm:ss time in region by a DELTA." | |
103 (interactive | |
104 "r\nsEnter time difference like \"-1:08:26\". Default is first time to zero: ") | |
105 (let ((re "[-+]?[0-9]+:[0-9]\\{2\\}:[0-9]\\{2\\}") p) | |
106 (unless (string-match "\\S-" delta) | |
107 (save-excursion | |
108 (goto-char beg) | |
109 (when (re-search-forward re end t) | |
110 (setq delta (match-string 0)) | |
111 (if (equal (string-to-char delta) ?-) | |
112 (setq delta (substring delta 1)) | |
113 (setq delta (concat "-" delta)))))) | |
114 (setq delta (org-timer-hms-to-secs (org-timer-fix-incomplete delta))) | |
115 (when (= delta 0) (error "No change")) | |
116 (save-excursion | |
117 (goto-char end) | |
118 (while (re-search-backward re beg t) | |
119 (setq p (point)) | |
120 (replace-match | |
121 (save-match-data | |
122 (org-timer-secs-to-hms (+ (org-timer-hms-to-secs (match-string 0)) delta))) | |
123 t t) | |
124 (goto-char p))))) | |
125 | |
126 ;;;###autoload | |
127 (defun org-timer-item (&optional arg) | |
128 "Insert a description-type item with the curren timer value." | |
129 (interactive "P") | |
130 (let ((ind 0)) | |
131 (save-excursion | |
132 (skip-chars-backward " \n\t") | |
133 (condition-case nil | |
134 (progn | |
135 (org-beginning-of-item) | |
136 (setq ind (org-get-indentation))) | |
137 (error nil))) | |
138 (or (bolp) (newline)) | |
139 (org-indent-line-to ind) | |
140 (insert "- ") | |
141 (org-timer (if arg '(4))) | |
142 (insert ":: "))) | |
143 | |
144 (defun org-timer-fix-incomplete (hms) | |
145 "If hms is a H:MM:SS string with missing hour or hour and minute, fix it." | |
146 (if (string-match "\\(?:\\([0-9]+:\\)?\\([0-9]+:\\)\\)?\\([0-9]+\\)" hms) | |
147 (replace-match | |
148 (format "%d:%02d:%02d" | |
149 (if (match-end 1) (string-to-number (match-string 1 hms)) 0) | |
150 (if (match-end 2) (string-to-number (match-string 2 hms)) 0) | |
151 (string-to-number (match-string 3 hms))) | |
152 t t hms) | |
153 (error "Canot parse HMS string \"%s\"" hms))) | |
154 | |
155 (defun org-timer-hms-to-secs (hms) | |
156 "Convert h:mm:ss string to an integer time. | |
157 If the string starts with a minus sign, the integer will be negative." | |
158 (if (not (string-match | |
159 "\\([-+]?[0-9]+\\):\\([0-9]\\{2\\}\\):\\([0-9]\\{2\\}\\)" | |
160 hms)) | |
161 0 | |
162 (let* ((h (string-to-number (match-string 1 hms))) | |
163 (m (string-to-number (match-string 2 hms))) | |
164 (s (string-to-number (match-string 3 hms))) | |
165 (sign (equal (substring (match-string 1 hms) 0 1) "-"))) | |
166 (setq h (abs h)) | |
167 (* (if sign -1 1) (+ s (* 60 (+ m (* 60 h)))))))) | |
168 | |
169 (defun org-timer-secs-to-hms (s) | |
170 "Convert integer S into h:mm:ss. | |
171 If the integer is negative, the strig will start with \"-\"." | |
172 (let (sign m h) | |
173 (setq sign (if (< s 0) "-" "") | |
174 s (abs s) | |
175 m (/ s 60) s (- s (* 60 m)) | |
176 h (/ m 60) m (- m (* 60 h))) | |
177 (format "%s%d:%02d:%02d" sign h m s))) | |
178 | |
179 ;; arch-tag: 97538f8c-3871-4509-8f23-1e7b3ff3d107 | |
180 | |
181 ;;; org-timer.el ends here |