@design-core/core 0.0.6 → 0.0.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.
- package/.eslintrc.json +4 -0
- package/TODO.md +49 -6
- package/core/core/core.js +0 -3
- package/core/dimensions/alignedDimension.js +5 -4
- package/core/dimensions/angularDimension.js +6 -5
- package/core/dimensions/baseCircularDimension.js +3 -2
- package/core/dimensions/baseDimension.js +59 -93
- package/core/dimensions/baseLinearDimension.js +6 -5
- package/core/dimensions/diametricDimension.js +4 -3
- package/core/dimensions/dimension.js +21 -14
- package/core/dimensions/radialDimension.js +4 -3
- package/core/dimensions/rotatedDimension.js +12 -11
- package/core/entities/arc.js +112 -145
- package/core/entities/arctext.js +212 -174
- package/core/entities/basePolyline.js +30 -282
- package/core/entities/circle.js +77 -99
- package/core/entities/entity.js +114 -93
- package/core/entities/hatch.js +322 -249
- package/core/entities/insert.js +66 -81
- package/core/entities/line.js +21 -142
- package/core/entities/lwpolyline.js +16 -11
- package/core/entities/polyline.js +4 -4
- package/core/entities/rectangle.js +3 -1
- package/core/entities/solid.js +6 -15
- package/core/entities/text.js +188 -199
- package/core/lib/auxiliary/rubberBand.js +32 -0
- package/core/lib/auxiliary/selectionWindow.js +63 -0
- package/core/lib/auxiliary/snapPoint.js +113 -0
- package/core/lib/auxiliary/trackingLine.js +76 -0
- package/core/lib/canvas.js +228 -166
- package/core/lib/clipboard.js +7 -1
- package/core/lib/colour.js +16 -0
- package/core/lib/commandLine.js +1 -6
- package/core/lib/commandManager.js +18 -8
- package/core/lib/constants.js +28 -0
- package/core/lib/dxf/dxf.js +4 -3
- package/core/lib/entityManager.js +18 -11
- package/core/lib/inputManager.js +35 -11
- package/core/lib/intersect.js +25 -0
- package/core/lib/patterns.js +8 -1
- package/core/lib/plotOptions.js +67 -0
- package/core/lib/polylineUtils.js +75 -0
- package/core/lib/renderers/cairoRenderer.js +371 -0
- package/core/lib/renderers/canvasRenderer.js +315 -0
- package/core/lib/renderers/pdfRenderer.js +366 -0
- package/core/lib/renderers/rendererBase.js +284 -0
- package/core/lib/renderers/svgRenderer.js +343 -0
- package/core/lib/scene.js +27 -5
- package/core/lib/selectionManager.js +2 -2
- package/core/lib/settings.js +4 -2
- package/core/lib/snapping.js +4 -191
- package/core/lib/stateManager.js +30 -1
- package/core/lib/utils.js +21 -2
- package/core/properties/entityProperties.js +104 -0
- package/core/properties/property.js +106 -2
- package/core/properties/propertyManager.js +29 -13
- package/core/tables/block.js +4 -37
- package/core/tables/endblk.js +1 -1
- package/core/tables/layer.js +8 -0
- package/core/tables/styleManagerBase.js +3 -2
- package/core/tables/tableManagerBase.js +8 -3
- package/core/tools/chamfer.js +111 -137
- package/core/tools/chamferFilletBase.js +135 -34
- package/core/tools/copy.js +3 -3
- package/core/tools/explode.js +2 -2
- package/core/tools/extend.js +132 -19
- package/core/tools/fillet.js +86 -183
- package/core/tools/matchProp.js +2 -11
- package/core/tools/mirror.js +7 -6
- package/core/tools/move.js +3 -3
- package/core/tools/offset.js +3 -5
- package/core/tools/pasteclip.js +1 -1
- package/core/tools/rotate.js +6 -3
- package/core/tools/scale.js +1 -1
- package/core/tools/trim.js +265 -23
- package/core/tools/zoom.js +1 -1
- package/jest.config.js +6 -0
- package/package.json +5 -3
- package/test/dimensions/alignedDimension.test.js +14 -7
- package/test/dimensions/angularDimension.test.js +6 -6
- package/test/dimensions/baseDimension.test.js +69 -8
- package/test/dimensions/baseLinearDimension.test.js +62 -0
- package/test/dimensions/diametricDimension.test.js +6 -6
- package/test/dimensions/radialDimension.test.js +6 -6
- package/test/dimensions/rotatedDimension.test.js +14 -7
- package/test/entities/arc.test.js +80 -83
- package/test/entities/arctext.test.js +180 -53
- package/test/entities/basePolyline.test.js +68 -2
- package/test/entities/circle.test.js +57 -85
- package/test/entities/entity.test.js +42 -8
- package/test/entities/hatch.test.js +543 -70
- package/test/entities/insert.test.js +96 -1
- package/test/entities/line.test.js +15 -41
- package/test/entities/lwpolyline.test.js +104 -0
- package/test/entities/polyline.test.js +11 -0
- package/test/entities/rectangle.test.js +11 -0
- package/test/entities/solid.test.js +1 -1
- package/test/entities/text.test.js +294 -69
- package/test/integration/exportIntegration.reference.dxf +9 -9
- package/test/integration/exportIntegration.test.js +2 -2
- package/test/integration/intersectionIntegration.test.js +4 -5
- package/test/integration/pdfRendererIntegration.reference.pdf +17709 -0
- package/test/integration/pdfRendererIntegration.test.js +61 -0
- package/test/integration/svgRendererIntegration.reference.svg +3343 -0
- package/test/integration/svgRendererIntegration.test.js +61 -0
- package/test/integration/userInputIntegration.reference.dxf +1165 -105
- package/test/integration/userInputIntegration.test.js +239 -132
- package/test/lib/canvas.test.js +742 -123
- package/test/lib/constants.test.js +27 -0
- package/test/lib/entityManager.test.js +4 -4
- package/test/lib/inputManager.test.js +80 -19
- package/test/lib/intersect.test.js +83 -0
- package/test/lib/plotOptions.test.js +179 -0
- package/test/lib/rubberBand.test.js +84 -0
- package/test/lib/settings.test.js +5 -6
- package/test/lib/snapping.test.js +71 -129
- package/test/lib/stateManager.test.js +7 -7
- package/test/lib/utils.test.js +36 -2
- package/test/properties/entityProperties.test.js +132 -0
- package/test/properties/property.test.js +53 -0
- package/test/properties/propertyManager.test.js +3 -3
- package/test/renderers/canvasRenderer.test.js +317 -0
- package/test/renderers/pdfRenderer.test.js +271 -0
- package/test/renderers/rendererBase.test.js +213 -0
- package/test/renderers/svgRenderer.test.js +326 -0
- package/test/tables/block.test.js +31 -1
- package/test/tables/endblk.test.js +2 -2
- package/test/tables/layer.test.js +30 -0
- package/test/test-helpers/hatchGridRenderer.js +180 -0
- package/test/test-helpers/test-helpers.js +152 -0
- package/test/tools/chamfer.test.js +227 -5
- package/test/tools/chamferFilletBase.test.js +98 -9
- package/test/tools/copy.test.js +2 -2
- package/test/tools/explode.test.js +3 -3
- package/test/tools/extend.test.js +331 -0
- package/test/tools/fillet.test.js +181 -0
- package/test/tools/matchProp.test.js +5 -5
- package/test/tools/mirror.test.js +13 -13
- package/test/tools/offset.test.js +170 -3
- package/test/tools/pasteclip.test.js +5 -5
- package/test/tools/rotate.test.js +32 -2
- package/test/tools/scale.test.js +5 -5
- package/test/tools/trim.test.js +526 -0
- package/test/tools/zoom.test.js +7 -7
- package/core/lib/selectionWindow.js +0 -83
package/.eslintrc.json
CHANGED
|
@@ -9,10 +9,14 @@
|
|
|
9
9
|
"ecmaVersion": "latest",
|
|
10
10
|
"sourceType": "module"
|
|
11
11
|
},
|
|
12
|
+
"plugins": [
|
|
13
|
+
"import"
|
|
14
|
+
],
|
|
12
15
|
"rules": {
|
|
13
16
|
"require-jsdoc": 2,
|
|
14
17
|
"valid-jsdoc": 2,
|
|
15
18
|
"max-len": 0,
|
|
19
|
+
"import/first": "error",
|
|
16
20
|
"function-paren-newline": "warn",
|
|
17
21
|
"object-curly-spacing": [
|
|
18
22
|
"error",
|
package/TODO.md
CHANGED
|
@@ -1,12 +1,6 @@
|
|
|
1
1
|
# Design-Core TODO list
|
|
2
2
|
|
|
3
3
|
## Beta
|
|
4
|
-
### UNDO / REDO
|
|
5
|
-
|
|
6
|
-
### Printing
|
|
7
|
-
|
|
8
|
-
### Export PDF
|
|
9
|
-
|
|
10
4
|
### Paperspace
|
|
11
5
|
|
|
12
6
|
### Entity Editing
|
|
@@ -17,3 +11,52 @@
|
|
|
17
11
|
- Radial Dimension
|
|
18
12
|
- Diametric Dimension
|
|
19
13
|
|
|
14
|
+
### Text sizing
|
|
15
|
+
- Text size - need a non-hacky glyph-advance measuring API on each the renderer
|
|
16
|
+
- ArcAlignedText characterSpacing=0 overlap — Cairo's cap-height correction scales glyph advances wider than getApproximateWidth predicts;
|
|
17
|
+
|
|
18
|
+
### performance optimisation
|
|
19
|
+
|
|
20
|
+
#### 1. `LType.getPattern(scale)` — cache the scaled array (easy)
|
|
21
|
+
Called once per entity per frame. Currently allocates a new array every call via `.map()`.
|
|
22
|
+
A two-field cache (`#lastScale`, `#cachedPattern`) returns the existing array when scale hasn't changed.
|
|
23
|
+
|
|
24
|
+
- **Effort**: ~10 lines, isolated to `ltype.js`
|
|
25
|
+
- **Expected gain**: small but consistent; removes N allocations per frame where N = entity count
|
|
26
|
+
|
|
27
|
+
#### 2. State dedup in renderers — skip no-op `setColour`/`setLineWidth`/`setDash` calls (medium)
|
|
28
|
+
`setContext` is called unconditionally for every entity. For entities sharing colour and line width (the common case), the underlying Canvas/Cairo API calls are redundant.
|
|
29
|
+
Track the last-set value in each renderer and return early when unchanged.
|
|
30
|
+
|
|
31
|
+
- **Effort**: ~20 lines per renderer, self-contained
|
|
32
|
+
- **Expected gain**: meaningful for large scenes with many same-layer entities; could save 10–30% of state-setting overhead
|
|
33
|
+
|
|
34
|
+
#### 3. Skip `save()`/`restore()` for leaf entities (medium)
|
|
35
|
+
`#paintEntity` wraps every entity in `save()`/`restore()` even though only container entities (Insert, BaseDimension) actually change the transform. Requires an `entity.isContainer` flag or restructuring to save lazily.
|
|
36
|
+
|
|
37
|
+
- **Effort**: entity API change + `#paintEntity` refactor
|
|
38
|
+
- **Expected gain**: ~1 `save`/`restore` pair eliminated per leaf entity per frame; measurable at high entity counts
|
|
39
|
+
|
|
40
|
+
#### 4. Offscreen canvas for static scene (large, architectural)
|
|
41
|
+
The full scene repaints on every mouse move (hover detection, rubber band, cursor). Splitting into a static layer (repaint on data change only) and a dynamic overlay (hover, preview, selection) would eliminate most per-frame work.
|
|
42
|
+
|
|
43
|
+
- **Effort**: significant — touches `canvas.js`, rendering pipeline, and UI integration
|
|
44
|
+
- **Expected gain**: potentially 3–5× frame rate improvement during mouse movement over a complex scene
|
|
45
|
+
|
|
46
|
+
#### 5. Viewport culling — skip entities outside the visible area (medium, high impact when zoomed in)
|
|
47
|
+
Every entity already has `boundingBox()` and `canvas.getSceneOffset()` returns the visible scene rectangle.
|
|
48
|
+
A simple AABB overlap test in `#paintEntities` would skip entities outside the viewport before calling `#paintEntity`.
|
|
49
|
+
|
|
50
|
+
- **Effort**: ~10 lines in `#paintEntities`; call `getSceneOffset()` once per `paint()` and pass it in
|
|
51
|
+
|
|
52
|
+
- **Caveat — bounding box caching**: `Hatch.boundingBox()` and `Block.boundingBox()` iterate all child entities on every call. Per-frame culling cost could exceed draw cost for those types unless bboxes are cached on the entity and invalidated on edit. Simple entity types (Line, Circle, Arc) have trivial bbox cost and benefit immediately.
|
|
53
|
+
|
|
54
|
+
- **Caveat — Text**: `Text.boundingBox()` depends on `boundingRect` which is only populated after the first `draw()` call — needs a fallback to avoid incorrectly culling undrawn text.
|
|
55
|
+
|
|
56
|
+
- **Expected gain**: negligible when fully zoomed out; potentially 5–50× reduction in draw calls when working zoomed into a small area of a large drawing
|
|
57
|
+
|
|
58
|
+
### Test clean up
|
|
59
|
+
- Have the renderer changes provided any opportunity to clean up tests
|
|
60
|
+
- Is there opportunity for extended testing with the mock renderer
|
|
61
|
+
|
|
62
|
+
|
package/core/core/core.js
CHANGED
|
@@ -24,9 +24,6 @@ import { Logging } from '../lib/logging.js';
|
|
|
24
24
|
|
|
25
25
|
import { DesignCore } from '../designCore.js';
|
|
26
26
|
|
|
27
|
-
// re-export core components for external use
|
|
28
|
-
export { Patterns } from '../lib/patterns.js';
|
|
29
|
-
|
|
30
27
|
/** Class representing design core. This is the primary entry point */
|
|
31
28
|
export class Core {
|
|
32
29
|
/** Create a core object */
|
|
@@ -7,6 +7,7 @@ import { Point } from '../entities/point.js';
|
|
|
7
7
|
import { BaseLinearDimension } from './baseLinearDimension.js';
|
|
8
8
|
|
|
9
9
|
import { DesignCore } from '../designCore.js';
|
|
10
|
+
import { Property } from '../properties/property.js';
|
|
10
11
|
|
|
11
12
|
|
|
12
13
|
/**
|
|
@@ -42,7 +43,7 @@ export class AlignedDimension extends BaseLinearDimension {
|
|
|
42
43
|
async execute() {
|
|
43
44
|
try {
|
|
44
45
|
DesignCore.Scene.selectionManager.reset();
|
|
45
|
-
this.
|
|
46
|
+
this.setProperty(Property.Names.DIMENSIONSTYLE, DesignCore.DimStyleManager.getCstyle());
|
|
46
47
|
this.dimType.setDimType(1); // Aligned dimension
|
|
47
48
|
|
|
48
49
|
const op = new PromptOptions(Strings.Input.START, [Input.Type.POINT]);
|
|
@@ -118,10 +119,10 @@ export class AlignedDimension extends BaseLinearDimension {
|
|
|
118
119
|
const Pt14 = this.getPointBySequence(this.points, 14);
|
|
119
120
|
|
|
120
121
|
file.writeGroupCode('0', 'DIMENSION');
|
|
121
|
-
file.writeGroupCode('5', this.
|
|
122
|
+
file.writeGroupCode('5', this.getProperty(Property.Names.HANDLE), DXFFile.Version.R2000); // Handle
|
|
122
123
|
file.writeGroupCode('100', 'AcDbEntity', DXFFile.Version.R2000);
|
|
123
124
|
file.writeGroupCode('100', 'AcDbDimension', DXFFile.Version.R2000);
|
|
124
|
-
file.writeGroupCode('8', this.
|
|
125
|
+
file.writeGroupCode('8', this.getProperty(Property.Names.LAYER));
|
|
125
126
|
// file.writeGroupCode('2', this.blockName); // Block not required
|
|
126
127
|
file.writeGroupCode('10', Pt10.x); // X - definition / arrow point
|
|
127
128
|
file.writeGroupCode('20', Pt10.y); // Y
|
|
@@ -130,7 +131,7 @@ export class AlignedDimension extends BaseLinearDimension {
|
|
|
130
131
|
file.writeGroupCode('21', Pt11.y); // Y
|
|
131
132
|
file.writeGroupCode('31', '0.0'); // Z
|
|
132
133
|
file.writeGroupCode('70', this.dimType.getDimType()); // DIMENSION TYPE
|
|
133
|
-
file.writeGroupCode('3', this.
|
|
134
|
+
file.writeGroupCode('3', this.getProperty(Property.Names.DIMENSIONSTYLE)); // DIMENSION STYLE
|
|
134
135
|
file.writeGroupCode('100', 'AcDbAlignedDimension', DXFFile.Version.R2000);
|
|
135
136
|
file.writeGroupCode('13', Pt13.x); // X - start point of first extension line
|
|
136
137
|
file.writeGroupCode('23', Pt13.y); // Y
|
|
@@ -14,6 +14,7 @@ import { Point } from '../entities/point.js';
|
|
|
14
14
|
import { Text } from '../entities/text.js'; // used to debug the dimension points
|
|
15
15
|
|
|
16
16
|
import { DesignCore } from '../designCore.js';
|
|
17
|
+
import { Property } from '../properties/property.js';
|
|
17
18
|
|
|
18
19
|
/**
|
|
19
20
|
* Angular Dimension Entity Class
|
|
@@ -47,7 +48,7 @@ export class AngularDimension extends BaseDimension {
|
|
|
47
48
|
*/
|
|
48
49
|
async execute() {
|
|
49
50
|
try {
|
|
50
|
-
this.
|
|
51
|
+
this.setProperty(Property.Names.DIMENSIONSTYLE, DesignCore.DimStyleManager.getCstyle());
|
|
51
52
|
this.dimType.setDimType(2); // Angular dimension
|
|
52
53
|
|
|
53
54
|
let Pt10;
|
|
@@ -146,7 +147,7 @@ export class AngularDimension extends BaseDimension {
|
|
|
146
147
|
|
|
147
148
|
const points = AngularDimension.getPointsFromSelection([tempLineOne, tempLineTwo], Pt11);
|
|
148
149
|
|
|
149
|
-
DesignCore.Scene.
|
|
150
|
+
DesignCore.Scene.previewEntities.create(this.type, { points: points, dimensionStyle: this.getProperty(Property.Names.DIMENSIONSTYLE) });
|
|
150
151
|
}
|
|
151
152
|
}
|
|
152
153
|
|
|
@@ -520,10 +521,10 @@ export class AngularDimension extends BaseDimension {
|
|
|
520
521
|
const Pt16 = this.getPointBySequence(this.points, 16);
|
|
521
522
|
|
|
522
523
|
file.writeGroupCode('0', 'DIMENSION');
|
|
523
|
-
file.writeGroupCode('5', this.
|
|
524
|
+
file.writeGroupCode('5', this.getProperty(Property.Names.HANDLE), DXFFile.Version.R2000); // Handle
|
|
524
525
|
file.writeGroupCode('100', 'AcDbEntity', DXFFile.Version.R2000);
|
|
525
526
|
file.writeGroupCode('100', 'AcDbDimension', DXFFile.Version.R2000);
|
|
526
|
-
file.writeGroupCode('8', this.
|
|
527
|
+
file.writeGroupCode('8', this.getProperty(Property.Names.LAYER));
|
|
527
528
|
// file.writeGroupCode('2', this.blockName); // Block not required
|
|
528
529
|
file.writeGroupCode('10', Pt10.x); // X - Start of Dimension Line
|
|
529
530
|
file.writeGroupCode('20', Pt10.y); // Y
|
|
@@ -532,7 +533,7 @@ export class AngularDimension extends BaseDimension {
|
|
|
532
533
|
file.writeGroupCode('21', Pt11.y); // Y
|
|
533
534
|
file.writeGroupCode('31', '0.0'); // Z
|
|
534
535
|
file.writeGroupCode('70', this.dimType.getDimType()); // DIMENSION TYPE
|
|
535
|
-
file.writeGroupCode('3', this.
|
|
536
|
+
file.writeGroupCode('3', this.getProperty(Property.Names.DIMENSIONSTYLE)); // DIMENSION STYLE
|
|
536
537
|
file.writeGroupCode('100', 'AcDb2LineAngularDimension', DXFFile.Version.R2000);
|
|
537
538
|
file.writeGroupCode('13', Pt13.x); // X
|
|
538
539
|
file.writeGroupCode('23', Pt13.y); // Y
|
|
@@ -11,6 +11,7 @@ import { Logging } from '../lib/logging.js';
|
|
|
11
11
|
import { BaseDimension } from './baseDimension.js';
|
|
12
12
|
|
|
13
13
|
import { DesignCore } from '../designCore.js';
|
|
14
|
+
import { Property } from '../properties/property.js';
|
|
14
15
|
|
|
15
16
|
|
|
16
17
|
/**
|
|
@@ -32,7 +33,7 @@ export class BaseCircularDimension extends BaseDimension {
|
|
|
32
33
|
*/
|
|
33
34
|
async execute() {
|
|
34
35
|
try {
|
|
35
|
-
this.
|
|
36
|
+
this.setProperty(Property.Names.DIMENSIONSTYLE, DesignCore.DimStyleManager.getCstyle());
|
|
36
37
|
|
|
37
38
|
let Pt10;
|
|
38
39
|
let Pt15;
|
|
@@ -96,7 +97,7 @@ export class BaseCircularDimension extends BaseDimension {
|
|
|
96
97
|
const tempCircle = new Circle({ points: [Pt10, Pt15] });
|
|
97
98
|
const points = this.constructor.getPointsFromSelection([tempCircle], Pt11);
|
|
98
99
|
|
|
99
|
-
DesignCore.Scene.
|
|
100
|
+
DesignCore.Scene.previewEntities.create(this.type, { points: points });
|
|
100
101
|
}
|
|
101
102
|
}
|
|
102
103
|
|
|
@@ -24,91 +24,67 @@ export class BaseDimension extends Entity {
|
|
|
24
24
|
constructor(data) {
|
|
25
25
|
super(data);
|
|
26
26
|
|
|
27
|
-
//
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
27
|
+
// lineType and lineWidth not applicable to dimensions
|
|
28
|
+
this.properties.remove(Property.Names.LINETYPE);
|
|
29
|
+
this.properties.remove(Property.Names.LINEWIDTH);
|
|
30
|
+
|
|
31
|
+
// DXF Groupcode 1 - Dimension text override
|
|
32
|
+
this.properties.add(Property.Names.TEXTOVERRIDE, {
|
|
33
|
+
type: Property.Type.STRING,
|
|
34
|
+
value: Property.loadValue([data?.[1], data?.textOverride], ''),
|
|
35
|
+
dxfCode: 1,
|
|
31
36
|
});
|
|
32
37
|
|
|
33
|
-
//
|
|
34
|
-
|
|
35
|
-
|
|
38
|
+
// DXF Groupcode 2 - Block name
|
|
39
|
+
this.properties.add(Property.Names.BLOCKNAME, {
|
|
40
|
+
type: Property.Type.STRING,
|
|
41
|
+
value: Property.loadValue([data?.blockName, data?.[2]], ''),
|
|
42
|
+
dxfCode: 2,
|
|
43
|
+
visible: false,
|
|
36
44
|
});
|
|
37
45
|
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
Object.defineProperty(this, 'block', {
|
|
44
|
-
value: new Block({ points: [new Point(), new Point()] }),
|
|
45
|
-
writable: true,
|
|
46
|
-
});
|
|
47
|
-
|
|
48
|
-
/*
|
|
49
|
-
Object.defineProperty(this, 'text', {
|
|
50
|
-
value: new Text(),
|
|
51
|
-
writable: true,
|
|
46
|
+
// DXF Groupcode 3 - Dimension Style Name
|
|
47
|
+
this.properties.add(Property.Names.DIMENSIONSTYLE, {
|
|
48
|
+
type: Property.Type.LIST,
|
|
49
|
+
value: Property.loadValue([data?.dimensionStyle, data?.[3]], 'STANDARD'),
|
|
50
|
+
dxfCode: 3,
|
|
52
51
|
});
|
|
53
|
-
*/
|
|
54
52
|
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
53
|
+
// DXF Groupcode 40 - Leader length for radius and diameter dimensions
|
|
54
|
+
this.properties.add(Property.Names.LEADERLENGTH, {
|
|
55
|
+
type: Property.Type.NUMBER,
|
|
56
|
+
value: Property.loadValue([data?.[40], data?.leaderLength], 0),
|
|
57
|
+
dxfCode: 40,
|
|
58
|
+
visible: false,
|
|
59
59
|
});
|
|
60
60
|
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
61
|
+
// DXF Groupcode 50 - Angle of rotated, horizontal, or vertical dimensions
|
|
62
|
+
this.properties.add(Property.Names.LINEARDIMANGLE, {
|
|
63
|
+
type: Property.Type.NUMBER,
|
|
64
|
+
value: Property.loadValue([data?.[50], data?.linearDimAngle], 0),
|
|
65
|
+
dxfCode: 50,
|
|
66
|
+
visible: false,
|
|
64
67
|
});
|
|
65
68
|
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
69
|
+
// DXF Groupcode 53 - Rotation angle of dimension text away from default orientation
|
|
70
|
+
this.properties.add(Property.Names.ANGLE, {
|
|
71
|
+
type: Property.Type.NUMBER,
|
|
72
|
+
value: Property.loadValue([data?.[53], data?.angle], 0),
|
|
73
|
+
dxfCode: 53,
|
|
74
|
+
visible: false,
|
|
70
75
|
});
|
|
71
76
|
|
|
72
|
-
Object.defineProperty(this, '
|
|
73
|
-
value:
|
|
77
|
+
Object.defineProperty(this, 'block', {
|
|
78
|
+
value: new Block({ points: [new Point(), new Point()] }),
|
|
74
79
|
writable: true,
|
|
75
80
|
});
|
|
76
81
|
|
|
77
|
-
Object.defineProperty(this, '
|
|
78
|
-
value:
|
|
82
|
+
Object.defineProperty(this, 'dimType', {
|
|
83
|
+
value: new DimType(),
|
|
79
84
|
writable: true,
|
|
80
85
|
});
|
|
81
86
|
|
|
82
87
|
if (data) {
|
|
83
|
-
if (data.hasOwnProperty('1')) {
|
|
84
|
-
// DXF Groupcode 1 - Dimension text
|
|
85
|
-
// The string explicitly entered by the user.
|
|
86
|
-
// Optional; default is the measurement. If null or “<>”, the dimension measurement is drawn as the text,
|
|
87
|
-
// if ““ (one blank space), the text is suppressed. Anything else is drawn as the text
|
|
88
|
-
this.textOverride = Property.loadValue([data[1], data.textOverride], '');
|
|
89
|
-
}
|
|
90
|
-
|
|
91
|
-
/*
|
|
92
|
-
if (data.hasOwnProperty('block')) {
|
|
93
|
-
// Reference to block that contains the entities that make up this dimension
|
|
94
|
-
this.block = data.block;
|
|
95
|
-
}*/
|
|
96
|
-
|
|
97
|
-
if (data.hasOwnProperty('blockName') || data.hasOwnProperty('2')) {
|
|
98
|
-
// DXF Groupcode 2 - Blockname
|
|
99
|
-
this.blockName = Property.loadValue([data.blockName, data[2]], '');
|
|
100
|
-
}
|
|
101
|
-
|
|
102
|
-
if (data.hasOwnProperty('dimensionStyle') || data.hasOwnProperty('3')) {
|
|
103
|
-
// DXF Groupcode 3 - Dimension Style Name
|
|
104
|
-
this.dimensionStyle = Property.loadValue([data.dimensionStyle, data[3]], 'STANDARD');
|
|
105
|
-
}
|
|
106
|
-
|
|
107
|
-
if (data.hasOwnProperty('40')) {
|
|
108
|
-
// DXF Groupcode 40 - Leader length for radius and diameter dimensions
|
|
109
|
-
this.leaderLength = data[40];
|
|
110
|
-
}
|
|
111
|
-
|
|
112
88
|
if (data.hasOwnProperty('41')) {
|
|
113
89
|
// DXF Groupcode 41 - Line Spacing Factor
|
|
114
90
|
// Percentage of default (3-on-5) line spacing to be applied.
|
|
@@ -124,11 +100,6 @@ export class BaseDimension extends Entity {
|
|
|
124
100
|
Logging.instance.debug(`${this.type} - ${err}`);
|
|
125
101
|
}
|
|
126
102
|
|
|
127
|
-
if (data.hasOwnProperty('50')) {
|
|
128
|
-
// DXF Groupcode 50 - Angle of rotated, horizontal, or vertical dimensions
|
|
129
|
-
this.linearDimAngle = Property.loadValue([data[50]], 0);
|
|
130
|
-
}
|
|
131
|
-
|
|
132
103
|
if (data.hasOwnProperty('51')) {
|
|
133
104
|
// DXF Groupcode 51 - Horizontal Direction
|
|
134
105
|
// All dimension types have an optional 51 group code, which indicates the horizontal direction
|
|
@@ -140,12 +111,6 @@ export class BaseDimension extends Entity {
|
|
|
140
111
|
Logging.instance.warn(`${this.type} - ${err}`);
|
|
141
112
|
}
|
|
142
113
|
|
|
143
|
-
if (data.hasOwnProperty('angle') || data.hasOwnProperty('53')) {
|
|
144
|
-
// DXF Groupcode 53 - Rotation
|
|
145
|
-
// rotation angle of the dimension text away from its default orientation
|
|
146
|
-
this.angle = Property.loadValue([data.angle, data[53]], 0);
|
|
147
|
-
}
|
|
148
|
-
|
|
149
114
|
if (data.hasOwnProperty('dimType') || data.hasOwnProperty('70')) {
|
|
150
115
|
// DXF Groupcode 70 - Dimension Type
|
|
151
116
|
// Values 0-6 are integer values that represent the dimension type. Values 32, 64, and 128
|
|
@@ -197,10 +162,6 @@ export class BaseDimension extends Entity {
|
|
|
197
162
|
const err = 'Groupcode 72 not implemented';
|
|
198
163
|
Logging.instance.debug(`${this.type} - ${err}`);
|
|
199
164
|
}
|
|
200
|
-
|
|
201
|
-
if (data.leaderLength) {
|
|
202
|
-
this.leaderLength = data.leaderLength;
|
|
203
|
-
}
|
|
204
165
|
}
|
|
205
166
|
}
|
|
206
167
|
|
|
@@ -280,8 +241,9 @@ export class BaseDimension extends Entity {
|
|
|
280
241
|
}
|
|
281
242
|
|
|
282
243
|
// Handle textOverride
|
|
283
|
-
|
|
284
|
-
|
|
244
|
+
const textOverride = this.getProperty(Property.Names.TEXTOVERRIDE);
|
|
245
|
+
if (textOverride !== '') {
|
|
246
|
+
formattedDimensionValue = textOverride.replace(/<>/g, formattedDimensionValue);
|
|
285
247
|
}
|
|
286
248
|
|
|
287
249
|
// TODO: Implement prefix and postsuffix - DIMPOST
|
|
@@ -338,13 +300,13 @@ export class BaseDimension extends Entity {
|
|
|
338
300
|
// get the text height
|
|
339
301
|
const textHeight = this.getDimensionStyle().getValue('DIMTXT');
|
|
340
302
|
// set the text height
|
|
341
|
-
text.
|
|
303
|
+
text.setProperty(Property.Names.HEIGHT, textHeight);
|
|
342
304
|
// Always set text horizontal alignment to center
|
|
343
|
-
text.
|
|
305
|
+
text.setProperty(Property.Names.HORIZONTALALIGNMENT, 1);
|
|
344
306
|
// Always set text vertical alignment to middle
|
|
345
|
-
text.
|
|
307
|
+
text.setProperty(Property.Names.VERTICALALIGNMENT, 2);
|
|
346
308
|
// set the text value
|
|
347
|
-
text.
|
|
309
|
+
text.setProperty(Property.Names.STRING, this.getDimensionValue(textValue));
|
|
348
310
|
// set the text position
|
|
349
311
|
text.points = [textPosition];
|
|
350
312
|
// set the text rotation
|
|
@@ -385,7 +347,7 @@ export class BaseDimension extends Entity {
|
|
|
385
347
|
* @return {Object} - the dimension style object
|
|
386
348
|
*/
|
|
387
349
|
getDimensionStyle() {
|
|
388
|
-
return DesignCore.DimStyleManager.getItemByName(this.
|
|
350
|
+
return DesignCore.DimStyleManager.getItemByName(this.getProperty(Property.Names.DIMENSIONSTYLE));
|
|
389
351
|
}
|
|
390
352
|
|
|
391
353
|
/**
|
|
@@ -470,15 +432,15 @@ export class BaseDimension extends Entity {
|
|
|
470
432
|
|
|
471
433
|
/**
|
|
472
434
|
* Draw the entity
|
|
473
|
-
* @param {Object}
|
|
474
|
-
* @
|
|
435
|
+
* @param {Object} renderer
|
|
436
|
+
* @return {Array} block items for the canvas to render recursively
|
|
475
437
|
*/
|
|
476
|
-
draw(
|
|
438
|
+
draw(renderer) {
|
|
477
439
|
if (this.block.items.length === 0) {
|
|
478
440
|
this.refresh();
|
|
479
441
|
}
|
|
480
442
|
|
|
481
|
-
this.block.
|
|
443
|
+
return this.block.items;
|
|
482
444
|
}
|
|
483
445
|
|
|
484
446
|
/**
|
|
@@ -538,7 +500,7 @@ export class BaseDimension extends Entity {
|
|
|
538
500
|
|
|
539
501
|
entities.forEach((element) => {
|
|
540
502
|
// For colour BYBLOCK for dimensions
|
|
541
|
-
element.
|
|
503
|
+
element.setProperty(Property.Names.COLOUR, 'BYBLOCK');
|
|
542
504
|
this.block.addItem(element);
|
|
543
505
|
});
|
|
544
506
|
}
|
|
@@ -550,6 +512,10 @@ export class BaseDimension extends Entity {
|
|
|
550
512
|
* @param {any} value
|
|
551
513
|
*/
|
|
552
514
|
setProperty(property, value) {
|
|
515
|
+
if (this.properties.has(property)) {
|
|
516
|
+
super.setProperty(property, value);
|
|
517
|
+
return;
|
|
518
|
+
}
|
|
553
519
|
if (this.hasOwnProperty(property)) {
|
|
554
520
|
this[property] = value;
|
|
555
521
|
this.refresh();
|
|
@@ -7,7 +7,9 @@ import { BaseDimension } from './baseDimension.js';
|
|
|
7
7
|
import { Point } from '../entities/point.js';
|
|
8
8
|
|
|
9
9
|
import { DesignCore } from '../designCore.js';
|
|
10
|
+
import { Property } from '../properties/property.js';
|
|
10
11
|
import { Utils } from '../lib/utils.js';
|
|
12
|
+
import { RubberBand } from '../lib/auxiliary/rubberBand.js';
|
|
11
13
|
|
|
12
14
|
/**
|
|
13
15
|
* Aligned Dimension Entity Class
|
|
@@ -29,7 +31,7 @@ export class BaseLinearDimension extends BaseDimension {
|
|
|
29
31
|
async execute() {
|
|
30
32
|
try {
|
|
31
33
|
DesignCore.Scene.selectionManager.reset();
|
|
32
|
-
this.
|
|
34
|
+
this.setProperty(Property.Names.DIMENSIONSTYLE, DesignCore.DimStyleManager.getCstyle());
|
|
33
35
|
this.dimType.setDimType(0); // Rotated dimension
|
|
34
36
|
|
|
35
37
|
const op = new PromptOptions(Strings.Input.START, [Input.Type.POINT]);
|
|
@@ -62,8 +64,7 @@ export class BaseLinearDimension extends BaseDimension {
|
|
|
62
64
|
preview() {
|
|
63
65
|
if (this.points.length == 1) {
|
|
64
66
|
const mousePoint = DesignCore.Mouse.pointOnScene();
|
|
65
|
-
|
|
66
|
-
DesignCore.Scene.tempEntities.create('Line', { points: points });
|
|
67
|
+
DesignCore.Scene.auxiliaryEntities.add(new RubberBand([this.points.at(0), mousePoint]));
|
|
67
68
|
}
|
|
68
69
|
|
|
69
70
|
if (this.points.length > 1) {
|
|
@@ -71,7 +72,7 @@ export class BaseLinearDimension extends BaseDimension {
|
|
|
71
72
|
pt11.sequence = 11;
|
|
72
73
|
const tempLine = new Line({ points: [...this.points] });
|
|
73
74
|
const points = this.constructor.getPointsFromSelection([tempLine], pt11);
|
|
74
|
-
DesignCore.Scene.
|
|
75
|
+
DesignCore.Scene.previewEntities.create(this.type, { points: points, dimensionStyle: this.getProperty(Property.Names.DIMENSIONSTYLE) });
|
|
75
76
|
}
|
|
76
77
|
}
|
|
77
78
|
|
|
@@ -155,7 +156,7 @@ export class BaseLinearDimension extends BaseDimension {
|
|
|
155
156
|
const midPoint = Pt13e.midPoint(Pt14e);
|
|
156
157
|
|
|
157
158
|
// set the dimension line angle. This is required for rotated dimension dxf definition
|
|
158
|
-
this.
|
|
159
|
+
this.setProperty(Property.Names.LINEARDIMANGLE, Utils.radians2degrees(dimLineAngle));
|
|
159
160
|
|
|
160
161
|
// Approximate text width based on height using the formatted dimension value i.e with units, precision and symbols
|
|
161
162
|
const approxTextWidth = Text.getApproximateWidth(this.getDimensionValue(dimension), DIMTXT);
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { DXFFile } from '../lib/dxf/dxfFile.js';
|
|
2
2
|
import { BaseCircularDimension } from './baseCircularDimension.js';
|
|
3
|
+
import { Property } from '../properties/property.js';
|
|
3
4
|
|
|
4
5
|
/**
|
|
5
6
|
* Diametric Dimension Entity Class
|
|
@@ -61,10 +62,10 @@ export class DiametricDimension extends BaseCircularDimension {
|
|
|
61
62
|
const Pt15 = this.getPointBySequence(this.points, 15);
|
|
62
63
|
|
|
63
64
|
file.writeGroupCode('0', 'DIMENSION');
|
|
64
|
-
file.writeGroupCode('5', this.
|
|
65
|
+
file.writeGroupCode('5', this.getProperty(Property.Names.HANDLE), DXFFile.Version.R2000); // Handle
|
|
65
66
|
file.writeGroupCode('100', 'AcDbEntity', DXFFile.Version.R2000);
|
|
66
67
|
file.writeGroupCode('100', 'AcDbDimension', DXFFile.Version.R2000);
|
|
67
|
-
file.writeGroupCode('8', this.
|
|
68
|
+
file.writeGroupCode('8', this.getProperty(Property.Names.LAYER));
|
|
68
69
|
// file.writeGroupCode('2', this.blockName); // Block not required
|
|
69
70
|
file.writeGroupCode('10', Pt10.x); // X - Start of Dimension Line
|
|
70
71
|
file.writeGroupCode('20', Pt10.y); // Y
|
|
@@ -73,7 +74,7 @@ export class DiametricDimension extends BaseCircularDimension {
|
|
|
73
74
|
file.writeGroupCode('21', Pt11.y); // Y
|
|
74
75
|
file.writeGroupCode('31', '0.0'); // Z
|
|
75
76
|
file.writeGroupCode('70', this.dimType.getDimType()); // DIMENSION TYPE
|
|
76
|
-
file.writeGroupCode('3', this.
|
|
77
|
+
file.writeGroupCode('3', this.getProperty(Property.Names.DIMENSIONSTYLE)); // DIMENSION STYLE
|
|
77
78
|
file.writeGroupCode('100', 'AcDbDiametricDimension', DXFFile.Version.R2000);
|
|
78
79
|
file.writeGroupCode('15', Pt15.x); // X - End of Dimension Line
|
|
79
80
|
file.writeGroupCode('25', Pt15.y); // Y
|
|
@@ -17,6 +17,7 @@ import { Logging } from '../lib/logging.js';
|
|
|
17
17
|
import { Intersection } from '../lib/intersect.js';
|
|
18
18
|
|
|
19
19
|
import { DesignCore } from '../designCore.js';
|
|
20
|
+
import { Property } from '../properties/property.js';
|
|
20
21
|
import { SingleSelection } from '../lib/selectionManager.js';
|
|
21
22
|
import { Utils } from '../lib/utils.js';
|
|
22
23
|
import { DimType } from '../properties/dimType.js';
|
|
@@ -33,18 +34,24 @@ export class Dimension extends BaseDimension {
|
|
|
33
34
|
constructor(data) {
|
|
34
35
|
super(data);
|
|
35
36
|
|
|
36
|
-
// map dimensions type to the class name
|
|
37
|
-
this
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
37
|
+
// map dimensions type to the class name — non-enumerable: internal workflow state
|
|
38
|
+
Object.defineProperty(this, 'dimensionMap', {
|
|
39
|
+
value: {
|
|
40
|
+
0: RotatedDimension,
|
|
41
|
+
1: AlignedDimension,
|
|
42
|
+
2: AngularDimension,
|
|
43
|
+
3: DiametricDimension,
|
|
44
|
+
4: RadialDimension,
|
|
45
|
+
5: null, // 5 = Angular 3 point;
|
|
46
|
+
6: null, // 6 = Ordinate;
|
|
47
|
+
},
|
|
48
|
+
writable: true,
|
|
49
|
+
});
|
|
50
|
+
|
|
51
|
+
Object.defineProperty(this, 'selectedItems', {
|
|
52
|
+
value: [],
|
|
53
|
+
writable: true,
|
|
54
|
+
});
|
|
48
55
|
|
|
49
56
|
if (data) {
|
|
50
57
|
const item = new this.dimensionMap[DimType.getBaseType(this.dimType.getBaseDimType())](data);
|
|
@@ -80,7 +87,7 @@ export class Dimension extends BaseDimension {
|
|
|
80
87
|
async execute() {
|
|
81
88
|
try {
|
|
82
89
|
let inputValid = false;
|
|
83
|
-
this.
|
|
90
|
+
this.setProperty(Property.Names.DIMENSIONSTYLE, DesignCore.DimStyleManager.getCstyle());
|
|
84
91
|
|
|
85
92
|
while (!inputValid) {
|
|
86
93
|
DesignCore.Scene.selectionManager.reset();
|
|
@@ -292,7 +299,7 @@ export class Dimension extends BaseDimension {
|
|
|
292
299
|
// get the points for the dimension
|
|
293
300
|
const points = dimensionType.getPointsFromSelection(this.selectedItems, Pt11);
|
|
294
301
|
// create the temporary dimension
|
|
295
|
-
DesignCore.Scene.
|
|
302
|
+
DesignCore.Scene.previewEntities.create(dimensionTypeString, { points: points, dimensionStyle: this.getProperty(Property.Names.DIMENSIONSTYLE) });
|
|
296
303
|
}
|
|
297
304
|
}
|
|
298
305
|
}
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
|
|
2
2
|
import { DXFFile } from '../lib/dxf/dxfFile.js';
|
|
3
3
|
import { BaseCircularDimension } from './baseCircularDimension.js';
|
|
4
|
+
import { Property } from '../properties/property.js';
|
|
4
5
|
|
|
5
6
|
/**
|
|
6
7
|
* Radial Dimension Entity Class
|
|
@@ -57,10 +58,10 @@ export class RadialDimension extends BaseCircularDimension {
|
|
|
57
58
|
const Pt15 = this.getPointBySequence(this.points, 15);
|
|
58
59
|
|
|
59
60
|
file.writeGroupCode('0', 'DIMENSION');
|
|
60
|
-
file.writeGroupCode('5', this.
|
|
61
|
+
file.writeGroupCode('5', this.getProperty(Property.Names.HANDLE), DXFFile.Version.R2000); // Handle
|
|
61
62
|
file.writeGroupCode('100', 'AcDbEntity', DXFFile.Version.R2000);
|
|
62
63
|
file.writeGroupCode('100', 'AcDbDimension', DXFFile.Version.R2000);
|
|
63
|
-
file.writeGroupCode('8', this.
|
|
64
|
+
file.writeGroupCode('8', this.getProperty(Property.Names.LAYER));
|
|
64
65
|
// file.writeGroupCode('2', this.blockName); // Block not required
|
|
65
66
|
file.writeGroupCode('10', Pt10.x); // X - Start of Dimension Line
|
|
66
67
|
file.writeGroupCode('20', Pt10.y); // Y
|
|
@@ -69,7 +70,7 @@ export class RadialDimension extends BaseCircularDimension {
|
|
|
69
70
|
file.writeGroupCode('21', Pt11.y); // Y
|
|
70
71
|
file.writeGroupCode('31', '0.0'); // Z
|
|
71
72
|
file.writeGroupCode('70', this.dimType.getDimType()); // DIMENSION TYPE
|
|
72
|
-
file.writeGroupCode('3', this.
|
|
73
|
+
file.writeGroupCode('3', this.getProperty(Property.Names.DIMENSIONSTYLE)); // DIMENSION STYLE
|
|
73
74
|
file.writeGroupCode('100', 'AcDbRadialDimension', DXFFile.Version.R2000);
|
|
74
75
|
file.writeGroupCode('15', Pt15.x); // X - End of Dimension Line
|
|
75
76
|
file.writeGroupCode('25', Pt15.y); // Y
|