circuitscript 0.1.4 → 0.1.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (102) hide show
  1. package/dist/cjs/BaseVisitor.js +149 -80
  2. package/dist/cjs/SemanticTokenVisitor.js +19 -13
  3. package/dist/cjs/antlr/CircuitScriptParser.js +711 -671
  4. package/dist/cjs/builtinMethods.js +48 -22
  5. package/dist/cjs/draw_symbols.js +4 -1
  6. package/dist/cjs/environment.js +118 -0
  7. package/dist/cjs/execute.js +98 -46
  8. package/dist/cjs/geometry.js +1 -0
  9. package/dist/cjs/globals.js +14 -7
  10. package/dist/cjs/helpers.js +142 -150
  11. package/dist/cjs/index.js +5 -0
  12. package/dist/cjs/layout.js +39 -14
  13. package/dist/cjs/main.js +34 -21
  14. package/dist/cjs/objects/ClassComponent.js +4 -1
  15. package/dist/cjs/objects/ExecutionScope.js +40 -2
  16. package/dist/cjs/objects/ParamDefinition.js +15 -15
  17. package/dist/cjs/parser.js +27 -21
  18. package/dist/cjs/regenerate-tests.js +9 -6
  19. package/dist/cjs/render.js +3 -1
  20. package/dist/cjs/sizing.js +10 -60
  21. package/dist/cjs/utils.js +148 -17
  22. package/dist/cjs/validate/SymbolTable.js +96 -0
  23. package/dist/cjs/validate/SymbolValidatorResolveVisitor.js +14 -0
  24. package/dist/cjs/validate/SymbolValidatorVisitor.js +170 -0
  25. package/dist/cjs/validate.js +52 -44
  26. package/dist/cjs/visitor.js +149 -31
  27. package/dist/esm/{BaseVisitor.mjs → BaseVisitor.js} +124 -56
  28. package/dist/esm/{SemanticTokenVisitor.mjs → SemanticTokenVisitor.js} +17 -11
  29. package/dist/esm/antlr/{CircuitScriptParser.mjs → CircuitScriptParser.js} +711 -671
  30. package/dist/esm/{builtinMethods.mjs → builtinMethods.js} +40 -14
  31. package/dist/esm/{draw_symbols.mjs → draw_symbols.js} +11 -8
  32. package/dist/esm/environment.js +110 -0
  33. package/dist/esm/{execute.mjs → execute.js} +111 -58
  34. package/dist/esm/{export.mjs → export.js} +2 -2
  35. package/dist/esm/{geometry.mjs → geometry.js} +6 -5
  36. package/dist/esm/{globals.mjs → globals.js} +9 -2
  37. package/dist/esm/helpers.js +377 -0
  38. package/dist/esm/index.js +20 -0
  39. package/dist/esm/{layout.mjs → layout.js} +44 -22
  40. package/dist/esm/{lexer.mjs → lexer.js} +2 -2
  41. package/dist/esm/{main.mjs → main.js} +36 -23
  42. package/dist/esm/objects/{ClassComponent.mjs → ClassComponent.js} +9 -5
  43. package/dist/esm/objects/{ExecutionScope.mjs → ExecutionScope.js} +40 -2
  44. package/dist/esm/objects/{Frame.mjs → Frame.js} +1 -1
  45. package/dist/esm/objects/{ParamDefinition.mjs → ParamDefinition.js} +1 -1
  46. package/dist/esm/objects/{PinDefinition.mjs → PinDefinition.js} +1 -1
  47. package/dist/esm/parser.js +71 -0
  48. package/dist/esm/{regenerate-tests.mjs → regenerate-tests.js} +10 -7
  49. package/dist/esm/{render.mjs → render.js} +11 -9
  50. package/dist/esm/{sizing.mjs → sizing.js} +11 -36
  51. package/dist/esm/utils.js +286 -0
  52. package/dist/esm/validate/SymbolTable.js +90 -0
  53. package/dist/esm/validate/SymbolValidatorResolveVisitor.js +10 -0
  54. package/dist/esm/validate/SymbolValidatorVisitor.js +163 -0
  55. package/dist/esm/validate.js +86 -0
  56. package/dist/esm/{visitor.mjs → visitor.js} +160 -42
  57. package/dist/fonts/Arial.ttf +0 -0
  58. package/dist/fonts/Inter-Bold.ttf +0 -0
  59. package/dist/fonts/Inter-Regular.ttf +0 -0
  60. package/dist/fonts/OpenSans-Regular.ttf +0 -0
  61. package/dist/fonts/Roboto-Regular.ttf +0 -0
  62. package/dist/libs/lib.cst +423 -0
  63. package/dist/types/BaseVisitor.d.ts +36 -22
  64. package/dist/types/SemanticTokenVisitor.d.ts +6 -5
  65. package/dist/types/antlr/CircuitScriptParser.d.ts +4 -2
  66. package/dist/types/builtinMethods.d.ts +3 -2
  67. package/dist/types/draw_symbols.d.ts +2 -6
  68. package/dist/types/environment.d.ts +31 -0
  69. package/dist/types/execute.d.ts +2 -3
  70. package/dist/types/globals.d.ts +7 -2
  71. package/dist/types/helpers.d.ts +12 -14
  72. package/dist/types/index.d.ts +5 -0
  73. package/dist/types/objects/ClassComponent.d.ts +2 -3
  74. package/dist/types/objects/ExecutionScope.d.ts +20 -6
  75. package/dist/types/objects/types.d.ts +6 -1
  76. package/dist/types/parser.d.ts +7 -11
  77. package/dist/types/sizing.d.ts +0 -3
  78. package/dist/types/utils.d.ts +33 -4
  79. package/dist/types/validate/SymbolTable.d.ts +40 -0
  80. package/dist/types/validate/SymbolValidatorResolveVisitor.d.ts +7 -0
  81. package/dist/types/validate/SymbolValidatorVisitor.d.ts +32 -0
  82. package/dist/types/validate.d.ts +1 -1
  83. package/libs/lib.cst +12 -22
  84. package/package.json +14 -13
  85. package/dist/cjs/SymbolValidatorVisitor.js +0 -233
  86. package/dist/esm/SymbolValidatorVisitor.mjs +0 -222
  87. package/dist/esm/helpers.mjs +0 -380
  88. package/dist/esm/index.mjs +0 -15
  89. package/dist/esm/parser.mjs +0 -64
  90. package/dist/esm/utils.mjs +0 -169
  91. package/dist/esm/validate.mjs +0 -74
  92. package/dist/types/SymbolValidatorVisitor.d.ts +0 -61
  93. package/dist/types/layout.d.ts +0 -148
  94. /package/dist/esm/antlr/{CircuitScriptLexer.mjs → CircuitScriptLexer.js} +0 -0
  95. /package/dist/esm/antlr/{CircuitScriptVisitor.mjs → CircuitScriptVisitor.js} +0 -0
  96. /package/dist/esm/{fonts.mjs → fonts.js} +0 -0
  97. /package/dist/esm/{logger.mjs → logger.js} +0 -0
  98. /package/dist/esm/objects/{Net.mjs → Net.js} +0 -0
  99. /package/dist/esm/objects/{PinTypes.mjs → PinTypes.js} +0 -0
  100. /package/dist/esm/objects/{Wire.mjs → Wire.js} +0 -0
  101. /package/dist/esm/objects/{types.mjs → types.js} +0 -0
  102. /package/dist/esm/{server.mjs → server.js} +0 -0
