react-native-unistyles
Version:
Level up your React Native StyleSheet
112 lines (106 loc) • 3.87 kB
JavaScript
;
import { UnistyleDependency } from '../specs/NativePlatform/NativePlatform.nitro';
import { deepMergeObjects } from '../utils';
import { extractSecrets, extractUnistyleDependencies, isGeneratedUnistyle, isServer } from './utils';
import { getVariants } from './variants';
export class UnistylesShadowRegistry {
// MOCKS
name = 'UnistylesShadowRegistry';
__type = 'web';
equals = () => true;
toString = () => 'UnistylesShadowRegistry';
dispose = () => {};
// END MOCKS
scopedTheme = undefined;
disposeMap = new Map();
constructor(services) {
this.services = services;
}
add = (ref, hash) => {
if (isServer() || !(ref instanceof HTMLElement) || !hash) {
return;
}
this.services.registry.connect(ref, hash);
};
addStyles = (unistyles, forChild) => {
const [firstStyle] = unistyles;
// If it is already a generated style, return it
if (firstStyle && isGeneratedUnistyle(firstStyle)) {
return firstStyle;
}
const getParsedStyles = () => {
const allStyles = unistyles.map(unistyle => {
const secrets = extractSecrets(unistyle);
// Regular style
if (!secrets) {
return unistyle;
}
// Animated styles - shouldn't be processed
if (Object.keys(secrets).length === 0) {
return {};
}
const {
__uni__key,
__uni__stylesheet,
__uni__args = [],
__stylesheetVariants: variants
} = secrets;
const newComputedStylesheet = this.services.registry.getComputedStylesheet(__uni__stylesheet, scopedTheme);
const style = newComputedStylesheet[__uni__key];
const result = typeof style === 'function' ? style(...__uni__args) : style;
const variantsResult = getVariants(result, variants);
const resultWithVariants = deepMergeObjects(result, variantsResult);
const dependencies = extractUnistyleDependencies(resultWithVariants);
if (typeof __uni__stylesheet === 'function') {
// Add dependencies from dynamic styles to stylesheet
this.services.registry.addDependenciesToStylesheet(__uni__stylesheet, dependencies);
}
return {
...resultWithVariants,
...resultWithVariants._web
};
});
return deepMergeObjects(...allStyles);
};
// Copy scoped theme to not use referenced value
const scopedTheme = this.scopedTheme;
const parsedStyles = getParsedStyles();
const {
hash,
existingHash
} = this.services.registry.add(parsedStyles, forChild);
const injectedClassNames = parsedStyles?._web?._classNames ?? [];
const injectedClassName = Array.isArray(injectedClassNames) ? injectedClassNames.join(' ') : injectedClassNames;
const dependencies = extractUnistyleDependencies(parsedStyles);
const filteredDependencies = this.services.state.CSSVars ? dependencies.filter(dependency => dependency !== UnistyleDependency.Theme) : dependencies;
if (!existingHash) {
this.disposeMap.set(hash, this.services.listener.addListeners(filteredDependencies, () => {
this.services.registry.applyStyles(hash, getParsedStyles());
}));
}
const hashClassname = forChild ? hash.replace(' > *', '') : hash;
return {
injectedClassName,
hash: hashClassname,
parsedStyles
};
};
setScopedTheme = theme => {
this.scopedTheme = theme;
};
getScopedTheme = () => this.scopedTheme;
remove = (ref, hash) => {
if (isServer() || !(ref instanceof HTMLElement) || !hash) {
return;
}
this.services.registry.remove(ref, hash).then(removed => {
if (!removed) {
return;
}
this.disposeMap.get(hash)?.();
this.disposeMap.delete(hash);
});
};
flush = () => {};
}
//# sourceMappingURL=shadowRegistry.js.map