@buttonschool/create-wireframe 0.1.1 → 0.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.
@@ -0,0 +1,31 @@
1
+ /* Wireframe Kit – text input component. Uses --wire-* tokens only. */
2
+
3
+ .wire-input {
4
+ display: block;
5
+ width: 100%;
6
+ min-inline-size: 0;
7
+ padding: var(--wire-space-md) var(--wire-space-lg);
8
+ font-family: inherit;
9
+ font-size: var(--wire-text-body);
10
+ color: var(--wire-text-primary);
11
+ background-color: var(--wire-surface);
12
+ border: var(--wire-border-width) solid var(--wire-border);
13
+ border-radius: var(--wire-radius-lg);
14
+ box-sizing: border-box;
15
+ }
16
+
17
+ .wire-input::placeholder {
18
+ color: var(--wire-text-placeholder);
19
+ }
20
+
21
+ .wire-input:focus {
22
+ outline: none;
23
+ border-color: var(--wire-dark);
24
+ }
25
+
26
+ .wire-input:disabled {
27
+ color: var(--wire-text-muted);
28
+ background-color: var(--wire-surface-alt);
29
+ border-color: var(--wire-border-light);
30
+ cursor: not-allowed;
31
+ }
@@ -0,0 +1,14 @@
1
+ /* Wireframe Kit – label component. Uses --wire-* tokens only. */
2
+
3
+ .wire-label {
4
+ display: block;
5
+ font-size: var(--wire-text-label);
6
+ font-weight: var(--wire-font-weight-bold);
7
+ color: var(--wire-text-secondary);
8
+ margin-block-end: var(--wire-space-2xs);
9
+ }
10
+
11
+ .wire-label--required::after {
12
+ content: " *";
13
+ color: var(--wire-text-muted);
14
+ }
@@ -0,0 +1,26 @@
1
+ /* Wireframe Kit – radio component. Uses --wire-* tokens only. */
2
+
3
+ .wire-radio {
4
+ display: flex;
5
+ align-items: center;
6
+ gap: var(--wire-space-sm);
7
+ cursor: pointer;
8
+ font-size: var(--wire-text-body);
9
+ color: var(--wire-text-primary);
10
+ }
11
+
12
+ .wire-radio input {
13
+ width: var(--wire-size-icon-md);
14
+ height: var(--wire-size-icon-md);
15
+ accent-color: var(--wire-dark);
16
+ cursor: pointer;
17
+ }
18
+
19
+ .wire-radio:has(input:disabled) {
20
+ color: var(--wire-text-muted);
21
+ cursor: not-allowed;
22
+ }
23
+
24
+ .wire-radio:has(input:disabled) input {
25
+ cursor: not-allowed;
26
+ }
@@ -0,0 +1,69 @@
1
+ /* Wireframe Kit – select component. Uses --wire-* tokens only. */
2
+
3
+ .wire-select,
4
+ .wire-select-wrap select {
5
+ display: block;
6
+ width: 100%;
7
+ min-inline-size: 0;
8
+ padding: var(--wire-space-md) var(--wire-space-lg);
9
+ font-family: inherit;
10
+ font-size: var(--wire-text-body);
11
+ color: var(--wire-text-primary);
12
+ background-color: var(--wire-surface);
13
+ border: var(--wire-border-width) solid var(--wire-border);
14
+ border-radius: var(--wire-radius-lg);
15
+ box-sizing: border-box;
16
+ cursor: pointer;
17
+ appearance: auto;
18
+ }
19
+
20
+ .wire-select:focus,
21
+ .wire-select-wrap select:focus {
22
+ outline: none;
23
+ border-color: var(--wire-dark);
24
+ }
25
+
26
+ .wire-select:disabled,
27
+ .wire-select-wrap select:disabled {
28
+ color: var(--wire-text-muted);
29
+ background-color: var(--wire-surface-alt);
30
+ border-color: var(--wire-border-light);
31
+ cursor: not-allowed;
32
+ }
33
+
34
+ /* Wrapper: hides native arrow and adds chevron via CSS (no icon element). */
35
+ .wire-select-wrap {
36
+ position: relative;
37
+ display: block;
38
+ }
39
+
40
+ .wire-select-wrap select {
41
+ appearance: none;
42
+ -webkit-appearance: none;
43
+ padding-inline-end: calc(var(--wire-space-lg) + var(--wire-size-icon-sm) + var(--wire-space-sm));
44
+ }
45
+
46
+ /* Chevron (Lucide-style) as pseudo-element so no JS or extra HTML is needed. */
47
+ .wire-select-wrap::after {
48
+ content: "";
49
+ position: absolute;
50
+ inset-inline-end: var(--wire-space-md);
51
+ top: 50%;
52
+ transform: translateY(-50%);
53
+ width: var(--wire-size-icon-sm);
54
+ height: var(--wire-size-icon-sm);
55
+ background-color: currentColor;
56
+ mask: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='black' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='m6 9 6 6 6-6'/%3E%3C/svg%3E") no-repeat center;
57
+ mask-size: contain;
58
+ -webkit-mask: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='black' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='m6 9 6 6 6-6'/%3E%3C/svg%3E") no-repeat center;
59
+ -webkit-mask-size: contain;
60
+ pointer-events: none;
61
+ }
62
+
63
+ .wire-select-wrap {
64
+ color: var(--wire-text-muted);
65
+ }
66
+
67
+ .wire-select-wrap:has(select:disabled) {
68
+ color: var(--wire-text-placeholder);
69
+ }
@@ -0,0 +1,33 @@
1
+ /* Wireframe Kit – textarea component. Uses --wire-* tokens only. */
2
+
3
+ .wire-textarea {
4
+ display: block;
5
+ width: 100%;
6
+ min-inline-size: 0;
7
+ padding: var(--wire-space-md) var(--wire-space-lg);
8
+ font-family: inherit;
9
+ font-size: var(--wire-text-body);
10
+ line-height: var(--wire-line-height);
11
+ color: var(--wire-text-primary);
12
+ background-color: var(--wire-surface);
13
+ border: var(--wire-border-width) solid var(--wire-border);
14
+ border-radius: var(--wire-radius-lg);
15
+ box-sizing: border-box;
16
+ resize: vertical;
17
+ }
18
+
19
+ .wire-textarea::placeholder {
20
+ color: var(--wire-text-placeholder);
21
+ }
22
+
23
+ .wire-textarea:focus {
24
+ outline: none;
25
+ border-color: var(--wire-dark);
26
+ }
27
+
28
+ .wire-textarea:disabled {
29
+ color: var(--wire-text-muted);
30
+ background-color: var(--wire-surface-alt);
31
+ border-color: var(--wire-border-light);
32
+ cursor: not-allowed;
33
+ }
@@ -29,7 +29,24 @@
29
29
  --wire-font-weight-bold: 700;
