From babel-fish
Turn a set of screenshots or images into a LinkedIn document-post PDF (carousel) with per-page background matching so padding disappears into the source. Triggers: linkedin carousel, carousel pdf, document post, slide pdf, screenshots to pdf, linkedin pdf, carousel from images.
npx claudepluginhub ondrej-svec/heart-of-gold-toolkit --plugin babel-fishThis skill is limited to using the following tools:
Translating a stack of screenshots into a feed-ready document post. The trick isn't the PDF — it's making the padding invisible.
Mandates invoking relevant skills via tools before any response in coding sessions. Covers access, priorities, and adaptations for Claude Code, Copilot CLI, Gemini CLI.
Share bugs, ideas, or general feedback.
Translating a stack of screenshots into a feed-ready document post. The trick isn't the PDF — it's making the padding invisible.
magick, write PNGs and PDFs to the requested output path.magick on PATH). Check with which magick.Entry: User asked for a LinkedIn carousel.
Gather, asking only what's missing:
harness-lab-carousel). If the user gives a topic, derive it; otherwise ask.thoughts/social-media/carousels/<slug>.pdf if the repo has that dir; otherwise ask.Exit: Source list, output path, and aspect intent are known.
Entry: Inputs gathered.
Reason step-by-step before generating:
magick identify on each source to get width × height.1080×1350 (×2 = 2160×2700).1080×1080 (×2 = 2160×2160).read W H < <(magick identify -format "%w %h" "$src")
magick "$src" -format \
"tl=%[pixel:p{5,5}] tr=%[pixel:p{$((W-5)),5}] bl=%[pixel:p{5,$((H-5))}]\n" \
info:
If all three corners agree, use that color. If they disagree, the source has no clean border — fall back to #F4EFE3 (or another neutral the user prefers) and tell them.Exit: Canvas dimensions chosen, per-page background colors sampled.
Entry: Plan complete.
Write the build script to a temp file (avoids shell quoting traps), then run it:
#!/bin/bash
set -e
OUT=/path/to/output/dir
SLUG=harness-lab-carousel # from Phase 0
CANVAS=2160x2700 # from Phase 1
declare -a SRCS=(/path/1.png /path/2.png /path/3.png)
declare -a BGS=('#EFF1F5' '#EFF1F5' '#F2ECEB') # from Phase 1 sampling
mkdir -p "$OUT"
PAGES=()
for i in "${!SRCS[@]}"; do
# Zero-pad page number so glob ordering survives 10+ pages.
n=$(printf "%02d" $((i+1)))
page="$OUT/page${n}.png"
magick "${SRCS[$i]}" \
-filter Lanczos \
-resize "$CANVAS" \
-background "${BGS[$i]}" \
-gravity center \
-extent "$CANVAS" \
-quality 95 \
"$page"
PAGES+=("$page")
done
# Pass pages explicitly in array order — never rely on shell glob ordering.
magick "${PAGES[@]}" -density 300 -quality 95 "$OUT/${SLUG}.pdf"
Notes:
-resize WxH (without > or !) fits inside the box preserving aspect; -extent then pads to exact canvas using -background.magick call from the PAGES array, not via glob — page*.png would put page10.png before page2.png lexicographically and reorder the carousel.page*.png files — useful for spot fixes without rebuilding everything.Exit: PDF and page PNGs exist at the output path.
Entry: PDF built.
Open the PDF for the user (open <path> on macOS). Report:
Ask whether any page needs a different aspect or a tighter crop. Common follow-ups:
{20,20}).The user receives:
<output-dir>/<slug>.pdf — the carousel, ready to upload via LinkedIn's "Add a document".<output-dir>/page1.png, page2.png, … — per-page renders for inspection.