@mikenotthepope/substrateui 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +226 -0
- package/base/substrate.css +489 -0
- package/dist/index.d.mts +1215 -0
- package/dist/index.d.ts +1215 -0
- package/dist/index.js +6472 -0
- package/dist/index.js.map +1 -0
- package/dist/index.mjs +6359 -0
- package/dist/index.mjs.map +1 -0
- package/package.json +159 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2025 mikenotthepope
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
package/README.md
ADDED
|
@@ -0,0 +1,226 @@
|
|
|
1
|
+
# Substrate UI
|
|
2
|
+
|
|
3
|
+
A neobrutalist React component library with bold borders, hard shadows, and high contrast design. Built on [Radix UI](https://www.radix-ui.com/) primitives and [Tailwind CSS v4](https://tailwindcss.com/).
|
|
4
|
+
|
|
5
|
+
[](LICENSE)
|
|
6
|
+
[](https://www.typescriptlang.org/)
|
|
7
|
+
[](https://react.dev/)
|
|
8
|
+
|
|
9
|
+
**[Documentation & Demos](https://www.substrateui.dev)** | **[Storybook](https://www.substrateui.dev)** | **[npm](https://www.npmjs.com/package/@mikenotthepope/substrateui)**
|
|
10
|
+
|
|
11
|
+
---
|
|
12
|
+
|
|
13
|
+
## Why Substrate UI?
|
|
14
|
+
|
|
15
|
+
Most component libraries optimize for invisibility — neutral colors, subtle shadows, rounded everything. Substrate UI goes the other direction: **hard pixel-offset shadows, bold borders, and sharp corners by default.** It's opinionated about aesthetics but flexible about theming, built on Radix UI so accessibility comes free.
|
|
16
|
+
|
|
17
|
+
- **57 UI primitives** — Button, Dialog, Tabs, Select, DataTable, and more
|
|
18
|
+
- **12 landing page components** — Hero, Pricing, FAQ, Testimonials, and more
|
|
19
|
+
- **5 composite layouts** — NavBar, CardGrid, SectionNav, SimplePage, TwoColumnLayout
|
|
20
|
+
- **Light & dark themes** with CSS custom properties
|
|
21
|
+
- **Tree-shakeable** ESM + CJS builds
|
|
22
|
+
- **Full TypeScript** support with exported types
|
|
23
|
+
|
|
24
|
+
## Quick Start
|
|
25
|
+
|
|
26
|
+
### Install
|
|
27
|
+
|
|
28
|
+
```bash
|
|
29
|
+
npm install @mikenotthepope/substrateui
|
|
30
|
+
```
|
|
31
|
+
|
|
32
|
+
Requires `react` and `react-dom` v19+ as peer dependencies.
|
|
33
|
+
|
|
34
|
+
### Import the stylesheet
|
|
35
|
+
|
|
36
|
+
Add the base stylesheet once in your app root. This provides all design tokens and component styles.
|
|
37
|
+
|
|
38
|
+
```tsx
|
|
39
|
+
// app/layout.tsx (Next.js) or src/main.tsx (Vite)
|
|
40
|
+
import "@mikenotthepope/substrateui/styles";
|
|
41
|
+
```
|
|
42
|
+
|
|
43
|
+
### Use components
|
|
44
|
+
|
|
45
|
+
```tsx
|
|
46
|
+
import { Button, Card, Text } from "@mikenotthepope/substrateui";
|
|
47
|
+
|
|
48
|
+
export function Example() {
|
|
49
|
+
return (
|
|
50
|
+
<Card>
|
|
51
|
+
<Card.Header>
|
|
52
|
+
<Text variant="h3">Hello</Text>
|
|
53
|
+
</Card.Header>
|
|
54
|
+
<Card.Body>
|
|
55
|
+
<Text>Neobrutalist components, ready to go.</Text>
|
|
56
|
+
<Button>Get Started</Button>
|
|
57
|
+
</Card.Body>
|
|
58
|
+
</Card>
|
|
59
|
+
);
|
|
60
|
+
}
|
|
61
|
+
```
|
|
62
|
+
|
|
63
|
+
## Fonts
|
|
64
|
+
|
|
65
|
+
Substrate UI uses three font families via CSS custom properties:
|
|
66
|
+
|
|
67
|
+
| Token | Default Font | Purpose |
|
|
68
|
+
| -------------- | --------------- | ---------- |
|
|
69
|
+
| `--font-head` | Archivo Black | Headings |
|
|
70
|
+
| `--font-sans` | Space Grotesk | Body text |
|
|
71
|
+
| `--font-mono` | Space Mono | Code |
|
|
72
|
+
|
|
73
|
+
**Next.js:**
|
|
74
|
+
|
|
75
|
+
```tsx
|
|
76
|
+
import { Space_Grotesk, Archivo_Black, Space_Mono } from "next/font/google";
|
|
77
|
+
|
|
78
|
+
const sans = Space_Grotesk({ variable: "--font-sans", subsets: ["latin"], weight: "400" });
|
|
79
|
+
const head = Archivo_Black({ variable: "--font-head", subsets: ["latin"], weight: "400" });
|
|
80
|
+
const mono = Space_Mono({ variable: "--font-mono", subsets: ["latin"], weight: "400" });
|
|
81
|
+
|
|
82
|
+
export default function RootLayout({ children }) {
|
|
83
|
+
return (
|
|
84
|
+
<html className={`${sans.variable} ${head.variable} ${mono.variable}`}>
|
|
85
|
+
<body>{children}</body>
|
|
86
|
+
</html>
|
|
87
|
+
);
|
|
88
|
+
}
|
|
89
|
+
```
|
|
90
|
+
|
|
91
|
+
**Plain HTML / Vite:**
|
|
92
|
+
|
|
93
|
+
```html
|
|
94
|
+
<link href="https://fonts.googleapis.com/css2?family=Archivo+Black&family=Space+Grotesk:wght@400;500;700&family=Space+Mono&display=swap" rel="stylesheet">
|
|
95
|
+
<style>
|
|
96
|
+
:root {
|
|
97
|
+
--font-head: 'Archivo Black', sans-serif;
|
|
98
|
+
--font-sans: 'Space Grotesk', sans-serif;
|
|
99
|
+
--font-mono: 'Space Mono', monospace;
|
|
100
|
+
}
|
|
101
|
+
</style>
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
If fonts aren't loaded, the library falls back to `Space Grotesk -> system-ui -> sans-serif`.
|
|
105
|
+
|
|
106
|
+
## Theming
|
|
107
|
+
|
|
108
|
+
### Light / Dark Mode
|
|
109
|
+
|
|
110
|
+
Use the built-in `ThemeProvider` to manage theme switching:
|
|
111
|
+
|
|
112
|
+
```tsx
|
|
113
|
+
import { ThemeProvider } from "@mikenotthepope/substrateui";
|
|
114
|
+
|
|
115
|
+
function App({ children }) {
|
|
116
|
+
return (
|
|
117
|
+
<ThemeProvider defaultTheme="system">
|
|
118
|
+
{children}
|
|
119
|
+
</ThemeProvider>
|
|
120
|
+
);
|
|
121
|
+
}
|
|
122
|
+
```
|
|
123
|
+
|
|
124
|
+
Access and toggle the theme anywhere:
|
|
125
|
+
|
|
126
|
+
```tsx
|
|
127
|
+
import { useTheme } from "@mikenotthepope/substrateui";
|
|
128
|
+
|
|
129
|
+
function ThemeToggle() {
|
|
130
|
+
const { theme, setTheme } = useTheme();
|
|
131
|
+
return (
|
|
132
|
+
<button onClick={() => setTheme(theme === "dark" ? "light" : "dark")}>
|
|
133
|
+
Toggle theme
|
|
134
|
+
</button>
|
|
135
|
+
);
|
|
136
|
+
}
|
|
137
|
+
```
|
|
138
|
+
|
|
139
|
+
Accepts `"light"`, `"dark"`, or `"system"` (default). Persists to `localStorage` and respects `prefers-color-scheme`.
|
|
140
|
+
|
|
141
|
+
### Rounded Corners
|
|
142
|
+
|
|
143
|
+
Components have sharp corners by default. Add `with-radius` to opt in to rounded corners:
|
|
144
|
+
|
|
145
|
+
```html
|
|
146
|
+
<html class="with-radius">
|
|
147
|
+
```
|
|
148
|
+
|
|
149
|
+
### Custom Tokens
|
|
150
|
+
|
|
151
|
+
Override any CSS custom property to customize the theme:
|
|
152
|
+
|
|
153
|
+
```css
|
|
154
|
+
:root {
|
|
155
|
+
--primary: #6366f1;
|
|
156
|
+
--primary-foreground: #fff;
|
|
157
|
+
--primary-hover: #4f46e5;
|
|
158
|
+
}
|
|
159
|
+
```
|
|
160
|
+
|
|
161
|
+
See the full token reference in `base/substrate.css`.
|
|
162
|
+
|
|
163
|
+
## Components
|
|
164
|
+
|
|
165
|
+
### Primitives
|
|
166
|
+
|
|
167
|
+
Accordion, Alert, AlertDialog, Avatar, Badge, Breadcrumb, Button, Calendar, Card, Carousel, Chart, Checkbox, Collapsible, Combobox, Command, Container, ContextMenu, DataTable, Dialog, Divider, Drawer, DropdownMenu, Flex, Form, FormLayout, Grid, HoverCard, IconButton, ImageCard, Input, InputOTP, Label, Link, Loader, Marquee, Menu, Menubar, NavigationMenu, Pagination, Popover, Progress, RadioGroup, Resizable, ScrollArea, Select, Sheet, Sidebar, Skeleton, Slider, Sonner, Stack, Switch, Table, Tabs, Text, Textarea, Tooltip
|
|
168
|
+
|
|
169
|
+
### Landing
|
|
170
|
+
|
|
171
|
+
AnnouncementBanner, CTABanner, FAQ, FeatureSection, Footer, Hero, LogoCloud, NewsletterSignup, PricingTable, Section, StatsBar, Testimonial
|
|
172
|
+
|
|
173
|
+
### Composite
|
|
174
|
+
|
|
175
|
+
CardGrid, NavBar, SectionNav, SimplePage, TwoColumnLayout
|
|
176
|
+
|
|
177
|
+
## Framework Compatibility
|
|
178
|
+
|
|
179
|
+
Works in any React 19 environment — Next.js, Vite, Remix, etc.
|
|
180
|
+
|
|
181
|
+
The `NavBar` component accepts an optional `linkComponent` prop for framework-specific routing:
|
|
182
|
+
|
|
183
|
+
```tsx
|
|
184
|
+
import Link from "next/link";
|
|
185
|
+
import { NavBar } from "@mikenotthepope/substrateui";
|
|
186
|
+
|
|
187
|
+
<NavBar linkComponent={Link} brand={{ name: "MyApp" }} auth={{ state: "signed-out", href: "/login" }} />
|
|
188
|
+
```
|
|
189
|
+
|
|
190
|
+
When omitted, it defaults to a plain `<a>` tag.
|
|
191
|
+
|
|
192
|
+
## Development
|
|
193
|
+
|
|
194
|
+
```bash
|
|
195
|
+
bun install # Install dependencies
|
|
196
|
+
bun dev # Start the demo app (Next.js)
|
|
197
|
+
bun storybook # Start Storybook
|
|
198
|
+
bun test # Run tests
|
|
199
|
+
bun run build # Build the library (tsup)
|
|
200
|
+
```
|
|
201
|
+
|
|
202
|
+
### Project Structure
|
|
203
|
+
|
|
204
|
+
```
|
|
205
|
+
substrateui/
|
|
206
|
+
├── src/index.ts # Barrel export for the published package
|
|
207
|
+
├── components/ui/ # 57 primitive components
|
|
208
|
+
├── components/landing/ # 12 landing page components
|
|
209
|
+
├── components/ # Composite components + ThemeProvider
|
|
210
|
+
├── base/substrate.css # Design tokens & base styles
|
|
211
|
+
├── app/ # Next.js demo/docs site
|
|
212
|
+
├── AGENTS.md # Shared AI agent instructions
|
|
213
|
+
├── CLAUDE.md # Claude Code config (imports AGENTS.md)
|
|
214
|
+
└── tsup.config.ts # Library build config
|
|
215
|
+
```
|
|
216
|
+
|
|
217
|
+
## Acknowledgements
|
|
218
|
+
|
|
219
|
+
Substrate UI draws inspiration from these projects:
|
|
220
|
+
|
|
221
|
+
- [neobrutalism-components](https://github.com/ekmas/neobrutalism-components) by ekmas
|
|
222
|
+
- [RetroUI](https://github.com/logging-studio/retroui) by Logging Studio
|
|
223
|
+
|
|
224
|
+
## License
|
|
225
|
+
|
|
226
|
+
[MIT](LICENSE)
|