30
30
  --wire-line-height: 1.4;
31
31
 
32
+ /* Type scale (rem), adapted from AUI wireframe kit */
33
+ --wire-text-2xs: 0.625rem;
34
+ --wire-text-xs: 0.75rem;
35
+ --wire-text-sm: 0.875rem;
36
+ --wire-text-base: 1rem;
37
+ --wire-text-lg: 1.125rem;
38
+ --wire-text-xl: 1.25rem;
39
+ --wire-text-2xl: 1.5rem;
40
+
41
+ /* Semantic type aliases */
42
+ --wire-text-body: var(--wire-text-sm);
43
+ --wire-text-caption: var(--wire-text-xs);
44
+ --wire-text-label: var(--wire-text-sm);
45
+ --wire-text-heading: var(--wire-text-2xl);
46
+ --wire-text-subheading: var(--wire-text-xl);
47
+
32
48
  /* Spacing scale */
49
+ --wire-space-2xs: 2px;
33
50
  --wire-space-xs: 4px;
34
51
  --wire-space-sm: 8px;
35
52
  --wire-space-md: 12px;
@@ -38,9 +55,20 @@
38
55
  --wire-space-2xl: 24px;
39
56
  --wire-space-3xl: 32px;
40
57
 
58
+ /* Border width – controls and strokes */
59
+ --wire-border-width: 2px;
60
+
41
61
  /* Border radius */
