react-screenshots 0.5.21 → 0.6.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 (139) hide show
  1. package/README.md +145 -145
  2. package/dist/electron.html +1 -0
  3. package/dist/index.html +1 -0
  4. package/dist/static/css/electron.7eee95c8.css +1 -0
  5. package/dist/static/css/index.7eee95c8.css +1 -0
  6. package/dist/static/image/image.1ca17a04.jpg +0 -0
  7. package/dist/static/js/589.5602a0fa.js +12 -0
  8. package/dist/static/js/electron.1c6ab61b.js +1 -0
  9. package/dist/static/js/index.fbe72af7.js +1 -0
  10. package/dist/static/js/lib-react.6d1aa3cf.js +2 -0
  11. package/dist/static/js/lib-react.6d1aa3cf.js.LICENSE.txt +39 -0
  12. package/lib/{types → Screenshots}/ScreenshotsBackground/getBoundsByPoints.d.ts +1 -1
  13. package/lib/Screenshots/ScreenshotsBackground/getBoundsByPoints.js +21 -0
  14. package/lib/Screenshots/ScreenshotsBackground/index.d.ts +3 -0
  15. package/lib/Screenshots/ScreenshotsBackground/index.js +100 -0
  16. package/lib/{types → Screenshots}/ScreenshotsButton/index.d.ts +2 -2
  17. package/lib/Screenshots/ScreenshotsButton/index.js +31 -0
  18. package/lib/{types → Screenshots}/ScreenshotsCanvas/getBoundsByPoints.d.ts +1 -1
  19. package/lib/Screenshots/ScreenshotsCanvas/getBoundsByPoints.js +33 -0
  20. package/lib/{types → Screenshots}/ScreenshotsCanvas/getPoints.d.ts +1 -1
  21. package/lib/Screenshots/ScreenshotsCanvas/getPoints.js +57 -0
  22. package/lib/{types → Screenshots}/ScreenshotsCanvas/index.d.ts +1 -2
  23. package/lib/Screenshots/ScreenshotsCanvas/index.js +199 -0
  24. package/lib/{types → Screenshots}/ScreenshotsCanvas/isPointInDraw.d.ts +1 -1
  25. package/lib/Screenshots/ScreenshotsCanvas/isPointInDraw.js +24 -0
  26. package/lib/{types → Screenshots}/ScreenshotsColor/index.d.ts +1 -2
  27. package/lib/Screenshots/ScreenshotsColor/index.js +30 -0
  28. package/lib/{types → Screenshots}/ScreenshotsContext.d.ts +4 -3
  29. package/lib/Screenshots/ScreenshotsContext.js +32 -0
  30. package/lib/{types → Screenshots}/ScreenshotsMagnifier/index.d.ts +1 -2
  31. package/lib/Screenshots/ScreenshotsMagnifier/index.js +99 -0
  32. package/lib/{types → Screenshots}/ScreenshotsOperations/index.d.ts +1 -1
  33. package/lib/Screenshots/ScreenshotsOperations/index.js +64 -0
  34. package/lib/{types → Screenshots}/ScreenshotsOption/index.d.ts +3 -3
  35. package/lib/Screenshots/ScreenshotsOption/index.js +94 -0
  36. package/lib/{types → Screenshots}/ScreenshotsSize/index.d.ts +1 -2
  37. package/lib/Screenshots/ScreenshotsSize/index.js +31 -0
  38. package/lib/{types → Screenshots}/ScreenshotsSizeColor/index.d.ts +2 -3
  39. package/lib/Screenshots/ScreenshotsSizeColor/index.js +21 -0
  40. package/lib/Screenshots/ScreenshotsTextarea/calculateNodeSize.js +69 -0
  41. package/lib/{types → Screenshots}/ScreenshotsTextarea/index.d.ts +2 -2
  42. package/lib/Screenshots/ScreenshotsTextarea/index.js +54 -0
  43. package/lib/{types → Screenshots}/composeImage.d.ts +1 -1
  44. package/lib/Screenshots/composeImage.js +27 -0
  45. package/lib/Screenshots/exports.d.ts +4 -0
  46. package/lib/Screenshots/exports.js +2 -0
  47. package/lib/{types → Screenshots}/hooks/useBounds.d.ts +1 -1
  48. package/lib/Screenshots/hooks/useBounds.js +25 -0
  49. package/lib/Screenshots/hooks/useCall.js +12 -0
  50. package/lib/{types → Screenshots}/hooks/useCanvasContextRef.d.ts +1 -1
  51. package/lib/Screenshots/hooks/useCanvasContextRef.js +6 -0
  52. package/lib/Screenshots/hooks/useCanvasMousedown.js +15 -0
  53. package/lib/Screenshots/hooks/useCanvasMousemove.js +15 -0
  54. package/lib/Screenshots/hooks/useCanvasMouseup.js +15 -0
  55. package/lib/Screenshots/hooks/useCursor.js +25 -0
  56. package/lib/Screenshots/hooks/useDispatcher.d.ts +2 -0
  57. package/lib/Screenshots/hooks/useDispatcher.js +7 -0
  58. package/lib/{types → Screenshots}/hooks/useDrawSelect.d.ts +1 -1
  59. package/lib/Screenshots/hooks/useDrawSelect.js +15 -0
  60. package/lib/{types → Screenshots}/hooks/useEmiter.d.ts +1 -1
  61. package/lib/Screenshots/hooks/useEmiter.js +41 -0
  62. package/lib/{types → Screenshots}/hooks/useHistory.d.ts +1 -1
  63. package/lib/Screenshots/hooks/useHistory.js +122 -0
  64. package/lib/{types → Screenshots}/hooks/useLang.d.ts +1 -1
  65. package/lib/Screenshots/hooks/useLang.js +6 -0
  66. package/lib/Screenshots/hooks/useOperation.js +25 -0
  67. package/lib/Screenshots/hooks/useReset.js +28 -0
  68. package/lib/Screenshots/hooks/useStore.d.ts +2 -0
  69. package/lib/Screenshots/hooks/useStore.js +7 -0
  70. package/lib/{types → Screenshots}/index.d.ts +2 -2
  71. package/lib/Screenshots/index.js +140 -0
  72. package/lib/{types → Screenshots}/operations/Arrow/draw.d.ts +2 -2
  73. package/lib/Screenshots/operations/Arrow/draw.js +51 -0
  74. package/lib/{types → Screenshots}/operations/Arrow/index.d.ts +1 -1
  75. package/lib/Screenshots/operations/Arrow/index.js +153 -0
  76. package/lib/{types → Screenshots}/operations/Brush/draw.d.ts +2 -2
  77. package/lib/Screenshots/operations/Brush/draw.js +31 -0
  78. package/lib/{types → Screenshots}/operations/Brush/index.d.ts +2 -2
  79. package/lib/Screenshots/operations/Brush/index.js +138 -0
  80. package/lib/{types → Screenshots}/operations/Cancel/index.d.ts +1 -1
  81. package/lib/Screenshots/operations/Cancel/index.js +24 -0
  82. package/lib/{types → Screenshots}/operations/Ellipse/draw.d.ts +2 -2
  83. package/lib/Screenshots/operations/Ellipse/draw.js +81 -0
  84. package/lib/{types → Screenshots}/operations/Ellipse/index.d.ts +1 -1
  85. package/lib/Screenshots/operations/Ellipse/index.js +185 -0
  86. package/lib/{types → Screenshots}/operations/Mosaic/index.d.ts +1 -1
  87. package/lib/Screenshots/operations/Mosaic/index.js +174 -0
  88. package/lib/{types → Screenshots}/operations/Ok/index.d.ts +1 -1
  89. package/lib/Screenshots/operations/Ok/index.js +48 -0
  90. package/lib/{types → Screenshots}/operations/Rectangle/draw.d.ts +2 -2
  91. package/lib/Screenshots/operations/Rectangle/draw.js +66 -0
  92. package/lib/{types → Screenshots}/operations/Rectangle/index.d.ts +1 -1
  93. package/lib/Screenshots/operations/Rectangle/index.js +186 -0
  94. package/lib/{types → Screenshots}/operations/Redo/index.d.ts +1 -1
  95. package/lib/Screenshots/operations/Redo/index.js +21 -0
  96. package/lib/{types → Screenshots}/operations/Save/index.d.ts +1 -1
  97. package/lib/Screenshots/operations/Save/index.js +48 -0
  98. package/lib/{types → Screenshots}/operations/Text/index.d.ts +1 -1
  99. package/lib/Screenshots/operations/Text/index.js +220 -0
  100. package/lib/{types → Screenshots}/operations/Undo/index.d.ts +1 -1
  101. package/lib/Screenshots/operations/Undo/index.js +21 -0
  102. package/lib/Screenshots/operations/index.js +27 -0
  103. package/lib/{types → Screenshots}/operations/utils.d.ts +1 -1
  104. package/lib/Screenshots/operations/utils.js +23 -0
  105. package/lib/{types → Screenshots}/types.d.ts +1 -1
  106. package/lib/Screenshots/types.js +6 -0
  107. package/lib/Screenshots/useGetLoadedImage.js +22 -0
  108. package/lib/Screenshots/zh_CN.js +16 -0
  109. package/lib/electron/app.d.ts +10 -0
  110. package/lib/electron/app.js +80 -0
  111. package/lib/electron/index.d.ts +1 -0
  112. package/lib/electron/index.js +7 -0
  113. package/lib/web/app.d.ts +3 -0
  114. package/lib/web/app.js +41 -0
  115. package/lib/web/index.d.ts +1 -0
  116. package/lib/web/index.js +7 -0
  117. package/package.json +35 -41
  118. package/LICENSE +0 -21
  119. package/electron/assets/electron-ed141e06.css +0 -1
  120. package/electron/assets/index-73f470f6.js +0 -53
  121. package/electron/electron.html +0 -14
  122. package/lib/react-screenshots.cjs.js +0 -14
  123. package/lib/react-screenshots.es.js +0 -1716
  124. package/lib/style.css +0 -1
  125. package/lib/types/ScreenshotsBackground/index.d.ts +0 -4
  126. package/lib/types/exports.d.ts +0 -3
  127. package/lib/types/hooks/useDispatcher.d.ts +0 -2
  128. package/lib/types/hooks/useStore.d.ts +0 -2
  129. /package/lib/{types → Screenshots}/ScreenshotsTextarea/calculateNodeSize.d.ts +0 -0
  130. /package/lib/{types → Screenshots}/hooks/useCall.d.ts +0 -0
  131. /package/lib/{types → Screenshots}/hooks/useCanvasMousedown.d.ts +0 -0
  132. /package/lib/{types → Screenshots}/hooks/useCanvasMousemove.d.ts +0 -0
  133. /package/lib/{types → Screenshots}/hooks/useCanvasMouseup.d.ts +0 -0
  134. /package/lib/{types → Screenshots}/hooks/useCursor.d.ts +0 -0
  135. /package/lib/{types → Screenshots}/hooks/useOperation.d.ts +0 -0
  136. /package/lib/{types → Screenshots}/hooks/useReset.d.ts +0 -0
  137. /package/lib/{types → Screenshots}/operations/index.d.ts +0 -0
  138. /package/lib/{types → Screenshots}/useGetLoadedImage.d.ts +0 -0
  139. /package/lib/{types → Screenshots}/zh_CN.d.ts +0 -0
