al-notification.el 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102
  1. ;;; al-notification.el --- Additional functionality for various notifications
  2. ;; Copyright © 2014-2016 Alex Kost
  3. ;; This program is free software; you can redistribute it and/or modify
  4. ;; it under the terms of the GNU General Public License as published by
  5. ;; the Free Software Foundation, either version 3 of the License, or
  6. ;; (at your option) any later version.
  7. ;; This program is distributed in the hope that it will be useful,
  8. ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
  9. ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  10. ;; GNU General Public License for more details.
  11. ;; You should have received a copy of the GNU General Public License
  12. ;; along with this program. If not, see <http://www.gnu.org/licenses/>.
  13. ;;; Code:
  14. (require 'timer)
  15. (require 'notifications)
  16. (require 'al-file)
  17. (defvar al/notification-sound
  18. (al/file-if-exists "/usr/share/sounds/freedesktop/stereo/bell.oga")
  19. "Default notification sound used by `al/timer-set'.")
  20. ;;; Timers
  21. (defvar al/timer nil
  22. "Current timer.")
  23. (defvar al/timer-format "%M:%S"
  24. "Format string for the time message.")
  25. (declare-function al/play-sound "al-sound" (file))
  26. ;;;###autoload
  27. (defun al/timer-set (msg seconds)
  28. "Notify with a sound and a message MSG in some SECONDS.
  29. Interactively, prompt for the message and the number of minutes.
  30. With prefix, prompt for the number of seconds."
  31. (interactive
  32. (list (read-string "Message: " nil nil "You should do something!")
  33. (if current-prefix-arg
  34. (read-number "Seconds for the timer: ")
  35. (* 60 (read-number "Minutes for the timer: ")))))
  36. (al/timer-cancel)
  37. (setq al/timer
  38. (run-at-time seconds nil
  39. (lambda (msg)
  40. (when (and al/notification-sound
  41. (require 'al-sound nil t))
  42. (al/play-sound al/notification-sound))
  43. (notifications-notify :title "Timer" :body msg))
  44. msg))
  45. (message "The timer has been set on %s."
  46. (format-time-string "%T" (timer--time al/timer))))
  47. (defun al/timer-funcall-on-active-timer (fun &optional silent)
  48. "Call function FUN if current timer is active.
  49. If timer is not active, display a message about it, unless SILENT
  50. is non-nil.
  51. FUN is called with a single argument - the number of seconds left
  52. for the current timer."
  53. (let ((seconds (al/timer-remaining-seconds)))
  54. (if (or (null seconds) (< seconds 0))
  55. (or silent (message "No active timer."))
  56. (funcall fun seconds))))
  57. (defun al/timer-remaining-seconds ()
  58. "Return the number of seconds left until the deadline of `al/timer'.
  59. The result is negative, if the timer is elapsed.
  60. Return nil if `al/timer' is not a proper timer."
  61. (and (timerp al/timer)
  62. (- (timer-until al/timer (current-time)))))
  63. (defun al/timer-remaining-time ()
  64. "Show the time left until the deadline of `al/timer'."
  65. (interactive)
  66. (al/timer-funcall-on-active-timer
  67. (lambda (sec)
  68. (message "Time left: %s."
  69. (format-time-string al/timer-format
  70. (seconds-to-time sec))))))
  71. (defun al/timer-cancel ()
  72. "Cancel current timer."
  73. (interactive)
  74. (al/timer-funcall-on-active-timer
  75. (lambda (sec)
  76. (cancel-timer al/timer)
  77. (setq al/timer nil)
  78. (message "The timer has been cancelled."))))
  79. (provide 'al-notification)
  80. ;;; al-notification.el ends here