42
62
  --wire-radius-sm: 4px;
43
63
  --wire-radius-md: 6px;
44
64
  --wire-radius-lg: 8px;
45
65
  --wire-radius-full: 50%;
66
+
67
+ /* Sizing – icons (square) and avatars (diameter) */
68
+ --wire-size-icon-sm: 1rem;
69
+ --wire-size-icon-md: 1.25rem;
70
+ --wire-size-icon-lg: 1.5rem;
71
+ --wire-size-avatar-sm: 1.5rem;
72
+ --wire-size-avatar-md: 2rem;
73
+ --wire-size-avatar-lg: 2.5rem;
46
74
  }
@@ -1,6 +1 @@
1
- import "./style.css";
2
-
3
- document.querySelector("#app").innerHTML = `
4
- <h1>Wireframe</h1>
5
- <p>Edit <code>src/main.js</code> and save. Vite will hot-reload.</p>
6
- `;
1
+ import "./game.js";
@@ -0,0 +1,24 @@
1
+ {
2
+ "site": {
3
+ "title": "Wireframe",
4
+ "nav": { "start": "Start", "tokens": "Tokens", "components": "Components" }
5
+ },
6
+ "game": {
7
+ "scoreLabel": " points",
8
+ "inputLabel": "Your word",
9
+ "inputPlaceholder": "Enter a word",
10
+ "submitButton": "Guess",
11
+ "foundHeading": "Found words",
12
+ "hint": "Make words with the letters. Use the center letter in every word.",
13
+ "feedback": {
14
+ "tryAgain": "Try again.",
15
+ "tooShort": "Too short.",
16
+ "missingCenter": "Missing center letter.",
17
+ "invalidLetters": "Invalid letters.",
18
+ "notInList": "Not in word list.",
19
+ "alreadyFound": "Already found.",
20
+ "pangram": "Pangram!",
21
+ "good": "Good!"
22
+ }
23
+ }
24
+ }
@@ -1,13 +1,13 @@
1
- @import "./kit/tokens.css";
1
+ *,
2
+ *::before,
3
+ *::after {
4
+ box-sizing: border-box;
5
+ }
2
6
 
3
7
  body {
8
+ margin: 0;
4
9
  font-family: var(--wire-font-family);
5
10
  line-height: var(--wire-line-height);
6
11
  color: var(--wire-text-primary);
7
- background-color: var(--wire-surface);
8
- margin: 0;
9
- }
10
-
11
- #app {
12
- padding: var(--wire-space-xl);
12
+ background-color: var(--wire-bg);
13
13
  }
