Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions AGENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ npm run typecheck # tsc --noEmit on @opencanva/core
```

- The demo app runs the CLI directly: `opencanva <dev|build|preview|sync|init>` (defaults to `dev`). Regenerate the committed skills with **`npm run sync`** (it runs in `apps/demo`); bare `opencanva sync` inside this monorepo is refused (it would write a stray skills tree).
- `npm run sync` copies the skills bundled in `packages/core/skills/` into the demo workspace's **`.agents/skills/`** (vendor-neutral, committed) **and `.claude/skills/`** (Claude-specific, git-ignored): `canva-authoring`, `create-design`, `apply-comments`, `current-design`, `create-theme`, `svg-illustration`.
- `npm run sync` copies the skills bundled in `packages/core/skills/` into the demo workspace's **`.agents/skills/`** (vendor-neutral, committed) **and `.claude/skills/`** (Claude-specific, git-ignored): `canva-authoring`, `create-design`, `write-marketing-copy`, `select-marketing-image`, `design-marketing-cover`, `apply-comments`, `current-design`, `create-theme`, `svg-illustration`.
- `opencanva init [dir]` scaffolds a fresh OpenCanva project (config, starter design, and both skill dirs) so a new project is multi-agent ready out of the box.
- After changing `designPresets` in `packages/core/src/design.ts` (every preset needs `vibe` + `tags`), run **`npm run gen:catalog && npm run sync`** — it regenerates the theme catalog table inside the `create-design` skill from the presets; `check:sync` fails CI if the table is stale.
- To typecheck the designs specifically: `npx tsc --noEmit -p apps/demo` (this is what CI runs alongside the core typecheck).
Expand All @@ -29,7 +29,7 @@ The authoring know-how ships as **Agent Skills** — `SKILL.md` files with YAML

(The repo-root `.agents/skills/` holds only `frontend-design` — a third-party design-quality skill vendored for work *on the framework*, tracked in `skills-lock.json`. It is intentionally not part of the bundle `sync`/`init` distribute.)

- **Authoring graphics** (the common task): write/edit files under `designs/<id>/`. Read the **`canva-authoring`** skill first — it's the source of truth for the file contract, the object primitives, the coordinate system, and the inspector-compatibility rules. Use **`create-design`** for the new-graphic workflow, **`apply-comments`** to process inspector markers, **`current-design`** to resolve "this design".
- **Authoring graphics** (the common task): write/edit files under `designs/<id>/`. Read the **`canva-authoring`** skill first — it's the source of truth for the file contract, the object primitives, the coordinate system, and the inspector-compatibility rules. Use **`create-design`** for the new-graphic workflow, **`write-marketing-copy`** to turn source material into a click/read/share content package, **`select-marketing-image`** to choose and crop the focal image, **`design-marketing-cover`** for cover composition, **`apply-comments`** to process inspector markers, and **`current-design`** to resolve "this design".
- If your agent does not auto-discover skills, read `apps/demo/.agents/skills/canva-authoring/SKILL.md` directly before editing any design.

## Working in this repo
Expand Down
4 changes: 2 additions & 2 deletions CLAUDE.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ npm run typecheck # tsc --noEmit on @opencanva/core
```

- The demo app runs the CLI directly: `opencanva <dev|build|preview|sync|init>` (defaults to `dev`). Regenerate the committed skills with **`npm run sync`** (it runs in `apps/demo`); bare `opencanva sync` inside this monorepo is refused (it would write a stray skills tree).
- `npm run sync` copies the skills bundled in `packages/core/skills/` into the demo workspace's **`.agents/skills/`** (vendor-neutral, committed) **and `.claude/skills/`** (Claude-specific, git-ignored): `canva-authoring`, `create-design`, `apply-comments`, `current-design`, `create-theme`, `svg-illustration`.
- `npm run sync` copies the skills bundled in `packages/core/skills/` into the demo workspace's **`.agents/skills/`** (vendor-neutral, committed) **and `.claude/skills/`** (Claude-specific, git-ignored): `canva-authoring`, `create-design`, `write-marketing-copy`, `select-marketing-image`, `design-marketing-cover`, `apply-comments`, `current-design`, `create-theme`, `svg-illustration`.
- `opencanva init [dir]` scaffolds a fresh OpenCanva project (config, starter design, and both skill dirs) so a new project is multi-agent ready out of the box.
- After changing `designPresets` in `packages/core/src/design.ts` (every preset needs `vibe` + `tags`), run **`npm run gen:catalog && npm run sync`** — it regenerates the theme catalog table inside the `create-design` skill from the presets; `check:sync` fails CI if the table is stale.
- To typecheck the designs specifically: `npx tsc --noEmit -p apps/demo` (this is what CI runs alongside the core typecheck).
Expand All @@ -29,7 +29,7 @@ The authoring know-how ships as **Agent Skills** — `SKILL.md` files with YAML

