Token导航 LogoToken导航

Agent Skill · 前端设计

grove-ui-design(格罗夫用户界面设计)

用于辅助界面设计、视觉规范、排版、配色、布局和交互体验优化。它适合让 Agent 根据产品场景整理页面结构、生成 UI 方案、检查视觉一致性或改进组件层级。使用时需要结合现有品牌、设计系统和用户任务,不应只堆装饰元素;涉及真实页面改动时,应通过截图或浏览器预览检查文本溢出、对齐和响应式表现。

grove-ui-design 是前端设计类 Agent Skill,可用宿主为 Codex、Claude、Cursor、Gemini CLI,通过GitHub 仓库获取,权限为只读;许可证信息还不明确,第三方扫描已通过,按安装量在前端设计类的 10,216 个 Skill 里排第 2,996。

总安装 1,676周安装 72GitHub Stars 4下载 588核验 2026-05-01

安装说明

本站只整理中文说明,不托管安装包,也不代用户安装。
GitHub
许可证
unknown

安装方式

通过对话安装

复制提示词发给支持本地命令或 Skills 的 AI 助手,先确认命令和权限,再让它执行。

请帮我安装这个 Agent Skill:grove-ui-design(格罗夫用户界面设计)
来源仓库:https://github.com/autumnsgrove/groveengine
仓库路径:skills/grove-ui-design
安装命令:
npx skills add https://github.com/autumnsgrove/groveengine --skill grove-ui-design
安装前请先检查当前环境是否支持对应 CLI,并向我确认将要执行的命令、安装目录、联网范围和文件读写权限;确认后再执行。

命令行安装

复制命令到本机终端执行。该命令会通过 npx skills 从第三方来源获取 Skill;本站只展示命令,不托管安装包,也不自动执行。

skills.shnpx skills
npx skills add https://github.com/autumnsgrove/groveengine --skill grove-ui-design

这个 Skill 是做什么的

前端设计类 Skill 关注页面结构、视觉规范和组件写法,输出通常是可运行的界面代码。

grove-ui-design 用于辅助界面设计、视觉规范和交互体验优化。适用于整理页面结构、生成 UI 方案或改进组件层级。结合现有品牌和设计系统,避免堆砌装饰元素。涉及真实页面改动时通过截图或预览检查文本溢出和对齐。

适用宿主包括 Codex、Claude、Cursor、Gemini CLI,接入前应确认版本、权限和运行环境要求。

来源仓库内路径:skills/grove-ui-design

上手步骤

4 步
  1. 1

    确认自己的宿主工具

    公开资料标注支持 Codex、Claude、Cursor、Gemini CLI;先确认自己用的是其中之一,再按对应工具的 Skills 目录放置。

  2. 2

    拿到安装命令

    可以直接复制的命令是 npx skills add https://github.com/autumnsgrove/groveengine --skill grove-ui-desi…;命令里的占位符换成自己的路径或密钥再执行。

  3. 3

    安装后重启宿主

    命令执行完要完全退出宿主工具再打开,让新装的 Skill 被重新扫描到,否则列表里可能看不到。

  4. 4

    按最小权限试用

    它标注为只读,先用只读任务试一次,确认行为符合预期再扩大使用范围。

常见问题

6 条

grove-ui-design 怎么安装?

在终端执行 npx skills add https://github.com/autumnsgrove/groveengine --skill grove-ui-design。装完完全退出宿主工具再打开,让它重新扫描本地 Skill。

grove-ui-design 支持哪些 AI 工具?

公开资料标注支持 Codex、Claude、Cursor、Gemini CLI。其他工具只要能读取本地 Skill 目录,一般也能手动放进去,但要自己确认触发方式是否一致。

grove-ui-design 需要什么权限?

权限级别是只读。该 Skill 主要提供规则、说明或参考内容,本身偏只读;真正读写文件、联网或执行命令仍取决于宿主 Agent 的任务。

grove-ui-design 是免费的吗?

公开资料没有标注明确许可证,收费和商用限制都无法确认。正式使用前请到来源仓库核对授权说明。

grove-ui-design 用的人多吗?

公开数据是累计安装 1,676 次,近一周安装 72 次,下载 588 次,GitHub 4 星。这些数字来自第三方目录统计,只能当作热度参考,不代表质量或安全性。

grove-ui-design 安全吗?

第三方扫描结果为通过,但这只覆盖已知的静态检查项,不能替代自己读一遍源码和安装命令。

值得选的地方和要先想清楚的地方

值得选的地方

  • 同时适配 4 种工具,换客户端不用重新找替代品。
  • 第三方扫描已通过,常见的高风险行为没有命中。
  • 标注为只读权限,试用阶段不容易误改本地文件。

先想清楚的地方

  • 许可证没有明确标注,能不能商用、能不能再分发都不确定。
  • 第三方目录整理,版本更新和行为细节以来源仓库为准。

适不适合你

更适合

  • 已经在用 Codex,想直接扩展它能力的人。
  • 需要处理前端设计类任务、又不想每次都手写提示词的人。
  • 只想先试试效果、不希望它改动本地文件的人。

不太适合

  • 需要明确授权才能用到公司项目里的场景。
  • 需要厂商级技术支持和 SLA 的生产系统。

前端设计类 Skill 对比

6 个同类
Skill总安装GitHub 星权限许可证扫描
frontend-design

前端设计 · Codex、Claude

8,823,360126,072只读MIT通过
vercel-composition-patterns

Vercel 组合模式 · Codex、Claude

3,858,81625,893需要联网MIT通过
vercel-react-native-skills

Vercel React native skills 前端 · Codex、Claude

