agentsclimarketplace

Html to pptx skill

Skill Alienxcript/html-export-skills/html-to-pptx skill

● Export HTML slide decks to PPTX or images using Claude Code skills — powered by headless Chrome and Pillow.

Install
npx -y skills add Alienxcript/html-export-skills --skill html-to-pptx skill

Assembled from the repository path, not quoted from the project. Check it against their README if it does not work.

2 things to look at

  • no licenseNo license file was found in the repository. Code published without one is not open source by default, so using it at work is a question for whoever answers licensing questions where you are.
  • 1 stars1 stars. Stars are a popularity signal and not a quality one, but at this level it is likely that nobody has read this closely except its author, and you would be relying on your own review.

What its author says it does

Copied from the file, not written here

Convert a single-file HTML slide deck into a pixel-perfect PPTX by rendering it in headless Chrome, taking a full-page screenshot, slicing it into per-slide images with Pillow, and packing them into a PowerPoint file. Use when the user has an HTML presentation and wants a .pptx export.

SKILL.md

5.1 KB, as published. Nobody here has run it

HTML to PPTX Skill

Convert any single-file HTML slide deck into a .pptx file that looks exactly like the browser render — fonts, glows, gradients, animations frozen at their initial state.

How It Works

  1. Headless Chrome (via Puppeteer) renders the HTML at 1920×1080 and takes a single fullPage: true screenshot → one tall PNG
  2. Pillow slices that PNG into N equal strips (one per slide)
  3. python-pptx packs each strip as a full-bleed image on its own PPTX slide

This avoids all scroll/clip coordinate bugs — each slide is a guaranteed unique pixel crop.


Requirements Check

Before running, verify these are available:

  • node + puppeteer npm package (installed locally or globally)
  • python with pillow and python-pptx packages
  • Chrome or Edge executable on the system

Step-by-Step Instructions

1. Ask the user for inputs

You need:

  • HTML file path — the source presentation
  • Number of slides — how many slides the deck has
  • Output PPTX filename — where to save (default: same folder as HTML, same name with .pptx)
  • Slide aspect ratio — default 16:9 (1920×1080). Ask only if non-standard.
  • Chrome path — auto-detect from common locations, only ask if not found

Auto-detect Chrome from these paths (check in order):

  • C:/Program Files/Google/Chrome/Application/chrome.exe
  • C:/Program Files (x86)/Google/Chrome/Application/chrome.exe
  • C:/Program Files (x86)/Microsoft/Edge/Application/msedge.exe
  • /usr/bin/google-chrome
  • /usr/bin/chromium-browser

2. Install puppeteer if needed

# Check
node -e "require('puppeteer')" 2>&1

# Install locally in the HTML file's directory if missing
npm install puppeteer --save-dev

3. Write the screenshot script

Write _screenshot.mjs to the same folder as the HTML:

import puppeteer from 'puppeteer';
import path from 'path';
import { fileURLToPath } from 'url';

const __dirname = path.dirname(fileURLToPath(import.meta.url));
const HTML_PATH = path.join(__dirname, '<HTML_FILENAME>');
const W = 1920;
const H = 1080;

const browser = await puppeteer.launch({
  executablePath: '<CHROME_PATH>',
  headless: true,
  args: ['--no-sandbox', `--window-size=${W},${H}`],
});

const page = await browser.newPage();
await page.setViewport({ width: W, height: H, deviceScaleFactor: 1 });
await page.goto(`file:///${HTML_PATH.replace(/\\/g, '/')}`, {
  waitUntil: 'networkidle0',
  timeout: 30000,
});

// Wait for fonts and transitions to settle
await new Promise(r => setTimeout(r, 2500));

// Freeze animations, hide fixed UI chrome
await page.addStyleTag({ content: `
  * { animation: none !important; transition: none !important; }
  body::after { display: none !important; }
  #nav, #progress, nav, header[data-fixed] { display: none !important; }
` });

