Threads Carousel logo

Threads Carousel

Community
itchernetski
threads-carousel

Convert text posts into visual carousel images or presentations for Threads, Instagram, LinkedIn, TikTok, YouTube. 12 slide types (incl. image/emoji/number), 6 format presets (incl. 1920×1080 wide), 8 background styles (incl. ruled paper), 3-axis style system (font × color × purpose), highlighted keywords with optional italic-box style. Generates PNG or single-file PDF via Next.js preview + browser export. RU/EN toolbar. Triggers: threads carousel, instagram carousel, linkedin carousel, tiktok carousel, карусель, slides, carousel images, presentation deck, presentation pdf.

Overview

Publisheritchernetski
Repositorythreads-carousel-claude-skill
Skill namethreads-carousel
Stars
119
Forks
14
Bundled files
15
LicenseMIT
Links
  • Markdown instructions

    A SKILL.md file the model loads on demand, so it only costs tokens when a request actually matches.

  • Works with any LLM

    AI skills are plain Markdown, not provider-specific code, so this works with GPT, Claude, Gemini, Grok, or a local model.

  • 15 bundled files

    Scripts, templates, and references the model can read while it works. Files are read-only and never executed.

  • Open source

    Published by itchernetski on GitHub. Read the source before you install it.

Installation

Install the Threads Carousel AI skill in TypingMind to use it with any LLM, or drop it into another agent that reads SKILL.md.

1

Install in TypingMind

TypingMind installs a skill straight from its GitHub folder — it reads SKILL.md, bundles the resource files, and stores the result locally.

  1. Open the app and go to Plugins → Skills.
  2. Choose "Install from GitHub".
  3. Paste the skill folder URL below and confirm.
    https://github.com/itchernetski/threads-carousel-claude-skill/tree/main
  4. Enable the skill in any chat where you want it available.
Plugins → Skills → Add skill → From GitHub URL, then paste the folder URL and press Continue.
2

Install in another agent

Any agent that reads the Agent Skills format can use this skill — copy the folder into that agent's skills directory.

Claude Code — .claude/skills
git clone --depth 1 https://github.com/itchernetski/threads-carousel-claude-skill.git \
  .claude/skills/threads-carousel
Restart Claude Code after copying so it picks up the new skill.

Use it in TypingMind

Enable Threads Carousel in any TypingMind chat and the model takes it from there. Its name and description sit in the system prompt, and the moment a request matches, the model loads the full instructions itself — you never invoke it by hand, and it costs no tokens until it is actually used.

The model loads Threads Carousel on its own as soon as a request matches it.

Works with any AI model

AI skills are plain Markdown instructions rather than provider-specific code, so Threads Carousel is not tied to the model it was written for. Install it once in TypingMind and use it with GPT-5, Claude, Gemini, Grok, DeepSeek, Mistral, Llama, or a local model you run yourself — all on your own API keys.

  • Loaded only when it is needed

    The system prompt carries just the name and description. The instructions are fetched on the first matching request, so an idle skill costs nothing.

  • Switch models mid-chat

    Because the skill is instructions rather than code, changing model does not break it — the next model reads the same SKILL.md.

Skill instructions

This is the SKILL.md content the model loads. Read it before installing — a skill is instructions your model will follow.

Threads Carousel Generator

Converts a text post into a set of visual carousel slides for Threads, Instagram, LinkedIn, TikTok, Stories, YouTube, or a standalone presentation deck. Composable design system with three independent style axes (font × color × purpose) and 12 slide types.

Invocation

/threads-carousel <post text>
/threads-carousel path/to/post.md

Format presets (choose target platform)

PresetSizePlatforms
threads-4x5 (default)1080×1350Threads, Instagram feed (portrait)
instagram-square1080×1080Instagram, Facebook, LinkedIn feed
linkedin-square1080×1080LinkedIn document post (PDF)
tiktok-9x161080×1920TikTok Photo Mode, Reels, Shorts
story-9x161080×1920Instagram Stories, Threads Stories
wide-16x91920×1080Presentations, YouTube, desktop decks

Slide types (12)

TypePurposeRequired fields
hookOpening slide — the catchiest linetext
bodyTitle + paragraphtitle, text
body (points)Pros/cons list with ✓/✗ SVG iconstitle, points[] (instead of text)
listNumbered items (ordered list)title, items[]
statsBig numbers with labelstitle, stats[]
quoteLarge pulled quotetext, author
checklistCheckmark bulletstitle, items[]
processNumbered steps with connector linetitle, steps[]
comparisonTwo-column VS / before-afterleftLabel, leftItems[], rightLabel, rightItems[]
ctaFinal call to actiontext, handle
imageTitle + screenshot/photo + optional captionimageSrc, optional title, imageCaption
emojiGiant emoji illustration + title + textemoji, optional title, text
numberHuge hero number/string + title + textbigNumber, optional title, text

