Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
Sort based on first occurence of a candidate
This primarily affects components and utilities which contain multiple matched classes
  • Loading branch information
thecrypticace committed Jun 28, 2023
commit 2aa12bba68ca6f4bf59caad0464cba0e97b5b110
4 changes: 3 additions & 1 deletion src/lib/setupContextUtils.js
Original file line number Diff line number Diff line change
Expand Up @@ -944,7 +944,9 @@ function registerPlugins(plugins, context) {
for (const [, rule] of rules) {
let candidate = rule.raws.tailwind.candidate

sortedClassNames.set(candidate, idx++)
// When multiple rules match a candidate
// always take the position of the first one
sortedClassNames.set(candidate, sortedClassNames.get(candidate) ?? idx++)
}

return classes.map((className) => {
Expand Down
39 changes: 39 additions & 0 deletions tests/getSortOrder.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -140,3 +140,42 @@ it('sorts classes deterministically across multiple class lists', () => {
expect(defaultSort(context.getClassOrder(input.split(' ')))).toEqual(output)
}
})

it('sorts based on first occurence of a candidate / rule', () => {
let classes = [
['foo-1 foo', 'foo foo-1'],
['bar', 'bar'],
['foo-1 foo', 'foo foo-1'],
]

let config = {
theme: {},
plugins: [
function ({ addComponents }) {
addComponents({
'.foo': { display: 'block' },
'.foo-1': { display: 'block' },
'.foo-2': { display: 'block' },
'.bar': { display: 'block' },

// This rule matches both the candidate `foo` and `bar`
// But when sorting `foo` — we've already got a
// position for `foo` so we should use it
'.bar .foo': { display: 'block' },
})
}
],
}

// Same context, different class lists
let context = createContext(resolveConfig(config))
for (const [input, output] of classes) {
expect(defaultSort(context.getClassOrder(input.split(' ')))).toEqual(output)
}

// Different context, different class lists
for (const [input, output] of classes) {
context = createContext(resolveConfig(config))
expect(defaultSort(context.getClassOrder(input.split(' ')))).toEqual(output)
}
})