@@ -1,3 +1,4 @@
1
+ import { Property_key_exprContext } from '../antlr/CircuitScriptParser.js';
1
2
  export class ExecutionScope {
2
3
  scopeId;
3
4
  nets = [];
@@ -6,6 +7,8 @@ export class ExecutionScope {
6
7
  variables = new Map();
7
8
  symbols = new Map();
8
9
  blockStack = new Map();
10
+ contextStack = [];
11
+ onPropertyHandler = [];
9
12
  breakStack = [];
10
13
  wires = [];
11
14
  frames = [];
@@ -16,8 +19,6 @@ export class ExecutionScope {
16
19
  currentPin = null;
17
20
  currentWireId = -1;
18
21
  currentFrameId = -1;
19
- netGnd = null;
20
- componentGnd = null;
21
22
  componentRoot = null;
22
23
  copyIDs = new Map();
23
24
  sequence = [];
@@ -41,6 +42,12 @@ export class ExecutionScope {
41
42
  });
42
43
  return found ? found[2] : null;
43
44
  }
45
+ getNetWithNamespacePath(namespace, name) {
46
+ const found = this.nets.find(([, , net]) => {
47
+ return net.namespace === namespace && net.name === name;
48
+ });
49
+ return found ? found[2] : null;
50
+ }
44
51
  hasNet(component, pin) {
45
52
  return this.findNet(component, pin) !== undefined;
46
53
  }
@@ -118,6 +125,36 @@ export class ExecutionScope {
118
125
  this.currentPin = null;
119
126
  }
120
127
  }