@@ -0,0 +1,122 @@
1
+ import { useCallback } from "react";
2
+ import { HistoryItemType } from "../types.js";
3
+ import useDispatcher from "./useDispatcher.js";
4
+ import useStore from "./useStore.js";
5
+ function useHistory() {
6
+ const { history } = useStore();
7
+ const { setHistory } = useDispatcher();
8
+ const push = useCallback((action)=>{
9
+ const { index, stack } = history;
10
+ stack.forEach((item)=>{
11
+ if (item.type === HistoryItemType.Source) item.isSelected = false;
12
+ });
13
+ if (action.type === HistoryItemType.Source) action.isSelected = true;
14
+ else if (action.type === HistoryItemType.Edit) action.source.isSelected = true;
15
+ stack.splice(index + 1);
16
+ stack.push(action);
17
+ setHistory?.({
18
+ index: stack.length - 1,
19
+ stack
20
+ });
21
+ }, [
22
+ history,
23
+ setHistory
24
+ ]);
25
+ const pop = useCallback(()=>{
26
+ const { stack } = history;
27
+ stack.pop();
28
+ setHistory?.({
29
+ index: stack.length - 1,
30
+ stack
31
+ });
32
+ }, [
33
+ history,
34
+ setHistory
35
+ ]);
36
+ const undo = useCallback(()=>{
37
+ const { index, stack } = history;
38
+ const item = stack[index];
39
+ if (item) {
40
+ if (item.type === HistoryItemType.Source) item.isSelected = false;
41
+ else if (item.type === HistoryItemType.Edit) item.source.editHistory.pop();
42
+ }
43
+ setHistory?.({
44
+ index: index <= 0 ? -1 : index - 1,
45
+ stack
46
+ });
47
+ }, [
48
+ history,
49
+ setHistory
50
+ ]);
51
+ const redo = useCallback(()=>{
52
+ const { index, stack } = history;
53
+ const item = stack[index + 1];
54
+ if (item) {
55
+ if (item.type === HistoryItemType.Source) item.isSelected = false;
56
+ else if (item.type === HistoryItemType.Edit) item.source.editHistory.push(item);
57
+ }
58
+ setHistory?.({
59
+ index: index >= stack.length - 1 ? stack.length - 1 : index + 1,
60
+ stack
61
+ });
62
+ }, [
63
+ history,
64
+ setHistory
65
+ ]);
66
+ const set = useCallback((history)=>{
67
+ setHistory?.({
68
+ ...history
69
+ });
70
+ }, [
71
+ setHistory
72
+ ]);
73
+ const select = useCallback((action)=>{
74
+ history.stack.forEach((item)=>{
75
+ if (item.type === HistoryItemType.Source) if (item === action) item.isSelected = true;
76
+ else item.isSelected = false;
77
+ });
78
+ setHistory?.({
79
+ ...history
80
+ });
81
+ }, [
82
+ history,
83
+ setHistory
84
+ ]);
85
+ const clearSelect = useCallback(()=>{
86
+ history.stack.forEach((item)=>{
87
+ if (item.type === HistoryItemType.Source) item.isSelected = false;
88
+ });
89
+ setHistory?.({
90
+ ...history
91
+ });
92
+ }, [
93
+ history,
94
+ setHistory
95
+ ]);
96
+ const reset = useCallback(()=>{
97
+ setHistory?.({
98
+ index: -1,
99
+ stack: []
100
+ });
101
+ }, [
102
+ setHistory
103
+ ]);
104
+ return [
105
+ {
106
+ index: history.index,
107
+ stack: history.stack,
108
+ top: history.stack.slice(history.index, history.index + 1)[0]
109
+ },
110
+ {
111
+ push,
112
+ pop,
113
+ undo,
114
+ redo,
115
+ set,
116
+ select,
117
+ clearSelect,
118
+ reset
119
+ }
120
+ ];
121
+ }
122
+ export { useHistory as default };
@@ -1,2 +1,2 @@
1
- import { Lang } from '../zh_CN';
1
+ import type { Lang } from '../zh_CN';
2
2
  export default function useLang(): Lang;
