circuitscript 0.1.0 → 0.1.2

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 (61) hide show
  1. package/dist/cjs/BaseVisitor.js +13 -8
  2. package/dist/cjs/antlr/CircuitScriptLexer.js +80 -80
  3. package/dist/cjs/antlr/CircuitScriptParser.js +599 -657
  4. package/dist/cjs/builtinMethods.js +27 -8
  5. package/dist/cjs/draw_symbols.js +314 -190
  6. package/dist/cjs/execute.js +113 -115
  7. package/dist/cjs/export.js +2 -4
  8. package/dist/cjs/geometry.js +52 -19
  9. package/dist/cjs/globals.js +12 -8
  10. package/dist/cjs/helpers.js +16 -3
  11. package/dist/cjs/layout.js +129 -125
  12. package/dist/cjs/logger.js +8 -1
  13. package/dist/cjs/objects/ClassComponent.js +22 -22
  14. package/dist/cjs/objects/ExecutionScope.js +10 -4
  15. package/dist/cjs/objects/Frame.js +2 -1
  16. package/dist/cjs/objects/ParamDefinition.js +120 -4
  17. package/dist/cjs/objects/PinDefinition.js +1 -4
  18. package/dist/cjs/render.js +40 -110
  19. package/dist/cjs/sizing.js +33 -7
  20. package/dist/cjs/utils.js +68 -2
  21. package/dist/cjs/visitor.js +214 -254
  22. package/dist/esm/BaseVisitor.mjs +15 -10
  23. package/dist/esm/antlr/CircuitScriptLexer.mjs +80 -80
  24. package/dist/esm/antlr/CircuitScriptParser.mjs +599 -657
  25. package/dist/esm/builtinMethods.mjs +24 -8
  26. package/dist/esm/draw_symbols.mjs +316 -193
  27. package/dist/esm/execute.mjs +115 -117
  28. package/dist/esm/export.mjs +2 -4
  29. package/dist/esm/geometry.mjs +52 -19
  30. package/dist/esm/globals.mjs +12 -8
  31. package/dist/esm/helpers.mjs +17 -4
  32. package/dist/esm/layout.mjs +131 -127
  33. package/dist/esm/logger.mjs +8 -1
  34. package/dist/esm/objects/ClassComponent.mjs +21 -26
  35. package/dist/esm/objects/ExecutionScope.mjs +10 -4
  36. package/dist/esm/objects/Frame.mjs +2 -1
  37. package/dist/esm/objects/ParamDefinition.mjs +119 -3
  38. package/dist/esm/objects/PinDefinition.mjs +0 -2
  39. package/dist/esm/render.mjs +42 -112
  40. package/dist/esm/sizing.mjs +34 -8
  41. package/dist/esm/utils.mjs +64 -1
  42. package/dist/esm/visitor.mjs +216 -256
  43. package/dist/types/BaseVisitor.d.ts +1 -1
  44. package/dist/types/antlr/CircuitScriptParser.d.ts +2 -3
  45. package/dist/types/draw_symbols.d.ts +71 -45
  46. package/dist/types/execute.d.ts +15 -10
  47. package/dist/types/geometry.d.ts +31 -19
  48. package/dist/types/globals.d.ts +14 -10
  49. package/dist/types/helpers.d.ts +2 -1
  50. package/dist/types/layout.d.ts +21 -21
  51. package/dist/types/logger.d.ts +1 -1
  52. package/dist/types/objects/ClassComponent.d.ts +19 -16
  53. package/dist/types/objects/ExecutionScope.d.ts +2 -1
  54. package/dist/types/objects/Frame.d.ts +2 -2
  55. package/dist/types/objects/ParamDefinition.d.ts +31 -2
  56. package/dist/types/objects/PinDefinition.d.ts +0 -2
  57. package/dist/types/render.d.ts +2 -1
  58. package/dist/types/utils.d.ts +6 -1
  59. package/dist/types/visitor.d.ts +4 -5
  60. package/libs/lib.cst +15 -3
  61. package/package.json +7 -3
@@ -1,6 +1,7 @@
1
1
  import { SymbolDrawingCommands } from '../draw_symbols.mjs';
2
2
  import { PinDefinition, PinIdType } from './PinDefinition.mjs';
3
3
  import { PinTypes } from './PinTypes.mjs';