points shape: Array<{ type: "plus" | "minus"; text: string }> — green ✓ for plus, muted ✗ for minus. Adaptive sizing (44–62px) based on item count and longest line.

All types also support optional:

  • badge — small outlined tag above title (e.g. "01", "TIP")
  • highlight — a word or phrase within text/title that will be colored in the preset's highlight color (yellow for dark themes)
  • highlightStyle: "italic-box" — renders the highlighted word in Playfair italic on a colored rectangle (instead of plain color)

Images in slides

image slides expect imageSrc as a path served by Next.js under /public/. Workflow when a user gives you a local file:

  1. User drops a file path like /Users/me/Desktop/screenshot.png (or passes a file via the chat).
  2. Copy it into template/public/images/ with a safe, lowercase filename — e.g. cp "$USER_PATH" template/public/images/screenshot.png.
  3. In slides.ts reference it as imageSrc: "/images/screenshot.png" (absolute from /public/).

Same-origin serving avoids CORS errors in the PNG export pipeline. Do not use external URLs — html-to-image will often blank them out.

Background decorations (8 types)

Switchable via toolbar in preview. Default: glow.

TypeWhat it is
noneSolid background
blobsOrganic colored shapes
gridDotted grid pattern
linesDiagonal line pattern
paperRuled notebook lines + left margin (use with paper/light/white colors for a literary feel)
noiseSVG grain overlay (overlay blend)
bignumberGiant slide index as watermark (01, 02…)
glow (default)Soft radial gradient in alternating corners

Style system (3 independent axes)

The final style is composed at runtime from three axes via composePreset(font, color, purpose):

Font axis (DEFAULT_FONT), 5 typefaces:

IdFontFeel
minimal (default)Unbounded (body + hook)Geometric display, bold, distinctive
editorialPlayfair DisplayClassic serif, literary
cleanInterNeutral sans-serif, most standard
monoJetBrains MonoMonospace, tech/dev feel
condensedOswaldNarrow + tall, editorial poster

Surface axis (DEFAULT_SURFACE) — bg + text neutrals, 8 options:

IdBgTextFeel
dark (default)#0A0A0Awhitedefault bold
whitepure #FFFFFFnear-blacksharp clinical, Apple-style
lightcool zinc #F4F4F5near-blackneutral cool grey, Vercel-style
papercream #ECE2C8warm brownnotebook / literary warm
gradientpurple→pink→amberwhitebright gradient
pastellilac #EDE9FEindigosoft
neondark gradientlight cyantech dark
emberblack→red radialnear-whitedramatic

Accent axis (DEFAULT_ACCENT) — pop color for highlighted words, 8 options:

IdHexMatches surfaces
yellow (default)#FACC15dark, ember
red#DC2626pure red — white, light, paper
teal#14B8A6versatile — dark, white, light, paper
coral#FB7185pink-family — paper, light, white
orange#F97316pumpkin — paper, light, dark
violet#A78BFAdark, neon, ember
lime#D9F056ember, dark
blue#3B82F6white, light, paper, dark
fuchsia#C026D3pastel, white, dark
pink#EC4899pastel, dark, light
amber#F59E0Bgradient, dark, paper

Total combinations: 8 surfaces × 8 accents × 5 fonts × 2 purposes = 640 valid styles. Pick surface for neutral base, accent for pop color — independently.

Reference combos (inspired by design refs):

  • dark + teal — noir / minimalist tech
  • paper + orange — literary warm
  • ember + lime — dramatic announcement
  • white + coral — sharp editorial
  • light + teal — calm informational

Purpose axis (DEFAULT_PURPOSE):

IdTitleBodyDivider
carousel (default)44px, weight 800, UPPERCASEweight 600, textColor, line-height 1.2visible (96×4px accent)
presentation72px, weight 700, sentence caseweight 400, textSecondary, line-height 1.45hidden

Pick purpose: "presentation" + format: "wide-16x9" for a desktop / YouTube presentation deck. Any 3 × 8 × 2 = 48 combinations are valid.


Workflow

Step 1 — Get the text

  • If passed inline — use it.
  • If a file path (.md, .txt) — read it.
  • If text is long (>500 chars) — confirm it's complete before planning.

Step 2 — Clarify parameters (optional, can assume defaults)

