xaringan是基于remark.js开发的幻灯片写作工具。

  • 优势在于可能更方便的嵌入R语言代码和相应的输出。其实也是可以支持Python,SQL和Bash等语言的,如果你使用RStudio的话。

  • 劣势在于,相对传统的PPT或者Keynote来说,在样式的调整上稍微有点门槛。你需要懂点HTML,CSS和Javascript才能游刃有余。

使用xaringan之后,一些简单的样式调整都可以通过CSS来实现。突发奇想的一个需求是,有没有办法在每一页幻灯片加上一个Logo?

查看一个编译后的幻灯片源码,你会发现每张片子都包含在一个class为remark-slide-container的div元素。而所有的正文都在class为remark-slide-content的div元素里。

那如何自动在所有这些div生成时加入一个DOM元素?这里的元素可以是logo或者任意其他东西,遗憾的是目前似乎没办法。回过头看remark.js的文档,目前并不支持自定义幻灯片的模板(也可能是我没找到)。但我们知道Javascript最是擅长操作DOM元素的增删改,所以可以在编译后的幻灯片里做些手脚,插入一些有趣的东西。

回到xaringan来,它依然是使用rmarkdown这个包来编译的,编译时有includes参数可以在文档的header标签里或者body标签前后插入元素。

output:
  xaringan::moon_reader:
    seal: FALSE
    lib_dir: libs
    css: header.css
    includes:
      after_body: header.js

这里我们使用自定义的header.css文件,并在body标签最后插入一个header.js文件,内容如下:

<script src=jquery.min.js></script>
<script>
(function () {
  $('.remark-slide-content').prepend('<div class="nyc-header" />');
})();
</script>

其中先是引入Jquery模块,接着使用Jquery的能力在所有remark-slide-content标签头部插入一个class为nyc-header的元素。这个元素就用来承载我们的Logo,接下来就全都是CSS的事情了。

header.css文件中定义nyc-header的样式,包括背景色,背景图片和位置等:

.nyc-header{
  background-color: #00a3af;
  background-image: url(logo.png);
  background-position: center center;
  background-repeat: no-repeat;
  background-size: auto;
  width: 100%;
  height: 8%;
  position: absolute;
  left: 0px;
  top: 0px;
}

最后的效果如下图,每页都会有顶层的logo。