Home / All Skills / Content & Media Creation / promo-video
Content & Media Creation · iart-ai/ecommerce-video-skills

promo-video

This skill should be used when the user asks to "make a sale video", "create a promo video", "build a discount/percentage-off reveal", "animate a was→now price with a strike-through", "do a Black Friday / flash-sale / clearance video", "make a promo-code reveal with a countdown", or "batch a promo template across many products". Covers the offer-announcement arc — discount reveal, price strike-through, promo code, urgency, product shot, CTA — and product+offer data → many videos.

L4 High-Privilege · Graded auth & full auditV1 Commit-PinnedExecute CommandNetwork AccessWrite FileDual-pass Audit
Author iart-aiGitHub iart-ai/ecommerce-video-skills ↗Stars 8License MIT(仓库根 LICENSE:「MIT License」/「Copyright (c) 2026 iart.ai」;.claude-plugin/plugin.json 与 README「## License」同声明 MIT)Commit 2bd0dd19c9
Control levels describe skill capabilities and suggested control measures; they do not represent quality or safety certifications, nor do they dictate usability. Usage decisions rest entirely with users and administrators. Different agent hosts apply varying constraints; do not assume hosts provide automatic protection. Third-party skill copyrights belong to their original authors. Use at your own risk.

1How It Works & Mechanism

Cardinal Rule #1: Numbers are information — prices and discounts must be derived, never input twice.

skills/promo-video/SKILL.md
1. **The number is the message — keep it exact.** Prices and percentages must be computed, never typed twice. Derive `now` and the `% off` from `was` and the discount so they can't disagree.
"Accuracy" here refers to a single source of truth for data, not display formatting.

Store only the ground truth: now and pct are never persisted and must be derived from was/discount, preventing self-contradictions.

skills/promo-video/references/promo-components.md
One object per product. `now` and `pct` are NOT stored — they are derived, so they can never contradict `was` and `discount`. Store only the source of truth.
A structural guarantee, rather than relying on manual checks.

Strike first, drop the price second — the wrong sequence will be perceived as a glitch.

skills/promo-video/SKILL.md
Order matters: strike the old price *first*, then drop the new one. Striking and counting at the same instant reads as a glitch.
In implementation, the strike is interpolated across widths from frames 0–12, while the new price counts up with a spring curve starting from frame 8.

Round currency to cents before formatting, and render using Intl.

skills/promo-video/references/promo-components.md
Compute every displayed figure from the offer in one place. Round to cents *before* formatting so the price a viewer reads is exactly the price they pay.
SKILL.md aligns with the requirement: Round currency to cents + Intl.NumberFormat + tabular-nums.

Validate row by row before batching, and fail loud on bad rows: silently rendering bad rows is precisely how "$470 gets marked as $47".

skills/promo-video/references/promo-components.md
A batch that silently renders a bad row is how a $470 item ships labelled "$47". Validate every offer before rendering and stop the run on the first bad one.
Validation checks include now < was, discount ∈ (0, 1), non-empty code, parseable deadline, and image existence.

Urgency must be genuine: provide a deadline or a realistic countdown; never use fake timers.

skills/promo-video/SKILL.md
Urgency lifts conversion only when it's real. Show a concrete deadline ("Ends Sun 11:59pm") or a live-looking countdown — never a fake timer.
Also requires maintaining a readable pace of ≥2s for the deadline, with the countdown placed on a separate line.

One focus per frame: one discount, one code, one CTA; if there are two offers, make two separate videos.

skills/promo-video/SKILL.md
2. **One offer, one focus per frame.** A single discount, a single code, a single CTA. Competing offers kill the urgency. If there are two deals, make two videos.
The discount number must be the loudest visual element on the screen (larger than the brand and the product).

Choose presentation by price tier: use percentages for high prices, and fixed amounts for low prices.

skills/promo-video/SKILL.md
Choose the framing by price: percentage for higher-priced items ("40% OFF" beats "$32 off"), a flat amount for low-priced items ("$5 off" beats "8% off").
Turn "how to say it" into an explicit rule rather than leaving it to aesthetic discretion.

The verification loop focuses on "is the money right, is the image present": numeric accuracy and product image loading are non-negotiable.

skills/promo-video/SKILL.md
This is heavy-tier: the deliverable is an MP4, not a live page. A promo carries exact money — the verify pass is mostly *are the numbers right and is the product image actually there*.
Checkpoints include exact was/now/%, the strike-through being drawn on the old price, correct promo code spelling, and verifying it is the exact intended image.

2Core Capabilities

01Offer derivation model (priceModel: now/pct/off are all derived from was)
02Row-by-row validation (now < was, discount range, code, deadline, image existence) with loud failures
03Discount badge (discount number is the loudest visual element on screen)
04was→now strike-through price drop (strike first + spring counter + settling overshoot)
05Promo code chip (mono font + dashed border + static for easy screenshotting)
06Countdown or static deadline (static deadline looks cleaner in a 6s video)
07Template × data batching (price table → N videos, with pricing guaranteed by data)
08Multi-aspect ratio reframing (keeping badge, price, code, and CTA within the center safe zone)

3External Dependencies

KindDependency / Endpoint
packageremotion(frame/spring/interpolate/Img/Sequence)
clinode fs(校验时检查图片是否存在)
packageIntl.NumberFormat / Intl.DateTimeFormat(运行时内置,无第三方包)
clinpx remotion render(逐 offer 渲染)
cliffmpeg / ffprobe(仓库共享 contact-sheet.sh、probe-mp4.sh)
networkiart.ai(reference 尾部推广链接,具 utm 参数;仅读者点击才请求)

4Recommended Governance & Evidence

Suggested Controls for Safe Operation
For Agent Runtime
Graded/per-use authorization, sandbox recommended
For Administrators
Approval workflow, rollback support, full audit
Evidence & Triggers (File Paths & Excerpts)
  • scripts/: Executes local scripts or commands: The skill directory contains no built-in scripts; SKILL.md/reference directs the agent to execute `node` (for validation/derivation, with source code embedded in documentation) and `npx re`
  • 网络端点: Declares external network access: No operational API calls during runtime; price and product data come from local offers/*.json, and product images come from the local public/ directory.
  • 本地工作目录: File reads/writes and artifact outputs: Writes `out/<name>.mp4` (one per offer), `out/f-discount.png`, and `out/f-price.png` within the user project.
Audit Notes: Triggered by the classification rubric: "relies on third-party plugins, mirrors, or remote packages". The skill directory consists purely of Markdown (no scripts, credential reads, or env reads), but the delivery path requires remotion and @remotion/cli (fetched and executed via npx from npm) as well as zod schemas; the sibling `remotion-video` in the same repo was classified as Orange under the same criteria, and this maintains consistency. Explicitly non-applicable items: no credential/cookie/environment variable reading (zero substantive hits on token scanning); no uploading of product assets to external services (rendering completes locally); no TLS downgrade, no `--no-verify`, no sandbox disabling, and no anti-automation bypassing. Trigger condition: occurs only when actually rendering videos.

5Second-Pass Verification

  • [discrepancy] 「全部为帧纯函数、禁用 Date.now()」与 reference 实现是否一致 — SKILL.md 明确要求所有动画值为 useCurrentFrame() 纯函数(no CSS transitions, timers, Date.now()),其自身示例也写「derived from a deadline prop (deterministic per frame)」;但 promo-components.md 的 Countdown 实际用 `const remaining = Math.max(0, (end - Date.now()) / 1000 - frame / fps);`——引入挂钟时间,同一 props 在不同时刻渲染会得到不同剩余时间,不可复现。
  • [discrepancy] 组件 import 名是否可运行 — promo-components.md 的 composition 写成 AbstractFill(Remotion 并无该导出,应为 AbsoluteFill),且使用处同样写 <AbstractFill …>;照抄会直接 import 失败。
  • [ok] 折扣公式是否两处一致 — SKILL.md 的 Math.round((1 - now / was) * 100) 与 priceModel 的 Math.round((1 - now / o.was) * 100) 同式同精度。
  • [ok] 校验清单是否与 SKILL.md 文字一致 — validateOffer 覆盖 now≥0 且 <was、discount∈(0,1)(当 now 未给)、code 非空、deadline 可解析、图片存在;与 SKILL.md 的 now < was / code present / image exists 一致且更强。
  • [ok] 节拍/时长的一致性 — SKILL.md 的 10s 节拍表与 reference 的帧调度(hook 0 / badge 27 / price 60 / code 210 / cta 270)及 --frames=0-299(10s@30fps)一致。
  • [ok] 「先划线后落价」顺序的实现 — PriceDrop 的 strike 从 f=0 起(0–12 帧画完),新价 spring 从 f-8 起跑;与 SKILL.md 的 strike the old price first 时序意图一致。

6Verdict & Scenarios

  • Stores only the ground truth for pricing while deriving now/pct, structurally eliminating contradictory pricing errors
  • Row-by-row pre-batch validation with loud failures, specifically preventing "selling $470 for $47"
  • Rounds currency to cents before formatting, using tabular-nums to prevent visual jitter
  • Rejects fake urgency by encoding honesty into explicit rules
  • Diverges discount presentation by price tier (percentage vs. fixed amount) with actionable criteria
  • Best for: E-commerce operations and growth teams creating promotional announcement videos: discount reveals, strike-through price drops, promo codes and deadlines, batching N videos (up to ~200 scale) from a price table, all requiring absolute pricing accuracy.
    Not for: Performance advertising and A/B testing campaigns (use ad-creative-video); customer testimonials/reviews (use testimonial-style skills); long-term brand films or deep-dive product explanations (this skill only creates 6–15s offer announcements).
    Install Agent-Ready
    ① Verified Mirror 2026-09-28
    Option A · Direct DownloadDownload promo-video.tar.gz
    sha256: 0c3e003bf0617b1c…
    Option B · Copy Guide for Agent
    install.json
    Agents automatically download and verify mirrors from this JSON guide.
    ② Upstream GitHub
    GitHub Repo ↗
    Pinned to commit 2bd0dd19c9.