@design-core/core 51.1.0 → 52.0.0

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 (51) hide show
  1. package/.github/workflows/publish.yml +40 -0
  2. package/README.md +14 -1
  3. package/core/dimensions/alignedDimension.js +3 -1
  4. package/core/dimensions/angularDimension.js +118 -36
  5. package/core/dimensions/circularDimensionBase.js +32 -12
  6. package/core/dimensions/diametricDimension.js +29 -1
  7. package/core/dimensions/dimension.js +58 -5
  8. package/core/dimensions/dimensionBase.js +107 -4
  9. package/core/dimensions/linearDimensionBase.js +75 -37
  10. package/core/dimensions/radialDimension.js +26 -1
  11. package/core/dimensions/rotatedDimension.js +6 -3
  12. package/core/entities/entity.js +9 -0
  13. package/core/lib/auxiliary/snapPoint.js +9 -0
  14. package/core/lib/canvas.js +26 -1
  15. package/core/lib/commandManager.js +9 -4
  16. package/core/lib/dxf/dxf.js +8 -2
  17. package/core/lib/inputManager.js +24 -3
  18. package/core/lib/mouse.js +10 -0
  19. package/core/lib/plotOptions.js +17 -0
  20. package/core/lib/renderers/pdfRenderer.js +17 -1
  21. package/core/lib/scene.js +2 -0
  22. package/core/lib/selectionManager.js +28 -0
  23. package/core/lib/strings.js +3 -0
  24. package/core/properties/dimType.js +14 -0
  25. package/core/properties/property.js +1 -0
  26. package/core/tables/dimStyle.js +32 -2
  27. package/core/tools/gripStretch.js +97 -0
  28. package/core/tools/offset.js +7 -1
  29. package/core/tools/tool.js +10 -0
  30. package/core/tools/windowPick.js +75 -0
  31. package/cspell.json +5 -0
  32. package/package.json +7 -2
  33. package/test/dimensions/alignedDimension.test.js +165 -0
  34. package/test/dimensions/angularDimension.test.js +149 -0
  35. package/test/dimensions/diametricDimension.test.js +76 -4
  36. package/test/dimensions/dimension.test.js +130 -0
  37. package/test/dimensions/dimensionBase.test.js +97 -4
  38. package/test/dimensions/radialDimension.test.js +33 -0
  39. package/test/dimensions/rotatedDimension.test.js +80 -0
  40. package/test/integration/exportIntegration.reference.dxf +3 -9
  41. package/test/integration/plotPageSizeIntegration.test.js +113 -0
  42. package/test/integration/userInputIntegration.reference.dxf +3 -9
  43. package/test/lib/inputManager.test.js +316 -1
  44. package/test/lib/plotOptions.test.js +58 -1
  45. package/test/lib/selectionManager.test.js +42 -0
  46. package/test/renderers/pdfRenderer.test.js +26 -0
  47. package/test/tables/dimstyle.test.js +32 -0
  48. package/test/tools/gripStretch.test.js +108 -0
  49. package/test/tools/offset.test.js +2 -0
  50. package/test/tools/tool.test.js +25 -0
  51. package/test/tools/windowPick.test.js +129 -0