Ask once, combined:

  1. Number of slides (3–10, default 6)
  2. Format (see table above, default threads-4x5; use wide-16x9 for a presentation deck)
  3. Purpose (carousel or presentation, default carousel)
  4. Font (minimal / editorial / clean, default minimal)
  5. Color (8 palettes, default dark)
  6. Handle for CTA slide (e.g. @username)

Shortcut: if user says "presentation" / "презентация" / "slide deck" → default to purpose: presentation, format: wide-16x9, font: clean, color: white.

If user says "your call" — apply defaults, do not block.

Step 3 — Plan the slide breakdown

Show the user a preview list before generation:

Slide 1 (hook): "Headline..."  [highlight: "word"]
Slide 2 (body): badge 01 — "Title" / "Text..."
Slide 3 (list): badge 02 — "iOS stack" / 3 items
Slide 4 (stats): badge 03 — "Growth" / 3 stats
Slide 5 (quote): "Quote..." — Author
Slide 6 (cta): "Final message" @username

Rules for splitting text into slides

  1. Hook = single most intriguing line from the post. 1–3 short lines. Works as a standalone thumbnail.
  2. Body slides = one idea each. Max 40 words. Max 5 lines. Never join two ideas with "and".
  3. Mix slide types for visual variety: prefer list for enumerations, stats for numbers, quote for direct speech, comparison for VS/before-after. Don't make every slide a body.
  4. CTA = conclusion + follow handle. Centered, short.

Step 4 — Generate

Prepare working copy
bash
WORK_DIR="/tmp/carousel-$(date +%s)"
rsync -a --exclude=node_modules ~/.claude/skills/threads-carousel/template/ "$WORK_DIR/"
ln -s ~/.claude/skills/threads-carousel/template/node_modules "$WORK_DIR/node_modules"
cd "$WORK_DIR"

Symlinking node_modules avoids the 350MB copy per run.

Inject content into src/slides.ts

