pydeck 文档画廊机制详解:images.rst 如何将示例缩略图与示例页面注册进 Sphinx 构建
【免费下载链接】deck.glWebGL2 powered visualization framework项目地址: https://gitcode.com/GitHub_Trending/de/deck.gl
images.rst 是 pydeck Sphinx 文档中一个完全由脚本自动生成的清单文件,承担两项职责:把examples/下全部 62 个示例的缩略图 PNG 注册进文档静态资源,并通过一个隐藏 toctree 确保对应的示例.rst页面都会被构建输出。本文基于该文件及其生成脚本,讲清 pydeck 文档画廊(Gallery)从示例代码到在线文档页的完整构建链路,以及新增示例时的标准操作流程。
images.rst 的两段式结构
整个文件由两部分组成,文件头部注释直接说明了其来源与用途:
.. Auto-generated by scripts/update_images_rst.py. Registers example thumbnails in the _static directory and the example pages in a hidden toctree.第一段:批量注册缩略图资源
前 62 条.. image::指令逐一列出全部示例缩略图,形式完全一致:
.. image:: gallery/images/a5_layer.png :width: 0从 IMAGES_RST_TEMPLATE 模板 看,这 62 条指令是循环渲染EXAMPLE_NAMES列表的结果:每条指令引用gallery/images/<示例名>.png,并统一设置:width: 0。将宽度置 0 的效果是从源码结构看,图片不会在页面正文中占据任何可见尺寸,而 Sphinx 在处理image指令时会把被引用的图片复制进构建输出目录供后续 HTML 页面引用——这正是头部注释所说“Registers example thumbnails in the _static directory”的实现手段。
清单覆盖的示例按主题可分为几大类(与 gallery/images 目录 下的 62 个 400x300 PNG 一一对应):
- 基础图层:
a5_layer、arc_layer、bitmap_layer、column_layer、contour_layer、custom_layer、geojson_layer、great_circle_layer、grid_layer、h3_cluster_layer、h3_hexagon_layer、heatmap_layer、hexagon_layer、icon_layer、line_layer、path_layer、point_cloud_layer、polygon_layer、s2_layer、scatterplot_layer、scenegraph_layer、screengrid_layer、terrain_layer、text_layer、trips_layer; - 扩展(extensions):
brushing_extension、clip_extension、collision_filter_extension、data_filter_extension、fill_style_extension、mask_extension、path_style_extension、terrain_extension; - 光照(lighting):
ambient_light、camera_light、directional_light、point_light、sun_light; - 后期处理(post_processing):
brightness_contrast、bulge_pinch、color_halftone、denoise、dot_screen、edge_work、fxaa、hexagonal_pixelate、hue_saturation、ink、magnify、noise、sepia、swirl、tilt_shift、triangle_blur、vibrance、vignette、zoom_blur; - 视图与集成:
binary_transport、geopandas_integration、globe_view、maplibre_globe、widgets。
第二段:隐藏 toctree 注册示例页面
文件后半段是一个隐藏的 Sphinx 目录树:
.. toctree:: :hidden: :maxdepth: 0 gallery/a5_layer gallery/arc_layer gallery/binary_transport ... gallery/widgets与图片清单同名、同序的 62 个gallery/<示例名>条目,指向每个示例对应的.rst页面。:hidden:使其不出现在侧边导航栏,:maxdepth: 0只注册顶层页面。其作用是从源码结构看,让 Sphinx 在构建文档时把这些示例页全部纳入构建图——即点击画廊网格中的某个缩略图后跳转到的页面(内嵌运行中的 deck.gl 可视化 + 完整 Python 源码)。没有这个 toctree,示例页就不会被构建,网格链接会 404。
生成源头:update_images_rst.py 与常量/模板
update_images_rst.py 是生成 images.rst 的入口,逻辑极简:
def main(): rendered = IMAGES_RST_TEMPLATE.render(assets=EXAMPLE_NAMES) with open(os.path.join(LOCAL_DOCS_PATH, "images.rst"), "w+") as f: f.write(rendered)它从 const.py 取EXAMPLE_NAMES,用 templates.py 中的IMAGES_RST_TEMPLATE渲染后覆盖写入docs/images.rst。因此该文件不应手工编辑——任何手工改动都会在下次重新生成时被冲掉。
示例清单如何被确定
const.py 是整条流水线的“单一事实来源”:
EXAMPLES_DIR = os.path.abspath(os.path.join(here, "..", "..", "examples")) EXAMPLE_GLOB = sorted(glob.glob(os.path.join(EXAMPLES_DIR, "**", "*.py"), recursive=True)) EXAMPLE_NAMES = [os.path.splitext(os.path.basename(p))[0] for p in EXAMPLE_GLOB]即:以 bindings/pydeck/examples 目录下所有.py文件(递归)的 snake_case 文件名作为示例标识,images.rst 的条目数完全由示例文件的实际数量决定。
同文件还定义了画廊分组规则,供网格页使用:
DEFAULT_GROUP = "Layers" GROUP_ORDER = ["Layers", "Extensions"] def group_label(example_path): parts = os.path.relpath(example_path, EXAMPLES_DIR).split(os.sep) if len(parts) > 1: return parts[0].replace("_", " ").title() return DEFAULT_GROUP也就是:直接放在examples/下的文件归入 “Layers” 分组;放在子目录(如examples/extensions/、examples/lighting/、examples/post_processing/)下的文件按目录名生成 “Extensions”“Lighting”“Post Processing” 分组。GROUP_ORDER固定前两组顺序,其余分组按字母序补在后面。grouped_examples()按此规则输出有序的 (分组名, 示例名列表)。
上游管线:缩略图、示例页与网格页
images.rst 只负责“注册”,真正产出被注册资产的是 docs/Makefile 中的三个目标:
html-embeds: python scripts/embed_examples.py html-thumbnails: uv run python scripts/snap_thumbnails.py html-grid-page: $(MAKE) html-embeds python scripts/generate_grid_html.pyscripts/README.md 对三者分工的描述是:
embed_examples.py生成一批同时内嵌源码与运行示例的.rst文件(对应 images.rst toctree 里的条目);generate_grid_html.py生成以缩略图链接成网格的 HTML 页,它是 pydeck 文档站的落地页;snap_thumbnails.py从示例运行结果截图生成.png缩略图(即 images.rst 第一段引用的gallery/images/*.png)。
截图环节 snap_thumbnails.py
snap_thumbnails.py 的关键参数与流程:
LARGE_EXAMPLES = ("bitmap_layer", "icon_layer", "heatmap_layer", "terrain_layer", "maplibre_globe") THUMBNAIL_SIZE = (400, 300)- 对每个示例,先
subprocess.run([sys.executable, fname])运行示例脚本,把产出的同名.html移入docs/gallery/html/; - 再用 Playwright 启动 Chromium,以
800x600视口打开该 HTML。数据量大的LARGE_EXAMPLES直接固定等待 10 秒,其余等待networkidle后再留 3 秒让 deck.gl 完成首帧渲染; wait_for_selector("canvas")确保画布出现后截图,snap_with_retries提供最多 3 次重试;- 最后用 Pillow 以
Image.LANCZOS重采样缩到400x300(与gallery/images/下全部 PNG 的实际尺寸一致),覆盖保存。
示例页环节 embed_examples.py
embed_examples.py 用 4 进程Pool并行处理每个示例:运行示例脚本、移动 HTML 产物,然后按DOC_TEMPLATE渲染出gallery/<示例名>.rst。模板(见 templates.py)包含三段raw html:指向deck.gl docs的外链(仅当示例名含 “layer” 时生成,链接到DECKGL_URL_BASE + <kebab-name>)、以:file:直接内联html/<示例名>.html实现页内交互、以及一段加宽内容区并约束#deck-container为 50vh 高度的样式;末尾附上完整的 Python 源码 code-block。
网格页环节 generate_grid_html.py
generate_grid_html.py 调用grouped_examples()渲染HTML_TEMPLATE,输出 gallery/html/grid.html:三列 CSS Grid,每个单元格是gallery/<示例名>.html链接 +./_images/<示例名>.png缩略图 + 展示名。to_presentation_name(utils.py)负责把 snake_case 转成展示标题,如arc_layer→ “Arc Layer”。
文档首页的接入点
docs/index.rst 将两条管线缝合在一起:
Gallery ^^^^^^^ .. raw:: html :file: gallery/html/grid.html .. include:: images.rst即首页先内联网格 HTML(展示层),再includeimages.rst(资源与页面注册层)。前者决定用户看到什么,后者决定构建产物里有什么。
新增一个示例到画廊的标准流程
scripts/README.md 给出了官方流程(“Adding a new layer to the gallery”):
- 安装截图依赖:
pip install pyppeteer && pip install Image(注意:README 仍写 pyppeteer,但当前 snap_thumbnails.py 的 docstring 已改用 Playwright:uv pip install playwright Pillow+playwright install chromium,以脚本头部说明为准); - 将新层加入
docs/images.rst(实际生效的做法是新增示例文件后重新运行生成脚本,使清单自动包含新条目); - 运行
make html-grid-page重建示例页与网格页; - 生成缩略图:单个示例
python scripts/snap_thumbnails.py ../examples/arc_layer.py,全部示例make html-thumbnails。
由于EXAMPLE_GLOB是递归 glob 的结果,把示例放进examples/<子目录>/即自动获得对应画廊分组,无需改动 images.rst 的分组逻辑;页面名、缩略图名、toctree 条目全部由文件名基名统一派生(to_snake_case_string只取 basename 去掉.py后缀)。
小结与适用前提
images.rst 本身没有可执行逻辑,它是 pydeck 文档构建链路的“注册表”:examples/*.py(const.py 扫描)→snap_thumbnails.py(PNG)+embed_examples.py(示例 rst/html)→update_images_rst.py(生成 images.rst)→generate_grid_html.py(grid.html)→index.rst(raw html + include 缝合)。理解这条链路后,任何画廊条目缺失、缩略图不更新或示例页 404 的问题,都可以沿“示例文件名 → 三处产物是否齐全”逐段定位。适用前提:需在bindings/pydeck/docs/目录下操作,依赖 uv、Playwright(Chromium)与 Pillow;文档仓库为只读,本文仅说明查看与构建方式。
【免费下载链接】deck.glWebGL2 powered visualization framework项目地址: https://gitcode.com/GitHub_Trending/de/deck.gl
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考