Rename buckets to layers, handle copying layer information to responsive variants
This commit is contained in:
parent
f25b0925a3
commit
b69e46cc1b
4 changed files with 96 additions and 39 deletions
|
|
@ -5,6 +5,40 @@ import chalk from 'chalk'
|
|||
import { log } from '../cli/utils'
|
||||
import * as emoji from '../cli/emoji'
|
||||
|
||||
function convertLayersToControlComments(css) {
|
||||
css.walkAtRules('layer', atRule => {
|
||||
const layer = atRule.params
|
||||
atRule.before(postcss.comment({ text: `tailwind start ${layer}` }))
|
||||
atRule.before(atRule.nodes)
|
||||
atRule.before(postcss.comment({ text: `tailwind end ${layer}` }))
|
||||
atRule.remove()
|
||||
})
|
||||
}
|
||||
|
||||
function convertControlCommentsToPurgeIgnoreComments(config) {
|
||||
return function(css) {
|
||||
const mode = _.get(config, 'purge.mode', 'conservative')
|
||||
|
||||
if (mode === 'conservative') {
|
||||
css.prepend(postcss.comment({ text: 'purgecss start ignore' }))
|
||||
css.append(postcss.comment({ text: 'purgecss end ignore' }))
|
||||
|
||||
css.walkComments(comment => {
|
||||
switch (comment.text.trim()) {
|
||||
case 'tailwind start utilities':
|
||||
comment.text = 'purgecss end ignore'
|
||||
break
|
||||
case 'tailwind end utilities':
|
||||
comment.text = 'purgecss start ignore'
|
||||
break
|
||||
default:
|
||||
break
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function removeTailwindComments(css) {
|
||||
css.walkComments(comment => {
|
||||
switch (comment.text.trim()) {
|
||||
|
|
@ -28,7 +62,7 @@ export default function purgeUnusedUtilities(config) {
|
|||
)
|
||||
|
||||
if (!purgeEnabled) {
|
||||
return removeTailwindComments
|
||||
return postcss([convertLayersToControlComments, removeTailwindComments])
|
||||
}
|
||||
|
||||
// Skip if `purge: []` since that's part of the default config
|
||||
|
|
@ -52,29 +86,9 @@ export default function purgeUnusedUtilities(config) {
|
|||
}
|
||||
|
||||
return postcss([
|
||||
function(css) {
|
||||
const mode = _.get(config, 'purge.mode', 'conservative')
|
||||
|
||||
if (mode === 'conservative') {
|
||||
css.prepend(postcss.comment({ text: 'purgecss start ignore' }))
|
||||
css.append(postcss.comment({ text: 'purgecss end ignore' }))
|
||||
|
||||
css.walkComments(comment => {
|
||||
switch (comment.text.trim()) {
|
||||
case 'tailwind start utilities':
|
||||
comment.text = 'purgecss end ignore'
|
||||
break
|
||||
case 'tailwind end utilities':
|
||||
comment.text = 'purgecss start ignore'
|
||||
break
|
||||
default:
|
||||
break
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
removeTailwindComments(css)
|
||||
},
|
||||
convertLayersToControlComments,
|
||||
convertControlCommentsToPurgeIgnoreComments(config),
|
||||
removeTailwindComments,
|
||||
purgecss({
|
||||
content: Array.isArray(config.purge) ? config.purge : config.purge.content,
|
||||
defaultExtractor: content => {
|
||||
|
|
|
|||
|
|
@ -4,8 +4,51 @@ import cloneNodes from '../util/cloneNodes'
|
|||
import buildMediaQuery from '../util/buildMediaQuery'
|
||||
import buildSelectorVariant from '../util/buildSelectorVariant'
|
||||
|
||||
function isLayer(node) {
|
||||
if (Array.isArray(node)) {
|
||||
return node.length === 1 && isLayer(node[0])
|
||||
}
|
||||
return node.type === 'atrule' && node.name === 'layer'
|
||||
}
|
||||
|
||||
function layerNodes(nodes) {
|
||||
return isLayer(nodes) ? nodes[0].nodes : nodes
|
||||
}
|
||||
|
||||
export default function(config) {
|
||||
return function(css) {
|
||||
// Wrap any `responsive` rules with a copy of their parent `layer` to
|
||||
// ensure the layer isn't lost when copying to the `screens` location.
|
||||
css.walkAtRules('layer', layerAtRule => {
|
||||
const layer = layerAtRule.params
|
||||
layerAtRule.walkAtRules('responsive', responsiveAtRule => {
|
||||
const nestedlayerAtRule = postcss.atRule({
|
||||
name: 'layer',
|
||||
params: layer,
|
||||
})
|
||||
nestedlayerAtRule.prepend(responsiveAtRule.nodes)
|
||||
responsiveAtRule.removeAll()
|
||||
responsiveAtRule.prepend(nestedlayerAtRule)
|
||||
})
|
||||
})
|
||||
|
||||
// Find any `responsive` rules with no parent `layer` (these only come
|
||||
// from the user's CSS, Tailwind never generates things this way itself)
|
||||
// and wrap them with a default `layer` of `utilities`.
|
||||
css.walkAtRules('responsive', responsiveAtRule => {
|
||||
const [node] = responsiveAtRule.nodes
|
||||
if (node.type === 'atrule' && node.name === 'layer') {
|
||||
return
|
||||
}
|
||||
const nestedlayerAtRule = postcss.atRule({
|
||||
name: 'layer',
|
||||
params: 'utilities',
|
||||
})
|
||||
nestedlayerAtRule.prepend(responsiveAtRule.nodes)
|
||||
responsiveAtRule.removeAll()
|
||||
responsiveAtRule.prepend(nestedlayerAtRule)
|
||||
})
|
||||
|
||||
const {
|
||||
theme: { screens },
|
||||
separator,
|
||||
|
|
@ -16,7 +59,16 @@ export default function(config) {
|
|||
css.walkAtRules('responsive', atRule => {
|
||||
const nodes = atRule.nodes
|
||||
responsiveRules.append(...cloneNodes(nodes))
|
||||
atRule.before(nodes)
|
||||
|
||||
// If the parent is already a `layer` (this is true for anything coming from
|
||||
// a plugin, including core plugins) we don't want to create a double nested
|
||||
// layer, so only insert the layer children. If there is no parent layer,
|
||||
// preserve the layer information when inserting the nodes.
|
||||
if (isLayer(atRule.parent)) {
|
||||
atRule.before(layerNodes(nodes))
|
||||
} else {
|
||||
atRule.before(nodes)
|
||||
}
|
||||
atRule.remove()
|
||||
})
|
||||
|
||||
|
|
|
|||
|
|
@ -24,15 +24,6 @@ export default function(getConfig) {
|
|||
substituteResponsiveAtRules(config),
|
||||
substituteScreenAtRules(config),
|
||||
substituteClassApplyAtRules(config, processedPlugins.utilities),
|
||||
function(css) {
|
||||
css.walkAtRules('bucket', atRule => {
|
||||
const bucket = atRule.params
|
||||
atRule.before(postcss.comment({ text: `tailwind start ${bucket}` }))
|
||||
atRule.before(atRule.nodes)
|
||||
atRule.before(postcss.comment({ text: `tailwind end ${bucket}` }))
|
||||
atRule.remove()
|
||||
})
|
||||
},
|
||||
purgeUnusedStyles(config),
|
||||
]).process(css, { from: _.get(css, 'source.input.file') })
|
||||
}
|
||||
|
|
|
|||
|
|
@ -28,11 +28,11 @@ function containsClass(value) {
|
|||
}).transformSync(value)
|
||||
}
|
||||
|
||||
function wrapWithBucket(rules, bucket) {
|
||||
function wrapWithLayer(rules, layer) {
|
||||
return postcss
|
||||
.atRule({
|
||||
name: 'bucket',
|
||||
params: bucket,
|
||||
name: 'layer',
|
||||
params: layer,
|
||||
})
|
||||
.append(cloneNodes(Array.isArray(rules) ? rules : [rules]))
|
||||
}
|
||||
|
|
@ -119,7 +119,7 @@ export default function(plugins, config) {
|
|||
})
|
||||
|
||||
pluginUtilities.push(
|
||||
wrapWithVariants(wrapWithBucket(styles.nodes, 'utilities'), options.variants)
|
||||
wrapWithLayer(wrapWithVariants(styles.nodes, options.variants), 'utilities')
|
||||
)
|
||||
},
|
||||
addComponents: (components, options) => {
|
||||
|
|
@ -138,7 +138,7 @@ export default function(plugins, config) {
|
|||
})
|
||||
|
||||
pluginComponents.push(
|
||||
wrapWithVariants(wrapWithBucket(styles.nodes, 'components'), options.variants)
|
||||
wrapWithLayer(wrapWithVariants(styles.nodes, options.variants), 'components')
|
||||
)
|
||||
},
|
||||
addBase: baseStyles => {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue