feat: flowbite-themable for theming components with no color prop(not only)
This commit is contained in:
52
src/utils/simplifyTailwindClasses.ts
Normal file
52
src/utils/simplifyTailwindClasses.ts
Normal file
@@ -0,0 +1,52 @@
|
||||
// function to simplify tailwind classes, can be upgraded with RegExp and by minimizing of using array methods
|
||||
// example:
|
||||
// simplifyClasses('dark:background-red-600 background-red text-black', 'dark:background-blue')
|
||||
|
||||
export type TailwindClassMatcherMap = Record<string, (c: string) => string>
|
||||
|
||||
const classTypeMatchers: TailwindClassMatcherMap = {
|
||||
border: (_class: string): string => {
|
||||
return _class.substring(0, _class.lastIndexOf('-')) // for splitting border-b-2 and border-red
|
||||
},
|
||||
}
|
||||
|
||||
const getTypeFromClass = (_class: string, matchers: TailwindClassMatcherMap = classTypeMatchers) => {
|
||||
const classesToMatch = Object.keys(matchers)
|
||||
const matchClass = classesToMatch.find(_matchClass => _class.includes(_matchClass)) // TODO: maybe need to filter instead of find
|
||||
if(!matchClass) return _class.substring(0, _class.indexOf('-'))
|
||||
|
||||
return matchers[matchClass as keyof typeof matchers](_class)
|
||||
}
|
||||
|
||||
export function simplifyTailwindClasses(...classes: (string | string[])[]): string {
|
||||
return classes.reduce((acc: { types: string[], classes: string[] }, value: string | string[]) => {
|
||||
const currentClasses = Array.isArray(value)
|
||||
? Array.from(value).map(_ => _.split(' ')).flat() // to support args like ['text-white background-red', 'flex'] etc.
|
||||
: value.split(' ')
|
||||
const currentTypes = currentClasses.map(_class => getTypeFromClass(_class))
|
||||
|
||||
const typesToAdd = currentTypes.filter(_ => !acc.types.includes(_))
|
||||
const typesToReplace = currentTypes.filter(_ => acc.types.includes(_))
|
||||
const newTypes = [...typesToReplace, ...typesToAdd]
|
||||
|
||||
const types = [...new Set([...acc.types, ...newTypes])]
|
||||
const classes = types.map(type => {
|
||||
if(newTypes.includes(type)) {
|
||||
const classIndex = currentTypes.indexOf(type)
|
||||
if(classIndex >= 0)
|
||||
return currentClasses[classIndex] || ''
|
||||
}
|
||||
const classIndex = acc.types.indexOf(type)
|
||||
if(classIndex >= 0)
|
||||
return acc.classes[classIndex] || ''
|
||||
return ''
|
||||
}).filter(_ => !!_)
|
||||
|
||||
return {
|
||||
types,
|
||||
classes,
|
||||
}
|
||||
}, { types: [], classes: [] }).classes.join(' ')
|
||||
}
|
||||
|
||||
// simplifyClasses('dark:background-red-600 background-red text-400-black', 'dark:background-blue', 'text-600-white', 'dark:background-red-600')
|
||||
Reference in New Issue
Block a user