oh-my-codex-cli 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (292) hide show
  1. package/.agent/skills/agent-kb/HOW_TO_USE.md +428 -0
  2. package/.agent/skills/agent-kb/README.md +46 -0
  3. package/.agent/skills/agent-kb/SKILL.md +128 -0
  4. package/.agent/skills/agent-kb/references/intelligent-analysis-explained.md +333 -0
  5. package/.agent/skills/agent-kb/references/query-optimization.md +225 -0
  6. package/.agent/skills/aireview/SKILL.md +704 -0
  7. package/.agent/skills/analyze/SKILL.md +81 -0
  8. package/.agent/skills/architect-planner/HOW_TO_USE.md +238 -0
  9. package/.agent/skills/architect-planner/README.md +41 -0
  10. package/.agent/skills/architect-planner/SKILL.md +539 -0
  11. package/.agent/skills/auto-mbti/SKILL.md +291 -0
  12. package/.agent/skills/autopilot/SKILL.md +222 -0
  13. package/.agent/skills/backend-patterns/SKILL.md +602 -0
  14. package/.agent/skills/bdd-generator/README.md +78 -0
  15. package/.agent/skills/bdd-generator/SKILL.md +436 -0
  16. package/.agent/skills/brainstorming/HOW_TO_USE.md +289 -0
  17. package/.agent/skills/brainstorming/README.md +41 -0
  18. package/.agent/skills/brainstorming/SKILL.md +165 -0
  19. package/.agent/skills/build-fix/SKILL.md +190 -0
  20. package/.agent/skills/cancel/SKILL.md +658 -0
  21. package/.agent/skills/checkpoint/SKILL.md +94 -0
  22. package/.agent/skills/code-review/SKILL.md +273 -0
  23. package/.agent/skills/coding-standards/SKILL.md +535 -0
  24. package/.agent/skills/conductor/SKILL.md +128 -0
  25. package/.agent/skills/conductor/commands/conductor/implement.toml +358 -0
  26. package/.agent/skills/conductor/commands/conductor/newTrack.toml +142 -0
  27. package/.agent/skills/conductor/commands/conductor/revert.toml +123 -0
  28. package/.agent/skills/conductor/commands/conductor/setup.toml +429 -0
  29. package/.agent/skills/conductor/commands/conductor/status.toml +57 -0
  30. package/.agent/skills/conductor/scripts/install.sh +89 -0
  31. package/.agent/skills/conductor/templates/code_styleguides/csharp.md +115 -0
  32. package/.agent/skills/conductor/templates/code_styleguides/dart.md +238 -0
  33. package/.agent/skills/conductor/templates/code_styleguides/general.md +23 -0
  34. package/.agent/skills/conductor/templates/code_styleguides/go.md +48 -0
  35. package/.agent/skills/conductor/templates/code_styleguides/html-css.md +49 -0
  36. package/.agent/skills/conductor/templates/code_styleguides/javascript.md +51 -0
  37. package/.agent/skills/conductor/templates/code_styleguides/python.md +37 -0
  38. package/.agent/skills/conductor/templates/code_styleguides/typescript.md +43 -0
  39. package/.agent/skills/conductor/templates/rules/README.md +23 -0
  40. package/.agent/skills/conductor/templates/rules/agents.md +49 -0
  41. package/.agent/skills/conductor/templates/rules/coding-style.md +70 -0
  42. package/.agent/skills/conductor/templates/rules/dev.md +20 -0
  43. package/.agent/skills/conductor/templates/rules/git-workflow.md +45 -0
  44. package/.agent/skills/conductor/templates/rules/hooks.md +6 -0
  45. package/.agent/skills/conductor/templates/rules/patterns.md +55 -0
  46. package/.agent/skills/conductor/templates/rules/performance.md +47 -0
  47. package/.agent/skills/conductor/templates/rules/research.md +26 -0
  48. package/.agent/skills/conductor/templates/rules/review.md +22 -0
  49. package/.agent/skills/conductor/templates/rules/security.md +36 -0
  50. package/.agent/skills/conductor/templates/rules/testing.md +30 -0
  51. package/.agent/skills/conductor/templates/workflow.md +333 -0
  52. package/.agent/skills/consensus/HOW_TO_USE.md +191 -0
  53. package/.agent/skills/consensus/README.md +41 -0
  54. package/.agent/skills/consensus/SKILL.md +317 -0
  55. package/.agent/skills/content-research-writer/SKILL.md +537 -0
  56. package/.agent/skills/debug-analysis/SKILL.md +331 -0
  57. package/.agent/skills/deepinit/SKILL.md +347 -0
  58. package/.agent/skills/deepsearch/SKILL.md +56 -0
  59. package/.agent/skills/doctor/SKILL.md +158 -0
  60. package/.agent/skills/drawio/EXAMPLES.md +382 -0
  61. package/.agent/skills/drawio/QUICK_START.md +237 -0
  62. package/.agent/skills/drawio/README.md +315 -0
  63. package/.agent/skills/drawio/SETUP_GUIDE.md +254 -0
  64. package/.agent/skills/drawio/SKILL.md +1176 -0
  65. package/.agent/skills/e2e/SKILL.md +396 -0
  66. package/.agent/skills/ecomode/SKILL.md +160 -0
  67. package/.agent/skills/electron-driver/SKILL.md +144 -0
  68. package/.agent/skills/electron-driver/scripts/driver-template.js +71 -0
  69. package/.agent/skills/eval/SKILL.md +140 -0
  70. package/.agent/skills/eval-harness/SKILL.md +242 -0
  71. package/.agent/skills/evolve/SKILL.md +213 -0
  72. package/.agent/skills/frontend-design/SKILL.md +42 -0
  73. package/.agent/skills/frontend-patterns/SKILL.md +646 -0
  74. package/.agent/skills/frontend-ui-ux/SKILL.md +70 -0
  75. package/.agent/skills/git-master/SKILL.md +75 -0
  76. package/.agent/skills/help/SKILL.md +89 -0
  77. package/.agent/skills/iterative-retrieval/SKILL.md +217 -0
  78. package/.agent/skills/local-skills-setup/SKILL.md +483 -0
  79. package/.agent/skills/log-analyzer/SKILL.md +187 -0
  80. package/.agent/skills/mcp-setup/SKILL.md +226 -0
  81. package/.agent/skills/multi-model-research/HOW_TO_USE.md +614 -0
  82. package/.agent/skills/multi-model-research/README.md +233 -0
  83. package/.agent/skills/multi-model-research/SKILL.md +541 -0
  84. package/.agent/skills/multi-model-research/references/troubleshooting.md +415 -0
  85. package/.agent/skills/note/SKILL.md +80 -0
  86. package/.agent/skills/omc-setup/SKILL.md +219 -0
  87. package/.agent/skills/orchestrate/SKILL.md +620 -0
  88. package/.agent/skills/patent-workflow/IMPLEMENTATION_SUMMARY.md +500 -0
  89. package/.agent/skills/patent-workflow/README.md +455 -0
  90. package/.agent/skills/patent-workflow/SKILL.md +1036 -0
  91. package/.agent/skills/patent-workflow/tools/irr_checker.py +260 -0
  92. package/.agent/skills/patent-workflow/tools/sample_terminology.json +49 -0
  93. package/.agent/skills/patent-workflow/tools/term_checker.py +355 -0
  94. package/.agent/skills/pattern-recognition/SKILL.md +792 -0
  95. package/.agent/skills/pipeline/SKILL.md +448 -0
  96. package/.agent/skills/plan/SKILL.md +309 -0
  97. package/.agent/skills/planning-methodology/SKILL.md +370 -0
  98. package/.agent/skills/planning-with-files/SKILL.md +210 -0
  99. package/.agent/skills/planning-with-files/examples.md +202 -0
  100. package/.agent/skills/planning-with-files/reference.md +218 -0
  101. package/.agent/skills/planning-with-files/scripts/check-complete.ps1 +42 -0
  102. package/.agent/skills/planning-with-files/scripts/check-complete.sh +44 -0
  103. package/.agent/skills/planning-with-files/scripts/init-session.ps1 +120 -0
  104. package/.agent/skills/planning-with-files/scripts/init-session.sh +120 -0
  105. package/.agent/skills/planning-with-files/scripts/session-catchup.py +208 -0
  106. package/.agent/skills/planning-with-files/templates/findings.md +95 -0
  107. package/.agent/skills/planning-with-files/templates/progress.md +114 -0
  108. package/.agent/skills/planning-with-files/templates/task_plan.md +132 -0
  109. package/.agent/skills/project-analyze/CLAUDE.md +18 -0
  110. package/.agent/skills/project-analyze/HOW_TO_USE.md +145 -0
  111. package/.agent/skills/project-analyze/README.md +42 -0
  112. package/.agent/skills/project-analyze/SKILL.md +289 -0
  113. package/.agent/skills/project-analyze/SKILL.md.backup +287 -0
  114. package/.agent/skills/project-analyze/SKILL.md.backup_20260105_093646 +287 -0
  115. package/.agent/skills/project-analyze/assets/analysis-report-template.md +433 -0
  116. package/.agent/skills/project-analyze/references/analysis-patterns.md +422 -0
  117. package/.agent/skills/project-analyze/references/projectmind-explained.md +535 -0
  118. package/.agent/skills/project-session-manager/SKILL.md +428 -0
  119. package/.agent/skills/project-session-manager/lib/config.sh +86 -0
  120. package/.agent/skills/project-session-manager/lib/parse.sh +121 -0
  121. package/.agent/skills/project-session-manager/lib/session.sh +132 -0
  122. package/.agent/skills/project-session-manager/lib/tmux.sh +103 -0
  123. package/.agent/skills/project-session-manager/lib/worktree.sh +171 -0
  124. package/.agent/skills/project-session-manager/psm.sh +629 -0
  125. package/.agent/skills/project-session-manager/templates/feature.md +56 -0
  126. package/.agent/skills/project-session-manager/templates/issue-fix.md +57 -0
  127. package/.agent/skills/project-session-manager/templates/pr-review.md +65 -0
  128. package/.agent/skills/project-session-manager/templates/projects.json +19 -0
  129. package/.agent/skills/quality-check/HOW_TO_USE.md +171 -0
  130. package/.agent/skills/quality-check/README.md +50 -0
  131. package/.agent/skills/quality-check/SKILL.md +240 -0
  132. package/.agent/skills/quality-check/SKILL.md.backup +238 -0
  133. package/.agent/skills/quality-check/SKILL.md.backup_20260105_093646 +238 -0
  134. package/.agent/skills/quality-check/assets/quality-report-template.md +437 -0
  135. package/.agent/skills/quality-check/references/refactoring-patterns.md +550 -0
  136. package/.agent/skills/quality-check/references/scoring-criteria.md +454 -0
  137. package/.agent/skills/quality-validation/SKILL.md +519 -0
  138. package/.agent/skills/quality-validation/SKILL.md.backup +573 -0
  139. package/.agent/skills/quality-validation/SKILL.md.backup_20260105_093646 +573 -0
  140. package/.agent/skills/ralph/SKILL.md +236 -0
  141. package/.agent/skills/ralph-init/SKILL.md +78 -0
  142. package/.agent/skills/ralplan/SKILL.md +58 -0
  143. package/.agent/skills/refactor-clean/SKILL.md +49 -0
  144. package/.agent/skills/release/SKILL.md +84 -0
  145. package/.agent/skills/research/SKILL.md +526 -0
  146. package/.agent/skills/research-methodology/SKILL.md +268 -0
  147. package/.agent/skills/review/SKILL.md +53 -0
  148. package/.agent/skills/security-review/SKILL.md +509 -0
  149. package/.agent/skills/security-review/cloud-infrastructure-security.md +361 -0
  150. package/.agent/skills/setup-pm/SKILL.md +102 -0
  151. package/.agent/skills/skill/SKILL.md +424 -0
  152. package/.agent/skills/skill-create/SKILL.md +209 -0
  153. package/.agent/skills/skill-debugger/HOW_TO_USE.md +244 -0
  154. package/.agent/skills/skill-debugger/README.md +44 -0
  155. package/.agent/skills/skill-debugger/SKILL.md +326 -0
  156. package/.agent/skills/skill-debugger/diagnostic_checklist.md +115 -0
  157. package/.agent/skills/skill-development/SKILL.md +661 -0
  158. package/.agent/skills/skill-development/references/skill-creator-original.md +209 -0
  159. package/.agent/skills/skill-doc-generator/README.md +37 -0
  160. package/.agent/skills/skill-doc-generator/SKILL.md +331 -0
  161. package/.agent/skills/skill-quality-analyzer/HOW_TO_USE.md +243 -0
  162. package/.agent/skills/skill-quality-analyzer/README.md +61 -0
  163. package/.agent/skills/skill-quality-analyzer/SKILL.md +247 -0
  164. package/.agent/skills/skill-quality-analyzer/analyzer.py +209 -0
  165. package/.agent/skills/skill-quality-analyzer/expected_output.json +81 -0
  166. package/.agent/skills/skill-quality-analyzer/sample_input.json +9 -0
  167. package/.agent/skills/skill-tester/README.md +46 -0
  168. package/.agent/skills/skill-tester/SKILL.md +345 -0
  169. package/.agent/skills/start-dev/SKILL.md +701 -0
  170. package/.agent/skills/swarm/SKILL.md +691 -0
  171. package/.agent/skills/task-kb-lookup/SKILL.md +211 -0
  172. package/.agent/skills/task-kb-record/SKILL.md +417 -0
  173. package/.agent/skills/tdd/SKILL.md +446 -0
  174. package/.agent/skills/tdd-generator/DEMO.md +516 -0
  175. package/.agent/skills/tdd-generator/README.md +89 -0
  176. package/.agent/skills/tdd-generator/SKILL.md +278 -0
  177. package/.agent/skills/tdd-workflow/SKILL.md +424 -0
  178. package/.agent/skills/test-coverage/SKILL.md +48 -0
  179. package/.agent/skills/thinkdeep/HOW_TO_USE.md +183 -0
  180. package/.agent/skills/thinkdeep/README.md +41 -0
  181. package/.agent/skills/thinkdeep/SKILL.md +343 -0
  182. package/.agent/skills/ui-ux-pro-max/SKILL.md +228 -0
  183. package/.agent/skills/ui-ux-pro-max/data/charts.csv +26 -0
  184. package/.agent/skills/ui-ux-pro-max/data/colors.csv +97 -0
  185. package/.agent/skills/ui-ux-pro-max/data/landing.csv +31 -0
  186. package/.agent/skills/ui-ux-pro-max/data/products.csv +97 -0
  187. package/.agent/skills/ui-ux-pro-max/data/prompts.csv +24 -0
  188. package/.agent/skills/ui-ux-pro-max/data/stacks/flutter.csv +53 -0
  189. package/.agent/skills/ui-ux-pro-max/data/stacks/html-tailwind.csv +56 -0
  190. package/.agent/skills/ui-ux-pro-max/data/stacks/nextjs.csv +53 -0
  191. package/.agent/skills/ui-ux-pro-max/data/stacks/react-native.csv +52 -0
  192. package/.agent/skills/ui-ux-pro-max/data/stacks/react.csv +54 -0
  193. package/.agent/skills/ui-ux-pro-max/data/stacks/svelte.csv +54 -0
  194. package/.agent/skills/ui-ux-pro-max/data/stacks/swiftui.csv +51 -0
  195. package/.agent/skills/ui-ux-pro-max/data/stacks/vue.csv +50 -0
  196. package/.agent/skills/ui-ux-pro-max/data/styles.csv +59 -0
  197. package/.agent/skills/ui-ux-pro-max/data/typography.csv +58 -0
  198. package/.agent/skills/ui-ux-pro-max/data/ux-guidelines.csv +100 -0
  199. package/.agent/skills/ui-ux-pro-max/scripts/core.py +236 -0
  200. package/.agent/skills/ui-ux-pro-max/scripts/search.py +61 -0
  201. package/.agent/skills/ultrapilot/SKILL.md +647 -0
  202. package/.agent/skills/ultraqa/SKILL.md +152 -0
  203. package/.agent/skills/ultrawork/SKILL.md +123 -0
  204. package/.agent/skills/update-codemaps/SKILL.md +38 -0
  205. package/.agent/skills/update-docs/SKILL.md +52 -0
  206. package/.agent/skills/verification-loop/SKILL.md +140 -0
  207. package/.agent/skills/verify/SKILL.md +80 -0
  208. package/.agent/skills/writer-memory/SKILL.md +459 -0
  209. package/.agent/skills/writer-memory/lib/character-tracker.ts +338 -0
  210. package/.agent/skills/writer-memory/lib/memory-manager.ts +804 -0
  211. package/.agent/skills/writer-memory/lib/relationship-graph.ts +400 -0
  212. package/.agent/skills/writer-memory/lib/scene-organizer.ts +544 -0
  213. package/.agent/skills/writer-memory/lib/synopsis-builder.ts +339 -0
  214. package/.agent/skills/writer-memory/templates/synopsis-template.md +46 -0
  215. package/.governance/skill-lint.allowlist +4 -0
  216. package/.governance/skill-llm.allowlist +4 -0
  217. package/AGENTS.md +59 -0
  218. package/LICENSE +21 -0
  219. package/README.md +169 -0
  220. package/README.zh.md +145 -0
  221. package/bin/omcodex.js +8 -0
  222. package/commands/conductor/implement.toml +358 -0
  223. package/commands/conductor/newTrack.toml +142 -0
  224. package/commands/conductor/revert.toml +123 -0
  225. package/commands/conductor/setup.toml +429 -0
  226. package/commands/conductor/status.toml +57 -0
  227. package/docs/ALIGNMENT.md +40 -0
  228. package/docs/CODEX.md +133 -0
  229. package/docs/NOTIFY.md +81 -0
  230. package/docs/SKILL_GOVERNANCE.md +72 -0
  231. package/docs/SKILL_GOVERNANCE_FRAMEWORK.md +182 -0
  232. package/docs/SKILL_GOVERNANCE_FRAMEWORK.zh.md +170 -0
  233. package/package.json +50 -0
  234. package/prompts/architect.md +105 -0
  235. package/prompts/executor.md +134 -0
  236. package/prompts/planner.md +113 -0
  237. package/scripts/check-skill-governance.sh +84 -0
  238. package/scripts/check-skill-llm-governance.js +302 -0
  239. package/scripts/eval-skills.js +217 -0
  240. package/scripts/generate-catalog-docs.js +95 -0
  241. package/scripts/generate-codex-mcp-config.sh +22 -0
  242. package/scripts/install-codex-force.sh +5 -0
  243. package/scripts/install-codex-incremental.sh +5 -0
  244. package/scripts/install-codex.sh +79 -0
  245. package/scripts/notify-dispatch.js +15 -0
  246. package/scripts/setup-package-manager.js +137 -0
  247. package/src/catalog/generated/public-catalog.json +547 -0
  248. package/src/catalog/manifest.json +542 -0
  249. package/src/catalog/reader.js +43 -0
  250. package/src/catalog/schema.js +79 -0
  251. package/src/cli/doctor.js +62 -0
  252. package/src/cli/index.js +85 -0
  253. package/src/cli/notify.js +127 -0
  254. package/src/cli/route.js +43 -0
  255. package/src/cli/setup.js +155 -0
  256. package/src/cli/team.js +125 -0
  257. package/src/config/generator.js +119 -0
  258. package/src/mcp/memory-server.js +241 -0
  259. package/src/mcp/state-server.js +112 -0
  260. package/src/mcp/trace-server.js +168 -0
  261. package/src/notify/dispatch.js +74 -0
  262. package/src/notify/extensibility/dispatcher.js +113 -0
  263. package/src/notify/extensibility/events.js +15 -0
  264. package/src/notify/extensibility/loader.js +54 -0
  265. package/src/router/skill-router.js +90 -0
  266. package/src/team/auto-advance.js +72 -0
  267. package/src/team/orchestrator.js +82 -0
  268. package/src/team/state-store.js +33 -0
  269. package/src/utils/paths.js +33 -0
  270. package/templates/AGENTS.md +15 -0
  271. package/templates/catalog-manifest.json +542 -0
  272. package/templates/code_styleguides/csharp.md +115 -0
  273. package/templates/code_styleguides/dart.md +238 -0
  274. package/templates/code_styleguides/general.md +23 -0
  275. package/templates/code_styleguides/go.md +48 -0
  276. package/templates/code_styleguides/html-css.md +49 -0
  277. package/templates/code_styleguides/javascript.md +51 -0
  278. package/templates/code_styleguides/python.md +37 -0
  279. package/templates/code_styleguides/typescript.md +43 -0
  280. package/templates/rules/README.md +23 -0
  281. package/templates/rules/agents.md +49 -0
  282. package/templates/rules/coding-style.md +70 -0
  283. package/templates/rules/dev.md +20 -0
  284. package/templates/rules/git-workflow.md +45 -0
  285. package/templates/rules/notify.md +6 -0
  286. package/templates/rules/patterns.md +55 -0
  287. package/templates/rules/performance.md +47 -0
  288. package/templates/rules/research.md +26 -0
  289. package/templates/rules/review.md +22 -0
  290. package/templates/rules/security.md +36 -0
  291. package/templates/rules/testing.md +30 -0
  292. package/templates/workflow.md +333 -0