@@ -0,0 +1,25 @@
1
+ import { Core } from '../../core/core/core.js';
2
+ import { DesignCore } from '../../core/designCore.js';
3
+ import { Tool } from '../../core/tools/tool.js';
4
+ import { jest } from '@jest/globals';
5
+
6
+ new Core();
7
+
8
+ afterEach(() => {
9
+ jest.restoreAllMocks();
10
+ });
11
+
12
+ test('Tool.cancel default delegates to inputManager.reset()', () => {
13
+ const tool = new Tool();
14
+ const resetSpy = jest.spyOn(DesignCore.Scene.inputManager, 'reset').mockImplementation(() => {});
15
+
16
+ tool.cancel();
17
+
18
+ expect(resetSpy).toHaveBeenCalledTimes(1);
19
+ });
20
+
21
+ test('Tool.preview and Tool.action are no-ops by default', () => {
22
+ const tool = new Tool();
23
+ expect(() => tool.preview()).not.toThrow();
24
+ expect(() => tool.action()).not.toThrow();
25
+ });
@@ -0,0 +1,129 @@
1
+ import { Core } from '../../core/core/core.js';
2
+ import { DesignCore } from '../../core/designCore.js';
3
+ import { Point } from '../../core/entities/point.js';
4
+ import { WindowPick } from '../../core/tools/windowPick.js';
5
+ import { expect, jest } from '@jest/globals';
6
+ import { withMockInput } from '../test-helpers/test-helpers.js';
7
+
8
+ const core = new Core();
9
+
10
+ // ─── register ────────────────────────────────────────────────────────────────
11
+
12
+ test('WindowPick.register returns correct command object', () => {
13
+ const reg = WindowPick.register();
14
+ expect(reg.command).toBe('WindowPick');
15
+ expect(reg.shortcut).toBeUndefined();
16
+ expect(reg.type).toBeUndefined();
17
+ });
18
+
19
+ // ─── execute ──────────────────────────────────────────────────────────────────
20
+
21
+ test('WindowPick.execute collects two points and calls executeCommand', async () => {
22
+ const executeCommandSpy = jest.fn();
23
+
24
+ await withMockInput(
25
+ core.scene,
26
+ [new Point(0, 0), new Point(10, 10)],
27
+ async () => {
28
+ const tool = new WindowPick();
29
+ await tool.execute();
30
+ },
31
+ { extraMethods: { executeCommand: executeCommandSpy } },
32
+ );
33
+
34
+ expect(executeCommandSpy).toHaveBeenCalled();
35
+ });
36
+
37
+ test('WindowPick.execute returns early when first point is undefined', async () => {
38
+ const executeCommandSpy = jest.fn();
39
+
40
+ await withMockInput(
41
+ core.scene,
42
+ [],
43
+ async () => {
44
+ const tool = new WindowPick();
45
+ await tool.execute();
46
+ },
47
+ { extraMethods: { executeCommand: executeCommandSpy } },
48
+ );
49
+
50
+ expect(executeCommandSpy).not.toHaveBeenCalled();
51
+ });
52
+
53
+ test('WindowPick.execute returns early when second point is undefined', async () => {
54
+ const executeCommandSpy = jest.fn();
55
+
56
+ await withMockInput(
57
+ core.scene,
58
+ [new Point(0, 0)],
59
+ async () => {
60
+ const tool = new WindowPick();
61
+ await tool.execute();
62
+ },
63
+ { extraMethods: { executeCommand: executeCommandSpy } },
64
+ );
65
+
66
+ expect(executeCommandSpy).not.toHaveBeenCalled();
67
+ });
68
+
69
+ test('WindowPick.execute stores the two collected points', async () => {
70
+ let capturedTool;
71
+ const executeCommandSpy = jest.fn();
72
+
73
+ await withMockInput(
74
+ core.scene,
75
+ [new Point(1, 2), new Point(30, 40)],
76
+ async () => {
77
+ capturedTool = new WindowPick();
78
+ await capturedTool.execute();
79
+ },
80
+ { extraMethods: { executeCommand: executeCommandSpy } },
81
+ );
82
+
83
+ expect(capturedTool.points).toHaveLength(2);
84
+ expect(capturedTool.points[0].x).toBe(1);
85
+ expect(capturedTool.points[0].y).toBe(2);
86
+ expect(capturedTool.points[1].x).toBe(30);
87
+ expect(capturedTool.points[1].y).toBe(40);
88
+ });
89
+
90
+ // ─── preview ──────────────────────────────────────────────────────────────────
91
+
92
+ test('WindowPick.preview with one point creates a rectangle polyline preview', () => {
93
+ const tool = new WindowPick();
94
+ tool.points.push(new Point(10, 10));
95
+
96
+ core.mouse.mouseMoved(50, 50);
97
+
98
+ const initialCount = DesignCore.Scene.previewEntities.count();
99
+
100
+ tool.preview();
101
+
102
+ expect(DesignCore.Scene.previewEntities.count()).toBe(initialCount + 1);
103
+
104
+ const tempItem = DesignCore.Scene.previewEntities.get(DesignCore.Scene.previewEntities.count() - 1);
105
+ expect(tempItem.type).toBe('Polyline');
106
+ expect(tempItem.points.length).toBe(4);
107
+ });
108
+
109
+ test('WindowPick.preview with no points does not create a preview', () => {
110
+ const tool = new WindowPick();
111
+
112
+ const initialCount = DesignCore.Scene.previewEntities.count();
113
+
114
+ tool.preview();
115
+
116
+ expect(DesignCore.Scene.previewEntities.count()).toBe(initialCount);
117
+ });
118
+
119
+ test('WindowPick.preview with two points does not create another preview', () => {
120
+ const tool = new WindowPick();
121
+ tool.points.push(new Point(0, 0));
122
+ tool.points.push(new Point(10, 10));
123
+
124
+ const initialCount = DesignCore.Scene.previewEntities.count();
125
+
126
+ tool.preview();
127
+
128
+ expect(DesignCore.Scene.previewEntities.count()).toBe(initialCount);
129
+ });