Créer une fonction pour basculer les thèmes

8

Comment puis-je créer une fonction interactive pour basculer entre deux thèmes de couleurs?

D'après ce que j'ai pu trouver, il n'y a pas de variable définie sur le thème de couleur actuellement utilisé, en fait plusieurs peuvent être chargés simultanément?

De plus, pour basculer, vous devez d'abord faire disable-themepour le thème actuellement chargé, pour ne pas faire de conflits entre les thèmes.

Comment faire cela sans savoir quel thème est actuellement chargé?

Jborg
la source
2
(car custom-enabled-themes)renvoie le thème actuellement activé.
mutbuerger
Copie possible de Comment réinitialiser le thème de couleur?
mutbuerger
Utilisez simplement l'avocat-charge-thème, si vous utilisez l'avocat.
InHarmsWay

Réponses:

4

Je l'ai fait mais je change de 3 thèmes (mes propres kosmos, leuven et default)

Vous pouvez consulter https://github.com/habamax/.emacs.d/blob/master/lisp/haba-appearance.el

extrait:

(defvar *haba-theme-dark* 'kosmos)
(defvar *haba-theme-light* 'leuven)
(defvar *haba-current-theme* *haba-theme-dark*)

;; disable other themes before loading new one
(defadvice load-theme (before theme-dont-propagate activate)
  "Disable theme before loading new one."
  (mapcar #'disable-theme custom-enabled-themes))


(defun haba/next-theme (theme)
  (if (eq theme 'default)
      (disable-theme *haba-current-theme*)
    (progn
      (load-theme theme t)))
  (setq *haba-current-theme* theme))

(defun haba/toggle-theme ()
  (interactive)
  (cond ((eq *haba-current-theme* *haba-theme-dark*) (haba/next-theme *haba-theme-light*))
        ((eq *haba-current-theme* *haba-theme-light*) (haba/next-theme 'default))
        ((eq *haba-current-theme* 'default) (haba/next-theme *haba-theme-dark*))))

Ensuite, liez une clé à haba / toggle-theme.

J'utilise emacs sur 2 machines et environnements différents (jour, fin de soirée) donc il est possible de sauvegarder / restaurer le thème actuel sur quitter / charger emacs. Ce qui est pratique :)

Maxim Kim
la source
5

J'ai écrit quelques fonctions pour parcourir un groupe de thèmes.

(setq ivan/themes '(elixir elixir-dark))
(setq ivan/themes-index 0)

(defun ivan/cycle-theme ()
  (interactive)
  (setq ivan/themes-index (% (1+ ivan/themes-index) (length ivan/themes)))
  (ivan/load-indexed-theme))

(defun ivan/load-indexed-theme ()
  (ivan/try-load-theme (nth ivan/themes-index ivan/themes)))

(defun ivan/try-load-theme (theme)
  (if (ignore-errors (load-theme theme :no-confirm))
      (mapcar #'disable-theme (remove theme custom-enabled-themes))
    (message "Unable to find theme file for ‘%s’" theme)))

J'appelle ivan/load-indexed-thememon fichier init pour initialiser mon thème.

Je lie ivan/cycle-themeà Space\en mode mal. ( Spaceest ma clé de leader.)

ivan
la source
2

Même si les réponses existantes fonctionnent bien, je voudrais partager une réponse plus simple:

(defun toggle-theme ()
  (interactive)
  (if (eq (car custom-enabled-themes) 'leuven)
      (disable-theme 'leuven)
    (enable-theme 'leuven)))
(global-set-key [f5] 'toggle-theme)

Cela ne désactive pas d'abord le thème personnalisé par défaut, mais j'aime ça.

Michel de Ruiter
la source
1

Ceci est le module que j'ai écrit pour mon propre .emacs pour résoudre ce problème. Mon approche de base semble être similaire dans son intention à la solution de Maxim Kim (rotation à travers une liste de thèmes), mais je pense que la mienne est plus modulaire et peut donc être plus accessible à un étranger. D'un autre côté, je n'ai aucune des fonctionnalités de persistance de Kim.

Voici le code pertinent, en laissant de côté les déclarations de variables et les commentaires de package:

(require 'dash)

(defun multitheme--enable (theme)
  "As `enable-theme', but load the theme if necessary.
Respect `custom-safe-themes'."
  (if (custom-theme-p theme)
      (enable-theme theme)
    (load-theme theme)))

(defun multitheme-cycle ()
  "Cycle between the themes in `multitheme-base-theme-list'.
If none of these themes is currently active, instead enable the
first element of `multitheme-base-theme-list'.

Also re-enable `multitheme-overtheme' so it remains \"on top\" of
the base theme.

If a theme to be enabled is not yet defined, attempt to load it
first (using `load-theme').  Respect `custom-safe-themes'.

After all theme changes have been made, run
`multitheme-base-change-hook'."
  (interactive)
  (when (require 'validate nil :noerror)
    (validate-variable 'multitheme-base-theme-list)
    (validate-variable 'multitheme-overtheme)
    (validate-variable 'multitheme-base-theme-change-hook))
  (let ((themes (-drop-while
                 (lambda (thm) (not (custom-theme-enabled-p thm)))
                 multitheme-base-theme-list)))
    ;; Cycle base theme
    (if (null themes)
        (multitheme--enable (car multitheme-base-theme-list))
      (disable-theme (car themes))
      (multitheme--enable (or (cadr themes)
                              (car multitheme-base-theme-list))))
    ;; Reassert overtheme
    (when multitheme-overtheme
      (multitheme--enable multitheme-overtheme))
    ;; Run hooks
    (run-hooks 'multitheme-base-theme-change-hook)))
Aaron Harris
la source
0

J'ai cette configuration pour les thèmes du cyclisme:

(defvar quick-switch-themes
  (let ((themes-list (list 'jazz
                           ;; 'vicarie-and-blackboard
                           ;; 'tangotango
                           'poet)))
    (nconc themes-list themes-list))
  "A circular list of themes to keep switching between.
Make sure that the currently enabled theme is at the head of this
list always.

A nil value implies no custom theme should be enabled.")

(defun quick-switch-themes* ()
  "Switch between to commonly used faces in Emacs.
One for writing code and the other for reading articles."
  (interactive)
  (if-let* ((next-theme (cadr quick-switch-themes)))
      (progn (when-let* ((current-theme (car quick-switch-themes)))
               (disable-theme (car quick-switch-themes)))
             (load-theme next-theme t)
             (message "Loaded theme: %s" next-theme))
    ;; Always have the dark mode-line theme
    (mapc #'disable-theme (delq 'smart-mode-line-dark custom-enabled-themes)))
  (setq quick-switch-themes (cdr quick-switch-themes)))
narendraj9
la source
0

Je sais que je suis un peu en retard à la fête, mais j'ai créé un package pour faire exactement cela, et bien plus encore.

Il vous permet essentiellement de définir une liste de vos thèmes de couleurs préférés (qui est facultative) et de parcourir la liste de manière pratique.

myTerminal
la source