2,468,66425,878只读MIT通过
adapt

adapt 搜索 · Codex、Claude

2,027,04023,125操作浏览器未明确通过
bolder

bolder 分析 · Codex、Claude

2,004,28823,130只读未明确通过
grove-ui-design

格罗夫用户界面设计 · 本页

1,6764只读未明确通过

按安装量取同分类前几名;数字来自第三方目录统计,只作热度参考,不代表质量结论。

SKILL.md 原文

Grove UI Design Skill

When to Activate

Activate this skill when:

  • Creating or enhancing pages for Grove sites
  • Adding decorative nature elements (trees, clouds, weather effects)
  • Implementing glassmorphism effects for readability
  • Working with the seasonal theme system
  • Building navigation patterns (navbar, mobile overflow menus)
  • Creating "story" pages that guide users through content
  • Ensuring mobile-friendly, accessible UI
  • Choosing icons or visual elements

The Grove Aesthetic

Grove is a place. It's nature-themed, warm, and inviting—like a midnight tea shop with good documentation.

Core Principles

Warm, introspective, queer, unapologetically building something meaningful.
Write with the warmth of a midnight tea shop and the clarity of good documentation.

Every design choice should feel:

  • Welcoming — like entering a cozy space
  • Organic — natural, not rigid or corporate
  • Readable — content-first, decorations enhance, never obstruct
  • Alive — subtle animations, seasonal changes, randomization

Grove Mode & Terminology (GroveTerm V2)

Grove has a terminology system that automatically switches between Grove-themed terms and standard terms based on the user's Grove Mode setting. Always use GroveTerm components instead of hardcoding Grove terminology in UI.

By default, Grove Mode is OFF for new visitors. They see familiar terms: "Posts" instead of "Blooms", "Dashboard" instead of "Arbor", "Support" instead of "Porch". When users opt in via the footer toggle, they see the full nature-themed vocabulary with interactive definitions.

The Component Suite:

import {(GroveTerm, GroveSwap, GroveText, GroveSwapText, GroveIntro)} from '@autumnsgrove/lattice/ui';
import groveTermManifest from '$lib/data/grove-term-manifest.json';
ComponentUse CaseBehavior
GroveTermInteractive terms with popup definitionsColored underline when ON, click for popup. Shows standard term when OFF.
GroveSwapSilent text replacementReactively swaps text. No underline, no interaction.
GroveTextParse [[term]] syntax in data stringsRenders `[[bloom\posts]]` as interactive GroveTerm components.
GroveSwapTextParse [[term]] syntax silentlySame parsing, silent swaps (no popups).
GroveIntro"We call it X" page bannersStandardized intro below page titles.

Usage:

<!-- Interactive term with popup -->
<GroveTerm term="bloom" manifest={groveTermManifest} />

<!-- Custom display text -->
<GroveTerm term="wanderer" manifest={groveTermManifest}>wanderers</GroveTerm>

<!-- Silent swap (no popup, no underline) -->
<GroveSwap term="arbor" manifest={groveTermManifest} />

<!-- Parse [[term]] syntax in data strings (ideal for FAQ items, pricing, etc.) -->
<GroveText
	content="Your [[bloom|posts]] live in your [[garden|blog]]."
	manifest={groveTermManifest}
/>

<!-- Silent text swap (non-interactive, default behavior) -->
<GroveTerm term="meadow" />

<!-- With leaf icon for Grove Mode hint -->
<GroveTerm term="meadow" icon />

Key Rules:

  • Never hardcode Grove terms in user-facing UI. Always use GroveTerm components.
  • Default is OFF for new visitors. Standard, familiar terminology first.
  • URLs stay as Grove terms (/porch, /garden) regardless of display mode.
  • Brand terms (Grove) and subscription tiers (Seedling/Sapling/Oak/Evergreen) always show as-is.
  • Use [[term]] syntax for data-driven content (FAQ items, pricing fineprint, feature lists).
  • Grove Mode store: groveModeStore from @autumnsgrove/lattice/ui/stores. Toggle lives in the footer.

See docs/grove-user-identity.md for the full identity language documentation and libs/engine/src/lib/ui/components/ui/groveterm/ for component source.


Glassmorphism Pattern

Glass effects create readability while revealing hints of background decoration.

The Layering Formula

Background (gradients, vines, nature)
    ↓
Decorative Elements (trees, clouds, particles)
    ↓
Glass Surface (translucent + blur)
    ↓
Content (text, cards, UI)

Glass Components

import {(Glass, GlassCard, GlassButton, GlassOverlay)} from '@lattice/ui/ui';

<!-- Container with glass effect -->
<Glass variant="tint" class="p-6 rounded-xl">
	<p>Readable text over busy backgrounds</p>
</Glass>

<!-- Card with glass styling -->
<GlassCard title="Settings" variant="default" hoverable>Content here</GlassCard>

<!-- Glass button -->
<GlassButton variant="accent">Subscribe</GlassButton>

Glass Variants

VariantUse CaseLight ModeDark Mode
surfaceHeaders, navbars95% white95% slate
tintText over backgrounds60% white50% slate
cardContent cards80% white70% slate
accentCallouts, highlights30% accent20% accent
overlayModal backdrops50% black60% black
mutedSubtle backgrounds40% white30% slate

CSS Utility Classes

<!-- Apply directly to any element -->
<div class="glass rounded-xl p-4">Basic glass</div>
<div class="glass-tint p-6">Text container</div>
<div class="glass-accent p-4">Highlighted section</div>
<nav class="glass-surface sticky top-0">Navbar</nav>

Key Pattern: Sticky Navigation

