From 3bf9b65c06671b9a2c9a6715a18b2fced6a992e1 Mon Sep 17 00:00:00 2001
From: Steve Stein
Date: Sun, 27 Feb 2022 09:08:38 -0700
Subject: [PATCH] Tailwind package setup (#8003)
Co-authored-by: Thibaud Colas
---
.eslintrc.js | 1 +
.stylelintrc.js | 19 +
client/scss/core.scss | 14 +-
.../overrides/_utilities.text.legacy.scss | 3 -
client/scss/overrides/_utilities.text.scss | 11 -
client/src/tokens/typography.js | 4 +-
client/storybook/main.js | 2 +-
client/tailwind.config.js | 56 +++
client/webpack.config.js | 2 +-
docs/contributing/css_guidelines.rst | 8 +
package-lock.json | 436 +++++++++++++++++-
package.json | 5 +-
tailwind.config.js | 18 +
.../templates/wagtailstyleguide/base.html | 2 +-
.../templates/wagtailimages/images/edit.html | 2 +-
15 files changed, 541 insertions(+), 42 deletions(-)
delete mode 100644 client/scss/overrides/_utilities.text.legacy.scss
delete mode 100644 client/scss/overrides/_utilities.text.scss
create mode 100644 client/tailwind.config.js
create mode 100644 tailwind.config.js
diff --git a/.eslintrc.js b/.eslintrc.js
index 9908570400..c33df91dfd 100644
--- a/.eslintrc.js
+++ b/.eslintrc.js
@@ -97,6 +97,7 @@ module.exports = {
'*.test.tsx',
'*.test.js',
'webpack.config.js',
+ 'tailwind.config.js',
'*.stories.js',
'*.stories.tsx',
'storybook/**/*',
diff --git a/.stylelintrc.js b/.stylelintrc.js
index cb62a31c5d..8a80fe37f2 100644
--- a/.stylelintrc.js
+++ b/.stylelintrc.js
@@ -1,6 +1,25 @@
module.exports = {
extends: '@wagtail/stylelint-config-wagtail',
rules: {
+ 'scss/at-rule-no-unknown': [
+ true,
+ {
+ ignoreAtRules: [
+ 'tailwind',
+ 'apply',
+ 'variants',
+ 'responsive',
+ 'screen',
+ 'layer',
+ ],
+ },
+ ],
+ 'no-invalid-position-at-import-rule': [
+ true,
+ {
+ ignoreAtRules: ['tailwind', 'use'],
+ },
+ ],
// Would be valuable for strict BEM components but is too hard to enforce with legacy code.
'no-descending-specificity': null,
},
diff --git a/client/scss/core.scss b/client/scss/core.scss
index 5560c0c5d2..ad0d1dd78b 100644
--- a/client/scss/core.scss
+++ b/client/scss/core.scss
@@ -41,6 +41,15 @@ OTHER PREFIXES
==============================================================================*/
+/* TAILWIND BASE
+These inject Tailwind's base, component and utility styles and any styles registered by plugins of each layer.
+Unused styles created within tailwinds layers won't be compiled into the compiled stylesheet
+https://tailwindcss.com/docs/adding-custom-styles#using-css-and-layer
+*/
+
+@tailwind base;
+@tailwind components;
+
/* SETTINGS
These are variables, maps, and fonts.
* No CSS should be produced by these files
@@ -143,15 +152,16 @@ These are classes that provide overrides.
// UTILITIES: classes that do one simple thing.
@import 'overrides/utilities.hidden';
-@import 'overrides/utilities.text';
@import 'overrides/utilities.dropdowns';
@import 'overrides/utilities.focus';
@import 'overrides/utilities.visuallyhidden';
// Legacy utilities
-@import 'overrides/utilities.text.legacy';
@import 'overrides/utilities.legacy';
// PAGES: page-specific overrides
@import 'overrides/pages.homepage';
@import 'overrides/pages.page-explorer';
+
+// TAILWIND: This is at the bottom so it can take precedence over other css classes
+@tailwind utilities;
diff --git a/client/scss/overrides/_utilities.text.legacy.scss b/client/scss/overrides/_utilities.text.legacy.scss
deleted file mode 100644
index f03d0e6a12..0000000000
--- a/client/scss/overrides/_utilities.text.legacy.scss
+++ /dev/null
@@ -1,3 +0,0 @@
-.unbold {
- font-weight: normal;
-}
diff --git a/client/scss/overrides/_utilities.text.scss b/client/scss/overrides/_utilities.text.scss
deleted file mode 100644
index 52d2014a36..0000000000
--- a/client/scss/overrides/_utilities.text.scss
+++ /dev/null
@@ -1,11 +0,0 @@
-.u-text-transform-uppercase {
- text-transform: uppercase;
-}
-
-.u-text-weight-normal {
- font-weight: normal;
-}
-
-.u-para {
- margin-bottom: 1rem;
-}
diff --git a/client/src/tokens/typography.js b/client/src/tokens/typography.js
index ffdeb9fa2d..12ed06c604 100644
--- a/client/src/tokens/typography.js
+++ b/client/src/tokens/typography.js
@@ -18,7 +18,7 @@ const systemUIFontStack = [
const monoFontStack = ['monospace', 'serif'];
-const fontFamilies = {
+const fontFamily = {
sans: systemUIFontStack,
mono: monoFontStack,
};
@@ -72,7 +72,7 @@ const lineHeight = {
module.exports = {
systemUIFontStack,
monoFontStack,
- fontFamilies,
+ fontFamily,
fontSize,
fontWeight,
letterSpacing,
diff --git a/client/storybook/main.js b/client/storybook/main.js
index 0581bfed0d..354059fc9e 100644
--- a/client/storybook/main.js
+++ b/client/storybook/main.js
@@ -27,7 +27,7 @@ module.exports = {
loader: 'postcss-loader',
options: {
postcssOptions: {
- plugins: ['autoprefixer', 'cssnano'],
+ plugins: ['tailwindcss', 'autoprefixer', 'cssnano'],
},
},
},
diff --git a/client/tailwind.config.js b/client/tailwind.config.js
new file mode 100644
index 0000000000..d184d94928
--- /dev/null
+++ b/client/tailwind.config.js
@@ -0,0 +1,56 @@
+const colors = require('./src/tokens/colors');
+const {
+ fontFamily,
+ fontSize,
+ fontWeight,
+ letterSpacing,
+ lineHeight,
+} = require('./src/tokens/typography');
+const { breakpoints } = require('./src/tokens/breakpoints');
+const {
+ borderRadius,
+ borderWidth,
+ boxShadow,
+} = require('./src/tokens/objectStyles');
+const { spacing } = require('./src/tokens/spacing');
+
+const themeColors = Object.fromEntries(
+ Object.entries(colors).map(([key, hues]) => {
+ const shades = Object.fromEntries(
+ Object.entries(hues).map(([k, shade]) => [k, shade.hex]),
+ );
+ return [key, shades];
+ }),
+);
+
+/**
+ * Root Tailwind config, reusable for other projects.
+ */
+module.exports = {
+ prefix: 'w-',
+ theme: {
+ screens: {
+ ...breakpoints,
+ },
+ colors: {
+ ...themeColors,
+ inherit: 'inherit',
+ current: 'currentColor',
+ transparent: 'transparent',
+ },
+ fontFamily,
+ fontSize,
+ fontWeight,
+ lineHeight,
+ letterSpacing,
+ borderRadius,
+ borderWidth,
+ boxShadow: {
+ ...boxShadow,
+ none: 'none',
+ },
+ spacing,
+ },
+ plugins: [],
+ corePlugins: {},
+};
diff --git a/client/webpack.config.js b/client/webpack.config.js
index 18a9bc9438..baf34b0c23 100644
--- a/client/webpack.config.js
+++ b/client/webpack.config.js
@@ -407,7 +407,7 @@ module.exports = function exports(env, argv) {
loader: 'postcss-loader',
options: {
postcssOptions: {
- plugins: ['autoprefixer', 'cssnano'],
+ plugins: ['tailwindcss', 'autoprefixer', 'cssnano'],
},
},
},
diff --git a/docs/contributing/css_guidelines.rst b/docs/contributing/css_guidelines.rst
index 124a3d1443..5293781c01 100644
--- a/docs/contributing/css_guidelines.rst
+++ b/docs/contributing/css_guidelines.rst
@@ -11,6 +11,14 @@ and `Prettier `_ for formatting.
You'll need Node.js and npm on your development machine.
Ensure project dependencies are installed by running ``npm install --no-save``
+Tailwind CSS
+-------------
+
+Wagtail uses utility classes via `Tailwind `_, generated based on values set in the ``tailwind.config.js`` file.
+
+To use these utilities you will need to prefix your class names with ``w-`` to avoid interfering with other predefined styles of similar names.
+
+
Linting code
------------
diff --git a/package-lock.json b/package-lock.json
index d095b437d8..73cea87e50 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -40,7 +40,7 @@
"@typescript-eslint/parser": "^5.8.0",
"@wagtail/eslint-config-wagtail": "^0.4.0",
"@wagtail/stylelint-config-wagtail": "^0.3.2",
- "autoprefixer": "^10.4.0",
+ "autoprefixer": "^10.4.2",
"babel-loader": "^8.2.3",
"copy-webpack-plugin": "^10.2.0",
"css-loader": "^6.5.1",
@@ -52,7 +52,7 @@
"expose-loader": "^3.1.0",
"jest": "^26.6.3",
"mini-css-extract-plugin": "^2.4.5",
- "postcss": "^8.4.5",
+ "postcss": "^8.4.7",
"postcss-loader": "^6.2.1",
"prettier": "^2.5.1",
"react-axe": "^3.5.4",
@@ -62,6 +62,7 @@
"sass-loader": "^12.4.0",
"storybook-django": "^0.3.0",
"stylelint": "^14.2.0",
+ "tailwindcss": "^3.0.23",
"ts-jest": "^26.5.6",
"ts-loader": "^9.2.6",
"typescript": "^4.5.4",
@@ -10513,6 +10514,29 @@
"acorn": "^6.0.0 || ^7.0.0 || ^8.0.0"
}
},
+ "node_modules/acorn-node": {
+ "version": "1.8.2",
+ "resolved": "https://registry.npmjs.org/acorn-node/-/acorn-node-1.8.2.tgz",
+ "integrity": "sha512-8mt+fslDufLYntIoPAaIMUe/lrbrehIiwmR3t2k9LljIzoigEPF27eLk2hy8zSGzmR/ogr7zbRKINMo1u0yh5A==",
+ "dev": true,
+ "dependencies": {
+ "acorn": "^7.0.0",
+ "acorn-walk": "^7.0.0",
+ "xtend": "^4.0.2"
+ }
+ },
+ "node_modules/acorn-node/node_modules/acorn": {
+ "version": "7.4.1",
+ "resolved": "https://registry.npmjs.org/acorn/-/acorn-7.4.1.tgz",
+ "integrity": "sha512-nQyp0o1/mNdbTO1PO6kHkwSrmgZ0MT/jCCpNiwbUjGoRN4dlBhqJtoQuCnEOKzgTVwg0ZWiCoQy6SxMebQVh8A==",
+ "dev": true,
+ "bin": {
+ "acorn": "bin/acorn"
+ },
+ "engines": {
+ "node": ">=0.4.0"
+ }
+ },
"node_modules/acorn-walk": {
"version": "7.2.0",
"resolved": "https://registry.npmjs.org/acorn-walk/-/acorn-walk-7.2.0.tgz",
@@ -10829,6 +10853,12 @@
"node": ">=10"
}
},
+ "node_modules/arg": {
+ "version": "5.0.1",
+ "resolved": "https://registry.npmjs.org/arg/-/arg-5.0.1.tgz",
+ "integrity": "sha512-e0hDa9H2Z9AwFkk2qDlwhoMYE4eToKarchkQHovNdLTCYMHZHeRjI71crOh+dio4K6u1IcwubQqo79Ga4CyAQA==",
+ "dev": true
+ },
"node_modules/argparse": {
"version": "2.0.1",
"resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz",
@@ -14257,6 +14287,12 @@
"node": ">=0.10.0"
}
},
+ "node_modules/defined": {
+ "version": "1.0.0",
+ "resolved": "https://registry.npmjs.org/defined/-/defined-1.0.0.tgz",
+ "integrity": "sha1-yY2bzvdWdBiOEQlpFRGZ45sfppM=",
+ "dev": true
+ },
"node_modules/delayed-stream": {
"version": "1.0.0",
"resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz",
@@ -14351,6 +14387,29 @@
"integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=",
"dev": true
},
+ "node_modules/detective": {
+ "version": "5.2.0",
+ "resolved": "https://registry.npmjs.org/detective/-/detective-5.2.0.tgz",
+ "integrity": "sha512-6SsIx+nUUbuK0EthKjv0zrdnajCCXVYGmbYYiYjFVpzcjwEs/JMDZ8tPRG29J/HhN56t3GJp2cGSWDRjjot8Pg==",
+ "dev": true,
+ "dependencies": {
+ "acorn-node": "^1.6.1",
+ "defined": "^1.0.0",
+ "minimist": "^1.1.1"
+ },
+ "bin": {
+ "detective": "bin/detective.js"
+ },
+ "engines": {
+ "node": ">=0.8.0"
+ }
+ },
+ "node_modules/didyoumean": {
+ "version": "1.2.2",
+ "resolved": "https://registry.npmjs.org/didyoumean/-/didyoumean-1.2.2.tgz",
+ "integrity": "sha512-gxtyfqMg7GKyhQmb056K7M3xszy/myH8w+B4RT+QXBQsvAOdc3XymqDDPHx1BgPgsdAA5SIifona89YtRATDzw==",
+ "dev": true
+ },
"node_modules/diff-sequences": {
"version": "26.6.2",
"resolved": "https://registry.npmjs.org/diff-sequences/-/diff-sequences-26.6.2.tgz",
@@ -14395,6 +14454,12 @@
"integrity": "sha1-44Mx8IRLukm5qctxx3FYWqsbxlo=",
"dev": true
},
+ "node_modules/dlv": {
+ "version": "1.1.3",
+ "resolved": "https://registry.npmjs.org/dlv/-/dlv-1.1.3.tgz",
+ "integrity": "sha512-+HlytyjlPKnIG8XuRG8WvmBP8xs8P71y+SKKS6ZXWoEgLuePxtDoUEiH7WkdePWrQ5JBpE6aoVqfZfJUQkjXwA==",
+ "dev": true
+ },
"node_modules/doctrine": {
"version": "3.0.0",
"resolved": "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz",
@@ -21590,9 +21655,9 @@
"optional": true
},
"node_modules/nanoid": {
- "version": "3.2.0",
- "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.2.0.tgz",
- "integrity": "sha512-fmsZYa9lpn69Ad5eDn7FMcnnSR+8R34W9qJEijxYhTbfOWzr22n1QxCMzXLK+ODyW2973V3Fux959iQoUxzUIA==",
+ "version": "3.3.1",
+ "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.1.tgz",
+ "integrity": "sha512-n6Vs/3KGyxPQd6uO0eH4Bv0ojGSUvuLlIHtC3Y0kEO23YRge8H9x1GCzLn28YX0H66pMkxuaeESFq4tKISKwdw==",
"dev": true,
"bin": {
"nanoid": "bin/nanoid.cjs"
@@ -22068,6 +22133,15 @@
"node": ">=0.10.0"
}
},
+ "node_modules/object-hash": {
+ "version": "2.2.0",
+ "resolved": "https://registry.npmjs.org/object-hash/-/object-hash-2.2.0.tgz",
+ "integrity": "sha512-gScRMn0bS5fH+IuwyIFgnh9zBdo4DV+6GhygmWM9HyNJSgS0hScp1f5vjtm7oIIOiT9trXrShAkLFSc2IqKNgw==",
+ "dev": true,
+ "engines": {
+ "node": ">= 6"
+ }
+ },
"node_modules/object-inspect": {
"version": "1.12.0",
"resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.12.0.tgz",
@@ -22794,14 +22868,14 @@
}
},
"node_modules/postcss": {
- "version": "8.4.5",
- "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.4.5.tgz",
- "integrity": "sha512-jBDboWM8qpaqwkMwItqTQTiFikhs/67OYVvblFFTM7MrZjt6yMKd6r2kgXizEbTTljacm4NldIlZnhbjr84QYg==",
+ "version": "8.4.7",
+ "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.4.7.tgz",
+ "integrity": "sha512-L9Ye3r6hkkCeOETQX6iOaWZgjp3LL6Lpqm6EtgbKrgqGGteRMNb9vzBfRL96YOSu8o7x3MfIH9Mo5cPJFGrW6A==",
"dev": true,
"dependencies": {
- "nanoid": "^3.1.30",
+ "nanoid": "^3.3.1",
"picocolors": "^1.0.0",
- "source-map-js": "^1.0.1"
+ "source-map-js": "^1.0.2"
},
"engines": {
"node": "^10 || ^12 || >=14"
@@ -22933,6 +23007,50 @@
"node": ">=0.10.0"
}
},
+ "node_modules/postcss-js": {
+ "version": "4.0.0",
+ "resolved": "https://registry.npmjs.org/postcss-js/-/postcss-js-4.0.0.tgz",
+ "integrity": "sha512-77QESFBwgX4irogGVPgQ5s07vLvFqWr228qZY+w6lW599cRlK/HmnlivnnVUxkjHnCu4J16PDMHcH+e+2HbvTQ==",
+ "dev": true,
+ "dependencies": {
+ "camelcase-css": "^2.0.1"
+ },
+ "engines": {
+ "node": "^12 || ^14 || >= 16"
+ },
+ "funding": {
+ "type": "opencollective",
+ "url": "https://opencollective.com/postcss/"
+ },
+ "peerDependencies": {
+ "postcss": "^8.3.3"
+ }
+ },
+ "node_modules/postcss-load-config": {
+ "version": "3.1.3",
+ "resolved": "https://registry.npmjs.org/postcss-load-config/-/postcss-load-config-3.1.3.tgz",
+ "integrity": "sha512-5EYgaM9auHGtO//ljHH+v/aC/TQ5LHXtL7bQajNAUBKUVKiYE8rYpFms7+V26D9FncaGe2zwCoPQsFKb5zF/Hw==",
+ "dev": true,
+ "dependencies": {
+ "lilconfig": "^2.0.4",
+ "yaml": "^1.10.2"
+ },
+ "engines": {
+ "node": ">= 10"
+ },
+ "funding": {
+ "type": "opencollective",
+ "url": "https://opencollective.com/postcss/"
+ },
+ "peerDependencies": {
+ "ts-node": ">=9.0.0"
+ },
+ "peerDependenciesMeta": {
+ "ts-node": {
+ "optional": true
+ }
+ }
+ },
"node_modules/postcss-loader": {
"version": "6.2.1",
"resolved": "https://registry.npmjs.org/postcss-loader/-/postcss-loader-6.2.1.tgz",
@@ -23133,6 +23251,25 @@
"postcss": "^8.1.0"
}
},
+ "node_modules/postcss-nested": {
+ "version": "5.0.6",
+ "resolved": "https://registry.npmjs.org/postcss-nested/-/postcss-nested-5.0.6.tgz",
+ "integrity": "sha512-rKqm2Fk0KbA8Vt3AdGN0FB9OBOMDVajMG6ZCf/GoHgdxUJ4sBFp0A/uMIRm+MJUdo33YXEtjqIz8u7DAp8B7DA==",
+ "dev": true,
+ "dependencies": {
+ "postcss-selector-parser": "^6.0.6"
+ },
+ "engines": {
+ "node": ">=12.0"
+ },
+ "funding": {
+ "type": "opencollective",
+ "url": "https://opencollective.com/postcss/"
+ },
+ "peerDependencies": {
+ "postcss": "^8.2.14"
+ }
+ },
"node_modules/postcss-normalize-charset": {
"version": "5.0.2",
"resolved": "https://registry.npmjs.org/postcss-normalize-charset/-/postcss-normalize-charset-5.0.2.tgz",
@@ -26876,6 +27013,110 @@
"integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==",
"dev": true
},
+ "node_modules/tailwindcss": {
+ "version": "3.0.23",
+ "resolved": "https://registry.npmjs.org/tailwindcss/-/tailwindcss-3.0.23.tgz",
+ "integrity": "sha512-+OZOV9ubyQ6oI2BXEhzw4HrqvgcARY38xv3zKcjnWtMIZstEsXdI9xftd1iB7+RbOnj2HOEzkA0OyB5BaSxPQA==",
+ "dev": true,
+ "dependencies": {
+ "arg": "^5.0.1",
+ "chalk": "^4.1.2",
+ "chokidar": "^3.5.3",
+ "color-name": "^1.1.4",
+ "cosmiconfig": "^7.0.1",
+ "detective": "^5.2.0",
+ "didyoumean": "^1.2.2",
+ "dlv": "^1.1.3",
+ "fast-glob": "^3.2.11",
+ "glob-parent": "^6.0.2",
+ "is-glob": "^4.0.3",
+ "normalize-path": "^3.0.0",
+ "object-hash": "^2.2.0",
+ "postcss": "^8.4.6",
+ "postcss-js": "^4.0.0",
+ "postcss-load-config": "^3.1.0",
+ "postcss-nested": "5.0.6",
+ "postcss-selector-parser": "^6.0.9",
+ "postcss-value-parser": "^4.2.0",
+ "quick-lru": "^5.1.1",
+ "resolve": "^1.22.0"
+ },
+ "bin": {
+ "tailwind": "lib/cli.js",
+ "tailwindcss": "lib/cli.js"
+ },
+ "engines": {
+ "node": ">=12.13.0"
+ },
+ "peerDependencies": {
+ "autoprefixer": "^10.0.2",
+ "postcss": "^8.0.9"
+ }
+ },
+ "node_modules/tailwindcss/node_modules/ansi-styles": {
+ "version": "4.3.0",
+ "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz",
+ "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==",
+ "dev": true,
+ "dependencies": {
+ "color-convert": "^2.0.1"
+ },
+ "engines": {
+ "node": ">=8"
+ },
+ "funding": {
+ "url": "https://github.com/chalk/ansi-styles?sponsor=1"
+ }
+ },
+ "node_modules/tailwindcss/node_modules/chalk": {
+ "version": "4.1.2",
+ "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz",
+ "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==",
+ "dev": true,
+ "dependencies": {
+ "ansi-styles": "^4.1.0",
+ "supports-color": "^7.1.0"
+ },
+ "engines": {
+ "node": ">=10"
+ },
+ "funding": {
+ "url": "https://github.com/chalk/chalk?sponsor=1"
+ }
+ },
+ "node_modules/tailwindcss/node_modules/has-flag": {
+ "version": "4.0.0",
+ "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz",
+ "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==",
+ "dev": true,
+ "engines": {
+ "node": ">=8"
+ }
+ },
+ "node_modules/tailwindcss/node_modules/quick-lru": {
+ "version": "5.1.1",
+ "resolved": "https://registry.npmjs.org/quick-lru/-/quick-lru-5.1.1.tgz",
+ "integrity": "sha512-WuyALRjWPDGtt/wzJiadO5AXY+8hZ80hVpe6MyivgraREW751X3SbhRvG3eLKOYN+8VEvqLcf3wdnt44Z4S4SA==",
+ "dev": true,
+ "engines": {
+ "node": ">=10"
+ },
+ "funding": {
+ "url": "https://github.com/sponsors/sindresorhus"
+ }
+ },
+ "node_modules/tailwindcss/node_modules/supports-color": {
+ "version": "7.2.0",
+ "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz",
+ "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==",
+ "dev": true,
+ "dependencies": {
+ "has-flag": "^4.0.0"
+ },
+ "engines": {
+ "node": ">=8"
+ }
+ },
"node_modules/tapable": {
"version": "1.1.3",
"resolved": "https://registry.npmjs.org/tapable/-/tapable-1.1.3.tgz",
@@ -37396,6 +37637,25 @@
"dev": true,
"requires": {}
},
+ "acorn-node": {
+ "version": "1.8.2",
+ "resolved": "https://registry.npmjs.org/acorn-node/-/acorn-node-1.8.2.tgz",
+ "integrity": "sha512-8mt+fslDufLYntIoPAaIMUe/lrbrehIiwmR3t2k9LljIzoigEPF27eLk2hy8zSGzmR/ogr7zbRKINMo1u0yh5A==",
+ "dev": true,
+ "requires": {
+ "acorn": "^7.0.0",
+ "acorn-walk": "^7.0.0",
+ "xtend": "^4.0.2"
+ },
+ "dependencies": {
+ "acorn": {
+ "version": "7.4.1",
+ "resolved": "https://registry.npmjs.org/acorn/-/acorn-7.4.1.tgz",
+ "integrity": "sha512-nQyp0o1/mNdbTO1PO6kHkwSrmgZ0MT/jCCpNiwbUjGoRN4dlBhqJtoQuCnEOKzgTVwg0ZWiCoQy6SxMebQVh8A==",
+ "dev": true
+ }
+ }
+ },
"acorn-walk": {
"version": "7.2.0",
"resolved": "https://registry.npmjs.org/acorn-walk/-/acorn-walk-7.2.0.tgz",
@@ -37643,6 +37903,12 @@
"readable-stream": "^3.6.0"
}
},
+ "arg": {
+ "version": "5.0.1",
+ "resolved": "https://registry.npmjs.org/arg/-/arg-5.0.1.tgz",
+ "integrity": "sha512-e0hDa9H2Z9AwFkk2qDlwhoMYE4eToKarchkQHovNdLTCYMHZHeRjI71crOh+dio4K6u1IcwubQqo79Ga4CyAQA==",
+ "dev": true
+ },
"argparse": {
"version": "2.0.1",
"resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz",
@@ -40343,6 +40609,12 @@
"isobject": "^3.0.1"
}
},
+ "defined": {
+ "version": "1.0.0",
+ "resolved": "https://registry.npmjs.org/defined/-/defined-1.0.0.tgz",
+ "integrity": "sha1-yY2bzvdWdBiOEQlpFRGZ45sfppM=",
+ "dev": true
+ },
"delayed-stream": {
"version": "1.0.0",
"resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz",
@@ -40419,6 +40691,23 @@
}
}
},
+ "detective": {
+ "version": "5.2.0",
+ "resolved": "https://registry.npmjs.org/detective/-/detective-5.2.0.tgz",
+ "integrity": "sha512-6SsIx+nUUbuK0EthKjv0zrdnajCCXVYGmbYYiYjFVpzcjwEs/JMDZ8tPRG29J/HhN56t3GJp2cGSWDRjjot8Pg==",
+ "dev": true,
+ "requires": {
+ "acorn-node": "^1.6.1",
+ "defined": "^1.0.0",
+ "minimist": "^1.1.1"
+ }
+ },
+ "didyoumean": {
+ "version": "1.2.2",
+ "resolved": "https://registry.npmjs.org/didyoumean/-/didyoumean-1.2.2.tgz",
+ "integrity": "sha512-gxtyfqMg7GKyhQmb056K7M3xszy/myH8w+B4RT+QXBQsvAOdc3XymqDDPHx1BgPgsdAA5SIifona89YtRATDzw==",
+ "dev": true
+ },
"diff-sequences": {
"version": "26.6.2",
"resolved": "https://registry.npmjs.org/diff-sequences/-/diff-sequences-26.6.2.tgz",
@@ -40459,6 +40748,12 @@
"integrity": "sha1-44Mx8IRLukm5qctxx3FYWqsbxlo=",
"dev": true
},
+ "dlv": {
+ "version": "1.1.3",
+ "resolved": "https://registry.npmjs.org/dlv/-/dlv-1.1.3.tgz",
+ "integrity": "sha512-+HlytyjlPKnIG8XuRG8WvmBP8xs8P71y+SKKS6ZXWoEgLuePxtDoUEiH7WkdePWrQ5JBpE6aoVqfZfJUQkjXwA==",
+ "dev": true
+ },
"doctrine": {
"version": "3.0.0",
"resolved": "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz",
@@ -45947,9 +46242,9 @@
"optional": true
},
"nanoid": {
- "version": "3.2.0",
- "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.2.0.tgz",
- "integrity": "sha512-fmsZYa9lpn69Ad5eDn7FMcnnSR+8R34W9qJEijxYhTbfOWzr22n1QxCMzXLK+ODyW2973V3Fux959iQoUxzUIA==",
+ "version": "3.3.1",
+ "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.1.tgz",
+ "integrity": "sha512-n6Vs/3KGyxPQd6uO0eH4Bv0ojGSUvuLlIHtC3Y0kEO23YRge8H9x1GCzLn28YX0H66pMkxuaeESFq4tKISKwdw==",
"dev": true
},
"nanomatch": {
@@ -46352,6 +46647,12 @@
}
}
},
+ "object-hash": {
+ "version": "2.2.0",
+ "resolved": "https://registry.npmjs.org/object-hash/-/object-hash-2.2.0.tgz",
+ "integrity": "sha512-gScRMn0bS5fH+IuwyIFgnh9zBdo4DV+6GhygmWM9HyNJSgS0hScp1f5vjtm7oIIOiT9trXrShAkLFSc2IqKNgw==",
+ "dev": true
+ },
"object-inspect": {
"version": "1.12.0",
"resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.12.0.tgz",
@@ -46906,14 +47207,14 @@
"dev": true
},
"postcss": {
- "version": "8.4.5",
- "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.4.5.tgz",
- "integrity": "sha512-jBDboWM8qpaqwkMwItqTQTiFikhs/67OYVvblFFTM7MrZjt6yMKd6r2kgXizEbTTljacm4NldIlZnhbjr84QYg==",
+ "version": "8.4.7",
+ "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.4.7.tgz",
+ "integrity": "sha512-L9Ye3r6hkkCeOETQX6iOaWZgjp3LL6Lpqm6EtgbKrgqGGteRMNb9vzBfRL96YOSu8o7x3MfIH9Mo5cPJFGrW6A==",
"dev": true,
"requires": {
- "nanoid": "^3.1.30",
+ "nanoid": "^3.3.1",
"picocolors": "^1.0.0",
- "source-map-js": "^1.0.1"
+ "source-map-js": "^1.0.2"
}
},
"postcss-colormin": {
@@ -46998,6 +47299,25 @@
}
}
},
+ "postcss-js": {
+ "version": "4.0.0",
+ "resolved": "https://registry.npmjs.org/postcss-js/-/postcss-js-4.0.0.tgz",
+ "integrity": "sha512-77QESFBwgX4irogGVPgQ5s07vLvFqWr228qZY+w6lW599cRlK/HmnlivnnVUxkjHnCu4J16PDMHcH+e+2HbvTQ==",
+ "dev": true,
+ "requires": {
+ "camelcase-css": "^2.0.1"
+ }
+ },
+ "postcss-load-config": {
+ "version": "3.1.3",
+ "resolved": "https://registry.npmjs.org/postcss-load-config/-/postcss-load-config-3.1.3.tgz",
+ "integrity": "sha512-5EYgaM9auHGtO//ljHH+v/aC/TQ5LHXtL7bQajNAUBKUVKiYE8rYpFms7+V26D9FncaGe2zwCoPQsFKb5zF/Hw==",
+ "dev": true,
+ "requires": {
+ "lilconfig": "^2.0.4",
+ "yaml": "^1.10.2"
+ }
+ },
"postcss-loader": {
"version": "6.2.1",
"resolved": "https://registry.npmjs.org/postcss-loader/-/postcss-loader-6.2.1.tgz",
@@ -47124,6 +47444,15 @@
"icss-utils": "^5.0.0"
}
},
+ "postcss-nested": {
+ "version": "5.0.6",
+ "resolved": "https://registry.npmjs.org/postcss-nested/-/postcss-nested-5.0.6.tgz",
+ "integrity": "sha512-rKqm2Fk0KbA8Vt3AdGN0FB9OBOMDVajMG6ZCf/GoHgdxUJ4sBFp0A/uMIRm+MJUdo33YXEtjqIz8u7DAp8B7DA==",
+ "dev": true,
+ "requires": {
+ "postcss-selector-parser": "^6.0.6"
+ }
+ },
"postcss-normalize-charset": {
"version": "5.0.2",
"resolved": "https://registry.npmjs.org/postcss-normalize-charset/-/postcss-normalize-charset-5.0.2.tgz",
@@ -50055,6 +50384,77 @@
}
}
},
+ "tailwindcss": {
+ "version": "3.0.23",
+ "resolved": "https://registry.npmjs.org/tailwindcss/-/tailwindcss-3.0.23.tgz",
+ "integrity": "sha512-+OZOV9ubyQ6oI2BXEhzw4HrqvgcARY38xv3zKcjnWtMIZstEsXdI9xftd1iB7+RbOnj2HOEzkA0OyB5BaSxPQA==",
+ "dev": true,
+ "requires": {
+ "arg": "^5.0.1",
+ "chalk": "^4.1.2",
+ "chokidar": "^3.5.3",
+ "color-name": "^1.1.4",
+ "cosmiconfig": "^7.0.1",
+ "detective": "^5.2.0",
+ "didyoumean": "^1.2.2",
+ "dlv": "^1.1.3",
+ "fast-glob": "^3.2.11",
+ "glob-parent": "^6.0.2",
+ "is-glob": "^4.0.3",
+ "normalize-path": "^3.0.0",
+ "object-hash": "^2.2.0",
+ "postcss": "^8.4.6",
+ "postcss-js": "^4.0.0",
+ "postcss-load-config": "^3.1.0",
+ "postcss-nested": "5.0.6",
+ "postcss-selector-parser": "^6.0.9",
+ "postcss-value-parser": "^4.2.0",
+ "quick-lru": "^5.1.1",
+ "resolve": "^1.22.0"
+ },
+ "dependencies": {
+ "ansi-styles": {
+ "version": "4.3.0",
+ "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz",
+ "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==",
+ "dev": true,
+ "requires": {
+ "color-convert": "^2.0.1"
+ }
+ },
+ "chalk": {
+ "version": "4.1.2",
+ "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz",
+ "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==",
+ "dev": true,
+ "requires": {
+ "ansi-styles": "^4.1.0",
+ "supports-color": "^7.1.0"
+ }
+ },
+ "has-flag": {
+ "version": "4.0.0",
+ "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz",
+ "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==",
+ "dev": true
+ },
+ "quick-lru": {
+ "version": "5.1.1",
+ "resolved": "https://registry.npmjs.org/quick-lru/-/quick-lru-5.1.1.tgz",
+ "integrity": "sha512-WuyALRjWPDGtt/wzJiadO5AXY+8hZ80hVpe6MyivgraREW751X3SbhRvG3eLKOYN+8VEvqLcf3wdnt44Z4S4SA==",
+ "dev": true
+ },
+ "supports-color": {
+ "version": "7.2.0",
+ "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz",
+ "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==",
+ "dev": true,
+ "requires": {
+ "has-flag": "^4.0.0"
+ }
+ }
+ }
+ },
"tapable": {
"version": "1.1.3",
"resolved": "https://registry.npmjs.org/tapable/-/tapable-1.1.3.tgz",
diff --git a/package.json b/package.json
index c624cd8769..97c8be1714 100644
--- a/package.json
+++ b/package.json
@@ -63,7 +63,7 @@
"@typescript-eslint/parser": "^5.8.0",
"@wagtail/eslint-config-wagtail": "^0.4.0",
"@wagtail/stylelint-config-wagtail": "^0.3.2",
- "autoprefixer": "^10.4.0",
+ "autoprefixer": "^10.4.2",
"babel-loader": "^8.2.3",
"copy-webpack-plugin": "^10.2.0",
"css-loader": "^6.5.1",
@@ -75,7 +75,7 @@
"expose-loader": "^3.1.0",
"jest": "^26.6.3",
"mini-css-extract-plugin": "^2.4.5",
- "postcss": "^8.4.5",
+ "postcss": "^8.4.7",
"postcss-loader": "^6.2.1",
"prettier": "^2.5.1",
"react-axe": "^3.5.4",
@@ -85,6 +85,7 @@
"sass-loader": "^12.4.0",
"storybook-django": "^0.3.0",
"stylelint": "^14.2.0",
+ "tailwindcss": "^3.0.23",
"ts-jest": "^26.5.6",
"ts-loader": "^9.2.6",
"typescript": "^4.5.4",
diff --git a/tailwind.config.js b/tailwind.config.js
new file mode 100644
index 0000000000..ce93c9d105
--- /dev/null
+++ b/tailwind.config.js
@@ -0,0 +1,18 @@
+const baseConfig = require('./client/tailwind.config');
+
+/**
+ * Tailwind config file for Wagtail itself.
+ */
+module.exports = {
+ presets: [baseConfig],
+ content: [
+ './wagtail/**/*.{py,html,ts,tsx}',
+ './wagtail/**/static_src/**/*.js',
+ './client/**/*.{js,ts,tsx}',
+ './docs/**/*.{md,rst}',
+ ],
+ corePlugins: {
+ // Risk of clashing with existing styles.
+ preflight: false,
+ },
+};
diff --git a/wagtail/contrib/styleguide/templates/wagtailstyleguide/base.html b/wagtail/contrib/styleguide/templates/wagtailstyleguide/base.html
index cc2ec17b67..8eb8c7bf59 100644
--- a/wagtail/contrib/styleguide/templates/wagtailstyleguide/base.html
+++ b/wagtail/contrib/styleguide/templates/wagtailstyleguide/base.html
@@ -585,7 +585,7 @@
Inline dropdown components, primarily used in the listing.
-