All content + defaults live in src/slides.ts — never touch the engine (src/app/CarouselApp.tsx, src/lib/*). Edit the SLIDES array and the 5 default constants.

Full injection example:

ts
import type { SlideData, BgType, FormatId, FontId, ColorThemeId, PurposeId } from "./lib/types";

export const SLIDES: SlideData[] = [
  { type: "hook", text: "Line one\nline two", highlight: "two" },
  { type: "body", badge: "01", title: "Title", text: "Body text...", highlight: "key" },
  { type: "body", badge: "02", title: "Pros & Cons", points: [
    { type: "plus",  text: "One click to register" },
    { type: "plus",  text: "Works on any background" },
    { type: "minus", text: "Requires provider setup" },
  ]},
  { type: "list", badge: "03", title: "Steps", items: ["First", "Second", "Third"] },
  { type: "stats", title: "Numbers", stats: [
    { value: "10×", label: "Faster" },
    { value: "50%", label: "Smaller" },
  ]},
  { type: "quote", text: "Big idea\nin few words", author: "Someone", role: "2026" },
  { type: "checklist", title: "Pre-flight", items: ["One", "Two", "Three"] },
  { type: "cta", text: "Last word", handle: "@username" },
];

export const DEFAULT_FONT: FontId = "minimal";
export const DEFAULT_COLOR: ColorThemeId = "dark";
export const DEFAULT_PURPOSE: PurposeId = "carousel";
export const DEFAULT_BG: BgType = "glow";
export const DEFAULT_FORMAT: FormatId = "threads-4x5";
Launch preview and export
bash
bun dev --port 3333

Tell the user to open http://localhost:3333. They can:

  • Switch Format / Mode / Font / Color / Background live via toolbar rows
  • Toggle UI language RU / EN in the top-right
  • Click PDF to download all slides in one file (JPEG-compressed, ~5–8 MB for 10 slides)
  • Click PNG (a.k.a. "Export All") to download every slide as 01-hook.png, 02-body.png, …
  • Click an individual slide thumbnail to export just that one as PNG

After export, stop the dev server.

Parallel carousels

If making multiple carousels at once: create multiple work dirs and launch on ports 3333, 3334, 3335 — they run side by side without conflict.


Design system

Canonical look (font: minimal, color: dark, purpose: carousel):

  • Display typeface: Unbounded (Google Fonts), for hooks — applied only when the font axis provides hookFontFamily
  • Body typeface: Space Grotesk (minimal) / Playfair (editorial) / Inter (clean) — everything else uses preset.fontFamily
  • Palette (dark): #0A0A0A bg, #FFFFFF text, #FACC15 highlight
  • Layout: 80px padding, left-aligned, slide counter bottom-center
  • Title discipline: carousel purpose — title → a 96×4px accent divider → body, with ≥64px breathing room above body. Presentation purpose — no divider, sentence case, 72px.
  • Hook size: 104–140px, adaptive by character/line count
  • Body text size: 48–88px, adaptive
  • Text balance: textWrap: "balance" on hook + title (no orphan words)

Typography table (carousel purpose)

The presentation purpose overrides titles to 72px / 700 / sentence case and body to 400 / textSecondary / line-height 1.45.

ElementSizeWeightFont source
Hook104–140px800hookFontFamily ?? fontFamily
Title44px800 uppercasefontFamily
Body48–88px600fontFamily
Points (pros/cons)44–62px600fontFamily
Badge26px800 uppercasefontFamily
Stats value140–170px900fontFamily
Stats label32px500 uppercasefontFamily
Quote62px600fontFamily
List item46px600fontFamily (numbers 48px)
Checklist item44px600fontFamily
Process step title36px700fontFamily
Handle36px500fontFamily

Common mistakes

MistakeFix
Too much text on a slideMax 40 words, max 5 lines
Two ideas on one slideSplit into two slides
All slides are body typeMix in list, stats, quote, checklist for visual variety
No hook on first slideSlide 1 must be the catchiest line
No CTA on last slideSlide N must end with a handle or call to action
Highlight word too longKeep highlight to 1–2 words, not whole phrase
Badge has too many charactersMax 2–4 characters (01, TIP, NEW)

Future work / TODOs

  • Satori server-side export — replace browser-based html-to-image with Satori + Resvg for CLI export (bun run export → out/*.png). Enables headless runs. See Slashgear/linkedin-carousel-gen for reference.
  • Per-slide background override — currently DEFAULT_BG is global; could accept a per-slide bg field to mix decorations across a deck.
  • Cyrillic-optimized adaptive sizing — current thresholds are calibrated for Latin; Russian copy tends to be 20–30% longer at the same font size.
  • Pencil MCP mode — previous skill version had a manual design mode via Pencil; not currently implemented in the template.

Bundled files

The model reads these on demand while the skill is loaded. They are exposed as readable files and are never executed.

Frequently asked questions

What does the Threads Carousel AI skill do?

Convert text posts into visual carousel images or presentations for Threads, Instagram, LinkedIn, TikTok, YouTube. 12 slide types (incl. image/emoji/number), 6 format presets (incl. 1920×1080 wide), 8 background styles (incl. ruled paper), 3-axis style system (font × color × purpose), highlighted keywords with optional italic-box style. Generates PNG or single-file PDF via Next.js preview + browser export. RU/EN toolbar. Triggers: threads carousel, instagram carousel, linkedin carousel, tiktok carousel, карусель, slides, carousel images, presentation deck, presentation pdf.

Why use Threads Carousel on TypingMind?

Because you install it once and use it with any model. Threads Carousel is plain Markdown rather than provider-specific code, so the same skill runs on GPT-5, Claude, Gemini, Grok, or a local model — and you can switch model mid-chat without it breaking. TypingMind runs on your own API keys, so you pay providers directly instead of a per-seat subscription, and your skills and chats stay in your own storage.

How do I install Threads Carousel in TypingMind?

Open Plugins → Skills → Install from GitHub in TypingMind and paste https://github.com/itchernetski/threads-carousel-claude-skill/tree/main. TypingMind reads its SKILL.md and bundles its files and installs it as a skill you can enable per chat.

Which AI models can use Threads Carousel?

Any model you connect in TypingMind. AI skills are plain Markdown instructions rather than provider-specific code, so GPT, Claude, Gemini, Grok, and local models can all load this skill when a request matches it.

How many AI models can I use with Threads Carousel?

As many as you like. As long as a model supports skills, you can use Threads Carousel with it — GPT, Claude, Gemini, Grok, DeepSeek, Mistral, Llama and more — all on TypingMind with your own API keys.

Is the Threads Carousel AI skill free?

Yes. It is published on GitHub by itchernetski under the MIT license. You only pay your own AI provider for the tokens you use.

What are AI skills?

An AI skill is a reusable instruction bundle that teaches an AI model how to do one specific task. It follows the open Agent Skills format: a SKILL.md file with a name and description, plus any scripts, templates or reference files the model may need. The model reads the instructions only when your request matches the skill, so an installed skill costs nothing until it is used.

How are AI skills different from plugins or MCP servers?

A plugin or MCP server gives a model new tools to call — code that runs somewhere and returns a result. An AI skill gives the model knowledge and process instead: how to approach a task, which steps to follow, what good output looks like. Skills are plain Markdown, so they need no server, no API key and no runtime, and they work with any model.

View all

Set up your own AI workspace now

Get notified about new features and future giveaways by subscribing to our newsletter 👇