scaff-ui 0.1.3 → 0.1.4
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/README.md +31 -2
- package/package.json +1 -1
- package/src/commands/add.js +26 -5
- package/src/commands/list.js +7 -0
- package/src/generators/component.js +4 -0
- package/src/templates/html/newsletter/basic-newsletter.html +30 -0
- package/src/templates/html/text-area/actions-inside.html +29 -0
- package/src/templates/html/text-area/actions-outside.html +29 -0
- package/src/templates/react/newsletter/basic-newsletter.jsx +39 -0
- package/src/templates/react/text-area/actions-outside.jsx +3 -3
package/README.md
CHANGED
|
@@ -2,9 +2,11 @@
|
|
|
2
2
|
|
|
3
3
|
Scaffold the UI. Make it your design.
|
|
4
4
|
|
|
5
|
-
|
|
5
|
+
Scaff UI is a CLI for generating minimalistic, customizable Tailwind CSS components for frontend projects.
|
|
6
6
|
|
|
7
|
-
|
|
7
|
+
Generate ready-made UI components directly into your project, then modify the source code and make each component fit your own design.
|
|
8
|
+
|
|
9
|
+
<!-- [Website](https://scaff-ui-site.jimroep.workers.dev) · [GitHub](https://github.com/carleoj/scaff-ui) -->
|
|
8
10
|
|
|
9
11
|
## Features
|
|
10
12
|
|
|
@@ -25,12 +27,22 @@ A minimalistic CLI for generating customizable Tailwind CSS components directly
|
|
|
25
27
|
|
|
26
28
|
## Installation
|
|
27
29
|
|
|
30
|
+
### Local installation
|
|
31
|
+
|
|
28
32
|
Install `scaff-ui` in your existing project:
|
|
29
33
|
|
|
30
34
|
```bash
|
|
31
35
|
npm install scaff-ui
|
|
32
36
|
```
|
|
33
37
|
|
|
38
|
+
### Global installation
|
|
39
|
+
|
|
40
|
+
Install scaff-ui globally to use the scf command directly:
|
|
41
|
+
|
|
42
|
+
```bash
|
|
43
|
+
npm install -g scaff-ui
|
|
44
|
+
```
|
|
45
|
+
|
|
34
46
|
## Usage
|
|
35
47
|
|
|
36
48
|
Run the interactive generator:
|
|
@@ -50,6 +62,8 @@ Select a framework, component, and variant:
|
|
|
50
62
|
❯ Header
|
|
51
63
|
Hero
|
|
52
64
|
Footer
|
|
65
|
+
Text Area
|
|
66
|
+
Newsletter
|
|
53
67
|
|
|
54
68
|
? Select Variant
|
|
55
69
|
❯ Logo + Navigation Links
|
|
@@ -63,6 +77,8 @@ You can also generate a specific component directly:
|
|
|
63
77
|
npx scf add header
|
|
64
78
|
npx scf add hero
|
|
65
79
|
npx scf add footer
|
|
80
|
+
npx scf add text-area
|
|
81
|
+
npx scf add newsletter
|
|
66
82
|
```
|
|
67
83
|
|
|
68
84
|
View available components:
|
|
@@ -121,6 +137,19 @@ Available variants:
|
|
|
121
137
|
- Copyright + Navigation Links
|
|
122
138
|
- Copyright + Social Links
|
|
123
139
|
|
|
140
|
+
### Text Area
|
|
141
|
+
|
|
142
|
+
Available variants:
|
|
143
|
+
|
|
144
|
+
- Actions Inside
|
|
145
|
+
- Actions Outside
|
|
146
|
+
|
|
147
|
+
### Newsletter
|
|
148
|
+
|
|
149
|
+
Available variants:
|
|
150
|
+
|
|
151
|
+
- Basic Newsletter
|
|
152
|
+
|
|
124
153
|
## Tailwind CSS
|
|
125
154
|
|
|
126
155
|
Generated components use Tailwind CSS utility classes.
|
package/package.json
CHANGED
package/src/commands/add.js
CHANGED
|
@@ -9,9 +9,11 @@ const FRAMEWORKS = [
|
|
|
9
9
|
];
|
|
10
10
|
|
|
11
11
|
const COMPONENTS = [
|
|
12
|
-
{ name: "Header", value: "header" },
|
|
13
|
-
{ name: "Hero", value: "hero" },
|
|
14
|
-
{ name: "Footer", value: "footer" },
|
|
12
|
+
{ name: "Header", value: "header", frameworks: ["html", "react"] },
|
|
13
|
+
{ name: "Hero", value: "hero", frameworks: ["html", "react"] },
|
|
14
|
+
{ name: "Footer", value: "footer", frameworks: ["html", "react"] },
|
|
15
|
+
{ name: "Text Area", value: "text-area", frameworks: ["html", "react"] },
|
|
16
|
+
{ name: "Newsletter", value: "newsletter", frameworks: ["html", "react"] },
|
|
15
17
|
];
|
|
16
18
|
|
|
17
19
|
const VARIANTS = {
|
|
@@ -44,6 +46,15 @@ const VARIANTS = {
|
|
|
44
46
|
},
|
|
45
47
|
{ name: "Copyright + Social Links", value: "copyright-social" },
|
|
46
48
|
],
|
|
49
|
+
|
|
50
|
+
"text-area": [
|
|
51
|
+
{ name: "Actions Inside", value: "actions-inside" },
|
|
52
|
+
{ name: "Actions Outside", value: "actions-outside" },
|
|
53
|
+
],
|
|
54
|
+
|
|
55
|
+
newsletter: [
|
|
56
|
+
{ name: "Basic Newsletter", value: "basic-newsletter" },
|
|
57
|
+
],
|
|
47
58
|
};
|
|
48
59
|
|
|
49
60
|
const requestedComponent = process.argv[3];
|
|
@@ -67,16 +78,26 @@ async function addComponent() {
|
|
|
67
78
|
process.exit(1);
|
|
68
79
|
}
|
|
69
80
|
|
|
81
|
+
const requestedDefinition = COMPONENTS.find(
|
|
82
|
+
(component) => component.value === requestedComponent,
|
|
83
|
+
);
|
|
84
|
+
|
|
70
85
|
const framework = await select({
|
|
71
86
|
message: "Select Framework",
|
|
72
|
-
choices:
|
|
87
|
+
choices: requestedDefinition
|
|
88
|
+
? FRAMEWORKS.filter((frameworkOption) =>
|
|
89
|
+
requestedDefinition.frameworks.includes(frameworkOption.value),
|
|
90
|
+
)
|
|
91
|
+
: FRAMEWORKS,
|
|
73
92
|
});
|
|
74
93
|
|
|
75
94
|
const type =
|
|
76
95
|
requestedComponent ??
|
|
77
96
|
(await select({
|
|
78
97
|
message: "Select Component",
|
|
79
|
-
choices: COMPONENTS
|
|
98
|
+
choices: COMPONENTS.filter((component) =>
|
|
99
|
+
component.frameworks.includes(framework),
|
|
100
|
+
),
|
|
80
101
|
}));
|
|
81
102
|
|
|
82
103
|
if (!VARIANTS[type]) {
|
package/src/commands/list.js
CHANGED
|
@@ -14,6 +14,13 @@ const components = {
|
|
|
14
14
|
"Copyright + Navigation Links",
|
|
15
15
|
"Copyright + Social Links",
|
|
16
16
|
],
|
|
17
|
+
"Text Area": [
|
|
18
|
+
"Actions Inside",
|
|
19
|
+
"Actions Outside",
|
|
20
|
+
],
|
|
21
|
+
Newsletter: [
|
|
22
|
+
"Basic Newsletter",
|
|
23
|
+
],
|
|
17
24
|
};
|
|
18
25
|
|
|
19
26
|
console.log("Available components:");
|
|
@@ -10,11 +10,15 @@ const FILE_NAMES = {
|
|
|
10
10
|
header: "header.html",
|
|
11
11
|
hero: "hero.html",
|
|
12
12
|
footer: "footer.html",
|
|
13
|
+
"text-area": "text-area.html",
|
|
14
|
+
newsletter: "newsletter.html",
|
|
13
15
|
},
|
|
14
16
|
react: {
|
|
15
17
|
header: "Header.jsx",
|
|
16
18
|
hero: "Hero.jsx",
|
|
17
19
|
footer: "Footer.jsx",
|
|
20
|
+
"text-area": "TextArea.jsx",
|
|
21
|
+
newsletter: "Newsletter.jsx",
|
|
18
22
|
},
|
|
19
23
|
};
|
|
20
24
|
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
<section class="mx-auto w-full max-w-xl rounded-2xl border border-gray-200 bg-zinc-50 p-8 text-center sm:p-10">
|
|
2
|
+
<h2 class="text-3xl font-bold tracking-tight text-gray-950">
|
|
3
|
+
Stay in the loop
|
|
4
|
+
</h2>
|
|
5
|
+
|
|
6
|
+
<p class="mx-auto mt-4 max-w-lg text-lg leading-7 text-gray-700">
|
|
7
|
+
Subscribe to our newsletter for updates, new releases, and useful resources.
|
|
8
|
+
</p>
|
|
9
|
+
|
|
10
|
+
<form class="mt-8">
|
|
11
|
+
<label for="email" class="sr-only">Email address</label>
|
|
12
|
+
|
|
13
|
+
<input
|
|
14
|
+
id="email"
|
|
15
|
+
type="email"
|
|
16
|
+
placeholder="Enter your email"
|
|
17
|
+
class="w-full rounded-lg border border-gray-300 bg-white px-5 py-4 text-base text-gray-950 outline-none transition focus:border-gray-950 focus:ring-1 focus:ring-gray-950"
|
|
18
|
+
required
|
|
19
|
+
/>
|
|
20
|
+
|
|
21
|
+
<button
|
|
22
|
+
type="submit"
|
|
23
|
+
class="mt-3 w-full rounded-lg bg-zinc-600 px-5 py-4 text-base font-semibold text-white transition hover:bg-zinc-700"
|
|
24
|
+
>
|
|
25
|
+
Subscribe
|
|
26
|
+
</button>
|
|
27
|
+
</form>
|
|
28
|
+
|
|
29
|
+
<p class="mt-6 text-sm text-gray-600">No spam. Unsubscribe anytime.</p>
|
|
30
|
+
</section>
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
<div class="mx-auto max-w-sm">
|
|
2
|
+
<label for="Notes">
|
|
3
|
+
<span class="text-sm font-medium text-gray-700">Notes</span>
|
|
4
|
+
|
|
5
|
+
<div class="relative mt-0.5 overflow-hidden rounded border border-gray-300 shadow-sm focus-within:ring focus-within:ring-blue-600">
|
|
6
|
+
<textarea
|
|
7
|
+
id="Notes"
|
|
8
|
+
class="w-full resize-none border-none outline-none focus:ring-0 sm:text-sm"
|
|
9
|
+
rows="4"
|
|
10
|
+
></textarea>
|
|
11
|
+
|
|
12
|
+
<div class="flex items-center justify-end gap-2 p-1.5">
|
|
13
|
+
<button
|
|
14
|
+
type="button"
|
|
15
|
+
class="rounded border border-transparent px-3 py-1.5 text-sm font-medium text-gray-700 transition-colors hover:text-gray-900"
|
|
16
|
+
>
|
|
17
|
+
Clear
|
|
18
|
+
</button>
|
|
19
|
+
|
|
20
|
+
<button
|
|
21
|
+
type="button"
|
|
22
|
+
class="rounded border border-gray-300 px-3 py-1.5 text-sm font-medium text-gray-900 shadow-sm transition-colors hover:bg-gray-100"
|
|
23
|
+
>
|
|
24
|
+
Save
|
|
25
|
+
</button>
|
|
26
|
+
</div>
|
|
27
|
+
</div>
|
|
28
|
+
</label>
|
|
29
|
+
</div>
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
<div class="mx-auto max-w-sm">
|
|
2
|
+
<label for="Notes">
|
|
3
|
+
<span class="text-sm font-medium text-gray-700">Notes</span>
|
|
4
|
+
|
|
5
|
+
<div class="relative mt-0.5 overflow-hidden rounded border border-gray-300 shadow-sm focus-within:ring focus-within:ring-blue-600">
|
|
6
|
+
<textarea
|
|
7
|
+
id="Notes"
|
|
8
|
+
class="w-full resize-none border-none outline-none focus:ring-0 sm:text-sm"
|
|
9
|
+
rows="4"
|
|
10
|
+
></textarea>
|
|
11
|
+
</div>
|
|
12
|
+
</label>
|
|
13
|
+
|
|
14
|
+
<div class="mt-2 flex items-center justify-end gap-2">
|
|
15
|
+
<button
|
|
16
|
+
type="button"
|
|
17
|
+
class="rounded border border-transparent px-3 py-1.5 text-sm font-medium text-gray-700 transition-colors hover:text-gray-900"
|
|
18
|
+
>
|
|
19
|
+
Clear
|
|
20
|
+
</button>
|
|
21
|
+
|
|
22
|
+
<button
|
|
23
|
+
type="button"
|
|
24
|
+
class="rounded border border-gray-300 px-3 py-1.5 text-sm font-medium text-gray-900 shadow-sm transition-colors hover:bg-gray-100"
|
|
25
|
+
>
|
|
26
|
+
Save
|
|
27
|
+
</button>
|
|
28
|
+
</div>
|
|
29
|
+
</div>
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
export default function Newsletter() {
|
|
2
|
+
return (
|
|
3
|
+
<section className="mx-auto w-full max-w-xl rounded-2xl border border-gray-200 bg-zinc-50 p-8 text-center sm:p-10">
|
|
4
|
+
<h2 className="text-3xl font-bold tracking-tight text-gray-950">
|
|
5
|
+
Stay in the loop
|
|
6
|
+
</h2>
|
|
7
|
+
|
|
8
|
+
<p className="mx-auto mt-4 max-w-lg text-lg leading-7 text-gray-700">
|
|
9
|
+
Subscribe to our newsletter for updates, new releases, and useful
|
|
10
|
+
resources.
|
|
11
|
+
</p>
|
|
12
|
+
|
|
13
|
+
<form className="mt-8">
|
|
14
|
+
<label htmlFor="email" className="sr-only">
|
|
15
|
+
Email address
|
|
16
|
+
</label>
|
|
17
|
+
|
|
18
|
+
<input
|
|
19
|
+
id="email"
|
|
20
|
+
type="email"
|
|
21
|
+
placeholder="Enter your email"
|
|
22
|
+
className="w-full rounded-lg border border-gray-300 bg-white px-5 py-4 text-base text-gray-950 outline-none transition focus:border-gray-950 focus:ring-1 focus:ring-gray-950"
|
|
23
|
+
required
|
|
24
|
+
/>
|
|
25
|
+
|
|
26
|
+
<button
|
|
27
|
+
type="submit"
|
|
28
|
+
className="mt-3 w-full rounded-lg bg-zinc-600 px-5 py-4 text-base font-semibold text-white transition hover:bg-zinc-700"
|
|
29
|
+
>
|
|
30
|
+
Subscribe
|
|
31
|
+
</button>
|
|
32
|
+
</form>
|
|
33
|
+
|
|
34
|
+
<p className="mt-6 text-sm text-gray-600">
|
|
35
|
+
No spam. Unsubscribe anytime.
|
|
36
|
+
</p>
|
|
37
|
+
</section>
|
|
38
|
+
);
|
|
39
|
+
}
|
|
@@ -15,17 +15,17 @@ export default function TextArea() {
|
|
|
15
15
|
</div>
|
|
16
16
|
</label>
|
|
17
17
|
|
|
18
|
-
<div
|
|
18
|
+
<div className="mt-2 flex items-center justify-end gap-2">
|
|
19
19
|
<button
|
|
20
20
|
type="button"
|
|
21
|
-
|
|
21
|
+
className="rounded border border-transparent px-3 py-1.5 text-sm font-medium text-gray-700 transition-colors hover:text-gray-900"
|
|
22
22
|
>
|
|
23
23
|
Clear
|
|
24
24
|
</button>
|
|
25
25
|
|
|
26
26
|
<button
|
|
27
27
|
type="button"
|
|
28
|
-
|
|
28
|
+
className="rounded border border-gray-300 px-3 py-1.5 text-sm font-medium text-gray-900 shadow-sm transition-colors hover:bg-gray-100"
|
|
29
29
|
>
|
|
30
30
|
Save
|
|
31
31
|
</button>
|