@@ -0,0 +1,6 @@
1
+ import useStore from "./useStore.js";
2
+ function useLang() {
3
+ const { lang } = useStore();
4
+ return lang;
5
+ }
6
+ export { useLang as default };
@@ -0,0 +1,25 @@
1
+ import { useCallback } from "react";
2
+ import useDispatcher from "./useDispatcher.js";
3
+ import useStore from "./useStore.js";
4
+ function useOperation() {
5
+ const { operation } = useStore();
6
+ const { setOperation } = useDispatcher();
7
+ const set = useCallback((operation)=>{
8
+ setOperation?.(operation);
9
+ }, [
10
+ setOperation
11
+ ]);
12
+ const reset = useCallback(()=>{
13
+ setOperation?.(void 0);
14
+ }, [
15
+ setOperation
16
+ ]);
17
+ return [
18
+ operation,
19
+ {
20
+ set,
21
+ reset
22
+ }
23
+ ];
24
+ }
25
+ export { useOperation as default };
@@ -0,0 +1,28 @@
1
+ import { useCallback } from "react";
2
+ import useBounds from "./useBounds.js";
3
+ import useCursor from "./useCursor.js";
4
+ import useEmiter from "./useEmiter.js";
5
+ import useHistory from "./useHistory.js";
6
+ import useOperation from "./useOperation.js";
7
+ function useReset() {
8
+ const emiter = useEmiter();
9
+ const [, boundsDispatcher] = useBounds();
10
+ const [, cursorDispatcher] = useCursor();
11
+ const [, historyDispatcher] = useHistory();
12
+ const [, operatioDispatcher] = useOperation();
13
+ const reset = useCallback(()=>{
14
+ emiter.reset();
15
+ historyDispatcher.reset();
16
+ boundsDispatcher.reset();
17
+ cursorDispatcher.reset();
18
+ operatioDispatcher.reset();
19
+ }, [
20
+ emiter,
21
+ historyDispatcher,
22
+ boundsDispatcher,
23
+ cursorDispatcher,
24
+ operatioDispatcher
25
+ ]);
26
+ return reset;
27
+ }
28
+ export { useReset as default };
@@ -0,0 +1,2 @@
1
+ import type { ScreenshotsContextStore } from '../ScreenshotsContext';
2
+ export default function useStore(): ScreenshotsContextStore;
@@ -0,0 +1,7 @@
1
+ import { useContext } from "react";
2
+ import ScreenshotsContext from "../ScreenshotsContext.js";
3
+ function useStore() {
4
+ const { store } = useContext(ScreenshotsContext);
5
+ return store;
6
+ }
7
+ export { useStore as default };
@@ -1,7 +1,7 @@
1
- import { ReactElement } from 'react';
1
+ import type { ReactElement } from 'react';
2
2
  import './icons/iconfont.less';
