mirror of
https://github.com/qlik-oss/nebula.js.git
synced 2026-05-24 16:00:16 -04:00
70 lines
1.6 KiB
JavaScript
70 lines
1.6 KiB
JavaScript
/* eslint no-param-reassign: 0 */
|
|
|
|
const VARIABLE_RX = /\$[A-z0-9.]+/g;
|
|
|
|
function throwCyclical(s) {
|
|
throw new Error(`Cyclical reference for "${s}"`);
|
|
}
|
|
|
|
function resolveStyle(style, references, replacer) {
|
|
const s = {};
|
|
|
|
Object.keys(style).forEach((key) => {
|
|
let value = style[key];
|
|
if (VARIABLE_RX.test(value)) {
|
|
value = value.replace(VARIABLE_RX, replacer);
|
|
}
|
|
s[key] = value;
|
|
});
|
|
return s;
|
|
}
|
|
|
|
function createRefs(obj, s = '', refs) {
|
|
Object.keys(obj).forEach((key) => {
|
|
if (typeof obj[key] === 'string') {
|
|
refs[`${s}${key}`] = obj[key];
|
|
} else if (typeof obj[key] === 'object') {
|
|
createRefs(obj[key], `${s}${key}.`, refs);
|
|
}
|
|
});
|
|
}
|
|
|
|
function resolver(theme = {}) {
|
|
const refs = {};
|
|
createRefs(theme, '', refs);
|
|
const replacer = (match) => refs[match.substring(1)];
|
|
|
|
function resolveValueReferences(value, path = []) {
|
|
const variables = typeof value === 'string' ? value.match(VARIABLE_RX) : null;
|
|
if (variables && variables.length) {
|
|
variables.forEach((v) => {
|
|
const ref = v.substring(1);
|
|
if (path.indexOf(ref) !== -1) {
|
|
throwCyclical(v);
|
|
}
|
|
const refValue = resolveValueReferences(refs[ref], [...path, ref]);
|
|
value = value.replace(v, refValue);
|
|
});
|
|
}
|
|
return value;
|
|
}
|
|
|
|
Object.keys(refs).forEach((key) => {
|
|
refs[key] = resolveValueReferences(refs[key], [key]);
|
|
});
|
|
|
|
return {
|
|
get(value) {
|
|
return resolveValueReferences(value);
|
|
},
|
|
resolve(style) {
|
|
return resolveStyle(style, refs, replacer);
|
|
},
|
|
references() {
|
|
return refs;
|
|
},
|
|
};
|
|
}
|
|
|
|
export default resolver;
|