<nav
	class="sticky top-[73px] z-30 bg-white/80 dark:bg-slate-900/80 backdrop-blur-sm border-b border-divider"
>
	<!-- Navigation content -->
</nav>

Seasonal Theme System

Grove uses four seasons, each with distinct colors, weather effects, and moods.

Season Detection

import {season} from '$lib/stores/season'; const isSpring = $derived($season === 'spring'); const isAutumn
= $derived($season === 'autumn'); const isWinter = $derived($season === 'winter'); // Summer is the default
(no flag needed)

Color Palette System

Import from: @autumnsgrove/lattice/ui/nature or $lib/components/nature/palette

Core Palettes (Year-Round)
Accent colors: These palette hex values are for nature SVGs, illustrations, and brand use. For CSS accent-colored surfaces (buttons, links, highlights), use var(--grove-accent-*) tokens instead — the user's accent color may not be green. See the accent scale: var(--grove-accent) (solid), var(--grove-accent-dark) (hover), var(--grove-accent-N) (opacity tints, stops 5-80). Pre-commit hook enforces this.
import { greens, bark, earth, natural } from "@autumnsgrove/lattice/ui/nature";

// Greens - organized dark-to-light for atmospheric depth
// NOTE: Use these for nature components and brand illustrations.
// For accent-colored UI surfaces, use var(--grove-accent-*) instead.
greens.darkForest; // #0d4a1c - Background trees
greens.deepGreen; // #166534 - Mid-distance
greens.grove; // #16a34a - Grove brand primary
greens.meadow; // #22c55e - Standard foliage
greens.spring; // #4ade80 - Bright accent
greens.mint; // #86efac - Light accent
greens.pale; // #bbf7d0 - Foreground highlights

// Bark - warm wood tones
bark.darkBark; // #3d2817 - Oak, older trees
bark.bark; // #5d4037 - Standard trunk
bark.warmBark; // #6B4423 - Pine, cedar
bark.lightBark; // #8b6914 - Young trees

// Earth - ground elements
(earth.soil, earth.mud, earth.clay, earth.sand, earth.stone, earth.pebble, earth.slate);

// Natural - cream and off-whites
(natural.cream, natural.aspenBark, natural.bone, natural.mushroom, natural.birchWhite);
Spring Palettes
import {
	springFoliage,
	springSky,
	wildflowers,
	cherryBlossoms,
	cherryBlossomsPeak,
} from "@autumnsgrove/lattice/ui/nature";

// Spring Foliage - yellow-green new growth
springFoliage.sprout; // #65a30d - Distant new growth
springFoliage.newLeaf; // #84cc16 - Classic spring lime
springFoliage.freshGreen; // #a3e635 - Bright foreground
springFoliage.budding; // #bef264 - Pale new leaf
springFoliage.tender; // #d9f99d - Very pale

// Spring Sky
springSky.clear; // #7dd3fc - Clear morning
springSky.soft; // #bae6fd - Pale sky

// Wildflowers - unified meadow flower colors
wildflowers.buttercup; // #facc15 - Yellow
wildflowers.daffodil; // #fde047 - Pale yellow
wildflowers.crocus; // #a78bfa - Purple crocus
wildflowers.violet; // #8b5cf6 - Wild violets
wildflowers.purple; // #a855f7 - Lupine, thistle
wildflowers.lavender; // #c4b5fd - Distant masses
wildflowers.tulipPink; // #f9a8d4 - Pink tulips
wildflowers.tulipRed; // #fb7185 - Red tulips
wildflowers.white; // #fefefe - Daisies, trillium

// Cherry Blossoms - summer standard
cherryBlossoms.deep; // #db2777 - Dense centers
cherryBlossoms.standard; // #ec4899 - Standard blossom
cherryBlossoms.light; // #f472b6 - Light petals
cherryBlossoms.pale; // #f9a8d4 - Pale blossoms
cherryBlossoms.falling; // #fbcfe8 - Falling petals

// Cherry Blossoms Peak - vibrant spring (one shade brighter!)
cherryBlossomsPeak.deep; // #ec4899
cherryBlossomsPeak.standard; // #f472b6
cherryBlossomsPeak.light; // #f9a8d4
cherryBlossomsPeak.pale; // #fbcfe8
cherryBlossomsPeak.falling; // #fce7f3
Unified Flowers Palette (NEW!)

The flowers namespace consolidates all flower colors into one organized structure:

import { flowers } from "@autumnsgrove/lattice/ui/nature";

// Meadow wildflowers (yellows, purples, pinks, whites)
flowers.wildflower.buttercup; // #facc15 - Yellow
flowers.wildflower.daffodil; // #fde047 - Pale yellow
flowers.wildflower.crocus; // #a78bfa - Purple crocus
flowers.wildflower.violet; // #8b5cf6 - Wild violets
flowers.wildflower.purple; // #a855f7 - Lupine, thistle
flowers.wildflower.lavender; // #c4b5fd - Distant masses
flowers.wildflower.tulipPink; // #f9a8d4 - Pink tulips
flowers.wildflower.tulipRed; // #fb7185 - Red tulips
flowers.wildflower.white; // #fefefe - Daisies, trillium

// Cherry blossoms - standard summer
flowers.cherry.deep; // #db2777
flowers.cherry.standard; // #ec4899
flowers.cherry.light; // #f472b6
flowers.cherry.pale; // #f9a8d4
flowers.cherry.falling; // #fbcfe8

// Cherry blossoms at peak bloom - vibrant spring
flowers.cherryPeak.deep; // #ec4899
flowers.cherryPeak.standard; // #f472b6
flowers.cherryPeak.light; // #f9a8d4
flowers.cherryPeak.pale; // #fbcfe8
flowers.cherryPeak.falling; // #fce7f3

