Skip to content

Commit b0b3662

Browse files
authored
Add container query support (#807)
1 parent 46276ac commit b0b3662

File tree

18 files changed

+456
-33
lines changed

18 files changed

+456
-33
lines changed

.changeset/rare-numbers-pull.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
'@vanilla-extract/babel-plugin': minor
3+
---
4+
5+
Add support for the new `createContainer` API

.changeset/real-cherries-give.md

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
---
2+
'@vanilla-extract/css': minor
3+
---
4+
5+
Add `createContainer` API
6+
7+
`createContainer` creates a single scoped container name for use with CSS Container Queries. This avoids potential naming collisions with other containers.
8+
9+
```ts
10+
import {
11+
style,
12+
createContainer
13+
} from '@vanilla-extract/css';
14+
15+
export const sidebarContainer = createContainer();
16+
17+
export const sidebar = style({
18+
containerName: sidebarContainer
19+
});
20+
21+
export const navigation = style({
22+
'@container': {
23+
[`${sidebarContainer} (min-width: 400px)`]: {
24+
display: 'flex'
25+
}
26+
}
27+
});
28+
```

.changeset/tiny-shirts-poke.md

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
---
2+
'@vanilla-extract/css': minor
3+
---
4+
5+
Add support for container queries via the new `@container` key.
6+
7+
```ts
8+
import { style } from '@vanilla-extract/css';
9+
10+
export const myStyle = style({
11+
'@container': {
12+
'(min-width: 400px)': {
13+
display: 'flex'
14+
}
15+
}
16+
});
17+
```

fixtures/low-level/src/index.ts

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,10 @@
1-
import { block } from './styles.css';
1+
import { block, container } from './styles.css';
22
import testNodes from '../test-nodes.json';
33

44
document.body.innerHTML = `
5+
<div class="${container}">
56
<div id="${testNodes.block}" class="${block}">
67
I'm a block
78
</div>
9+
</div>
810
`;
Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,28 @@
1-
import { style, createVar } from '@vanilla-extract/css';
1+
import { style, createVar, createContainer } from '@vanilla-extract/css';
22

33
const color = createVar();
44

5+
const myContainer = createContainer('my-container');
6+
7+
export const container = style({
8+
containerType: 'size',
9+
containerName: myContainer,
10+
width: 500,
11+
});
12+
513
export const block = style({
614
vars: {
715
[color]: 'blue',
816
},
917
backgroundColor: color,
10-
color: 'white',
1118
padding: 20,
19+
'@media': {
20+
'screen and (min-width: 200px)': {
21+
'@container': {
22+
[`${myContainer} (min-width: 400px)`]: {
23+
color: 'white',
24+
},
25+
},
26+
},
27+
},
1228
});

packages/babel-plugin/src/index.test.ts

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -269,6 +269,25 @@ describe('babel plugin', () => {
269269
`);
270270
});
271271

272+
it('should handle createContainer assigned to const', () => {
273+
const source = `
274+
import { createContainer } from '@vanilla-extract/css';
275+
276+
const myContainer = createContainer();
277+
`;
278+
279+
expect(transform(source)).toMatchInlineSnapshot(`
280+
"import * as __vanilla_filescope__ from '@vanilla-extract/css/fileScope';
281+
282+
__vanilla_filescope__.setFileScope(\\"src/dir/mockFilename.css.ts\\", \\"@vanilla-extract/babel-plugin\\");
283+
284+
import { createContainer } from '@vanilla-extract/css';
285+
const myContainer = createContainer(\\"myContainer\\");
286+
287+
__vanilla_filescope__.endFileScope();"
288+
`);
289+
});
290+
272291
it('should handle fontFace assigned to const', () => {
273292
const source = `
274293
import { fontFace } from '@vanilla-extract/css';

packages/babel-plugin/src/index.ts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,9 @@ const debuggableFunctionConfig = {
4343
recipe: {
4444
maxParams: 2,
4545
},
46+
createContainer: {
47+
maxParams: 1,
48+
},
4649
};
4750

4851
const styleFunctions = [

packages/css/src/container.ts

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
import { generateIdentifier } from './identifier';
2+
3+
// createContainer is used for local scoping of CSS containers
4+
// For now it is mostly just an alias of generateIdentifier
5+
export const createContainer = (debugId?: string) =>
6+
generateIdentifier(debugId);

packages/css/src/index.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,3 +12,4 @@ export * from './identifier';
1212
export * from './theme';
1313
export * from './style';
1414
export * from './vars';
15+
export { createContainer } from './container';

packages/css/src/transformCss.test.ts

Lines changed: 76 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -961,7 +961,41 @@ describe('transformCss', () => {
961961
`);
962962
});
963963

964-
it('should handle nested @supports and @media queries', () => {
964+
it('should handle @container queries', () => {
965+
expect(
966+
transformCss({
967+
composedClassLists: [],
968+
localClassNames: ['testClass'],
969+
cssObjs: [
970+
{
971+
type: 'local',
972+
selector: 'testClass',
973+
rule: {
974+
display: 'flex',
975+
containerName: 'sidebar',
976+
'@container': {
977+
'sidebar (min-width: 700px)': {
978+
display: 'grid',
979+
},
980+
},
981+
},
982+
},
983+
],
984+
}).join('\n'),
985+
).toMatchInlineSnapshot(`
986+
".testClass {
987+
display: flex;
988+
container-name: sidebar;
989+
}
990+
@container sidebar (min-width: 700px) {
991+
.testClass {
992+
display: grid;
993+
}
994+
}"
995+
`);
996+
});
997+
998+
it('should handle nested @supports, @media and @container queries', () => {
965999
expect(
9661000
transformCss({
9671001
composedClassLists: [],
@@ -978,16 +1012,27 @@ describe('transformCss', () => {
9781012
'@media': {
9791013
'screen and (min-width: 700px)': {
9801014
display: 'grid',
1015+
'@container': {
1016+
'sidebar (min-width: 700px)': {
1017+
display: 'grid',
1018+
},
1019+
},
9811020
},
9821021
},
9831022
},
9841023
},
1024+
9851025
'@media': {
9861026
'screen and (min-width: 700px)': {
9871027
color: 'green',
9881028
'@supports': {
9891029
'(display: grid)': {
9901030
borderColor: 'blue',
1031+
'@container': {
1032+
'sidebar (min-width: 700px)': {
1033+
display: 'grid',
1034+
},
1035+
},
9911036
},
9921037
},
9931038
},
@@ -1008,6 +1053,11 @@ describe('transformCss', () => {
10081053
.testClass {
10091054
border-color: blue;
10101055
}
1056+
@container sidebar (min-width: 700px) {
1057+
.testClass {
1058+
display: grid;
1059+
}
1060+
}
10111061
}
10121062
}
10131063
@supports (display: grid) {
@@ -1018,12 +1068,17 @@ describe('transformCss', () => {
10181068
.testClass {
10191069
display: grid;
10201070
}
1071+
@container sidebar (min-width: 700px) {
1072+
.testClass {
1073+
display: grid;
1074+
}
1075+
}
10211076
}
10221077
}"
10231078
`);
10241079
});
10251080

1026-
it('should merge nested @supports and @media queries', () => {
1081+
it('should merge nested @supports, @media and @container queries', () => {
10271082
expect(
10281083
transformCss({
10291084
composedClassLists: [],
@@ -1038,12 +1093,18 @@ describe('transformCss', () => {
10381093
'@supports': {
10391094
'(display: grid)': {
10401095
borderColor: 'blue',
1096+
'@container': {
1097+
'sidebar (min-width: 700px)': {
1098+
display: 'grid',
1099+
},
1100+
},
10411101
},
10421102
},
10431103
},
10441104
},
10451105
},
10461106
},
1107+
10471108
{
10481109
type: 'local',
10491110
selector: 'otherClass',
@@ -1053,6 +1114,11 @@ describe('transformCss', () => {
10531114
'@supports': {
10541115
'(display: grid)': {
10551116
backgroundColor: 'yellow',
1117+
'@container': {
1118+
'sidebar (min-width: 700px)': {
1119+
display: 'grid',
1120+
},
1121+
},
10561122
},
10571123
},
10581124
},
@@ -1070,6 +1136,14 @@ describe('transformCss', () => {
10701136
.otherClass {
10711137
background-color: yellow;
10721138
}
1139+
@container sidebar (min-width: 700px) {
1140+
.testClass {
1141+
display: grid;
1142+
}
1143+
.otherClass {
1144+
display: grid;
1145+
}
1146+
}
10731147
}
10741148
}"
10751149
`);

0 commit comments

Comments
 (0)