@polygonjs/polygonjs
Version:
node-based WebGL 3D engine https://polygonjs.com
111 lines (110 loc) • 3.17 kB
JavaScript
;
import jsep from "jsep";
import { isString } from "../../../core/Type";
jsep.addUnaryOp("@");
let precedence = 10;
jsep.addBinaryOp("**", precedence);
const JSEP_IDENTIFIER = "Identifier";
const JSEP_LITERAL = "Literal";
const JSEP_CALL_EXPRESSION = "CallExpression";
const STRING_EXPRESSION_SEPARATOR = "`";
export function stringValueElements(v) {
if (v != null) {
if (isString(v)) {
return v.split(STRING_EXPRESSION_SEPARATOR);
} else {
return [];
}
} else {
return [];
}
}
export class ParsedTree {
constructor(_param) {
this._param = _param;
}
node() {
return this._node;
}
errorMessage() {
return this._errorMessage;
}
parseExpression(string) {
try {
this.reset();
this._node = jsep(string);
} catch (e) {
const message = `could not parse the expression '${string}' (error: ${e})`;
this._errorMessage = message;
}
}
parseExpressionForStringParam(string) {
try {
this.reset();
const elements = stringValueElements(string);
const nodes = [];
for (let i = 0; i < elements.length; i++) {
const element = elements[i];
let node;
if (i % 2 == 1) {
node = jsep(element);
} else {
const sanitizedElement = element.replace(/\'/g, "\\'");
node = {
type: JSEP_LITERAL,
value: `'${sanitizedElement}'`,
raw: `'${sanitizedElement}'`
};
this._param.scene().missingExpressionReferencesController.registerToIgnore(node);
}
nodes.push(node);
}
this._node = {
type: JSEP_CALL_EXPRESSION,
arguments: nodes,
callee: {
type: JSEP_IDENTIFIER,
name: "strConcat"
}
};
} catch (e) {
const message = `could not parse the expression '${string}' (error: ${e})`;
this._errorMessage = message;
}
}
// static string_value_contains_expression(v:string): boolean{
// return ((this.string_value_elements(v).length - 1) % 2) === 0;
// }
// deep_parse_for_string_expressions(){
// // for string expressions which have more than a single `<expr>` element
// // pt_`@ptnum`
// // `@ptnum`_pt
// // pt_`@ptnum`_`1+1`
// if(this.node.type == JSEP_COMPOUND){
// const args = this.node.body
// let arg;
// for(let i=0; i<args.length; i++){
// arg = args[i]
// if(arg.type == JSEP_LITERAL){
// const arg_node = jsep(arg.value)
// args[i] = arg_node
// }
// }
// } else {
// // for string expressions which havea single `<expr>` element
// // `@ptnum`
// if(this.node.type == JSEP_LITERAL){
// const raw = this.node.raw
// const first_char_code = raw.charCodeAt(0)
// const last_char_code = raw.charCodeAt(raw.length-1)
// if(first_char_code == HOUDINI_QUOTE_CODE && last_char_code == HOUDINI_QUOTE_CODE){
// this.node = jsep("''+"+this.node.value) // add the prefix ''+ to ensure we have a string as a result, and not a number
// }
// }
// }
// }
reset() {
this._node = void 0;
this._errorMessage = void 0;
}
}