128
+ enterContext(context) {
129
+ this.contextStack.push(context);
130
+ }
131
+ exitContext() {
132
+ return this.contextStack.pop();
133
+ }
134
+ findPropertyKeyTree() {
135
+ const keyNames = [];
136
+ for (let i = this.contextStack.length - 1; i >= 0; i--) {
137
+ const ctx = this.contextStack[i];
138
+ if (ctx instanceof Property_key_exprContext) {
139
+ keyNames.push([ctx, ctx.getText()]);
140
+ }
141
+ else if (typeof ctx === 'number') {
142
+ keyNames.push(['index', ctx]);
143
+ }
144
+ }
145
+ return keyNames.reverse();
146
+ }
147
+ setOnPropertyHandler(handler) {
148
+ this.onPropertyHandler.push(handler);
149
+ }
150
+ popOnPropertyHandler() {
151
+ return this.onPropertyHandler.pop();
152
+ }
153
+ triggerPropertyHandler(value, valueCtx) {
154
+ const lastHandler = this.onPropertyHandler[this.onPropertyHandler.length - 1];
155
+ const propertyTree = this.findPropertyKeyTree();
156
+ lastHandler && lastHandler(propertyTree, value, valueCtx);
157
+ }
121
158
  }
122
159
  export var SequenceAction;
123
160
  (function (SequenceAction) {
@@ -126,6 +163,7 @@ export var SequenceAction;
126
163
  SequenceAction["Wire"] = "wire";
127
164
  SequenceAction["WireJump"] = "wire-jump";
128
165
  SequenceAction["Frame"] = "frame";
166
+ SequenceAction["Assign"] = "assign";
129
167
  })(SequenceAction || (SequenceAction = {}));
130
168
  export var FrameAction;