await page.screenshot({
  path: path.join(__dirname, '_fullpage.png'),
  fullPage: true,
});

console.log('Done.');
await browser.close();

4. Write the slice + pack script

Write _pack_pptx.py to the same folder:

from PIL import Image
from pptx import Presentation
from pptx.util import Inches
import os

FOLDER   = r'<FOLDER_PATH>'
FULLPAGE = os.path.join(FOLDER, '_fullpage.png')
OUT      = os.path.join(FOLDER, '<OUTPUT_FILENAME>')
SLIDES   = <SLIDE_COUNT>

img = Image.open(FULLPAGE)
W, H = img.size
slide_h = H // SLIDES

print(f"Full image: {W}x{H}, {SLIDES} slides, {slide_h}px each")

prs = Presentation()
prs.slide_width  = Inches(20)      # 1920px at 96dpi
prs.slide_height = Inches(11.25)   # 1080px at 96dpi
blank = prs.slide_layouts[6]

for i in range(SLIDES):
    top  = i * slide_h
    crop = img.crop((0, top, W, top + slide_h))
    tmp  = os.path.join(FOLDER, f'_slide_{i+1:02d}.png')
    crop.save(tmp)
    slide = prs.slides.add_slide(blank)
    slide.shapes.add_picture(tmp, left=0, top=0,
                             width=prs.slide_width,
                             height=prs.slide_height)
    print(f"  Slide {i+1:02d} rows {top}-{top+slide_h}")

prs.save(OUT)
print(f"Saved: {OUT}")

5. Run both scripts

node _screenshot.mjs
python _pack_pptx.py

6. Clean up temp files

After confirming the PPTX looks correct, delete:

  • _fullpage.png
  • _screenshot.mjs
  • _pack_pptx.py
  • _slide_01.png_slide_NN.png

Common Issues

ProblemCauseFix
All slides identicalUsing clip:{y:0} on scrolled viewportAlways use fullPage:true + slice — never scroll
PermissionError on savePPTX open in PowerPointClose the file first, or save to a new filename
Fonts wrong in PPTXCustom web fonts not installed locallyThis approach embeds pixel images so fonts are always correct
Slide count wrongH // SLIDES roundingCheck H % SLIDES == 0; if not, slides have min-height inconsistency in HTML
Chrome not foundWrong exe pathCheck Edge as fallback

Gives 0 of the 12 instructions most pdf office docs skills give

Counted across 635 of the 690 authors here whose files we hold, read 2026-08-06

  • extract text using pdfplumberin 92 of 635, across 25 files
  • create PDFs using reportlabin 83 of 635, across 16 files
  • read FORMS.md to fill out PDF formsin 80 of 635, across 13 files
  • OCR scanned PDFs using pytesseractin 77 of 635, across 10 files
  • merge or split PDFs using qpdfin 70 of 635, across 3 files
  • use Excel formulas instead of hardcoded calculated valuesin 68 of 635, across 12 files
  • unpack edit xml and repack existing documentsin 63 of 635, across 8 files
  • document sources for hardcoded valuesin 61 of 635, across 9 files
  • write minimal python code without unnecessary commentsin 59 of 635, across 7 files
  • run the recalculation script after adding or modifying formulasin 58 of 635, across 6 files
  • fix all identified formula errors and recalculatein 58 of 635, across 6 files
  • format years as text stringsin 57 of 635, across 5 files

Said here and by no other author read

  • ask the user for the html file path and slide count
  • render the HTML in headless Chrome at 1920x1080
  • take a full page screenshot of the presentation
  • freeze CSS animations and transitions before screenshotting
  • hide fixed UI chrome elements before screenshotting
  • slice the full page image into equal vertical strips

Grouped from the skills themselves: near-identical wordings counted once, and counted by distinct author, so one author publishing three of these counts once.

Keep looking

Skills are one crate of 328,083. Ordering is by how many stacks a row turns up in, so the top of any crate is what has actually been picked rather than what has the most stars.