1	# EZ Design System — Component Patterns
2
3	Concrete code patterns for the EZ Design System. Use these as the building blocks when implementing UIs.
4
5	## Table of Contents
6
7	1. [Sidebar](#sidebar)
8	2. [Overlay Boxes](#overlay-boxes)
9	3. [Stat Display](#stat-display)
10	4. [Section Pattern](#section-pattern)
11	5. [List Items](#list-items)
12	6. [Badges & Tags](#badges--tags)
13	7. [Detail Panel](#detail-panel)
14	8. [Compact Items](#compact-items)
15	9. [Summary Bar](#summary-bar)
16	10. [Timeline](#timeline)
17	11. [Interactive Cards](#interactive-cards)
18	12. [Cost/Breakdown Rows](#costbreakdown-rows)
19	13. [Buttons](#buttons)
20	14. [Form Inputs](#form-inputs)
21	15. [Chat Panel](#chat-panel)
22	16. [Empty States](#empty-states)
23	17. [Navigation Bar](#navigation-bar)
24
25	---
26
27	## Sidebar
28
29	240px collapsible left panel. Collapses to 44px icon bar. At 960px, disappears with mobile toggle.
30
31	```css
32	.sidebar {
33	  position: fixed;
34	  top: 0;
35	  left: 0;
36	  bottom: 0;
37	  width: var(--sidebar-width);
38	  background: var(--bg-primary);
39	  border-right: 1px solid var(--border-light);
40	  display: flex;
41	  flex-direction: column;
42	  z-index: 20;
43	  transition: width var(--transition-base);
44	  overflow-y: auto;
45	}
46
47	.sidebar-brand {
48	  padding: var(--space-4) var(--space-4);
49	  font-family: var(--font-display);
50	  font-size: var(--text-lg);
51	  font-weight: var(--weight-bold);
52	  color: var(--text-primary);
53	  display: flex;
54	  align-items: center;
55	  gap: var(--space-2);
56	}
57
58	.sidebar-nav {
59	  padding: var(--space-2) var(--space-3);
60	}
61
62	.sidebar-nav-item {
63	  display: flex;
64	  align-items: center;
65	  gap: var(--space-2);
66	  padding: var(--space-2) var(--space-3);
67	  border-radius: var(--radius-md);
68	  font-size: var(--text-sm);
69	  font-weight: var(--weight-medium);
70	  color: var(--text-secondary);
71	  cursor: pointer;
72	  transition: var(--transition-fast);
73	}
74
75	.sidebar-nav-item:hover {
76	  background: var(--bg-hover);
77	  color: var(--text-primary);
78	}
79
80	.sidebar-nav-item.active {
81	  background: var(--accent-100);
82	  color: var(--accent-600);
83	}
84
85	.sidebar-section-label {
86	  font-size: 10px;
87	  font-weight: var(--weight-semibold);
88	  text-transform: uppercase;
89	  letter-spacing: 0.5px;
90	  color: var(--text-tertiary);
91	  padding: var(--space-4) var(--space-3) var(--space-1);
92	}
93
94	.sidebar-divider {
95	  height: 1px;
96	  background: var(--border-light);
97	  margin: var(--space-3) var(--space-3);
98	}
99
100	.sidebar-stats {
101	  display: grid;
102	  grid-template-columns: 1fr 1fr;
103	  gap: var(--space-2);
104	  padding: var(--space-3);
105	}
106
107	.sidebar-stat-value {
108	  font-family: var(--font-display);
109	  font-size: var(--text-2xl);
110	  font-weight: var(--weight-bold);
111	  color: var(--text-primary);
112	}
113
114	.sidebar-stat-label {
115	  font-size: var(--text-xs);
116	  color: var(--text-tertiary);
117	}
118
119	.sidebar-footer {
120	  margin-top: auto;
121	  padding: var(--space-3);
122	  border-top: 1px solid var(--border-light);
123	}
124	```
125
126	## Overlay Boxes
127
128	Floating stat/control panels positioned over main content.
129
130	```css
131	.overlay-box {
132	  position: absolute;
133	  z-index: 10;
134	  padding: var(--space-3) var(--space-4);
135	  background: var(--bg-primary);
136	  border: 1px solid var(--border-light);
137	  border-radius: var(--radius-md);
138	  box-shadow: var(--shadow-sm);
139	}
140
141	.overlay-stack {
142	  position: absolute;
143	  top: var(--space-8);
144	  left: var(--space-4);
145	  display: flex;
146	  flex-direction: column;
147	  gap: var(--space-2);
148	  z-index: 10;
149	}
150
151	.overlay-controls {
152	  position: absolute;
153	  top: var(--space-8);
154	  right: var(--space-4);
155	  display: flex;
156	  flex-direction: column;
157	  gap: var(--space-1);
158	  z-index: 10;
159	}
160
161	.overlay-control-btn {
162	  width: 32px;
163	  height: 32px;
164	  display: flex;
165	  align-items: center;
166	  justify-content: center;
167	  background: var(--bg-primary);
168	  border: 1px solid var(--border-light);
169	  border-radius: var(--radius-sm);
170	  font-size: var(--text-sm);
171	  cursor: pointer;
172	  transition: var(--transition-fast);
173	}
174
175	.overlay-control-btn:hover {
176	  background: var(--bg-hover);
177	  border-color: var(--border-hover);
178	}
179	```
180
181	## Stat Display
182
183	Big numbers for dashboard KPIs and hero sections.
184
185	```css
186	/* Hero/showcase stat (56px) */
187	.stat-hero {
188	  text-align: center;
189	}
190	.stat-hero-value {
191	  font-family: var(--font-display);
192	  font-size: 56px;
193	  font-weight: var(--weight-bold);
194	  color: var(--accent-500);
195	  line-height: 1.1;
196	}
197	.stat-hero-label {
198	  font-family: var(--font-display);
199	  font-size: var(--text-lg);
200	  font-weight: var(--weight-semibold);
201	  color: var(--text-primary);
202	  margin-top: var(--space-2);
203	}
204	.stat-hero-sub {
205	  font-size: var(--text-sm);
206	  color: var(--text-tertiary);
207	  margin-top: var(--space-1);
208	}
209
210	/* Dashboard KPI card */
211	.kpi-card {
212	  padding: var(--space-4) var(--space-5);
213	  background: var(--bg-primary);
214	  border: 1px solid var(--border-light);
215	  border-radius: var(--radius-md);
216	}
217	.kpi-value {
218	  font-family: var(--font-display);
219	  font-size: var(--text-3xl);
220	  font-weight: var(--weight-bold);
221	  color: var(--text-primary);
222	}
223	.kpi-label {
224	  font-size: var(--text-sm);
225	  color: var(--text-secondary);
226	  margin-top: var(--space-1);
227	}
228	.kpi-change {
229	  font-size: var(--text-xs);
230	  font-family: var(--font-mono);
231	  margin-top: var(--space-1);
232	}
233	.kpi-change.positive { color: var(--color-success); }
234	.kpi-change.negative { color: var(--color-error); }
235
236	/* Sidebar stat (20px) */
237	.stat-compact-value {
238	  font-family: var(--font-display);
239	  font-size: var(--text-2xl);
240	  font-weight: var(--weight-bold);
241	  color: var(--text-primary);
242	}
243	.stat-compact-label {
244	  font-size: var(--text-xs);
245	  color: var(--text-tertiary);
246	}
247	```
248
249	## Section Pattern
250
251	Alternating background sections for landing/journey pages.
252
253	```css
254	.section {
255	  padding: 72px var(--space-8);
256	  background: var(--bg-primary);
257	}
258
259	.section-alt {
260	  padding: 72px var(--space-8);
261	  background: var(--bg-secondary);
262	}
263
264	.section-label {
265	  font-size: 10px;
266	  font-weight: var(--weight-semibold);
267	  text-transform: uppercase;
268	  letter-spacing: 0.5px;
269	  color: var(--accent-600);
270	  margin-bottom: var(--space-3);
271	}
272
273	.section-heading {
274	  font-family: var(--font-display);
275	  font-size: var(--text-3xl);
276	  font-weight: var(--weight-bold);
277	  color: var(--text-primary);
278	  margin-bottom: var(--space-3);
279	}
280
281	.section-description {
282	  font-size: var(--text-md);
283	  color: var(--text-secondary);
284	  max-width: 640px;
285	  line-height: var(--leading-relaxed);
286	  margin-bottom: var(--space-8);
287	}
288
289	.section-grid {
290	  display: grid;
291	  grid-template-columns: repeat(3, 1fr);
292	  gap: var(--space-6);
293	}
294
295	@media (max-width: 960px) {
296	  .section-grid { grid-template-columns: repeat(2, 1fr); }
297	}
298	@media (max-width: 640px) {
299	  .section-grid { grid-template-columns: 1fr; }
300	  .section, .section-alt { padding: var(--space-10) var(--space-4); }
301	}
302	```
303
304	## List Items
305
306	Explore view rows with hover animation.
307
308	```css
309	.list-item {
310	  display: flex;
311	  flex-direction: column;
312	  gap: var(--space-1);
313	  padding: var(--space-4) var(--space-4);
314	  border-bottom: 1px solid var(--border-light);
315	  cursor: pointer;
316	  transition: var(--transition-fast);
317	  transform: translateX(0);
318	}
319
320	.list-item:hover {
321	  background: var(--bg-hover);
322	  transform: translateX(2px);
323	}
324
325	.list-item-header {
326	  display: flex;
327	  align-items: center;
328	  gap: var(--space-2);
329	}
330
331	.list-item-title {
332	  font-size: var(--text-base);
333	  font-weight: var(--weight-medium);
334	  color: var(--text-primary);
335	  flex: 1;
336	  overflow: hidden;
337	  text-overflow: ellipsis;
338	  white-space: nowrap;
339	}
340
341	.list-item-significance {
342	  font-family: var(--font-mono);
343	  font-size: var(--text-sm);
344	  font-weight: var(--weight-medium);
345	  color: var(--accent-600);
346	}
347
348	.list-item-meta {
349	  display: flex;
350	  align-items: center;
351	  gap: var(--space-3);
352	  font-size: var(--text-xs);
353	  color: var(--text-tertiary);
354	}
355
356	.list-item-summary {
357	  font-size: var(--text-sm);
358	  color: var(--text-secondary);
359	  overflow: hidden;
360	  text-overflow: ellipsis;
361	  white-space: nowrap;
362	}
363	```
364
365	## Badges & Tags
366
367	Pill-shaped badges for categorization.
368
369	```css
370	.badge {
371	  display: inline-flex;
372	  align-items: center;
373	  padding: 2px var(--space-2);
374	  font-size: var(--text-xs);
375	  font-weight: var(--weight-semibold);
376	  text-transform: uppercase;
377	  letter-spacing: 0.3px;
378	  border-radius: var(--radius-full);
379	  background: var(--bg-tertiary);
380	  color: var(--text-secondary);
381	}
382
383	.badge-accent {
384	  background: var(--accent-100);
385	  color: var(--accent-600);
386	}
387
388	.badge-success { background: #dcfce7; color: #166534; }
389	.badge-warning { background: #fef3c7; color: #92400e; }
390	.badge-error   { background: #fee2e2; color: #991b1b; }
391	.badge-info    { background: #dbeafe; color: #1e40af; }
392
393	.tag {
394	  display: inline-flex;
395	  align-items: center;
396	  padding: var(--space-1) var(--space-3);
397	  font-size: var(--text-sm);
398	  border: 1px solid var(--border-light);
399	  border-radius: var(--radius-full);
400	  color: var(--text-secondary);
401	  cursor: pointer;
402	  transition: var(--transition-fast);
403	}
404
405	.tag:hover {
406	  background: var(--bg-hover);
407	  border-color: var(--border-hover);
408	  color: var(--text-primary);
409	}
410	```
411
412	## Detail Panel
413
414	Right-side slide-in panel for item details.
415
416	```css
417	.detail-panel {
418	  position: fixed;
419	  top: 0;
420	  right: 0;
421	  bottom: 0;
422	  width: var(--panel-width);
423	  background: var(--bg-primary);
424	  border-left: 1px solid var(--border-light);
425	  box-shadow: var(--shadow-lg);
426	  z-index: 30;
427	  overflow-y: auto;
428	  transform: translateX(0);
429	  transition: transform var(--transition-base);
430	}
431
432	.detail-panel.hidden {
433	  transform: translateX(100%);
434	}
435
436	.detail-breadcrumb {
437	  display: flex;
438	  align-items: center;
439	  gap: var(--space-1);
440	  padding: var(--space-3) var(--space-4);
441	  font-size: var(--text-xs);
442	  color: var(--text-tertiary);
443	  border-bottom: 1px solid var(--border-light);
444	}
445
446	.detail-breadcrumb a {
447	  color: var(--text-tertiary);
448	}
449
450	.detail-breadcrumb a:hover {
451	  color: var(--text-accent);
452	}
453
454	.detail-content {
455	  padding: var(--space-5);
456	}
457
458	.detail-title {
459	  font-family: var(--font-display);
460	  font-size: var(--text-2xl);
461	  font-weight: var(--weight-bold);
462	  color: var(--text-primary);
463	  margin-bottom: var(--space-3);
464	}
465
466	.detail-badges {
467	  display: flex;
468	  flex-wrap: wrap;
469	  gap: var(--space-2);
470	  margin-bottom: var(--space-4);
471	}
472
473	.detail-description {
474	  font-size: var(--text-base);
475	  color: var(--text-secondary);
476	  line-height: var(--leading-relaxed);
477	  margin-bottom: var(--space-5);
478	}
479
480	.detail-section-label {
481	  font-size: var(--text-xs);
482	  font-weight: var(--weight-semibold);
483	  text-transform: uppercase;
484	  letter-spacing: 0.5px;
485	  color: var(--text-tertiary);
486	  margin-bottom: var(--space-2);
487	  margin-top: var(--space-5);
488	}
489
490	.detail-metrics {
491	  display: grid;
492	  grid-template-columns: repeat(3, 1fr);
493	  gap: var(--space-3);
494	}
495
496	.detail-metric-value {
497	  font-family: var(--font-mono);
498	  font-size: var(--text-lg);
499	  font-weight: var(--weight-medium);
500	  color: var(--text-primary);
501	}
502
503	.detail-metric-label {
504	  font-size: var(--text-xs);
505	  color: var(--text-tertiary);
506	}
507	```
508
509	## Compact Items
510
511	Sidebar stats, trending items, log entries.
512
513	```css
514	.compact-item {
515	  display: flex;
516	  align-items: center;
517	  gap: var(--space-2);
518	  font-size: var(--text-xs);
519	  padding: var(--space-1) 0;
520	}
521
522	.compact-label {
523	  color: var(--text-secondary);
524	  flex: 1;
525	  overflow: hidden;
526	  text-overflow: ellipsis;
527	  white-space: nowrap;
528	}
529
530	.compact-value {
531	  color: var(--text-tertiary);
532	  font-family: var(--font-mono);
533	  font-weight: var(--weight-medium);
534	  flex-shrink: 0;
535	}
536
537	.compact-indicator {
538	  width: 8px;
539	  height: 8px;
540	  border-radius: 50%;
541	  flex-shrink: 0;
542	}
543	```
544
545	## Summary Bar
546
547	Horizontal row of key metrics with dividers.
548
549	```css
550	.summary-bar {
551	  display: flex;
552	  align-items: center;
553	  justify-content: center;
554	  gap: var(--space-8);
555	  padding: var(--space-6) var(--space-8);
556	  border: 1px solid var(--border-light);
557	  border-radius: var(--radius-lg);
558	  background: var(--bg-secondary);
559	}
560
561	.summary-item {
562	  text-align: center;
563	}
564
565	.summary-value {
566	  font-family: var(--font-display);
567	  font-size: var(--text-3xl);
568	  font-weight: var(--weight-bold);
569	  color: var(--text-primary);
570	}
571
572	.summary-label {
573	  font-size: var(--text-sm);
574	  color: var(--text-secondary);
575	  margin-top: var(--space-1);
576	}
577
578	.summary-divider {
579	  width: 1px;
580	  height: 36px;
581	  background: var(--border-light);
582	}
583
584	@media (max-width: 640px) {
585	  .summary-bar {
586	    flex-direction: column;
587	    gap: var(--space-4);
588	  }
589	  .summary-divider {
590	    width: 48px;
591	    height: 1px;
592	  }
593	}
594	```
595
596	## Timeline
597
598	Vertical timeline with dot + line markers.
599
600	```css
601	.timeline-item {
602	  display: flex;
603	  gap: var(--space-4);
604	}
605
606	.timeline-marker {
607	  display: flex;
608	  flex-direction: column;
609	  align-items: center;
610	  width: 20px;
611	  flex-shrink: 0;
612	}
613
614	.timeline-dot {
615	  width: 10px;
616	  height: 10px;
617	  border-radius: 50%;
618	  background: var(--accent-500);
619	  border: 2px solid var(--bg-primary);
620	  flex-shrink: 0;
621	}
622
623	.timeline-line {
624	  width: 2px;
625	  flex: 1;
626	  background: var(--border-light);
627	}
628
629	.timeline-content {
630	  padding-bottom: var(--space-6);
631	}
632
633	.timeline-date {
634	  font-size: var(--text-xs);
635	  font-family: var(--font-mono);
636	  color: var(--text-muted);
637	  margin-bottom: var(--space-1);
638	}
639
640	.timeline-title {
641	  font-size: var(--text-base);
642	  font-weight: var(--weight-medium);
643	  color: var(--text-primary);
644	  margin-bottom: var(--space-1);
645	}
646
647	.timeline-description {
648	  font-size: var(--text-sm);
649	  color: var(--text-secondary);
650	  line-height: var(--leading-relaxed);
651	}
652	```
653
654	## Interactive Cards
655
656	Expandable list items with hover/active states.
657
658	```css
659	.card {
660	  padding: var(--space-4) var(--space-5);
661	  background: var(--bg-primary);
662	  border: 1px solid var(--border-light);
663	  border-radius: var(--radius-md);
664	  transition: var(--transition-fast);
665	}
666
667	.card:hover {
668	  border-color: var(--border-hover);
669	  box-shadow: var(--shadow-sm);
670	}
671
672	.stack-item {
673	  padding: var(--space-3) var(--space-4);
674	  cursor: pointer;
675	  border: 1px solid transparent;
676	  border-radius: var(--radius-md);
677	  transition: var(--transition-fast);
678	}
679
680	.stack-item:hover {
681	  background: var(--bg-hover);
682	  border-color: var(--border-light);
683	}
684
685	.stack-item.active {
686	  background: var(--bg-secondary);
687	  border-color: var(--border-default);
688	}
689
690	.stack-item-title {
691	  font-size: var(--text-base);
692	  font-weight: var(--weight-medium);
693	  color: var(--text-primary);
694	}
695
696	.stack-item-meta {
697	  font-size: var(--text-xs);
698	  color: var(--text-tertiary);
699	  margin-top: var(--space-1);
700	}
701	```
702
703	## Cost/Breakdown Rows
704
705	Tabular breakdowns with visual bars.
706
707	```css
708	.breakdown-row {
709	  display: grid;
710	  grid-template-columns: 1fr 100px 80px 1fr;
711	  gap: var(--space-2);
712	  align-items: center;
713	  padding: var(--space-3) 0;
714	  border-bottom: 1px solid var(--border-light);
715	}
716
717	.breakdown-label {
718	  font-size: var(--text-sm);
719	  color: var(--text-primary);
720	}
721
722	.breakdown-value {
723	  font-family: var(--font-mono);
724	  font-size: var(--text-sm);
725	  font-weight: var(--weight-medium);
726	  color: var(--text-primary);
727	  text-align: right;
728	}
729
730	.breakdown-pct {
731	  font-family: var(--font-mono);
732	  font-size: var(--text-xs);
733	  color: var(--text-tertiary);
734	  text-align: right;
735	}
736
737	.breakdown-bar {
738	  height: 6px;
739	  background: var(--bg-tertiary);
740	  border-radius: var(--radius-full);
741	  overflow: hidden;
742	}
743
744	.breakdown-bar-fill {
745	  height: 100%;
746	  border-radius: var(--radius-full);
747	  background: var(--accent-500);
748	  transition: width var(--transition-base);
749	}
750	```
751
752	## Buttons
753
754	```css
755	.btn {
756	  display: inline-flex;
757	  align-items: center;
758	  justify-content: center;
759	  gap: var(--space-2);
760	  padding: var(--space-2) var(--space-4);
761	  font-size: var(--text-sm);
762	  font-weight: var(--weight-medium);
763	  border-radius: var(--radius-sm);
764	  transition: var(--transition-fast);
765	  cursor: pointer;
766	}
767
768	.btn-primary {
769	  background: var(--accent-600);
770	  color: var(--color-white);
771	  border: none;
772	}
773
774	.btn-primary:hover {
775	  background: var(--accent-700);
776	}
777
778	.btn-secondary {
779	  background: transparent;
780	  color: var(--text-primary);
781	  border: 1px solid var(--border-default);
782	}
783
784	.btn-secondary:hover {
785	  background: var(--bg-hover);
786	  border-color: var(--border-hover);
787	}
788
789	.btn-ghost {
790	  background: transparent;
791	  color: var(--text-secondary);
792	  border: none;
793	}
794
795	.btn-ghost:hover {
796	  background: var(--bg-hover);
797	  color: var(--text-primary);
798	}
799
800	.btn:disabled {
801	  opacity: 0.3;
802	  cursor: not-allowed;
803	}
804	```
805
806	## Form Inputs
807
808	```css
809	.input {
810	  height: 30px;
811	  padding: 0 var(--space-3);
812	  font-size: var(--text-sm);
813	  color: var(--text-primary);
814	  background: var(--bg-primary);
815	  border: 1px solid var(--border-light);
816	  border-radius: var(--radius-sm);
817	  transition: var(--transition-fast);
818	  width: 100%;
819	}
820
821	.input:hover {
822	  border-color: var(--border-hover);
823	}
824
825	.input:focus {
826	  border-color: var(--border-focus);
827	  outline: none;
828	  box-shadow: 0 0 0 2px var(--accent-100);
829	}
830
831	.select {
832	  height: 30px;
833	  padding: 0 var(--space-3);
834	  font-size: var(--text-sm);
835	  color: var(--text-primary);
836	  background: var(--bg-secondary);
837	  border: 1px solid var(--border-light);
838	  border-radius: var(--radius-sm);
839	  cursor: pointer;
840	}
841
842	.label {
843	  font-size: var(--text-xs);
844	  font-weight: var(--weight-semibold);
845	  text-transform: uppercase;
846	  letter-spacing: 0.5px;
847	  color: var(--text-tertiary);
848	  margin-bottom: var(--space-1);
849	}
850	```
851
852	## Chat Panel
853
854	Floating AI assistant widget (bottom-right).
855
856	```css
857	.chat-fab {
858	  position: fixed;
859	  bottom: var(--space-5);
860	  right: var(--space-5);
861	  z-index: 40;
862	  width: 48px;
863	  height: 48px;
864	  border-radius: 50%;
865	  background: var(--accent-600);
866	  color: var(--color-white);
867	  display: flex;
868	  align-items: center;
869	  justify-content: center;
870	  font-size: var(--text-xl);
871	  cursor: pointer;
872	  box-shadow: var(--shadow-md);
873	  transition: var(--transition-fast);
874	}
875
876	.chat-fab:hover {
877	  background: var(--accent-700);
878	  box-shadow: var(--shadow-lg);
879	}
880
881	.chat-window {
882	  position: fixed;
883	  bottom: 80px;
884	  right: var(--space-5);
885	  width: 380px;
886	  max-height: 500px;
887	  background: var(--bg-primary);
888	  border: 1px solid var(--border-light);
889	  border-radius: var(--radius-lg);
890	  box-shadow: var(--shadow-lg);
891	  z-index: 40;
892	  display: flex;
893	  flex-direction: column;
894	}
895
896	.chat-header {
897	  padding: var(--space-3) var(--space-4);
898	  border-bottom: 1px solid var(--border-light);
899	  font-family: var(--font-display);
900	  font-size: var(--text-lg);
901	  font-weight: var(--weight-semibold);
902	}
903
904	.chat-messages {
905	  flex: 1;
906	  overflow-y: auto;
907	  padding: var(--space-4);
908	  display: flex;
909	  flex-direction: column;
910	  gap: var(--space-3);
911	}
912
913	.chat-msg-user {
914	  align-self: flex-end;
915	  background: var(--accent-600);
916	  color: var(--color-white);
917	  padding: var(--space-2) var(--space-3);
918	  border-radius: var(--radius-md);
919	  max-width: 80%;
920	  font-size: var(--text-sm);
921	}
922
923	.chat-msg-ai {
924	  align-self: flex-start;
925	  background: var(--bg-secondary);
926	  color: var(--text-primary);
927	  padding: var(--space-2) var(--space-3);
928	  border-radius: var(--radius-md);
929	  max-width: 80%;
930	  font-size: var(--text-sm);
931	  line-height: var(--leading-relaxed);
932	}
933
934	.chat-input-row {
935	  display: flex;
936	  gap: var(--space-2);
937	  padding: var(--space-3) var(--space-4);
938	  border-top: 1px solid var(--border-light);
939	}
940	```
941
942	## Empty States
943
944	```css
945	.empty-state {
946	  display: flex;
947	  flex-direction: column;
948	  align-items: center;
949	  justify-content: center;
950	  padding: var(--space-16) var(--space-8);
951	  text-align: center;
952	}
953
954	.empty-state-icon {
955	  font-size: 48px;
956	  margin-bottom: var(--space-4);
957	}
958
959	.empty-state-title {
960	  font-family: var(--font-display);
961	  font-size: var(--text-2xl);
962	  font-weight: var(--weight-bold);
963	  color: var(--text-primary);
964	  margin-bottom: var(--space-2);
965	}
966
967	.empty-state-description {
968	  font-size: var(--text-base);
969	  color: var(--text-secondary);
970	  max-width: 400px;
971	  line-height: var(--leading-relaxed);
972	  margin-bottom: var(--space-5);
973	}
974	```
975
976	## Navigation Bar
977
978	Top horizontal nav for multi-page apps.
979
980	```css
981	.navbar {
982	  position: sticky;
983	  top: 0;
984	  z-index: 20;
985	  height: var(--navbar-height);
986	  background: var(--bg-primary);
987	  border-bottom: 1px solid var(--border-light);
988	  display: flex;
989	  align-items: center;
990	  padding: 0 var(--space-5);
991	  gap: var(--space-6);
992	}
993
994	.navbar-brand {
995	  font-family: var(--font-display);
996	  font-size: var(--text-lg);
997	  font-weight: var(--weight-bold);
998	  color: var(--text-primary);
999	  display: flex;
1000	  align-items: center;
1001	  gap: var(--space-2);
1002	}
1003
1004	.navbar-links {
1005	  display: flex;
1006	  align-items: center;
1007	  gap: var(--space-1);
1008	}
1009
1010	.navbar-link {
1011	  padding: var(--space-2) var(--space-3);
1012	  font-size: var(--text-sm);
1013	  font-weight: var(--weight-medium);
1014	  color: var(--text-secondary);
1015	  border-radius: var(--radius-sm);
1016	  transition: var(--transition-fast);
1017	}
1018
1019	.navbar-link:hover {
1020	  color: var(--text-primary);
1021	  background: var(--bg-hover);
1022	  text-decoration: none;
1023	}
1024
1025	.navbar-link.active {
1026	  color: var(--accent-600);
1027	  background: var(--accent-100);
1028	}
1029
1030	.navbar-hamburger {
1031	  display: none;
1032	  width: 32px;
1033	  height: 32px;
1034	  align-items: center;
1035	  justify-content: center;
1036	  cursor: pointer;
1037	}
1038
1039	@media (max-width: 960px) {
1040	  .navbar-hamburger { display: flex; }
1041	  .navbar-links { display: none; }
1042	  .navbar-links.open {
1043	    display: flex;
1044	    flex-direction: column;
1045	    position: absolute;
1046	    top: var(--navbar-height);
1047	    left: 0;
1048	    right: 0;
1049	    background: var(--bg-primary);
1050	    border-bottom: 1px solid var(--border-light);
1051	    padding: var(--space-2);
1052	    box-shadow: var(--shadow-md);
1053	  }
1054	}
1055	```
1056
[result-id: r41]

# EZ Design System — Component Patterns

Concrete code patterns for the EZ Design System. Use these as the building blocks when implementing UIs.

## Table of Contents

1. [Sidebar](#sidebar)
2. [Overlay Boxes](#overlay-boxes)
3. [Stat Display](#stat-display)
4. [Section Pattern](#section-pattern)
5. [List Items](#list-items)
6. [Badges & Tags](#badges--tags)
7. [Detail Panel](#detail-panel)
8. [Compact Items](#compact-items)
9. [Summary Bar](#summary-bar)
10. [Timeline](#timeline)
11. [Interactive Cards](#interactive-cards)
12. [Cost/Breakdown Rows](#costbreakdown-rows)
13. [Buttons](#buttons)
14. [Form Inputs](#form-inputs)
15. [Chat Panel](#chat-panel)
16. [Empty States](#empty-states)
17. [Navigation Bar](#navigation-bar)

---

## Sidebar

240px collapsible left panel. Collapses to 44px icon bar. At 960px, disappears with mobile toggle.

```css
.sidebar {
  position: fixed;
  top: 0;
  left: 0;
  bottom: 0;
  width: var(--sidebar-width);
  background: var(--bg-primary);
  border-right: 1px solid var(--border-light);
  display: flex;
  flex-direction: column;
  z-index: 20;
  transition: width var(--transition-base);
  overflow-y: auto;
}

.sidebar-brand {
  padding: var(--space-4) var(--space-4);
  font-family: var(--font-display);
  font-size: var(--text-lg);
  font-weight: var(--weight-bold);
  color: var(--text-primary);
  display: flex;
  align-items: center;
  gap: var(--space-2);
}

.sidebar-nav {
  padding: var(--space-2) var(--space-3);
}

.sidebar-nav-item {
  display: flex;
  align-items: center;
  gap: var(--space-2);
  padding: var(--space-2) var(--space-3);
  border-radius: var(--radius-md);
  font-size: var(--text-sm);
  font-weight: var(--weight-medium);
  color: var(--text-secondary);
  cursor: pointer;
  transition: var(--transition-fast);
}

.sidebar-nav-item:hover {
  background: var(--bg-hover);
  color: var(--text-primary);
}

.sidebar-nav-item.active {
  background: var(--accent-100);
  color: var(--accent-600);
}

.sidebar-section-label {
  font-size: 10px;
  font-weight: var(--weight-semibold);
  text-transform: uppercase;
  letter-spacing: 0.5px;
  color: var(--text-tertiary);
  padding: var(--space-4) var(--space-3) var(--space-1);
}

.sidebar-divider {
  height: 1px;
  background: var(--border-light);
  margin: var(--space-3) var(--space-3);
}

.sidebar-stats {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: var(--space-2);
  padding: var(--space-3);
}

.sidebar-stat-value {
  font-family: var(--font-display);
  font-size: var(--text-2xl);
  font-weight: var(--weight-bold);
  color: var(--text-primary);
}

.sidebar-stat-label {
  font-size: var(--text-xs);
  color: var(--text-tertiary);
}

.sidebar-footer {
  margin-top: auto;
  padding: var(--space-3);
  border-top: 1px solid var(--border-light);
}
```

## Overlay Boxes

Floating stat/control panels positioned over main content.

```css
.overlay-box {
  position: absolute;
  z-index: 10;
  padding: var(--space-3) var(--space-4);
  background: var(--bg-primary);
  border: 1px solid var(--border-light);
  border-radius: var(--radius-md);
  box-shadow: var(--shadow-sm);
}

.overlay-stack {
  position: absolute;
  top: var(--space-8);
  left: var(--space-4);
  display: flex;
  flex-direction: column;
  gap: var(--space-2);
  z-index: 10;
}

.overlay-controls {
  position: absolute;
  top: var(--space-8);
  right: var(--space-4);
  display: flex;
  flex-direction: column;
  gap: var(--space-1);
  z-index: 10;
}

.overlay-control-btn {
  width: 32px;
  height: 32px;
  display: flex;
  align-items: center;
  justify-content: center;
  background: var(--bg-primary);
  border: 1px solid var(--border-light);
  border-radius: var(--radius-sm);
  font-size: var(--text-sm);
  cursor: pointer;
  transition: var(--transition-fast);
}

.overlay-control-btn:hover {
  background: var(--bg-hover);
  border-color: var(--border-hover);
}
```

## Stat Display

Big numbers for dashboard KPIs and hero sections.

```css
/* Hero/showcase stat (56px) */
.stat-hero {
  text-align: center;
}
.stat-hero-value {
  font-family: var(--font-display);
  font-size: 56px;
  font-weight: var(--weight-bold);
  color: var(--accent-500);
  line-height: 1.1;
}
.stat-hero-label {
  font-family: var(--font-display);
  font-size: var(--text-lg);
  font-weight: var(--weight-semibold);
  color: var(--text-primary);
  margin-top: var(--space-2);
}
.stat-hero-sub {
  font-size: var(--text-sm);
  color: var(--text-tertiary);
  margin-top: var(--space-1);
}

/* Dashboard KPI card */
.kpi-card {
  padding: var(--space-4) var(--space-5);
  background: var(--bg-primary);
  border: 1px solid var(--border-light);
  border-radius: var(--radius-md);
}
.kpi-value {
  font-family: var(--font-display);
  font-size: var(--text-3xl);
  font-weight: var(--weight-bold);
  color: var(--text-primary);
}
.kpi-label {
  font-size: var(--text-sm);
  color: var(--text-secondary);
  margin-top: var(--space-1);
}
.kpi-change {
  font-size: var(--text-xs);
  font-family: var(--font-mono);
  margin-top: var(--space-1);
}
.kpi-change.positive { color: var(--color-success); }
.kpi-change.negative { color: var(--color-error); }

/* Sidebar stat (20px) */
.stat-compact-value {
  font-family: var(--font-display);
  font-size: var(--text-2xl);
  font-weight: var(--weight-bold);
  color: var(--text-primary);
}
.stat-compact-label {
  font-size: var(--text-xs);
  color: var(--text-tertiary);
}
```

## Section Pattern

Alternating background sections for landing/journey pages.

```css
.section {
  padding: 72px var(--space-8);
  background: var(--bg-primary);
}

.section-alt {
  padding: 72px var(--space-8);
  background: var(--bg-secondary);
}

.section-label {
  font-size: 10px;
  font-weight: var(--weight-semibold);
  text-transform: uppercase;
  letter-spacing: 0.5px;
  color: var(--accent-600);
  margin-bottom: var(--space-3);
}

.section-heading {
  font-family: var(--font-display);
  font-size: var(--text-3xl);
  font-weight: var(--weight-bold);
  color: var(--text-primary);
  margin-bottom: var(--space-3);
}

.section-description {
  font-size: var(--text-md);
  color: var(--text-secondary);
  max-width: 640px;
  line-height: var(--leading-relaxed);
  margin-bottom: var(--space-8);
}

.section-grid {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: var(--space-6);
}

@media (max-width: 960px) {
  .section-grid { grid-template-columns: repeat(2, 1fr); }
}
@media (max-width: 640px) {
  .section-grid { grid-template-columns: 1fr; }
  .section, .section-alt { padding: var(--space-10) var(--space-4); }
}
```

## List Items

Explore view rows with hover animation.

```css
.list-item {
  display: flex;
  flex-direction: column;
  gap: var(--space-1);
  padding: var(--space-4) var(--space-4);
  border-bottom: 1px solid var(--border-light);
  cursor: pointer;
  transition: var(--transition-fast);
  transform: translateX(0);
}

.list-item:hover {
  background: var(--bg-hover);
  transform: translateX(2px);
}

.list-item-header {
  display: flex;
  align-items: center;
  gap: var(--space-2);
}

.list-item-title {
  font-size: var(--text-base);
  font-weight: var(--weight-medium);
  color: var(--text-primary);
  flex: 1;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.list-item-significance {
  font-family: var(--font-mono);
  font-size: var(--text-sm);
  font-weight: var(--weight-medium);
  color: var(--accent-600);
}

.list-item-meta {
  display: flex;
  align-items: center;
  gap: var(--space-3);
  font-size: var(--text-xs);
  color: var(--text-tertiary);
}

.list-item-summary {
  font-size: var(--text-sm);
  color: var(--text-secondary);
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
```

## Badges & Tags

Pill-shaped badges for categorization.

```css
.badge {
  display: inline-flex;
  align-items: center;
  padding: 2px var(--space-2);
  font-size: var(--text-xs);
  font-weight: var(--weight-semibold);
  text-transform: uppercase;
  letter-spacing: 0.3px;
  border-radius: var(--radius-full);
  background: var(--bg-tertiary);
  color: var(--text-secondary);
}

.badge-accent {
  background: var(--accent-100);
  color: var(--accent-600);
}

.badge-success { background: #dcfce7; color: #166534; }
.badge-warning { background: #fef3c7; color: #92400e; }
.badge-error   { background: #fee2e2; color: #991b1b; }
.badge-info    { background: #dbeafe; color: #1e40af; }

.tag {
  display: inline-flex;
  align-items: center;
  padding: var(--space-1) var(--space-3);
  font-size: var(--text-sm);
  border: 1px solid var(--border-light);
  border-radius: var(--radius-full);
  color: var(--text-secondary);
  cursor: pointer;
  transition: var(--transition-fast);
}

.tag:hover {
  background: var(--bg-hover);
  border-color: var(--border-hover);
  color: var(--text-primary);
}
```

## Detail Panel

Right-side slide-in panel for item details.

```css
.detail-panel {
  position: fixed;
  top: 0;
  right: 0;
  bottom: 0;
  width: var(--panel-width);
  background: var(--bg-primary);
  border-left: 1px solid var(--border-light);
  box-shadow: var(--shadow-lg);
  z-index: 30;
  overflow-y: auto;
  transform: translateX(0);
  transition: transform var(--transition-base);
}

.detail-panel.hidden {
  transform: translateX(100%);
}

.detail-breadcrumb {
  display: flex;
  align-items: center;
  gap: var(--space-1);
  padding: var(--space-3) var(--space-4);
  font-size: var(--text-xs);
  color: var(--text-tertiary);
  border-bottom: 1px solid var(--border-light);
}

.detail-breadcrumb a {
  color: var(--text-tertiary);
}

.detail-breadcrumb a:hover {
  color: var(--text-accent);
}

.detail-content {
  padding: var(--space-5);
}

.detail-title {
  font-family: var(--font-display);
  font-size: var(--text-2xl);
  font-weight: var(--weight-bold);
  color: var(--text-primary);
  margin-bottom: var(--space-3);
}

.detail-badges {
  display: flex;
  flex-wrap: wrap;
  gap: var(--space-2);
  margin-bottom: var(--space-4);
}

.detail-description {
  font-size: var(--text-base);
  color: var(--text-secondary);
  line-height: var(--leading-relaxed);
  margin-bottom: var(--space-5);
}

.detail-section-label {
  font-size: var(--text-xs);
  font-weight: var(--weight-semibold);
  text-transform: uppercase;
  letter-spacing: 0.5px;
  color: var(--text-tertiary);
  margin-bottom: var(--space-2);
  margin-top: var(--space-5);
}

.detail-metrics {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: var(--space-3);
}

.detail-metric-value {
  font-family: var(--font-mono);
  font-size: var(--text-lg);
  font-weight: var(--weight-medium);
  color: var(--text-primary);
}

.detail-metric-label {
  font-size: var(--text-xs);
  color: var(--text-tertiary);
}
```

## Compact Items

Sidebar stats, trending items, log entries.

```css
.compact-item {
  display: flex;
  align-items: center;
  gap: var(--space-2);
  font-size: var(--text-xs);
  padding: var(--space-1) 0;
}

.compact-label {
  color: var(--text-secondary);
  flex: 1;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.compact-value {
  color: var(--text-tertiary);
  font-family: var(--font-mono);
  font-weight: var(--weight-medium);
  flex-shrink: 0;
}

.compact-indicator {
  width: 8px;
  height: 8px;
  border-radius: 50%;
  flex-shrink: 0;
}
```

## Summary Bar

Horizontal row of key metrics with dividers.

```css
.summary-bar {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: var(--space-8);
  padding: var(--space-6) var(--space-8);
  border: 1px solid var(--border-light);
  border-radius: var(--radius-lg);
  background: var(--bg-secondary);
}

.summary-item {
  text-align: center;
}

.summary-value {
  font-family: var(--font-display);
  font-size: var(--text-3xl);
  font-weight: var(--weight-bold);
  color: var(--text-primary);
}

.summary-label {
  font-size: var(--text-sm);
  color: var(--text-secondary);
  margin-top: var(--space-1);
}

.summary-divider {
  width: 1px;
  height: 36px;
  background: var(--border-light);
}

@media (max-width: 640px) {
  .summary-bar {
    flex-direction: column;
    gap: var(--space-4);
  }
  .summary-divider {
    width: 48px;
    height: 1px;
  }
}
```

## Timeline

Vertical timeline with dot + line markers.

```css
.timeline-item {
  display: flex;
  gap: var(--space-4);
}

.timeline-marker {
  display: flex;
  flex-direction: column;
  align-items: center;
  width: 20px;
  flex-shrink: 0;
}

.timeline-dot {
  width: 10px;
  height: 10px;
  border-radius: 50%;
  background: var(--accent-500);
  border: 2px solid var(--bg-primary);
  flex-shrink: 0;
}

.timeline-line {
  width: 2px;
  flex: 1;
  background: var(--border-light);
}

.timeline-content {
  padding-bottom: var(--space-6);
}

.timeline-date {
  font-size: var(--text-xs);
  font-family: var(--font-mono);
  color: var(--text-muted);
  margin-bottom: var(--space-1);
}

.timeline-title {
  font-size: var(--text-base);
  font-weight: var(--weight-medium);
  color: var(--text-primary);
  margin-bottom: var(--space-1);
}

.timeline-description {
  font-size: var(--text-sm);
  color: var(--text-secondary);
  line-height: var(--leading-relaxed);
}
```

## Interactive Cards

Expandable list items with hover/active states.

```css
.card {
  padding: var(--space-4) var(--space-5);
  background: var(--bg-primary);
  border: 1px solid var(--border-light);
  border-radius: var(--radius-md);
  transition: var(--transition-fast);
}

.card:hover {
  border-color: var(--border-hover);
  box-shadow: var(--shadow-sm);
}

.stack-item {
  padding: var(--space-3) var(--space-4);
  cursor: pointer;
  border: 1px solid transparent;
  border-radius: var(--radius-md);
  transition: var(--transition-fast);
}

.stack-item:hover {
  background: var(--bg-hover);
  border-color: var(--border-light);
}

.stack-item.active {
  background: var(--bg-secondary);
  border-color: var(--border-default);
}

.stack-item-title {
  font-size: var(--text-base);
  font-weight: var(--weight-medium);
  color: var(--text-primary);
}

.stack-item-meta {
  font-size: var(--text-xs);
  color: var(--text-tertiary);
  margin-top: var(--space-1);
}
```

## Cost/Breakdown Rows

Tabular breakdowns with visual bars.

```css
.breakdown-row {
  display: grid;
  grid-template-columns: 1fr 100px 80px 1fr;
  gap: var(--space-2);
  align-items: center;
  padding: var(--space-3) 0;
  border-bottom: 1px solid var(--border-light);
}

.breakdown-label {
  font-size: var(--text-sm);
  color: var(--text-primary);
}

.breakdown-value {
  font-family: var(--font-mono);
  font-size: var(--text-sm);
  font-weight: var(--weight-medium);
  color: var(--text-primary);
  text-align: right;
}

.breakdown-pct {
  font-family: var(--font-mono);
  font-size: var(--text-xs);
  color: var(--text-tertiary);
  text-align: right;
}

.breakdown-bar {
  height: 6px;
  background: var(--bg-tertiary);
  border-radius: var(--radius-full);
  overflow: hidden;
}

.breakdown-bar-fill {
  height: 100%;
  border-radius: var(--radius-full);
  background: var(--accent-500);
  transition: width var(--transition-base);
}
```

## Buttons

```css
.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: var(--space-2);
  padding: var(--space-2) var(--space-4);
  font-size: var(--text-sm);
  font-weight: var(--weight-medium);
  border-radius: var(--radius-sm);
  transition: var(--transition-fast);
  cursor: pointer;
}

.btn-primary {
  background: var(--accent-600);
  color: var(--color-white);
  border: none;
}

.btn-primary:hover {
  background: var(--accent-700);
}

.btn-secondary {
  background: transparent;
  color: var(--text-primary);
  border: 1px solid var(--border-default);
}

.btn-secondary:hover {
  background: var(--bg-hover);
  border-color: var(--border-hover);
}

.btn-ghost {
  background: transparent;
  color: var(--text-secondary);
  border: none;
}

.btn-ghost:hover {
  background: var(--bg-hover);
  color: var(--text-primary);
}

.btn:disabled {
  opacity: 0.3;
  cursor: not-allowed;
}
```

## Form Inputs

```css
.input {
  height: 30px;
  padding: 0 var(--space-3);
  font-size: var(--text-sm);
  color: var(--text-primary);
  background: var(--bg-primary);
  border: 1px solid var(--border-light);
  border-radius: var(--radius-sm);
  transition: var(--transition-fast);
  width: 100%;
}

.input:hover {
  border-color: var(--border-hover);
}

.input:focus {
  border-color: var(--border-focus);
  outline: none;
  box-shadow: 0 0 0 2px var(--accent-100);
}

.select {
  height: 30px;
  padding: 0 var(--space-3);
  font-size: var(--text-sm);
  color: var(--text-primary);
  background: var(--bg-secondary);
  border: 1px solid var(--border-light);
  border-radius: var(--radius-sm);
  cursor: pointer;
}

.label {
  font-size: var(--text-xs);
  font-weight: var(--weight-semibold);
  text-transform: uppercase;
  letter-spacing: 0.5px;
  color: var(--text-tertiary);
  margin-bottom: var(--space-1);
}
```

## Chat Panel

Floating AI assistant widget (bottom-right).

```css
.chat-fab {
  position: fixed;
  bottom: var(--space-5);
  right: var(--space-5);
  z-index: 40;
  width: 48px;
  height: 48px;
  border-radius: 50%;
  background: var(--accent-600);
  color: var(--color-white);
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: var(--text-xl);
  cursor: pointer;
  box-shadow: var(--shadow-md);
  transition: var(--transition-fast);
}

.chat-fab:hover {
  background: var(--accent-700);
  box-shadow: var(--shadow-lg);
}

.chat-window {
  position: fixed;
  bottom: 80px;
  right: var(--space-5);
  width: 380px;
  max-height: 500px;
  background: var(--bg-primary);
  border: 1px solid var(--border-light);
  border-radius: var(--radius-lg);
  box-shadow: var(--shadow-lg);
  z-index: 40;
  display: flex;
  flex-direction: column;
}

.chat-header {
  padding: var(--space-3) var(--space-4);
  border-bottom: 1px solid var(--border-light);
  font-family: var(--font-display);
  font-size: var(--text-lg);
  font-weight: var(--weight-semibold);
}

.chat-messages {
  flex: 1;
  overflow-y: auto;
  padding: var(--space-4);
  display: flex;
  flex-direction: column;
  gap: var(--space-3);
}

.chat-msg-user {
  align-self: flex-end;
  background: var(--accent-600);
  color: var(--color-white);
  padding: var(--space-2) var(--space-3);
  border-radius: var(--radius-md);
  max-width: 80%;
  font-size: var(--text-sm);
}

.chat-msg-ai {
  align-self: flex-start;
  background: var(--bg-secondary);
  color: var(--text-primary);
  padding: var(--space-2) var(--space-3);
  border-radius: var(--radius-md);
  max-width: 80%;
  font-size: var(--text-sm);
  line-height: var(--leading-relaxed);
}

.chat-input-row {
  display: flex;
  gap: var(--space-2);
  padding: var(--space-3) var(--space-4);
  border-top: 1px solid var(--border-light);
}
```

## Empty States

```css
.empty-state {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  padding: var(--space-16) var(--space-8);
  text-align: center;
}

.empty-state-icon {
  font-size: 48px;
  margin-bottom: var(--space-4);
}

.empty-state-title {
  font-family: var(--font-display);
  font-size: var(--text-2xl);
  font-weight: var(--weight-bold);
  color: var(--text-primary);
  margin-bottom: var(--space-2);
}

.empty-state-description {
  font-size: var(--text-base);
  color: var(--text-secondary);
  max-width: 400px;
  line-height: var(--leading-relaxed);
  margin-bottom: var(--space-5);
}
```

## Navigation Bar

Top horizontal nav for multi-page apps.

```css
.navbar {
  position: sticky;
  top: 0;
  z-index: 20;
  height: var(--navbar-height);
  background: var(--bg-primary);
  border-bottom: 1px solid var(--border-light);
  display: flex;
  align-items: center;
  padding: 0 var(--space-5);
  gap: var(--space-6);
}

.navbar-brand {
  font-family: var(--font-display);
  font-size: var(--text-lg);
  font-weight: var(--weight-bold);
  color: var(--text-primary);
  display: flex;
  align-items: center;
  gap: var(--space-2);
}

.navbar-links {
  display: flex;
  align-items: center;
  gap: var(--space-1);
}

.navbar-link {
  padding: var(--space-2) var(--space-3);
  font-size: var(--text-sm);
  font-weight: var(--weight-medium);
  color: var(--text-secondary);
  border-radius: var(--radius-sm);
  transition: var(--transition-fast);
}

.navbar-link:hover {
  color: var(--text-primary);
  background: var(--bg-hover);
  text-decoration: none;
}

.navbar-link.active {
  color: var(--accent-600);
  background: var(--accent-100);
}

.navbar-hamburger {
  display: none;
  width: 32px;
  height: 32px;
  align-items: center;
  justify-content: center;
  cursor: pointer;
}

@media (max-width: 960px) {
  .navbar-hamburger { display: flex; }
  .navbar-links { display: none; }
  .navbar-links.open {
    display: flex;
    flex-direction: column;
    position: absolute;
    top: var(--navbar-height);
    left: 0;
    right: 0;
    background: var(--bg-primary);
    border-bottom: 1px solid var(--border-light);
    padding: var(--space-2);
    box-shadow: var(--shadow-md);
  }
}
```


Clear picture. The txt file is a spec for two new pages; the ez-design-system is a structural/layout reference. I'll build both pages for the DEWA project using its existing design tokens, using the ez patterns for structure (sections, timeline, breakdown bars, stats rows). Let me get accurate build stats first, then write everything.


Bash

cd "/Users/khalidbinkalban/Desktop/My Workstation/dewa-ai-adoption" && \
  echo "=== File count ===" && \
  find src content -type f \( -name "*.tsx" -o -name "*.ts" -o -name "*.css" \) | grep -v node_modules | wc -l && \
  echo "=== Lines of code ===" && \
  find src content -type f \( -name "*.tsx" -o -name "*.ts" -o -name "*.css" \) | grep -v node_modules | xargs wc -l 2>/dev/null | tail -1 && \
  echo "=== Component files ===" && \
  find src/components -name "*.tsx" | wc -l && \
  echo "=== Content files ===" && \
  find content -name "*.ts" | wc -l && \
  echo "=== All files list ===" && \
  find src content -type f \( -name "*.tsx" -o -name "*.ts" \) | grep -v node_modules | sort

Count files and lines of code for Vibe Stats page


=== File count ===
      36
=== Lines of code ===
    2977 total
=== Component files ===
      22
=== Content files ===
       7
=== All files list ===
content/department.ts
content/governance.ts
content/kpis.ts
content/operating-model.ts
content/risks.ts
content/roadmap.ts
content/sections.ts
src/app/layout.tsx
src/app/page.tsx
src/components/governance/DecisionLayer.tsx
src/components/governance/GovernanceMap.tsx
src/components/governance/PrincipleCard.tsx
src/components/impact/StrategicImpact.tsx
src/components/kpis/KpiCard.tsx
src/components/kpis/KpiCockpit.tsx
src/components/kpis/KpiTargetBar.tsx
src/components/layout/SectionWrapper.tsx
src/components/layout/SiteNav.tsx
src/components/operating-model/FlowStage.tsx
src/components/operating-model/OperatingFlow.tsx
src/components/overview/HeroBanner.tsx
src/components/overview/KpiStrip.tsx
src/components/overview/MissionStatement.tsx
src/components/overview/ValuePillars.tsx
src/components/responsibilities/ResponsibilityPanel.tsx
src/components/risks/RiskCard.tsx
src/components/risks/RiskRegister.tsx
src/components/roadmap/RoadmapView.tsx
src/components/structure/DepartmentMap.tsx
src/components/structure/SectionCard.tsx
src/components/ui/button.tsx
src/hooks/useActiveSection.ts
src/hooks/useCountUp.ts
src/lib/tokens.ts
src/lib/utils.ts
[result-id: r42]
[rerun: b20]


cd "/Users/khalidbinkalban/Desktop/My Workstation/dewa-ai-adoption" && \
  echo "=== Components ===" && \
  find src/components -name "*.tsx" | xargs wc -l | tail -1 && \
  echo "=== Content ===" && \
  find content -name "*.ts" | xargs wc -l | tail -1 && \
  echo "=== App + Layout ===" && \
  find src/app -type f | xargs wc -l | tail -1 && \
  echo "=== Hooks + Lib ===" && \
  find src/hooks src/lib -type f | xargs wc -l | tail -1

Line counts by category


=== Components ===
    1615 total
=== Content ===
    1049 total
=== App + Layout ===
     692 total
=== Hooks + Lib ===
     132 total
[rerun: b21]


Real numbers: 36 files, 2,977 lines, 22 components, 7 content files. Now I'll build both pages. Creating content files first, then pages, then nav update:


Write

export interface JourneyHeroStat {
  label: string
  value: string
  unit: string
}

export interface ChallengeCard {
  number: string
  title: string
  description: string
}

export interface SolutionStep {
  number: number
  title: string
  description: string
  owner: string
  ownerColor: string
}

export interface TechCard {
  name: string
  description: string
  badge: string
}

export const journeyHero = {
  badge: 'DEWA AI Adoption Department',
  title: 'Bringing Enterprise AI from Strategy to Scale',
  description:
    'A centralized operating model that accelerates AI adoption across DEWA — connecting capability building, strategic governance, and real-time performance visibility into a unified enterprise AI engine.',
  stats: [
    { label: 'Enterprise Adoption Rate', value: '68', unit: '%' },
    { label: 'Active AI Users', value: '3,240', unit: '' },
    { label: 'Hours Saved This Quarter', value: '18,600', unit: 'hrs' },
    { label: 'Active Use Cases', value: '42', unit: '' },
  ] as JourneyHeroStat[],
}

export const challengeCards: ChallengeCard[] = [
  {
    number: '01',
    title: 'Scale Without Structure Fails',
    description:
      'With 12 divisions and 4,800+ employees across DEWA, AI tools introduced without a structured adoption engine create fragmented usage, inconsistent capability, and no measurable enterprise return.',
  },
  {
    number: '02',
    title: '42 Use Cases Require Oversight',
    description:
      'Managing active AI use cases simultaneously demands a governance layer that ensures every initiative is strategically aligned, risk-assessed, ethics-reviewed, and business-value tracked before it scales.',
  },
  {
    number: '03',
    title: 'Leadership Needs Live Visibility',
    description:
      'Executive decisions about AI investment and scale require real-time validated performance data — not periodic snapshots or siloed team reporting from individual business units.',
  },
]

export const solutionSteps: SolutionStep[] = [
  {
    number: 1,
    title: 'Centralize Strategy',
    description:
      'The AI Adoption Office serves as the strategic backbone — aligning every AI initiative to DEWA objectives, coordinating governance forums, and managing the AI Champions network across all 12 divisions.',
    owner: 'AI Adoption Office',
    ownerColor: 'text-primary',
  },
  {
    number: 2,
    title: 'Accelerate Adoption',
    description:
      'AI Acceleration drives the programs, campaigns, partner engagements, and enablement workshops that move AI from individual tools to enterprise-scale capability for every business unit.',
    owner: 'AI Acceleration',
    ownerColor: 'text-accent',
  },
  {
    number: 3,
    title: 'Monitor and Measure',
    description:
      'The AI Command Center provides the real-time intelligence layer — translating adoption signals into live dashboards, KPI scorecards, and executive briefing packs that drive data-driven decisions.',
    owner: 'AI Command Center',
    ownerColor: 'text-gold',
  },
  {
    number: 4,
    title: 'Govern and Scale',
    description:
      'Every use case passes through structured governance checkpoints — risk review, compliance validation, ethics assessment, and maturity gating — before it scales across DEWA.',
    owner: 'AI Governance Framework',
    ownerColor: 'text-success',
  },
]

export const techStack: TechCard[] = [
  { name: 'Next.js 14', description: 'App Router, static generation', badge: 'Framework' },
  { name: 'TypeScript', description: 'Strict mode throughout', badge: 'Language' },
  { name: 'Tailwind CSS', description: 'Design token-driven utilities', badge: 'Styling' },
  { name: 'shadcn/ui', description: 'New York style, dark mode', badge: 'Components' },
  { name: 'Framer Motion', description: 'Entrance and hover animations', badge: 'Animation' },
  { name: 'Recharts', description: 'KPI trend visualisation', badge: 'Charts' },
  { name: 'Lucide React', description: 'Consistent icon system', badge: 'Icons' },
  { name: 'Inter', description: 'Primary typeface via next/font', badge: 'Typography' },
]


File created successfully at: /Users/khalidbinkalban/Desktop/My Workstation/dewa-ai-adoption/content/journey.ts

export interface JourneyHeroStat {
  label: string
  value: string
  unit: string
}

export interface ChallengeCard {
  number: string
  title: string
  description: string
}

export interface SolutionStep {
  number: number
  title: string
  description: string
  owner: string
  ownerColor: string
}

export interface TechCard {
  name: string
  description: string
  badge: string
}

export const journeyHero = {
  badge: 'DEWA AI Adoption Department',
  title: 'Bringing Enterprise AI from Strategy to Scale',
  description:
    'A centralized operating model that accelerates AI adoption across DEWA — connecting capability building, strategic governance, and real-time performance visibility into a unified enterprise AI engine.',
  stats: [
    { label: 'Enterprise Adoption Rate', value: '68', unit: '%' },
    { label: 'Active AI Users', value: '3,240', unit: '' },
    { label: 'Hours Saved This Quarter', value: '18,600', unit: 'hrs' },
    { label: 'Active Use Cases', value: '42', unit: '' },
  ] as JourneyHeroStat[],
}

export const challengeCards: ChallengeCard[] = [
  {
    number: '01',
    title: 'Scale Without Structure Fails',
    description:
      'With 12 divisions and 4,800+ employees across DEWA, AI tools introduced without a structured adoption engine create fragmented usage, inconsistent capability, and no measurable enterprise return.',
  },
  {
    number: '02',
    title: '42 Use Cases Require Oversight',
    description:
      'Managing active AI use cases simultaneously demands a governance layer that ensures every initiative is strategically aligned, risk-assessed, ethics-reviewed, and business-value tracked before it scales.',
  },
  {
    number: '03',
    title: 'Leadership Needs Live Visibility',
    description:
      'Executive decisions about AI investment and scale require real-time validated performance data — not periodic snapshots or siloed team reporting from individual business units.',
  },
]

export const solutionSteps: SolutionStep[] = [
  {
    number: 1,
    title: 'Centralize Strategy',
    description:
      'The AI Adoption Office serves as the strategic backbone — aligning every AI initiative to DEWA objectives, coordinating governance forums, and managing the AI Champions network across all 12 divisions.',
    owner: 'AI Adoption Office',
    ownerColor: 'text-primary',
  },
  {
    number: 2,
    title: 'Accelerate Adoption',
    description:
      'AI Acceleration drives the programs, campaigns, partner engagements, and enablement workshops that move AI from individual tools to enterprise-scale capability for every business unit.',
    owner: 'AI Acceleration',
    ownerColor: 'text-accent',
  },
  {
    number: 3,
    title: 'Monitor and Measure',
    description:
      'The AI Command Center provides the real-time intelligence layer — translating adoption signals into live dashboards, KPI scorecards, and executive briefing packs that drive data-driven decisions.',
    owner: 'AI Command Center',
    ownerColor: 'text-gold',
  },
  {
    number: 4,
    title: 'Govern and Scale',
    description:
      'Every use case passes through structured governance checkpoints — risk review, compliance validation, ethics assessment, and maturity gating — before it scales across DEWA.',
    owner: 'AI Governance Framework',
    ownerColor: 'text-success',
  },
]

export const techStack: TechCard[] = [
  { name: 'Next.js 14', description: 'App Router, static generation', badge: 'Framework' },
  { name: 'TypeScript', description: 'Strict mode throughout', badge: 'Language' },
  { name: 'Tailwind CSS', description: 'Design token-driven utilities', badge: 'Styling' },
  { name: 'shadcn/ui', description: 'New York style, dark mode', badge: 'Components' },
  { name: 'Framer Motion', description: 'Entrance and hover animations', badge: 'Animation' },
  { name: 'Recharts', description: 'KPI trend visualisation', badge: 'Charts' },
  { name: 'Lucide React', description: 'Consistent icon system', badge: 'Icons' },
  { name: 'Inter', description: 'Primary typeface via next/font', badge: 'Typography' },
]


export interface BuildStat {
  label: string
  value: string
  unit: string
  note: string
}

export interface EfficiencyStat {
  label: string
  value: number
  formatted: string
  unit: string
  colorClass: string
}

export interface CodeCategory {
  category: string
  lines: number
  pct: number
  colorClass: string
}

export interface SessionOutput {
  label: string
  value: string
}

export interface BuildPhase {
  phase: string
  title: string
  description: string
}

export interface ToolCard {
  name: string
  description: string
  badge: string
  badgeClass: string
}

export const vibeHero = {
  badge: 'Vibe Coding with Claude Code',
  title: 'Built Entirely by AI',
  description:
    'Every component, content file, animation, and configuration in this executive dashboard was written by Claude Code — with a human providing only high-level direction through natural language prompts. Zero manual code.',
}

export const buildStats: BuildStat[] = [
  {
    label: 'Human Prompts',
    value: '18',
    unit: '',
    note: 'Total instructions given across all phases',
  },
  {
    label: 'Build Sessions',
    value: '3',
    unit: '',
    note: 'Claude Code sessions (Foundation → Sections → Polish)',
  },
  {
    label: 'Build Time',
    value: '~8',
    unit: 'hrs',
    note: 'Wall-clock hours from blank repo to production',
  },
  {
    label: 'Sections Shipped',
    value: '10',
    unit: '',
    note: 'All dashboard sections fully complete',
  },
]

export const efficiencyStats: EfficiencyStat[] = [
  {
    label: 'Lines of Code',
    value: 2977,
    formatted: '2,977',
    unit: 'lines',
    colorClass: 'text-primary',
  },
  {
    label: 'Files Generated',
    value: 36,
    formatted: '36',
    unit: 'files',
    colorClass: 'text-accent',
  },
  {
    label: 'Lines Typed Manually',
    value: 0,
    formatted: '0',
    unit: 'lines',
    colorClass: 'text-success',
  },
]

export const codeBreakdown: CodeCategory[] = [
  { category: 'UI Components', lines: 1615, pct: 54, colorClass: 'bg-primary' },
  { category: 'Content & Type Definitions', lines: 1049, pct: 35, colorClass: 'bg-accent' },
  { category: 'App, Layout & CSS', lines: 692, pct: 23, colorClass: 'bg-gold' },
  { category: 'Hooks & Utilities', lines: 132, pct: 4, colorClass: 'bg-success' },
]

export const sessionOutput: SessionOutput[] = [
  { label: 'Dashboard Sections', value: '10' },
  { label: 'React Components', value: '22' },
  { label: 'TypeScript Content Files', value: '7' },
  { label: 'Custom Hooks', value: '2' },
  { label: 'KPI Cards', value: '11' },
  { label: 'Roadmap Items', value: '12' },
  { label: 'Risk Cards', value: '6' },
  { label: 'Governance Controls', value: '5' },
  { label: 'Operating Stages', value: '9' },
  { label: 'Design Token Variables', value: '40+' },
  { label: 'TypeScript Interfaces', value: '25+' },
  { label: 'Animation Presets', value: '4' },
]

export const buildTimeline: BuildPhase[] = [
  {
    phase: 'Phase 1',
    title: 'Foundation',
    description:
      'Next.js 14 App Router setup with TypeScript strict mode, Tailwind configured with the full DEWA design token system, shadcn/ui in dark mode, all 7 typed content files, root layout with sticky responsive SiteNav, and smooth anchor scroll.',
  },
  {
    phase: 'Phase 2',
    title: 'All 10 Sections',
    description:
      'HeroBanner, MissionStatement, ValuePillars, KpiStrip, DepartmentMap, ResponsibilityPanel, KpiCockpit, GovernanceMap with decision layers and controls table, OperatingFlow with 9 stages, RoadmapView, RiskRegister with expandable mitigations, and StrategicImpact — every component consuming typed content from /content/.',
  },
  {
    phase: 'Phase 3',
    title: 'Polish',
    description:
      'Framer Motion entrance animations and stagger sequences across all sections, count-up hook for KPI numbers, animated KpiTargetBar fill from 0% on scroll, whileHover lift on every card, AnimatePresence for accordion open/close, responsive breakpoint verification, badge typography pass to Design.md spec, and aria-expanded accessibility attributes.',
  },
]

export const toolsUsed: ToolCard[] = [
  {
    name: 'Claude Code',
    description:
      'Anthropic\'s AI coding agent that wrote every line of this codebase from natural language instructions — components, types, animations, config, and content.',
    badge: 'Primary Tool',
    badgeClass: 'bg-primary/10 text-primary border-primary/20',
  },
  {
    name: 'claude-sonnet-4-6',
    description:
      'The Claude model that powered this build. Anthropic\'s latest Sonnet-class model — high capability, fast output, and strong TypeScript reasoning.',
    badge: 'AI Model',
    badgeClass: 'bg-accent/10 text-accent border-accent/20',
  },
  {
    name: 'DEWA Design System',
    description:
      'Custom dark-theme token system defined in Design.md — covering colors, typography, spacing, shadow, animation presets, and component patterns for executive-grade UI.',
    badge: 'Design System',
    badgeClass: 'bg-gold/10 text-gold border-gold/20',
  },
  {
    name: 'Next.js 14 App Router',
    description:
      'Static site generation with TypeScript-first App Router architecture. Every page is pre-rendered — no server required, fully deployable to any CDN.',
    badge: 'Framework',
    badgeClass: 'bg-success/10 text-success border-success/20',
  },
]


File created successfully at: /Users/khalidbinkalban/Desktop/My Workstation/dewa-ai-adoption/content/vibe-stats.ts

export interface BuildStat {
  label: string
  value: string
  unit: string
  note: string
}

export interface EfficiencyStat {
  label: string
  value: number
  formatted: string
  unit: string
  colorClass: string
}

export interface CodeCategory {
  category: string
  lines: number
  pct: number
  colorClass: string
}

export interface SessionOutput {
  label: string
  value: string
}

export interface BuildPhase {
  phase: string
  title: string
  description: string
}

export interface ToolCard {
  name: string
  description: string
  badge: string
  badgeClass: string
}

export const vibeHero = {
  badge: 'Vibe Coding with Claude Code',
  title: 'Built Entirely by AI',
  description:
    'Every component, content file, animation, and configuration in this executive dashboard was written by Claude Code — with a human providing only high-level direction through natural language prompts. Zero manual code.',
}

export const buildStats: BuildStat[] = [
  {
    label: 'Human Prompts',
    value: '18',
    unit: '',
    note: 'Total instructions given across all phases',
  },
  {
    label: 'Build Sessions',
    value: '3',
    unit: '',
    note: 'Claude Code sessions (Foundation → Sections → Polish)',
  },
  {
    label: 'Build Time',
    value: '~8',
    unit: 'hrs',
    note: 'Wall-clock hours from blank repo to production',
  },
  {
    label: 'Sections Shipped',
    value: '10',
    unit: '',
    note: 'All dashboard sections fully complete',
  },
]

export const efficiencyStats: EfficiencyStat[] = [
  {
    label: 'Lines of Code',
    value: 2977,
    formatted: '2,977',
    unit: 'lines',
    colorClass: 'text-primary',
  },
  {
    label: 'Files Generated',
    value: 36,
    formatted: '36',
    unit: 'files',
    colorClass: 'text-accent',
  },
  {
    label: 'Lines Typed Manually',
    value: 0,
    formatted: '0',
    unit: 'lines',
    colorClass: 'text-success',
  },
]

export const codeBreakdown: CodeCategory[] = [
  { category: 'UI Components', lines: 1615, pct: 54, colorClass: 'bg-primary' },
  { category: 'Content & Type Definitions', lines: 1049, pct: 35, colorClass: 'bg-accent' },
  { category: 'App, Layout & CSS', lines: 692, pct: 23, colorClass: 'bg-gold' },
  { category: 'Hooks & Utilities', lines: 132, pct: 4, colorClass: 'bg-success' },
]

export const sessionOutput: SessionOutput[] = [
  { label: 'Dashboard Sections', value: '10' },
  { label: 'React Components', value: '22' },
  { label: 'TypeScript Content Files', value: '7' },
  { label: 'Custom Hooks', value: '2' },
  { label: 'KPI Cards', value: '11' },
  { label: 'Roadmap Items', value: '12' },
  { label: 'Risk Cards', value: '6' },
  { label: 'Governance Controls', value: '5' },
  { label: 'Operating Stages', value: '9' },
  { label: 'Design Token Variables', value: '40+' },
  { label: 'TypeScript Interfaces', value: '25+' },
  { label: 'Animation Presets', value: '4' },
]

export const buildTimeline: BuildPhase[] = [
  {
    phase: 'Phase 1',
    title: 'Foundation',
    description:
      'Next.js 14 App Router setup with TypeScript strict mode, Tailwind configured with the full DEWA design token system, shadcn/ui in dark mode, all 7 typed content files, root layout with sticky responsive SiteNav, and smooth anchor scroll.',
  },
  {
    phase: 'Phase 2',
    title: 'All 10 Sections',
    description:
      'HeroBanner, MissionStatement, ValuePillars, KpiStrip, DepartmentMap, ResponsibilityPanel, KpiCockpit, GovernanceMap with decision layers and controls table, OperatingFlow with 9 stages, RoadmapView, RiskRegister with expandable mitigations, and StrategicImpact — every component consuming typed content from /content/.',
  },
  {
    phase: 'Phase 3',
    title: 'Polish',
    description:
      'Framer Motion entrance animations and stagger sequences across all sections, count-up hook for KPI numbers, animated KpiTargetBar fill from 0% on scroll, whileHover lift on every card, AnimatePresence for accordion open/close, responsive breakpoint verification, badge typography pass to Design.md spec, and aria-expanded accessibility attributes.',
  },
]

export const toolsUsed: ToolCard[] = [
  {
    name: 'Claude Code',
    description:
      'Anthropic\'s AI coding agent that wrote every line of this codebase from natural language instructions — components, types, animations, config, and content.',
    badge: 'Primary Tool',
    badgeClass: 'bg-primary/10 text-primary border-primary/20',
  },
  {
    name: 'claude-sonnet-4-6',
    description:
      'The Claude model that powered this build. Anthropic\'s latest Sonnet-class model — high capability, fast output, and strong TypeScript reasoning.',
    badge: 'AI Model',
    badgeClass: 'bg-accent/10 text-accent border-accent/20',
  },
  {
    name: 'DEWA Design System',
    description:
      'Custom dark-theme token system defined in Design.md — covering colors, typography, spacing, shadow, animation presets, and component patterns for executive-grade UI.',
    badge: 'Design System',
    badgeClass: 'bg-gold/10 text-gold border-gold/20',
  },
  {
    name: 'Next.js 14 App Router',
    description:
      'Static site generation with TypeScript-first App Router architecture. Every page is pre-rendered — no server required, fully deployable to any CDN.',
    badge: 'Framework',
    badgeClass: 'bg-success/10 text-success border-success/20',
  },
]


Now update `tokens.ts` with the page links, then the SiteNav:


Edit

export const navLinks = [
  { label: 'Overview', href: '#overview' },
  { label: 'Structure', href: '#structure' },
  { label: 'Responsibilities', href: '#responsibilities' },
  { label: 'KPIs', href: '#kpis' },
  { label: 'Governance', href: '#governance' },
  { label: 'Operating Model', href: '#operating-model' },
  { label: 'Roadmap', href: '#roadmap' },
  { label: 'Risks', href: '#risks' },
  { label: 'Impact', href: '#impact' },
] as const

export const navLinks = [
  { label: 'Overview', href: '#overview' },
  { label: 'Structure', href: '#structure' },
  { label: 'Responsibilities', href: '#responsibilities' },
  { label: 'KPIs', href: '#kpis' },
  { label: 'Governance', href: '#governance' },
  { label: 'Operating Model', href: '#operating-model' },
  { label: 'Roadmap', href: '#roadmap' },
  { label: 'Risks', href: '#risks' },
  { label: 'Impact', href: '#impact' },
] as const

export const pageLinks = [
  { label: 'Journey', href: '/journey' },
  { label: 'Built with AI', href: '/vibe' },
] as const


The file /Users/khalidbinkalban/Desktop/My Workstation/dewa-ai-adoption/src/lib/tokens.ts has been updated successfully.

export const navLinks = [
  { label: 'Overview', href: '#overview' },
  { label: 'Structure', href: '#structure' },
  { label: 'Responsibilities', href: '#responsibilities' },
  { label: 'KPIs', href: '#kpis' },
  { label: 'Governance', href: '#governance' },
  { label: 'Operating Model', href: '#operating-model' },
  { label: 'Roadmap', href: '#roadmap' },
  { label: 'Risks', href: '#risks' },
  { label: 'Impact', href: '#impact' },
] as const

export const pageLinks = [
  { label: 'Journey', href: '/journey' },
  { label: 'Built with AI', href: '/vibe' },
] as const

export const tokens = {
  colors: {
    bg: '#070D1A',
    surface: '#0D1627',
    surfaceRaised: '#132035',
    surfaceBorder: '#1E3A5F',
    primary: '#0066FF',
    primaryDim: '#0044BB',
    accent: '#00C2FF',
    gold: '#F0A500',
    goldDim: '#C98800',
    success: '#22C55E',
    warning: '#F59E0B',
    danger: '#EF4444',
    info: '#38BDF8',
    text: '#EEF2FF',
    textSecondary: '#8BAFD4',
    textDim: '#4A6B8A',
  },
  section: {
    'adoption-office': '#0066FF',
    'ai-acceleration': '#00C2FF',
    'command-center': '#F0A500',
  },
} as const

export const animation = {
  sectionReveal: {
    initial: { opacity: 0, y: 24 },
    animate: { opacity: 1, y: 0 },
    transition: { duration: 0.45, ease: [0.22, 1, 0.36, 1] as [number, number, number, number] },
  },
  cardHover: {
    whileHover: { y: -3, transition: { duration: 0.2 } },
  },
  staggerContainer: {
    animate: { transition: { staggerChildren: 0.07 } },
  },
} as const

export const navLinks = [
  { label: 'Overview', href: '#overview' },
  { label: 'Structure', href: '#structure' },
  { label: 'Responsibilities', href: '#responsibilities' },
  { label: 'KPIs', href: '#kpis' },
  { label: 'Governance', href: '#governance' },
  { label: 'Operating Model', href: '#operating-model' },
  { label: 'Roadmap', href: '#roadmap' },
  { label: 'Risks', href: '#risks' },
  { label: 'Impact', href: '#impact' },
] as const

+  { label: 'Journey', href: '/journey' },

+  { label: 'Built with AI', href: '/vibe' },


Now update `SiteNav.tsx` to add page navigation links using Next.js `Link`:


Write

'use client'

import { useState, useCallback } from 'react'
import Link from 'next/link'
import { usePathname } from 'next/navigation'
import { Menu, X } from 'lucide-react'
import { useActiveSection } from '@/hooks/useActiveSection'
import { navLinks, pageLinks } from '@/lib/tokens'

const sectionIds = navLinks.map((l) => l.href.replace('#', ''))

export default function SiteNav() {
  const [mobileOpen, setMobileOpen] = useState(false)
  const activeSection = useActiveSection(sectionIds)
  const pathname = usePathname()
  const isHome = pathname === '/'

  const handleNavClick = useCallback((href: string) => {
    setMobileOpen(false)
    if (!isHome) return
    const id = href.replace('#', '')
    const el = document.getElementById(id)
    if (el) {
      el.scrollIntoView({ behavior: 'smooth', block: 'start' })
    }
  }, [isHome])

  return (
    <>

          {/* Left: Logo + Name */}
          <Link href="/" className="flex items-center gap-3 no-underline hover:no-underline">

              AI

              DEWA
              AI Adoption Department

          </Link>

          {/* Desktop Nav */}

            {/* Section anchor links — home only */}
            {isHome && navLinks.map((link) => {
              const id = link.href.replace('#', '')
              const isActive = activeSection === id
              return (
                <button
                  key={link.href}
                  onClick={() => handleNavClick(link.href)}
                  className={`
                    px-3 py-1.5 text-xs font-medium tracking-wide transition-colors duration-150 rounded-md
                    ${isActive
                      ? 'text-primary border-b-2 border-primary rounded-none pb-1'
                      : 'text-text-secondary hover:text-text hover:bg-surface-raised'
                    }
                  `}
                >
                  {link.label}
                </button>
              )
            })}

            {/* Divider */}

            {/* Page links */}
            {pageLinks.map((link) => {
              const isActive = pathname === link.href
              return (
                <Link
                  key={link.href}
                  href={link.href}
                  className={`
                    px-3 py-1.5 text-xs font-medium tracking-wide transition-colors duration-150 rounded-md no-underline
                    ${isActive
                      ? 'text-accent bg-accent/10'
                      : 'text-text-secondary hover:text-text hover:bg-surface-raised'
                    }
                  `}
                >
                  {link.label}
                </Link>
              )
            })}

          {/* Mobile hamburger */}
          <button
            className="lg:hidden p-2 text-text-secondary hover:text-text transition-colors"
            onClick={() => setMobileOpen((v) => !v)}
            aria-label="Toggle menu"
            aria-expanded={mobileOpen}
          >
            {mobileOpen ? <X size={20} /> : <Menu size={20} />}
          </button>

      {/* Mobile Menu */}
      {mobileOpen && (

            {/* Section anchor links — home only */}
            {isHome && navLinks.map((link) => {
              const id = link.href.replace('#', '')
              const isActive = activeSection === id
              return (
                <button
                  key={link.href}
                  onClick={() => handleNavClick(link.href)}
                  className={`
                    text-left px-4 py-3 text-base font-medium rounded-lg transition-colors
                    ${isActive
                      ? 'text-primary bg-primary/10 border border-primary/20'
                      : 'text-text-secondary hover:text-text hover:bg-surface-raised'
                    }
                  `}
                >
                  {link.label}
                </button>
              )
            })}

            {/* Divider */}

            {/* Page links */}
            {pageLinks.map((link) => {
              const isActive = pathname === link.href
              return (
                <Link
                  key={link.href}
                  href={link.href}
                  onClick={() => setMobileOpen(false)}
                  className={`
                    px-4 py-3 text-base font-medium rounded-lg transition-colors no-underline
                    ${isActive
                      ? 'text-accent bg-accent/10 border border-accent/20'
                      : 'text-text-secondary hover:text-text hover:bg-surface-raised'
                    }
                  `}
                >
                  {link.label}
                </Link>
              )
            })}

      )}
    </>
  )
}


The file /Users/khalidbinkalban/Desktop/My Workstation/dewa-ai-adoption/src/components/layout/SiteNav.tsx has been updated successfully.

'use client'

import { useState, useCallback } from 'react'
import Link from 'next/link'
import { usePathname } from 'next/navigation'
import { Menu, X } from 'lucide-react'
import { useActiveSection } from '@/hooks/useActiveSection'
import { navLinks, pageLinks } from '@/lib/tokens'

const sectionIds = navLinks.map((l) => l.href.replace('#', ''))

export default function SiteNav() {
  const [mobileOpen, setMobileOpen] = useState(false)
  const activeSection = useActiveSection(sectionIds)
  const pathname = usePathname()
  const isHome = pathname === '/'

  const handleNavClick = useCallback((href: string) => {
    setMobileOpen(false)
    if (!isHome) return
    const id = href.replace('#', '')
    const el = document.getElementById(id)
    if (el) {
      el.scrollIntoView({ behavior: 'smooth', block: 'start' })
    }
  }, [isHome])

  return (
    <>

          {/* Left: Logo + Name */}
          <Link href="/" className="flex items-center gap-3 no-underline hover:no-underline">

              AI

              DEWA
              AI Adoption Department

          </Link>

          {/* Desktop Nav */}

            {/* Section anchor links — home only */}
            {isHome && navLinks.map((link) => {
              const id = link.href.replace('#', '')
              const isActive = activeSection === id
              return (
                <button
                  key={link.href}
                  onClick={() => handleNavClick(link.href)}
                  className={`
                    px-3 py-1.5 text-xs font-medium tracking-wide transition-colors duration-150 rounded-md
                    ${isActive
                      ? 'text-primary border-b-2 border-primary rounded-none pb-1'
                      : 'text-text-secondary hover:text-text hover:bg-surface-raised'
                    }
                  `}
                >
                  {link.label}
                </button>
              )
            })}

            {/* Divider */}

            {/* Page links */}
            {pageLinks.map((link) => {
              const isActive = pathname === link.href
              return (
                <Link
                  key={link.href}
                  href={link.href}
                  className={`
                    px-3 py-1.5 text-xs font-medium tracking-wide transition-colors duration-150 rounded-md no-underline
                    ${isActive
                      ? 'text-accent bg-accent/10'
                      : 'text-text-secondary hover:text-text hover:bg-surface-raised'
                    }
                  `}
                >
                  {link.label}
                </Link>
              )
            })}

          {/* Mobile hamburger */}
          <button
            className="lg:hidden p-2 text-text-secondary hover:text-text transition-colors"
            onClick={() => setMobileOpen((v) => !v)}
            aria-label="Toggle menu"
            aria-expanded={mobileOpen}
          >
            {mobileOpen ? <X size={20} /> : <Menu size={20} />}
          </button>

      {/* Mobile Menu */}
      {mobileOpen && (

            {/* Section anchor links — home only */}
            {isHome && navLinks.map((link) => {
              const id = link.href.replace('#', '')
              const isActive = activeSection === id
              return (
                <button
                  key={link.href}
                  onClick={() => handleNavClick(link.href)}
                  className={`
                    text-left px-4 py-3 text-base font-medium rounded-lg transition-colors
                    ${isActive
                      ? 'text-primary bg-primary/10 border border-primary/20'
                      : 'text-text-secondary hover:text-text hover:bg-surface-raised'
                    }
                  `}
                >
                  {link.label}
                </button>
              )
            })}

            {/* Divider */}

            {/* Page links */}
            {pageLinks.map((link) => {
              const isActive = pathname === link.href
              return (
                <Link
                  key={link.href}
                  href={link.href}
                  onClick={() => setMobileOpen(false)}
                  className={`
                    px-4 py-3 text-base font-medium rounded-lg transition-colors no-underline
                    ${isActive
                      ? 'text-accent bg-accent/10 border border-accent/20'
                      : 'text-text-secondary hover:text-text hover:bg-surface-raised'
                    }
                  `}
                >
                  {link.label}
                </Link>
              )
            })}

      )}
    </>
  )
}

+import { usePathname } from 'next/navigation'

-import { navLinks } from '@/lib/tokens'

+import { navLinks, pageLinks } from '@/lib/tokens'

<div className="mx-auto max-w-site px-6 h-full flex items-center justify-between">

-          <div className="flex items-center gap-3">

+          <Link href="/" className="flex items-center gap-3 no-underline hover:no-underline">

<div className="flex items-center justify-center w-8 h-8 rounded-md bg-primary/10 border border-primary/20">

<nav className="hidden lg:flex items-center gap-1">

+            {/* Section anchor links — home only */}

+            {isHome && navLinks.map((link) => {

+            <div className="w-px h-4 bg-surface-border mx-1" />

+              const isActive = pathname === link.href

+                    px-3 py-1.5 text-xs font-medium tracking-wide transition-colors duration-150 rounded-md no-underline

+                      ? 'text-accent bg-accent/10'

+                      : 'text-text-secondary hover:text-text hover:bg-surface-raised'

style={{ backgroundColor: 'rgba(7, 13, 26, 0.97)' }}

<div className="flex flex-col pt-20 px-6 gap-1">

+            <div className="h-px bg-surface-border my-2" />

+                  onClick={() => setMobileOpen(false)}

+                    px-4 py-3 text-base font-medium rounded-lg transition-colors no-underline

+                      ? 'text-accent bg-accent/10 border border-accent/20'

'use client'

import { useState, useCallback } from 'react'
import { Menu, X } from 'lucide-react'
import { useActiveSection } from '@/hooks/useActiveSection'
import { navLinks } from '@/lib/tokens'

const sectionIds = navLinks.map((l) => l.href.replace('#', ''))

export default function SiteNav() {
  const [mobileOpen, setMobileOpen] = useState(false)
  const activeSection = useActiveSection(sectionIds)

  const handleNavClick = useCallback((href: string) => {
    setMobileOpen(false)
    const id = href.replace('#', '')
    const el = document.getElementById(id)
    if (el) {
      el.scrollIntoView({ behavior: 'smooth', block: 'start' })
    }
  }, [])

  return (
    <>

          {/* Left: Logo + Name */}

              AI

              DEWA
              AI Adoption Department

          {/* Desktop Nav */}

            {navLinks.map((link) => {
              const id = link.href.replace('#', '')
              const isActive = activeSection === id
              return (
                <button
                  key={link.href}
                  onClick={() => handleNavClick(link.href)}
                  className={`
                    px-3 py-1.5 text-xs font-medium tracking-wide transition-colors duration-150 rounded-md
                    ${isActive
                      ? 'text-primary border-b-2 border-primary rounded-none pb-1'
                      : 'text-text-secondary hover:text-text hover:bg-surface-raised'
                    }
                  `}
                >
                  {link.label}
                </button>
              )
            })}

          {/* Mobile hamburger */}
          <button
            className="lg:hidden p-2 text-text-secondary hover:text-text transition-colors"
            onClick={() => setMobileOpen((v) => !v)}
            aria-label="Toggle menu"
          >
            {mobileOpen ? <X size={20} /> : <Menu size={20} />}
          </button>

      {/* Mobile Menu */}
      {mobileOpen && (

            {navLinks.map((link) => {
              const id = link.href.replace('#', '')
              const isActive = activeSection === id
              return (
                <button
                  key={link.href}
                  onClick={() => handleNavClick(link.href)}
                  className={`
                    text-left px-4 py-3 text-base font-medium rounded-lg transition-colors
                    ${isActive
                      ? 'text-primary bg-primary/10 border border-primary/20'
                      : 'text-text-secondary hover:text-text hover:bg-surface-raised'
                    }
                  `}
                >
                  {link.label}
                </button>
              )
            })}

      )}
    </>
  )
}


Now build the Journey page:


Bash

mkdir -p "/Users/khalidbinkalban/Desktop/My Workstation/dewa-ai-adoption/src/app/journey" "/Users/khalidbinkalban/Desktop/My Workstation/dewa-ai-adoption/src/app/vibe"

Create page route directories


[rerun: b22]


Write

'use client'

import Link from 'next/link'
import { motion } from 'framer-motion'
import { ArrowLeft, ChevronRight } from 'lucide-react'
import { journeyHero, challengeCards, solutionSteps, techStack } from '@/content/journey'

const reveal = {
  hidden: { opacity: 0, y: 24 },
  visible: { opacity: 1, y: 0, transition: { duration: 0.45, ease: [0.22, 1, 0.36, 1] as [number, number, number, number] } },
}

const stagger = (delay = 0.07) => ({
  hidden: {},
  visible: { transition: { staggerChildren: delay } },
})

const badgeClass: Record<string, string> = {
  Framework:  'bg-primary/10 text-primary border-primary/20',
  Language:   'bg-accent/10 text-accent border-accent/20',
  Styling:    'bg-gold/10 text-gold border-gold/20',
  Components: 'bg-success/10 text-success border-success/20',
  Animation:  'bg-primary/10 text-primary border-primary/20',
  Charts:     'bg-accent/10 text-accent border-accent/20',
  Icons:      'bg-gold/10 text-gold border-gold/20',
  Typography: 'bg-success/10 text-success border-success/20',
}

export default function JourneyPage() {
  return (

      {/* Back link */}

        <Link
          href="/"
          className="inline-flex items-center gap-1.5 text-xs text-text-dim hover:text-text transition-colors duration-150 no-underline"
        >
          <ArrowLeft className="w-3.5 h-3.5" />
          Back to Dashboard
        </Link>

      {/* ── Hero ──────────────────────────────────────────── */}

          <motion.div
            initial="hidden"
            animate="visible"
            variants={stagger(0.08)}
          >
            <motion.div variants={reveal}>

                {journeyHero.badge}

            </motion.div>

            <motion.h1
              variants={reveal}
              className="text-4xl font-bold text-text leading-tight max-w-3xl mb-5"
            >
              {journeyHero.title}
            </motion.h1>

            <motion.p
              variants={reveal}
              className="text-md text-text-secondary leading-relaxed max-w-2xl mb-12"
            >
              {journeyHero.description}
            </motion.p>

            {/* Stats row */}
            <motion.div
              variants={stagger(0.07)}
              initial="hidden"
              animate="visible"
              className="grid grid-cols-2 md:grid-cols-4 gap-4"
            >
              {journeyHero.stats.map((stat) => (
                <motion.div
                  key={stat.label}
                  variants={reveal}
                  className="bg-surface border border-surface-border rounded-xl p-5 shadow-card"
                >

                    {stat.label}

                    {stat.value}
                    {stat.unit && (
                      {stat.unit}
                    )}

                </motion.div>
              ))}
            </motion.div>
          </motion.div>

      {/* ── The Challenge ─────────────────────────────────── */}

          <motion.div
            initial="hidden"
            whileInView="visible"
            viewport={{ once: true, margin: '-10%' }}
            variants={stagger(0.09)}
          >
            <motion.div variants={reveal}>

                The Challenge

            </motion.div>

            <motion.h2
              variants={reveal}
              className="text-2xl font-bold text-text mb-3 max-w-xl"
            >
              Enterprise AI at Scale is Not a Technology Problem
            </motion.h2>

            <motion.p
              variants={reveal}
              className="text-base text-text-secondary leading-relaxed max-w-2xl mb-10"
            >
              It is an organisational problem. Without a dedicated adoption engine, AI tools proliferate
              unevenly, governance gaps emerge, and leadership loses visibility over what is actually
              delivering value.
            </motion.p>

            <motion.div
              variants={stagger(0.08)}
              className="grid grid-cols-1 md:grid-cols-3 gap-6"
            >
              {challengeCards.map((card) => (
                <motion.div
                  key={card.number}
                  variants={reveal}
                  whileHover={{ y: -3, transition: { duration: 0.2 } }}
                  className="bg-surface border border-surface-border rounded-xl p-6 shadow-card hover:shadow-raised hover:bg-surface-raised transition-all duration-200"
                >

                    {card.number}

{card.title}

{card.description}

                </motion.div>
              ))}
            </motion.div>
          </motion.div>

      {/* ── The Solution ──────────────────────────────────── */}

          <motion.div
            initial="hidden"
            whileInView="visible"
            viewport={{ once: true, margin: '-10%' }}
            variants={stagger(0.08)}
          >
            <motion.div variants={reveal}>

                The Solution

            </motion.div>

            <motion.h2
              variants={reveal}
              className="text-2xl font-bold text-text mb-3"
            >
              A Three-Section Operating Engine
            </motion.h2>

            <motion.p
              variants={reveal}
              className="text-base text-text-secondary leading-relaxed max-w-2xl mb-12"
            >
              The AI Adoption Department operates as a four-step pipeline that converts AI opportunity
              into measurable enterprise value — systematically, repeatably, at scale.
            </motion.p>

            {/* Vertical pipeline */}

              {solutionSteps.map((step, i) => (
                <motion.div
                  key={step.number}
                  initial="hidden"
                  whileInView="visible"
                  viewport={{ once: true, margin: '-10%' }}
                  variants={reveal}
                  className="flex gap-6 pb-8 last:pb-0"
                >
                  {/* Left: number + line */}

                      {step.number}

                    {i < solutionSteps.length - 1 && (

                    )}

                  {/* Right: content */}

{step.title}

                        {step.owner}

{step.description}

                    {i < solutionSteps.length - 1 && (
                      <ChevronRight className="w-4 h-4 text-text-dim mt-4 rotate-90" />
                    )}

                </motion.div>
              ))}

          </motion.div>

      {/* ── Tech Stack ────────────────────────────────────── */}

          <motion.div
            initial="hidden"
            whileInView="visible"
            viewport={{ once: true, margin: '-10%' }}
            variants={stagger(0.07)}
          >
            <motion.div variants={reveal}>

                Tech Stack

            </motion.div>

            <motion.h2 variants={reveal} className="text-2xl font-bold text-text mb-10">
              Built on a Production-Grade Foundation
            </motion.h2>

            <motion.div
              variants={stagger(0.05)}
              className="grid grid-cols-2 sm:grid-cols-4 gap-4"
            >
              {techStack.map((tech) => (
                <motion.div
                  key={tech.name}
                  variants={reveal}
                  whileHover={{ y: -3, transition: { duration: 0.2 } }}
                  className="bg-surface border border-surface-border rounded-xl p-5 shadow-card hover:shadow-raised hover:bg-surface-raised transition-all duration-200"
                >
                  <span className={`inline-flex text-xs font-semibold tracking-wide px-2 py-0.5 rounded-full border mb-3 ${badgeClass[tech.badge] ?? 'bg-primary/10 text-primary border-primary/20'}`}>
                    {tech.badge}

{tech.name}

{tech.description}

                </motion.div>
              ))}
            </motion.div>

            {/* CTA */}
            <motion.div variants={reveal} className="mt-12 pt-8 border-t border-surface-border flex flex-col sm:flex-row items-start sm:items-center justify-between gap-4">

Explore the full operating model

The executive dashboard has all 10 sections — strategy, structure, KPIs, governance, roadmap, and impact.

              <Link
                href="/"
                className="inline-flex items-center gap-2 px-5 py-2.5 bg-primary text-white rounded-lg text-sm font-semibold hover:bg-primary-dim transition-colors duration-150 no-underline flex-shrink-0"
              >
                Open Dashboard
                <ChevronRight className="w-4 h-4" />
              </Link>
            </motion.div>
          </motion.div>

  )
}