---
name: frontend-layout-fixer
description: This skill should be used when identifying and fixing frontend layout issues (clipping, spacing, overflow, RTL text problems) by analyzing DOM and CSS structure and proposing minimal, scoped CSS patches. Triggers on layout bugs, text clipping, overflow issues, spacing problems, and when vanilla Claude cannot pinpoint which CSS selector to modify from a screenshot alone.
---
# Frontend Layout Fixer - Unified Bug Fixer
## Overview
A **unified frontend debugging toolkit** that fixes ALL frontend issues with structured patch recommendations, clear diagnostics, and testing checklists.
```
┌─────────────────────────────────────────────────────────┐
│ UNIFIED FRONTEND SKILL │
├─────────────────────────────────────────────────────────┤
│ Category 1: State Hydration (phantom/stale data) │
│ Category 2: Data Persistence (vanishing data) │
│ Category 3: CSS Layout (shadows, overflow, clipping) │
│ Category 4: Badge & Label Styling (alignment, sizing) │
│ Category 5: Text Overflow (truncation, wrapping) │
└─────────────────────────────────────────────────────────┘
```
## When to Use This Skill
### Category 1: State Hydration Bugs
- Phantom duplicate items appearing on load
- Stale data showing before fresh data loads
- Data appearing then vanishing
- Different data on different page loads
- Key prop warnings in React/Vue lists
### Category 2: Data Persistence Bugs
- Data appears in UI but vanishes after refresh
- localStorage/sessionStorage out of sync with UI
- API updates but cache not invalidated
- Multiple data sources conflicting
### Category 3: CSS Layout Bugs
- Text clipped at top/bottom of containers
- Box shadow invisible or cut off
- Content overflows parent element
- RTL (Hebrew, Arabic) text display problems
- Fixed-height containers cutting off content
- Flex/grid layout alignment issues
### Category 4: Badge & Label Styling Bugs
- Badge text not vertically centered
- Icon floating around text
- Label color too light (contrast issue)
- Badge size inconsistent
- RTL badge positioning issues
### Category 5: Text Overflow Bugs
- Text truncated with "..." unnecessarily
- Long text forced to single line
- Line-clamp cutting off needed content
- Text not wrapping in flex container
---
## Core Workflow
### Step 1: Gather Input
```json
{
"javascript": "// Component code (for state/persistence bugs)",
"html": "",
"css": "/* The relevant CSS rules */",
"issue_description": "Clear description of the bug",
"context": {
"project_type": "vue",
"bug_category": "auto",
"storage_type": "localStorage",
"layout_direction": "ltr",
"target_selectors": [".card", ".card-title"],
"constraints": ["Do not change colors"],
"viewport_width": 360,
"viewport_height": 800
}
}
```
### Step 2: Auto-Detect Bug Category
The skill automatically identifies bug category from:
- Code structure (JavaScript → state/persistence)
- Description keywords (shadow/overflow → CSS)
- HTML/CSS provided (visual issues)
### Step 3: Generate Patches
```json
{
"skill_type": "frontend",
"bug_category": "state|persistence|css_layout|badge|text_overflow",
"diagnosis": {
"severity": "critical|high|medium|low",
"root_causes": ["cause 1", "cause 2"],
"category_details": {}
},
"explanation": "Detailed explanation of what's wrong",
"fixes": {
"javascript_patches": [
{ "location": "...", "old": "...", "new": "...", "rationale": "..." }
],
"css_patches": [
{ "selector": "...", "old": "...", "new": "...", "rationale": "..." }
]
},
"testing_checklist": ["Step 1", "Step 2", "Step 3"],
"prevention": "How to prevent this in future"
}
```
---
## Bug Category Details
---
### Category 1: State Hydration Bugs
**Symptoms:**
- Phantom duplicate items appearing
- Stale data showing before fresh data loads
- Data appearing then vanishing
- Different data showing on different loads
**Root Causes:**
- useState() initialized with cached data
- useEffect() not clearing old state
- Multiple component mounts
- Race conditions in async loading
- Key prop using array index instead of ID
**Detection Patterns:**
```javascript
// ❌ BAD: Initializing state with localStorage
const [tasks, setTasks] = useState(
JSON.parse(localStorage.getItem('tasks') || '[]')
);
// ✅ GOOD: Empty initial state, load in useEffect
const [tasks, setTasks] = useState([]);
useEffect(() => {
fetch('/api/tasks').then(r => r.json()).then(setTasks);
}, []);
```
```javascript
// ❌ BAD: Array index as key
{tasks.map((task, i) =>
Task description