131
169
  (function (FrameAction) {
@@ -1,4 +1,4 @@
1
- import { FrameType } from "../globals.mjs";
1
+ import { FrameType } from "../globals.js";
2
2
  export class Frame {
3
3
  parameters = new Map();
4
4
  frameId;
@@ -1,4 +1,4 @@
1
- import { getNumberExponential, getNumberExponentialText, resolveToNumericValue } from "../utils";
1
+ import { getNumberExponential, getNumberExponentialText, resolveToNumericValue } from "../utils.js";
2
2
  import { Big } from 'big.js';
3
3
  export class ParamDefinition {
4
4
  paramName;
@@ -1,4 +1,4 @@
1
- import { PinTypes } from './PinTypes.mjs';
1
+ import { PinTypes } from './PinTypes.js';
2
2
  export class PinDefinition {
3
3
  id;
4
4
  idType;
@@ -0,0 +1,71 @@
1
+ import { CircuitScriptParser } from './antlr/CircuitScriptParser.js';
2
+ import { MainLexer } from './lexer.js';
3
+ import { ParseSyntaxError, RuntimeExecutionError, SimpleStopwatch } from './utils.js';
4
+ import { CharStream, CommonTokenStream } from 'antlr4ng';
5
+ export async function parseFileWithVisitor(visitor, data) {
6
+ const lexerErrorListener = new CircuitscriptParserErrorListener(visitor.onErrorHandler);
7
+ const parserErrorListener = new CircuitscriptParserErrorListener(visitor.onErrorHandler);
8
+ const chars = CharStream.fromString(data);
9
+ const lexer = new MainLexer(chars);
10
+ lexer.removeErrorListeners();
11
+ lexer.addErrorListener(lexerErrorListener);
12
+ const lexerTimer = new SimpleStopwatch();
13
+ const tokens = new CommonTokenStream(lexer);
14
+ tokens.fill();
15
+ const lexerTimeTaken = lexerTimer.lap();
16
+ const parserTimer = new SimpleStopwatch();
17
+ const parser = new CircuitScriptParser(tokens);
18
+ parser.removeErrorListeners();
19
+ parser.addErrorListener(parserErrorListener);
20
+ const tree = parser.script();
21
+ try {
22
+ await visitor.visitAsync(tree);
23
+ }
24
+ catch (error) {
25
+ if (visitor.onErrorHandler) {
26
+ if (error instanceof RuntimeExecutionError) {
27
+ visitor.onErrorHandler(error.message, null, error);
28
+ }
29
+ else {
30
+ throw error;
31
+ }
32
+ }
33
+ }
34
+ const parserTimeTaken = parserTimer.lap();
35
+ return {
36
+ tree, parser,
37
+ hasParseError: false,
38
+ hasError: false,
39
+ parserTimeTaken,
40
+ lexerTimeTaken,
41
+ };
42
+ }
43
+ export class CircuitscriptParserErrorListener {
44
+ syntaxErrorCounter = 0;
45
+ onErrorHandler = null;
46
+ constructor(onErrorHandler = null) {
47
+ this.onErrorHandler = onErrorHandler;
48
+ }
49
+ syntaxError(recognizer, offendingSymbol, line, column, msg, e) {
50
+ if (this.onErrorHandler && e) {
51
+ this.onErrorHandler(msg, e.ctx, e);
52
+ }
53
+ else {
54
+ if (offendingSymbol && msg.match("extraneous input 'import' expecting")) {
55
+ msg = "Invalid import statement";
56
+ throw new ParseSyntaxError("Invalid import statement", offendingSymbol);
57
+ }
58
+ console.log("Syntax error at line", line, ':', column, ' - ', msg);
59
+ }
60
+ this.syntaxErrorCounter++;
61
+ }
62
+ reportAmbiguity(recognizer, dfa, startIndex, stopIndex, exact, ambigAlts, configs) {
63
+ }
64
+ reportAttemptingFullContext(recognizer, dfa, startIndex, stopIndex, conflictingAlts, configs) {
65
+ }
66
+ reportContextSensitivity(recognizer, dfa, startIndex, stopIndex, prediction, configs) {
67
+ }
68
+ hasSyntaxErrors() {
69
+ return (this.syntaxErrorCounter > 0);
70
+ }
71
+ }
@@ -1,11 +1,11 @@
1
1
  import fs from 'fs';
2
- import { getDefaultLibsPath, getFontsPath, renderScript } from './helpers.mjs';
3
- import { prepareSVGEnvironment } from './sizing.mjs';
2
+ import { renderScript } from './helpers.js';
3
+ import { NodeScriptEnvironment } from "./environment.js";
4
4
  const mainDir = './__tests__/renderData/';
5
- const fontsPath = getFontsPath();
6
- const defaultLibsPath = getDefaultLibsPath();
5
+ const env = new NodeScriptEnvironment();
6
+ NodeScriptEnvironment.setInstance(env);
7
7
  async function regenerateTests(extra = "") {
8
- await prepareSVGEnvironment(fontsPath);
8
+ env.prepareSVGEnvironment();
9
9
  const cstFiles = [];
10
10
  const files = fs.readdirSync(mainDir);
11
11
  files.forEach(file => {
@@ -17,9 +17,12 @@ async function regenerateTests(extra = "") {
17
17
  const inputPath = mainDir + file;
18
18
  const scriptData = fs.readFileSync(inputPath, { encoding: 'utf-8' });
19
19
  const outputPath = mainDir + 'svgs/' + file + extra + '.svg';
20
+ env.setModuleDirectory(mainDir);
20
21
  renderScript(scriptData, outputPath, {
21
- currentDirectory: mainDir,
22
- defaultLibsPath,
22
+ dumpNets: false,
23
+ dumpData: false,
24
+ showStats: false,
25
+ environment: env,
23
26
  });
24
27
  console.log('generated ', outputPath);
25
28
  });
@@ -1,15 +1,17 @@
1
1
  import { SVG, registerWindow } from '@svgdotjs/svg.js';
2
- import { ExtractDrawingRects, RenderFrameType, getBounds } from "./layout.mjs";
3
- import { applyFontsToSVG, getCreateSVGWindow } from './sizing.mjs';
4
- import { ColorScheme, ComponentTypes, FrameType, MMToPt, MMToPx, ParamKeys, RenderFlags, defaultGridSizeUnits, defaultPageSpacingMM, defaultWireLineWidth, fontDisplayScale, junctionSize } from './globals.mjs';
5
- import { numeric, NumericValue } from './objects/ParamDefinition.mjs';
6
- import { combineMaps, getBoundsSize } from './utils.mjs';
7
- import { getPaperSize, milsToMM } from './helpers.mjs';
2
+ import { ExtractDrawingRects, RenderFrameType, getBounds } from "./layout.js";
3
+ import { applyFontsToSVG } from './sizing.js';
4
+ import { ColorScheme, ComponentTypes, FrameType, MMToPt, MMToPx, ParamKeys, RenderFlags, defaultGridSizeUnits, defaultPageSpacingMM, defaultWireLineWidth, fontDisplayScale, junctionSize } from './globals.js';
5
+ import { numeric, NumericValue } from './objects/ParamDefinition.js';
6
+ import { combineMaps, getBoundsSize } from './utils.js';
7
+ import { getPaperSize, milsToMM } from './helpers.js';
8
+ import { NodeScriptEnvironment } from "./environment.js";
8
9
  import SVGtoPDF from 'svg-to-pdfkit';
9
- import { FrameParamKeys } from './objects/Frame.mjs';
10
- import { SymbolPlaceholder } from './draw_symbols.mjs';
10
+ import { FrameParamKeys } from './objects/Frame.js';
11
+ import { SymbolPlaceholder } from './draw_symbols.js';
11
12
  function createSvgCanvas() {
12
- const window = getCreateSVGWindow()();
13
+ const env = NodeScriptEnvironment.getInstance();
14
+ const window = env.createSVGWindow();
13
15
  const document = window.document;
14
16
  registerWindow(window, document);
15
17
  const canvas = SVG(document.documentElement);
@@ -1,41 +1,14 @@
1
- import { SVG, registerWindow } from '@svgdotjs/svg.js';
2
- import { HorizontalAlign, HorizontalAlignProp, VerticalAlign, VerticalAlignProp } from './geometry.mjs';
3
- import { defaultFont } from './globals.mjs';
4
- import { JSModuleType, detectJSModuleType } from './helpers.mjs';
5
- let MainCanvas = null;
6
- const supportedFonts = {
7
- 'Arial': 'Arial.ttf',
8
- };
9
- let globalCreateSVGWindow;
10
- export async function prepareSVGEnvironment(fontsPath) {
11
- const moduleType = detectJSModuleType();
12
- if (moduleType === JSModuleType.CommonJs) {
13
- const { config, createSVGWindow } = await import('svgdom');
14
- globalCreateSVGWindow = createSVGWindow;
15
- if (fontsPath !== null) {
16
- await config.setFontDir(fontsPath)
17
- .setFontFamilyMappings(supportedFonts)
18
- .preloadFonts();
19
- }
20
- }
21
- }
22
- export function getCreateSVGWindow() {
23
- if (globalCreateSVGWindow === undefined) {
24
- throw "SVG environment is not set up yet";
25
- }
26
- return globalCreateSVGWindow;
27
- }
1
+ import { Big } from 'big.js';
2
+ import { HorizontalAlign, HorizontalAlignProp, VerticalAlign, VerticalAlignProp } from './geometry.js';
3
+ import { defaultFont } from './globals.js';
4
+ import { NodeScriptEnvironment } from "./environment.js";
28
5
  export function applyFontsToSVG(canvas) {
29
6
  }
30
7
  const measureTextSizeCache = {};
31
8
  const measureTextSizeCacheHits = {};
32
9
  export function measureTextSize2(text, fontFamily, fontSize, fontWeight = 'regular', anchor = HorizontalAlign.Left, vanchor = VerticalAlign.Bottom) {
33
- if (MainCanvas === null) {
34
- const window = getCreateSVGWindow()();
35
- const { document } = window;
36
- registerWindow(window, document);
37
- MainCanvas = SVG(document.documentElement);
38
- }
10
+ const environment = NodeScriptEnvironment.getInstance();
11
+ const mainCanvas = environment.getCanvasWindow();
39
12
  const key = `${text}-${fontFamily}-${fontSize}-${fontWeight}-${anchor}-${vanchor}`;
40
13
  if (measureTextSizeCache[key] === undefined) {
41
14
  let dominantBaseline = VerticalAlignProp.Hanging;
@@ -63,7 +36,7 @@ export function measureTextSize2(text, fontFamily, fontSize, fontWeight = 'regul
63
36
  break;
64
37
  }
65
38
  fontFamily = defaultFont;
66
- const tmpTextElement = MainCanvas.text(text).font({
39
+ const tmpTextElement = mainCanvas.text(text).font({
67
40
  family: fontFamily,
68
41
  size: fontSize,
69
42
  anchor: useAnchor,
@@ -87,9 +60,11 @@ export function measureTextSize2(text, fontFamily, fontSize, fontWeight = 'regul
87
60
  }
88
61
  const { width, height } = textbox;
89
62
  tmpTextElement.remove();
63
+ const finalWidth = new Big(width).round(4).toNumber();
64
+ const finalHeight = new Big(height).round(4).toNumber();
90
65
  measureTextSizeCache[key] = {
91
- width: Math.round(width * 100) / 100,
92
- height: Math.round(height * 100) / 100,
66
+ width: finalWidth,
67
+ height: finalHeight,
93
68
  box: textbox,
94
69
  };
95
70
  measureTextSizeCacheHits[key] = 0;
@@ -0,0 +1,286 @@
1
+ import { Big } from 'big.js';
2
+ import { ClassComponent } from "./objects/ClassComponent.js";
3
+ import { NumericValue } from "./objects/ParamDefinition.js";
4
+ import { SequenceAction } from './objects/ExecutionScope.js';
5
+ import { BlockTypes } from './globals.js';
6
+ export class SimpleStopwatch {
7
+ startTime;
8
+ constructor() {
9
+ this.startTime = new Date();
10
+ }
11
+ lap() {
12
+ return (new Date()).getTime() - this.startTime.getTime();
13
+ }
14
+ }
15
+ export function resizeBounds(bounds, value) {
16
+ return {
17
+ xmin: bounds.xmin - value,
18
+ xmax: bounds.xmax + value,
19
+ ymin: bounds.ymin - value,
20
+ ymax: bounds.ymax + value
21
+ };
22
+ }
23
+ export function printBounds(bounds) {
24
+ if (bounds !== null) {
25
+ return `[${bounds.xmin}, ${bounds.ymin} to ${bounds.xmax}, ${bounds.ymax}]`;
26
+ }
27
+ else {
28
+ return 'null';
29
+ }
30
+ }
31
+ function hasRemainder(value, value2) {
32
+ const tmpValue = Math.abs(value) / value2;
33
+ const flooredValue = Math.floor(tmpValue);
34
+ const diff = tmpValue - flooredValue;
35
+ return diff;
36
+ }
37
+ export function resizeToNearestGrid(bounds, gridSize = 20) {
38
+ const addXMin = hasRemainder(bounds.xmin, gridSize) === 0 ? -1 : 0;
39
+ const addYMin = hasRemainder(bounds.ymin, gridSize) === 0 ? -1 : 0;
40
+ const addXMax = hasRemainder(bounds.xmax, gridSize) === 0 ? 1 : 0;
41
+ const addYMax = hasRemainder(bounds.ymax, gridSize) === 0 ? 1 : 0;
42
+ return {
43
+ xmin: Math.floor((bounds.xmin + addXMin) / gridSize) * gridSize,
44
+ ymin: Math.floor((bounds.ymin + addYMin) / gridSize) * gridSize,
45
+ xmax: Math.ceil((bounds.xmax + addXMax) / gridSize) * gridSize,
46
+ ymax: Math.ceil((bounds.ymax + addYMax) / gridSize) * gridSize,
47
+ };
48
+ }
49
+ export function toNearestGrid(value, gridSize) {
50
+ return Math.floor(value / gridSize) * gridSize;
51
+ }
52
+ export function getBoundsSize(bounds) {
53
+ return {
54
+ width: bounds.xmax - bounds.xmin,
55
+ height: bounds.ymax - bounds.ymin,
56
+ };
57
+ }
58
+ export function getPortType(component) {
59
+ const drawingCommands = component.displayProp;
60
+ let foundPinType = null;
61
+ const commands = drawingCommands.getCommands();
62
+ commands.some(item => {
63
+ if (item[0] === 'label' && item[2].has('portType')) {
64
+ foundPinType = item[2].get('portType');
65
+ return true;
66
+ }
67
+ return false;
68
+ });
69
+ return foundPinType;
70
+ }
71
+ export function roundValue(value) {
72
+ return resolveToNumericValue(new Big(value.toBigNumber().toFixed(7)));
73
+ }
74
+ export function throwWithContext(context, messageOrError) {
75
+ if (messageOrError instanceof BaseError) {
76
+ throw messageOrError;
77
+ }
78
+ throwWithTokenRange(messageOrError, context.start, context.stop);
79
+ }
80
+ export function throwWithToken(message, token) {
81
+ throw new ParseError(message, token);
82
+ }
83
+ export function throwWithTokenRange(message, startToken, endToken) {
84
+ throw new ParseError(message, startToken, endToken);
85
+ }
86
+ export function combineMaps(map1, map2) {
87
+ const newMap = new Map(map1);
88
+ map2.forEach((value, key) => {
89
+ newMap.set(key, value);
90
+ });
91
+ return newMap;
92
+ }
93
+ export function getNumberExponential(value) {
94
+ value = value.trim();
95
+ switch (value) {
96
+ case 'G':
97
+ return 9;
98
+ case 'M':
99
+ return 6;
100
+ case 'k':
101
+ case 'K':
102
+ return 3;
103
+ case 'm':
104
+ return -3;
105
+ case 'u':
106
+ return -6;
107
+ case 'n':
108
+ return -9;
109
+ case 'p':
110
+ return -12;
111
+ case 'f':
112
+ return -15;
113
+ default:
114
+ return 0;
115
+ }
116
+ }
117
+ export function getNumberExponentialText(value) {
118
+ switch (value) {
119
+ case -15:
120
+ return 'f';
121
+ case -12:
122
+ return 'p';
123
+ case -9:
124
+ return 'n';
125
+ case -6:
126
+ return 'u';
127
+ case -3:
128
+ return 'm';
129
+ case 3:
130
+ return 'k';
131
+ case 6:
132
+ return 'M';
133
+ case 9:
134
+ return 'G';
135
+ case 0:
136
+ default:
137
+ return '';
138
+ }
139
+ }
140
+ export function resolveToNumericValue(value) {
141
+ if (value.toNumber() === 0) {
142
+ return new NumericValue(0);
143
+ }
144
+ const isNeg = value.lt(0);
145
+ const positiveValue = isNeg ? value.neg() : value;
146
+ const prefixPart = Math.floor(Math.log10(positiveValue.toNumber()) / 3);
147
+ let useValue = value;
148
+ if (prefixPart !== 0) {
149
+ const tmpValue1 = positiveValue.div(Math.pow(10, prefixPart * 3));
150
+ useValue = isNeg ? tmpValue1.neg() : tmpValue1;
151
+ }
152
+ return new NumericValue(useValue, prefixPart * 3);
153
+ }
154
+ export function isPointWithinArea(point, bounds) {
155
+ const [xPt, yPt] = point;
156
+ const [xmin, ymin, xmax, ymax] = bounds;
157
+ return (xPt > xmin && xPt < xmax && yPt > ymin && yPt < ymax);
158
+ }
159
+ export function areasOverlap(area1, area2) {
160
+ const [xmin, ymin, xmax, ymax] = area1;
161
+ const pt1 = [xmin, ymin];
162
+ const pt2 = [xmin, ymax];
163
+ const pt3 = [xmax, ymin];
164
+ const pt4 = [xmax, ymax];
165
+ return isPointWithinArea(pt1, area2)
166
+ || isPointWithinArea(pt2, area2)
167
+ || isPointWithinArea(pt3, area2)
168
+ || isPointWithinArea(pt4, area2);
169
+ }
170
+ export function sequenceActionString(sequenceAction) {
171
+ const tmp = [...sequenceAction];
172
+ const action = tmp[0];
173
+ if (action === SequenceAction.Wire) {
174
+ tmp[2] = tmp[2].map(item2 => {
175
+ const lengthValue = item2.value;
176
+ const useValue = [item2.direction];
177
+ if (lengthValue !== null) {
178
+ useValue.push(lengthValue.value);
179
+ useValue.push(lengthValue.type);
180
+ }
181
+ return useValue.join(",");
182
+ }).join(" ");
183
+ }
184
+ else if (action === SequenceAction.Frame) {
185
+ tmp[1] = sequenceAction[1].frameId;
186
+ }
187
+ else if (action !== SequenceAction.WireJump) {
188
+ const [, component] = sequenceAction;
189
+ if (component instanceof ClassComponent) {
190
+ tmp[1] = sequenceAction[1].instanceName;
191
+ }
192
+ }
193
+ return tmp.join(" | ");
194
+ }
195
+ export function generateDebugSequenceAction(sequence) {
196
+ const variableMapping = new Map();
197
+ return sequence.map(item => {
198
+ const returnResult = [...item];
199
+ const [action,] = item;
200
+ if (action === SequenceAction.Assign) {
201
+ const [, name, component] = item;
202
+ variableMapping.set(name, component);
203
+ }
204
+ else {
205
+ if (action === SequenceAction.At || action === SequenceAction.To) {
206
+ const [, component,] = item;
207
+ const foundIndex = Array.from(variableMapping.values()).findIndex(item2 => {
208
+ if (component._copyFrom !== null) {
209
+ return component._copyFrom === item2;
210
+ }
211
+ return component === item2;
212
+ });
213
+ if (foundIndex !== -1) {
214
+ const name = Array.from(variableMapping.keys())[foundIndex];
215
+ returnResult[1] = name + ':' + component._copyID;
216
+ }
217
+ }
218
+ }
219
+ return returnResult;
220
+ });
221
+ }
222
+ export function getBlockTypeString(type) {
223
+ let returnValue = 'branch';
224
+ switch (type) {
225
+ case BlockTypes.Branch:
226
+ returnValue = 'branch';
227
+ break;
228
+ case BlockTypes.Join:
229
+ returnValue = 'join';
230
+ break;
231
+ case BlockTypes.Parallel:
232
+ returnValue = 'parallel';
233
+ break;
234
+ case BlockTypes.Point:
235
+ returnValue = 'point';
236
+ break;
237
+ }
238
+ return returnValue;
239
+ }
240
+ export class BaseError extends Error {
241
+ name = 'BaseError';
242
+ message;
243
+ startToken;
244
+ endToken;
245
+ filePath;
246
+ constructor(message, startToken, endToken, filePath) {
247
+ super(message);
248
+ this.message = message;
249
+ this.startToken = startToken;
250
+ this.endToken = endToken;
251
+ this.filePath = filePath;
252
+ }
253
+ toString() {
254
+ const parts = [this.name];
255
+ if (this.startToken) {
256
+ const { line, column } = this.startToken;
257
+ if (this.endToken && (this.endToken.line !== this.startToken.line || this.endToken.column !== this.startToken.column)) {
258
+ const endLine = this.endToken.line;
259
+ const endColumn = this.endToken.column + (this.endToken.stop - this.endToken.start);
260
+ parts.push(` at ${line}:${column}-${endLine}:${endColumn}`);
261
+ }
262
+ else {
263
+ parts.push(` at ${line}:${column}`);
264
+ }
265
+ }
266
+ parts.push(`: ${this.message}`);
267
+ return parts.join('');
268
+ }
269
+ }
270
+ export class ParseSyntaxError extends BaseError {
271
+ name = 'ParseSyntaxError';
272
+ }
273
+ export class ParseError extends ParseSyntaxError {
274
+ name = 'ParseError';
275
+ }
276
+ export class RuntimeExecutionError extends BaseError {
277
+ name = 'RuntimeExecutionError';
278
+ }
279
+ export class RenderError extends Error {
280
+ stage;
281
+ constructor(message, stage) {
282
+ super(message);
283
+ this.name = 'RenderError';
284
+ this.stage = stage;
285
+ }
286
+ }
@@ -0,0 +1,90 @@
1
+ import { ParseSymbolType } from "../objects/types.js";
2
+ export class SymbolTable {
3
+ symbols = new Map();
4
+ executonContextsNamespaces = [];
5
+ getSymbols() {
6
+ return this.symbols;
7
+ }
8
+ addFunction(token, fileName, executionContext, id, funcDefinedParameters) {
9
+ return this.add(fileName, executionContext, id, ParseSymbolType.Function, {
10
+ funcDefinedParameters
11
+ }, token);
12
+ }
13
+ addVariable(token, fileName, executionContext, id, variableValue) {
14
+ return this.add(fileName, executionContext, id, ParseSymbolType.Variable, {
15
+ variableValue
16
+ }, token);
17
+ }
18
+ addUndefined(filePath, executionContext, id, token) {
19
+ return this.add(filePath, executionContext, id, ParseSymbolType.Undefined, {}, token);
20
+ }
21
+ add(fileName, executionContext, id, type, extra, token) {
22
+ if (this.executonContextsNamespaces.indexOf(executionContext.namespace) === -1) {
23
+ this.executonContextsNamespaces.push(executionContext.namespace);
24
+ }
25
+ const item = {
26
+ id,
27
+ type,
28
+ context: executionContext,
29
+ fileName,
30
+ extra,
31
+ token,
32
+ instances: [],
33
+ };
34
+ if (token !== null) {
35
+ item.instances.push(token);
36
+ }
37
+ this.symbols.set(this.idName(executionContext, id), item);
38
+ return item;
39
+ }
40
+ idName(executionContext, id) {
41
+ return executionContext.namespace + id;
42
+ }
43
+ dumpSymbols() {
44
+ for (const [key, value] of this.symbols) {
45
+ console.log(value.type.padEnd(10, " "), key);
46
+ }
47
+ }
48
+ exists(executionContext, id) {
49
+ const name = this.idName(executionContext, id);
50
+ return this.symbols.has(name);
51
+ }
52
+ existsAny(executionContext, id) {
53
+ if (this.exists(executionContext, id)) {
54
+ return true;
55
+ }
56
+ else {
57
+ return this.searchParentContext(executionContext, id) !== null;
58
+ }
59
+ }
60
+ get(executionContext, id) {
61
+ const name = this.idName(executionContext, id);
62
+ return this.symbols.get(name);
63
+ }
64
+ getParentContexts(executionContext, contextsNamespace) {
65
+ if (executionContext.parentContext !== null) {
66
+ contextsNamespace.push(executionContext.parentContext.namespace);
67
+ this.getParentContexts(executionContext.parentContext, contextsNamespace);
68
+ }
69
+ return contextsNamespace;
70
+ }
71
+ searchParentContext(executionContext, id) {
72
+ const contextNames = this.getParentContexts(executionContext, []);
73
+ for (const [key,] of this.symbols) {
74
+ if (key.endsWith(`.${id}`)) {
75
+ const { context } = this.symbols.get(key);
76
+ if (contextNames.indexOf(context.namespace) !== -1) {
77
+ return context;
78
+ }
79
+ }
80
+ }
81
+ return null;
82
+ }
83
+ clearUndefined() {
84
+ for (const [key, value] of this.symbols) {
85
+ if (value.type === ParseSymbolType.Undefined) {
86
+ this.symbols.delete(key);
87
+ }
88
+ }
89
+ }
90
+ }
@@ -0,0 +1,10 @@
1
+ import { SymbolValidatorVisitor } from "./SymbolValidatorVisitor.js";
2
+ export class SymbolValidatorResolveVisitor extends SymbolValidatorVisitor {
3
+ addSymbolVariable(token, name, value) {
4
+ }
5
+ addSymbolFunction(token, functionName, funcDefinedParameters) {
6
+ if (this.symbolTable.exists(this.getExecutor(), functionName)) {
7
+ this.symbolTable.addFunction(token, this.getCurrentFile(), this.getExecutor(), functionName, funcDefinedParameters);
8
+ }
9
+ }
10
+ }