@yorab/react-paint 0.6.4 → 0.7.1
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/README.md +5 -5
- package/dist/components/App.js +236 -423
- package/dist/components/Canvas.js +120 -139
- package/dist/components/common/Button.js +41 -50
- package/dist/components/common/Loading.js +24 -33
- package/dist/components/common/Modal.js +18 -17
- package/dist/components/common/Panel.js +20 -28
- package/dist/components/common/Snackbar.js +31 -38
- package/dist/components/settings/ColorField.js +59 -68
- package/dist/components/settings/DeleteButton.js +10 -9
- package/dist/components/settings/FontFamilyField.js +25 -20
- package/dist/components/settings/LayoutButton.js +11 -9
- package/dist/components/settings/Layouts.js +111 -111
- package/dist/components/settings/LineArrowField.js +25 -22
- package/dist/components/settings/LineTypeField.js +23 -20
- package/dist/components/settings/PointsNumberField.js +14 -13
- package/dist/components/settings/RangeField.js +35 -47
- package/dist/components/settings/SelectField.js +34 -43
- package/dist/components/settings/SettingsBar.js +100 -121
- package/dist/components/settings/ToggleField.js +18 -25
- package/dist/components/toolbox/EditTextBox.js +62 -49
- package/dist/components/toolbox/LoadFileTool.js +19 -21
- package/dist/components/toolbox/MenuGroup.js +66 -100
- package/dist/components/toolbox/PictureUrlInput.js +33 -62
- package/dist/components/toolbox/Tool.js +13 -13
- package/dist/components/toolbox/Toolbar.js +79 -113
- package/dist/components/toolbox/ToolbarGroup.js +60 -63
- package/dist/constants/app.js +51 -0
- package/dist/constants/icons.js +42 -48
- package/dist/constants/loading.js +8 -0
- package/dist/constants/shapes.js +10 -8
- package/dist/constants/snackbar.js +7 -15
- package/dist/constants/style.js +21 -18
- package/dist/constants/tools.js +99 -103
- package/dist/hooks/useComponent.js +15 -20
- package/dist/hooks/useDoubleClick.js +12 -12
- package/dist/hooks/useDrag.js +24 -32
- package/dist/hooks/useDrawableCanvas.js +106 -122
- package/dist/hooks/useKeyboard.js +80 -63
- package/dist/hooks/useResizeObserver.js +18 -16
- package/dist/hooks/useShapes.js +92 -144
- package/dist/hooks/useSnackbar.js +28 -58
- package/dist/styles.css +16 -13
- package/dist/types/Mode.js +1 -13
- package/dist/types/Shapes.js +1 -17
- package/dist/types/snackbar.js +5 -0
- package/dist/types/tools.js +1 -18
- package/dist/utils/canvas.js +49 -0
- package/dist/utils/data.js +15 -274
- package/dist/utils/dom.js +12 -0
- package/dist/utils/file.js +75 -120
- package/dist/utils/intersect.js +54 -131
- package/dist/utils/migration.js +59 -0
- package/dist/utils/selection.js +18 -20
- package/dist/utils/shapes/brush.js +135 -0
- package/dist/utils/shapes/circle.js +93 -0
- package/dist/utils/shapes/curve.js +55 -0
- package/dist/utils/shapes/default.js +73 -0
- package/dist/utils/shapes/ellipse.js +101 -0
- package/dist/utils/shapes/grid.js +36 -0
- package/dist/utils/shapes/index.js +341 -0
- package/dist/utils/shapes/line.js +179 -0
- package/dist/utils/shapes/picture.js +88 -0
- package/dist/utils/shapes/polygon.js +69 -0
- package/dist/utils/shapes/rectangle.js +100 -0
- package/dist/utils/shapes/text.js +128 -0
- package/dist/utils/shapes/triangle.js +24 -0
- package/dist/utils/string.js +10 -16
- package/dist/utils/style.js +11 -13
- package/dist/utils/toolbar.js +35 -49
- package/dist/utils/transform.js +47 -339
- package/dist/utils/trigo.js +42 -0
- package/package.json +6 -6
- package/Changelog.md +0 -119
- package/dist/types/keyboard.js +0 -28
- package/dist/utils/draw.js +0 -461
- package/dist/utils/shapeData.js +0 -173
|
@@ -0,0 +1,179 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
|
|
4
|
+
|
|
5
|
+
Object.defineProperty(exports, "__esModule", {
|
|
6
|
+
value: true
|
|
7
|
+
});
|
|
8
|
+
exports.resizeLine = exports.getLineBorder = exports.drawLineSelection = exports.drawLine = exports.createLine = exports.buildTriangleOnLine = void 0;
|
|
9
|
+
|
|
10
|
+
var _shapes = require("../../constants/shapes");
|
|
11
|
+
|
|
12
|
+
var _fp = _interopRequireDefault(require("lodash/fp"));
|
|
13
|
+
|
|
14
|
+
var _canvas = require("../canvas");
|
|
15
|
+
|
|
16
|
+
var _intersect = require("../intersect");
|
|
17
|
+
|
|
18
|
+
var _trigo = require("../trigo");
|
|
19
|
+
|
|
20
|
+
var _2 = require(".");
|
|
21
|
+
|
|
22
|
+
var _circle = require("./circle");
|
|
23
|
+
|
|
24
|
+
var _rectangle = require("./rectangle");
|
|
25
|
+
|
|
26
|
+
var _triangle = require("./triangle");
|
|
27
|
+
|
|
28
|
+
const createLine = (shape, cursorPosition) => {
|
|
29
|
+
return {
|
|
30
|
+
toolId: shape.id,
|
|
31
|
+
type: shape.type,
|
|
32
|
+
id: _fp.default.uniqueId("".concat(shape.type, "_")),
|
|
33
|
+
points: [cursorPosition, cursorPosition],
|
|
34
|
+
rotation: 0,
|
|
35
|
+
style: {
|
|
36
|
+
globalAlpha: shape.settings.opacity.default,
|
|
37
|
+
strokeColor: shape.settings.strokeColor.default,
|
|
38
|
+
lineWidth: shape.settings.lineWidth.default,
|
|
39
|
+
lineDash: shape.settings.lineDash.default,
|
|
40
|
+
lineArrow: shape.settings.lineArrow.default
|
|
41
|
+
}
|
|
42
|
+
};
|
|
43
|
+
};
|
|
44
|
+
|
|
45
|
+
exports.createLine = createLine;
|
|
46
|
+
|
|
47
|
+
const buildTriangleOnLine = (center, rotation, lineStyle) => {
|
|
48
|
+
var _lineStyle$style$line, _lineStyle$style, _lineStyle$style$line2, _lineStyle$style2, _lineStyle$style$line3, _lineStyle$style3, _lineStyle$style$line4, _lineStyle$style4, _lineStyle$style$line5, _lineStyle$style5, _lineStyle$style6;
|
|
49
|
+
|
|
50
|
+
const trianglePoints = [(0, _trigo.rotatePoint)({
|
|
51
|
+
point: [0, -(10 + ((_lineStyle$style$line = (_lineStyle$style = lineStyle.style) === null || _lineStyle$style === void 0 ? void 0 : _lineStyle$style.lineWidth) !== null && _lineStyle$style$line !== void 0 ? _lineStyle$style$line : 0) * 1)],
|
|
52
|
+
rotation
|
|
53
|
+
}), (0, _trigo.rotatePoint)({
|
|
54
|
+
point: [-(5 + ((_lineStyle$style$line2 = (_lineStyle$style2 = lineStyle.style) === null || _lineStyle$style2 === void 0 ? void 0 : _lineStyle$style2.lineWidth) !== null && _lineStyle$style$line2 !== void 0 ? _lineStyle$style$line2 : 0) * 1), 5 + ((_lineStyle$style$line3 = (_lineStyle$style3 = lineStyle.style) === null || _lineStyle$style3 === void 0 ? void 0 : _lineStyle$style3.lineWidth) !== null && _lineStyle$style$line3 !== void 0 ? _lineStyle$style$line3 : 0) * 2],
|
|
55
|
+
rotation
|
|
56
|
+
}), (0, _trigo.rotatePoint)({
|
|
57
|
+
point: [5 + ((_lineStyle$style$line4 = (_lineStyle$style4 = lineStyle.style) === null || _lineStyle$style4 === void 0 ? void 0 : _lineStyle$style4.lineWidth) !== null && _lineStyle$style$line4 !== void 0 ? _lineStyle$style$line4 : 0) * 1, 5 + ((_lineStyle$style$line5 = (_lineStyle$style5 = lineStyle.style) === null || _lineStyle$style5 === void 0 ? void 0 : _lineStyle$style5.lineWidth) !== null && _lineStyle$style$line5 !== void 0 ? _lineStyle$style$line5 : 0) * 2],
|
|
58
|
+
rotation
|
|
59
|
+
})];
|
|
60
|
+
return {
|
|
61
|
+
points: [[center[0] + trianglePoints[0][0], center[1] + trianglePoints[0][1]], [center[0] + trianglePoints[1][0], center[1] + trianglePoints[1][1]], [center[0] + trianglePoints[2][0], center[1] + trianglePoints[2][1]]],
|
|
62
|
+
style: { ...lineStyle.style,
|
|
63
|
+
fillColor: (_lineStyle$style6 = lineStyle.style) === null || _lineStyle$style6 === void 0 ? void 0 : _lineStyle$style6.strokeColor,
|
|
64
|
+
strokeColor: 'transparent'
|
|
65
|
+
}
|
|
66
|
+
};
|
|
67
|
+
};
|
|
68
|
+
|
|
69
|
+
exports.buildTriangleOnLine = buildTriangleOnLine;
|
|
70
|
+
|
|
71
|
+
const drawLine = (ctx, line) => {
|
|
72
|
+
var _line$style, _line$style2, _line$style3, _line$style4, _line$style5, _line$style6;
|
|
73
|
+
|
|
74
|
+
(0, _canvas.updateCanvasContext)(ctx, line.style);
|
|
75
|
+
if (ctx.globalAlpha === 0) return;
|
|
76
|
+
ctx.beginPath();
|
|
77
|
+
ctx.moveTo(...line.points[0]);
|
|
78
|
+
ctx.lineTo(...line.points[1]);
|
|
79
|
+
((_line$style = line.style) === null || _line$style === void 0 ? void 0 : _line$style.fillColor) !== 'transparent' && ctx.fill();
|
|
80
|
+
((_line$style2 = line.style) === null || _line$style2 === void 0 ? void 0 : _line$style2.strokeColor) !== 'transparent' && ctx.stroke();
|
|
81
|
+
|
|
82
|
+
if (((_line$style3 = line.style) === null || _line$style3 === void 0 ? void 0 : _line$style3.lineArrow) === 1 || ((_line$style4 = line.style) === null || _line$style4 === void 0 ? void 0 : _line$style4.lineArrow) === 3) {
|
|
83
|
+
const rotation = Math.PI / 2 - (0, _trigo.getAngleFromVector)(line.points[0], line.points[1]);
|
|
84
|
+
(0, _triangle.drawTriangle)(ctx, buildTriangleOnLine(line.points[0], rotation, {
|
|
85
|
+
style: line.style
|
|
86
|
+
}));
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
if (((_line$style5 = line.style) === null || _line$style5 === void 0 ? void 0 : _line$style5.lineArrow) === 2 || ((_line$style6 = line.style) === null || _line$style6 === void 0 ? void 0 : _line$style6.lineArrow) === 3) {
|
|
90
|
+
const rotation = Math.PI / 2 - (0, _trigo.getAngleFromVector)(line.points[1], line.points[0]);
|
|
91
|
+
(0, _triangle.drawTriangle)(ctx, buildTriangleOnLine(line.points[1], rotation, {
|
|
92
|
+
style: line.style
|
|
93
|
+
}));
|
|
94
|
+
}
|
|
95
|
+
};
|
|
96
|
+
|
|
97
|
+
exports.drawLine = drawLine;
|
|
98
|
+
|
|
99
|
+
const getLineBorder = (line, selectionPadding) => {
|
|
100
|
+
const x = Math.min(line.points[0][0], line.points[1][0]) - selectionPadding;
|
|
101
|
+
const width = Math.abs(line.points[0][0] - line.points[1][0]) + selectionPadding * 2;
|
|
102
|
+
const y = Math.min(line.points[0][1], line.points[1][1]) - selectionPadding;
|
|
103
|
+
const height = Math.abs(line.points[0][1] - line.points[1][1]) + selectionPadding * 2;
|
|
104
|
+
return {
|
|
105
|
+
x,
|
|
106
|
+
width,
|
|
107
|
+
y,
|
|
108
|
+
height
|
|
109
|
+
};
|
|
110
|
+
};
|
|
111
|
+
|
|
112
|
+
exports.getLineBorder = getLineBorder;
|
|
113
|
+
|
|
114
|
+
const resizeLine = (cursorPosition, canvasOffset, originalShape, selectionMode, selectionPadding) => {
|
|
115
|
+
const {
|
|
116
|
+
center
|
|
117
|
+
} = (0, _2.getShapeInfos)(originalShape, selectionPadding);
|
|
118
|
+
const cursorPositionBeforeResize = (0, _intersect.getPointPositionAfterCanvasTransformation)(cursorPosition, originalShape.rotation, center, canvasOffset);
|
|
119
|
+
|
|
120
|
+
const updatedShape = _fp.default.set(['points', selectionMode.anchor], cursorPositionBeforeResize, originalShape);
|
|
121
|
+
|
|
122
|
+
return updatedShape;
|
|
123
|
+
};
|
|
124
|
+
|
|
125
|
+
exports.resizeLine = resizeLine;
|
|
126
|
+
|
|
127
|
+
const drawLineSelection = _ref => {
|
|
128
|
+
let {
|
|
129
|
+
ctx,
|
|
130
|
+
shape,
|
|
131
|
+
withAnchors,
|
|
132
|
+
selectionPadding,
|
|
133
|
+
selectionWidth,
|
|
134
|
+
selectionColor,
|
|
135
|
+
currentScale = 1
|
|
136
|
+
} = _ref;
|
|
137
|
+
const {
|
|
138
|
+
borders
|
|
139
|
+
} = (0, _2.getShapeInfos)(shape, selectionPadding);
|
|
140
|
+
(0, _rectangle.drawRect)(ctx, { ...borders,
|
|
141
|
+
style: {
|
|
142
|
+
fillColor: 'transparent',
|
|
143
|
+
strokeColor: selectionColor,
|
|
144
|
+
lineWidth: selectionWidth / currentScale
|
|
145
|
+
}
|
|
146
|
+
});
|
|
147
|
+
if (!withAnchors || shape.locked) return;
|
|
148
|
+
|
|
149
|
+
for (let i = 0; i < shape.points.length; i++) {
|
|
150
|
+
const coordinate = shape.points[i];
|
|
151
|
+
|
|
152
|
+
if (shape.type === 'curve' && i > 0 && i < shape.points.length - 1) {
|
|
153
|
+
(0, _rectangle.drawRect)(ctx, {
|
|
154
|
+
x: coordinate[0] - _shapes.SELECTION_ANCHOR_SIZE / 2,
|
|
155
|
+
y: coordinate[1] - _shapes.SELECTION_ANCHOR_SIZE / 2,
|
|
156
|
+
width: _shapes.SELECTION_ANCHOR_SIZE / currentScale,
|
|
157
|
+
height: _shapes.SELECTION_ANCHOR_SIZE / currentScale,
|
|
158
|
+
style: {
|
|
159
|
+
fillColor: 'rgb(255,255,255)',
|
|
160
|
+
strokeColor: 'rgb(150,150,150)',
|
|
161
|
+
lineWidth: selectionWidth / currentScale
|
|
162
|
+
}
|
|
163
|
+
});
|
|
164
|
+
} else {
|
|
165
|
+
(0, _circle.drawCircle)(ctx, {
|
|
166
|
+
x: coordinate[0],
|
|
167
|
+
y: coordinate[1],
|
|
168
|
+
radius: _shapes.SELECTION_ANCHOR_SIZE / 2 / currentScale,
|
|
169
|
+
style: {
|
|
170
|
+
fillColor: 'rgb(255,255,255)',
|
|
171
|
+
strokeColor: 'rgb(150,150,150)',
|
|
172
|
+
lineWidth: selectionWidth / currentScale
|
|
173
|
+
}
|
|
174
|
+
});
|
|
175
|
+
}
|
|
176
|
+
}
|
|
177
|
+
};
|
|
178
|
+
|
|
179
|
+
exports.drawLineSelection = drawLineSelection;
|
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
|
|
4
|
+
|
|
5
|
+
Object.defineProperty(exports, "__esModule", {
|
|
6
|
+
value: true
|
|
7
|
+
});
|
|
8
|
+
exports.resizePicture = exports.getPictureBorder = exports.drawPicture = exports.createPicture = void 0;
|
|
9
|
+
|
|
10
|
+
var _fp = _interopRequireDefault(require("lodash/fp"));
|
|
11
|
+
|
|
12
|
+
var _transform = require("../transform");
|
|
13
|
+
|
|
14
|
+
var _file = require("../file");
|
|
15
|
+
|
|
16
|
+
var _tools = require("../../constants/tools");
|
|
17
|
+
|
|
18
|
+
var _canvas = require("../canvas");
|
|
19
|
+
|
|
20
|
+
var _rectangle = require("./rectangle");
|
|
21
|
+
|
|
22
|
+
const createPicture = (fileOrUrl, maxPictureWidth, maxPictureHeight) => {
|
|
23
|
+
return new Promise((resolve, reject) => {
|
|
24
|
+
const img = new Image();
|
|
25
|
+
|
|
26
|
+
img.onload = () => {
|
|
27
|
+
const [width, height] = (0, _transform.fitContentInsideContainer)(img.width, img.height, maxPictureWidth, maxPictureHeight, true);
|
|
28
|
+
const pictureShape = {
|
|
29
|
+
toolId: _tools.DEFAULT_SHAPE_PICTURE.id,
|
|
30
|
+
type: 'picture',
|
|
31
|
+
id: _fp.default.uniqueId('picture'.concat("_")),
|
|
32
|
+
x: (maxPictureWidth - width) / 2,
|
|
33
|
+
y: (maxPictureHeight - height) / 2,
|
|
34
|
+
width,
|
|
35
|
+
height,
|
|
36
|
+
src: fileOrUrl instanceof File ? img.src : fileOrUrl,
|
|
37
|
+
img,
|
|
38
|
+
rotation: 0
|
|
39
|
+
};
|
|
40
|
+
resolve(pictureShape);
|
|
41
|
+
};
|
|
42
|
+
|
|
43
|
+
img.onerror = () => {
|
|
44
|
+
reject(new Error('Some images could not be loaded'));
|
|
45
|
+
};
|
|
46
|
+
|
|
47
|
+
if (fileOrUrl instanceof File) {
|
|
48
|
+
img.src = URL.createObjectURL(fileOrUrl);
|
|
49
|
+
} else {
|
|
50
|
+
(0, _file.fetchAndStringify)(fileOrUrl).then(picData => {
|
|
51
|
+
img.src = picData;
|
|
52
|
+
}).catch(() => {
|
|
53
|
+
img.src = ''; // to trigger onerror
|
|
54
|
+
});
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
img.onerror = () => {
|
|
58
|
+
reject(new Error('Error while loading the src'));
|
|
59
|
+
};
|
|
60
|
+
|
|
61
|
+
setTimeout(() => {
|
|
62
|
+
reject(new Error('Timeout while loading the src'));
|
|
63
|
+
}, 4000);
|
|
64
|
+
});
|
|
65
|
+
};
|
|
66
|
+
|
|
67
|
+
exports.createPicture = createPicture;
|
|
68
|
+
|
|
69
|
+
const drawPicture = (ctx, picture) => {
|
|
70
|
+
(0, _canvas.updateCanvasContext)(ctx, picture.style);
|
|
71
|
+
if (ctx.globalAlpha === 0) return;
|
|
72
|
+
ctx.beginPath();
|
|
73
|
+
ctx.drawImage(picture.img, picture.x, picture.y, picture.width, picture.height);
|
|
74
|
+
};
|
|
75
|
+
|
|
76
|
+
exports.drawPicture = drawPicture;
|
|
77
|
+
|
|
78
|
+
const getPictureBorder = (picture, selectionPadding) => {
|
|
79
|
+
return (0, _rectangle.getRectBorder)(picture, selectionPadding);
|
|
80
|
+
};
|
|
81
|
+
|
|
82
|
+
exports.getPictureBorder = getPictureBorder;
|
|
83
|
+
|
|
84
|
+
const resizePicture = (cursorPosition, canvasOffset, originalShape, selectionMode, selectionPadding, keepRatio) => {
|
|
85
|
+
return (0, _rectangle.resizeRect)(cursorPosition, canvasOffset, originalShape, selectionMode, selectionPadding, keepRatio);
|
|
86
|
+
};
|
|
87
|
+
|
|
88
|
+
exports.resizePicture = resizePicture;
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
|
|
4
|
+
|
|
5
|
+
Object.defineProperty(exports, "__esModule", {
|
|
6
|
+
value: true
|
|
7
|
+
});
|
|
8
|
+
exports.getPolygonBorder = exports.drawPolygon = exports.createPolygon = void 0;
|
|
9
|
+
|
|
10
|
+
var _fp = _interopRequireDefault(require("lodash/fp"));
|
|
11
|
+
|
|
12
|
+
var _canvas = require("../canvas");
|
|
13
|
+
|
|
14
|
+
const createPolygon = (shape, cursorPosition) => {
|
|
15
|
+
return {
|
|
16
|
+
toolId: shape.id,
|
|
17
|
+
type: shape.type,
|
|
18
|
+
id: _fp.default.uniqueId("".concat(shape.type, "_")),
|
|
19
|
+
points: _fp.default.flow(_fp.default.range(0), _fp.default.map(() => cursorPosition))(shape.settings.pointsCount.default),
|
|
20
|
+
rotation: 0,
|
|
21
|
+
style: {
|
|
22
|
+
globalAlpha: shape.settings.opacity.default,
|
|
23
|
+
fillColor: shape.settings.fillColor.default,
|
|
24
|
+
strokeColor: shape.settings.strokeColor.default,
|
|
25
|
+
lineWidth: shape.settings.lineWidth.default,
|
|
26
|
+
lineDash: shape.settings.lineDash.default,
|
|
27
|
+
pointsCount: shape.settings.pointsCount.default
|
|
28
|
+
}
|
|
29
|
+
};
|
|
30
|
+
};
|
|
31
|
+
|
|
32
|
+
exports.createPolygon = createPolygon;
|
|
33
|
+
|
|
34
|
+
const drawPolygon = (ctx, polygon) => {
|
|
35
|
+
var _polygon$style, _polygon$style2;
|
|
36
|
+
|
|
37
|
+
if (polygon.points.length < 1) return;
|
|
38
|
+
(0, _canvas.updateCanvasContext)(ctx, polygon.style);
|
|
39
|
+
if (ctx.globalAlpha === 0) return;
|
|
40
|
+
ctx.beginPath();
|
|
41
|
+
ctx.moveTo(...polygon.points[0]);
|
|
42
|
+
polygon.points.slice(1).forEach(point => {
|
|
43
|
+
ctx.lineTo(...point);
|
|
44
|
+
});
|
|
45
|
+
ctx.lineTo(...polygon.points[0]);
|
|
46
|
+
((_polygon$style = polygon.style) === null || _polygon$style === void 0 ? void 0 : _polygon$style.fillColor) !== 'transparent' && ctx.fill();
|
|
47
|
+
((_polygon$style2 = polygon.style) === null || _polygon$style2 === void 0 ? void 0 : _polygon$style2.strokeColor) !== 'transparent' && ctx.stroke();
|
|
48
|
+
};
|
|
49
|
+
|
|
50
|
+
exports.drawPolygon = drawPolygon;
|
|
51
|
+
|
|
52
|
+
const getPolygonBorder = (polygon, selectionPadding) => {
|
|
53
|
+
const minX = _fp.default.flow(_fp.default.map(point => point[0]), _fp.default.min, _fp.default.add(-selectionPadding))(polygon.points);
|
|
54
|
+
|
|
55
|
+
const maxX = _fp.default.flow(_fp.default.map(point => point[0]), _fp.default.max, _fp.default.add(selectionPadding))(polygon.points);
|
|
56
|
+
|
|
57
|
+
const minY = _fp.default.flow(_fp.default.map(point => point[1]), _fp.default.min, _fp.default.add(-selectionPadding))(polygon.points);
|
|
58
|
+
|
|
59
|
+
const maxY = _fp.default.flow(_fp.default.map(point => point[1]), _fp.default.max, _fp.default.add(selectionPadding))(polygon.points);
|
|
60
|
+
|
|
61
|
+
return {
|
|
62
|
+
x: minX,
|
|
63
|
+
width: maxX - minX,
|
|
64
|
+
y: minY,
|
|
65
|
+
height: maxY - minY
|
|
66
|
+
};
|
|
67
|
+
};
|
|
68
|
+
|
|
69
|
+
exports.getPolygonBorder = getPolygonBorder;
|
|
@@ -0,0 +1,100 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
|
|
4
|
+
|
|
5
|
+
Object.defineProperty(exports, "__esModule", {
|
|
6
|
+
value: true
|
|
7
|
+
});
|
|
8
|
+
exports.resizeRect = exports.getRectOppositeAnchorAbsolutePosition = exports.getRectBorder = exports.drawRect = exports.createRectangle = void 0;
|
|
9
|
+
|
|
10
|
+
var _fp = _interopRequireDefault(require("lodash/fp"));
|
|
11
|
+
|
|
12
|
+
var _canvas = require("../canvas");
|
|
13
|
+
|
|
14
|
+
var _intersect = require("../intersect");
|
|
15
|
+
|
|
16
|
+
var _transform = require("../transform");
|
|
17
|
+
|
|
18
|
+
var _2 = require(".");
|
|
19
|
+
|
|
20
|
+
const createRectangle = (shape, cursorPosition) => {
|
|
21
|
+
return {
|
|
22
|
+
toolId: shape.id,
|
|
23
|
+
type: shape.type,
|
|
24
|
+
id: _fp.default.uniqueId("".concat(shape.type, "_")),
|
|
25
|
+
x: cursorPosition[0],
|
|
26
|
+
y: cursorPosition[1],
|
|
27
|
+
width: 1,
|
|
28
|
+
height: 1,
|
|
29
|
+
rotation: 0,
|
|
30
|
+
style: {
|
|
31
|
+
globalAlpha: shape.settings.opacity.default,
|
|
32
|
+
fillColor: shape.settings.fillColor.default,
|
|
33
|
+
strokeColor: shape.settings.strokeColor.default,
|
|
34
|
+
lineWidth: shape.settings.lineWidth.default,
|
|
35
|
+
lineDash: shape.settings.lineDash.default
|
|
36
|
+
}
|
|
37
|
+
};
|
|
38
|
+
};
|
|
39
|
+
|
|
40
|
+
exports.createRectangle = createRectangle;
|
|
41
|
+
|
|
42
|
+
const drawRect = (ctx, rect) => {
|
|
43
|
+
var _rect$style, _rect$style2;
|
|
44
|
+
|
|
45
|
+
(0, _canvas.updateCanvasContext)(ctx, rect.style);
|
|
46
|
+
if (ctx.globalAlpha === 0) return;
|
|
47
|
+
ctx.beginPath();
|
|
48
|
+
ctx.rect(rect.x, rect.y, rect.width, rect.height);
|
|
49
|
+
((_rect$style = rect.style) === null || _rect$style === void 0 ? void 0 : _rect$style.fillColor) !== 'transparent' && ctx.fill();
|
|
50
|
+
((_rect$style2 = rect.style) === null || _rect$style2 === void 0 ? void 0 : _rect$style2.strokeColor) !== 'transparent' && ctx.stroke();
|
|
51
|
+
};
|
|
52
|
+
|
|
53
|
+
exports.drawRect = drawRect;
|
|
54
|
+
|
|
55
|
+
const getRectBorder = (rect, selectionPadding) => {
|
|
56
|
+
return {
|
|
57
|
+
x: rect.x - selectionPadding,
|
|
58
|
+
width: rect.width + selectionPadding * 2,
|
|
59
|
+
y: rect.y - selectionPadding,
|
|
60
|
+
height: rect.height + selectionPadding * 2
|
|
61
|
+
};
|
|
62
|
+
};
|
|
63
|
+
|
|
64
|
+
exports.getRectBorder = getRectBorder;
|
|
65
|
+
|
|
66
|
+
const getRectOppositeAnchorAbsolutePosition = function (anchor, center, shape, canvasOffset) {
|
|
67
|
+
let [negW, negH] = arguments.length > 4 && arguments[4] !== undefined ? arguments[4] : [false, false];
|
|
68
|
+
const oppositeX = anchor[0] === 0.5 ? shape.x + shape.width / 2 : anchor[0] === 0 ? shape.x + (negW ? 0 : shape.width) : shape.x + (negW ? shape.width : 0);
|
|
69
|
+
const oppositeY = anchor[1] === 0.5 ? shape.y + shape.height / 2 : anchor[1] === 0 ? shape.y + (negH ? 0 : shape.height) : shape.y + (negH ? shape.height : 0);
|
|
70
|
+
return (0, _intersect.getPointPositionBeforeCanvasTransformation)([oppositeX, oppositeY], shape.rotation, center, canvasOffset);
|
|
71
|
+
};
|
|
72
|
+
|
|
73
|
+
exports.getRectOppositeAnchorAbsolutePosition = getRectOppositeAnchorAbsolutePosition;
|
|
74
|
+
|
|
75
|
+
const resizeRect = function (cursorPosition, canvasOffset, originalShape, selectionMode, selectionPadding) {
|
|
76
|
+
let keepRatio = arguments.length > 5 && arguments[5] !== undefined ? arguments[5] : false;
|
|
77
|
+
const {
|
|
78
|
+
center,
|
|
79
|
+
borders
|
|
80
|
+
} = (0, _2.getShapeInfos)(originalShape, selectionPadding);
|
|
81
|
+
const cusroPositionAfterShapeTransormation = (0, _intersect.getPointPositionAfterCanvasTransformation)(cursorPosition, originalShape.rotation, center, canvasOffset);
|
|
82
|
+
const scaledWidth = selectionMode.anchor[0] === 0.5 ? originalShape.width : selectionMode.anchor[0] === 0 ? borders.x + borders.width - cusroPositionAfterShapeTransormation[0] + selectionPadding * -2 : cusroPositionAfterShapeTransormation[0] - borders.x - selectionPadding * 2;
|
|
83
|
+
const scaledHeight = selectionMode.anchor[1] === 0.5 ? originalShape.height : selectionMode.anchor[1] === 0 ? borders.y + borders.height - cusroPositionAfterShapeTransormation[1] + selectionPadding * -2 : cusroPositionAfterShapeTransormation[1] - borders.y - selectionPadding * 2;
|
|
84
|
+
const [widthWithRatio, heightWithRatio] = keepRatio ? (0, _transform.getNormalizedSize)(originalShape.width, originalShape.height, scaledWidth, scaledHeight) : [scaledWidth, scaledHeight];
|
|
85
|
+
const shapeWithNewDimensions = { ...originalShape,
|
|
86
|
+
width: Math.abs(widthWithRatio),
|
|
87
|
+
height: Math.abs(heightWithRatio)
|
|
88
|
+
};
|
|
89
|
+
const {
|
|
90
|
+
center: shapeWithNewDimensionsCenter
|
|
91
|
+
} = (0, _2.getShapeInfos)(shapeWithNewDimensions, selectionPadding);
|
|
92
|
+
const [oppTrueX, oppTrueY] = getRectOppositeAnchorAbsolutePosition(selectionMode.anchor, center, originalShape, canvasOffset);
|
|
93
|
+
const [newOppTrueX, newOppTrueY] = getRectOppositeAnchorAbsolutePosition(selectionMode.anchor, shapeWithNewDimensionsCenter, shapeWithNewDimensions, canvasOffset, [widthWithRatio < 0, heightWithRatio < 0]);
|
|
94
|
+
return { ...shapeWithNewDimensions,
|
|
95
|
+
x: shapeWithNewDimensions.x - (newOppTrueX - oppTrueX),
|
|
96
|
+
y: shapeWithNewDimensions.y - (newOppTrueY - oppTrueY)
|
|
97
|
+
};
|
|
98
|
+
};
|
|
99
|
+
|
|
100
|
+
exports.resizeRect = resizeRect;
|
|
@@ -0,0 +1,128 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
|
|
4
|
+
|
|
5
|
+
Object.defineProperty(exports, "__esModule", {
|
|
6
|
+
value: true
|
|
7
|
+
});
|
|
8
|
+
exports.resizeTextShapeWithNewContent = exports.resizeText = exports.getTextBorder = exports.drawText = exports.createText = exports.calculateTextFontSize = void 0;
|
|
9
|
+
|
|
10
|
+
var _fp = _interopRequireDefault(require("lodash/fp"));
|
|
11
|
+
|
|
12
|
+
var _canvas = require("../canvas");
|
|
13
|
+
|
|
14
|
+
var _style = require("../../constants/style");
|
|
15
|
+
|
|
16
|
+
var _rectangle = require("./rectangle");
|
|
17
|
+
|
|
18
|
+
var _2 = require(".");
|
|
19
|
+
|
|
20
|
+
const calculateTextFontSize = function (ctx, text, maxWidth, fontBold, fontItalic) {
|
|
21
|
+
var _$flow;
|
|
22
|
+
|
|
23
|
+
let fontFamily = arguments.length > 5 && arguments[5] !== undefined ? arguments[5] : _style.STYLE_FONT_DEFAULT;
|
|
24
|
+
ctx.font = "".concat(fontItalic ? 'italic' : '', " ").concat(fontBold ? 'bold' : '', " 1px ").concat(fontFamily);
|
|
25
|
+
return (_$flow = _fp.default.flow(_fp.default.map(value => maxWidth / ctx.measureText(value).width), _fp.default.min)(text)) !== null && _$flow !== void 0 ? _$flow : _style.STYLE_FONT_SIZE_DEFAULT;
|
|
26
|
+
};
|
|
27
|
+
|
|
28
|
+
exports.calculateTextFontSize = calculateTextFontSize;
|
|
29
|
+
|
|
30
|
+
const createText = (ctx, shape, cursorPosition) => {
|
|
31
|
+
var _shape$settings$fontB, _shape$settings, _shape$settings$fontI, _shape$settings2;
|
|
32
|
+
|
|
33
|
+
const defaultValue = ['Texte'];
|
|
34
|
+
const fontSize = calculateTextFontSize(ctx, defaultValue, 50, (_shape$settings$fontB = (_shape$settings = shape.settings) === null || _shape$settings === void 0 ? void 0 : _shape$settings.fontBold.default) !== null && _shape$settings$fontB !== void 0 ? _shape$settings$fontB : false, (_shape$settings$fontI = (_shape$settings2 = shape.settings) === null || _shape$settings2 === void 0 ? void 0 : _shape$settings2.fontItalic.default) !== null && _shape$settings$fontI !== void 0 ? _shape$settings$fontI : false, shape.settings.fontFamily.default);
|
|
35
|
+
return {
|
|
36
|
+
toolId: shape.id,
|
|
37
|
+
type: shape.type,
|
|
38
|
+
id: _fp.default.uniqueId("".concat(shape.type, "_")),
|
|
39
|
+
x: cursorPosition[0],
|
|
40
|
+
y: cursorPosition[1],
|
|
41
|
+
value: defaultValue,
|
|
42
|
+
fontSize,
|
|
43
|
+
width: 50,
|
|
44
|
+
height: fontSize * (defaultValue.length || 1),
|
|
45
|
+
rotation: 0,
|
|
46
|
+
style: {
|
|
47
|
+
globalAlpha: shape.settings.opacity.default,
|
|
48
|
+
strokeColor: shape.settings.strokeColor.default,
|
|
49
|
+
fontFamily: shape.settings.fontFamily.default
|
|
50
|
+
}
|
|
51
|
+
};
|
|
52
|
+
};
|
|
53
|
+
|
|
54
|
+
exports.createText = createText;
|
|
55
|
+
|
|
56
|
+
const drawText = (ctx, text) => {
|
|
57
|
+
var _text$style, _text$style2, _text$style3, _text$style$fontFamil, _text$style4;
|
|
58
|
+
|
|
59
|
+
(0, _canvas.updateCanvasContext)(ctx, text.style);
|
|
60
|
+
if (ctx.globalAlpha === 0 || !((_text$style = text.style) !== null && _text$style !== void 0 && _text$style.strokeColor) || text.style.strokeColor === 'transparent') return;
|
|
61
|
+
ctx.font = "".concat((_text$style2 = text.style) !== null && _text$style2 !== void 0 && _text$style2.fontItalic ? 'italic' : '', " ").concat((_text$style3 = text.style) !== null && _text$style3 !== void 0 && _text$style3.fontBold ? 'bold' : '', " ").concat(text.fontSize, "px ").concat((_text$style$fontFamil = (_text$style4 = text.style) === null || _text$style4 === void 0 ? void 0 : _text$style4.fontFamily) !== null && _text$style$fontFamil !== void 0 ? _text$style$fontFamil : _style.STYLE_FONT_DEFAULT);
|
|
62
|
+
ctx.textBaseline = 'top';
|
|
63
|
+
ctx.fillStyle = text.style.strokeColor;
|
|
64
|
+
|
|
65
|
+
for (let i = 0; i < text.value.length; i++) {
|
|
66
|
+
ctx.fillText(text.value[i], text.x, text.y + i * text.fontSize, text.width);
|
|
67
|
+
}
|
|
68
|
+
};
|
|
69
|
+
|
|
70
|
+
exports.drawText = drawText;
|
|
71
|
+
|
|
72
|
+
const getTextBorder = (text, selectionPadding) => {
|
|
73
|
+
return {
|
|
74
|
+
x: text.x - selectionPadding,
|
|
75
|
+
width: text.width + selectionPadding * 2,
|
|
76
|
+
y: text.y - selectionPadding,
|
|
77
|
+
height: text.height + selectionPadding * 2
|
|
78
|
+
};
|
|
79
|
+
};
|
|
80
|
+
|
|
81
|
+
exports.getTextBorder = getTextBorder;
|
|
82
|
+
|
|
83
|
+
const resizeText = (ctx, cursorPosition, canvasOffset, originalShape, selectionMode, selectionPadding) => {
|
|
84
|
+
var _newRect$style$fontBo, _newRect$style, _newRect$style$fontIt, _newRect$style2, _newRect$style3;
|
|
85
|
+
|
|
86
|
+
const newRect = (0, _rectangle.resizeRect)(cursorPosition, canvasOffset, originalShape, selectionMode, selectionPadding, true);
|
|
87
|
+
return { ...newRect,
|
|
88
|
+
fontSize: calculateTextFontSize(ctx, newRect.value, newRect.width, (_newRect$style$fontBo = (_newRect$style = newRect.style) === null || _newRect$style === void 0 ? void 0 : _newRect$style.fontBold) !== null && _newRect$style$fontBo !== void 0 ? _newRect$style$fontBo : false, (_newRect$style$fontIt = (_newRect$style2 = newRect.style) === null || _newRect$style2 === void 0 ? void 0 : _newRect$style2.fontItalic) !== null && _newRect$style$fontIt !== void 0 ? _newRect$style$fontIt : false, (_newRect$style3 = newRect.style) === null || _newRect$style3 === void 0 ? void 0 : _newRect$style3.fontFamily)
|
|
89
|
+
};
|
|
90
|
+
};
|
|
91
|
+
|
|
92
|
+
exports.resizeText = resizeText;
|
|
93
|
+
|
|
94
|
+
const calculateTextWidth = function (ctx, text, fontSize, fontBold, fontItalic) {
|
|
95
|
+
var _$flow2;
|
|
96
|
+
|
|
97
|
+
let fontFamily = arguments.length > 5 && arguments[5] !== undefined ? arguments[5] : _style.STYLE_FONT_DEFAULT;
|
|
98
|
+
ctx.font = "".concat(fontItalic ? 'italic' : '', " ").concat(fontBold ? 'bold' : '', " ").concat(fontSize, "px ").concat(fontFamily);
|
|
99
|
+
return (_$flow2 = _fp.default.flow(_fp.default.map(value => ctx.measureText(value).width), _fp.default.max)(text)) !== null && _$flow2 !== void 0 ? _$flow2 : 20;
|
|
100
|
+
};
|
|
101
|
+
|
|
102
|
+
const resizeTextShapeWithNewContent = (ctx, shape, newValue, canvasOffset) => {
|
|
103
|
+
var _newShape$style$fontB, _newShape$style, _newShape$style$fontI, _newShape$style2, _newShape$style3;
|
|
104
|
+
|
|
105
|
+
const newShape = _fp.default.set('value', newValue, shape);
|
|
106
|
+
|
|
107
|
+
const newWidth = calculateTextWidth(ctx, newShape.value, newShape.fontSize, (_newShape$style$fontB = (_newShape$style = newShape.style) === null || _newShape$style === void 0 ? void 0 : _newShape$style.fontBold) !== null && _newShape$style$fontB !== void 0 ? _newShape$style$fontB : false, (_newShape$style$fontI = (_newShape$style2 = newShape.style) === null || _newShape$style2 === void 0 ? void 0 : _newShape$style2.fontItalic) !== null && _newShape$style$fontI !== void 0 ? _newShape$style$fontI : false, (_newShape$style3 = newShape.style) === null || _newShape$style3 === void 0 ? void 0 : _newShape$style3.fontFamily);
|
|
108
|
+
const newHeight = newShape.fontSize * newShape.value.length;
|
|
109
|
+
const resizedShape = { ...newShape,
|
|
110
|
+
width: newWidth,
|
|
111
|
+
height: newHeight
|
|
112
|
+
};
|
|
113
|
+
const selectionPadding = 0;
|
|
114
|
+
const {
|
|
115
|
+
center
|
|
116
|
+
} = (0, _2.getShapeInfos)(shape, selectionPadding);
|
|
117
|
+
const {
|
|
118
|
+
center: shapeWithNewDimensionsCenter
|
|
119
|
+
} = (0, _2.getShapeInfos)(resizedShape, selectionPadding);
|
|
120
|
+
const [oppTrueX, oppTrueY] = (0, _rectangle.getRectOppositeAnchorAbsolutePosition)([1, 0.5], center, shape, canvasOffset);
|
|
121
|
+
const [newOppTrueX, newOppTrueY] = (0, _rectangle.getRectOppositeAnchorAbsolutePosition)([1, 0.5], shapeWithNewDimensionsCenter, resizedShape, canvasOffset, [false, false]);
|
|
122
|
+
return { ...resizedShape,
|
|
123
|
+
x: resizedShape.x - (newOppTrueX - oppTrueX),
|
|
124
|
+
y: resizedShape.y - (newOppTrueY - oppTrueY)
|
|
125
|
+
};
|
|
126
|
+
};
|
|
127
|
+
|
|
128
|
+
exports.resizeTextShapeWithNewContent = resizeTextShapeWithNewContent;
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports.drawTriangle = void 0;
|
|
7
|
+
|
|
8
|
+
var _canvas = require("../canvas");
|
|
9
|
+
|
|
10
|
+
const drawTriangle = (ctx, triangle) => {
|
|
11
|
+
var _triangle$style, _triangle$style2;
|
|
12
|
+
|
|
13
|
+
(0, _canvas.updateCanvasContext)(ctx, triangle.style);
|
|
14
|
+
if (ctx.globalAlpha === 0) return;
|
|
15
|
+
ctx.beginPath();
|
|
16
|
+
ctx.moveTo(...triangle.points[0]);
|
|
17
|
+
ctx.lineTo(...triangle.points[1]);
|
|
18
|
+
ctx.lineTo(...triangle.points[2]);
|
|
19
|
+
ctx.lineTo(...triangle.points[0]);
|
|
20
|
+
((_triangle$style = triangle.style) === null || _triangle$style === void 0 ? void 0 : _triangle$style.fillColor) !== 'transparent' && ctx.fill();
|
|
21
|
+
((_triangle$style2 = triangle.style) === null || _triangle$style2 === void 0 ? void 0 : _triangle$style2.strokeColor) !== 'transparent' && ctx.stroke();
|
|
22
|
+
};
|
|
23
|
+
|
|
24
|
+
exports.drawTriangle = drawTriangle;
|
package/dist/utils/string.js
CHANGED
|
@@ -9,34 +9,28 @@ exports.decodeHtmlEntities = exports.convertStringArrayToDivContent = exports.co
|
|
|
9
9
|
|
|
10
10
|
var _fp = _interopRequireDefault(require("lodash/fp"));
|
|
11
11
|
|
|
12
|
-
|
|
13
|
-
|
|
12
|
+
const stripBrRegexp = /<br(\/?\s?)>/g;
|
|
13
|
+
const stripDivRegexp = /<(\/)?div(\/?\s?)>/g;
|
|
14
14
|
|
|
15
|
-
|
|
16
|
-
return toConvert.map(
|
|
17
|
-
return "<div>".concat(val === '' ? '<br/>' : val, "</div>");
|
|
18
|
-
}).join('');
|
|
15
|
+
const convertStringArrayToDivContent = toConvert => {
|
|
16
|
+
return toConvert.map(val => "<div>".concat(val === '' ? '<br/>' : val, "</div>")).join('');
|
|
19
17
|
};
|
|
20
18
|
|
|
21
19
|
exports.convertStringArrayToDivContent = convertStringArrayToDivContent;
|
|
22
20
|
|
|
23
|
-
|
|
24
|
-
|
|
21
|
+
const decodeHtmlEntities = html => {
|
|
22
|
+
const textareaElement = document.createElement('textarea');
|
|
25
23
|
textareaElement.innerHTML = html;
|
|
26
24
|
return textareaElement.value;
|
|
27
25
|
};
|
|
28
26
|
|
|
29
27
|
exports.decodeHtmlEntities = decodeHtmlEntities;
|
|
30
28
|
|
|
31
|
-
|
|
32
|
-
return _fp
|
|
33
|
-
|
|
34
|
-
}, function (divContent) {
|
|
35
|
-
return divContent.split('<div>');
|
|
36
|
-
}, _fp["default"].flatMap(function (val) {
|
|
37
|
-
var newVal = val.replaceAll(stripDivRegexp, '');
|
|
29
|
+
const convertDivContentToStringArray = toConvert => {
|
|
30
|
+
return _fp.default.flow(divContent => decodeHtmlEntities(divContent), divContent => divContent.split('<div>'), _fp.default.flatMap(val => {
|
|
31
|
+
const newVal = val.replaceAll(stripDivRegexp, '');
|
|
38
32
|
return newVal === '' ? undefined : newVal.replaceAll(stripBrRegexp, '');
|
|
39
|
-
}), _fp
|
|
33
|
+
}), _fp.default.reject(_fp.default.isUndefined))(toConvert);
|
|
40
34
|
};
|
|
41
35
|
|
|
42
36
|
exports.convertDivContentToStringArray = convertDivContentToStringArray;
|