Cómo mostrar un contador visual de segundos - 10, 9, 8,. . ¡se acabó el tiempo!

8

Q: ¿Cómo, por favor, puedo incorporar un contador visual de segundos que desaparecerá cuando se seleccione una opción o cuando se agote el reloj?

Ejemplo : *Messages*búfer

  • Tienes 10 segundos para hacer tu selección.

  • Tienes 9 segundos para hacer tu selección.

  • . . .

  • ¡Se acabó el tiempo!

Tengo una variable que se llama init-variable. Cuando non-nil, Emacs se carga con una configuración completa de varias personalizaciones de usuario. Cuando nil, Emacs se carga con el equivalente de Emacs -Q, es decir, no se cargan personalizaciones de usuario. La función read-char-exclusivetiene una buena característica para un contador de segundos, y he incorporado esa característica en el fragmento de código a continuación. El número de opción 1establece el init-variablea nil; número de opción 2o ninguna acción da como resultado la configuración predeterminada de non-nil.

(defvar init-variable t)

(let* (
    (emacs-q (read-char-exclusive nil nil 10)))
  (cond
    ((eq emacs-q ?1)
      (setq init-variable nil)
      (message "Emacs -Q"))
    ((eq emacs-q ?2)
      (message "Regular Loading."))
    (t (message "This is the default.")) ))
lista de leyes
fuente

Respuestas:

7

Desde su cadena de documentos, supongo que no puede incorporar la funcionalidad del mensaje de cuenta atrás read-char-exclusive. Sin embargo, puede envolverlo en su propio temporizador:

(let ((choice nil)
      (count  3))
  (while (>= count 0)
    (message (format "Seconds left to make your choice: %d" count))
    (setq count (if (setq choice (read-char-exclusive nil nil 1))
                    -1
                  (1- count))))
  (cond ((eq choice ?1)
         (message "You entered 1"))
        ((eq choice ?2)
         (message "You entered 2"))
        (t
         (message "The default"))))

En realidad, esto podría ser lo suficientemente útil como para envolverlo en una función. Aquí está un boceto rápido que funciona para algunas funciones que tienen los mismos argumentos en el mismo orden ( read-char, read-char-exclusive, read-event, y tal vez otros) - se extienden como te gusta hacer cosas con read-stringy otras personas que toman una lista de argumentos diferentes:

(defun countdown-read (fnx &optional prompt inherit-input-method seconds)
  "Reads a character or event and provides a countdown of SECONDS
to provide input.  Return nil if no input arrives in time.

FNX is a function that supports the rest of the
arguments (currently, `read-char', `read-char-exclusive',
`read-event', and maybe others).
If the optional argument PROMPT is non-nil, display that as a
prompt.
If the optional argument INHERIT-INPUT-METHOD is non-nil and some
input method is turned on in the current buffer, that input
method is used for reading a character.
If the optional argument SECONDS is non-nil, it should be a
number specifying the maximum number of seconds to wait for
input (default: 5)."
  (let (choice (seconds (or seconds 5)))
    (while (>= seconds 0)
      (message (format (concat (or prompt "") " (%d): ") seconds))
      (setq seconds (if (setq choice
                              (funcall fnx nil inherit-input-method 1))
                        -1
                      (1- seconds))))
    choice))

Usarlo se vería así:

(countdown-read #'read-char-exclusive "Please enter a character" nil 3)
Dan
fuente
¡Sí, esa nueva función será realmente muy útil! Gracias por extender su respuesta para incluirla, muy apreciada.
abogados