Skip to content

Commit 58cc486

Browse files
committed
feat: implement initial version of the library
1 parent b1e4d41 commit 58cc486

38 files changed

+1991
-1
lines changed

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
{
22
"name": "outlinecss",
33
"description": "A headless, responsive, and composable CSS framework designed for easy customization.",
4-
"version": "0.0.3",
4+
"version": "0.0.4",
55
"main": "./lib/index.js",
66
"types": "./lib/index.d.ts",
77
"bin": {

styles/components/_index.scss

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
// Form
2+
@forward "form/button";
3+
@forward "form/checkbox";
4+
@forward "form/input";
5+
@forward "form/radio";
6+
@forward "form/select";
7+
@forward "form/slider";
8+
@forward "form/textarea";
9+
@forward "form/toggle";
10+
11+
// Layout
12+
@forward "layout/card";
13+
@forward "layout/columns";
14+
@forward "layout/container";
15+
@forward "layout/dialog";
16+
@forward "layout/divider";
17+
@forward "layout/grid";
18+
@forward "layout/hero";
19+
@forward "layout/stack";
20+
21+
// Navigation
22+
@forward "navigation/dropdown";
23+
@forward "navigation/link";
24+
@forward "navigation/navbar";
25+
@forward "navigation/menu2";
Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
.button {
2+
--ui__button__spacing-x: var(--spacing__md);
3+
--ui__button__spacing-y: var(--spacing__xs);
4+
--ui__button__text-color: var(--color__current);
5+
--ui__button__background: transparent;
6+
--ui__button__border-color: var(--color__current);
7+
--ui__button__roundness: var(--roundness);
8+
--ui__button__shadow: var(--shadow__none);
9+
10+
box-sizing: border-box;
11+
display: flex;
12+
flex-direction: column;
13+
justify-content: center;
14+
position: relative;
15+
font-family: inherit;
16+
font-size: inherit;
17+
font-weight: inherit;
18+
padding: var(--ui__button__spacing-y) var(--ui__button__spacing-x);
19+
color: var(--ui__button__text-color);
20+
background: var(--ui__button__background);
21+
border-color: var(--ui__button__border-color);
22+
border-width: 1px;
23+
border-style: none;
24+
border-radius: var(--ui__button__roundness);
25+
box-shadow: var(--ui__button__shadow);
26+
cursor: pointer;
27+
transition-property: color, background, background-color, border-color, box-shadow;
28+
transition-duration: var(--transition__duration);
29+
transition-timing-function: var(--transition__easing);
30+
31+
&:focus {
32+
outline-color: var(--color__current);
33+
}
34+
35+
&:is(a) {
36+
text-decoration: none;
37+
}
38+
}
Lines changed: 102 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,102 @@
1+
.checkbox {
2+
--ui__checkbox__scale: 1.5;
3+
--ui__checkbox__spacing-x: var(--spacing__md);
4+
--ui__checkbox__spacing-y: var(--spacing__xs);
5+
--ui__checkbox__text-color: var(--color__current);
6+
--ui__checkbox__background: transparent;
7+
--ui__checkbox__border-color: var(--color__current);
8+
--ui__checkbox__roundness: var(--roundness);
9+
--ui__checkbox__box-shadow: var(--shadow__none);
10+
--ui__checkbox__tick-color: var(--color__current);
11+
--ui__checkbox__box-color: transparent;
12+
13+
padding: var(--ui__checkbox__spacing-y) var(--ui__checkbox__spacing-x);
14+
color: var(--ui__checkbox__text-color);
15+
background: var(--ui__checkbox__background);
16+
border-radius: var(--ui__checkbox__roundness);
17+
18+
& > label::before {
19+
height: calc(1em * var(--ui__checkbox__scale));
20+
margin-right: var(--ui__checkbox__spacing-x);
21+
background: var(--ui__checkbox__box-color);
22+
border-color: var(--ui__checkbox__border-color);
23+
border-radius: var(--ui__checkbox__roundness);
24+
box-shadow: var(--ui__checkbox__box-shadow);
25+
}
26+
27+
& > label::after {
28+
left: calc(-100% + 1em * var(--ui__checkbox__scale));
29+
width: calc(1em * var(--ui__checkbox__scale));
30+
height: calc(1em * var(--ui__checkbox__scale));
31+
background: var(--ui__checkbox__tick-color);
32+
}
33+
}
34+
35+
.checkbox {
36+
box-sizing: border-box;
37+
white-space: nowrap;
38+
position: relative;
39+
transition-property: background;
40+
transition-duration: var(--transition__duration);
41+
transition-timing-function: var(--transition__easing);
42+
43+
& > input {
44+
appearance: none;
45+
box-sizing: border-box;
46+
position: absolute;
47+
top: 0;
48+
right: 0;
49+
bottom: 0;
50+
left: 0;
51+
color: inherit;
52+
cursor: pointer;
53+
z-index: 1;
54+
}
55+
56+
& > label {
57+
position: relative;
58+
}
59+
60+
& > label::before {
61+
content: "";
62+
box-sizing: border-box;
63+
display: inline-block;
64+
vertical-align: middle;
65+
margin-top: -3px; // Font Metrics hack
66+
border-style: solid;
67+
border-width: 1px;
68+
pointer-events: none;
69+
}
70+
71+
& > label::after {
72+
content: "";
73+
box-sizing: border-box;
74+
display: inline-block;
75+
vertical-align: middle;
76+
position: relative;
77+
margin-top: -3px; // Font Metrics hack
78+
transition-property: transform, left;
79+
transition-duration: var(--transition__duration);
80+
transition-timing-function: var(--transition__easing);
81+
}
82+
}
83+
84+
.checkbox {
85+
& > label::before {
86+
width: calc(1em * var(--ui__checkbox__scale));
87+
}
88+
}
89+
90+
// Checkbox
91+
.checkbox {
92+
& > label::after {
93+
mask: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyNCIgaGVpZ2h0PSIyNCIgdmlld0JveD0iMCAwIDI0IDI0IiBmaWxsPSJub25lIiBzdHJva2U9ImN1cnJlbnRDb2xvciIgc3Ryb2tlLXdpZHRoPSIyIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS1saW5lam9pbj0icm91bmQiIGNsYXNzPSJsdWNpZGUgbHVjaWRlLWNoZWNrIj48cGF0aCBkPSJNMjAgNiA5IDE3bC01LTUiLz48L3N2Zz4=") no-repeat 50% 50%;
94+
mask-size: cover;
95+
opacity: 0;
96+
transform: scale(0.75);
97+
}
98+
99+
& > input:checked + label::after {
100+
opacity: 1;
101+
}
102+
}

styles/components/form/_input.scss

Lines changed: 161 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,161 @@
1+
.input {
2+
--ui__input__spacing-x: var(--spacing__md);
3+
--ui__input__spacing-y: var(--spacing__xs);
4+
--ui__input__text-color: var(--color__current);
5+
--ui__input__background: transparent;
6+
--ui__input__border-color: --color__current;
7+
--ui__input__roundness: var(--roundness);
8+
--ui__input__shadow: var(--shadow__none);
9+
--ui__input__grip-color: var(--color__text-400);
10+
11+
box-sizing: border-box;
12+
position: relative;
13+
display: flex;
14+
min-width: 192px;
15+
max-width: fit-content;
16+
height: fit-content;
17+
color: var(--ui__input__text-color);
18+
background: var(--ui__input__background);
19+
border-color: var(--ui__input__border-color);
20+
border-width: 1px;
21+
border-style: solid;
22+
border-radius: var(--ui__input__roundness);
23+
box-shadow: var(--ui__input__shadow);
24+
transition-property: border-color;
25+
transition-duration: var(--transition--duration);
26+
transition-timing-function: var(--transition--easing);
27+
28+
& > input, & > select {
29+
line-height: 1;
30+
box-sizing: border-box;
31+
position: relative;
32+
font-family: inherit;
33+
font-size: inherit;
34+
width: 0;
35+
min-width: 100%;
36+
margin: 0;
37+
padding: var(--ui__input__spacing-y) var(--ui__input__spacing-x);
38+
color: var(--ui__input__text-color);
39+
background: transparent;
40+
border: none;
41+
42+
&::-webkit-input-placeholder {
43+
font-family: inherit;
44+
font-weight: inherit;
45+
font-size: 100%;
46+
color: var(--color__text-400);
47+
}
48+
49+
&:focus {
50+
outline-color: var(--color__current);
51+
}
52+
}
53+
54+
& > textarea, & > div[contenteditable] {
55+
flex: 1 1 auto;
56+
display: block;
57+
width: 0;
58+
min-height: 64px;
59+
margin: 0;
60+
padding: var(--ui__input__spacing-y) var(--ui__input__spacing-x);
61+
}
62+
63+
64+
& > textarea {
65+
resize: none;
66+
font-family: inherit;
67+
font-size: inherit;
68+
height: auto;
69+
max-height: 256px;
70+
color: inherit;
71+
background: none;
72+
border: none;
73+
74+
&::-webkit-input-placeholder {
75+
font-family: inherit;
76+
font-weight: inherit;
77+
font-size: 100%;
78+
color: var(--color__text-400);
79+
}
80+
81+
&:focus {
82+
outline-color: var(--color__current);
83+
}
84+
}
85+
86+
& > div[contenteditable] {
87+
&:focus {
88+
outline-color: var(--color__current);
89+
}
90+
91+
&:empty:before {
92+
content: attr(placeholder);
93+
font-family: inherit;
94+
font-weight: inherit;
95+
font-size: 100%;
96+
color: var(--color__text-400);
97+
}
98+
}
99+
100+
& > select {
101+
appearance: none;
102+
103+
& > option {
104+
font-size: 100%;
105+
color: var(--color__current);
106+
background: var(--ui__input__background);
107+
}
108+
}
109+
110+
& > label {
111+
font-size: 75%;
112+
position: absolute;
113+
top: -1rem;
114+
left: 1.25rem;
115+
}
116+
117+
& > .grip:has(+ textarea), & > textarea + .grip {
118+
&::before, &::after {
119+
content: "";
120+
display: block;
121+
position: absolute;
122+
right: 0;
123+
bottom: 0;
124+
width: 12px;
125+
height: 12px;
126+
background-color: var(--color__background);
127+
pointer-events: none;
128+
}
129+
130+
&::after {
131+
background-color: var(--ui__input__grip-color);
132+
mask: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyNCIgaGVpZ2h0PSIyNCIgdmlld0JveD0iMCAwIDI0IDI0IiBmaWxsPSJub25lIiBzdHJva2U9ImN1cnJlbnRDb2xvciIgc3Ryb2tlLXdpZHRoPSIyIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS1saW5lam9pbj0icm91bmQiIGNsYXNzPSJsdWNpZGUgbHVjaWRlLWdyaXAtaG9yaXpvbnRhbCI+PGNpcmNsZSBjeD0iMTIiIGN5PSI5IiByPSIxIi8+PGNpcmNsZSBjeD0iMTkiIGN5PSI5IiByPSIxIi8+PGNpcmNsZSBjeD0iNSIgY3k9IjkiIHI9IjEiLz48Y2lyY2xlIGN4PSIxMiIgY3k9IjE1IiByPSIxIi8+PGNpcmNsZSBjeD0iMTkiIGN5PSIxNSIgcj0iMSIvPjxjaXJjbGUgY3g9IjUiIGN5PSIxNSIgcj0iMSIvPjwvc3ZnPg==") no-repeat 50% 50%;
133+
mask-size: cover;
134+
}
135+
}
136+
137+
& > .grip + textarea, textarea:has(+.grip) {
138+
resize: vertical;
139+
}
140+
141+
&:has(> select)::before {
142+
content: "";
143+
display: block;
144+
position: absolute;
145+
right: var(--ui__input__spacing-x);
146+
bottom: 50%;
147+
width: 1em;
148+
height: 1em;
149+
background-color: var(--ui__input__grip-color);
150+
mask: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyNCIgaGVpZ2h0PSIyNCIgdmlld0JveD0iMCAwIDI0IDI0IiBmaWxsPSJub25lIiBzdHJva2U9ImN1cnJlbnRDb2xvciIgc3Ryb2tlLXdpZHRoPSIyIiBzdHJva2UtbGluZWNhcD0icm91bmQiIHN0cm9rZS1saW5lam9pbj0icm91bmQiIGNsYXNzPSJsdWNpZGUgbHVjaWRlLWNoZXZyb24tZG93biI+PHBhdGggZD0ibTYgOSA2IDYgNi02Ii8+PC9zdmc+") no-repeat 50% 50%;
151+
mask-size: cover;
152+
transition-property: transform, color;
153+
transition-duration: var(--transition--duration);
154+
transition-timing-function: var(--transition--easing);
155+
transform: translateY(50%) rotate(0);
156+
}
157+
158+
&:has(> select:focus)::before {
159+
transform: translateY(50%) rotate(180deg);
160+
}
161+
}

0 commit comments

Comments
 (0)