@@ -0,0 +1,36 @@
1
+ .site-nav {
2
+ display: flex;
3
+ gap: 0;
4
+ padding: 0 var(--wire-space-lg);
5
+ border-bottom: var(--wire-border-width) solid var(--wire-border-light);
6
+ background-color: var(--wire-surface);
7
+ }
8
+
9
+ .site-nav a {
10
+ color: var(--wire-text-secondary);
11
+ display: block;
12
+ font-weight: var(--wire-font-weight-bold);
13
+ padding: var(--wire-space-sm) var(--wire-space-md);
14
+ text-decoration: none;
15
+ }
16
+
17
+ .site-nav a:hover {
18
+ color: var(--wire-text-primary);
19
+ }
20
+
21
+ .site-nav a[aria-current="page"] {
22
+ color: var(--wire-text-primary);
23
+ position: relative;
24
+ }
25
+
26
+ .site-nav a[aria-current="page"]::after {
27
+ content: "";
28
+ display: block;
29
+ height: var(--wire-border-width);
30
+ background-color: var(--wire-light);
31
+ border-radius: var(--wire-radius-sm) var(--wire-radius-sm) 0 0;
32
+ position: absolute;
33
+ bottom: 0;
34
+ left: 0;
35
+ right: 0;
36
+ }
@@ -0,0 +1,5 @@
1
+ main {
2
+ max-width: 60ch;
3
+ margin: 0 auto;
4
+ padding: var(--wire-space-xl);
5
+ }
@@ -0,0 +1,15 @@
1
+ @import "../kit/tokens.css";
2
+ @import "../kit/components/button.css";
3
+ @import "../kit/components/input.css";
4
+ @import "../kit/components/textarea.css";
5
+ @import "../kit/components/checkbox.css";
6
+ @import "../kit/components/radio.css";
7
+ @import "../kit/components/select.css";
8
+ @import "../kit/components/label.css";
9
+ @import "../kit/components/field.css";
10
+ @import "base.css";
11
+ @import "layout.css";
12
+ @import "components/nav.css";
13
+ @import "pages/start.css";
14
+ @import "pages/tokens-showcase.css";
15
+ @import "pages/components-showcase.css";
@@ -0,0 +1,38 @@
1
+ /* Components showcase page. Reuses .showcase-section from tokens-showcase. */
2
+
3
+ .components-showcase-intro {
4
+ margin-block-end: var(--wire-space-2xl);
5
+ color: var(--wire-text-muted);
6
+ }
7
+
8
+ .components-showcase code {
9
+ padding: var(--wire-space-2xs) 0;
10
+ background-color: var(--wire-surface-alt);
11
+ border-radius: var(--wire-radius-sm);
12
+ font-family: "Monaspace Argon", monospace;
13
+ font-size: var(--wire-text-xs);
14
+ color: #c41;
15
+ white-space: nowrap;
16
+ }
17
+
18
+ .component-demo-row {
19
+ display: flex;
20
+ flex-wrap: wrap;
21
+ gap: var(--wire-space-md);
22
+ align-items: center;
23
+ }
24
+
25
+ .component-demo-block {
26
+ max-inline-size: 20rem;
27
+ margin-block-end: var(--wire-space-lg);
28
+ }
29
+
30
+ .component-demo-block:last-child {
31
+ margin-block-end: 0;
32
+ }
33
+
34
+ .component-demo-stack {
35
+ display: flex;
36
+ flex-direction: column;
37
+ gap: var(--wire-space-md);
38
+ }
@@ -0,0 +1,243 @@
1
+ /* Start page – Spelling Bee game */
2
+
3
+ .visually-hidden {
4
+ position: absolute;
5
+ inline-size: 1px;
6
+ block-size: 1px;
7
+ padding: 0;
8
+ margin: -1px;
9
+ overflow: hidden;
10
+ clip: rect(0, 0, 0, 0);
11
+ white-space: nowrap;
12
+ border: 0;
13
+ }
14
+
15
+ .game-area {
16
+ max-inline-size: 36rem;
17
+ margin-inline: auto;
18
+ }
19
+
20
+ .game-area .bee-score {
21
+ display: flex;
22
+ justify-content: flex-end;
23
+ align-items: center;
24
+ gap: var(--wire-space-sm);
25
+ font-size: var(--wire-text-xl);
26
+ margin-block-end: var(--wire-space-lg);
27
+ }
28
+
29
+ .game-area .bee-score-icon {
30
+ width: var(--wire-size-icon-md);
31
+ height: var(--wire-size-icon-md);
32
+ flex-shrink: 0;
33
+ color: var(--wire-text-muted);
34
+ }
35
+
36
+ .game-area .bee-score-value {
37
+ font-weight: var(--wire-font-weight-bold);
38
+ }
39
+
40
+ .game-area .bee-score-label {
41
+ font-size: var(--wire-text-body);
42
+ font-weight: var(--wire-font-weight-normal);
43
+ color: var(--wire-text-muted);
44
+ }
45
+
46
+ /* Honeycomb: 7 letters, pointy-top hexes via ::before, absolute positioning */
47
+ .bee-honeycomb {
48
+ --width: 3.25em;
49
+ --height: calc(var(--width) * 0.8660254);
50
+ --gap: var(--wire-space-xs);
51
+ box-sizing: content-box;
52
+ position: relative;
53
+ height: calc(3 * var(--height) + 2 * var(--gap));
54
+ width: calc(2.5 * var(--width) + 2 * 1.1547 * var(--gap));
55
+ margin-block-end: var(--wire-space-2xl);
56
+ margin-inline: auto;
57
+ padding: calc(var(--height) / 2 - var(--gap)) calc(var(--width) / 2 - var(--gap));
58
+ }
59
+
60
+ /* DOM order: 1=E(center), 2=W, 3=I, 4=R, 5=F, 6=A, 7=M */
61
+ .bee-honeycomb .bee-letter:nth-child(1) {
62
+ transform: scale(var(--bee-scale, 1));
63
+ }
64
+ .bee-honeycomb .bee-letter:nth-child(2) {
65
+ transform: translate(0, calc(-1 * var(--height) - var(--gap))) scale(var(--bee-scale, 1));
66
+ }
67
+ .bee-honeycomb .bee-letter:nth-child(3) {
68
+ transform: translate(
69
+ calc(0.75 * var(--width) + 1.1547 * var(--gap)),
70
+ calc(-0.5 * var(--height) - 0.5 * var(--gap))
71
+ ) scale(var(--bee-scale, 1));
72
+ }
73
+ .bee-honeycomb .bee-letter:nth-child(4) {
74
+ transform: translate(
75
+ calc(0.75 * var(--width) + 1.1547 * var(--gap)),
76
+ calc(0.5 * var(--height) + 0.5 * var(--gap))
77
+ ) scale(var(--bee-scale, 1));
78
+ }
79
+ .bee-honeycomb .bee-letter:nth-child(5) {
80
+ transform: translate(
81
+ calc(-0.75 * var(--width) - 1.1547 * var(--gap)),
82
+ calc(-0.5 * var(--height) - 0.5 * var(--gap))
83
+ ) scale(var(--bee-scale, 1));
84
+ }
85
+ .bee-honeycomb .bee-letter:nth-child(6) {
86
+ transform: translate(
87
+ calc(-0.75 * var(--width) - 1.1547 * var(--gap)),
88
+ calc(0.5 * var(--height) + 0.5 * var(--gap))
89
+ ) scale(var(--bee-scale, 1));
90
+ }
91
+ .bee-honeycomb .bee-letter:nth-child(7) {
92
+ transform: translate(0, calc(var(--height) + var(--gap))) scale(var(--bee-scale, 1));
93
+ }
94
+
95
+ .bee-letter {
96
+ --bee-hex: polygon(25% 0%, 75% 0%, 100% 50%, 75% 100%, 25% 100%, 0% 50%);
97
+ --bee-scale: 1;
98
+ position: absolute;
99
+ left: 50%;
100
+ top: 50%;
101
+ width: var(--width);
102
+ height: var(--height);
103
+ margin-left: calc(-0.5 * var(--width));
104
+ margin-top: calc(-0.5 * var(--height));
105
+ display: flex;
106
+ align-items: center;
107
+ justify-content: center;
108
+ font-family: inherit;
109
+ font-size: var(--wire-text-xl);
110
+ font-weight: var(--wire-font-weight-bold);
111
+ color: var(--wire-text-primary);
112
+ cursor: pointer;
113
+ transition: transform 50ms ease-out;
114
+ }
115
+ .bee-letter:active,
116
+ .bee-letter.bee-letter--typed-press {
117
+ --bee-scale: 0.92;
118
+ }
119
+
120
+ .bee-letter::before {
121
+ content: "";
122
+ position: absolute;
123
+ inset: 2px;
124
+ z-index: -1;
125
+ background-color: var(--wire-white);
126
+ clip-path: var(--bee-hex);
127
+ -webkit-clip-path: var(--bee-hex);
128
+ }
129
+
130
+ .bee-letter::after {
131
+ content: "";
132
+ position: absolute;
133
+ inset: 0;
134
+ z-index: -2;
135
+ background-color: var(--wire-black);
136
+ clip-path: var(--bee-hex);
137
+ -webkit-clip-path: var(--bee-hex);
138
+ }
139
+
140
+ .bee-letter.bee-letter--center {
141
+ color: var(--wire-white);
142
+ z-index: 1;
143
+ }
144
+
145
+ .bee-letter.bee-letter--center::before {
146
+ background-color: var(--wire-dark);
147
+ }
148
+
149
+ .bee-focus-region:focus {
150
+ outline: none;
151
+ }
152
+
153
+ /* Word input row */
154
+ .bee-input-row {
155
+ display: flex;
156
+ gap: var(--wire-space-sm);
157
+ margin-block-end: var(--wire-space-md);
158
+ }
159
+
160
+ .bee-input {
161
+ flex: 1;
162
+ min-inline-size: 0;
163
+ padding: var(--wire-space-md) var(--wire-space-lg);
164
+ font-family: inherit;
165
+ font-size: var(--wire-text-body);
166
+ color: var(--wire-text-primary);
167
+ background-color: var(--wire-surface);
168
+ border: var(--wire-border-width) solid var(--wire-border);
169
+ border-radius: var(--wire-radius-lg);
170
+ }
171
+
172
+ .bee-input::placeholder {
173
+ color: var(--wire-text-placeholder);
174
+ }
175
+
176
+ .bee-input:focus,
177
+ .game-area:focus-within .bee-input {
178
+ outline: none;
179
+ border-color: var(--wire-dark);
180
+ }
181
+
182
+ .bee-submit {
183
+ padding: var(--wire-space-md) var(--wire-space-xl);
184
+ font-family: inherit;
185
+ font-size: var(--wire-text-body);
186
+ font-weight: var(--wire-font-weight-bold);
187
+ color: var(--wire-white);
188
+ background-color: var(--wire-dark);
189
+ border: var(--wire-border-width) solid var(--wire-dark);
190
+ border-radius: var(--wire-radius-lg);
191
+ cursor: pointer;
192
+ }
193
+
194
+ .bee-submit:hover {
195
+ background-color: var(--wire-black);
196
+ border-color: var(--wire-black);
197
+ }
198
+
199
+ /* Feedback message */
200
+ .bee-feedback {
201
+ min-block-size: 1.5em;
202
+ margin-block-end: var(--wire-space-lg);
203
+ font-size: var(--wire-text-body);
204
+ color: var(--wire-text-secondary);
205
+ }
206
+
207
+ .bee-feedback.bee-feedback--success {
208
+ color: var(--wire-text-primary);
209
+ font-weight: var(--wire-font-weight-bold);
210
+ }
211
+
212
+ .bee-feedback.bee-feedback--error {
213
+ color: var(--wire-text-primary);
214
+ }
215
+
216
+ /* Found words list */
217
+ .bee-found-heading {
218
+ font-size: var(--wire-text-sm);
219
+ font-weight: var(--wire-font-weight-bold);
220
+ color: var(--wire-text-muted);
221
+ margin-block-end: var(--wire-space-sm);
222
+ }
223
+
224
+ .bee-found-list {
225
+ display: flex;
226
+ flex-wrap: wrap;
227
+ gap: var(--wire-space-xs) var(--wire-space-lg);
228
+ font-size: var(--wire-text-body);
229
+ color: var(--wire-text-secondary);
230
+ list-style: none;
231
+ padding: 0;
232
+ margin: 0;
233
+ }
234
+
235
+ .bee-found-list li {
236
+ display: flex;
237
+ align-items: center;
238
+ gap: var(--wire-space-xs);
239
+ }
240
+
241
+ .bee-found-list .bee-pangram {
242
+ font-weight: var(--wire-font-weight-bold);
243
+ }