关于 create-marp-deck
create-marp-deck 是用于创建 Marp Markdown 演示文稿的 Agent 技能,面向需要按访谈流程整理内容并生成幻灯片的人。它规定了幻灯片结构与样式,并提供 HTML、PPTX 和移动端网页导出步骤。
主要功能
- 01逐项访谈收集演示需求
- 02按规定结构生成 Marp 幻灯片
- 03应用版式、配色与格式规范
- 04导出 HTML 和 PPTX
- 05为网页分享生成移动端视图
适用场景
- 01根据目标和受众创建演示文稿
- 02将资料整理成有结构的幻灯片
- 03为网页分享准备移动端版演示
- 04按需生成可编辑 PPTX
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ omerr/ claude-skills --skill create-marp-deck安装后在 Claude Code 中输入/create-marp-deck确认已加载。
附带文件scripts/marp-mobile.py
详细介绍
创建 Marp 幻灯片
使用 Marp Markdown 格式创建演示文稿,并遵循以下既定规范。
阶段 1:访谈
开始生成任何内容之前,先按顺序逐个向用户提问,每次只问一个问题,并等待用户回答后再继续。
问题 1 — 目标与主题: 询问:“这场演示的主题是什么?你希望听众听完后了解什么,或能够做什么?”
问题 2 — 受众: 询问:“受众是谁?(例如:工程团队、高管、外部客户、会议参会者)”
问题 3 — 要点: 询问:“你想涵盖哪些要点或部分?请列出主要想法,粗略列出也可以。”
- 如果用户提供了文件、URL 或参考资料,请在继续之前仔细阅读或获取这些内容。
问题 4 — 数据与演示: 询问:“有没有要纳入的特定数据、代码示例、图表或演示?你已经准备好这些内容了吗,还是需要我来创建?”
问题 5 — 限制条件: 询问:“有什么限制条件吗?例如:目标幻灯片数量、演讲时长、需要避免的内容或特定品牌要求。”
收集完所有回答后,简要总结你的理解,并在继续之前请用户确认。
阶段 2:生成幻灯片
严格遵循以下结构和规范。
FRONTMATTER
每份幻灯片都必须以以下 frontmatter 开头:
---
marp: true
theme: default
paginate: true
size: 16:9
---
CSS 样式块
紧接 frontmatter 后,加入一个 <style> 块,其中包含:
- 基础字号,适用于 section、table、blockquote、pre
- 标题样式,用于面包屑导航(灰色文字,当前部分为蓝色)
- 部分样式类,用于标题页和每个部分/章节分隔页 - 这些页面使用渐变背景和白色文字
部分分隔页的配色方案(根据部分数量选择 2-4 种):
- 蓝色:
linear-gradient(135deg, #1e3a5f 0%, #2d5a8e 100%) - 绿色:
linear-gradient(135deg, #064e3b 0%, #047857 100%) - 琥珀色:
linear-gradient(135deg, #7a4a1a 0%, #a66b2e 100%) - 紫色:
linear-gradient(135deg, #3d1e5c 0%, #5a2d8e 100%) - 标题页(始终使用深海军蓝):
linear-gradient(135deg, #0f172a 0%, #1e293b 50%, #0f172a 100%)
模板:
<style>
section {
font-size: 22px;
}
table {
font-size: 18px;
}
blockquote {
font-size: 22px;
}
pre {
font-size: 16px;
}
header {
font-size: 14px;
color: #999;
}
header strong {
color: #2563eb;
}
section.title-slide {
background: linear-gradient(135deg, #0f172a 0%, #1e293b 50%, #0f172a 100%);
}
section.part-FIRST,
section.part-SECOND,
section.part-THIRD,
section.title-slide {
--h1-color: #fff;
--heading-strong-color: #fff;
--fgColor-default: rgba(255, 255, 255, 0.95);
--fgColor-muted: rgba(255, 255, 255, 0.7);
color: white;
}
section.part-FIRST {
background: linear-gradient(135deg, #1e3a5f 0%, #2d5a8e 100%);
}
section.part-SECOND {
background: linear-gradient(135deg, #064e3b 0%, #047857 100%);
}
section.part-THIRD {
background: linear-gradient(135deg, #3d1e5c 0%, #5a2d8e 100%);
}
</style>
将 FIRST、SECOND、THIRD 替换为简短且具有描述性的部分名称(例如:part-context、part-results、part-summary)。
幻灯片结构
幻灯片必须严格按照以下顺序排列:
1. 标题页
# Main Title
## Subtitle
**Key detail 1**: value
**Key detail 2**: value
**Date**: Month Year
2. 问题 / 目标页
列出 3-5 个本演示将解答的问题,使用带粗体引导语的编号列表。
3. 议程页
# Agenda
### Part 1: Name
Short description
### Part 2: Name
Short description
### Part 3: Name
Short description
4. 每个部分:分隔页 + 内容页
部分分隔页(全幅彩色背景):
# Part N: Section title
**One-line description**
内容页(带面包屑标题):
# Slide title
Content here
面包屑用于显示当前所在位置。当前部分需用 **粗体** 标记。标题指令会持续生效,直到更改为止,因此每个部分只需在分隔页后的第一张内容页设置一次。每个部分分隔页之前,使用 `` 重置。
5. 结尾幻灯片
以总结/要点回顾幻灯片作为结尾,并将其保留在最后一个部分中。
格式规则
- 所有标题使用句首字母大写格式——只大写首字母和专有名词(例如:“5 分钟内快速上手”,而不是“5 分钟内快速上手”)。面包屑标题也遵循相同规则
- 项目符号、文本行或表格单元格末尾不得加句号
- 用单个短横线(
-)分隔插入语,不要使用双短横线(--) - 程序名称、文件名和技术标识符使用反引号(不要加粗)
- 使用粗体强调关键短语和发现
- 使用表格进行数据比较 - 保持简洁
- 使用引用块(
>)突出关键信息或区别 - 每张幻灯片只表达一个想法——如果内容过于密集,就拆分成两张
- 每张幻灯片的项目符号列表最多包含 3-5 项
- 除非绝对必要,否则幻灯片正文中不要使用括号补充说明
导出
编写完幻灯片后,导出为 HTML 和 PPTX:
npx @marp-team/marp-cli@latest --no-stdin FILENAME.md -o FILENAME.html
npx @marp-team/marp-cli@latest --no-stdin --pptx FILENAME.md -o FILENAME.pptx
始终使用 --no-stdin,以防止 marp 在 stdin 上挂起。
移动设备友好的网页导出
只要幻灯片是通过链接分享(Netlify、GitHub Pages、Slack),而不是现场演示,就必须执行此操作。
每次 Marp HTML 导出都会将每张幻灯片渲染为固定的 1280×720 舞台。在手机上,整个舞台会缩小到约 30%,因此 22px 的正文文本会变成约 7px。对幻灯片舞台应用 CSS 无法解决这个问题——文字太小是因为幻灯片本身太小。缩小舞台或启用滚动吸附,只会得到一个无法阅读、需要滚动的幻灯片。
解决方法是提供两种不同的内容:
| 文件 | 内容 | 面向对象 |
|---|---|---|
index.html | 普通幻灯片——支持方向键、滑动和全屏。保持不变 | 桌面设备和平板电脑 |
mobile.html | 将幻灯片的内容重新排版为响应式文档——手机尺寸的真实文本,每张幻灯片对应一张卡片 | 手机(自动重定向) |
mobile.html 不是缩小后的幻灯片。scripts/marp-mobile.py(随此技能打包)会重新解析幻灯片 Markdown,并生成普通 HTML 文档:17px 的正文文本会自动换行以适应屏幕;每张幻灯片对应一张卡片;章节分隔页和标题页会保留渐变色,渐变色从幻灯片自身的 <style> 块中读取(因此适用于任何采用这些约定的幻灯片);面包屑标题会作为导航行显示;还包括幻灯片编号、各自带有水平滚动容器的表格,以及深色模式变体。
# 1. Desktop slideshow (unchanged)
npx @marp-team/marp-cli@latest --no-stdin --html FILENAME.md -o SITE_DIR/index.html
# 2. Reflowed mobile document
python3 scripts/marp-mobile.py FILENAME.md -o SITE_DIR/mobile.html --slideshow-href "./"
# 3. Send phones to the mobile view — inject right after <head>, before anything renders
python3 - <<'EOF'
import io
p = 'SITE_DIR/index.html'
html = io.open(p, encoding='utf-8').read()
redirect = "<script>if(matchMedia('(pointer:coarse)').matches&&Math.min(screen.width,screen.height)<700)location.replace('mobile.html')</script>"
assert '<head>' in html
io.open(p, 'w', encoding='utf-8').write(html.replace('<head>', '<head>' + redirect, 1))
EOF
需要安装 markdown-it-py(pip install markdown-it-py)。
注意:
- 重定向必须使用 JS,不能使用 meta refresh——重定向需要检测指针和屏幕。最小维度
< 700px的检查可确保平板电脑仍显示真正的幻灯片。location.replace可确保后退按钮正常工作。 mobile.html只会在支持悬停的设备上显示返回index.html的“幻灯片 ↗”链接,因此通过该页面打开的桌面用户不会被困住。- Netlify 的美化 URL 后处理会重写
href属性,但不会重写 JS 字符串,因此'mobile.html'重定向目标在部署后仍然有效。 - 脚本重新排版的是Markdown,而不是 Marp 渲染后的内容。渲染器级功能(
![bg]背景图片、多列 CSS、定位图片展示效果)不会保留。对于组件较多的幻灯片,可接受纯文本移动视图,或改为分享 PDF。 - 部署前,请直接为
mobile.html截图进行验证——无头 Chrome 会报告指针精度较高,因此index.html不会重定向:chrome-headless-shell --headless --screenshot=/tmp/m.png --window-size=390,900 file://…/mobile.html
可编辑的 PPTX 导出(可选)
如果用户需要可编辑的 PPTX(可在 PowerPoint 或 Google Slides 中编辑的文本),请执行以下额外步骤。此操作需要安装 LibreOffice 和 python-pptx。
# PPTX - editable text (experimental, requires LibreOffice)
npx @marp-team/marp-cli@latest --no-stdin --pptx --pptx-editable --allow-local-files FILENAME.md -o FILENAME-editable.pptx
python3 -c "
from pptx import Presentation
from pptx.util import Emu
prs = Presentation('FILENAME-editable.pptx')
margin = Emu(747720)
for slide in prs.slides:
for shape in slide.shapes:
if shape.has_text_frame and shape.shape_type == 17:
tf = shape.text_frame
if not tf.text.strip() or tf.text.strip().isdigit():
continue
font_size = None
if tf.paragraphs and tf.paragraphs[0].runs:
font_size = tf.paragraphs[0].runs[0].font.size
if not font_size:
continue
new_width = prs.slide_width - margin - shape.left
if new_width > shape.width:
shape.width = new_width
min_height = int(font_size * 1.4) * 2
if shape.height < min_height:
shape.height = min_height
tf.word_wrap = True
prs.save('FILENAME-editable.pptx')
"
注意:
- 本地图片需要使用
--allow-local-files --pptx-editable需要安装 LibreOffice- python-pptx 后处理可修复 LibreOffice 转换产生的文本框尺寸问题
- 始终使用
--no-stdin,以防止 marp 在 stdin 上挂起