Use flowers.wildflower instead of accents.flower — the accents version is deprecated.

Autumn & Winter Palettes
import { autumn, autumnReds, winter } from "@autumnsgrove/lattice/ui/nature";

// Autumn - warm fall foliage (dark-to-light for depth)
autumn.rust; // #9a3412 - Deep background
autumn.ember; // #c2410c - Oak-like
autumn.pumpkin; // #ea580c - Maple mid-tones
autumn.amber; // #d97706 - Classic fall
autumn.gold; // #eab308 - Aspen/birch
autumn.honey; // #facc15 - Bright foreground
autumn.straw; // #fde047 - Pale dying leaves

// Autumn Reds - cherry/maple fall foliage
autumnReds.crimson; // #be123c - Deep maple
autumnReds.scarlet; // #e11d48 - Bright cherry
autumnReds.rose; // #f43f5e - Light autumn
autumnReds.coral; // #fb7185 - Pale accent

// Winter - frost, snow, ice + frosted evergreens
(winter.snow, winter.frost, winter.ice, winter.glacier);
(winter.frostedPine, winter.winterGreen, winter.coldSpruce);
(winter.winterSky, winter.twilight, winter.overcast);
(winter.bareBranch, winter.frostedBark, winter.coldWood);
(winter.hillDeep, winter.hillMid, winter.hillNear, winter.hillFront);
Accent Palettes
import { accents, wildflowers } from "@autumnsgrove/lattice/ui/nature";

// Mushrooms - fairy tale pops of color
(accents.mushroom.redCap, accents.mushroom.orangeCap, accents.mushroom.brownCap);
(accents.mushroom.spots, accents.mushroom.gill);

// Firefly - bioluminescence
(accents.firefly.glow, accents.firefly.warmGlow, accents.firefly.body);

// Berry - rich saturated
(accents.berry.ripe, accents.berry.elderberry, accents.berry.red);

// Water - cool blue spectrum
(accents.water.surface, accents.water.deep, accents.water.shallow, accents.water.lily);

// Sky - time of day
(accents.sky.dayLight, accents.sky.dayMid, accents.sky.sunset, accents.sky.night, accents.sky.star);

// Birds - species-specific colors
(accents.bird.cardinalRed, accents.bird.cardinalMask, accents.bird.cardinalBeak);
(accents.bird.chickadeeCap, accents.bird.chickadeeBody, accents.bird.chickadeeBelly);
(accents.bird.robinBody, accents.bird.robinBreast, accents.bird.robinBeak);
(accents.bird.bluebirdBody, accents.bird.bluebirdWing, accents.bird.bluebirdBreast);

// NOTE: accents.flower is deprecated - use flowers.wildflower instead
Seasonal Helper Functions
import {
	getSeasonalGreens,
	getCherryColors,
	isTreeBare,
	pickRandom,
	pickFrom,
} from "@autumnsgrove/lattice/ui/nature";

// Get foliage colors mapped to season
const foliage = getSeasonalGreens(season);
// spring → springFoliage colors
// summer → greens
// autumn → autumn palette
// winter → frosted evergreen colors

// Get cherry tree colors by season
const cherryColors = getCherryColors(season);
// spring → cherryBlossomsPeak (vibrant!)
// summer → cherryBlossoms (standard)
// autumn → autumnReds
// winter → null (bare tree)

// Check if deciduous tree is bare
if (isTreeBare("cherry", "winter")) {
	/* no foliage */
}

// Random color selection for natural variation
const randomGreen = pickRandom(greens);
const specificGreen = pickFrom(greens, ["grove", "meadow"]);
Deprecated Aliases (Still Work)
// These work but will be removed in v1.0:
import { spring, pinks, springBlossoms } from "@autumnsgrove/lattice/ui/nature";

// spring → use springFoliage, wildflowers, springSky instead
// pinks → use cherryBlossoms instead
// springBlossoms → use cherryBlossomsPeak instead
// accents.flower → use flowers.wildflower instead
Season Mood Summary
SeasonPrimary ColorsMood
SpringspringFoliage, cherryBlossomsPeak, wildflowersRenewal, hope
Summergreens, cherryBlossomsGrowth, warmth
Autumnautumn, autumnRedsHarvest, reflection
Winterwinter (frost, snow, frosted pines)Rest, stillness

Seasonal Weather Effects