3
3
  import './screenshots.less';
4
- import { Lang } from './zh_CN';
4
+ import type { Lang } from './zh_CN';
5
5
  export interface ScreenshotsProps {
6
6
  url?: string;
7
7
  width: number;
@@ -0,0 +1,140 @@
1
+ import { jsx, jsxs } from "react/jsx-runtime";
2
+ import { useCallback, useLayoutEffect, useRef, useState } from "react";
3
+ import composeImage from "./composeImage.js";
4
+ import "./icons/iconfont.css";
5
+ import "./screenshots.css";
6
+ import ScreenshotsBackground from "./ScreenshotsBackground/index.js";
7
+ import ScreenshotsCanvas from "./ScreenshotsCanvas/index.js";
8
+ import ScreenshotsContext from "./ScreenshotsContext.js";
9
+ import ScreenshotsOperations from "./ScreenshotsOperations/index.js";
10
+ import useGetLoadedImage from "./useGetLoadedImage.js";
11
+ import zh_CN from "./zh_CN.js";
12
+ function Screenshots({ url, width, height, lang, className, ...props }) {
13
+ const image = useGetLoadedImage(url);
14
+ const canvasContextRef = useRef(null);
15
+ const emiterRef = useRef({});
16
+ const [history, setHistory] = useState({
17
+ index: -1,
18
+ stack: []
19
+ });
20
+ const [bounds, setBounds] = useState(null);
21
+ const [cursor, setCursor] = useState('move');
22
+ const [operation, setOperation] = useState(void 0);
23
+ const store = {
24
+ url,
25
+ width,
26
+ height,
27
+ image,
28
+ lang: {
29
+ ...zh_CN,
30
+ ...lang
31
+ },
32
+ emiterRef,
33
+ canvasContextRef,
34
+ history,
35
+ bounds,
36
+ cursor,
37
+ operation
38
+ };
39
+ const call = useCallback((funcName, ...args)=>{
40
+ const func = props[funcName];
41
+ if ('function' == typeof func) func(...args);
42
+ }, [
43
+ props
44
+ ]);
45
+ const dispatcher = {
46
+ call,
47
+ setHistory,
48
+ setBounds,
49
+ setCursor,
50
+ setOperation
51
+ };
52
+ const classNames = [
53
+ 'screenshots'
54
+ ];
55
+ if (className) classNames.push(className);
56
+ const reset = ()=>{
57
+ emiterRef.current = {};
58
+ setHistory({
59
+ index: -1,
60
+ stack: []
61
+ });
62
+ setBounds(null);
63
+ setCursor('move');
64
+ setOperation(void 0);
65
+ };
66
+ const onDoubleClick = useCallback(async (e)=>{
67
+ if (0 !== e.button || !image) return;
68
+ if (bounds && canvasContextRef.current) composeImage({
69
+ image,
70
+ width,
71
+ height,
72
+ history,
73
+ bounds
74
+ }).then((blob)=>{
75
+ call('onOk', blob, bounds);
76
+ reset();
77
+ });
78
+ else {
79
+ const targetBounds = {
80
+ x: 0,
81
+ y: 0,
82
+ width,
83
+ height
84
+ };
85
+ composeImage({
86
+ image,
87
+ width,
88
+ height,
89
+ history,
90
+ bounds: targetBounds
91
+ }).then((blob)=>{
92
+ call('onOk', blob, targetBounds);
93
+ reset();
94
+ });
95
+ }
96
+ }, [
97
+ image,
98
+ history,
99
+ bounds,
100
+ width,
101
+ height,
102
+ call
103
+ ]);
104
+ const onContextMenu = useCallback((e)=>{
105
+ if (2 !== e.button) return;
106
+ e.preventDefault();
107
+ call('onCancel');
108
+ reset();
109
+ }, [
110
+ call
111
+ ]);
112
+ useLayoutEffect(()=>{
113
+ reset();
114
+ }, [
115
+ url
116
+ ]);
117
+ return /*#__PURE__*/ jsx(ScreenshotsContext.Provider, {
118
+ value: {
119
+ store,
120
+ dispatcher
121
+ },
122
+ children: /*#__PURE__*/ jsxs("div", {
123
+ className: classNames.join(' '),
124
+ style: {
125
+ width,
126
+ height
127
+ },
128
+ onDoubleClick: onDoubleClick,
129
+ onContextMenu: onContextMenu,
130
+ children: [
131
+ /*#__PURE__*/ jsx(ScreenshotsBackground, {}),
132
+ /*#__PURE__*/ jsx(ScreenshotsCanvas, {
133
+ ref: canvasContextRef
134
+ }),
135
+ /*#__PURE__*/ jsx(ScreenshotsOperations, {})
136
+ ]
137
+ })
138
+ });
139
+ }
140
+ export { Screenshots as default };
@@ -1,5 +1,5 @@
1
- import { ArrowData, ArrowEditData } from '.';
2
- import { HistoryItemSource } from '../../types';
1
+ import type { ArrowData, ArrowEditData } from '.';
2
+ import type { HistoryItemSource } from '../../types';
3
3
  export declare function getEditedArrowData(action: HistoryItemSource<ArrowData, ArrowEditData>): {
4
4
  x1: number;
5
5
  x2: number;
@@ -0,0 +1,51 @@
1
+ import { ArrowEditType } from "./index.js";
2
+ import { drawDragCircle } from "../utils.js";
3
+ function getEditedArrowData(action) {
4
+ let { x1, y1, x2, y2 } = action.data;
5
+ action.editHistory.forEach(({ data })=>{
6
+ const x = data.x2 - data.x1;
7
+ const y = data.y2 - data.y1;
8
+ if (data.type === ArrowEditType.Move) {
9
+ x1 += x;
10
+ y1 += y;
11
+ x2 += x;
12
+ y2 += y;
13
+ } else if (data.type === ArrowEditType.MoveStart) {
14
+ x1 += x;
15
+ y1 += y;
16
+ } else if (data.type === ArrowEditType.MoveEnd) {
17
+ x2 += x;
18
+ y2 += y;
19
+ }
20
+ });
21
+ return {
22
+ ...action.data,
23
+ x1,
24
+ x2,
25
+ y1,
26
+ y2
27
+ };
28
+ }
29
+ function draw(ctx, action) {
30
+ const { size, color, x1, x2, y1, y2 } = getEditedArrowData(action);
31
+ ctx.lineCap = 'round';
32
+ ctx.lineJoin = 'bevel';
33
+ ctx.lineWidth = size;
34
+ ctx.strokeStyle = color;
35
+ const dx = x2 - x1;
36
+ const dy = y2 - y1;
37
+ const length = 3 * size;
38
+ const angle = Math.atan2(dy, dx);
39
+ ctx.beginPath();
40
+ ctx.moveTo(x1, y1);
41
+ ctx.lineTo(x2, y2);
42
+ ctx.lineTo(x2 - length * Math.cos(angle - Math.PI / 6), y2 - length * Math.sin(angle - Math.PI / 6));
43
+ ctx.moveTo(x2, y2);
44
+ ctx.lineTo(x2 - length * Math.cos(angle + Math.PI / 6), y2 - length * Math.sin(angle + Math.PI / 6));
45
+ ctx.stroke();
46
+ if (action.isSelected) {
47
+ drawDragCircle(ctx, x1, y1);
48
+ drawDragCircle(ctx, x2, y2);
49
+ }
50
+ }
51
+ export { draw as default, getEditedArrowData };
@@ -1,4 +1,4 @@
1
- import { ReactElement } from 'react';
1
+ import type { ReactElement } from 'react';
2
2
  export interface ArrowData {
3
3
  size: number;
4
4
  color: string;
@@ -0,0 +1,153 @@
1
+ import { jsx } from "react/jsx-runtime";
2
+ import { useCallback, useRef, useState } from "react";
3
+ import ScreenshotsButton from "../../ScreenshotsButton/index.js";
4
+ import ScreenshotsSizeColor from "../../ScreenshotsSizeColor/index.js";
5
+ import useCanvasMousedown from "../../hooks/useCanvasMousedown.js";
6
+ import useCanvasMousemove from "../../hooks/useCanvasMousemove.js";
7
+ import useCanvasMouseup from "../../hooks/useCanvasMouseup.js";
8
+ import { HistoryItemType } from "../../types.js";
9
+ import useCursor from "../../hooks/useCursor.js";
10
+ import useOperation from "../../hooks/useOperation.js";
11
+ import useHistory from "../../hooks/useHistory.js";
12
+ import useCanvasContextRef from "../../hooks/useCanvasContextRef.js";
13
+ import { isHit, isHitCircle } from "../utils.js";
14
+ import useDrawSelect from "../../hooks/useDrawSelect.js";
15
+ import draw, { getEditedArrowData } from "./draw.js";
16
+ import useLang from "../../hooks/useLang.js";
17
+ var Arrow_ArrowEditType = /*#__PURE__*/ function(ArrowEditType) {
18
+ ArrowEditType[ArrowEditType["Move"] = 0] = "Move";
19
+ ArrowEditType[ArrowEditType["MoveStart"] = 1] = "MoveStart";
20
+ ArrowEditType[ArrowEditType["MoveEnd"] = 2] = "MoveEnd";
21
+ return ArrowEditType;
22
+ }({});
23
+ function Arrow() {
24
+ const lang = useLang();
25
+ const [, cursorDispatcher] = useCursor();
26
+ const [operation, operationDispatcher] = useOperation();
27
+ const [history, historyDispatcher] = useHistory();
28
+ const canvasContextRef = useCanvasContextRef();
29
+ const [size, setSize] = useState(3);
30
+ const [color, setColor] = useState('#ee5126');
31
+ const arrowRef = useRef(null);
32
+ const arrowEditRef = useRef(null);
33
+ const checked = 'Arrow' === operation;
34
+ const selectArrow = useCallback(()=>{
35
+ operationDispatcher.set('Arrow');
36
+ cursorDispatcher.set('default');
37
+ }, [
38
+ operationDispatcher,
39
+ cursorDispatcher
40
+ ]);
41
+ const onSelectArrow = useCallback(()=>{
42
+ if (checked) return;
43
+ selectArrow();
44
+ historyDispatcher.clearSelect();
45
+ }, [
46
+ checked,
47
+ selectArrow,
48
+ historyDispatcher
49
+ ]);
50
+ const onDrawSelect = useCallback((action, e)=>{
51
+ if ('Arrow' !== action.name || !canvasContextRef.current) return;
52
+ const source = action;
53
+ selectArrow();
54
+ const { x1, y1, x2, y2 } = getEditedArrowData(source);
55
+ let type = 0;
56
+ if (isHitCircle(canvasContextRef.current.canvas, e, {
57
+ x: x1,
58
+ y: y1
59
+ })) type = 1;
60
+ else if (isHitCircle(canvasContextRef.current.canvas, e, {
61
+ x: x2,
62
+ y: y2
63
+ })) type = 2;
64
+ arrowEditRef.current = {
65
+ type: HistoryItemType.Edit,
66
+ data: {
67
+ type,
68
+ x1: e.clientX,
69
+ y1: e.clientY,
70
+ x2: e.clientX,
71
+ y2: e.clientY
72
+ },
73
+ source
74
+ };
75
+ historyDispatcher.select(action);
76
+ }, [
77
+ canvasContextRef,
78
+ selectArrow,
79
+ historyDispatcher
80
+ ]);
81
+ const onMousedown = useCallback((e)=>{
82
+ if (!checked || arrowRef.current || !canvasContextRef.current) return;
83
+ const { left, top } = canvasContextRef.current.canvas.getBoundingClientRect();
84
+ arrowRef.current = {
85
+ name: 'Arrow',
86
+ type: HistoryItemType.Source,
87
+ data: {
88
+ size,
89
+ color,
90
+ x1: e.clientX - left,
91
+ y1: e.clientY - top,
92
+ x2: e.clientX - left,
93
+ y2: e.clientY - top
94
+ },
95
+ editHistory: [],
96
+ draw: draw,
97
+ isHit: isHit
98
+ };
99
+ }, [
100
+ checked,
101
+ color,
102
+ size,
103
+ canvasContextRef
104
+ ]);
105
+ const onMousemove = useCallback((e)=>{
106
+ if (!checked || !canvasContextRef.current) return;
107
+ if (arrowEditRef.current) {
108
+ arrowEditRef.current.data.x2 = e.clientX;
109
+ arrowEditRef.current.data.y2 = e.clientY;
110
+ if (history.top !== arrowEditRef.current) {
111
+ arrowEditRef.current.source.editHistory.push(arrowEditRef.current);
112
+ historyDispatcher.push(arrowEditRef.current);
113
+ } else historyDispatcher.set(history);
114
+ } else if (arrowRef.current) {
115
+ const { left, top } = canvasContextRef.current.canvas.getBoundingClientRect();
116
+ arrowRef.current.data.x2 = e.clientX - left;
117
+ arrowRef.current.data.y2 = e.clientY - top;
118
+ if (history.top !== arrowRef.current) historyDispatcher.push(arrowRef.current);
119
+ else historyDispatcher.set(history);
120
+ }
121
+ }, [
122
+ checked,
123
+ history,
124
+ canvasContextRef,
125
+ historyDispatcher
126
+ ]);
127
+ const onMouseup = useCallback(()=>{
128
+ if (!checked) return;
129
+ if (arrowRef.current) historyDispatcher.clearSelect();
130
+ arrowRef.current = null;
131
+ arrowEditRef.current = null;
132
+ }, [
133
+ checked,
134
+ historyDispatcher
135
+ ]);
136
+ useDrawSelect(onDrawSelect);
137
+ useCanvasMousedown(onMousedown);
138
+ useCanvasMousemove(onMousemove);
139
+ useCanvasMouseup(onMouseup);
140
+ return /*#__PURE__*/ jsx(ScreenshotsButton, {
141
+ title: lang.operation_arrow_title,
142
+ icon: "icon-arrow",
143
+ checked: checked,
144
+ onClick: onSelectArrow,
145
+ option: /*#__PURE__*/ jsx(ScreenshotsSizeColor, {
146
+ size: size,
147
+ color: color,
148
+ onSizeChange: setSize,
149
+ onColorChange: setColor
150
+ })
151
+ });
152
+ }
153
+ export { Arrow_ArrowEditType as ArrowEditType, Arrow as default };
@@ -1,3 +1,3 @@
1
- import { BrushData, BrushEditData } from '.';
2
- import { HistoryItemSource } from '../../types';
1
+ import type { BrushData, BrushEditData } from '.';
2
+ import type { HistoryItemSource } from '../../types';
3
3
  export default function draw(ctx: CanvasRenderingContext2D, action: HistoryItemSource<BrushData, BrushEditData>): void;
@@ -0,0 +1,31 @@
1
+ function draw(ctx, action) {
2
+ const { size, color, points } = action.data;
3
+ ctx.lineCap = 'round';
4
+ ctx.lineJoin = 'round';
5
+ ctx.lineWidth = size;
6
+ ctx.strokeStyle = color;
7
+ const distance = action.editHistory.reduce((distance, { data })=>({
8
+ x: distance.x + data.x2 - data.x1,
9
+ y: distance.y + data.y2 - data.y1
10
+ }), {
11
+ x: 0,
12
+ y: 0
13
+ });
14
+ ctx.beginPath();
15
+ points.forEach((item, index)=>{
16
+ if (0 === index) ctx.moveTo(item.x + distance.x, item.y + distance.y);
17
+ else ctx.lineTo(item.x + distance.x, item.y + distance.y);
18
+ });
19
+ ctx.stroke();
20
+ if (action.isSelected) {
21
+ ctx.lineWidth = 1;
22
+ ctx.strokeStyle = '#000000';
23
+ ctx.beginPath();
24
+ points.forEach((item, index)=>{
25
+ if (0 === index) ctx.moveTo(item.x + distance.x, item.y + distance.y);
26
+ else ctx.lineTo(item.x + distance.x, item.y + distance.y);
27
+ });
28
+ ctx.stroke();
29
+ }
30
+ }
31
+ export { draw as default };
@@ -1,5 +1,5 @@
1
- import { ReactElement } from 'react';
2
- import { Point } from '../../types';
1
+ import type { ReactElement } from 'react';
2
+ import type { Point } from '../../types';
3
3
  export interface BrushData {
4
4
  size: number;
5
5
  color: string;