Ink.js (React for CLI) design and implementation guide. Use when: (1) Creating or modifying Ink.js components (2) Implementing Ink-specific hooks (useInput, useApp, useFocus) (3) Handling emoji/icon width issues (string-width workarounds) (4) Building terminal-responsive layouts (5) Managing multi-screen navigation (6) Implementing animations (spinners, progress bars) (7) Optimizing performance (React.memo, useMemo) (8) Handling keyboard input and shortcuts (9) Testing CLI UI (ink-testing-library)
View on GitHubFebruary 1, 2026
Select agents to install to:
npx add-skill https://github.com/akiojin/skills/blob/main/cli-design/skills/inkjs-design/SKILL.md -a claude-code --skill inkjs-designInstallation paths:
.claude/skills/inkjs-design/# Ink.js Design Comprehensive guide for building terminal UIs with Ink.js (React for CLI). ## Quick Start ### Creating a New Component 1. Determine component type: Screen / Part / Common 2. Reference [component-patterns.md](references/component-patterns.md) for similar patterns 3. Add type definitions 4. Implement component 5. Write tests ### Common Issues & Solutions | Issue | Reference | |-------|-----------| | Emoji width misalignment | [ink-gotchas.md](references/ink-gotchas.md#icon-emoji-width) | | Ctrl+C called twice | [ink-gotchas.md](references/ink-gotchas.md#ctrl-c-handling) | | useInput conflicts | [ink-gotchas.md](references/ink-gotchas.md#useinput-conflicts) | | Layout breaking | [responsive-layout.md](references/responsive-layout.md) | | Screen navigation | [multi-screen-navigation.md](references/multi-screen-navigation.md) | ## Directory Conventions ``` src/cli/ui/ ├── components/ │ ├── App.tsx # Root component with screen management │ ├── common/ # Common input components (Select, Input) │ ├── parts/ # Reusable UI parts (Header, Footer) │ └── screens/ # Full-screen components ├── hooks/ # Custom hooks ├── utils/ # Utility functions └── types.ts # Type definitions ``` ## Component Classification ### Screen (Full-page views) - Represents a complete screen/page - Handles keyboard input via `useInput` - Implements Header/Content/Footer layout - Manages screen-level state ### Part (Reusable elements) - Reusable UI building blocks - Optimized with `React.memo` - Stateless/pure components preferred - Accept configuration via props ### Common (Input components) - Basic input components - Support both controlled and uncontrolled modes - Handle focus management - Provide consistent UX ## Essential Patterns ### 1. Icon Width Override Fix string-width v8 emoji width calculation issues: ```typescript const WIDTH_OVERRIDES: Record<strin