@@ -0,0 +1,646 @@
1
+ ---
2
+ name: frontend-patterns
3
+ description: Frontend development patterns for React, Next.js, state management, performance optimization, and UI best practices.
4
+ ---
5
+
6
+ # Frontend Development Patterns
7
+
8
+
9
+ ## Native Subagent Protocol (Codex)
10
+
11
+ Codex supports native subagents. Delegate with `spawn_agent`, coordinate with `send_input`, collect via `wait`, and clean up with `close_agent`.
12
+
13
+ Execution preference:
14
+ 1. Use native subagents first for independent workstreams (parallel when possible).
15
+ 2. Merge results in main thread and run final verification.
16
+ 3. Fallback only when delegation is blocked: use the `[ANALYST]`/`[ARCHITECT]`/`[EXECUTOR]`/`[REVIEWER]` structure in a single response.
17
+
18
+ Minimal orchestration pattern:
19
+ ```text
20
+ spawn_agent -> send_input (optional) -> wait -> close_agent
21
+ ```
22
+
23
+ Modern frontend patterns for React, Next.js, and performant user interfaces.
24
+
25
+ ## Component Patterns
26
+
27
+ ### Composition Over Inheritance
28
+
29
+ ```typescript
30
+ // ✅ GOOD: Component composition
31
+ interface CardProps {
32
+ children: React.ReactNode
33
+ variant?: 'default' | 'outlined'
34
+ }
35
+
36
+ export function Card({ children, variant = 'default' }: CardProps) {
37
+ return <div className={`card card-${variant}`}>{children}</div>
38
+ }
39
+
40
+ export function CardHeader({ children }: { children: React.ReactNode }) {
41
+ return <div className="card-header">{children}</div>
42
+ }
43
+
44
+ export function CardBody({ children }: { children: React.ReactNode }) {
45
+ return <div className="card-body">{children}</div>
46
+ }
47
+
48
+ // Usage
49
+ <Card>
50
+ <CardHeader>Title</CardHeader>
51
+ <CardBody>Content</CardBody>
52
+ </Card>
53
+ ```
54
+
55
+ ### Compound Components
56
+
57
+ ```typescript
58
+ interface TabsContextValue {
59
+ activeTab: string
60
+ setActiveTab: (tab: string) => void
61
+ }
62
+
63
+ const TabsContext = createContext<TabsContextValue | undefined>(undefined)
64
+
65
+ export function Tabs({ children, defaultTab }: {
66
+ children: React.ReactNode
67
+ defaultTab: string
68
+ }) {
69
+ const [activeTab, setActiveTab] = useState(defaultTab)
70
+
71
+ return (
72
+ <TabsContext.Provider value={{ activeTab, setActiveTab }}>
73
+ {children}
74
+ </TabsContext.Provider>
75
+ )
76
+ }
77
+
78
+ export function TabList({ children }: { children: React.ReactNode }) {
79
+ return <div className="tab-list">{children}</div>
80
+ }
81
+
82
+ export function Tab({ id, children }: { id: string, children: React.ReactNode }) {
83
+ const context = useContext(TabsContext)
84
+ if (!context) throw new Error('Tab must be used within Tabs')
85
+
86
+ return (
87
+ <button
88
+ className={context.activeTab === id ? 'active' : ''}
89
+ onClick={() => context.setActiveTab(id)}
90
+ >
91
+ {children}
92
+ </button>
93
+ )
94
+ }
95
+
96
+ // Usage
97
+ <Tabs defaultTab="overview">
98
+ <TabList>
99
+ <Tab id="overview">Overview</Tab>
100
+ <Tab id="details">Details</Tab>
101
+ </TabList>
102
+ </Tabs>
103
+ ```
104
+
105
+ ### Render Props Pattern
106
+
107
+ ```typescript
108
+ interface DataLoaderProps<T> {
109
+ url: string
110
+ children: (data: T | null, loading: boolean, error: Error | null) => React.ReactNode
111
+ }
112
+
113
+ export function DataLoader<T>({ url, children }: DataLoaderProps<T>) {
114
+ const [data, setData] = useState<T | null>(null)
115
+ const [loading, setLoading] = useState(true)
116
+ const [error, setError] = useState<Error | null>(null)
117
+
118
+ useEffect(() => {
119
+ fetch(url)
120
+ .then(res => res.json())
121
+ .then(setData)
122
+ .catch(setError)
123
+ .finally(() => setLoading(false))
124
+ }, [url])
125
+
126
+ return <>{children(data, loading, error)}</>
127
+ }
128
+
129
+ // Usage
130
+ <DataLoader<Market[]> url="/api/markets">
131
+ {(markets, loading, error) => {
132
+ if (loading) return <Spinner />
133
+ if (error) return <Error error={error} />
134
+ return <MarketList markets={markets!} />
135
+ }}
136
+ </DataLoader>
137
+ ```
138
+
139
+ ## Custom Hooks Patterns
140
+
141
+ ### State Management Hook
142
+
143
+ ```typescript
144
+ export function useToggle(initialValue = false): [boolean, () => void] {
145
+ const [value, setValue] = useState(initialValue)
146
+
147
+ const toggle = useCallback(() => {
148
+ setValue(v => !v)
149
+ }, [])
150
+
151
+ return [value, toggle]
152
+ }
153
+
154
+ // Usage
155
+ const [isOpen, toggleOpen] = useToggle()
156
+ ```
157
+
158
+ ### Async Data Fetching Hook
159
+
160
+ ```typescript
161
+ interface UseQueryOptions<T> {
162
+ onSuccess?: (data: T) => void
163
+ onError?: (error: Error) => void
164
+ enabled?: boolean
165
+ }
166
+
167
+ export function useQuery<T>(
168
+ key: string,
169
+ fetcher: () => Promise<T>,
170
+ options?: UseQueryOptions<T>
171
+ ) {
172
+ const [data, setData] = useState<T | null>(null)
173
+ const [error, setError] = useState<Error | null>(null)
174
+ const [loading, setLoading] = useState(false)
175
+
176
+ const refetch = useCallback(async () => {
177
+ setLoading(true)
178
+ setError(null)
179
+
180
+ try {
181
+ const result = await fetcher()
182
+ setData(result)
183
+ options?.onSuccess?.(result)
184
+ } catch (err) {
185
+ const error = err as Error
186
+ setError(error)
187
+ options?.onError?.(error)
188
+ } finally {
189
+ setLoading(false)
190
+ }
191
+ }, [fetcher, options])
192
+
193
+ useEffect(() => {
194
+ if (options?.enabled !== false) {
195
+ refetch()
196
+ }
197
+ }, [key, refetch, options?.enabled])
198
+
199
+ return { data, error, loading, refetch }
200
+ }
201
+
202
+ // Usage
203
+ const { data: markets, loading, error, refetch } = useQuery(
204
+ 'markets',
205
+ () => fetch('/api/markets').then(r => r.json()),
206
+ {
207
+ onSuccess: data => console.log('Fetched', data.length, 'markets'),
208
+ onError: err => console.error('Failed:', err)
209
+ }
210
+ )
211
+ ```
212
+
213
+ ### Debounce Hook
214
+
215
+ ```typescript
216
+ export function useDebounce<T>(value: T, delay: number): T {
217
+ const [debouncedValue, setDebouncedValue] = useState<T>(value)
218
+
219
+ useEffect(() => {
220
+ const handler = setTimeout(() => {
221
+ setDebouncedValue(value)
222
+ }, delay)
223
+
224
+ return () => clearTimeout(handler)
225
+ }, [value, delay])
226
+
227
+ return debouncedValue
228
+ }
229
+
230
+ // Usage
231
+ const [searchQuery, setSearchQuery] = useState('')
232
+ const debouncedQuery = useDebounce(searchQuery, 500)
233
+
234
+ useEffect(() => {
235
+ if (debouncedQuery) {
236
+ performSearch(debouncedQuery)
237
+ }
238
+ }, [debouncedQuery])
239
+ ```
240
+
241
+ ## State Management Patterns
242
+
243
+ ### Context + Reducer Pattern
244
+
245
+ ```typescript
246
+ interface State {
247
+ markets: Market[]
248
+ selectedMarket: Market | null
249
+ loading: boolean
250
+ }
251
+
252
+ type Action =
253
+ | { type: 'SET_MARKETS'; payload: Market[] }
254
+ | { type: 'SELECT_MARKET'; payload: Market }
255
+ | { type: 'SET_LOADING'; payload: boolean }
256
+
257
+ function reducer(state: State, action: Action): State {
258
+ switch (action.type) {
259
+ case 'SET_MARKETS':
260
+ return { ...state, markets: action.payload }
261
+ case 'SELECT_MARKET':
262
+ return { ...state, selectedMarket: action.payload }
263
+ case 'SET_LOADING':
264
+ return { ...state, loading: action.payload }
265
+ default:
266
+ return state
267
+ }
268
+ }
269
+
270
+ const MarketContext = createContext<{
271
+ state: State
272
+ dispatch: Dispatch<Action>
273
+ } | undefined>(undefined)
274
+
275
+ export function MarketProvider({ children }: { children: React.ReactNode }) {
276
+ const [state, dispatch] = useReducer(reducer, {
277
+ markets: [],
278
+ selectedMarket: null,
279
+ loading: false
280
+ })
281
+
282
+ return (
283
+ <MarketContext.Provider value={{ state, dispatch }}>
284
+ {children}
285
+ </MarketContext.Provider>
286
+ )
287
+ }
288
+
289
+ export function useMarkets() {
290
+ const context = useContext(MarketContext)
291
+ if (!context) throw new Error('useMarkets must be used within MarketProvider')
292
+ return context
293
+ }
294
+ ```
295
+
296
+ ## Performance Optimization
297
+
298
+ ### Memoization
299
+
300
+ ```typescript
301
+ // ✅ useMemo for expensive computations
302
+ const sortedMarkets = useMemo(() => {
303
+ return markets.sort((a, b) => b.volume - a.volume)
304
+ }, [markets])
305
+
306
+ // ✅ useCallback for functions passed to children
307
+ const handleSearch = useCallback((query: string) => {
308
+ setSearchQuery(query)
309
+ }, [])
310
+
311
+ // ✅ React.memo for pure components
312
+ export const MarketCard = React.memo<MarketCardProps>(({ market }) => {
313
+ return (
314
+ <div className="market-card">
315
+ <h3>{market.name}</h3>
316
+ <p>{market.description}</p>
317
+ </div>
318
+ )
319
+ })
320
+ ```
321
+
322
+ ### Code Splitting & Lazy Loading
323
+
324
+ ```typescript
325
+ import { lazy, Suspense } from 'react'
326
+
327
+ // ✅ Lazy load heavy components
328
+ const HeavyChart = lazy(() => import('./HeavyChart'))
329
+ const ThreeJsBackground = lazy(() => import('./ThreeJsBackground'))
330
+
331
+ export function Dashboard() {
332
+ return (
333
+ <div>
334
+ <Suspense fallback={<ChartSkeleton />}>
335
+ <HeavyChart data={data} />
336
+ </Suspense>
337
+
338
+ <Suspense fallback={null}>
339
+ <ThreeJsBackground />
340
+ </Suspense>
341
+ </div>
342
+ )
343
+ }
344
+ ```
345
+
346
+ ### Virtualization for Long Lists
347
+
348
+ ```typescript
349
+ import { useVirtualizer } from '@tanstack/react-virtual'
350
+
351
+ export function VirtualMarketList({ markets }: { markets: Market[] }) {
352
+ const parentRef = useRef<HTMLDivElement>(null)
353
+
354
+ const virtualizer = useVirtualizer({
355
+ count: markets.length,
356
+ getScrollElement: () => parentRef.current,
357
+ estimateSize: () => 100, // Estimated row height
358
+ overscan: 5 // Extra items to render
359
+ })
360
+
361
+ return (
362
+ <div ref={parentRef} style={{ height: '600px', overflow: 'auto' }}>
363
+ <div
364
+ style={{
365
+ height: `${virtualizer.getTotalSize()}px`,
366
+ position: 'relative'
367
+ }}
368
+ >
369
+ {virtualizer.getVirtualItems().map(virtualRow => (
370
+ <div
371
+ key={virtualRow.index}
372
+ style={{
373
+ position: 'absolute',
374
+ top: 0,
375
+ left: 0,
376
+ width: '100%',
377
+ height: `${virtualRow.size}px`,
378
+ transform: `translateY(${virtualRow.start}px)`
379
+ }}
380
+ >
381
+ <MarketCard market={markets[virtualRow.index]} />
382
+ </div>
383
+ ))}
384
+ </div>
385
+ </div>
386
+ )
387
+ }
388
+ ```
389
+
390
+ ## Form Handling Patterns
391
+
392
+ ### Controlled Form with Validation
393
+
394
+ ```typescript
395
+ interface FormData {
396
+ name: string
397
+ description: string
398
+ endDate: string
399
+ }
400
+
401
+ interface FormErrors {
402
+ name?: string
403
+ description?: string
404
+ endDate?: string
405
+ }
406
+
407
+ export function CreateMarketForm() {
408
+ const [formData, setFormData] = useState<FormData>({
409
+ name: '',
410
+ description: '',
411
+ endDate: ''
412
+ })
413
+
414
+ const [errors, setErrors] = useState<FormErrors>({})
415
+
416
+ const validate = (): boolean => {
417
+ const newErrors: FormErrors = {}
418
+
419
+ if (!formData.name.trim()) {
420
+ newErrors.name = 'Name is required'
421
+ } else if (formData.name.length > 200) {
422
+ newErrors.name = 'Name must be under 200 characters'
423
+ }
424
+
425
+ if (!formData.description.trim()) {
426
+ newErrors.description = 'Description is required'
427
+ }
428
+
429
+ if (!formData.endDate) {
430
+ newErrors.endDate = 'End date is required'
431
+ }
432
+
433
+ setErrors(newErrors)
434
+ return Object.keys(newErrors).length === 0
435
+ }
436
+
437
+ const handleSubmit = async (e: React.FormEvent) => {
438
+ e.preventDefault()
439
+
440
+ if (!validate()) return
441
+
442
+ try {
443
+ await createMarket(formData)
444
+ // Success handling
445
+ } catch (error) {
446
+ // Error handling
447
+ }
448
+ }
449
+
450
+ return (
451
+ <form onSubmit={handleSubmit}>
452
+ <input
453
+ value={formData.name}
454
+ onChange={e => setFormData(prev => ({ ...prev, name: e.target.value }))}
455
+ placeholder="Market name"
456
+ />
457
+ {errors.name && <span className="error">{errors.name}</span>}
458
+
459
+ {/* Other fields */}
460
+
461
+ <button type="submit">Create Market</button>
462
+ </form>
463
+ )
464
+ }
465
+ ```
466
+
467
+ ## Error Boundary Pattern
468
+
469
+ ```typescript
470
+ interface ErrorBoundaryState {
471
+ hasError: boolean
472
+ error: Error | null
473
+ }
474
+
475
+ export class ErrorBoundary extends React.Component<
476
+ { children: React.ReactNode },
477
+ ErrorBoundaryState
478
+ > {
479
+ state: ErrorBoundaryState = {
480
+ hasError: false,
481
+ error: null
482
+ }
483
+
484
+ static getDerivedStateFromError(error: Error): ErrorBoundaryState {
485
+ return { hasError: true, error }
486
+ }
487
+
488
+ componentDidCatch(error: Error, errorInfo: React.ErrorInfo) {
489
+ console.error('Error boundary caught:', error, errorInfo)
490
+ }
491
+
492
+ render() {
493
+ if (this.state.hasError) {
494
+ return (
495
+ <div className="error-fallback">
496
+ <h2>Something went wrong</h2>
497
+ <p>{this.state.error?.message}</p>
498
+ <button onClick={() => this.setState({ hasError: false })}>
499
+ Try again
500
+ </button>
501
+ </div>
502
+ )
503
+ }
504
+
505
+ return this.props.children
506
+ }
507
+ }
508
+
509
+ // Usage
510
+ <ErrorBoundary>
511
+ <App />
512
+ </ErrorBoundary>
513
+ ```
514
+
515
+ ## Animation Patterns
516
+
517
+ ### Framer Motion Animations
518
+
519
+ ```typescript
520
+ import { motion, AnimatePresence } from 'framer-motion'
521
+
522
+ // ✅ List animations
523
+ export function AnimatedMarketList({ markets }: { markets: Market[] }) {
524
+ return (
525
+ <AnimatePresence>
526
+ {markets.map(market => (
527
+ <motion.div
528
+ key={market.id}
529
+ initial={{ opacity: 0, y: 20 }}
530
+ animate={{ opacity: 1, y: 0 }}
531
+ exit={{ opacity: 0, y: -20 }}
532
+ transition={{ duration: 0.3 }}
533
+ >
534
+ <MarketCard market={market} />
535
+ </motion.div>
536
+ ))}
537
+ </AnimatePresence>
538
+ )
539
+ }
540
+
541
+ // ✅ Modal animations
542
+ export function Modal({ isOpen, onClose, children }: ModalProps) {
543
+ return (
544
+ <AnimatePresence>
545
+ {isOpen && (
546
+ <>
547
+ <motion.div
548
+ className="modal-overlay"
549
+ initial={{ opacity: 0 }}
550
+ animate={{ opacity: 1 }}
551
+ exit={{ opacity: 0 }}
552
+ onClick={onClose}
553
+ />
554
+ <motion.div
555
+ className="modal-content"
556
+ initial={{ opacity: 0, scale: 0.9, y: 20 }}
557
+ animate={{ opacity: 1, scale: 1, y: 0 }}
558
+ exit={{ opacity: 0, scale: 0.9, y: 20 }}
559
+ >
560
+ {children}
561
+ </motion.div>
562
+ </>
563
+ )}
564
+ </AnimatePresence>
565
+ )
566
+ }
567
+ ```
568
+
569
+ ## Accessibility Patterns
570
+
571
+ ### Keyboard Navigation
572
+
573
+ ```typescript
574
+ export function Dropdown({ options, onSelect }: DropdownProps) {
575
+ const [isOpen, setIsOpen] = useState(false)
576
+ const [activeIndex, setActiveIndex] = useState(0)
577
+
578
+ const handleKeyDown = (e: React.KeyboardEvent) => {
579
+ switch (e.key) {
580
+ case 'ArrowDown':
581
+ e.preventDefault()
582
+ setActiveIndex(i => Math.min(i + 1, options.length - 1))
583
+ break
584
+ case 'ArrowUp':
585
+ e.preventDefault()
586
+ setActiveIndex(i => Math.max(i - 1, 0))
587
+ break
588
+ case 'Enter':
589
+ e.preventDefault()
590
+ onSelect(options[activeIndex])
591
+ setIsOpen(false)
592
+ break
593
+ case 'Escape':
594
+ setIsOpen(false)
595
+ break
596
+ }
597
+ }
598
+
599
+ return (
600
+ <div
601
+ role="combobox"
602
+ aria-expanded={isOpen}
603
+ aria-haspopup="listbox"
604
+ onKeyDown={handleKeyDown}
605
+ >
606
+ {/* Dropdown implementation */}
607
+ </div>
608
+ )
609
+ }
610
+ ```
611
+
612
+ ### Focus Management
613
+
614
+ ```typescript
615
+ export function Modal({ isOpen, onClose, children }: ModalProps) {
616
+ const modalRef = useRef<HTMLDivElement>(null)
617
+ const previousFocusRef = useRef<HTMLElement | null>(null)
618
+
619
+ useEffect(() => {
620
+ if (isOpen) {
621
+ // Save currently focused element
622
+ previousFocusRef.current = document.activeElement as HTMLElement
623
+
624
+ // Focus modal
625
+ modalRef.current?.focus()
626
+ } else {
627
+ // Restore focus when closing
628
+ previousFocusRef.current?.focus()
629
+ }
630
+ }, [isOpen])
631
+
632
+ return isOpen ? (
633
+ <div
634
+ ref={modalRef}
635
+ role="dialog"
636
+ aria-modal="true"
637
+ tabIndex={-1}
638
+ onKeyDown={e => e.key === 'Escape' && onClose()}
639
+ >
640
+ {children}
641
+ </div>
642
+ ) : null
643
+ }
644
+ ```
645
+
646
+ **Remember**: Modern frontend patterns enable maintainable, performant user interfaces. Choose patterns that fit your project complexity.
@@ -0,0 +1,70 @@
1
+ ---
2
+ name: frontend-ui-ux
3
+ description: Designer-turned-developer who crafts stunning UI/UX even without design mockups
4
+ ---
5
+
6
+ # Frontend UI/UX Skill
7
+
8
+
9
+ ## Native Subagent Protocol (Codex)
10
+
11
+ Codex supports native subagents. Delegate with `spawn_agent`, coordinate with `send_input`, collect via `wait`, and clean up with `close_agent`.
12
+
13
+ Execution preference:
14
+ 1. Use native subagents first for independent workstreams (parallel when possible).
15
+ 2. Merge results in main thread and run final verification.
16
+ 3. Fallback only when delegation is blocked: use the `[ANALYST]`/`[ARCHITECT]`/`[EXECUTOR]`/`[REVIEWER]` structure in a single response.
17
+
18
+ Minimal orchestration pattern:
19
+ ```text
20
+ spawn_agent -> send_input (optional) -> wait -> close_agent
21
+ ```
22
+
23
+ > Codex invocation: use `$frontend-ui-ux ...` or `frontend-ui-ux: ...`
24
+
25
+
26
+ You are a designer who learned to code. You see what pure developers miss—spacing, color harmony, micro-interactions, that indefinable "feel" that makes interfaces memorable.
27
+
28
+ ## Design Process
29
+
30
+ Before coding, commit to a **BOLD aesthetic direction**:
31
+
32
+ 1. **Purpose**: What problem does this solve? Who uses it?
33
+ 2. **Tone**: Pick an extreme:
34
+ - Brutally minimal
35
+ - Maximalist chaos
36
+ - Retro-futuristic
37
+ - Organic/natural
38
+ - Luxury/refined
39
+ - Playful/toy-like
40
+ - Editorial/magazine
41
+ - Brutalist/raw
42
+ - Art deco/geometric
43
+ - Soft/pastel
44
+ - Industrial/utilitarian
45
+ 3. **Constraints**: Technical requirements (framework, performance, accessibility)
46
+ 4. **Differentiation**: What's the ONE thing someone will remember?
47
+
48
+ ## Aesthetic Guidelines
49
+
50
+ ### Typography
51
+ Choose distinctive fonts. **Avoid**: Arial, Inter, Roboto, system fonts, Space Grotesk.
52
+
53
+ ### Color
54
+ Commit to a cohesive palette. Use CSS variables. **Avoid**: purple gradients on white (AI slop).
55
+
56
+ ### Motion
57
+ Focus on high-impact moments. One well-orchestrated page load > scattered micro-interactions. Use CSS-only where possible.
58
+
59
+ ### Spatial Composition
60
+ Unexpected layouts. Asymmetry. Overlap. Diagonal flow. Grid-breaking elements.
61
+
62
+ ### Visual Details
63
+ Create atmosphere—gradient meshes, noise textures, geometric patterns, layered transparencies, dramatic shadows.
64
+
65
+ ## Anti-Patterns (NEVER)
66
+
67
+ - Generic fonts (Inter, Roboto, Arial)
68
+ - Cliched color schemes (purple gradients on white)
69
+ - Predictable layouts
70
+ - Cookie-cutter design