(The repo-root `.agents/skills/` holds only `frontend-design` — a third-party design-quality skill vendored for work *on the framework*, tracked in `skills-lock.json`. It is intentionally not part of the bundle `sync`/`init` distribute.)

- **Authoring graphics** (the common task): write/edit files under `designs/<id>/`. Read the **`canva-authoring`** skill first — it's the source of truth for the file contract, the object primitives, the coordinate system, and the inspector-compatibility rules. Use **`create-design`** for the new-graphic workflow, **`apply-comments`** to process inspector markers, **`current-design`** to resolve "this design".
- **Authoring graphics** (the common task): write/edit files under `designs/<id>/`. Read the **`canva-authoring`** skill first — it's the source of truth for the file contract, the object primitives, the coordinate system, and the inspector-compatibility rules. Use **`create-design`** for the new-graphic workflow, **`write-marketing-copy`** to turn source material into a click/read/share content package, **`select-marketing-image`** to choose and crop the focal image, **`design-marketing-cover`** for cover composition, **`apply-comments`** to process inspector markers, and **`current-design`** to resolve "this design".
- If your agent does not auto-discover skills, read `apps/demo/.agents/skills/canva-authoring/SKILL.md` directly before editing any design.

## Working in this repo
Expand Down
3 changes: 2 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,8 @@ export default [Poster] satisfies Scene[];
- **Click-to-source.** Every object you click resolves to the exact `<Box>`/`<Text>` in your source (via injected `data-ox-loc` read off the React fiber — works across files and components). Drag/resize/recolor rewrite the object's props **in place** through a dev-only write-back API; the source stays byte-stable so HMR is surgical.
- **Comments → edits.** Leave a `@canva-comment` on any object; the bundled `apply-comments` skill applies them.
- **Current-design pointer.** The dev server writes `.opencanva/current.json` so an agent can resolve "this design / the object I selected".
- **Works with any agent.** A root `AGENTS.md` (the cross-tool standard read by Codex, Cursor, Copilot, …) carries the repo guide, and `CLAUDE.md` is a byte-identical copy of it (kept in sync by CI). The authoring skills — `canva-authoring`, `create-design`, `apply-comments`, `current-design`, `create-theme`, `svg-illustration` — ship as Agent Skills: `npm run sync` copies them into both `.agents/skills/` (vendor-neutral, committed) and `.claude/skills/` (local). `opencanva init` scaffolds a new project with all of it baked in.
- **Marketing message → image → cover → design.** The bundled `write-marketing-copy` skill creates a truthful click/read/share content package; `select-marketing-image` chooses, ranks, and crops the focal image; `design-marketing-cover` turns both into a thumbnail-tested composition. `create-design` orchestrates the pipeline when the graphic has a marketing goal.
- **Works with any agent.** A root `AGENTS.md` (the cross-tool standard read by Codex, Cursor, Copilot, …) carries the repo guide, and `CLAUDE.md` is a byte-identical copy of it (kept in sync by CI). The nine authoring skills — `canva-authoring`, `create-design`, `write-marketing-copy`, `select-marketing-image`, `design-marketing-cover`, `apply-comments`, `current-design`, `create-theme`, `svg-illustration` — ship as Agent Skills: `npm run sync` copies them into both `.agents/skills/` (vendor-neutral, committed) and `.claude/skills/` (local). `opencanva init` scaffolds a new project with all of it baked in.

## Layout

Expand Down
8 changes: 8 additions & 0 deletions apps/demo/.agents/skills/create-design/SKILL.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,14 @@ description: Use this skill when the user wants to create, draft, design, or gen