4
+ import { ParamKeys } from '../globals.mjs';
4
5
  export class ClassComponent {
5
6
  instanceName;
6
7
  numPins;
@@ -8,14 +9,15 @@ export class ClassComponent {
8
9
  pins = new Map();
9
10
  pinNets = new Map();
10
11
  pinWires = new Map();
12
+ pinsMaxPositions = {};
11
13
  _cachedPins;
12
14
  _cachedParams;
13
- className;
14
15
  _copyID = null;
15
16
  _copyFrom = null;
16
17
  arrangeProps = null;
17
18
  displayProp = null;
18
19
  widthProp = null;
20
+ heightProp = null;
19
21
  typeProp = null;
20
22
  copyProp = false;
21
23
  angleProp = 0;
@@ -23,17 +25,10 @@ export class ClassComponent {
23
25
  wireOrientationAngle = 0;
24
26
  useWireOrientationAngle = true;
25
27
  didSetWireOrientationAngle = false;
26
- styles = {};
27
28
  assignedRefDes = null;
28
- moduleContainsExpressions;
29
- moduleCounter = 0;
30
- moduleExecutionContext;
31
- moduleExecutionContextName;
32
- modulePinIdToPortMap;
33
- constructor(instanceName, numPins, className) {
29
+ constructor(instanceName, numPins) {
34
30
  this.instanceName = instanceName;
35
31
  this.numPins = numPins;
36
- this.className = className;
37
32
  }
38
33
  setupPins() {
39
34
  for (let i = 1; i < this.numPins + 1; i++) {
@@ -110,25 +105,26 @@ export class ClassComponent {
110
105
  toString() {
111
106
  return this.instanceName;
112
107
  }
113
- static simple(instanceName, numPins, className) {
114
- const component = new ClassComponent(instanceName, numPins, className);
108
+ static simple(instanceName, numPins) {
109
+ const component = new ClassComponent(instanceName, numPins);
115
110
  component.setupPins();
116
111
  return component;
117
112
  }
118
113
  isEqual(other) {
119
114
  return this.instanceName === other.instanceName
120
115
  && this.numPins === other.numPins
121
- && this.className === other.className
122
116
  && this._copyID === other._copyID
123
117
  && this.arrangeProps === other.arrangeProps
124
- && this.displayProp === other.displayProp
118
+ && ((this.displayProp === null && other.displayProp === null)
119
+ ||
120
+ (this.displayProp !== null && other.displayProp !== null && this.displayProp.eq(other.displayProp)))
125
121
  && this.widthProp === other.widthProp
126
122
  && this.typeProp === other.typeProp
127
123
  && this._cachedPins === other._cachedPins
128
124
  && this._cachedParams === other._cachedParams;
129
125
  }
130
126
  clone() {
131
- const component = new ClassComponent(this.instanceName, this.numPins, this.className);
127
+ const component = new ClassComponent(this.instanceName, this.numPins);
132
128
  component._copyID = this._copyID;
133
129
  component.arrangeProps = this.arrangeProps;
134
130
  component.widthProp = this.widthProp;
@@ -136,17 +132,12 @@ export class ClassComponent {
136
132
  component.angleProp = this.angleProp;
137
133
  component.followWireOrientationProp = this.followWireOrientationProp;
138
134
  component.useWireOrientationAngle = this.useWireOrientationAngle;
139
- if (this.displayProp) {
140
- if (typeof this.displayProp === "string") {
141
- component.displayProp = this.displayProp;
142
- }
143
- else if (this.displayProp instanceof SymbolDrawingCommands) {
144
- component.displayProp =
145
- this.displayProp.clone();
146
- }
135
+ if (this.displayProp instanceof SymbolDrawingCommands) {
136
+ component.displayProp =
137
+ this.displayProp.clone();
147
138
  }
148
139
  for (const [key, value] of this.parameters) {
149
- if (key === 'flipX' || key === 'flipY' || key === 'angle') {
140
+ if (key === ParamKeys.flipX || key === ParamKeys.flipY || key === ParamKeys.angle) {
150
141
  continue;
151
142
  }
152
143
  component.parameters.set(key, value);
@@ -154,10 +145,14 @@ export class ClassComponent {
154
145
  for (const [key, value] of this.pins) {
155
146
  component.pins.set(key, value);
156
147
  }
157
- for (const key in this.styles) {
158
- component.styles[key] = this.styles[key];
159
- }
160
148
  component.refreshCache();
161
149
  return component;
162
150
  }
163
151
  }
152
+ export class ModuleComponent extends ClassComponent {
153
+ moduleContainsExpressions;
154
+ moduleCounter = 0;
155
+ moduleExecutionContext;
156
+ moduleExecutionContextName;
157
+ modulePinIdToPortMap;
158
+ }
@@ -46,10 +46,7 @@ export class ExecutionScope {
46
46
  }
47
47
  getNet(component, pin) {
48
48
  const result = this.findNet(component, pin);
49
- if (result) {
50
- return result[2];
51
- }
52
- return null;
49
+ return result ? result[2] : null;
53
50
  }
54
51
  setNet(component, pin, net) {
55
52
  const pair = this.findNet(component, pin);
@@ -112,6 +109,15 @@ export class ExecutionScope {
112
109
  this.currentWireId = -1;
113
110
  this.currentFrameId = -1;
114
111
  }
112
+ setCurrent(component, pin = null) {
113
+ this.currentComponent = component;
114
+ if (component !== null) {
115
+ this.currentPin = (pin === null) ? component.getDefaultPin() : pin;
116
+ }
117
+ else {
118
+ this.currentPin = null;
119
+ }
120
+ }
115
121
  }
116
122
  export var SequenceAction;
117
123
  (function (SequenceAction) {
@@ -1,8 +1,9 @@
1
+ import { FrameType } from "../globals.mjs";
1
2
  export class Frame {
2
3
  parameters = new Map();
3
4
  frameId;
4
5
  frameType;
5
- constructor(frameId, frameType) {
6
+ constructor(frameId, frameType = FrameType.Frame) {
6
7
  this.frameId = frameId;
7
8
  this.frameType = frameType;
8
9
  }
@@ -1,3 +1,5 @@
1
+ import { getNumberExponential, getNumberExponentialText, resolveToNumericValue } from "../utils";
2
+ import { Big } from 'big.js';
1
3
  export class ParamDefinition {
2
4
  paramName;
3
5
  paramValue;
@@ -8,8 +10,26 @@ export class ParamDefinition {
8
10
  }
9
11
  export class NumericValue {
10
12
  value;
11
- constructor(value) {
13
+ valuePart;
14
+ prefixPart;
15
+ constructor(value, prefix = 0) {
12
16
  this.value = value;
17
+ if (typeof value === 'string') {
18
+ const matches = value.match(/^([\d]+(?:.[\d]+)?)([\w]*)$/);
19
+ if (matches) {
20
+ this.valuePart = new Big(matches[1]);
21
+ this.prefixPart = getNumberExponential(matches[2]);
22
+ }
23
+ else {
24
+ throw new Error("Invalid numeric value: " + value);
25
+ }
26
+ }
27
+ else {
28
+ this.valuePart = new Big(value);
29
+ this.prefixPart = prefix;
30
+ this.value = this.valuePart.toString()
31
+ + getNumberExponentialText(prefix);
32
+ }
13
33
  }
14
34
  toString() {
15
35
  return 'numeric:' + this.value;
@@ -18,11 +38,57 @@ export class NumericValue {
18
38
  if (typeof this.value === 'number') {
19
39
  return this.value.toString();
20
40
  }
21
- else if (typeof this.value === 'string') {
22
- return this.value;
41
+ else {
42
+ return this.valuePart.toString()
43
+ + getNumberExponentialText(this.prefixPart);
44
+ }
45
+ }
46
+ toNumber() {
47
+ return this.toBigNumber().toNumber();
48
+ }
49
+ toBigNumber() {
50
+ return this.valuePart.mul(new Big(Math.pow(10, this.prefixPart)));
51
+ }
52
+ div(value) {
53
+ if (typeof value === 'number') {
54
+ value = numeric(value);
55
+ }
56
+ return resolveToNumericValue(this.toBigNumber().div(value.toBigNumber()));
57
+ }
58
+ mul(value) {
59
+ if (typeof value === 'number') {
60
+ value = numeric(value);
23
61
  }
62
+ return resolveToNumericValue(this.toBigNumber().mul(value.toBigNumber()));
63
+ }
64
+ add(value) {
65
+ if (typeof value === 'number') {
66
+ value = numeric(value);
67
+ }
68
+ return resolveToNumericValue(this.toBigNumber().add(value.toBigNumber()));
69
+ }
70
+ sub(value) {
71
+ if (typeof value === 'number') {
72
+ value = numeric(value);
73
+ }
74
+ return resolveToNumericValue(this.toBigNumber().sub(value.toBigNumber()));
75
+ }
76
+ mod(value) {
77
+ if (typeof value === 'number') {
78
+ value = numeric(value);
79
+ }
80
+ return resolveToNumericValue(this.toBigNumber().mod(value.toBigNumber()));
81
+ }
82
+ neg() {
83
+ return resolveToNumericValue(this.toBigNumber().neg());
84
+ }
85
+ eq(value) {
86
+ return this.toBigNumber().eq(value.toBigNumber());
24
87
  }
25
88
  }
89
+ export function numeric(value) {
90
+ return new NumericValue(value);
91
+ }
26
92
  export class PercentageValue {
27
93
  value;
28
94
  constructor(value) {
@@ -31,4 +97,54 @@ export class PercentageValue {
31
97
  toString() {
32
98
  return this.value.toString();
33
99
  }
100
+ toNumber() {
101
+ return 0;
102
+ }
103
+ }
104
+ export class WrappedNumber {
105
+ value;
106
+ constructor(value) {
107
+ this.value = value;
108
+ }
109
+ toString() {
110
+ return this.value.toString();
111
+ }
112
+ toNumber() {
113
+ return this.value;
114
+ }
115
+ }
116
+ export class NumberOperator {
117
+ prepare(value) {
118
+ if (typeof value === 'number') {
119
+ return new WrappedNumber(value);
120
+ }
121
+ else {
122
+ return value;
123
+ }
124
+ }
125
+ multiply(value1, value2) {
126
+ const big1 = new Big(value1.toNumber());
127
+ const big2 = new Big(value2.toNumber());
128
+ return resolveToNumericValue(big1.mul(big2));
129
+ }
130
+ divide(value1, value2) {
131
+ const big1 = new Big(value1.toNumber());
132
+ const big2 = new Big(value2.toNumber());
133
+ return resolveToNumericValue(big1.div(big2));
134
+ }
135
+ addition(value1, value2) {
136
+ const big1 = new Big(value1.toNumber());
137
+ const big2 = new Big(value2.toNumber());
138
+ return resolveToNumericValue(big1.add(big2));
139
+ }
140
+ subtraction(value1, value2) {
141
+ const big1 = new Big(value1.toNumber());
142
+ const big2 = new Big(value2.toNumber());
143
+ return resolveToNumericValue(big1.sub(big2));
144
+ }
145
+ modulus(value1, value2) {
146
+ const big1 = new Big(value1.toNumber());
147
+ const big2 = new Big(value2.toNumber());
148
+ return resolveToNumericValue(big1.mod(big2));
149
+ }
34
150
  }
@@ -27,5 +27,3 @@ export var PortSide;
27
27
  PortSide["SOUTH"] = "SOUTH";
28
28
  PortSide["NORTH"] = "NORTH";
29
29
  })(PortSide || (PortSide = {}));
30
- export class PinReference {
31
- }
@@ -1,10 +1,10 @@
1
1
  import { SVG, registerWindow } from '@svgdotjs/svg.js';
2
2
  import { ExtractDrawingRects, RenderFrameType, getBounds } from "./layout.mjs";
3
3
  import { applyFontsToSVG, getCreateSVGWindow } from './sizing.mjs';
4
- import { ColorScheme, ComponentTypes, FrameType, MMToPt, MMToPx, ParamKeys, RenderFlags, defaultFont, defaultGridSizeUnits, defaultPageSpacingMM, defaultWireLineWidth, fontDisplayScale, junctionSize } from './globals.mjs';
4
+ import { ColorScheme, ComponentTypes, FrameType, MMToPt, MMToPx, ParamKeys, RenderFlags, defaultGridSizeUnits, defaultPageSpacingMM, defaultWireLineWidth, fontDisplayScale, junctionSize } from './globals.mjs';
5
5
  import { NumericValue } from './objects/ParamDefinition.mjs';
6
6
  import { combineMaps, getBoundsSize } from './utils.mjs';
7
- import { getPaperSize, milsToMM, PaperGridReferences } from './helpers.mjs';
7
+ import { getPaperSize, milsToMM } from './helpers.mjs';
8
8
  import SVGtoPDF from 'svg-to-pdfkit';
9
9
  import { FrameParamKeys } from './objects/Frame.mjs';
10
10
  import { SymbolPlaceholder } from './draw_symbols.mjs';
@@ -16,11 +16,12 @@ function createSvgCanvas() {
16
16
  applyFontsToSVG(canvas);
17
17
  return canvas;
18
18
  }
19
- export function renderSheetsToSVG(sheetFrames) {
19
+ export function renderSheetsToSVG(sheetFrames, logger) {
20
20
  const canvas = createSvgCanvas();
21
21
  sheetFrames.forEach((sheet, index) => {
22
22
  const sheetGroup = canvas.group();
23
- sheetGroup.id('sheet-' + index);
23
+ sheetGroup.id('sheet-' + index).addClass('sheet');
24
+ logger.add('rendering sheet: sheet-' + index);
24
25
  const { components, wires, junctions, mergedWires, frames, textObjects } = sheet;
25
26
  const allFrames = [sheet.frame, ...frames];
26
27
  let gridBounds = null;
@@ -29,6 +30,7 @@ export function renderSheetsToSVG(sheetFrames) {
29
30
  let yOffset = 0;
30
31
  let sheetYOffset = 0;
31
32
  if (sheet.frame.frame) {
33
+ logger.add('drawing frame');
32
34
  const frameComponent = sheet.frame.frame.parameters
33
35
  .get(FrameParamKeys.SheetType);
34
36
  if (frameComponent) {
@@ -41,15 +43,18 @@ export function renderSheetsToSVG(sheetFrames) {
41
43
  let widthMM = 0;
42
44
  let heightMM = 0;
43
45
  if (frameRects[0]) {
44
- originalWidthMM = milsToMM(frameRects[0].width);
45
- originalHeightMM = milsToMM(frameRects[0].height);
46
+ originalWidthMM = milsToMM(frameRects[0].width).toNumber();
47
+ originalHeightMM = milsToMM(frameRects[0].height).toNumber();
48
+ logger.add('first frame size: ' + originalWidthMM + ' ' + originalHeightMM);
46
49
  }
47
50
  if (frameRects[1]) {
48
- widthMM = milsToMM(frameRects[1].width);
49
- heightMM = milsToMM(frameRects[1].height);
51
+ widthMM = milsToMM(frameRects[1].width).toNumber();
52
+ heightMM = milsToMM(frameRects[1].height).toNumber();
53
+ logger.add('second frame size: ' + widthMM + ' ' + heightMM);
50
54
  }
51
55
  xOffset = (originalWidthMM - widthMM) / 2;
52
56
  yOffset = (originalHeightMM - heightMM) / 2;
57
+ logger.add('offset', xOffset, yOffset);
53
58
  sheetYOffset = index * (originalHeightMM + defaultPageSpacingMM);
54
59
  gridBounds = {
55
60
  xmin: 0,
@@ -60,8 +65,10 @@ export function renderSheetsToSVG(sheetFrames) {
60
65
  extendGrid = false;
61
66
  }
62
67
  }
63
- const sheetElements = sheetGroup.group();
64
- generateSVGChild(sheetElements, components, wires, junctions, mergedWires, allFrames, textObjects, gridBounds, extendGrid);
68
+ logger.add('sheet contents offset: ' + xOffset + ' ' + yOffset);
69
+ logger.add('generating svg children in sheet');
70
+ const sheetElements = sheetGroup.group().addClass('sheet-elements');
71
+ generateSVGChild(sheetElements, components, wires, junctions, mergedWires, allFrames, textObjects, gridBounds, extendGrid, logger);
65
72
  sheetElements.translate(xOffset, yOffset);
66
73
  sheetGroup.translate(0, sheetYOffset);
67
74
  });
@@ -105,16 +112,18 @@ export function generatePdfOutput(doc, canvas, sheetSize, sheetSizeDefined, zoom
105
112
  }
106
113
  });
107
114
  }
108
- function generateSVGChild(canvas, components, wires, junctions, mergedWires, frameObjects, textObjects, gridBounds, extendGrid) {
115
+ function generateSVGChild(canvas, components, wires, junctions, mergedWires, frameObjects, textObjects, gridBounds, extendGrid, logger) {
109
116
  const displayWireId = false;
110
117
  if (gridBounds === null) {
118
+ logger.add('get grid bounds');
111
119
  gridBounds = getBounds(components, wires, junctions, frameObjects);
112
120
  }
113
- drawGrid(canvas.group().translate(0, 0), gridBounds, extendGrid);
121
+ logger.add('grid bounds', gridBounds.xmin, gridBounds.ymin, gridBounds.xmax, gridBounds.ymax);
122
+ drawGrid(canvas.group().translate(0, 0), gridBounds, extendGrid, logger);
114
123
  components.forEach(item => {
115
124
  const { x, y, width, height } = item;
116
125
  const symbolGroup = canvas.group();
117
- symbolGroup.translate(x, y);
126
+ symbolGroup.translate(x.toNumber(), y.toNumber());
118
127
  const { symbol = null } = item;
119
128
  if (symbol !== null && symbol) {
120
129
  const extra = {};
@@ -151,7 +160,7 @@ function generateSVGChild(canvas, components, wires, junctions, mergedWires, fra
151
160
  family: 'Arial',
152
161
  size: 50 * fontDisplayScale,
153
162
  })
154
- .translate(wire.x + 5, wire.y + 5);
163
+ .translate(wire.x.add(5).toNumber(), wire.y.add(5).toNumber());
155
164
  });
156
165
  }
157
166
  const mergedWireGroup = canvas.group();
@@ -185,7 +194,7 @@ function generateSVGChild(canvas, components, wires, junctions, mergedWires, fra
185
194
  drawSheetFrameBorder(frameGroup, item);
186
195
  }
187
196
  else {
188
- if (borderWidth > 0) {
197
+ if (borderWidth.toNumber() > 0) {
189
198
  if (item.type === RenderFrameType.Container) {
190
199
  strokeColor = '#111';
191
200
  }
@@ -197,24 +206,27 @@ function generateSVGChild(canvas, components, wires, junctions, mergedWires, fra
197
206
  }
198
207
  const tmpRect = frameGroup.rect(width, height)
199
208
  .fill('none')
200
- .stroke({ width: milsToMM(borderWidth), color: strokeColor });
201
- tmpRect.translate(item.x, item.y);
209
+ .stroke({
210
+ width: milsToMM(borderWidth).toNumber(),
211
+ color: strokeColor
212
+ });
213
+ tmpRect.translate(item.x.toNumber(), item.y.toNumber());
202
214
  }
203
215
  }
204
216
  });
205
217
  textObjects.forEach(item => {
206
218
  const { x, y, symbol } = item;
207
219
  const innerGroup = canvas.group();
208
- innerGroup.translate(x, y);
220
+ innerGroup.translate(x.toNumber(), y.toNumber());
209
221
  symbol.draw(innerGroup);
210
222
  });
211
- const originSize = milsToMM(10);
223
+ const originSize = milsToMM(10).toNumber();
212
224
  RenderFlags.ShowOrigin && canvas.group().translate(0, 0)
213
225
  .circle(originSize)
214
226
  .translate(-originSize / 2, -originSize / 2)
215
227
  .stroke('none').fill('red');
216
228
  }
217
- function drawGrid(group, canvasSize, extendGrid) {
229
+ function drawGrid(group, canvasSize, extendGrid, logger) {
218
230
  const gridSize = defaultGridSizeUnits;
219
231
  const { xmin, ymin, xmax, ymax } = canvasSize;
220
232
  const extraValue = extendGrid ? 1 : 0;
@@ -228,8 +240,12 @@ function drawGrid(group, canvasSize, extendGrid) {
228
240
  : (ymax - ymin);
229
241
  const numCols = Math.floor((gridEndX - gridStartX) / gridSize)
230
242
  + (extendGrid ? 1 : 0);
243
+ const originSize = milsToMM(10).toNumber();
244
+ RenderFlags.ShowGridOrigin && group.circle(originSize)
245
+ .translate(-originSize / 2, -originSize / 2)
246
+ .stroke('none').fill('blue');
231
247
  const lines = [];
232
- const smallOffset = milsToMM(3);
248
+ const smallOffset = milsToMM(3).toNumber();
233
249
  const startY = gridStartY - smallOffset / 2;
234
250
  const endY = gridEndY + smallOffset;
235
251
  for (let i = 0; i < numCols; i++) {
@@ -237,12 +253,13 @@ function drawGrid(group, canvasSize, extendGrid) {
237
253
  lines.push(`M ${startX} ${startY} L ${startX} ${endY}`);
238
254
  }
239
255
  const strokeSize = milsToMM(3);
240
- group.path(lines.join(" "))
256
+ group.addClass('grid')
257
+ .path(lines.join(" "))
241
258
  .attr({
242
- 'stroke-dasharray': `${strokeSize},${gridSize - strokeSize}`,
259
+ 'stroke-dasharray': `${strokeSize.toNumber()},${gridSize - strokeSize.toNumber()}`,
243
260
  })
244
261
  .stroke({
245
- width: strokeSize,
262
+ width: strokeSize.toNumber(),
246
263
  color: '#000'
247
264
  });
248
265
  }
@@ -259,94 +276,7 @@ function drawSheetFrameBorder(frameGroup, frame) {
259
276
  symbol.draw(sheetFrameGroup);
260
277
  const offsetX = milsToMM(frameComponent.getParam('offset_x'));
261
278
  const offsetY = milsToMM(frameComponent.getParam('offset_y'));
262
- sheetFrameGroup.translate(-offsetX, -offsetY);
263
- }
264
- }
265
- }
266
- function drawSheetFrameBorderDirect(frameGroup, frame, borderWidth, strokeColor, width, height) {
267
- const commonStroke = {
268
- width: milsToMM(borderWidth),
269
- color: strokeColor
270
- };
271
- const commonFont = {
272
- family: defaultFont,
273
- size: 50 * fontDisplayScale,
274
- 'dominant-baseline': 'middle',
275
- 'text-anchor': 'middle',
276
- };
277
- let rows = 1;
278
- let columns = 1;
279
- let showGridReference = true;
280
- if (PaperGridReferences[frame.size]) {
281
- [rows, columns] = PaperGridReferences[frame.size];
282
- }
283
- else {
284
- showGridReference = false;
285
- }
286
- if (!showGridReference) {
287
- return;
288
- }
289
- const outerMargin = 2;
290
- const outerWidth = width + outerMargin * 2;
291
- const outerHeight = height + outerMargin * 2;
292
- const outerRect = frameGroup.rect(outerWidth, outerHeight)
293
- .fill('none')
294
- .stroke(commonStroke);
295
- outerRect.translate(frame.x - outerMargin, frame.y - outerMargin);
296
- const gridWidth = outerWidth / columns;
297
- const gridHeight = outerHeight / rows;
298
- const pathPoints = [];
299
- for (let i = 1; i < rows + 1; i++) {
300
- const lineStartX = frame.x - outerMargin;
301
- const lineStartX2 = frame.x - outerMargin + outerWidth - outerMargin;
302
- const lineY = frame.y - outerMargin + (gridHeight * i);
303
- if (i < rows) {
304
- pathPoints.push(...[
305
- "M", lineStartX, lineY, "L", lineStartX + outerMargin, lineY,
306
- "M", lineStartX2, lineY, "L", lineStartX2 + outerMargin, lineY
307
- ]);
279
+ sheetFrameGroup.translate(-offsetX.toNumber(), -offsetY.toNumber());
308
280
  }
309
- const displayValue = String.fromCharCode(i + 64);
310
- frameGroup.text(displayValue)
311
- .font(commonFont)
312
- .translate(lineStartX + outerMargin / 2, lineY - gridHeight / 2);
313
- frameGroup.text(displayValue)
314
- .font(commonFont)
315
- .translate(lineStartX2 + outerMargin / 2, lineY - gridHeight / 2);
316
- }
317
- for (let i = 1; i < columns + 1; i++) {
318
- const lineStartY = frame.y - outerMargin;
319
- const lineStartY2 = frame.y - outerMargin + outerHeight - outerMargin;
320
- const lineX = frame.x - outerMargin + (gridWidth * i);
321
- if (i < columns) {
322
- pathPoints.push(...[
323
- "M", lineX, lineStartY, "L", lineX, lineStartY + outerMargin,
324
- "M", lineX, lineStartY2, "L", lineX, lineStartY2 + outerMargin
325
- ]);
326
- }
327
- frameGroup.text(i.toString())
328
- .font(commonFont)
329
- .translate(lineX - gridWidth / 2, lineStartY + outerMargin / 2 + milsToMM(10));
330
- frameGroup.text(i.toString())
331
- .font(commonFont)
332
- .translate(lineX - gridWidth / 2, lineStartY2 + outerMargin / 2 + milsToMM(10));
333
- }
334
- frameGroup.path(pathPoints).stroke(commonStroke);
335
- const titleWidth = milsToMM(3000);
336
- const titleHeight = milsToMM(1000);
337
- const rowHeight = milsToMM(200);
338
- const points = [
339
- "M", width - titleWidth, height,
340
- "L", width - titleWidth, height - titleHeight,
341
- "L", width, height - titleHeight,
342
- "M", width - titleWidth, height - rowHeight,
343
- "L", width, height - rowHeight,
344
- "M", width - titleWidth, height - rowHeight * 2,
345
- "L", width, height - rowHeight * 2,
346
- "M", width - titleWidth, height - rowHeight * 3,
347
- "L", width, height - rowHeight * 3
348
- ];
349
- frameGroup.path(points).stroke(commonStroke).fill('none');
350
- if (frame.containsTitle) {
351
281
  }
352
282
  }
@@ -1,5 +1,5 @@
1
1
  import { SVG, registerWindow } from '@svgdotjs/svg.js';
2
- import { HorizontalAlign, VerticalAlign } from './geometry.mjs';
2
+ import { HorizontalAlign, HorizontalAlignProp, VerticalAlign, VerticalAlignProp } from './geometry.mjs';
3
3
  import { defaultFont } from './globals.mjs';
4
4
  import { JSModuleType, detectJSModuleType } from './helpers.mjs';
5
5
  let MainCanvas = null;
@@ -38,27 +38,53 @@ export function measureTextSize2(text, fontFamily, fontSize, fontWeight = 'regul
38
38
  }
39
39
  const key = `${text}-${fontFamily}-${fontSize}-${fontWeight}-${anchor}-${vanchor}`;
40
40
  if (measureTextSizeCache[key] === undefined) {
41
- let dominantBaseline = 'hanging';
41
+ let dominantBaseline = VerticalAlignProp.Hanging;
42
42
  switch (vanchor) {
43
43
  case VerticalAlign.Top:
44
- dominantBaseline = 'hanging';
44
+ dominantBaseline = VerticalAlignProp.Hanging;
45
45
  break;
46
46
  case VerticalAlign.Middle:
47
- dominantBaseline = 'middle';
47
+ dominantBaseline = VerticalAlignProp.Central;
48
48
  break;
49
49
  case VerticalAlign.Bottom:
50
- dominantBaseline = 'text-top';
50
+ dominantBaseline = VerticalAlignProp.TextTop;
51
+ break;
52
+ }
53
+ let useAnchor = HorizontalAlignProp.Start;
54
+ switch (anchor) {
55
+ case HorizontalAlign.Left:
56
+ useAnchor = HorizontalAlignProp.Start;
57
+ break;
58
+ case HorizontalAlign.Middle:
59
+ useAnchor = HorizontalAlignProp.Middle;
60
+ break;
61
+ case HorizontalAlign.Right:
62
+ useAnchor = HorizontalAlignProp.End;
51
63
  break;
52
64
  }
53
65
  fontFamily = defaultFont;
54
66
  const tmpTextElement = MainCanvas.text(text).font({
55
67
  family: fontFamily,
56
68
  size: fontSize,
57
- anchor: anchor,
69
+ anchor: useAnchor,
58
70
  'dominant-baseline': dominantBaseline,
59
71
  weight: fontWeight,
60
- }).fill('#333');
61
- const textbox = tmpTextElement.bbox();
72
+ })
73
+ .attr("xml:space", "preserve")
74
+ .fill('#333');
75
+ let textbox = tmpTextElement.bbox();
76
+ const tmpTextBox = { ...textbox };
77
+ if (dominantBaseline === VerticalAlignProp.Hanging) {
78
+ tmpTextBox.y = textbox.cy - textbox.height;
79
+ tmpTextBox.y2 = tmpTextBox.y + textbox.height;
80
+ textbox = tmpTextBox;
81
+ }
82
+ else if (dominantBaseline === VerticalAlignProp.Central) {
83
+ tmpTextBox.y -= textbox.cy;
84
+ tmpTextBox.y2 -= textbox.cy;
85
+ tmpTextBox.cy = 0;
86
+ textbox = tmpTextBox;
87
+ }
62
88
  const { width, height } = textbox;
63
89
  tmpTextElement.remove();
64
90
  measureTextSizeCache[key] = {