Removed Symbol parse node
Too much overlap with accessors, so now all symbols are a special case of accessors
This commit is contained in:
@@ -1,4 +1,4 @@
|
||||
// Generated automatically by nearley, version 2.16.0
|
||||
// Generated automatically by nearley, version 2.20.1
|
||||
// http://github.com/Hardmath123/nearley
|
||||
function id(x) { return x[0]; }
|
||||
|
||||
@@ -122,7 +122,7 @@ let ParserRules = [
|
||||
{"name": "valueExpression", "symbols": ["string"], "postprocess": id},
|
||||
{"name": "valueExpression", "symbols": ["boolean"], "postprocess": id},
|
||||
{"name": "number", "symbols": [(lexer.has("number") ? {type: "number"} : number)], "postprocess": d => node.constant.create({value: +d[0].value})},
|
||||
{"name": "name", "symbols": [(lexer.has("name") ? {type: "name"} : name)], "postprocess": d => node.symbol.create({name: d[0].value})},
|
||||
{"name": "name", "symbols": [(lexer.has("name") ? {type: "name"} : name)], "postprocess": d => node.accessor.create({name: d[0].value})},
|
||||
{"name": "string", "symbols": [(lexer.has("string") ? {type: "string"} : string)], "postprocess": d => node.constant.create({value: d[0].value})},
|
||||
{"name": "boolean", "symbols": [{"literal":"true"}], "postprocess": d => node.constant.create({value: true})},
|
||||
{"name": "boolean", "symbols": [{"literal":"false"}], "postprocess": d => node.constant.create({value: false})},
|
||||
|
||||
@@ -159,7 +159,7 @@ number ->
|
||||
%number {% d => node.constant.create({value: +d[0].value}) %}
|
||||
|
||||
name ->
|
||||
%name {% d => node.symbol.create({name: d[0].value}) %}
|
||||
%name {% d => node.accessor.create({name: d[0].value}) %}
|
||||
|
||||
string ->
|
||||
%string {% d => node.constant.create({value: d[0].value}) %}
|
||||
|
||||
@@ -10,7 +10,6 @@ import operator from './operator.js';
|
||||
import parenthesis from './parenthesis.js';
|
||||
import roll from './roll.js';
|
||||
import rollArray from './rollArray.js';
|
||||
import symbol from './symbol.js';
|
||||
import unaryOperator from './unaryOperator.js';
|
||||
|
||||
export default Object.freeze({
|
||||
@@ -26,6 +25,7 @@ export default Object.freeze({
|
||||
parenthesis,
|
||||
roll,
|
||||
rollArray,
|
||||
symbol,
|
||||
// What used to be symbols are now just treated as accessors without a path
|
||||
symbol: accessor,
|
||||
unaryOperator,
|
||||
});
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
import constant from './constant.js';
|
||||
// import array from './array.js';
|
||||
import { toString } from '../resolve.js';
|
||||
import array from './array.js';
|
||||
import resolve from '../resolve.js';
|
||||
import { getFromScope } from '/imports/api/creature/creatures/CreatureVariables';
|
||||
|
||||
const accessor = {
|
||||
create({ name, path }) {
|
||||
@@ -11,16 +12,21 @@ const accessor = {
|
||||
};
|
||||
},
|
||||
compile(node, scope, context) {
|
||||
let value = scope && scope[node.name];
|
||||
// For objects, get their value
|
||||
node.path.forEach(name => {
|
||||
let value = getFromScope(node.name, scope);
|
||||
// Get the value from the given path
|
||||
node.path?.forEach(name => {
|
||||
if (value === undefined) return;
|
||||
value = value[name];
|
||||
});
|
||||
let valueType = getType(value);
|
||||
// If the accessor returns an objet, get the object's value instead
|
||||
// If the accessor returns an object, get the object's value instead
|
||||
while (valueType === 'object') {
|
||||
value = value.value;
|
||||
// Prefer the valueNode over the value
|
||||
if (value.valueNode) {
|
||||
value = value.valueNode;
|
||||
} else {
|
||||
value = value.value;
|
||||
}
|
||||
valueType = getType(value);
|
||||
}
|
||||
// Return a discovered parse node
|
||||
@@ -40,40 +46,44 @@ const accessor = {
|
||||
context,
|
||||
};
|
||||
}
|
||||
/* Can't access #object.tags until this is fixed
|
||||
* If we activate this, the array node expects values to be an array of
|
||||
* parse nodes, so it will break unless the values are coerced here or at
|
||||
* in the array node's code to be parse nodes, not raw js
|
||||
else if (valueType === 'array') {
|
||||
// Return a parser array
|
||||
if (valueType === 'array') {
|
||||
// If the first value is a parse node, assume all the values are
|
||||
if (getType(value[0]) === 'parseNode') {
|
||||
return {
|
||||
result: array.create({
|
||||
values: value,
|
||||
}),
|
||||
context,
|
||||
};
|
||||
}
|
||||
// Create the array from js primitives instead
|
||||
return {
|
||||
result: array.create({
|
||||
values: value,
|
||||
}),
|
||||
result: array.fromConstantArray(value),
|
||||
context,
|
||||
};
|
||||
}
|
||||
*/
|
||||
else if (valueType === 'undefined') {
|
||||
if (valueType === 'undefined') {
|
||||
// Undefined defaults to zero
|
||||
return {
|
||||
result: accessor.create({
|
||||
name: node.name,
|
||||
path: node.path,
|
||||
result: constant.create({
|
||||
value: 0,
|
||||
}),
|
||||
context,
|
||||
};
|
||||
} else {
|
||||
context.error(`Accessing ${accessor.toString(node)} is not supported yet`);
|
||||
return {
|
||||
result: accessor.create({
|
||||
name: node.name,
|
||||
path: node.path,
|
||||
}),
|
||||
context,
|
||||
context
|
||||
};
|
||||
}
|
||||
context.error(`Accessing ${accessor.toString(node)} is not supported yet`);
|
||||
return {
|
||||
result: accessor.create({
|
||||
name: node.name,
|
||||
path: node.path,
|
||||
}),
|
||||
context,
|
||||
};
|
||||
},
|
||||
reduce(node, scope, context) {
|
||||
let { result } = accessor.compile(node, scope, context);
|
||||
({ result } = resolve('reduce', result, scope, context));
|
||||
if (result.parseType === 'accessor') {
|
||||
return {
|
||||
result: constant.create({
|
||||
@@ -86,6 +96,7 @@ const accessor = {
|
||||
}
|
||||
},
|
||||
toString(node) {
|
||||
if (!node.path) return `${node.name}`;
|
||||
return `${node.name}.${node.path.join('.')}`;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,57 +0,0 @@
|
||||
import resolve, { toString } from '../resolve.js';
|
||||
import constant from './constant.js';
|
||||
|
||||
const symbol = {
|
||||
create({ name }) {
|
||||
return {
|
||||
parseType: 'symbol',
|
||||
name,
|
||||
};
|
||||
},
|
||||
toString(node) {
|
||||
return `${node.name}`
|
||||
},
|
||||
compile(node, scope, context, calledFromReduce = false) {
|
||||
let value = scope && scope[node.name];
|
||||
let type = typeof value;
|
||||
// For objects, default to their .value
|
||||
if (type === 'object') {
|
||||
value = value.value;
|
||||
type = typeof value;
|
||||
}
|
||||
// For parse nodes, compile and return
|
||||
if (value?.parseType) {
|
||||
if (calledFromReduce) {
|
||||
return resolve('reduce', value, scope, context);
|
||||
} else {
|
||||
return resolve('compile', value, scope, context);
|
||||
}
|
||||
}
|
||||
if (type === 'string' || type === 'number' || type === 'boolean') {
|
||||
return {
|
||||
result: constant.create({ value }),
|
||||
context,
|
||||
};
|
||||
} else if (type === 'undefined') {
|
||||
return {
|
||||
result: symbol.create({ name: node.name }),
|
||||
context,
|
||||
};
|
||||
} else {
|
||||
throw new Meteor.Error(`Unexpected case: ${node.name} resolved to ${value}`);
|
||||
}
|
||||
},
|
||||
reduce(node, scope, context) {
|
||||
let { result } = symbol.compile(node, scope, context, true);
|
||||
if (result.parseType === 'symbol') {
|
||||
return {
|
||||
result: constant.create({ value: 0 }),
|
||||
context,
|
||||
};
|
||||
} else {
|
||||
return { result, context };
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
export default symbol;
|
||||
Reference in New Issue
Block a user