Skip to content

Commit

Permalink
lots or organization
Browse files Browse the repository at this point in the history
  • Loading branch information
CarelessCourage committed Jan 5, 2024
1 parent c48ef7f commit 799d41d
Show file tree
Hide file tree
Showing 2 changed files with 62 additions and 83 deletions.
119 changes: 56 additions & 63 deletions packages/core/engine/primitives/attach.ts
Original file line number Diff line number Diff line change
Expand Up @@ -96,98 +96,91 @@ function getMeta(selector?: string) {
export function attach({ outputs, target, alias }: Attach) {
const meta = getMeta(target.selector)

const filtered = outputs.flattened.filter(({ name }) => !invalidColor(name))
if (target.element) setElementColors(target.element, filtered)
if (target.selector) setColorSheet(target.selector, filtered, meta)
const colors = outputs.flattened.filter(({ name }) => !invalidColor(name))
if (target.element) setElementColors(target.element, colors)
if (target.selector) setColorSheet(target.selector, colors, meta)

if (alias) {
const ali = alias === true ? defaultAliases : alias
const aliasesArray = makeAliasArray(ali)
if (target.element) setElementAliases(target.element, aliasesArray)
if (target.selector) setAliasesSheet(target.selector, aliasesArray, meta)
const aliases = Object.entries(alias === true ? defaultAliases : alias)
const array = aliases.map(([key, value]) => ({ name: '--' + key, color: `var(${value})` }))
if (target.element) setElementAliases(target.element, array)
if (target.selector) setAliasSheet(target.selector, array, meta)
}

return outputs
}

interface SetProperty {
name: 'foreground' | 'background' | 'accents' | string
color: string
}

const setProperty = (element: HTMLElement, { name, color }: SetProperty) => {
element.style.setProperty(name, color)
}

type AliasObject = {
name: string
value: string
}

const makeAliasArray = (obj: Alias): AliasObject[] => {
const objArray = Object.entries(obj)
return objArray.map(([key, value]) => {
return { name: key, value: value }
})
}

function invalidColor(name: string) {
const regex = /(?:background|foreground).*contrast/i
return regex.test(name)
}

function setColorSheet(selector = ':root', flattened: FlattenColor[], meta?: string) {
const sheet = new CSSStyleSheet()
sheet.replace(
`theme-${meta}, ${selector} {${flattened
.map(({ name, color }) => `${name}: ${color};`)
.join('')}}`
)
setSheet(sheet, selector)
}
//sheet functions

function setElementColors(element: HTMLElement | null, colors: FlattenColor[]) {
if (!element) return
colors.forEach(({ name, color }) => setProperty(element, { name, color }))
//Ensure that the foreground color is always set to the attached element
setProperty(element, {
name: 'color',
color: 'var(--foreground)'
})
interface MTS {
meta?: string
marker?: string
selector?: string
}

function setAliasesSheet(selector = ':root', aliases: AliasObject[], meta?: string) {
function camelToVariable(name: string) {
return '--' + name.replace(/([a-z])([A-Z])/g, '$1-$2').toLowerCase()
}

function makeThemeSheet(
colors: FlattenColor[],
{ selector = ':root', meta = '1', marker = 'theme' }: MTS
) {
const sheet = new CSSStyleSheet()
sheet.replace(
`theme-alias-${meta}, :${selector} {${aliases
.map(({ name, value }) => `${camelToVariable(name)}: var(--${value});`)
`${marker}-${meta}, ${selector} {${colors
.map(({ name, color }) => `${name}: ${color};`)
.join('')}}`
)
return sheet
}

setSheet(sheet, selector)
function setColorSheet(selector = ':root', colors: FlattenColor[], meta?: string) {
const marker = 'theme'
const sheet = makeThemeSheet(colors, { meta, marker, selector })
setSheet(sheet, selector, marker)
}

function setElementAliases(element: HTMLElement | null, aliases: AliasObject[]) {
if (!element) return
aliases.forEach(({ name, value }) => {
setProperty(element, {
name: name,
color: `var(--${value})`
})
})
function setAliasSheet(selector = ':root', colors: FlattenColor[], meta?: string) {
const marker = 'theme-alias'
const sheet = makeThemeSheet(colors, { meta, marker, selector })
setSheet(sheet, selector, marker)
}

function setSheet(sheet: CSSStyleSheet, selector: string) {
function setSheet(sheet: CSSStyleSheet, selector: string, marker = 'theme') {
//this is only possible because of ...spreading the adoptedStylesheets.
//Normally, you can't access the cssRules of an adopted stylesheet
const filtered = [...document.adoptedStyleSheets].filter((sheet) => {
const includesUmbra = sheet.cssRules[0].cssText.includes('theme')
console.log(sheet)
const includesUmbra = sheet.cssRules[0].cssText.includes(marker)
const sameTarget = sheet.cssRules[0].cssText.includes(selector)
return !includesUmbra || !sameTarget
})
document.adoptedStyleSheets = [...filtered, sheet]
}

//element functions

interface SetProperty {
name: 'foreground' | 'background' | 'accents' | string
color: string
}

const setProperty = (element: HTMLElement, { name, color }: SetProperty) => {
element.style.setProperty(name, color)
}

function setElementColors(element: HTMLElement | null, colors: FlattenColor[]) {
if (!element) return
colors.forEach(({ name, color }) => setProperty(element, { name, color }))
//Ensure that the foreground color is always set to the attached element
setProperty(element, {
name: 'color',
color: 'var(--base-contrast)'
})
}

function setElementAliases(element: HTMLElement | null, aliases: FlattenColor[]) {
element && aliases.forEach((p) => setProperty(element, p))
}
26 changes: 6 additions & 20 deletions packages/playground/src/App.vue
Original file line number Diff line number Diff line change
Expand Up @@ -54,31 +54,17 @@ const theme = umbra({
background: '#000000',
foreground: '#ffffff',
accents: [radixBlue, radixRed, radixYellow, success, royal, brown, something, accent]
}).apply('html')
umbra({
background: '#000000',
foreground: '#ffffff',
accents: [radixBlue, radixRed, radixYellow, success, royal, brown, something, accent]
}).apply()
umbra({
background: '#000000',
foreground: '#ffffff',
accents: [radixBlue, radixRed, radixYellow, success, royal, brown, something, accent]
}).apply('body')
umbra({
background: '#000000',
foreground: '#ffffff',
accents: [radixBlue, radixRed, radixYellow, success, royal, brown, something, accent]
}).apply('.umbra')
}).apply('html', {
alias: true
})
const t = ref(theme.input)
const formated = ref(theme.formated)
function inverse() {
const newTheme = umbra(t.value.scheme).inverse().apply('body')
const newTheme = umbra(t.value.scheme).inverse().apply('body', {
alias: true
})
t.value = newTheme.input
}
Expand Down

0 comments on commit 799d41d

Please sign in to comment.