Установить фон экспортированных из org блоков <code> в соответствии с темой

24

Я экспортирую файлы в режиме org довольно часто, и почти во всех них есть код. Когда я делаю экспортный код, он заканчивает окраску текста в зависимости от моей темы, однако я регулярно переключаюсь между темной и светлой темами. В случае светлой темы у <code>блоков должен быть светлый фон, а для темной темы у них должен быть темный фон (в противном случае я получаю светло-желтый текст на сероватом фоне, и он не читается).

Я должен добавить эту строку для темных фонов:

#+HTML_HEAD: <style>pre.src {background-color: #303030; color: #e5e5e5;}</style>

И затем не забудьте удалить его каждый раз, когда я переключаюсь на светлый фон

Есть ли способ, которым я могу автоматически определить цвет фона текущей темы во время экспорта и использовать его в CSS экспортированного HTML?

РЕДАКТИРОВАТЬ

Я иду с ответом Джордона (спасибо Джордон, вы получаете очки кармы!), Однако я хотел опубликовать решение, которое в итоге добавил к своему коду, поскольку это была слегка измененная версия его ответа:

(defun my/org-inline-css-hook (exporter)
  "Insert custom inline css to automatically set the
background of code to whatever theme I'm using's background"
  (when (eq exporter 'html)
    (let* ((my-pre-bg (face-background 'default))
           (my-pre-fg (face-foreground 'default)))
      (setq
       org-html-head-extra
       (concat
        org-html-head-extra
        (format "<style type=\"text/css\">\n pre.src {background-color: %s; color: %s;}</style>\n"
                my-pre-bg my-pre-fg))))))

(add-hook 'org-export-before-processing-hook 'my/org-inline-css-hook)

Это устанавливает не только цвет фона, но и цвет переднего плана. Он также добавляет строку к существующей org-html-head-extraнастройке, чтобы другой HTML не был перезаписан случайно. Я проверил, и это прекрасно работает для меня!

Ли Х
источник
1
Я уверен, что есть способ, но не лучше ли вместо этого всегда использовать одну и ту же тему при экспорте? Или вы намеренно экспортируете с разными темами?
Малабарба
@ Malabarba намерение состоит в том, чтобы иметь возможность экспортировать, какую тему я сейчас использую, и чтобы код был читабельным. Поскольку многие темы не переключаются чисто (даже с disable-theme), я не хочу перезапускать Emacs с отдельной темой только для экспорта HTML, что я делаю много раз в день.
Ли Х
1
Если я правильно понимаю, ваша текущая настройка уже использует цвета темы в блоках кода, и проблема в том, что фон темы не используется. Если я ошибся, пожалуйста, не стесняйтесь откатить изменения, внесенные в ваше название.
Малабарба
@Malabarba моя текущая настройка не определяет цвет фона блоков кода (хотя я могу жестко кодировать цвет фона в CSS, если это поможет). Я хотел бы, чтобы цвет фона темы использовался для блоков кода режима орг. Новое название работает для меня.
Ли Х
Есть две проблемы с вышеупомянутым решением. Во-первых, цвета, такие как 'grey80', не будут правильно переведены в значения CSS и не будут установлены. Во-вторых, каждый раз, когда выполняется экспорт, к нему org-html-head-extraдобавляются элементы, что приводит к неограниченному росту, хотя функциональность стиля не пострадает.
RP Диллон

Ответы:

10

Во-первых, я считаю, что org может использовать htmlizeдля автоматического окрашивания блоков исходного кода в соответствии с вашей темой.

В качестве альтернативы.

Проверьте http://definiteaplug.b0.cx/post/custom-inlined-css-in-org-mode-html-export/ . У этого есть отличный пример того, как использовать, org-export-before-processing-hookчтобы бросить пользовательский css в документ org перед экспортом html.

Вот код на случай, если сайт отключится:

Здесь, в html-экспорте, org будет искать файл с именем styles.css в текущем каталоге или файл по умолчанию в каталоге .emacs.d и вставлять этот css в документ. Это хорошо, но не идеально подходит для вашего случая использования.

(defun my-org-inline-css-hook (exporter)
  "Insert custom inline css"
  (when (eq exporter 'html)
    (let* ((dir (ignore-errors (file-name-directory (buffer-file-name))))
           (path (concat dir "style.css"))
           (homestyle (or (null dir) (null (file-exists-p path))))
           (final (if homestyle "~/.emacs.d/org-style.css" path)))
      (setq org-html-head-include-default-style nil)
      (setq org-html-head (concat
                           "<style type=\"text/css\">\n"
                           "<!--/*--><![CDATA[/*><!--*/\n"
                           (with-temp-buffer
                             (insert-file-contents final)
                             (buffer-string))
                           "/*]]>*/-->\n"
                           "</style>\n")))))

(add-hook 'org-export-before-processing-hook 'my-org-inline-css-hook)

Вы можете настроить это несколькими способами, чтобы заставить его работать так, как вы хотите.

Один из способов - вручную создать CSS на основе вашей темы и вставить его.

Вот измененная версия, которая устанавливает фон pre.srcв шестнадцатеричное значение граней по умолчанию: свойство background.

(defun my-org-inline-css-hook (exporter)
  "Insert custom inline css"
  (when (eq exporter 'html)
    (let ((my-pre-bg (face-background 'default)))
      (setq org-html-head-include-default-style nil)
      (setq org-html-head
            (format "<style type=\"text/css\">\n pre.src { background-color: %s;}</style>\n" my-pre-bg)))))

(add-hook 'org-export-before-processing-hook 'my-org-inline-css-hook)
Джордон Биондо
источник
1
Спасибо Джордон, это здорово! Я обновил свой первоначальный вопрос моей слегка отредактированной версией, но вы получаете награду и решение!
Ли Х