[Emacs] Org-Beamer 导出 slidshow (PDF)
Table of Contents
简介
在之前公司转正答辩做 PPT 的时候就已经萌生了这种想法了:通过写代码来做 PPT 。这种想法起源很简单, Latex 就是一个典型的例子嘛,丢弃鼠标,完全通过代码控制排版。当时想的是这种东西应该有很多成熟的项目,而后来没怎么做 PPT 也就忘了。直到前段时间刷到一个视频,它介绍了如何通过 Markdown 来做 PPT, 于是死灰复燃,开始折腾起来。跟 Org Mode 相关的项目也有,我试了几个:
- org-beamer: Org Mode buildin 的,通过 latex 的 beamer 来导出 pdf
- ox-reveal: 基于 reveal.js ,用于制作网页的幻灯片
- ox-spectacle: 这个是大佬刚开始做的,基于 spectacle.js, 也是用于制作 HTML 的演示
reveal.js vs spectacle.js
reveal.js 把每个 frame 放到 section 下,具体可以去看官网。 spectacle.js 就类似传统的幻灯片。
这两个 HTML 的演示都非常好看,动画丝滑流畅,且可以做到 all-in-one, 就是把所有 js, css 压缩到一个 HTML, 方便携带。
我只是想做一些简单的幻灯片,想着不整这么复杂,这些主题啊什么的要用 js/css 去调,我不太会,最终转向 org-beamer.
安装
org-beamer 是 Org Mode 自带的,因此只需要安装 Beamer 相关的环境就行了。
我使用的是 Tex Live ,安装 Arch Linux 官网上,把能安装的都安装了:
sudo pacman -S texlive-most texlive-lang texlive-fontsextra
Emacs 配置
Emacs 这边不需要太多配置,主要是解决中文相关的问题 [1] :
(with-eval-after 'ox-latex
;; 使用xelatex一步生成PDF
(setq org-latex-pdf-process
'("xelatex -interaction nonstopmode -output-directory %o %f"
"xelatex -interaction nonstopmode -output-directory %o %f"
"xelatex -interaction nonstopmode -output-directory %o %f"))
;; 设置默认后端为 `xelatex'
(setq org-latex-compiler "xelatex")
;; 在 Latex 文档导言区添加 \userpackage{xeCJK}
(add-to-list 'org-latex-packages-alist '("" "xeCJK"))
;; 幻灯片标题
(setq org-beamer-frame-level 2)
)
org-beamer 使用
官方文档:《The Org Manual》
编辑增强
在 .org
里面加上头: #+startup: beamer
, 可以提供额外的编辑帮助,比如补全标签、补全属性等。
org-beamer-frame-level
首先要关注的是一个变量: org-beamer-frame-level
, 在配置那里给它设成了 2 ,它的含义是:
- 所有等级小于它的标题,会被视为 Section
- 所有等级等于它的标题,会被视为 Frame
- 所有等级大于它的标题,会被视为 Block
来看一段框架:
* 第一章
** (第一张幻灯片)
第一张幻灯片的内容
** (第二张幻灯片)
第二张幻灯片的内容
* 第二章
** 块的展示
这里展示两个块元素
*** 第一块
这里是第一块
*** 第二块
这里是第二块
使用 C-c C-e l P
来在同一目录生成同名的 PDF 文件。输出如下:
对于不同的文件,可以通过 options 来设置:
#+options: H:1
富文本
强调, 倾斜 等富文本正常使用。
Block 块
根据前面的配置, 3 级标题及以上会被视作块,也就是每张 Frame 里面的小框框。
类型
在 Beamer 中有三种不同类型的 Block: 普通、警告和示例。通过设置标题的属性 BEAMER_ENV
来实现,三者分别对应的是 block
, alertblock
, example
.
** 块类型
*** 普通块
:PROPERTIES:
:BEAMER_ENV: block
:END:
这里是普通块。
*** 警告块
:PROPERTIES:
:BEAMER_ENV: alertblock
:END:
这里是警告块。
*** 示例块
:PROPERTIES:
:BEAMER_ENV: example
:END:
这里是示例块。
没有设置 BEAMER_ENV
的块默认为普通快(block)
此外,还有一种类型 ignoreheading
, 即忽视标题,这个块会像一个段落一样,不会有框框作用在上边。但如果想要标题背景,不想要文字,标题留空不行,要用到 @@beamer: ~~@@
, 见后面的例子 [2] 。
宽度
通过标题属性 BEAMER_COL
来设置列宽。它是一个 [0,1] 区间上的一个小数,表示当前块宽度占整个 Frame 宽度的比例。如果相邻两个快的宽度之和小于 1 ,就可以实现两个并排的块。
如果同一 Frame 下的连续块太多,宽度和超过 1 org-beamer 不会自动换行,然后所有块都挤到一行。目前我找到的办法是在该分行的地方创建一个空块:
***
:PROPERTIES:
:BEAMER_ENV: ignoreheading
:END:
因为空文本,所以它不会占据空间。
单行 columns
有一个 BEAMER_ENV
的值 columns
, 它用于把它下面的标题变成块,使得它们都限定在当前行内。因此它可以做到无视块之间的间距,尽管它们可能会重合 [2] 。
** Frame
*** 第一行
:PROPERTIES:
:BEAMER_env: columns
:END:
**** 左边
:PROPERTIES:
:BEAMER_env: block
:BEAMER_col: 0.5
:END:
**** 右边
:PROPERTIES:
:BEAMER_env: block
:BEAMER_col: 0.50
:END:
*** 第二行
:PROPERTIES:
:BEAMER_env: columns
:END:
**** @@beamer: ~@@
:PROPERTIES:
:BEAMER_env: block
:BEAMER_col: 0.99
:END:
即使左边 0.99 也能排下
**** @@beamer: ~@@
:PROPERTIES:
:BEAMER_env: block
:BEAMER_col: 0.01
:END:
动画
“动画”是给伪概念, PDF 哪来的动画一说,只能说是简单的通过重叠重复的方式来实现块元素的出现和消失。
\pause
\pause 就像断点一样,在当前处放了之后,演示到这里时会“停下”,即后续内容先不展示,下一页开始出现。
在 Org Mode 中的使用是: #+BEAMER: \pause
块的动画
通过设置 BEAMER_ACT
属性来控制动画,其值用一对尖括号 <N>
包裹,其中 N
表示出现的位置。
单个数字,表示第几个位置出现。如 <1>
表示在一开始就出现, <2>
表示在第二个位置出现,即下一页。以此类推。这个数字并不会真正改变当前的“页数” -–— 见下图,右下角,还是在同一 Frame 下 -–— 所以我更愿意称它做“位置”。
** 动画
*** A
:PROPERTIES:
:BEAMER_ENV: block
:BEAMER_ACT: <1>
:END:
*** B
:PROPERTIES:
:BEAMER_ENV: block
:BEAMER_ACT: <2>
:END:
*** C
:PROPERTIES:
:BEAMER_ACT: <3>
:BEAMER_ENV: block
:END:
输出会得到三张幻灯片:
横杠 (-) 表示连续范围,如: <1-2>
表示出现在 1 和 2 位置。如果横杠后的数字没制定如 <2->
,就表示出现到当前 Frame 结束.
** 动画
*** A
:PROPERTIES:
:BEAMER_ENV: block
:BEAMER_ACT: <1->
:END:
一直出现
*** B
:PROPERTIES:
:BEAMER_ENV: block
:BEAMER_ACT: <2>
:END:
位置 2 出现,其他位置不出现
*** C
:PROPERTIES:
:BEAMER_ACT: <2-3>
:BEAMER_ENV: block
:END:
地址 2 到地址 3 出现,其他位置不出现
*** D
:PROPERTIES:
:BEAMER_ACT: <4>
:BEAMER_ENV: block
:END:
地址 4 才出现
逗号 (,) 表示“与”,可以用来指定离散开的页数,如 <1,3,6>
表示出现在位置 1, 3 和 6 。也可以和范围组合,如 1,4,7-10
表示出现在位置 1, 4, 7, 8, 9.
文本强调
给一段文本加上强调,在到达位置时会变色。先用 *
把文本包裹,然后在文本前加上命令: *@@beamer:<N>@@要强调的文本*
。
** 文本强调
这是一段文本,最后两个字是强调 *@@beamer:<2>@@文本* 。因为是 2 所以是下一页强调,如果是 1 就是当前页。
图片
直接通过 Org Mode 的链接插入即可,通过 #+attr_latex:
来设置属性,比如常用的宽度 :width .6\textwidth
, 或者是缩放 :scale 0.5
,标题 :caption Title
等等
重复页面
重复页面简单说就是复制之前的某个页面,比如讲到后面的内容,需要回顾前面的某些页面 [3] 。
** Again
:PROPERTIES:
:BEAMER_ENV: againframe
:BEAMER_ACT: 2-
:BEAMER_ref: id:a047ce4d-288b-4137-853a-d4e757d293c4
:END:
BEAMER_ENV
设为againframe
, 标题不用,因为重复了目标页面的标题BEAMER_ACT
表示显示范围,和动画的格式一致,只是不用加尖括号BEAMER_ref
要重复的页面,可以用*标题
来跳转,但为了防止某些重名标题,最好使用 ID. 目标页面通过M-x org-id-get-create
来添加一个随机 ID, 然后使用id:xxx
链接过去。
其他 Latex 命令
想使用额外的 Latex 命令,用 @@beamer:code@@
来执行。
目录
开启目录: #+options: toc: t
, 便会在封面首页之后插入一页目录页。
设置 #+TOC: headlines [currentsection]
, 则会在进入每一个章节的时候插入目录页,同时高亮即将要进入的章节。
#+options: toc: nil
, 关闭目录。
具体目录层次及其他更多相关设置参考文档:《The Org Manual》。
自定义样式
这里给一个博主的博文,有很大帮助:《Latex - 随笔分类 - 南宫二狗 - 博客园》,找到 Beamer 相关文章即可。
结构
Beamer 将样式分为 4 块:
- 主题,包含了方方面面的样式,一般以下三个会包含其中。通过
#+BEAMER_THEME:
来调用 - 颜色主题,就是规定了各个模块,如文字、 Frame 标题等的颜色。通过
#+BEAMER_COLOR_THEME:
来调用 - 字体主题,规定了各个模块使用的字体。通过
#+BEAMER_FONT_THEME:
来调用 - 内部主题,规定了比如 Block, 列表的样式,像是无须列表前是原点还是小方块。通过
#+BEAMER_INNER_THEME:
来调用 - 外部主题,规定了各组分之间如页眉页脚、侧边栏等的样式。通过
#+BEAMER_OUTER_THEME:
来调用
事实上,也可以通过一个文件就全部包含了,这样模块化的好处就是可以弄出各种各样的组合,满足不同场景,更加灵活。
这里给内置的样式 [4] ,没用完,我基于其中的主题自己写了一套。
- theme: Madrid, sidebar, Bergen …
- colortheme: dolphin, dove, seagull …
- fonttheme: default, professionalfonts, serif, structurebold, structureitalicserif, structuresmallcapsserif
- innertheme: default, circles, rectangles, rounded, inmargin
- outertheme: default, infolines, miniframes, smoothbars, sidebar, split, shadow, tree, smoothtree
想要自定义颜色,需要基于内置的主题做参考去配置,其路径在 tex/latex/beamer
, 在 Arch Linux 下绝对路径: /usr/share/texmf-dist/tex/latex/beamer
.
其命名方式是: beamer<type><name>.sty
, 其中 <type>
是主题类型, <name>
是主题名字。比如要写一个名字为 mylight
的颜色主题就是 beamercolorthememylight.sty
, 把它放到环境变量的路径下就能够识别了。
在主题( theme )中,通过 \usecolortheme{}
, \usefonttheme{}
, \useinnertheme
, \useoutertheme
来导入相关的样式。
我的主题在 fingerknight/presentation ,自己也是摸爬打滚、复制粘贴过来的,我没有总结出系统性的内容,但目前满足我的需求。更多资料可以看参考资料:
- 删除导航栏:header footer - How to remove footline on the title page of beamer slides - TeX - LaTeX Stack Exchange
- 背景图片透明度:graphics - Transparent image background in beamer - TeX - LaTeX Stack Exchange
- 文字的背景颜色,用于调控比如行内代码的背景:Changing background color of text in Latex - TeX - LaTeX Stack Exchange
- 超链接的颜色:beamer - How do I change hyperlinks' color only? - TeX - LaTeX Stack Exchange
- 列表的表头样式:lists - Change bullet style / formatting in Beamer - TeX - LaTeX Stack Exchange
- 定义一个尾页:How to define a "final slide" in a beamer template? - TeX - LaTeX Stack Exchange
- 高亮代码快:latex - Colour for R code chunk in listings package - Stack Overflow
- 高亮代码快:listings - Lstlisting in beamer presentation - TeX - LaTeX Stack Exchange