@djangocfg/layouts 1.0.6 → 1.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +5 -5
- package/src/layouts/AppLayout/AppLayout.tsx +132 -28
- package/src/layouts/AppLayout/components/ErrorBoundary.tsx +99 -0
- package/src/layouts/AppLayout/components/PageProgress.tsx +28 -11
- package/src/layouts/AppLayout/components/index.ts +1 -0
- package/src/layouts/AppLayout/layouts/AuthLayout/AuthContext.tsx +1 -1
- package/src/layouts/AppLayout/layouts/AuthLayout/AuthHelp.tsx +5 -5
- package/src/layouts/AppLayout/layouts/AuthLayout/AuthLayout.tsx +2 -2
- package/src/layouts/AppLayout/layouts/AuthLayout/IdentifierForm.tsx +2 -2
- package/src/layouts/AppLayout/layouts/PrivateLayout/components/DashboardHeader.tsx +1 -1
- package/src/layouts/AppLayout/layouts/PublicLayout/components/Footer.tsx +1 -1
- package/src/layouts/AppLayout/layouts/PublicLayout/components/MobileMenu.tsx +53 -36
- package/src/layouts/AppLayout/layouts/PublicLayout/components/Navigation.tsx +64 -52
- package/src/layouts/AppLayout/types/config.ts +22 -0
- package/src/layouts/ErrorLayout/ErrorLayout.tsx +169 -0
- package/src/layouts/ErrorLayout/errorConfig.tsx +152 -0
- package/src/layouts/ErrorLayout/index.ts +8 -0
- package/src/layouts/UILayout/README.md +267 -0
- package/src/layouts/UILayout/REFACTORING.md +331 -0
- package/src/layouts/UILayout/UIGuideApp.tsx +18 -0
- package/src/layouts/UILayout/UIGuideLanding.tsx +198 -0
- package/src/layouts/UILayout/UIGuideView.tsx +61 -0
- package/src/layouts/UILayout/UILayout.tsx +122 -0
- package/src/layouts/UILayout/components/AutoComponentDemo.tsx +77 -0
- package/src/layouts/UILayout/components/CategoryRenderer.tsx +45 -0
- package/src/layouts/UILayout/components/Header.tsx +114 -0
- package/src/layouts/UILayout/components/MobileOverlay.tsx +33 -0
- package/src/layouts/UILayout/components/Sidebar.tsx +195 -0
- package/src/layouts/UILayout/components/TailwindGuideRenderer.tsx +138 -0
- package/src/layouts/UILayout/config/ai-export.config.ts +80 -0
- package/src/layouts/UILayout/config/categories.config.tsx +114 -0
- package/src/layouts/UILayout/config/components/blocks.config.tsx +233 -0
- package/src/layouts/UILayout/config/components/data.config.tsx +308 -0
- package/src/layouts/UILayout/config/components/feedback.config.tsx +246 -0
- package/src/layouts/UILayout/config/components/forms.config.tsx +171 -0
- package/src/layouts/UILayout/config/components/hooks.config.tsx +131 -0
- package/src/layouts/UILayout/config/components/index.ts +69 -0
- package/src/layouts/UILayout/config/components/layout.config.tsx +133 -0
- package/src/layouts/UILayout/config/components/navigation.config.tsx +244 -0
- package/src/layouts/UILayout/config/components/overlay.config.tsx +561 -0
- package/src/layouts/UILayout/config/components/specialized.config.tsx +125 -0
- package/src/layouts/UILayout/config/components/types.ts +14 -0
- package/src/layouts/UILayout/config/index.ts +42 -0
- package/src/layouts/UILayout/config/tailwind.config.ts +77 -0
- package/src/layouts/UILayout/constants.ts +23 -0
- package/src/layouts/UILayout/context/ShowcaseContext.tsx +53 -0
- package/src/layouts/UILayout/context/index.ts +1 -0
- package/src/layouts/UILayout/index.ts +64 -0
- package/src/layouts/UILayout/types.ts +13 -0
- package/src/layouts/index.ts +5 -1
- package/src/snippets/Chat/types.ts +3 -4
|
@@ -0,0 +1,195 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Sidebar Component
|
|
3
|
+
* Navigation sidebar for component categories
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
'use client';
|
|
7
|
+
|
|
8
|
+
import React from 'react';
|
|
9
|
+
import { createPortal } from 'react-dom';
|
|
10
|
+
import { cn } from '@djangocfg/ui/lib';
|
|
11
|
+
import { useIsMobile } from '@djangocfg/ui';
|
|
12
|
+
import type { ComponentCategory } from '../types';
|
|
13
|
+
|
|
14
|
+
interface SidebarProps {
|
|
15
|
+
categories: ComponentCategory[];
|
|
16
|
+
currentCategory?: string;
|
|
17
|
+
onCategoryChange?: (categoryId: string) => void;
|
|
18
|
+
isOpen?: boolean;
|
|
19
|
+
projectName?: string;
|
|
20
|
+
logo?: React.ReactNode;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
interface SidebarContentProps {
|
|
24
|
+
categories: ComponentCategory[];
|
|
25
|
+
currentCategory?: string;
|
|
26
|
+
onCategoryChange?: (categoryId: string) => void;
|
|
27
|
+
projectName?: string;
|
|
28
|
+
logo?: React.ReactNode;
|
|
29
|
+
isMobile: boolean;
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
/**
|
|
33
|
+
* Sidebar Content Component
|
|
34
|
+
* Extracted content for reuse in desktop and mobile versions
|
|
35
|
+
*/
|
|
36
|
+
function SidebarContent({
|
|
37
|
+
categories,
|
|
38
|
+
currentCategory,
|
|
39
|
+
onCategoryChange,
|
|
40
|
+
projectName,
|
|
41
|
+
logo,
|
|
42
|
+
isMobile,
|
|
43
|
+
}: SidebarContentProps) {
|
|
44
|
+
return (
|
|
45
|
+
<div className={cn("flex flex-col overflow-hidden", isMobile ? "h-full" : "h-screen")}>
|
|
46
|
+
{/* Logo - Desktop only */}
|
|
47
|
+
{!isMobile && (
|
|
48
|
+
<div className="flex h-14 items-center border-b px-6 gap-2 flex-shrink-0">
|
|
49
|
+
{logo}
|
|
50
|
+
<span className="font-semibold text-sm">{projectName}</span>
|
|
51
|
+
</div>
|
|
52
|
+
)}
|
|
53
|
+
|
|
54
|
+
{/* Navigation */}
|
|
55
|
+
<div className="flex-1 overflow-y-auto scrollbar-thin">
|
|
56
|
+
<div className="p-4">
|
|
57
|
+
<nav>
|
|
58
|
+
<div className="mb-4">
|
|
59
|
+
<h3 className="mb-2 px-2 text-xs font-semibold text-muted-foreground uppercase tracking-wider">
|
|
60
|
+
Component Categories
|
|
61
|
+
</h3>
|
|
62
|
+
</div>
|
|
63
|
+
|
|
64
|
+
<div className="space-y-1">
|
|
65
|
+
{categories.map((category) => (
|
|
66
|
+
<button
|
|
67
|
+
key={category.id}
|
|
68
|
+
onClick={() => onCategoryChange?.(category.id)}
|
|
69
|
+
className={cn(
|
|
70
|
+
"w-full flex items-center gap-3 px-3 py-2 rounded-md text-sm font-medium transition-colors",
|
|
71
|
+
currentCategory === category.id
|
|
72
|
+
? "bg-primary text-primary-foreground"
|
|
73
|
+
: "text-muted-foreground hover:bg-muted hover:text-foreground"
|
|
74
|
+
)}
|
|
75
|
+
title={category.description}
|
|
76
|
+
>
|
|
77
|
+
<span className="flex-shrink-0">{category.icon}</span>
|
|
78
|
+
<span className="flex-1 text-left break-words">{category.label}</span>
|
|
79
|
+
{category.count && (
|
|
80
|
+
<span className={cn(
|
|
81
|
+
"text-xs px-2 py-0.5 rounded-full flex-shrink-0",
|
|
82
|
+
currentCategory === category.id
|
|
83
|
+
? "bg-primary-foreground/20 text-primary-foreground"
|
|
84
|
+
: "bg-muted text-muted-foreground"
|
|
85
|
+
)}>
|
|
86
|
+
{category.count}
|
|
87
|
+
</span>
|
|
88
|
+
)}
|
|
89
|
+
</button>
|
|
90
|
+
))}
|
|
91
|
+
</div>
|
|
92
|
+
</nav>
|
|
93
|
+
</div>
|
|
94
|
+
</div>
|
|
95
|
+
|
|
96
|
+
{/* Tailwind 4 Info Section */}
|
|
97
|
+
<div className="border-t p-4 bg-muted/30">
|
|
98
|
+
<div className="mb-3">
|
|
99
|
+
<h4 className="text-xs font-semibold text-foreground uppercase tracking-wider mb-2">
|
|
100
|
+
Tailwind CSS v4
|
|
101
|
+
</h4>
|
|
102
|
+
<p className="text-xs text-muted-foreground leading-relaxed mb-3">
|
|
103
|
+
This UI library uses Tailwind CSS v4 with CSS-first configuration
|
|
104
|
+
</p>
|
|
105
|
+
</div>
|
|
106
|
+
|
|
107
|
+
<div className="space-y-2 text-xs">
|
|
108
|
+
<div className="flex items-start gap-2">
|
|
109
|
+
<span className="text-primary mt-0.5">✓</span>
|
|
110
|
+
<span className="text-muted-foreground">CSS-first @theme configuration</span>
|
|
111
|
+
</div>
|
|
112
|
+
<div className="flex items-start gap-2">
|
|
113
|
+
<span className="text-primary mt-0.5">✓</span>
|
|
114
|
+
<span className="text-muted-foreground">10x faster build times</span>
|
|
115
|
+
</div>
|
|
116
|
+
<div className="flex items-start gap-2">
|
|
117
|
+
<span className="text-primary mt-0.5">✓</span>
|
|
118
|
+
<span className="text-muted-foreground">Modern CSS features (color-mix, @property)</span>
|
|
119
|
+
</div>
|
|
120
|
+
<div className="flex items-start gap-2">
|
|
121
|
+
<span className="text-primary mt-0.5">✓</span>
|
|
122
|
+
<span className="text-muted-foreground">Responsive: px-4 sm:px-6 lg:px-8</span>
|
|
123
|
+
</div>
|
|
124
|
+
</div>
|
|
125
|
+
</div>
|
|
126
|
+
|
|
127
|
+
{/* Footer */}
|
|
128
|
+
<div className="border-t p-4">
|
|
129
|
+
<p className="text-xs text-muted-foreground">
|
|
130
|
+
Built with Radix UI + Tailwind CSS v4
|
|
131
|
+
</p>
|
|
132
|
+
</div>
|
|
133
|
+
</div>
|
|
134
|
+
);
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
export function Sidebar({
|
|
138
|
+
categories,
|
|
139
|
+
currentCategory,
|
|
140
|
+
onCategoryChange,
|
|
141
|
+
isOpen = false,
|
|
142
|
+
projectName = 'Django CFG',
|
|
143
|
+
logo,
|
|
144
|
+
}: SidebarProps) {
|
|
145
|
+
const isMobile = useIsMobile();
|
|
146
|
+
const [mounted, setMounted] = React.useState(false);
|
|
147
|
+
|
|
148
|
+
React.useEffect(() => {
|
|
149
|
+
setMounted(true);
|
|
150
|
+
}, []);
|
|
151
|
+
|
|
152
|
+
// Desktop sidebar - always visible, no portal
|
|
153
|
+
if (!isMobile) {
|
|
154
|
+
return (
|
|
155
|
+
<aside className="w-64 border-r bg-background flex-shrink-0">
|
|
156
|
+
<SidebarContent
|
|
157
|
+
categories={categories}
|
|
158
|
+
currentCategory={currentCategory}
|
|
159
|
+
onCategoryChange={onCategoryChange}
|
|
160
|
+
projectName={projectName}
|
|
161
|
+
logo={logo}
|
|
162
|
+
isMobile={false}
|
|
163
|
+
/>
|
|
164
|
+
</aside>
|
|
165
|
+
);
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
// Mobile sidebar - use portal when open
|
|
169
|
+
if (!isOpen || !mounted) {
|
|
170
|
+
return null;
|
|
171
|
+
}
|
|
172
|
+
|
|
173
|
+
if (typeof window === 'undefined') {
|
|
174
|
+
return null;
|
|
175
|
+
}
|
|
176
|
+
|
|
177
|
+
return createPortal(
|
|
178
|
+
<aside
|
|
179
|
+
className={cn(
|
|
180
|
+
"fixed inset-y-0 left-0 w-64 z-[200] bg-background border-r shadow-lg transition-transform duration-300",
|
|
181
|
+
isOpen ? "translate-x-0" : "-translate-x-full"
|
|
182
|
+
)}
|
|
183
|
+
>
|
|
184
|
+
<SidebarContent
|
|
185
|
+
categories={categories}
|
|
186
|
+
currentCategory={currentCategory}
|
|
187
|
+
onCategoryChange={onCategoryChange}
|
|
188
|
+
projectName={projectName}
|
|
189
|
+
logo={logo}
|
|
190
|
+
isMobile={true}
|
|
191
|
+
/>
|
|
192
|
+
</aside>,
|
|
193
|
+
document.body
|
|
194
|
+
);
|
|
195
|
+
}
|
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* TailwindGuideRenderer
|
|
3
|
+
* Renders Tailwind CSS v4 guide from config
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
'use client';
|
|
7
|
+
|
|
8
|
+
import React from 'react';
|
|
9
|
+
import { Card, CardContent, CardDescription, CardHeader, CardTitle } from '@djangocfg/ui';
|
|
10
|
+
import { PrettyCode } from '@djangocfg/ui/tools';
|
|
11
|
+
import { TAILWIND_GUIDE } from '../config';
|
|
12
|
+
import { CategorySection } from './AutoComponentDemo';
|
|
13
|
+
|
|
14
|
+
/**
|
|
15
|
+
* TailwindGuideRenderer - Dynamically renders Tailwind guide from config
|
|
16
|
+
*/
|
|
17
|
+
export function TailwindGuideRenderer() {
|
|
18
|
+
return (
|
|
19
|
+
<CategorySection
|
|
20
|
+
title="Tailwind CSS v4 Guide"
|
|
21
|
+
description="Everything you need to know about migrating to and using Tailwind CSS v4"
|
|
22
|
+
>
|
|
23
|
+
{/* Key Changes */}
|
|
24
|
+
<Card>
|
|
25
|
+
<CardHeader>
|
|
26
|
+
<CardTitle>Key Changes in Tailwind CSS v{TAILWIND_GUIDE.version}</CardTitle>
|
|
27
|
+
<CardDescription>
|
|
28
|
+
Major improvements and breaking changes you should know about
|
|
29
|
+
</CardDescription>
|
|
30
|
+
</CardHeader>
|
|
31
|
+
<CardContent>
|
|
32
|
+
<ul className="list-disc list-inside space-y-2 text-muted-foreground">
|
|
33
|
+
{TAILWIND_GUIDE.keyChanges.map((change, index) => (
|
|
34
|
+
<li key={index}>{change}</li>
|
|
35
|
+
))}
|
|
36
|
+
</ul>
|
|
37
|
+
</CardContent>
|
|
38
|
+
</Card>
|
|
39
|
+
|
|
40
|
+
{/* Best Practices */}
|
|
41
|
+
<Card>
|
|
42
|
+
<CardHeader>
|
|
43
|
+
<CardTitle>Best Practices</CardTitle>
|
|
44
|
+
<CardDescription>
|
|
45
|
+
Follow these patterns for clean, maintainable code
|
|
46
|
+
</CardDescription>
|
|
47
|
+
</CardHeader>
|
|
48
|
+
<CardContent>
|
|
49
|
+
<div className="space-y-4">
|
|
50
|
+
<div>
|
|
51
|
+
<h3 className="font-semibold mb-2">✅ Recommended Patterns</h3>
|
|
52
|
+
<ul className="list-disc list-inside space-y-1 text-muted-foreground ml-4">
|
|
53
|
+
{TAILWIND_GUIDE.bestPractices.map((practice, index) => (
|
|
54
|
+
<li key={index}>{practice}</li>
|
|
55
|
+
))}
|
|
56
|
+
</ul>
|
|
57
|
+
</div>
|
|
58
|
+
</div>
|
|
59
|
+
</CardContent>
|
|
60
|
+
</Card>
|
|
61
|
+
|
|
62
|
+
{/* Migration Steps */}
|
|
63
|
+
<Card>
|
|
64
|
+
<CardHeader>
|
|
65
|
+
<CardTitle>Migration Steps (v3 → v4)</CardTitle>
|
|
66
|
+
<CardDescription>
|
|
67
|
+
Step-by-step guide to upgrade your project
|
|
68
|
+
</CardDescription>
|
|
69
|
+
</CardHeader>
|
|
70
|
+
<CardContent>
|
|
71
|
+
<ol className="list-decimal list-inside space-y-2 text-muted-foreground">
|
|
72
|
+
{TAILWIND_GUIDE.migrationSteps.map((step, index) => (
|
|
73
|
+
<li key={index}>{step}</li>
|
|
74
|
+
))}
|
|
75
|
+
</ol>
|
|
76
|
+
</CardContent>
|
|
77
|
+
</Card>
|
|
78
|
+
|
|
79
|
+
{/* Examples */}
|
|
80
|
+
{TAILWIND_GUIDE.examples.map((example, index) => (
|
|
81
|
+
<Card key={index}>
|
|
82
|
+
<CardHeader>
|
|
83
|
+
<CardTitle>{example.title}</CardTitle>
|
|
84
|
+
<CardDescription>{example.description}</CardDescription>
|
|
85
|
+
</CardHeader>
|
|
86
|
+
<CardContent>
|
|
87
|
+
<PrettyCode
|
|
88
|
+
data={example.code}
|
|
89
|
+
language="css"
|
|
90
|
+
className="text-sm"
|
|
91
|
+
/>
|
|
92
|
+
</CardContent>
|
|
93
|
+
</Card>
|
|
94
|
+
))}
|
|
95
|
+
|
|
96
|
+
{/* Resources */}
|
|
97
|
+
<Card>
|
|
98
|
+
<CardHeader>
|
|
99
|
+
<CardTitle>Official Resources</CardTitle>
|
|
100
|
+
</CardHeader>
|
|
101
|
+
<CardContent>
|
|
102
|
+
<ul className="space-y-2">
|
|
103
|
+
<li>
|
|
104
|
+
<a
|
|
105
|
+
href="https://tailwindcss.com/docs/upgrade-guide"
|
|
106
|
+
target="_blank"
|
|
107
|
+
rel="noopener noreferrer"
|
|
108
|
+
className="text-primary hover:underline"
|
|
109
|
+
>
|
|
110
|
+
Official Upgrade Guide
|
|
111
|
+
</a>
|
|
112
|
+
</li>
|
|
113
|
+
<li>
|
|
114
|
+
<a
|
|
115
|
+
href="https://tailwindcss.com/docs/guides/nextjs"
|
|
116
|
+
target="_blank"
|
|
117
|
+
rel="noopener noreferrer"
|
|
118
|
+
className="text-primary hover:underline"
|
|
119
|
+
>
|
|
120
|
+
Next.js Integration Guide
|
|
121
|
+
</a>
|
|
122
|
+
</li>
|
|
123
|
+
<li>
|
|
124
|
+
<a
|
|
125
|
+
href="https://tailwindcss.com/blog/tailwindcss-v4"
|
|
126
|
+
target="_blank"
|
|
127
|
+
rel="noopener noreferrer"
|
|
128
|
+
className="text-primary hover:underline"
|
|
129
|
+
>
|
|
130
|
+
Tailwind CSS v4.0 Release Notes
|
|
131
|
+
</a>
|
|
132
|
+
</li>
|
|
133
|
+
</ul>
|
|
134
|
+
</CardContent>
|
|
135
|
+
</Card>
|
|
136
|
+
</CategorySection>
|
|
137
|
+
);
|
|
138
|
+
}
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* AI Export Configuration
|
|
3
|
+
* Generates formatted documentation for AI consumption
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
import { COMPONENTS_CONFIG, getAllCategories } from './components';
|
|
7
|
+
import { TAILWIND_GUIDE } from './tailwind.config';
|
|
8
|
+
|
|
9
|
+
export interface UILibraryConfig {
|
|
10
|
+
projectName: string;
|
|
11
|
+
version: string;
|
|
12
|
+
description: string;
|
|
13
|
+
totalComponents: number;
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
export const UI_LIBRARY_CONFIG: UILibraryConfig = {
|
|
17
|
+
projectName: "Django CFG UI",
|
|
18
|
+
version: "1.0.0",
|
|
19
|
+
description: "Comprehensive React UI library with 56+ components, 7 blocks, and 11 hooks built with Radix UI, Tailwind CSS v4, and TypeScript",
|
|
20
|
+
totalComponents: COMPONENTS_CONFIG.length,
|
|
21
|
+
};
|
|
22
|
+
|
|
23
|
+
/**
|
|
24
|
+
* Generate formatted text for AI consumption
|
|
25
|
+
* This is the single source of truth that gets copied to clipboard
|
|
26
|
+
*/
|
|
27
|
+
export function generateAIContext(): string {
|
|
28
|
+
const { projectName, version, description } = UI_LIBRARY_CONFIG;
|
|
29
|
+
|
|
30
|
+
let output = `# ${projectName} v${version}\n\n`;
|
|
31
|
+
output += `${description}\n\n`;
|
|
32
|
+
|
|
33
|
+
// Tailwind 4 Guide
|
|
34
|
+
output += `## Tailwind CSS v${TAILWIND_GUIDE.version} Guidelines\n\n`;
|
|
35
|
+
|
|
36
|
+
output += `### Key Changes\n`;
|
|
37
|
+
TAILWIND_GUIDE.keyChanges.forEach(change => {
|
|
38
|
+
output += `- ${change}\n`;
|
|
39
|
+
});
|
|
40
|
+
output += `\n`;
|
|
41
|
+
|
|
42
|
+
output += `### Best Practices\n`;
|
|
43
|
+
TAILWIND_GUIDE.bestPractices.forEach(practice => {
|
|
44
|
+
output += `- ${practice}\n`;
|
|
45
|
+
});
|
|
46
|
+
output += `\n`;
|
|
47
|
+
|
|
48
|
+
output += `### Migration Steps\n`;
|
|
49
|
+
TAILWIND_GUIDE.migrationSteps.forEach((step, index) => {
|
|
50
|
+
output += `${index + 1}. ${step}\n`;
|
|
51
|
+
});
|
|
52
|
+
output += `\n`;
|
|
53
|
+
|
|
54
|
+
output += `### Examples\n\n`;
|
|
55
|
+
TAILWIND_GUIDE.examples.forEach(example => {
|
|
56
|
+
output += `#### ${example.title}\n`;
|
|
57
|
+
output += `${example.description}\n\n`;
|
|
58
|
+
output += `\`\`\`css\n${example.code}\n\`\`\`\n\n`;
|
|
59
|
+
});
|
|
60
|
+
|
|
61
|
+
// Components by Category
|
|
62
|
+
const categories = getAllCategories();
|
|
63
|
+
|
|
64
|
+
categories.forEach(category => {
|
|
65
|
+
const comps = COMPONENTS_CONFIG.filter(comp => comp.category === category);
|
|
66
|
+
|
|
67
|
+
output += `## ${category.charAt(0).toUpperCase() + category.slice(1)} (${comps.length})\n\n`;
|
|
68
|
+
|
|
69
|
+
comps.forEach(comp => {
|
|
70
|
+
output += `### ${comp.name}\n`;
|
|
71
|
+
output += `${comp.description}\n\n`;
|
|
72
|
+
output += `\`\`\`tsx\n`;
|
|
73
|
+
output += `${comp.importPath}\n\n`;
|
|
74
|
+
output += `${comp.example}\n`;
|
|
75
|
+
output += `\`\`\`\n\n`;
|
|
76
|
+
});
|
|
77
|
+
});
|
|
78
|
+
|
|
79
|
+
return output;
|
|
80
|
+
}
|
|
@@ -0,0 +1,114 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Categories Configuration
|
|
3
|
+
* Defines all component categories with metadata
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
import React from 'react';
|
|
7
|
+
import {
|
|
8
|
+
Home,
|
|
9
|
+
FormInput,
|
|
10
|
+
LayoutGrid,
|
|
11
|
+
Navigation as NavigationIcon,
|
|
12
|
+
Square,
|
|
13
|
+
MessageSquare,
|
|
14
|
+
Table2,
|
|
15
|
+
Puzzle,
|
|
16
|
+
Boxes,
|
|
17
|
+
Code2,
|
|
18
|
+
Palette,
|
|
19
|
+
} from 'lucide-react';
|
|
20
|
+
import { getComponentCount } from './components';
|
|
21
|
+
|
|
22
|
+
export interface ComponentCategory {
|
|
23
|
+
id: string;
|
|
24
|
+
label: string;
|
|
25
|
+
icon: React.ReactNode;
|
|
26
|
+
count?: number;
|
|
27
|
+
description?: string;
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
export const CATEGORIES: ComponentCategory[] = [
|
|
31
|
+
{
|
|
32
|
+
id: 'overview',
|
|
33
|
+
label: 'Overview',
|
|
34
|
+
icon: <Home className="h-4 w-4" />,
|
|
35
|
+
description: 'Welcome to Django CFG UI Library - explore 56+ components, 7 blocks, and 11 hooks',
|
|
36
|
+
},
|
|
37
|
+
{
|
|
38
|
+
id: 'forms',
|
|
39
|
+
label: 'Form Components',
|
|
40
|
+
icon: <FormInput className="h-4 w-4" />,
|
|
41
|
+
count: getComponentCount('forms'),
|
|
42
|
+
description: 'Input fields, buttons, checkboxes, selects, and form validation components',
|
|
43
|
+
},
|
|
44
|
+
{
|
|
45
|
+
id: 'layout',
|
|
46
|
+
label: 'Layout Components',
|
|
47
|
+
icon: <LayoutGrid className="h-4 w-4" />,
|
|
48
|
+
count: getComponentCount('layout'),
|
|
49
|
+
description: 'Cards, separators, skeletons, and structural layout components',
|
|
50
|
+
},
|
|
51
|
+
{
|
|
52
|
+
id: 'navigation',
|
|
53
|
+
label: 'Navigation',
|
|
54
|
+
icon: <NavigationIcon className="h-4 w-4" />,
|
|
55
|
+
count: getComponentCount('navigation'),
|
|
56
|
+
description: 'Menus, breadcrumbs, tabs, and pagination components',
|
|
57
|
+
},
|
|
58
|
+
{
|
|
59
|
+
id: 'overlay',
|
|
60
|
+
label: 'Overlay Components',
|
|
61
|
+
icon: <Square className="h-4 w-4" />,
|
|
62
|
+
count: getComponentCount('overlay'),
|
|
63
|
+
description: 'Dialogs, sheets, popovers, tooltips, and dropdown menus',
|
|
64
|
+
},
|
|
65
|
+
{
|
|
66
|
+
id: 'feedback',
|
|
67
|
+
label: 'Feedback',
|
|
68
|
+
icon: <MessageSquare className="h-4 w-4" />,
|
|
69
|
+
count: getComponentCount('feedback'),
|
|
70
|
+
description: 'Toasts, alerts, progress bars, badges, and status indicators',
|
|
71
|
+
},
|
|
72
|
+
{
|
|
73
|
+
id: 'data',
|
|
74
|
+
label: 'Data Display',
|
|
75
|
+
icon: <Table2 className="h-4 w-4" />,
|
|
76
|
+
count: getComponentCount('data'),
|
|
77
|
+
description: 'Tables, accordions, collapsibles, and data visualization',
|
|
78
|
+
},
|
|
79
|
+
{
|
|
80
|
+
id: 'specialized',
|
|
81
|
+
label: 'Specialized',
|
|
82
|
+
icon: <Puzzle className="h-4 w-4" />,
|
|
83
|
+
count: getComponentCount('specialized'),
|
|
84
|
+
description: 'Advanced components like sidebar navigation and image handling',
|
|
85
|
+
},
|
|
86
|
+
{
|
|
87
|
+
id: 'blocks',
|
|
88
|
+
label: 'Blocks',
|
|
89
|
+
icon: <Boxes className="h-4 w-4" />,
|
|
90
|
+
count: getComponentCount('blocks'),
|
|
91
|
+
description: 'Pre-built landing page sections: Hero, SuperHero, Features, CTA, Newsletter, Stats, Testimonials',
|
|
92
|
+
},
|
|
93
|
+
{
|
|
94
|
+
id: 'hooks',
|
|
95
|
+
label: 'Hooks',
|
|
96
|
+
icon: <Code2 className="h-4 w-4" />,
|
|
97
|
+
count: getComponentCount('hooks'),
|
|
98
|
+
description: 'Custom React hooks for common functionality and state management',
|
|
99
|
+
},
|
|
100
|
+
{
|
|
101
|
+
id: 'tailwind4',
|
|
102
|
+
label: 'Tailwind CSS v4',
|
|
103
|
+
icon: <Palette className="h-4 w-4" />,
|
|
104
|
+
description: 'Migration guide and best practices for Tailwind CSS v4',
|
|
105
|
+
},
|
|
106
|
+
];
|
|
107
|
+
|
|
108
|
+
export function getCategoryById(id: string): ComponentCategory | undefined {
|
|
109
|
+
return CATEGORIES.find(cat => cat.id === id);
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
export function getTotalComponentCount(): number {
|
|
113
|
+
return CATEGORIES.reduce((sum, cat) => sum + (cat.count || 0), 0);
|
|
114
|
+
}
|