--- name: favicon description: Generate a complete set of favicons from a source image and update HTML. Use when setting up favicons for a web project. argument-hint: [path to source image] --- Generate a complete set of favicons from the source image at `$1` and update the project's HTML with the appropriate link tags. ## Prerequisites First, verify ImageMagick v7+ is installed by running: ```bash which magick ``` If not found, stop and instruct the user to install it: - **macOS**: `brew install imagemagick` - **Linux**: `sudo apt install imagemagick` ## Step 1: Validate Source Image 1. Verify the source image exists at the provided path: `$1` 2. Check the file extension is a supported format (PNG, JPG, JPEG, SVG, WEBP, GIF) 3. If the file doesn't exist or isn't a valid image format, report the error and stop Note whether the source is an SVG file - if so, it will also be copied as `favicon.svg`. ## Step 2: Detect Project Type and Static Assets Directory Detect the project type and determine where static assets should be placed. Check in this order: | Framework | Detection | Static Assets Directory | |-----------|-----------|------------------------| | **Rails** | `config/routes.rb` exists | `public/` | | **Next.js** | `next.config.*` exists | `public/` | | **Gatsby** | `gatsby-config.*` exists | `static/` | | **SvelteKit** | `svelte.config.*` exists | `static/` | | **Astro** | `astro.config.*` exists | `public/` | | **Hugo** | `hugo.toml` or `config.toml` with Hugo markers | `static/` | | **Jekyll** | `_config.yml` with Jekyll markers | Root directory (same as `index.html`) | | **Vite** | `vite.config.*` exists | `public/` | | **Create React App** | `package.json` has `react-scripts` dependency | `public/` | | **Vue CLI** | `vue.config.*` exists | `public/` | | **Angular** | `angular.json` exists | `src/assets/` | | **Eleventy** | `.eleventy.js` or `eleventy.config.*` exists | Check `_site` output or root | | **Static HTML** | `index.html` in root | Same directory as `index.html` | **Important**: If existing favicon files are found (e.g., `favicon.ico`, `apple-touch-icon.png`), use their location as the target directory regardless of framework detection. Report the detected project type and the static assets directory that will be used. **When in doubt, ask**: If you are not 100% confident about where static assets should be placed (e.g., ambiguous project structure, multiple potential locations, unfamiliar framework), use `AskUserQuestionTool` to confirm the target directory before proceeding. It's better to ask than to put files in the wrong place. ## Step 3: Determine App Name Find the app name from these sources (in priority order): 1. **Existing `site.webmanifest`** - Check the detected static assets directory for an existing manifest and extract the `name` field 2. **`package.json`** - Extract the `name` field if it exists 3. **Rails `config/application.rb`** - Extract the module name (e.g., `module MyApp` → "MyApp") 4. **Directory name** - Use the current working directory name as fallback Convert the name to title case if needed (e.g., "my-app" → "My App"). ## Step 4: Ensure Static Assets Directory Exists Check if the detected static assets directory exists. If not, create it. ## Step 5: Generate Favicon Files Run these ImageMagick commands to generate all favicon files. Replace `[STATIC_DIR]` with the detected static assets directory from Step 2. ### favicon.ico (multi-resolution: 16x16, 32x32, 48x48) ```bash magick "$1" \ \( -clone 0 -resize 16x16 \) \ \( -clone 0 -resize 32x32 \) \ \( -clone 0 -resize 48x48 \) \ -delete 0 -alpha on -background none \ [STATIC_DIR]/favicon.ico ``` ### favicon-96x96.png ```bash magick "$1" -resize 96x96 -background none -alpha on [STATIC_DIR]/favicon-96x96.png ``` ### apple-touch-icon.png (180x180) ```bash magick "$1" -resize 180x180 -background none -alpha on [STATIC_DIR]/apple-touch-icon.png ``` ### web-app-manifest-192x192.png ```bash magick "$1" -resize 192x192 -background none -alpha on [STATIC_DIR]/web-app-manifest-192x192.png ``` ### web-app-manifest-512x512.png ```bash magick "$1" -resize 512x512 -background none -alpha on [STATIC_DIR]/web-app-manifest-512x512.png ``` ### favicon.svg (only if source is SVG) If the source file has a `.svg` extension, copy it: ```bash cp "$1" [STATIC_DIR]/favicon.svg ``` ## Step 6: Create/Update site.webmanifest Create or update `[STATIC_DIR]/site.webmanifest` with this content (substitute the detected app name): ```json { "name": "[APP_NAME]", "short_name": "[APP_NAME]", "icons": [ { "src": "/web-app-manifest-192x192.png", "sizes": "192x192", "type": "image/png", "purpose": "maskable" }, { "src": "/web-app-manifest-512x512.png", "sizes": "512x512", "type": "image/png", "purpose": "maskable" } ], "theme_color": "#ffffff", "background_color": "#ffffff", "display": "standalone" } ``` If `site.webmanifest` already exists in the static directory, preserve the existing `theme_color`, `background_color`, and `display` values while updating the `name`, `short_name`, and `icons` array. ## Step 7: Update HTML/Layout Files Based on the detected project type, update the appropriate file. Adjust the `href` paths based on where the static assets directory is relative to the web root: - If static files are in `public/` or `static/` and served from root → use `/favicon.ico` - If static files are in `src/assets/` → use `/assets/favicon.ico` - If static files are in the same directory as HTML → use `./favicon.ico` or just `favicon.ico` ### For Rails Projects Edit `app/views/layouts/application.html.erb`. Find the `
` section and add/replace favicon-related tags with: ```html ``` **Important**: - If the source was NOT an SVG, omit the `` line - Remove any existing `` section, after `` and `` if present ### For Next.js Projects Edit the detected layout file (`app/layout.tsx` or `src/app/layout.tsx`). Update or add the `metadata` export to include icons configuration: ```typescript export const metadata: Metadata = { // ... keep existing metadata fields icons: { icon: [ { url: '/favicon.ico' }, { url: '/favicon-96x96.png', sizes: '96x96', type: 'image/png' }, { url: '/favicon.svg', type: 'image/svg+xml' }, ], shortcut: '/favicon.ico', apple: '/apple-touch-icon.png', }, manifest: '/site.webmanifest', appleWebApp: { title: '[APP_NAME]', }, }; ``` **Important**: - If the source was NOT an SVG, omit the `{ url: '/favicon.svg', type: 'image/svg+xml' }` entry from the icon array - If metadata export doesn't exist, create it with just the icons-related fields - If metadata export exists, merge the icons configuration with existing fields ### For Static HTML Projects Edit the detected `index.html` file. Add the same HTML as Rails within the `` section. ### If No Project Detected Skip HTML updates and inform the user they need to manually add the following to their HTML ``: ```html ``` ## Step 8: Summary Report completion with: - Detected project type and framework - Static assets directory used - List of files generated - App name used in manifest and HTML - Layout file updated (or note if manual update is needed) - Note if any existing files were overwritten ## Error Handling - If ImageMagick is not installed, provide installation instructions and stop - If the source image doesn't exist, report the exact path that was tried and stop - If ImageMagick commands fail, report the specific error message - If the layout file cannot be found for HTML updates, generate files anyway and instruct on manual HTML addition