<!-- Winter: Snowfall -->
{#if isWinter}
	<SnowfallLayer count={40} zIndex={5} opacity={{ min: 0.4, max: 0.8 }} spawnDelay={8} />
{/if}

<!-- Spring: Cherry blossom petals -->
{#if isSpring}
	<FallingPetalsLayer count={80} zIndex={100} opacity={{ min: 0.5, max: 0.9 }} />
{/if}

<!-- Autumn: Falling leaves (tied to trees) -->
{#if isAutumn}
	<FallingLeavesLayer
		trees={forestTrees}
		season={$season}
		minLeavesPerTree={2}
		maxLeavesPerTree={4}
	/>
{/if}

Seasonal Background Gradients

<main class="min-h-screen transition-colors duration-1000
  {isWinter ? 'bg-gradient-to-b from-slate-200 via-slate-100 to-slate-50 dark:from-slate-900 dark:via-slate-800 dark:to-slate-700' : ''}
  {isAutumn ? 'bg-gradient-to-b from-orange-100 via-amber-50 to-yellow-50 dark:from-slate-900 dark:via-amber-950 dark:to-orange-950' : ''}
  {isSpring ? 'bg-gradient-to-b from-pink-50 via-sky-50 to-lime-50 dark:from-slate-900 dark:via-pink-950 dark:to-lime-950' : ''}
  {/* Summer default */} 'bg-gradient-to-b from-sky-100 via-sky-50 to-emerald-50 dark:from-slate-900 dark:via-slate-800 dark:to-emerald-950'
">

When to Use Seasons

  • Roadmap pages — Show progress through seasonal metaphor
  • Story/about pages — Create atmosphere and emotional connection
  • Interactive demos — Let users toggle seasons (like /forest)
  • Help articles — Consider seasonal decor to break up long content
  • Anywhere you want magic — Use judgment based on page purpose

Randomized Forests

The forest should feel alive and different every visit.

Tree Generation Pattern

interface GeneratedTree {
	id: number;
	x: number; // percentage from left (5-93% to avoid edges)
	size: number; // base width in pixels
	aspectRatio: number; // height = size * aspectRatio (1.0-1.5 range)
	treeType: TreeType; // 'logo' | 'pine' | 'cherry' | 'aspen' | 'birch'
	opacity: number; // 0.5-0.9 for depth
	zIndex: number; // larger trees = higher z-index
}

// Aspect ratio creates natural height variation
const TREE_ASPECT_RATIO_RANGE = { min: 1.0, max: 1.5 };

function generateSectionTrees(count: number): GeneratedTree[] {
	const trees: GeneratedTree[] = [];
	const usedPositions: number[] = [];

	for (let i = 0; i < count; i++) {
		// Find non-overlapping position
		let x: number;
		let attempts = 0;
		do {
			x = 5 + Math.random() * 88;
			attempts++;
		} while (usedPositions.some((pos) => Math.abs(pos - x) < 8) && attempts < 20);
		usedPositions.push(x);

		const size = 80 + Math.random() * 80;
		const aspectRatio = 1.0 + Math.random() * 0.5;
		const opacity = 0.5 + Math.random() * 0.4;
		const zIndex = size > 130 ? 3 : size > 100 ? 2 : 1;

		trees.push({
			id: i,
			x,
			size,
			aspectRatio,
			treeType: pickRandom(treeTypes),
			opacity,
			zIndex,
		});
	}

	return trees.sort((a, b) => a.x - b.x);
}

Regeneration Timing

  • On mount — Trees generate once when page loads
  • On resize (significant) — Only if viewport bracket changes dramatically
  • Never on scroll — Keep forest stable during reading

Rendering Trees

{#each forestTrees as tree (tree.id)}
	<div
		class="absolute"
		style="
      left: {tree.x}%;
      bottom: 0;
      width: {tree.size}px;
      height: {tree.size * tree.aspectRatio}px;
      opacity: {tree.opacity};
      z-index: {tree.zIndex};
      transform: translateX(-50%);
    "
	>
		{#if tree.treeType === "logo"}
			<Logo class="w-full h-full" season={$season} animate />
		{:else if tree.treeType === "pine"}
			<TreePine class="w-full h-full" season={$season} animate />
		{:else if tree.treeType === "cherry"}
			<TreeCherry class="w-full h-full" season={$season} animate />
		{:else if tree.treeType === "aspen"}
			<TreeAspen class="w-full h-full" season={$season} animate />
		{:else if tree.treeType === "birch"}
			<TreeBirch class="w-full h-full" season={$season} animate />
		{/if}
	</div>
{/each}

Responsive Density

function calculateDensity(): number {
	const width = window.innerWidth;
	if (width < 768) return 1; // Mobile: base count
	if (width < 1024) return 1.3; // Tablet
	if (width < 1440) return 1.8; // Desktop
	if (width < 2560) return 2.5; // Large desktop
	return 3.5; // Ultrawide
}

Nature Components

Grove has an extensive library of decorative components. Explore with:

# Trees
ls landing/src/lib/components/trees/
ls landing/src/lib/components/nature/trees/

# Weather (seasonal particles)
ls landing/src/lib/components/nature/weather/

# Sky (clouds, stars, moon)
ls landing/src/lib/components/nature/sky/

# Botanical (leaves, petals, vines)
ls landing/src/lib/components/nature/botanical/

# Ground (flowers, grass, mushrooms)
ls landing/src/lib/components/nature/ground/

# Structural (lattice, lanterns, paths)
ls landing/src/lib/components/nature/structural/

# Birds (cardinals, robins, bluebirds)
ls landing/src/lib/components/nature/creatures/

Key Components

ComponentUseExample Props
LogoGrove tree, seasonalseason, animate, breathing
TreePineEvergreen, stays green in autumnseason, animate
TreeCherryBlossoms in spring, bare in winterseason, animate
TreeAspen / TreeBirchDeciduous, seasonal colorsseason, animate
CloudDecorative sky elementvariant, animate, speed, direction
SnowfallLayerWinter particlescount, opacity, spawnDelay
FallingPetalsLayerSpring cherry blossomscount, opacity, fallDuration
FallingLeavesLayerAutumn leaves (tied to trees)trees, season
Cardinal / ChickadeeWinter birdsfacing
Robin / BluebirdSpring birdsfacing
VineDecorative ivy/vinesvaries
LanternWarm glow pointsvaries

Birds by Season

<!-- Winter birds -->
{#if isWinter}
	<Cardinal facing="right" style="..." />
	<Chickadee facing="left" style="..." />
{/if}

<!-- Spring birds -->
{#if isSpring}
	<Robin facing="right" style="..." />
	<Bluebird facing="left" style="..." />
{/if}

Midnight Bloom Palette

For dreamy, far-future, mystical content. The tea shop that exists at the edge of tomorrow.

import { midnightBloom } from "$lib/components/nature/palette";

// Available colors:
midnightBloom.deepPlum; // #581c87 - Night sky depth
midnightBloom.purple; // #7c3aed - Soft purple glow
midnightBloom.violet; // #8b5cf6 - Lighter accent
midnightBloom.amber; // #f59e0b - Lantern warmth
midnightBloom.warmCream; // #fef3c7 - Tea steam, page glow
midnightBloom.softGold; // #fcd34d - Fairy lights

Midnight Bloom Styling

<section class="bg-gradient-to-b from-orange-950/50 via-purple-950 to-slate-950">
	<!-- Stars -->
	<StarCluster count={12} class="absolute top-12 left-[10%]" />

	<!-- Moon -->
	<Moon phase="waning-crescent" class="absolute top-20 right-[15%] w-16 h-16 opacity-60" />

	<!-- Fireflies -->
	<Firefly count={8} class="absolute inset-0" />

	<!-- Content with purple glass -->
	<blockquote class="bg-purple-900/30 backdrop-blur-sm border border-purple-700/30 rounded-lg p-6">
		<p class="text-purple-200 italic">Dreamy quote here...</p>
	</blockquote>
</section>

Icons: Lucide Only

NEVER use emojis. ALWAYS use Lucide icons.

import {(MapPin, Check, Leaf, Trees, Mail)} from '@lucide/svelte';

<!-- Good -->
<MapPin class="w-4 h-4" />
<Check class="w-5 h-5 text-green-500" />

<!-- Bad - NEVER do this -->
<!-- ❌ 🌱 📧 ✅ -->

Standardized Icon Mapping

Use these icons consistently across the project:

ConceptIconNotes
Navigation
HomeHome
AboutInfo
VisionTelescopeLooking forward
RoadmapMapJourney/direction
PricingHandCoinsMoney/currency
KnowledgeBookOpenLearning/docs
ForestTreesCommunity blogs
BlogPenLineWriting
Features
EmailMail
StorageHardDrive
ThemingPaletteCustomization
AuthenticationShieldCheckSecurity
CloudCloudRemote/serverless
SearchSearchCodeCode/advanced search
ArchivesArchiveBackups
UploadUpload
VideoVideo
CommentsMessagesSquareUser discussions
GitHubGithubExternal links to GitHub
States
SuccessCheckCompleted/valid
ErrorXFailed/close
LoadingLoader2With animate-spin
Content
PostsFileTextBlog posts
TagsTagCategorization
GrowthSproutGrove brand, new beginnings
HeartHeartLove, care
ExternalExternalLinkOpens new tab
LocationMapPinCurrent position
Phases
Coming SoonSeedlingSomething growing
RefinementGemPolish, quality
The DreamSparklesMystical (use sparingly!)
NightStarMidnight themes
Actions
Getting StartedCompassGuidance
What's NewMegaphoneAnnouncements
Next StepsLightbulbIdeas

Icon Mapping Tables in Files

Create a consistent icon map at the top of each component/page that uses icons:

// landing/src/lib/utils/icons.ts - Centralized icon registry
import {
	Mail,
	HardDrive,
	Palette,
	ShieldCheck,
	Cloud,
	SearchCode,
	Archive,
	Upload,
	MessagesSquare,
	Github,
	Check,
	X,
	Loader2,
	FileText,
	Tag,
	Sprout,
	Heart,
	ExternalLink,
	MapPin, // ... etc
} from "@lucide/svelte";

export const featureIcons = {
	mail: Mail,
	harddrive: HardDrive,
	palette: Palette,
	shieldcheck: ShieldCheck,
	cloud: Cloud,
	searchcode: SearchCode,
	// ... all mapped icons
} as const;

export const stateIcons = {
	success: Check,
	error: X,
	loading: Loader2,
} as const;

Then use in components:

<script lang="ts">
	import { featureIcons } from "$lib/utils/icons";
</script>

{#each features as feature}
	<svelte:component this={featureIcons[feature.icon]} class="w-5 h-5" />
{/each}

Benefits:

  • Single source of truth for all icons
  • Prevents undefined icon errors
  • Easy to maintain and extend
  • Reusable across entire project

Icon Usage Guidelines

  1. Always use icon maps - Never hardcode icon imports in every component
  2. Avoid overusing Sparkles - Reserve for truly mystical/magical contexts
  3. Be consistent - Use the same icon for the same concept everywhere
  4. Semantic meaning - Choose icons that convey meaning, not just decoration
  5. Export from central utility - Use landing/src/lib/utils/icons.ts for all icon sets

Icon Sizing

<!-- Inline with text -->
<span class="inline-flex items-center gap-1.5">
	<Leaf class="w-4 h-4" /> Feature name
</span>

<!-- Button icon -->
<button class="p-2">
	<Menu class="w-5 h-5" />
</button>

<!-- Large decorative -->
<Gem class="w-8 h-8 text-amber-400" />

Icon Composition (Building Block Pattern)

Philosophy: "The grove doesn't need to be drawn. It just needs to be arranged."

For creating custom logos, illustrations, or decorative elements, compose existing Lucide icons rather than drawing custom SVG from scratch. This ensures visual consistency with the icon system.

Why This Pattern?

  • Consistency — Icons match the Lucide aesthetic (24x24 grid, 2px strokes, round caps)
  • Minimal custom code — Let Lucide do the heavy lifting
  • Maintainable — Updating Lucide updates your compositions
  • MIT licensed — All paths come from open-source icons

How to Extract Lucide Paths

Lucide icons use a 24×24 viewBox with 2px strokes. Extract paths directly from source:

# Find icon paths in Lucide source
curl -s https://raw.githubusercontent.com/lucide-icons/lucide/main/icons/tree-pine.svg
# Look for the <path d="..." /> elements

Key Lucide icon paths for Grove compositions:

// TreePine - conifer silhouette
const treePine = {
	canopy:
		"m17 14 3 3.3a1 1 0 0 1-.7 1.7H4.7a1 1 0 0 1-.7-1.7L7 14h-.3a1 1 0 0 1-.7-1.7L9 9h-.2A1 1 0 0 1 8 7.3L12 3l4 4.3a1 1 0 0 1-.8 1.7H15l3 3.3a1 1 0 0 1-.7 1.7H17Z",
	trunk: "M12 22v-3",
};

// TreeDeciduous - deciduous/round tree
const treeDeciduous = {
	canopy:
		"M8 19a4 4 0 0 1-2.24-7.32A3.5 3.5 0 0 1 9 6.03V6a3 3 0 1 1 6 0v.04a3.5 3.5 0 0 1 3.24 5.65A4 4 0 0 1 16 19Z",
	trunk: "M12 19v3",
};

// Moon - crescent moon
const moon =
	"M20.985 12.486a9 9 0 1 1-9.473-9.472c.405-.022.617.46.402.803a6 6 0 0 0 8.268 8.268c.344-.215.825-.004.803.401";

// Flame - campfire/hearth
const flame =
	"M12 3q1 4 4 6.5t3 5.5a1 1 0 0 1-14 0 5 5 0 0 1 1-3 1 1 0 0 0 5 0c0-2-1.5-3-1.5-5q0-2 2.5-4";

Composing with SVG Transforms

Use <g transform="..."> to position, scale, and rotate icons:

<svg viewBox="0 0 48 32" fill="none">
	<!-- Left tree (larger, foreground) -->
	<g
		transform="translate(2, 4) scale(0.85)"
		stroke={color}
		stroke-width="2"
		stroke-linecap="round"
		stroke-linejoin="round"
	>
		<path d={treePine.canopy} />
		<path d={treePine.trunk} />
	</g>

	<!-- Right tree (smaller, background, tilted) -->
	<g
		transform="translate(20, 8) scale(0.65) rotate(-5, 12, 12)"
		stroke={color}
		stroke-width="2"
		stroke-linecap="round"
		stroke-linejoin="round"
		opacity="0.7"
	>
		<path d={treePine.canopy} />
		<path d={treePine.trunk} />
	</g>

	<!-- Add simple custom elements sparingly -->
	<circle cx="30" cy="10" r="1.5" fill={glowColor} opacity="0.8" />
	<!-- firefly -->
	<path d="M2 28h44" stroke={color} stroke-width="1.5" opacity="0.3" />
	<!-- ground -->
</svg>

Transform Cheatsheet

TransformEffectExample
translate(x, y)Move origintranslate(20, 8) moves icon right 20, down 8
scale(s)Uniform sizescale(0.65) makes icon 65% size
rotate(deg, cx, cy)Rotation around pointrotate(-5, 12, 12) tilts 5° around center
CombinedChain transformstranslate(20, 8) scale(0.65) rotate(-5, 12, 12)

Example: Grove Logo Compositions

See /landing/src/lib/components/logo-concepts/ for real implementations:

LogoComposition
LogoFireflyForestTreePine + TreeDeciduous + glowing circles
LogoGatheringHearthTwo trees angled toward center Flame
LogoStarlightPinesTwo TreePines + Moon + star circles
LogoShelterTwo TreePines forming archway + Moon
LogoWinterGroveTreePines + snow line accents

Guidelines

  1. Use Lucide paths as primary structure — Trees, moon, flame, etc.
  2. Custom SVG only for simple primitives — circles (fireflies), lines (ground, snow)
  3. Maintain Lucide styling — 2px strokes, round caps/joins, consistent opacity
  4. Create depth with opacity/scale — Larger = foreground (opacity 0.9), smaller = background (0.5-0.7)
  5. Keep viewBox aspect ratios reasonable — 40×32 or 48×32 for horizontal compositions

When to Use

  • Logos & branding — Compose icons into unique marks
  • Illustrations — Scene building (forest, sky, etc.)
  • Custom icons — When Lucide doesn't have exactly what you need
  • Seasonal variations — Same composition, different elements (snow, blossoms)

Mobile Considerations

Overflow Menu Pattern

Desktop navigation items that don't fit should go to a mobile sheet menu:

<!-- Mobile menu button (visible md:hidden) -->
<button onclick={() => (mobileMenuOpen = true)} class="md:hidden p-2">
	<Menu class="w-5 h-5" />
</button>

<!-- Sheet menu -->
<MobileMenu bind:open={mobileMenuOpen} onClose={() => (mobileMenuOpen = false)} />

Decorative Elements on Mobile

ElementMobile Treatment
TreesReduce count, simplify (density multiplier = 1)
ParticlesReduce count (40→20 snowflakes)
CloudsHide some, keep 2-3
Complex animationsReduce or disable
Touch targetsMinimum 44x44px

Performance Guidelines

<!-- Reduce particle counts on mobile -->
<SnowfallLayer count={isLargeScreen ? 100 : 40} ... />

<!-- Skip complex effects for reduced-motion -->
{#if !prefersReducedMotion}
	<FallingLeavesLayer ... />
{/if}

When to Use

PatternGood For
GlassmorphismText over backgrounds, navbars, cards, modals
Randomized forestsStory pages, about pages, visual sections
Seasonal themesRoadmaps, timelines, emotional storytelling
Midnight BloomFuture features, dreams, mystical content
Weather particlesHero sections, transitions between seasons
BirdsAdding life to forest scenes, seasonal indicators

When NOT to Use

PatternAvoid When
Heavy decorationData-dense pages, admin interfaces, forms
Particle effectsPerformance-critical pages, accessibility concerns
Seasonal colorsBrand-critical contexts needing consistent colors
Multiple glass layersCan cause blur performance issues
RandomizationContent that needs to match between sessions
Complex forestsMobile-first pages, simple informational content

Reference Pages

Study these for implementation patterns:

  • /forest — Full randomized forest with all seasons
  • /roadmap — Seasonal sections, progressive decoration, midnight bloom
  • /vision — Narrative page with glass callouts

OG Images (Social Previews)

Grove uses dynamic OG images for social media previews (Discord, Twitter, iMessage, etc.).

Architecture

OG images are generated by a separate Cloudflare Worker at og.grove.place due to WASM bundling limitations with SvelteKit + Cloudflare Pages.

grove.place/api/og?title=X
       ↓ 302 redirect
og.grove.place/?title=X
       ↓ workers-og
PNG image (1200×630)

API

GET https://og.grove.place/?title=X&subtitle=Y&accent=HEX
ParamDefaultDescription
title"Grove"Main title (max 100 chars)
subtitle"A place to Be."Subtitle (max 200 chars)
accent"16a34a"Hex color without # (forest green)

Adding OG to New Pages

Use the SEO component which handles OG meta tags:

<script>
	import SEO from "$lib/components/SEO.svelte";
</script>

<SEO
	title="Page Title"
	description="Page description for search engines"
	ogImage="/api/og?title=Page%20Title&subtitle=Custom%20subtitle"
/>

Files

  • services/og-worker/ — Standalone Worker (uses workers-og)
  • landing/src/routes/api/og/+server.ts — Proxy to og.grove.place
  • landing/src/lib/components/SEO.svelte — Meta tag management

Integration with Other Skills

When writing text for Grove UI (tooltips, buttons, onboarding, error messages), invoke the grove-documentation skill first. The voice should match the visuals.

Typical flow:

  1. Design the UI component/page
  2. Activate grove-documentation for any user-facing text
  3. Write content following Grove voice principles
  4. Return to visual implementation

Component Auditing with Showroom

Before verifying full pages, audit individual components. Showroom renders a single .svelte component in isolation, runs design compliance checks (color tokens, spacing grid, typography, focus styles, heading hierarchy), and diffs against visual baselines. It catches issues that full-page Glimpse captures miss.

# Audit a component in isolation
uv run --project tools/glimpse glimpse showroom \
  libs/engine/src/lib/ui/components/primitives/button/button.svelte

# Scaffold a fixture for a new component (generates .showroom.ts with scenarios)
uv run --project tools/glimpse glimpse showroom \
  libs/engine/src/lib/ui/components/ui/MyComponent.svelte --scaffold

# Audit with specific scenario and theme
uv run --project tools/glimpse glimpse showroom \
  libs/engine/src/lib/ui/components/ui/MyComponent.svelte \
  --scenario error --theme dark

# Update visual baselines after intentional design changes
uv run --project tools/glimpse glimpse showroom \
  libs/engine/src/lib/ui/components/ui/MyComponent.svelte --update-baselines

The component gate: Every component you build or modify must pass glimpse showroom before you move to page-level Glimpse verification. Fix all compliance violations first.


Visual Verification with Glimpse

Before shipping any Grove page, look at it. CI passing is not the same as looking correct. Use Glimpse to capture the rendered page and review it yourself:

# Capture the page with Grove theme injection
uv run --project tools/glimpse glimpse capture http://localhost:5173/[page] \
  --season autumn --theme dark --logs

# Verify all season × theme combos
uv run --project tools/glimpse glimpse matrix http://localhost:5173/[page]

# Interactive browse — click around, verify navigation and flows
uv run --project tools/glimpse glimpse browse http://localhost:5173/[page] \
  --do "click links, scroll down, interact with elements" --screenshot-each --logs

The iterate loop: Capture → review → fix → capture again. Repeat until the page matches the Grove aesthetic. Don't ship what you haven't seen.


Quick Checklist

Before shipping a Grove page:

  • Showroom: Every built/modified component passes glimpse showroom with no compliance violations
  • Glimpse: Page captured and visually reviewed
  • Glimpse: All target seasons render correctly (use matrix)
  • Glimpse: No console errors in --logs output
  • Glass effects used for text readability over busy backgrounds?
  • Lucide icons, no emojis?
  • Mobile overflow menu for navigation items?
  • Decorative elements respect prefers-reduced-motion?
  • Touch targets at least 44x44px?
  • Seasonal colors match the page's emotional tone?
  • Trees randomized with proper spacing (8% minimum gap)?
  • Dark mode supported with appropriate glass variants?
  • User-facing text follows Grove voice (see grove-documentation)?
  • Grove terminology uses GroveTerm components (not hardcoded)?
  • Data-driven content uses [[term]] syntax with GroveText?

平台分布

Codex

36.66%
按下载量换算216

Claude

31.35%
按下载量换算184

Cursor

18.48%
按下载量换算109

Gemini CLI

9.69%
按下载量换算57

安全审计

Gen Agent Trust Hub

通过

Socket

通过

Snyk

通过

权限和风险

只读

该 Skill 主要提供规则、说明或参考内容,本身偏只读;真正读写文件、联网或执行命令仍取决于宿主 Agent 的任务。

安装前确认

本站仅展示第三方公开信息,不托管安装包,不提供自动安装或运行环境。安装前应自行审查源码、依赖和命令行为。目前只有一个公开来源,建议同时核对源仓库。

继续浏览同类 Skills