| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228 | ;;; org-effectiveness.el --- Measuring the personal effectiveness;; Copyright (C) 2013 Free Software Foundation, Inc.;; Author: David Arroyo Menéndez <davidam@es.gnu.org>;; Keywords: effectiveness, plot;; Homepage: http://orgmode.org;;;; This file is not part of GNU Emacs, yet.;;;; GNU Emacs is free software: you can redistribute it and/or modify;; it under the terms of the GNU General Public License as published by;; the Free Software Foundation, either version 3 of the License, or;; (at your option) any later version.;; GNU Emacs is distributed in the hope that it will be useful,;; but WITHOUT ANY WARRANTY; without even the implied warranty of;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the;; GNU General Public License for more details.;; You should have received a copy of the GNU General Public License;; along with GNU Emacs.  If not, see <http://www.gnu.org/licenses/>.;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Commentary:;; This file implements functions to measure the effectiveness in org.;; Org-mode doesn't load this module by default - if this is not what;; you want, configure the variable `org-modules'. Thanks to #emacs-es;; irc channel for your support.;;; Code:(require 'org)(defun org-effectiveness-count-keyword(keyword)  "Print a message with the number of keyword outline in the current buffer"  (interactive "sKeyword: ")  (save-excursion    (goto-char (point-min))    (message "Number of %s: %d" keyword (count-matches (concat "* " keyword)))))(defun org-effectiveness-count-todo()  "Print a message with the number of todo tasks in the current buffer"  (interactive)  (save-excursion     (goto-char (point-min))    (message "Number of TODO: %d" (count-matches "* TODO"))))									     (defun org-effectiveness-count-done()  "Print a message with the number of done tasks in the current buffer"  (interactive)  (save-excursion    (goto-char (point-min))    (message "Number of DONE: %d" (count-matches "* DONE"))))(defun org-effectiveness-count-canceled()  "Print a message with the number of canceled tasks in the current buffer"  (interactive)  (save-excursion    (goto-char (point-min))    (message "Number of Canceled: %d" (count-matches "* CANCEL+ED"))))(defun org-effectiveness()  "Returns the effectiveness in the current org buffer"  (interactive)  (save-excursion    (goto-char (point-min))    (let ((done (float (count-matches "* DONE.*\n.*")))	  (canc (float (count-matches "* CANCEL+ED.*\n.*"))))      (if (and (= done canc) (zerop done))	  (setq effectiveness 0)	(setq effectiveness (* 100 (/ done (+ done canc)))))      (message "Effectiveness: %f" effectiveness))))(defun org-effectiveness-keywords-in-date(keyword date)  (interactive "sKeyword: \nsDate: " keyword date)  (setq count (count-matches (concat keyword ".*\n.*" date)))  (message (concat "%sS: %d" keyword count)))(defun org-effectiveness-dones-in-date(date)   (interactive "sGive me a date: " date)   (setq count (count-matches (concat "DONE.*\n.*" date)))   (message "DONES: %d" count))(defun org-effectivenes-todos-in-date(date)   (interactive "sGive me a date: " date)   (setq count (count-matches (concat "TODO.*\n.*" date)))   (message "TODOS: %d" count))(defun org-effectiveness-canceled-in-date(date)   (interactive "sGive me a date: " date)   (setq count (count-matches (concat "CANCEL+ED.*\n.*" date)))   (message "CANCELEDS: %d" count))(defun org-effectiveness-in-date(date &optional notmessage)  (interactive "sGive me a date: " date)  (save-excursion    (goto-char (point-min))    (let ((done (float (count-matches (concat "* DONE.*\n.*" date))))	  (canc (float (count-matches (concat "* CANCEL+ED.*\n.*" date)))))      (if (and (= done canc) (zerop done))	  (setq effectiveness 0)	(setq effectiveness (* 100 (/ done (+ done canc)))))      (if (eq notmessage 1)	  (message "%d" effectiveness)	(message "Effectiveness: %d " effectiveness)))))(defun org-effectiveness-month-to-string (m)  (if (< m 10)      (concat "0" (number-to-string m))    (number-to-string m)))(defun org-effectiveness-plot(startdate enddate)  (interactive "sGive me the start date: \nsGive me the end date: " startdate enddate)  (setq dates (org-effectiveness-check-dates startdate enddate))  (setq syear (cadr (assoc 'startyear dates)))  (setq smonth (cadr (assoc 'startmonth dates)))  (setq eyear (cadr (assoc 'endyear dates)))  (setq emonth (assoc 'endmonth dates));; Checking the format of the dates  (if (not (string-match "[0-9][0-9][0-9][0-9]-[0-9][0-9]" startdate))       (message "The start date must have the next format YYYY-MM"))  (if (not (string-match "[0-9][0-9][0-9][0-9]-[0-9][0-9]" enddate))       (message "The end date must have the next format YYYY-MM"));; Checking if startdate < enddate  (if (string-match "^[0-9][0-9][0-9][0-9]" startdate)      (setq startyear (string-to-number (match-string 0 startdate))))  (if (string-match "[0-9][0-9]$" startdate)      (setq startmonth (string-to-number (match-string 0 startdate))))  (if (string-match "^[0-9][0-9][0-9][0-9]" enddate)      (setq endyear (string-to-number (match-string 0 enddate))))  (if (string-match "[0-9][0-9]$" enddate)      (setq endmonth (string-to-number (match-string 0 enddate))))  (if (> startyear endyear)       (message "The start date must be before that end date"))  (if (and (= startyear endyear) (> startmonth endmonth))      (message "The start date must be before that end date"));; Create a file   (let ((month startmonth)	(year startyear)	(str ""))    (while (and (>= endyear year) (>= endmonth month))      (setq str (concat str (number-to-string year) "-" (org-effectiveness-month-to-string month) " " (org-effectiveness-in-date (concat (number-to-string year) "-" (org-effectiveness-month-to-string month)) 1) "\n"))      (if (= month 12)	  (progn 	    (setq year (+ 1 year))	    (setq month 1))	(setq month (+ 1 month))))      (write-region str nil "/tmp/org-effectiveness"));; Create the bar graph   (if (file-exists-p "/usr/bin/gnuplot")      (call-process "/bin/bash" nil t nil "-c" "/usr/bin/gnuplot -e 'plot \"/tmp/org-effectiveness\" using 2:xticlabels(1) with histograms' -p")    (message "gnuplot is not installed")))(defun org-effectiveness-ascii-bar(n &optional label)  "Print a bar with the percentage from 0 to 100 printed in ascii"  (interactive "nPercentage: \nsLabel: ")  (if (or (< n 0) (> n 100))      (message "The percentage must be between 0 to 100")    (let ((x 0)	  (y 0)	  (z 0))      (insert (format "\n### %s ###" label))      (insert "\n-")      (while (< x n)	(insert "-")	(setq x (+ x 1)))      (insert "+\n")      (insert (format "%d" n))      (if (> n 10)	  (setq y (+ y 1)))      (while (< y n)	(insert " ")	(setq y (+ y 1)))      (insert "|\n")      (insert "-")      (while (< z n)	(insert "-")	(setq z (+ z 1)))      (insert "+"))))(defun org-effectiveness-check-dates (startdate enddate)  "Generate a list with ((startyear startmonth) (endyear endmonth))"  (setq str nil)  (if (not (string-match "[0-9][0-9][0-9][0-9]-[0-9][0-9]" startdate))       (setq str "The start date must have the next format YYYY-MM"))  (if (not (string-match "[0-9][0-9][0-9][0-9]-[0-9][0-9]" enddate))       (setq str "The end date must have the next format YYYY-MM"));; Checking if startdate < enddate  (if (string-match "^[0-9][0-9][0-9][0-9]" startdate)      (setq startyear (string-to-number (match-string 0 startdate))))  (if (string-match "[0-9][0-9]$" startdate)      (setq startmonth (string-to-number (match-string 0 startdate))))  (if (string-match "^[0-9][0-9][0-9][0-9]" enddate)      (setq endyear (string-to-number (match-string 0 enddate))))  (if (string-match "[0-9][0-9]$" enddate)      (setq endmonth (string-to-number (match-string 0 enddate))))  (if (> startyear endyear)      (setq str "The start date must be before that end date"))  (if (and (= startyear endyear) (> startmonth endmonth))      (setq str "The start date must be before that end date"))  (if str      (message str);;    (list (list startyear startmonth) (list endyear endmonth))))    (list (list 'startyear startyear) (list 'startmonth startmonth) (list 'endyear endyear) (list 'endmonth endmonth))))(defun org-effectiveness-plot-ascii (startdate enddate)  (interactive "sGive me the start date: \nsGive me the end date: " startdate enddate)  (setq dates (org-effectiveness-check-dates startdate enddate))  (setq syear (cadr (assoc 'startyear dates)))  (setq smonth (cadr (assoc 'startmonth dates)))  (setq eyear (cadr (assoc 'endyear dates)))  (setq emonth (cadr (assoc 'endmonth dates)));;  (switch-to-buffer "*org-effectiveness*")  (let ((month smonth)  	(year syear)  	(str ""))    (while (and (>= eyear year) (>= emonth month))      (org-effectiveness-ascii-bar (string-to-number (org-effectiveness-in-date (concat (number-to-string year) "-" (org-effectiveness-month-to-string month)) 1)) (format "%s-%s" year month))      (if (= month 12)  	  (progn   	    (setq year (+ 1 year))  	    (setq month 1))  	(setq month (+ 1 month))))))(provide 'org-effectiveness)
 |