This skill owns the **workflow** for making a new graphic. The technical reference — file contract, object primitives, coordinate system, design tokens — lives in the **`canva-authoring`** skill. Read that before writing code. You only write files under `designs/<id>/`; never modify `package.json`, `opencanva.config.ts`, or other designs.

## Step 0 — Build the marketing message when needed

If the graphic must earn clicks, reading, saves, or shares—a social post, ad, campaign carousel, launch graphic, cover, or thumbnail—read **`write-marketing-copy`** first and turn the user's source into a `ContentPack`. Settle the audience, one truthful promise, title, cover copy, body/board outline, proof, and CTA before composing the visual.

If the first board is a cover or thumbnail and its focal image is not locked, read **`select-marketing-image`** and settle an `ImageSelectionPack`. Then read **`design-marketing-cover`** for the stop/click strategy, cover copy tests, layout pattern, and thumbnail audit. This skill still owns the OpenCanva creation workflow.

Skip this branch for graphics whose purpose is purely decorative or where the user has already locked the exact copy and cover direction.

## Step 1 — Clarify the brief (ask before designing)

Use `AskUserQuestion` to lock in, unless the user's message already answers them:
Expand Down
113 changes: 113 additions & 0 deletions apps/demo/.agents/skills/design-marketing-cover/SKILL.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,113 @@
---
name: design-marketing-cover
description: Plan, create, or improve a marketing cover or thumbnail that earns attention, communicates relevance, and converts the right viewer without deceptive clickbait. Use for Xiaohongshu covers, social post covers, video thumbnails, carousel first boards, ad hero graphics, cover copy, cover A/B variants, or before create-design when the first board must drive clicks and reading.
---

# Design a marketing cover

Design the cover as a two-stage decision: the visual makes the right person pause; the words give them a truthful reason to enter. Optimize for qualified attention and promise match, not beauty or curiosity in isolation.

`create-design` owns the new-design workflow and `canva-authoring` owns the React/file contract. This skill owns the cover composition. Read `canva-authoring` before editing any file under `designs/`. If the title, promise, or body is not settled, use `write-marketing-copy` first. If the focal image is not locked, use `select-marketing-image` before composing the cover.

## Establish the click contract

Extract these fields from the request or its `ContentPack`:

- audience and recognizable situation;
- one-sentence promise;
- proof or result actually present in the content;
- desired action after the click;
- channel and aspect ratio;
- brand or creator memory anchors;
- available photos, screenshots, product images, or illustrations.

Reject a cover concept if the body cannot pay it off. Never fake a result image, endorsement, transformation, scarcity cue, UI state, or emotional reaction.

For Xiaohongshu, read [references/xiaohongshu.md](references/xiaohongshu.md).

## Resolve the focal image

Consume the `ImageSelectionPack` from `select-marketing-image`: selected asset, evidence boundary, focal point, essential region, text-safe zone, crop, treatment, rights/privacy status, and validation status.

If the user has already locked an image, verify that it matches the promise and can survive the target crop. Do not replace it merely because another option is prettier. If it is misleading, unusable, or unlicensed, explain the conflict and use `select-marketing-image` to find a truthful alternative.

## Write cover copy with three tests

The cover copy must answer, at a glance:

1. **Is this about me?** Name the person, moment, task, or symptom.
2. **What do I gain or avoid?** Make the practical value visible.
3. **Why open this one?** Surface credible specificity, a gap, proof, or an unresolved tension.

Keep cover copy shorter than the title. Do not repeat the title verbatim. Use a short eyebrow or proof chip only when it adds a distinct piece of information.

## Pick a layout pattern

- **Sandwich:** headline above, focal person/object in the middle, payoff or proof below. Use for a strong portrait or product.
- **Information center:** one large text block integrated with the image. Use when rapid comprehension matters more than atmosphere.
- **Top/bottom:** headline in one zone, supporting line or proof in the other, with the visual carrying the center. Use for clean repeatable series.
- **Four-corner:** distribute very short text around a strong central image. Use only when every corner remains legible and the image has enough negative space.

Choose the simplest pattern that preserves the image and the promise. Do not fill every empty area.

## Build it in OpenCanva

Follow `create-design` for id, theme, scene, and handoff; follow `canva-authoring` for primitives and source-safe coordinates. Additionally:

