diff --git a/README.md b/README.md index 433ab6e0..0623367f 100644 --- a/README.md +++ b/README.md @@ -18,7 +18,7 @@ Sponsor

-![SnapOtter - Dashboard](branding/dashboard.png) +![SnapOtter - Dashboard](branding/dashboard.gif) ## Key Features diff --git a/apps/landing/public/og-image.png b/apps/landing/public/og-image.png index 31243cbc..5a1223d9 100644 Binary files a/apps/landing/public/og-image.png and b/apps/landing/public/og-image.png differ diff --git a/apps/web/public/og-image.png b/apps/web/public/og-image.png index 29872b2e..5a1223d9 100644 Binary files a/apps/web/public/og-image.png and b/apps/web/public/og-image.png differ diff --git a/branding/README.md b/branding/README.md index b3f60748..f7c2a635 100644 --- a/branding/README.md +++ b/branding/README.md @@ -2,6 +2,8 @@ Press kit for use in blog posts, articles, reviews, and other publications about SnapOtter. Free to use when referencing SnapOtter. +SnapOtter is an open-source, self-hosted file processing suite with 157 tools across image, video, audio, PDF, and file workflows. + ## Files | File | Size | Use | @@ -17,23 +19,26 @@ Press kit for use in blog posts, articles, reviews, and other publications about | `social-preview.png` | 1280x640 | OpenGraph / social media preview | | `wordmark.svg` | Scalable | "SnapOtter" text mark (dark text) | | `wordmark-white.svg` | Scalable | "SnapOtter" text mark (white text, for dark backgrounds) | -| `banner.svg` | Scalable | Logo + tagline banner on dark background | -| `dashboard.png` | Screenshot | Full dashboard screenshot for README / marketing | -| `dashboard_no_detail.png` | Screenshot | Dashboard screenshot without detail panel | +| `banner.svg` | Scalable | Wordmark + tagline banner on dark background | +| `dashboard.gif` | Animated | Scrolling tour of all 157 tools across the five modalities (README hero) | ## Brand Colors | Name | Hex | Usage | |------|-----|-------| -| Primary Blue | `#3b82f6` | "Otter" in wordmark, buttons, accents | -| Dark | `#0f172a` | "Snap" in wordmark, dark mode background | -| Slate | `#94a3b8` | Subtitle/muted text | -| White | `#ffffff` | Light mode background | +| Otter Orange | `#E07832` | "Otter" in wordmark, buttons, links, CTAs | +| Orange Light | `#F09550` | Hover states | +| Orange Dark | `#C06520` | Text emphasis on light backgrounds | +| Dark Chocolate | `#1A1210` | Dark sections, banner background | +| Foreground | `#1A1814` | "Snap" in wordmark, primary text | +| Cream | `#FAFAF7` | Page / light background | +| Muted | `#6B6560` | Secondary / subtitle text | ## Typography -- **Headings / brand name**: Nunito (weight 800) -- **Body text**: Inter +- **Headings / brand name**: Bricolage Grotesque (weight 800) +- **Body text**: Instrument Sans +- **Code / monospace**: JetBrains Mono ## Usage Guidelines diff --git a/branding/banner.svg b/branding/banner.svg index d3953a6c..0bb1a2f7 100644 --- a/branding/banner.svg +++ b/branding/banner.svg @@ -1,9 +1,9 @@ - - - SnapOtter + + + SnapOtter - - Self-hosted image processing suite + + Self-hosted file processing suite diff --git a/branding/dashboard.gif b/branding/dashboard.gif new file mode 100644 index 00000000..0167a9c0 Binary files /dev/null and b/branding/dashboard.gif differ diff --git a/branding/dashboard.png b/branding/dashboard.png deleted file mode 100644 index b6377b0d..00000000 Binary files a/branding/dashboard.png and /dev/null differ diff --git a/branding/dashboard_no_detail.png b/branding/dashboard_no_detail.png deleted file mode 100644 index 9e11229d..00000000 Binary files a/branding/dashboard_no_detail.png and /dev/null differ diff --git a/branding/social-preview.png b/branding/social-preview.png index 31243cbc..5a1223d9 100644 Binary files a/branding/social-preview.png and b/branding/social-preview.png differ diff --git a/branding/wordmark-white.svg b/branding/wordmark-white.svg index fd394eee..8ff4018f 100644 --- a/branding/wordmark-white.svg +++ b/branding/wordmark-white.svg @@ -1,5 +1,5 @@ - - SnapOtter + + SnapOtter diff --git a/branding/wordmark.svg b/branding/wordmark.svg index 82bed2c7..2794c107 100644 --- a/branding/wordmark.svg +++ b/branding/wordmark.svg @@ -1,5 +1,5 @@ - - SnapOtter + + SnapOtter diff --git a/scripts/branding/generate-social-preview.mjs b/scripts/branding/generate-social-preview.mjs new file mode 100644 index 00000000..ea3416f8 --- /dev/null +++ b/scripts/branding/generate-social-preview.mjs @@ -0,0 +1,150 @@ +// Generates branding/social-preview.png (1280x640) -- the SnapOtter social/OG card. +// Echoes the landing hero: trust badges, the "Every file tool you need / Nothing +// leaves your network" headline, the supporting subhead, and the five modality +// cards. Rendered from HTML with the real brand fonts via headless Chromium. +// Run: node scripts/branding/generate-social-preview.mjs +// +// The same output is the canonical OG image; sync it to apps/landing/public/og-image.png +// and apps/web/public/og-image.png (see scripts/branding/sync-og.sh). + +import { rmSync, writeFileSync } from "node:fs"; +import { dirname, resolve } from "node:path"; +import { fileURLToPath } from "node:url"; +import { chromium } from "@playwright/test"; + +const repoRoot = resolve(dirname(fileURLToPath(import.meta.url)), "..", ".."); +const out = resolve(repoRoot, "branding/social-preview.png"); +// Temp HTML lives in branding/ so the page origin is file:// and can load the +// sibling logo and the ../apps fonts as file:// subresources. +const htmlPath = resolve(repoRoot, "branding/.og.html"); + +// Enterprise trust badges (subset of Hero.astro's list). +const BADGES = ["On-premise", "GDPR & HIPAA", "Air-gap", "SAML SSO", "Open source"]; + +// lucide icon inner-SVG (stroke), matching the icons used in CategoryCards.astro. +const ICON = { + image: + '', + video: + '', + music: '', + fileText: + '', + database: + '', +}; + +// Mirrors CategoryCards.astro (label/blurb/color/icon). Counts are toolSection() +// section counts (image 64, video 29, audio 17, pdf 25, files 22 = 157); refresh +// with: tsx -e "import('@snapotter/shared')..." over toolSection (see git history). +const CARDS = [ + { + label: "Image Tools", + count: 64, + blurb: "Resize, convert, and enhance", + color: "#E07832", + icon: ICON.image, + }, + { + label: "Video Tools", + count: 29, + blurb: "Trim, convert, and caption", + color: "#BE4A3C", + icon: ICON.video, + }, + { + label: "Audio Tools", + count: 17, + blurb: "Convert, trim, and transcribe", + color: "#2C7A75", + icon: ICON.music, + }, + { + label: "PDF & Documents", + count: 25, + blurb: "Merge, split, and convert", + color: "#44568C", + icon: ICON.fileText, + }, + { + label: "File Tools", + count: 22, + blurb: "Convert and transform", + color: "#5C8642", + icon: ICON.database, + }, +]; +const total = CARDS.reduce((s, c) => s + c.count, 0); + +const badgesHtml = BADGES.map( + (b) => + `${b}`, +).join(""); + +const cardsHtml = CARDS.map( + (c) => `
+
+ ${c.icon} + ${c.count} tools +
+
${c.label}
+
${c.blurb}
+
`, +).join(""); + +const html = `
+
SnapOtter${total} tools
+
${badgesHtml}
+
Every file tool you need.Nothing leaves your network.
+
The file-processing suite for teams that keep sensitive data in-house.
+
${cardsHtml}
+
`; + +writeFileSync(htmlPath, html); +try { + const browser = await chromium.launch(); + const ctx = await browser.newContext({ viewport: { width: 1280, height: 640 } }); + const page = await ctx.newPage(); + await page.goto("file://" + htmlPath, { waitUntil: "load" }); + await page.evaluate(async () => { + await document.fonts.ready; + }); + await page.waitForTimeout(150); + await page.screenshot({ path: out }); + await browser.close(); + console.log("wrote " + out); +} finally { + rmSync(htmlPath, { force: true }); +} diff --git a/scripts/branding/sync-og.sh b/scripts/branding/sync-og.sh new file mode 100755 index 00000000..33b07ec8 --- /dev/null +++ b/scripts/branding/sync-og.sh @@ -0,0 +1,9 @@ +#!/usr/bin/env bash +# Propagate the canonical social card to the app OG-image locations. +# Run after regenerating branding/social-preview.png. +set -euo pipefail +root="$(cd "$(dirname "$0")/../.." && pwd)" +src="$root/branding/social-preview.png" +cp "$src" "$root/apps/landing/public/og-image.png" +cp "$src" "$root/apps/web/public/og-image.png" +echo "synced social-preview.png -> apps/landing/public/og-image.png, apps/web/public/og-image.png"