- Make one element dominant: the focal image or the headline, not both at equal weight.
- Keep the reading order obvious at thumbnail size: context → promise → proof.
- Put text on a quiet region, solid panel, gradient/scrim, or high-contrast crop.
- Use high contrast based on the actual background. Yellow can attract attention only when it still contrasts; it is not a universal rule.
- Control line breaks. Keep the key phrase together and remove words before shrinking it into illegibility.
- Keep essential text and faces away from likely UI overlays and crop edges.
- Use named groups such as `FocalImage`, `Headline`, `Proof`, and `BrandAnchor`.
- Reuse a stable visual anchor—type treatment, framing device, color, or recurring position—when the user is building a recognizable series.

View the result at fitted zoom and at roughly 25% size. If the promise cannot be understood at the smaller view, simplify it.

## Create variants that teach something

When the user asks for options or the concept is high-stakes, create two or three labeled Scene variants. Keep the promise and brand constant; change only one major variable per variant:

- focal image;
- copy angle;
- layout;
- contrast treatment.

Do not create cosmetic variants that cannot reveal why one performs better. Once a pattern performs well, reuse its core structure until evidence supports changing it.

## Deliver a CoverSpec

Before or alongside implementation, capture:

```md
## CoverSpec
- Audience / situation:
- Channel / dimensions:
- Promise paid off by:
- Selected asset / source mode:
- Focal image / crop:
- Essential region / text-safe zone:
- Cover copy:
- Supporting proof or eyebrow:
- Layout pattern:
- Reading order:
- Contrast treatment:
- Brand anchor:
- Optional test variable:
```

## Two-second audit

Score each item 0–2:

- **Pause:** the visual has a clear focal reason to stop.
- **Relevance:** the right viewer recognizes themselves.
- **Value:** the benefit or avoided cost is concrete.
- **Reason to click:** specificity, proof, or tension remains after the topic is understood.
- **Legibility:** the message survives thumbnail size and likely UI crops.
- **Promise match:** the underlying content pays off the cover early.

Revise below 10/12. Treat a 0 on relevance, legibility, or promise match as a hard failure regardless of total score. Finally run the OpenCanva layout lint; a marketing cover is not done with hidden, crowded, occluded, or off-canvas content.

Do not award a final **Pause** or **Legibility** score to an unrendered `CoverSpec`. Mark those items `provisional` until the cover has been viewed at fitted zoom and thumbnail size. A written intention is not visual verification.
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
interface:
display_name: "Design Marketing Cover"
short_description: "Design clear, clickable covers that keep their promise"
default_prompt: "Use $design-marketing-cover to turn my content into a clickable, trustworthy social cover."
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
# Xiaohongshu cover reference

Use this reference for Xiaohongshu note covers. Treat it as a practical creative heuristic, not a guarantee about distribution.

## Format and roles

- Default a portrait note cover to 3:4, commonly 1080×1440, unless the user's publishing workflow requires another size.
- Treat the image as the stopping device and the overlay copy as the clicking reason.
- Design for a two-column discovery feed and test the cover at small size.
- Make the cover and note title complementary. The title can carry topic/search context while the cover carries self-relevance, payoff, or tension.

## Strong focal image options

1. A high-contrast scene with a clear social or visual tension.
2. A genuine emotional close-up relevant to the content.
3. A visible, source-supported outcome or comparison.
4. A first-person view that puts the reader inside the task.

Prefer self-insertion over generic prettiness. The viewer should recognize a situation they want, fear, or already experience.

## Overlay copy

Check three questions:

- Does the target reader know it concerns them?
- Is the gain or avoided mistake visible?
- Is there a credible reason this specific note is worth opening?

Use high contrast against the real image region. A bright yellow accent is common and can attract attention, but switch colors whenever it loses contrast or clashes with the brand.

## Layout patterns

- Sandwich: headline / face or object / payoff.
- Information center: large message integrated across the composition.
- Top/bottom: primary line above, secondary proof below.
- Four-corner: short fragments around a clean central image; reserve for images with strong negative space.

## Series behavior

Keep a successful cover grammar recognizable across a series: stable type, crop logic, color cue, and information order. Test one major variable at a time instead of changing the entire style every post.
Loading
Loading