@versa_ai/vmml-editor 1.0.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (47) hide show
  1. package/.turbo/turbo-build.log +335 -0
  2. package/CHANGELOG.md +16 -0
  3. package/README.md +1 -0
  4. package/biome.json +7 -0
  5. package/dist/index.d.mts +5 -0
  6. package/dist/index.d.ts +5 -0
  7. package/dist/index.js +2675 -0
  8. package/dist/index.js.map +1 -0
  9. package/dist/index.mjs +2673 -0
  10. package/dist/index.mjs.map +1 -0
  11. package/package.json +48 -0
  12. package/postcss.config.js +3 -0
  13. package/src/assets/css/closeLayer.scss +50 -0
  14. package/src/assets/css/colorSelector.scss +59 -0
  15. package/src/assets/css/editorTextMenu.less +130 -0
  16. package/src/assets/css/editorTextMenu.scss +149 -0
  17. package/src/assets/css/index.scss +252 -0
  18. package/src/assets/css/loading.scss +31 -0
  19. package/src/assets/css/maxTextLayer.scss +31 -0
  20. package/src/assets/img/icon_Brush.png +0 -0
  21. package/src/assets/img/icon_Change.png +0 -0
  22. package/src/assets/img/icon_Cut.png +0 -0
  23. package/src/assets/img/icon_Face.png +0 -0
  24. package/src/assets/img/icon_Graffiti.png +0 -0
  25. package/src/assets/img/icon_Mute.png +0 -0
  26. package/src/assets/img/icon_Refresh.png +0 -0
  27. package/src/assets/img/icon_Text1.png +0 -0
  28. package/src/assets/img/icon_Text2.png +0 -0
  29. package/src/assets/img/icon_Volume.png +0 -0
  30. package/src/assets/img/icon_Word.png +0 -0
  31. package/src/components/CloseLayer.tsx +25 -0
  32. package/src/components/ColorSelector.tsx +90 -0
  33. package/src/components/Controls.tsx +32 -0
  34. package/src/components/EditorCanvas.tsx +566 -0
  35. package/src/components/Loading.tsx +16 -0
  36. package/src/components/MaxTextLayer.tsx +27 -0
  37. package/src/components/SeekBar.tsx +126 -0
  38. package/src/components/TextMenu.tsx +332 -0
  39. package/src/components/VideoMenu.tsx +49 -0
  40. package/src/index.tsx +551 -0
  41. package/src/utils/HistoryClass.ts +131 -0
  42. package/src/utils/VmmlConverter.ts +339 -0
  43. package/src/utils/const.ts +10 -0
  44. package/src/utils/keyBoardUtils.ts +199 -0
  45. package/src/utils/usePeekControl.ts +242 -0
  46. package/tsconfig.json +5 -0
  47. package/tsup.config.ts +14 -0
package/dist/index.js ADDED
@@ -0,0 +1,2675 @@
1
+ 'use strict';
2
+
3
+ var vmmlPlayer = require('@versa_ai/vmml-player');
4
+ var react = require('react');
5
+ var vmmlUtils = require('@versa_ai/vmml-utils');
6
+ var remotion = require('remotion');
7
+ var jsxRuntime = require('react/jsx-runtime');
8
+ var fabric = require('fabric');
9
+ var uuid = require('uuid');
10
+ var domToImage = require('dom-to-image');
11
+
12
+ // src/index.tsx
13
+
14
+ // src/assets/css/index.scss
15
+ var css = `@charset "UTF-8";
16
+ .editor {
17
+ background: #000;
18
+ width: 100%;
19
+ min-height: 100vh;
20
+ overflow: hidden;
21
+ display: flex;
22
+ flex-direction: column;
23
+ }
24
+ .editor .padding-box {
25
+ flex: 1;
26
+ }
27
+ .editor > .header {
28
+ width: 100%;
29
+ display: flex;
30
+ justify-content: space-between;
31
+ align-items: center;
32
+ height: 11.467vw;
33
+ padding-left: 4.4vw;
34
+ padding-right: 3.2vw;
35
+ box-sizing: border-box;
36
+ position: relative;
37
+ }
38
+ .editor > .header > .close {
39
+ width: 4vw;
40
+ height: 4vw;
41
+ }
42
+ .editor > .header > .close img {
43
+ width: 100%;
44
+ height: 100%;
45
+ }
46
+ .editor > .header > .history-operate {
47
+ height: 7.2vw;
48
+ display: none;
49
+ align-items: center;
50
+ position: absolute;
51
+ left: 50%;
52
+ top: 50%;
53
+ transform: translate(-50%, -50%);
54
+ }
55
+ .editor > .header > .history-operate img {
56
+ width: 4.667vw;
57
+ height: 5.067vw;
58
+ }
59
+ .editor > .header > .history-operate > img:last-child {
60
+ margin-left: 8vw;
61
+ }
62
+ .editor > .header > .next-button {
63
+ width: 16vw;
64
+ height: 7.2vw;
65
+ line-height: 7.2vw;
66
+ background: #1677FF;
67
+ border-radius: 6.533vw;
68
+ text-align: center;
69
+ font-size: 3.2vw;
70
+ color: #fff;
71
+ }
72
+ .editor .text-style {
73
+ filter: blur(10px);
74
+ }
75
+ .editor .editor-vessel {
76
+ padding-top: 3.2vw;
77
+ }
78
+ .editor .main {
79
+ width: 81.467vw;
80
+ height: 144.8vw;
81
+ margin: auto;
82
+ position: relative;
83
+ display: flex;
84
+ justify-content: center;
85
+ border-radius: 3.2vw;
86
+ overflow: hidden;
87
+ }
88
+ .editor .main .vessel {
89
+ width: 100%;
90
+ height: 100%;
91
+ }
92
+ .editor .main .controls-box {
93
+ height: 12vw;
94
+ position: absolute;
95
+ bottom: 0;
96
+ width: 100%;
97
+ border-radius: 3.2vw;
98
+ }
99
+ .editor .main .player-controls {
100
+ display: flex;
101
+ align-items: center;
102
+ width: 100%;
103
+ height: 100%;
104
+ padding: 0 2.13vw;
105
+ box-sizing: border-box;
106
+ background: linear-gradient(180deg, rgba(0, 0, 0, 0) 0%, rgba(0, 0, 0, 0.6) 100%);
107
+ }
108
+ .editor .main .player-controls .mr-16 {
109
+ margin-right: 2.13vw;
110
+ }
111
+ .editor .main .player-controls .player-controls-toggle > img {
112
+ display: block;
113
+ width: 4.8vw;
114
+ height: 4.8vw;
115
+ cursor: pointer;
116
+ }
117
+ .editor .main .player-controls .player-controls-seekbar {
118
+ flex: 1;
119
+ position: relative;
120
+ }
121
+ .editor .main .player-controls .player-controls-seekbar .seekbar-container {
122
+ height: 100%;
123
+ user-select: none;
124
+ touch-action: none;
125
+ position: relative;
126
+ cursor: pointer;
127
+ box-sizing: border-box;
128
+ }
129
+ .editor .main .player-controls .player-controls-seekbar .seekbar-container .seekbar-background {
130
+ user-select: none;
131
+ height: 1.6vw;
132
+ width: 100%;
133
+ background-color: rgba(255, 255, 255, 0.2);
134
+ border-radius: 1vw;
135
+ }
136
+ .editor .main .player-controls .player-controls-seekbar .seekbar-container .seekbar-background .seekbar-fill {
137
+ position: absolute;
138
+ user-select: none;
139
+ width: 100%;
140
+ height: 100%;
141
+ border-radius: 1vw;
142
+ }
143
+ .editor .main .player-controls .player-controls-seekbar .seekbar-container .seekbar-background .seekbar-line {
144
+ height: 100%;
145
+ border-radius: 1vw;
146
+ background-color: #eeeeee;
147
+ }
148
+ .editor .main .player-controls .player-controls-seekbar .seekbar-container .seekbar-background .seekbar-sign {
149
+ width: 10px;
150
+ position: absolute;
151
+ top: 50%;
152
+ margin-top: -6px;
153
+ }
154
+ .editor .main .player-controls .player-controls-seekbar .seekbar-container .seekbar-background .seekbar-cirle {
155
+ position: absolute;
156
+ top: -0.8vw;
157
+ width: 3.2vw;
158
+ height: 3.2vw;
159
+ border-radius: 50%;
160
+ background: #eeeeee;
161
+ }
162
+ .editor .main .player-controls .player-controls-time {
163
+ width: 10vw;
164
+ color: #fff;
165
+ }
166
+ .editor .main .play-btn {
167
+ position: absolute;
168
+ bottom: 4vw;
169
+ left: 3vw;
170
+ width: 4.8vw;
171
+ height: 4.8vw;
172
+ }
173
+ .editor .main .play-btn img {
174
+ width: 100%;
175
+ height: 100%;
176
+ display: block;
177
+ }
178
+ .editor .main .opacity-06 {
179
+ opacity: 0.6;
180
+ }
181
+ .editor .footer {
182
+ display: flex;
183
+ justify-content: center;
184
+ box-sizing: border-box;
185
+ width: 100%;
186
+ padding: 0 20.333vw 10.933vw;
187
+ }
188
+ .editor .footer > div {
189
+ width: 30%;
190
+ margin: 0 15%;
191
+ }
192
+ .editor .footer > div img {
193
+ width: 6.4vw;
194
+ height: 6.4vw;
195
+ display: block;
196
+ margin: auto;
197
+ }
198
+ .editor .footer > div p {
199
+ font-size: 3.2vw;
200
+ color: #fff;
201
+ margin-top: 1.867vw;
202
+ text-align: center;
203
+ }
204
+ .editor .not-show-text {
205
+ justify-content: space-around;
206
+ }
207
+ .editor .editor-video-menu {
208
+ position: fixed;
209
+ height: 0;
210
+ width: 100%;
211
+ background: #1E1E1E;
212
+ bottom: 0;
213
+ border-radius: 8px 8px 0 0;
214
+ transition: all 0.5s ease-in-out;
215
+ }
216
+ .editor .editor-video-menu.active {
217
+ height: 38.13vh;
218
+ }
219
+ .editor .editor-video-menu .editor-video-menu-header {
220
+ display: flex;
221
+ padding: 1.6vw 1.6vw 0;
222
+ height: 4.81vh;
223
+ line-height: 4.81vh;
224
+ color: rgba(255, 255, 255, 0.4);
225
+ overflow: hidden;
226
+ overflow-x: auto;
227
+ }
228
+ .editor .editor-video-menu .editor-video-menu-header::-webkit-scrollbar {
229
+ display: none; /* \u9690\u85CF\u6EDA\u52A8\u6761 */
230
+ }
231
+ .editor .editor-video-menu .editor-video-menu-header > div {
232
+ margin: 0 3.2vw;
233
+ white-space: nowrap;
234
+ }
235
+ .editor .editor-video-menu .editor-video-menu-header .active {
236
+ color: #FFFFFF;
237
+ }
238
+ .editor .editor-video-menu .editor-video-menu-itmes {
239
+ padding: 0 3.33vw;
240
+ max-height: calc(100% - 4.81vh - 1.6vw);
241
+ display: grid;
242
+ grid-template-columns: repeat(4, 1fr);
243
+ row-gap: 3.2vw;
244
+ column-gap: 2.6vw;
245
+ overflow: auto;
246
+ }
247
+ .editor .editor-video-menu .editor-video-menu-itmes > div {
248
+ width: 21.33vw;
249
+ height: 21.33vw;
250
+ background-color: #1e1e1e;
251
+ }
252
+ .editor .editor-video-menu .editor-video-menu-itmes > div img {
253
+ width: 100%;
254
+ height: 100%;
255
+ object-fit: contain;
256
+ }
257
+ /*# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VSb290IjoiRDpcXHByb2plY3RzXFx2bW1sLXBsYXllclxccGFja2FnZXNcXGVkaXRvclxcc3JjXFxhc3NldHNcXGNzcyIsInNvdXJjZXMiOlsiaW5kZXguc2NzcyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiO0FBQUE7RUFDRTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7O0FBQ0E7RUFDRTs7QUFHRjtFQUNFO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTs7QUFDQTtFQUNFO0VBQ0E7O0FBQ0E7RUFDRTtFQUNBOztBQUdKO0VBQ0U7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7O0FBQ0E7RUFDRTtFQUNBOztBQUVGO0VBQ0U7O0FBR0o7RUFDRTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBOztBQUdKO0VBQ0U7O0FBR0Y7RUFDRTs7QUFHRjtFQUNFO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7O0FBQ0E7RUFDRTtFQUNBOztBQUVGO0VBQ0U7RUFDQTtFQUNBO0VBQ0E7RUFDQTs7QUFFRjtFQUNFO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBOztBQUNBO0VBQ0U7O0FBR0E7RUFDRTtFQUNBO0VBQ0E7RUFDQTs7QUFHSjtFQUNFO0VBQ0E7O0FBQ0E7RUFDRTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7O0FBQ0E7RUFDRTtFQUNBO0VBQ0E7RUFDQTtFQUNBOztBQUNBO0VBQ0U7RUFDQTtFQUNBO0VBQ0E7RUFDQTs7QUFFRjtFQUNFO0VBQ0E7RUFDQTs7QUFFRjtFQUNFO0VBQ0E7RUFDQTtFQUNBOztBQUVGO0VBQ0U7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBOztBQUtSO0VBQ0U7RUFDQTs7QUFHSjtFQUNFO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7O0FBQ0E7RUFDRTtFQUNBO0VBQ0E7O0FBR0o7RUFDRTs7QUFLSjtFQUNFO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7O0FBQ0E7RUFDRTtFQUNBOztBQUNBO0VBQ0U7RUFDQTtFQUNBO0VBQ0E7O0FBRUY7RUFDRTtFQUNBO0VBQ0E7RUFDQTs7QUFLTjtFQUNFOztBQUdGO0VBQ0U7RUFFQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7O0FBQ0E7RUFDRTs7QUFFRjtFQUNFO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBOztBQUNBO0VBQ0U7O0FBRUY7RUFDRTtFQUNBOztBQUVGO0VBQ0U7O0FBR0o7RUFDRTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTs7QUFDQTtFQUNFO0VBQ0E7RUFDQTs7QUFDQTtFQUNFO0VBQ0E7RUFDQSIsInNvdXJjZXNDb250ZW50IjpbIi5lZGl0b3J7XHJcbiAgYmFja2dyb3VuZDogIzAwMDtcclxuICB3aWR0aDogMTAwJTtcclxuICBtaW4taGVpZ2h0OiAxMDB2aDtcclxuICBvdmVyZmxvdzogaGlkZGVuO1xyXG4gIGRpc3BsYXk6IGZsZXg7XHJcbiAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjtcclxuICAucGFkZGluZy1ib3gge1xyXG4gICAgZmxleDogMTtcclxuICB9XHJcbiAgLy8g6aG26YOoXHJcbiAgJj4uaGVhZGVye1xyXG4gICAgd2lkdGg6IDEwMCU7XHJcbiAgICBkaXNwbGF5OiBmbGV4O1xyXG4gICAganVzdGlmeS1jb250ZW50OiBzcGFjZS1iZXR3ZWVuO1xyXG4gICAgYWxpZ24taXRlbXM6IGNlbnRlcjtcclxuICAgIGhlaWdodDogMTEuNDY3dnc7XHJcbiAgICBwYWRkaW5nLWxlZnQ6IDQuNHZ3O1xyXG4gICAgcGFkZGluZy1yaWdodDogMy4ydnc7XHJcbiAgICBib3gtc2l6aW5nOiBib3JkZXItYm94O1xyXG4gICAgcG9zaXRpb246IHJlbGF0aXZlO1xyXG4gICAgJj4uY2xvc2V7XHJcbiAgICAgIHdpZHRoOiA0dnc7XHJcbiAgICAgIGhlaWdodDogNHZ3O1xyXG4gICAgICBpbWd7XHJcbiAgICAgICAgd2lkdGg6IDEwMCU7XHJcbiAgICAgICAgaGVpZ2h0OiAxMDAlO1xyXG4gICAgICB9XHJcbiAgICB9XHJcbiAgICAmPi5oaXN0b3J5LW9wZXJhdGV7XHJcbiAgICAgIGhlaWdodDogNy4ydnc7XHJcbiAgICAgIGRpc3BsYXk6IG5vbmU7XHJcbiAgICAgIGFsaWduLWl0ZW1zOiBjZW50ZXI7XHJcbiAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTtcclxuICAgICAgbGVmdDogNTAlO1xyXG4gICAgICB0b3A6IDUwJTtcclxuICAgICAgdHJhbnNmb3JtOiB0cmFuc2xhdGUoLTUwJSwtNTAlKTtcclxuICAgICAgaW1ne1xyXG4gICAgICAgIHdpZHRoOiA0LjY2N3Z3O1xyXG4gICAgICAgIGhlaWdodDogNS4wNjd2dztcclxuICAgICAgfVxyXG4gICAgICAmPmltZzpsYXN0LWNoaWxke1xyXG4gICAgICAgIG1hcmdpbi1sZWZ0OiA4dnc7XHJcbiAgICAgIH1cclxuICAgIH1cclxuICAgICY+Lm5leHQtYnV0dG9ue1xyXG4gICAgICB3aWR0aDogMTZ2dztcclxuICAgICAgaGVpZ2h0OiA3LjJ2dztcclxuICAgICAgbGluZS1oZWlnaHQ6IDcuMnZ3O1xyXG4gICAgICBiYWNrZ3JvdW5kOiAjMTY3N0ZGO1xyXG4gICAgICBib3JkZXItcmFkaXVzOiA2LjUzM3Z3O1xyXG4gICAgICB0ZXh0LWFsaWduOiBjZW50ZXI7XHJcbiAgICAgIGZvbnQtc2l6ZTogMy4ydnc7XHJcbiAgICAgIGNvbG9yOiAjZmZmO1xyXG4gICAgfVxyXG4gIH1cclxuICAudGV4dC1zdHlsZXtcclxuICAgIGZpbHRlcjpibHVyKDEwcHgpXHJcbiAgfVxyXG5cclxuICAuZWRpdG9yLXZlc3NlbCB7XHJcbiAgICBwYWRkaW5nLXRvcDogMy4ydnc7XHJcbiAgfVxyXG4gIC8vcGxheWVy5LiO55S75biDXHJcbiAgLm1haW57XHJcbiAgICB3aWR0aDogODEuNDY3dnc7XHJcbiAgICBoZWlnaHQ6IDE0NC44dnc7XHJcbiAgICBtYXJnaW46IGF1dG87XHJcbiAgICBwb3NpdGlvbjogcmVsYXRpdmU7XHJcbiAgICBkaXNwbGF5OiBmbGV4O1xyXG4gICAganVzdGlmeS1jb250ZW50OiBjZW50ZXI7XHJcbiAgICBib3JkZXItcmFkaXVzOiAzLjJ2dztcclxuICAgIG92ZXJmbG93OiBoaWRkZW47XHJcbiAgICAudmVzc2VsIHtcclxuICAgICAgd2lkdGg6IDEwMCU7XHJcbiAgICAgIGhlaWdodDogMTAwJTtcclxuICAgIH1cclxuICAgIC5jb250cm9scy1ib3gge1xyXG4gICAgICBoZWlnaHQ6IDEydnc7XHJcbiAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTtcclxuICAgICAgYm90dG9tOiAwO1xyXG4gICAgICB3aWR0aDogMTAwJTtcclxuICAgICAgYm9yZGVyLXJhZGl1czogMy4ydnc7XHJcbiAgICB9XHJcbiAgICAucGxheWVyLWNvbnRyb2xzIHtcclxuICAgICAgZGlzcGxheTogZmxleDtcclxuICAgICAgYWxpZ24taXRlbXM6IGNlbnRlcjtcclxuICAgICAgd2lkdGg6IDEwMCU7XHJcbiAgICAgIGhlaWdodDogMTAwJTtcclxuICAgICAgcGFkZGluZzogMCAyLjEzdnc7XHJcbiAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XHJcbiAgICAgIGJhY2tncm91bmQ6IGxpbmVhci1ncmFkaWVudCggMTgwZGVnLCByZ2JhKDAsMCwwLDApIDAlLCByZ2JhKDAsMCwwLDAuNikgMTAwJSk7XHJcbiAgICAgIC5tci0xNiB7XHJcbiAgICAgICAgbWFyZ2luLXJpZ2h0OiAyLjEzdnc7XHJcbiAgICAgIH1cclxuICAgICAgLnBsYXllci1jb250cm9scy10b2dnbGUge1xyXG4gICAgICAgID5pbWcge1xyXG4gICAgICAgICAgZGlzcGxheTogYmxvY2s7XHJcbiAgICAgICAgICB3aWR0aDogNC44dnc7XHJcbiAgICAgICAgICBoZWlnaHQ6IDQuOHZ3O1xyXG4gICAgICAgICAgY3Vyc29yOiBwb2ludGVyO1xyXG4gICAgICAgIH1cclxuICAgICAgfVxyXG4gICAgICAucGxheWVyLWNvbnRyb2xzLXNlZWtiYXIge1xyXG4gICAgICAgIGZsZXg6IDE7XHJcbiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlO1xyXG4gICAgICAgIC5zZWVrYmFyLWNvbnRhaW5lciB7XHJcbiAgICAgICAgICBoZWlnaHQ6IDEwMCU7XHJcbiAgICAgICAgICB1c2VyLXNlbGVjdDogbm9uZTtcclxuICAgICAgICAgIHRvdWNoLWFjdGlvbjogbm9uZTtcclxuICAgICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTtcclxuICAgICAgICAgIGN1cnNvcjogcG9pbnRlcjtcclxuICAgICAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XHJcbiAgICAgICAgICAuc2Vla2Jhci1iYWNrZ3JvdW5kIHtcclxuICAgICAgICAgICAgdXNlci1zZWxlY3Q6IG5vbmU7XHJcbiAgICAgICAgICAgIGhlaWdodDogMS42dnc7XHJcbiAgICAgICAgICAgIHdpZHRoOiAxMDAlO1xyXG4gICAgICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiByZ2JhKDI1NSwgMjU1LCAyNTUsIDAuMik7XHJcbiAgICAgICAgICAgIGJvcmRlci1yYWRpdXM6IDF2dztcclxuICAgICAgICAgICAgLnNlZWtiYXItZmlsbCB7XHJcbiAgICAgICAgICAgICAgcG9zaXRpb246IGFic29sdXRlO1xyXG4gICAgICAgICAgICAgIHVzZXItc2VsZWN0OiBub25lO1xyXG4gICAgICAgICAgICAgIHdpZHRoOiAxMDAlO1xyXG4gICAgICAgICAgICAgIGhlaWdodDogMTAwJTtcclxuICAgICAgICAgICAgICBib3JkZXItcmFkaXVzOiAxdnc7XHJcbiAgICAgICAgICAgIH1cclxuICAgICAgICAgICAgLnNlZWtiYXItbGluZSB7XHJcbiAgICAgICAgICAgICAgaGVpZ2h0OiAxMDAlO1xyXG4gICAgICAgICAgICAgIGJvcmRlci1yYWRpdXM6IDF2dztcclxuICAgICAgICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiAjZWVlZWVlO1xyXG4gICAgICAgICAgICB9XHJcbiAgICAgICAgICAgIC5zZWVrYmFyLXNpZ24ge1xyXG4gICAgICAgICAgICAgIHdpZHRoOiAxMHB4O1xyXG4gICAgICAgICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTtcclxuICAgICAgICAgICAgICB0b3A6IDUwJTtcclxuICAgICAgICAgICAgICBtYXJnaW4tdG9wOiAtNnB4O1xyXG4gICAgICAgICAgICB9XHJcbiAgICAgICAgICAgIC5zZWVrYmFyLWNpcmxlIHtcclxuICAgICAgICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7XHJcbiAgICAgICAgICAgICAgdG9wOiAtMC44dnc7XHJcbiAgICAgICAgICAgICAgd2lkdGg6IDMuMnZ3O1xyXG4gICAgICAgICAgICAgIGhlaWdodDogMy4ydnc7XHJcbiAgICAgICAgICAgICAgYm9yZGVyLXJhZGl1czogNTAlO1xyXG4gICAgICAgICAgICAgIGJhY2tncm91bmQ6ICNlZWVlZWU7XHJcbiAgICAgICAgICAgIH1cclxuICAgICAgICAgIH1cclxuICAgICAgICB9XHJcbiAgICAgIH1cclxuICAgICAgLnBsYXllci1jb250cm9scy10aW1lIHtcclxuICAgICAgICB3aWR0aDogMTB2dztcclxuICAgICAgICBjb2xvcjogI2ZmZjtcclxuICAgICAgfVxyXG4gICAgfVxyXG4gICAgLnBsYXktYnRuIHtcclxuICAgICAgcG9zaXRpb246IGFic29sdXRlO1xyXG4gICAgICBib3R0b206IDR2dztcclxuICAgICAgbGVmdDogM3Z3O1xyXG4gICAgICB3aWR0aDogNC44dnc7XHJcbiAgICAgIGhlaWdodDogNC44dnc7XHJcbiAgICAgIGltZyB7XHJcbiAgICAgICAgd2lkdGg6IDEwMCU7XHJcbiAgICAgICAgaGVpZ2h0OiAxMDAlO1xyXG4gICAgICAgIGRpc3BsYXk6IGJsb2NrO1xyXG4gICAgICB9XHJcbiAgICB9XHJcbiAgICAub3BhY2l0eS0wNiB7XHJcbiAgICAgIG9wYWNpdHk6IDAuNjtcclxuICAgIH1cclxuICB9XHJcblxyXG4gIC8v5bqV6YOoXHJcbiAgLmZvb3RlcntcclxuICAgIGRpc3BsYXk6IGZsZXg7XHJcbiAgICBqdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjtcclxuICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XHJcbiAgICB3aWR0aDogMTAwJTtcclxuICAgIHBhZGRpbmc6IDAgMjAuMzMzdncgMTAuOTMzdnc7XHJcbiAgICAmPmRpdntcclxuICAgICAgd2lkdGg6IDMwJTtcclxuICAgICAgbWFyZ2luOiAwIDE1JTtcclxuICAgICAgaW1ne1xyXG4gICAgICAgIHdpZHRoOiA2LjR2dztcclxuICAgICAgICBoZWlnaHQ6IDYuNHZ3O1xyXG4gICAgICAgIGRpc3BsYXk6IGJsb2NrO1xyXG4gICAgICAgIG1hcmdpbjogYXV0bztcclxuICAgICAgfVxyXG4gICAgICBwe1xyXG4gICAgICAgIGZvbnQtc2l6ZTogMy4ydnc7XHJcbiAgICAgICAgY29sb3I6ICNmZmY7XHJcbiAgICAgICAgbWFyZ2luLXRvcDogMS44Njd2dztcclxuICAgICAgICB0ZXh0LWFsaWduOiBjZW50ZXI7XHJcbiAgICAgIH1cclxuICAgIH1cclxuICB9XHJcblxyXG4gIC5ub3Qtc2hvdy10ZXh0e1xyXG4gICAganVzdGlmeS1jb250ZW50OiBzcGFjZS1hcm91bmQ7XHJcbiAgfVxyXG5cclxuICAuZWRpdG9yLXZpZGVvLW1lbnUge1xyXG4gICAgcG9zaXRpb246IGZpeGVkO1xyXG4gICAgLy8gaGVpZ2h0OiAzOC4xM3ZoO1xyXG4gICAgaGVpZ2h0OiAwO1xyXG4gICAgd2lkdGg6IDEwMCU7XHJcbiAgICBiYWNrZ3JvdW5kOiAjMUUxRTFFO1xyXG4gICAgYm90dG9tOiAwO1xyXG4gICAgYm9yZGVyLXJhZGl1czogOHB4IDhweCAwIDA7XHJcbiAgICB0cmFuc2l0aW9uOiBhbGwgMC41cyBlYXNlLWluLW91dDsgIFxyXG4gICAgJi5hY3RpdmUge1xyXG4gICAgICBoZWlnaHQ6IDM4LjEzdmg7XHJcbiAgICB9XHJcbiAgICAuZWRpdG9yLXZpZGVvLW1lbnUtaGVhZGVyIHtcclxuICAgICAgZGlzcGxheTogZmxleDtcclxuICAgICAgcGFkZGluZzogMS42dncgMS42dncgMDtcclxuICAgICAgaGVpZ2h0OiA0Ljgxdmg7XHJcbiAgICAgIGxpbmUtaGVpZ2h0OiA0Ljgxdmg7XHJcbiAgICAgIGNvbG9yOiByZ2JhKDI1NSwgMjU1LCAyNTUsIDAuNDApO1xyXG4gICAgICBvdmVyZmxvdzogaGlkZGVuO1xyXG4gICAgICBvdmVyZmxvdy14OiBhdXRvO1xyXG4gICAgICAmOjotd2Via2l0LXNjcm9sbGJhciB7XHJcbiAgICAgICAgZGlzcGxheTogbm9uZTsgLyog6ZqQ6JeP5rua5Yqo5p2hICovXHJcbiAgICAgIH1cclxuICAgICAgPmRpdiB7XHJcbiAgICAgICAgbWFyZ2luOiAwIDMuMnZ3O1xyXG4gICAgICAgIHdoaXRlLXNwYWNlOiBub3dyYXA7XHJcbiAgICAgIH1cclxuICAgICAgLmFjdGl2ZSB7XHJcbiAgICAgICAgY29sb3I6ICNGRkZGRkY7XHJcbiAgICAgIH1cclxuICAgIH1cclxuICAgIC5lZGl0b3ItdmlkZW8tbWVudS1pdG1lcyB7XHJcbiAgICAgIHBhZGRpbmc6IDAgMy4zM3Z3O1xyXG4gICAgICBtYXgtaGVpZ2h0OiBjYWxjKDEwMCUgLSA0LjgxdmggLSAxLjZ2dyk7XHJcbiAgICAgIGRpc3BsYXk6IGdyaWQ7XHJcbiAgICAgIGdyaWQtdGVtcGxhdGUtY29sdW1uczogcmVwZWF0KDQsIDFmcik7XHJcbiAgICAgIHJvdy1nYXA6IDMuMnZ3O1xyXG4gICAgICBjb2x1bW4tZ2FwOiAyLjZ2dztcclxuICAgICAgb3ZlcmZsb3c6IGF1dG87XHJcbiAgICAgID5kaXYge1xyXG4gICAgICAgIHdpZHRoOiAyMS4zM3Z3O1xyXG4gICAgICAgIGhlaWdodDogMjEuMzN2dztcclxuICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiAjMWUxZTFlO1xyXG4gICAgICAgIGltZyB7XHJcbiAgICAgICAgICB3aWR0aDogMTAwJTtcclxuICAgICAgICAgIGhlaWdodDogMTAwJTtcclxuICAgICAgICAgIG9iamVjdC1maXQ6IGNvbnRhaW47XHJcbiAgICAgICAgfVxyXG4gICAgICB9XHJcbiAgICB9XHJcbiAgfVxyXG5cclxufVxyXG4iXX0= */`;
258
+ document.head.appendChild(document.createElement("style")).appendChild(document.createTextNode(css));
259
+
260
+ // src/utils/const.ts
261
+ var closeIcon = "https://mass.alipay.com/finmedia_versaassets/uri/file/as/c5dc68e4-2db5-4ea6-ada6-191bb9128a4c.png";
262
+ var wordIcon = "https://mass.alipay.com/finmedia_versaassets/uri/file/as/6ba37577-5fef-4722-9a61-f7ab5e5790ad.png";
263
+ var emotionIcon = "https://mass.alipay.com/finmedia_versaassets/uri/file/as/a6bb2684-4f26-481a-81dd-90500c1f7544.png";
264
+ var playIcon = "https://mass.alipay.com/finmedia_versaassets/uri/file/as/9c6d947f-071a-4875-9546-fd0dce371928.png";
265
+ var pauseIcon = "https://mass.alipay.com/finmedia_versaassets/uri/file/as/65076da8-c1e4-42a9-90af-839a2e42ace7.png";
266
+ var iconText2 = "https://mass.alipay.com/finmedia_versaassets/uri/file/as/f50a1be1-512b-49f5-8be5-61b85c7cbb66.png";
267
+ var iconText1 = "https://mass.alipay.com/finmedia_versaassets/uri/file/as/f9071de5-48d0-42ca-8b9a-13ae19ed48e3.png";
268
+ var signIcon = "https://mass.alipay.com/finmedia_versaassets/uri/file/as/bcbd9a71-ec40-4c4d-ba03-29c2bec2bf89.png";
269
+ var getFrameFromX = (clientX, durationInFrames, width) => {
270
+ const pos = clientX;
271
+ const frame = Math.round(
272
+ remotion.interpolate(pos, [0, width], [0, durationInFrames - 1], {
273
+ extrapolateLeft: "clamp",
274
+ extrapolateRight: "clamp"
275
+ })
276
+ );
277
+ return frame;
278
+ };
279
+ console.log(2222);
280
+ var SeekBar = ({ player, vmmlRef, frame, durationInFrames, intoEdit, setDragState, signList }) => {
281
+ const containerRef = react.useRef(null);
282
+ const [dragging, setDragging] = react.useState({
283
+ dragging: false
284
+ });
285
+ const fillStyle = react.useMemo(() => {
286
+ return {
287
+ width: `${frame / (durationInFrames - 1) * 100}%`
288
+ };
289
+ }, [frame, durationInFrames]);
290
+ const cirleStyle = react.useMemo(() => {
291
+ return {
292
+ left: `calc(${frame / (durationInFrames - 1) * 100}% - 1.6vw)`
293
+ };
294
+ }, [frame, durationInFrames]);
295
+ const onPointerDown = react.useCallback((e) => {
296
+ var _a;
297
+ if (e.button !== 0) {
298
+ return;
299
+ }
300
+ const { left, width } = (_a = containerRef.current) == null ? void 0 : _a.getBoundingClientRect();
301
+ const _frame = getFrameFromX(
302
+ e.clientX - left,
303
+ durationInFrames,
304
+ width
305
+ );
306
+ setDragState(1);
307
+ setDragging({
308
+ dragging: true,
309
+ wasPlaying: player.isPlaying()
310
+ });
311
+ player.pause();
312
+ player.seekTo(_frame);
313
+ vmmlRef.current && vmmlRef.current.onSeekStart();
314
+ }, [player, durationInFrames]);
315
+ const onPointerMove = react.useCallback((e) => {
316
+ var _a;
317
+ if (!dragging.dragging) {
318
+ return;
319
+ }
320
+ const { left, width } = (_a = containerRef.current) == null ? void 0 : _a.getBoundingClientRect();
321
+ const _frame = getFrameFromX(
322
+ e.clientX - left,
323
+ durationInFrames,
324
+ width
325
+ );
326
+ setDragState(2);
327
+ player.seekTo(_frame);
328
+ }, [player, dragging.dragging, durationInFrames]);
329
+ const onPointerUp = (e) => {
330
+ setDragging({
331
+ dragging: false
332
+ });
333
+ if (!dragging.dragging) {
334
+ return;
335
+ }
336
+ setDragState(3);
337
+ intoEdit();
338
+ vmmlRef.current && vmmlRef.current.onSeekEnd();
339
+ };
340
+ const onClickSign = (sign) => {
341
+ player.pause();
342
+ player.seekTo(sign.inFrame);
343
+ vmmlRef.current && vmmlRef.current.onSeekStart();
344
+ setTimeout(() => {
345
+ setDragState(4);
346
+ intoEdit(sign.inFrame);
347
+ vmmlRef.current && vmmlRef.current.onSeekEnd();
348
+ }, 100);
349
+ };
350
+ react.useEffect(() => {
351
+ if (!dragging.dragging) {
352
+ return;
353
+ }
354
+ const body = document.querySelector("body");
355
+ if (body) {
356
+ body.addEventListener("pointermove", onPointerMove);
357
+ body.addEventListener("pointerup", onPointerUp);
358
+ return () => {
359
+ body.removeEventListener("pointermove", onPointerMove);
360
+ body.removeEventListener("pointerup", onPointerUp);
361
+ };
362
+ }
363
+ }, [dragging.dragging, onPointerMove, onPointerUp]);
364
+ return /* @__PURE__ */ jsxRuntime.jsx("div", { ref: containerRef, className: "seekbar-container", children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "seekbar-background", children: [
365
+ /* @__PURE__ */ jsxRuntime.jsx("div", { className: "seekbar-fill", onPointerDown }),
366
+ /* @__PURE__ */ jsxRuntime.jsx("div", { className: "seekbar-line", style: fillStyle }),
367
+ /* @__PURE__ */ jsxRuntime.jsx("div", { className: "seekbar-signs", children: signList.map((item, index) => /* @__PURE__ */ jsxRuntime.jsx("img", { onClick: () => onClickSign(item), style: { left: `calc(${item.inFrame / durationInFrames * 100}% - 6px)` }, className: "seekbar-sign", src: signIcon, alt: "" }, index)) }),
368
+ /* @__PURE__ */ jsxRuntime.jsx("div", { className: "seekbar-cirle", style: cirleStyle, onPointerDown })
369
+ ] }) });
370
+ };
371
+ var SeekBar_default = SeekBar;
372
+ var Controls = ({ player, vmmlRef, frame, fps, durationInFrames, intoEdit, isPlaying, setDragState, onControlsClick, signList }) => {
373
+ const onClickToggle = (e) => {
374
+ if (isPlaying) {
375
+ intoEdit();
376
+ } else {
377
+ onControlsClick();
378
+ }
379
+ };
380
+ return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "player-controls", children: [
381
+ /* @__PURE__ */ jsxRuntime.jsx("div", { className: "player-controls-toggle mr-16 opacity-06", onClick: onClickToggle, children: isPlaying ? /* @__PURE__ */ jsxRuntime.jsx("img", { src: pauseIcon, alt: "\u6682\u505C" }) : /* @__PURE__ */ jsxRuntime.jsx("img", { src: playIcon, alt: "\u64AD\u653E" }) }),
382
+ /* @__PURE__ */ jsxRuntime.jsx("div", { className: "player-controls-time opacity-06", children: vmmlUtils.formatTime(frame / fps) }),
383
+ /* @__PURE__ */ jsxRuntime.jsx("div", { className: "player-controls-seekbar mr-16", children: /* @__PURE__ */ jsxRuntime.jsx(SeekBar_default, { player, vmmlRef, frame, durationInFrames, intoEdit, setDragState, signList }) }),
384
+ /* @__PURE__ */ jsxRuntime.jsx("div", { className: "player-controls-time opacity-06", children: vmmlUtils.formatTime(durationInFrames / fps) })
385
+ ] });
386
+ };
387
+ var Controls_default = Controls;
388
+
389
+ // src/utils/HistoryClass.ts
390
+ var HistoryClass = class {
391
+ historyUndo;
392
+ historyRedo;
393
+ cacheAction;
394
+ canvas;
395
+ historyProcessing;
396
+ editorInstance;
397
+ actionTypeList;
398
+ constructor(canvas) {
399
+ console.log("history init");
400
+ this.canvas = canvas;
401
+ this.historyUndo = [];
402
+ this.historyRedo = [];
403
+ this.cacheAction = [];
404
+ this.editorInstance = [];
405
+ this.actionTypeList = [];
406
+ this.historyProcessing = false;
407
+ this.initHistory();
408
+ }
409
+ initHistory() {
410
+ this.historyUndo = [];
411
+ this.historyRedo = [];
412
+ this.cacheAction = [];
413
+ this.canvas && this.canvas.on(this._historyEvents());
414
+ }
415
+ _historyNext() {
416
+ const keys = [
417
+ "id",
418
+ "gradientAngle",
419
+ "selectable",
420
+ "hasControls",
421
+ "linkData",
422
+ "editable",
423
+ "extensionType",
424
+ "extension",
425
+ "clipData"
426
+ ];
427
+ const getJson = this.canvas && this.canvas.toJSON(keys);
428
+ return getJson;
429
+ }
430
+ _historyEvents() {
431
+ return {
432
+ "object:added": (e) => this._historySaveAction(e, "object:added"),
433
+ "object:removed": (e) => this._historySaveAction(e, "object:removed"),
434
+ "object:modified": (e) => this._historySaveAction(e, "object:modified"),
435
+ "object:skewing": (e) => this._historySaveAction(e, "object:skewing"),
436
+ "object:muteChange": (e) => this._historySaveAction(e, "object:muteChange")
437
+ };
438
+ }
439
+ _historySaveAction(e, type) {
440
+ if (this.historyProcessing) return;
441
+ this.actionTypeList.length < 1 && this.actionTypeList.push({ type });
442
+ if (!e || e.target && !e.target.excludeFromExport) {
443
+ const json = this._historyNext();
444
+ this.cacheAction.push(json);
445
+ if (this.cacheAction.length > 1) {
446
+ this.cacheAction.shift();
447
+ }
448
+ this.historyRedo = [];
449
+ this.canvas.fire("history:appnd", { json });
450
+ }
451
+ }
452
+ undo(callback) {
453
+ this.historyProcessing = true;
454
+ const history = this.historyUndo.pop();
455
+ if (history) {
456
+ this._loadHistory(history, "history:undo", callback);
457
+ } else {
458
+ this.historyProcessing = false;
459
+ }
460
+ }
461
+ redo(callback) {
462
+ this.historyProcessing = true;
463
+ const history = this.historyRedo.pop();
464
+ if (history) {
465
+ this.historyUndo.push(this._historyNext());
466
+ this._loadHistory(history, "history:redo", callback);
467
+ } else {
468
+ this.historyProcessing = false;
469
+ }
470
+ }
471
+ _loadHistory(history, event, callback) {
472
+ this.canvas && this.canvas.loadFromJSON(history, () => {
473
+ this.canvas.renderAll();
474
+ this.canvas.fire(event);
475
+ this.historyProcessing = false;
476
+ if (callback && typeof callback === "function") callback();
477
+ });
478
+ }
479
+ _historyDispose() {
480
+ this.canvas.off(this._historyEvents());
481
+ }
482
+ clearHistory() {
483
+ this.historyUndo = [];
484
+ this.historyRedo = [];
485
+ this.cacheAction = [];
486
+ this.canvas.fire("history:clear");
487
+ }
488
+ canUndo() {
489
+ return this.historyUndo.length > 0;
490
+ }
491
+ canRedo() {
492
+ return this.historyRedo.length > 0;
493
+ }
494
+ //离开画布保存上一次编辑的状态
495
+ onCanvasRoute(canvas) {
496
+ this.editorInstance.push(canvas);
497
+ }
498
+ getActionType() {
499
+ return this.actionTypeList;
500
+ }
501
+ };
502
+ var VmmlConverter = class {
503
+ vmml;
504
+ canvasSize;
505
+ tracks;
506
+ heightScale;
507
+ widthScale;
508
+ fontSize;
509
+ /**
510
+ * VmmlConverter 构造函数
511
+ * @param vmml - VMML 模板数据
512
+ * @param canvasSize - 画布尺寸
513
+ */
514
+ constructor({ vmml, canvasSize }) {
515
+ const { width, height } = vmml.template.dimension;
516
+ this.vmml = vmml;
517
+ this.canvasSize = canvasSize;
518
+ this.tracks = vmml.template.tracks;
519
+ this.fontSize = vmmlUtils.getFontSize(width, height);
520
+ this.heightScale = height / canvasSize.height;
521
+ this.widthScale = width / canvasSize.width;
522
+ }
523
+ //更新位置
524
+ setPosParam(fObj) {
525
+ console.log("setPosParam fObj", fObj);
526
+ const {
527
+ clipData: { type },
528
+ centerPoint,
529
+ scaleX,
530
+ scaleY,
531
+ angle,
532
+ width,
533
+ height
534
+ } = fObj;
535
+ let _scaleX, _scaleY, _centerX, _centerY;
536
+ if (type === "\u6587\u5B57") {
537
+ _scaleX = 22 * scaleX * this.widthScale / this.fontSize;
538
+ _scaleY = 22 * scaleY * this.heightScale / this.fontSize;
539
+ _centerX = centerPoint.x / this.canvasSize.width;
540
+ _centerY = centerPoint.y / this.canvasSize.height;
541
+ } else if (type === "\u8868\u60C5\u5305") {
542
+ _scaleX = width * scaleX * this.widthScale / width;
543
+ _scaleY = height * scaleY * this.heightScale / height;
544
+ _centerX = centerPoint.x / this.canvasSize.width;
545
+ _centerY = centerPoint.y / this.canvasSize.height;
546
+ }
547
+ return {
548
+ scaleX: _scaleX,
549
+ scaleY: _scaleY,
550
+ centerX: _centerX,
551
+ centerY: _centerY,
552
+ rotationZ: angle
553
+ };
554
+ }
555
+ /**
556
+ * 转换 TextClip
557
+ * @param fObj - 画布fObj
558
+ */
559
+ addTextClip(fObj) {
560
+ console.log("addTextClip fObj", fObj);
561
+ const posParam = this.setPosParam(fObj);
562
+ const { clipData: { id, inPoint, text, textColor, bgColor } } = fObj;
563
+ const { template: { duration } } = this.vmml;
564
+ const clips = [];
565
+ const editorTrack = this.tracks.find((track) => track.editorType === "\u6587\u5B57");
566
+ const tClipData = {
567
+ duration,
568
+ originDuration: duration,
569
+ start: 0,
570
+ end: duration,
571
+ inPoint,
572
+ id,
573
+ type: 202,
574
+ fObj,
575
+ textClip: {
576
+ lineSpacing: 0,
577
+ alignType: 0,
578
+ fontCode: "",
579
+ bold: false,
580
+ dimension: {
581
+ height: 282,
582
+ width: 825
583
+ },
584
+ posParam,
585
+ backgroundColor: this.toARGB(bgColor),
586
+ textContent: text,
587
+ textColor: this.toARGB(textColor)
588
+ // fontFamily:'unset'
589
+ }
590
+ };
591
+ if (!editorTrack) {
592
+ clips.push(tClipData);
593
+ this.tracks.push({
594
+ clips,
595
+ description: "editorText",
596
+ id: uuid.v4(),
597
+ type: 2,
598
+ editorType: "\u6587\u5B57"
599
+ });
600
+ } else {
601
+ editorTrack.clips.push(tClipData);
602
+ }
603
+ console.log("addTextClip \u6700\u7EC8vmml", this.vmml);
604
+ }
605
+ /**
606
+ * 转换 VideoClip
607
+ * @param fObj - 画布fObj
608
+ */
609
+ addVideoClip(fObj) {
610
+ console.log("addVideoClip fObj", fObj);
611
+ const clips = [];
612
+ const editorTrack = this.tracks.find((track) => track.editorType === "\u8868\u60C5\u5305");
613
+ const clipData = this.loadClipData(fObj);
614
+ if (!editorTrack) {
615
+ const index = this.tracks.findIndex((track) => track.editorType === "\u6587\u5B57");
616
+ for (const item of clipData) {
617
+ if (item !== null) {
618
+ clips.push(item);
619
+ }
620
+ }
621
+ const data = {
622
+ clips,
623
+ description: "editorEmoji",
624
+ id: uuid.v4(),
625
+ type: 1,
626
+ editorType: "\u8868\u60C5\u5305"
627
+ };
628
+ if (index !== -1) {
629
+ this.tracks.splice(index, 0, data);
630
+ } else {
631
+ this.tracks.push(data);
632
+ }
633
+ } else {
634
+ for (const item of clipData) {
635
+ if (item !== null) {
636
+ editorTrack.clips.push(item);
637
+ }
638
+ }
639
+ }
640
+ console.log("addVideoClip \u6700\u7EC8vmml", this.vmml);
641
+ }
642
+ /**
643
+ * 更新 clip
644
+ * @param fObj - 画布fObj
645
+ */
646
+ updateClip(fObj) {
647
+ console.log("updateClip fObj", fObj);
648
+ const posParam = this.setPosParam(fObj);
649
+ const {
650
+ // clipData: { id, type, lineSpacing },
651
+ clipData: { id, type, lineSpacing, originClip }
652
+ } = fObj;
653
+ let existClip = null;
654
+ if (originClip) {
655
+ existClip = originClip;
656
+ } else {
657
+ const editorTrack = this.tracks.find((track) => track.editorType === type);
658
+ existClip = ((editorTrack == null ? void 0 : editorTrack.clips) || []).find((clip) => clip.id === id);
659
+ }
660
+ if (existClip) {
661
+ !originClip && (existClip.fObj = fObj);
662
+ if (type === "\u8868\u60C5\u5305") {
663
+ existClip.videoClip.posParam = posParam;
664
+ } else if (type === "\u6587\u5B57") {
665
+ const { clipData: { text, textColor, bgColor } } = fObj;
666
+ const scale = this.fontSize / 22;
667
+ existClip.textClip = {
668
+ ...existClip.textClip,
669
+ posParam,
670
+ backgroundColor: this.toARGB(bgColor),
671
+ textContent: text,
672
+ textColor: this.toARGB(textColor),
673
+ dimension: {
674
+ width: Math.floor(fObj.width * scale),
675
+ height: Math.floor(fObj.height * scale)
676
+ }
677
+ };
678
+ }
679
+ }
680
+ console.log("updateClip \u6700\u7EC8vmml", this.vmml);
681
+ }
682
+ /**
683
+ * 删除 Clip
684
+ * @param id - 实例 id
685
+ * @param type - 实例 类型
686
+ */
687
+ deleteClip({ id, type, originClip }) {
688
+ if (originClip) {
689
+ originClip.duration = 0;
690
+ } else {
691
+ const editorTrack = this.tracks.find((track) => track.editorType === type);
692
+ const index = editorTrack.clips.findIndex((item) => item.id === id);
693
+ if (index !== -1) {
694
+ if (editorTrack.clips[index + 1] && editorTrack.clips[index + 1].audioClip) {
695
+ editorTrack.clips.splice(index, 2);
696
+ } else {
697
+ editorTrack.clips.splice(index, 1);
698
+ }
699
+ }
700
+ if (editorTrack.clips.length === 0) {
701
+ const trackIndex = this.tracks.indexOf(editorTrack);
702
+ if (trackIndex !== -1) {
703
+ this.tracks.splice(trackIndex, 1);
704
+ }
705
+ }
706
+ }
707
+ console.log("deleteClip \u6700\u7EC8Vmml", this.vmml);
708
+ }
709
+ //切换静音 视频/音频
710
+ changeMute({ id, isMute }) {
711
+ const editorTrack = this.tracks.find((track) => track.editorType === "\u8868\u60C5\u5305");
712
+ const index = editorTrack.clips.findIndex((item) => item.id === id);
713
+ if (index !== -1) {
714
+ const volume = isMute ? 0 : 1;
715
+ editorTrack.clips[index].videoClip.volume = volume;
716
+ if (editorTrack.clips[index + 1] && editorTrack.clips[index + 1].audioClip) {
717
+ editorTrack.clips[index + 1].audioClip.volume = volume;
718
+ }
719
+ }
720
+ console.log("changeMute \u6700\u7EC8Vmml", this.vmml);
721
+ }
722
+ //加载clip数据
723
+ loadClipData(fObj) {
724
+ const posParam = this.setPosParam(fObj);
725
+ const {
726
+ clipData: { id, inPoint, fileUrl },
727
+ width,
728
+ height
729
+ } = fObj;
730
+ let aClipData = null;
731
+ const availableDuration = this.vmml.template.duration - inPoint;
732
+ const _duration = fileUrl.duration > availableDuration ? availableDuration : fileUrl.duration;
733
+ const vClipData = {
734
+ duration: _duration,
735
+ originDuration: fileUrl.duration,
736
+ start: 0,
737
+ end: _duration,
738
+ inPoint,
739
+ type: 102,
740
+ id,
741
+ fObj,
742
+ videoClip: {
743
+ grayMaskUrl: fileUrl.grayMaskUrl,
744
+ webmUrl: fileUrl.webmUrl,
745
+ movUrl: fileUrl.movUrl,
746
+ gifUrl: fileUrl.visibleUrl,
747
+ dimension: {
748
+ height,
749
+ width
750
+ },
751
+ posParam,
752
+ constantSpeed: 1,
753
+ volume: 1,
754
+ sourceUrl: fileUrl.visibleUrl,
755
+ thumbnailSourceUrl: fileUrl.thumbnailUrl,
756
+ sourceCode: "",
757
+ mimeType: fileUrl.visiableMimeType
758
+ }
759
+ };
760
+ if (fileUrl.hasAudio === "true") {
761
+ aClipData = {
762
+ duration: _duration,
763
+ originDuration: fileUrl.duration,
764
+ start: 0,
765
+ end: _duration,
766
+ inPoint,
767
+ type: 304,
768
+ id: uuid.v4(),
769
+ audioClip: {
770
+ sourceUrl: fileUrl.soundUrl,
771
+ volume: 1,
772
+ constantSpeed: 1
773
+ }
774
+ };
775
+ }
776
+ return [vClipData, aClipData];
777
+ }
778
+ /**
779
+ * 将颜色转换为 ARGB 格式
780
+ * @param color - 颜色字符串
781
+ * @returns ARGB 颜色字符串
782
+ */
783
+ toARGB(color) {
784
+ if (color === "transparent") {
785
+ return "#00000000";
786
+ }
787
+ if (color.includes("rgb")) {
788
+ return vmmlUtils.rgbaToArgb(color);
789
+ }
790
+ if (color.includes("#")) {
791
+ return vmmlUtils.hexToArgb(color);
792
+ }
793
+ }
794
+ };
795
+ var VmmlConverter_default = VmmlConverter;
796
+ function drawImg(ctx, left, top, img, wSize, hSize, angle) {
797
+ if (angle === void 0) return;
798
+ ctx.save();
799
+ ctx.translate(left, top);
800
+ ctx.rotate(fabric.fabric.util.degreesToRadians(angle));
801
+ ctx.drawImage(img, -wSize / 2, -hSize / 2, wSize, hSize);
802
+ ctx.restore();
803
+ }
804
+ function usePeekControl(canvas) {
805
+ const iconUrls = {
806
+ delete: "https://mass.alipay.com/finmedia_versaassets/uri/file/as/0c7084a9-6067-4277-a5af-2932983cbeb7.png",
807
+ // zoom: "https://mass.alipay.com/finmedia_versaassets/uri/file/as/ff6aea73-4d12-4201-9404-3134d5f9525c.png",
808
+ zoom: "https://mass.alipay.com/finmedia_versaassets/uri/file/as/0909485d-46db-47b4-8bb1-5a686510ddb3.png",
809
+ mute: "https://mass.alipay.com/finmedia_versaassets/uri/file/as/3fef2c5d-7576-424d-813c-34508b051884.png",
810
+ volume: "https://mass.alipay.com/finmedia_versaassets/uri/file/as/1ab2e829-c5b1-4177-8554-ae2f74b02e1d.png",
811
+ edit: "https://mass.alipay.com/finmedia_versaassets/uri/file/as/9e9ed472-62cf-4b71-891f-bc08c8b08a5d.png"
812
+ };
813
+ const createIconElement = (url) => {
814
+ const img = document.createElement("img");
815
+ img.src = url;
816
+ return img;
817
+ };
818
+ const deleteObject = (mouseEvent, target) => {
819
+ if (target.action === "rotate") return true;
820
+ const activeObject = canvas.getActiveObjects();
821
+ if (activeObject) {
822
+ activeObject.map((item) => canvas.remove(item));
823
+ canvas.requestRenderAll();
824
+ canvas.discardActiveObject();
825
+ }
826
+ return true;
827
+ };
828
+ const delImg = createIconElement(iconUrls.delete);
829
+ const zoomImg = createIconElement(iconUrls.zoom);
830
+ const muteImg = createIconElement(iconUrls.mute);
831
+ const volumeImg = createIconElement(iconUrls.volume);
832
+ const editImg = createIconElement(iconUrls.edit);
833
+ const renderDelIcon = (ctx, left, top, styleOverride, fabricObject) => {
834
+ drawImg(ctx, left, top, delImg, 28, 28, fabricObject.angle);
835
+ };
836
+ const renderIconRotate = (ctx, left, top, styleOverride, fabricObject) => {
837
+ drawImg(ctx, left, top, zoomImg, 28, 28, fabricObject.angle);
838
+ };
839
+ const renderMuteIcon = (ctx, left, top, styleOverride, fabricObject) => {
840
+ if (!fabricObject.clipData) return false;
841
+ if (fabricObject.clipData.type === "\u8868\u60C5\u5305") {
842
+ if (fabricObject.clipData.isMute === null || fabricObject.clipData.isMute === void 0) return false;
843
+ if (fabricObject.clipData.isMute) {
844
+ drawImg(ctx, left, top, muteImg, 28, 28, fabricObject.angle);
845
+ } else {
846
+ drawImg(ctx, left, top, volumeImg, 28, 28, fabricObject.angle);
847
+ }
848
+ }
849
+ };
850
+ const renderEditIcon = (ctx, left, top, styleOverride, fabricObject) => {
851
+ if (!fabricObject.clipData) return false;
852
+ if (fabricObject.clipData.type === "\u6587\u5B57") {
853
+ drawImg(ctx, left, top, editImg, 28, 28, fabricObject.angle);
854
+ }
855
+ };
856
+ const muteAction = (eventData, transform, x, y) => {
857
+ if (transform.target.clipData.isMute === null) return false;
858
+ transform.target.clipData = JSON.parse(JSON.stringify(transform.target.clipData));
859
+ transform.target.clipData.isMute = !transform.target.clipData.isMute;
860
+ canvas.renderAll();
861
+ canvas.fire("object:muteChange", { target: transform.target });
862
+ return true;
863
+ };
864
+ const editAction = (eventData, transform, x, y) => {
865
+ if (transform.target.clipData.type === "\u6587\u5B57") {
866
+ canvas.fire("object:textEdit", { target: transform.target });
867
+ }
868
+ return true;
869
+ };
870
+ const actionHandler = (eventData, transform, x, y) => {
871
+ try {
872
+ const t = transform, target = t.target, pivotPoint = target.translateToOriginPoint(
873
+ target.getCenterPoint(),
874
+ t.originX,
875
+ t.originY
876
+ );
877
+ const lastAngle = Math.atan2(t.ey - pivotPoint.y, t.ex - pivotPoint.x), curAngle = Math.atan2(y - pivotPoint.y, x - pivotPoint.x);
878
+ let angle2 = Math.floor((curAngle - lastAngle + t.theta) * (180 / Math.PI));
879
+ fabric.fabric.controlsUtils.scalingEqually(eventData, transform, x, y);
880
+ const rotateAngles = [
881
+ [85, 95, 90],
882
+ [175, 185, 180],
883
+ [265, 275, 270],
884
+ [355, 365, 360],
885
+ [440, 460, 90],
886
+ [-5, 5, 0],
887
+ [-95, -85, 270],
888
+ [-185, -175, 180]
889
+ ];
890
+ for (let i = 0; i < rotateAngles.length; i++) {
891
+ if (rotateAngles[i][0] < angle2 && angle2 < rotateAngles[i][1]) {
892
+ target.rotate(rotateAngles[i][2]);
893
+ return true;
894
+ }
895
+ }
896
+ fabric.fabric.controlsUtils.rotationWithSnapping(eventData, transform, x, y);
897
+ return true;
898
+ } catch (error) {
899
+ console.error("Action handler error:", error);
900
+ return false;
901
+ }
902
+ };
903
+ fabric.fabric.Object.prototype.controls.tl = new fabric.fabric.Control({
904
+ x: -0.5,
905
+ y: -0.5,
906
+ mouseUpHandler: deleteObject,
907
+ render: renderDelIcon
908
+ });
909
+ fabric.fabric.Object.prototype.controls.bl = new fabric.fabric.Control({
910
+ x: -0.5,
911
+ y: 0.5,
912
+ mouseUpHandler: muteAction,
913
+ render: renderMuteIcon
914
+ });
915
+ fabric.fabric.Object.prototype.controls.tr = new fabric.fabric.Control({
916
+ x: 0.5,
917
+ y: -0.5,
918
+ mouseUpHandler: editAction,
919
+ render: renderEditIcon
920
+ });
921
+ fabric.fabric.Object.prototype.controls.ml = new fabric.fabric.Control({ visible: false });
922
+ fabric.fabric.Object.prototype.controls.mr = new fabric.fabric.Control({ visible: false });
923
+ fabric.fabric.Object.prototype.controls.mb = new fabric.fabric.Control({ visible: false });
924
+ fabric.fabric.Object.prototype.controls.mt = new fabric.fabric.Control({ visible: false });
925
+ fabric.fabric.Object.prototype.controls.mtr = new fabric.fabric.Control({ visible: false });
926
+ fabric.fabric.Object.prototype.controls.br = new fabric.fabric.Control({
927
+ x: 0.5,
928
+ y: 0.5,
929
+ actionName: "rotate",
930
+ actionHandler,
931
+ render: renderIconRotate
932
+ });
933
+ fabric.fabric.Object.prototype.set({
934
+ borderColor: "#d6d6d699",
935
+ borderScaleFactor: 1.5,
936
+ borderOpacityWhenMoving: 1,
937
+ padding: 5
938
+ });
939
+ return canvas;
940
+ }
941
+ var EditorCanvas = react.forwardRef(
942
+ ({ previewState, showCanvas, canvasSize, enterPreview, intoTextEdit, frame, vmml, dragState, initFcObjs, onVideoChange }, ref) => {
943
+ const [fc, setFc] = react.useState(null);
944
+ const [history, setHistory] = react.useState(null);
945
+ const waitFcTasks = react.useRef([]);
946
+ const vmmlConverterRef = react.useRef(null);
947
+ const heightScaleRef = react.useRef(1);
948
+ const widthScaleRef = react.useRef(1);
949
+ const initCanvas = () => {
950
+ const canvas = new fabric.fabric.Canvas("canvas", {
951
+ width: canvasSize.width,
952
+ height: canvasSize.height,
953
+ selection: false
954
+ // 画布框选
955
+ });
956
+ heightScaleRef.current = vmml.template.dimension.height / canvasSize.height;
957
+ widthScaleRef.current = vmml.template.dimension.width / canvasSize.width;
958
+ if (initFcObjs.length) {
959
+ createFcObjs(canvas);
960
+ }
961
+ setFc(canvas);
962
+ initCanvasEvent(canvas);
963
+ usePeekControl(canvas);
964
+ };
965
+ const createFcObjs = (canvas) => {
966
+ const ns = Math.floor(frame / 30 * 1e6);
967
+ fabric.fabric.util.enlivenObjects(initFcObjs, (objects) => {
968
+ objects.forEach((item) => {
969
+ item.on("modified", () => {
970
+ const fObj = convertToJSON(item);
971
+ vmmlConverterRef.current.updateClip(fObj);
972
+ });
973
+ item.set("visible", ns >= item.clipData.inPoint);
974
+ canvas.add(item);
975
+ });
976
+ canvas.renderAll();
977
+ }, "");
978
+ };
979
+ const checkObjectInPoint = (f) => {
980
+ if (fc) {
981
+ const ns = Math.floor((f ?? frame) / 30 * 1e6);
982
+ const objects = fc.getObjects();
983
+ objects.forEach((item) => {
984
+ var _a, _b, _c;
985
+ if (((_a = item == null ? void 0 : item.clipData) == null ? void 0 : _a.type) === "\u6587\u5B57") {
986
+ item.set("visible", ns >= item.clipData.inPoint && ns < item.clipData.inPoint + (item.clipData.duration || vmml.template.duration));
987
+ } else {
988
+ item.set("visible", ns >= item.clipData.inPoint && ns < item.clipData.inPoint + ((_c = (_b = item.clipData) == null ? void 0 : _b.fileUrl) == null ? void 0 : _c.duration));
989
+ }
990
+ });
991
+ fc.discardActiveObject();
992
+ fc.renderAll();
993
+ }
994
+ };
995
+ const initCanvasEvent = (canvas) => {
996
+ canvas.on("mouse:down", (e) => {
997
+ const active = canvas.getActiveObject();
998
+ if (active) {
999
+ if (active.isSelected !== null && active.clipData.type === "\u6587\u5B57") {
1000
+ imitateDBclick(active, canvas);
1001
+ }
1002
+ } else {
1003
+ enterPreview(canvas);
1004
+ }
1005
+ });
1006
+ canvas.on("object:removed", (e) => {
1007
+ if (e.target.clipData && !e.target.clipData.originClip) {
1008
+ onVideoChange(e.target.clipData);
1009
+ }
1010
+ const { clipData } = e.target.toJSON(["clipData"]);
1011
+ vmmlConverterRef.current.deleteClip(clipData);
1012
+ });
1013
+ canvas.on("object:muteChange", (e) => {
1014
+ const { clipData } = e.target.toJSON(["clipData"]);
1015
+ vmmlConverterRef.current.changeMute(clipData);
1016
+ });
1017
+ canvas.on("object:textEdit", (e) => {
1018
+ const active = canvas.getActiveObject();
1019
+ handleIntoTextMenu(active, canvas);
1020
+ });
1021
+ };
1022
+ const imitateDBclick = (active, canvas) => {
1023
+ active.isSelected++;
1024
+ const timer = setTimeout(() => {
1025
+ active.isSelected = 0;
1026
+ }, 500);
1027
+ if (active.isSelected === 2) {
1028
+ active.isSelected = 0;
1029
+ clearTimeout(timer);
1030
+ handleIntoTextMenu(active, canvas);
1031
+ }
1032
+ };
1033
+ const handleIntoTextMenu = (active, canvas) => {
1034
+ const {
1035
+ left,
1036
+ top,
1037
+ angle,
1038
+ scaleX,
1039
+ scaleY,
1040
+ zoomX,
1041
+ zoomY,
1042
+ clipData: { textBasicInfo, textColor, text, bgColor, fontFamily, id, fontAssetUrl }
1043
+ } = active;
1044
+ const textInfo = {
1045
+ id,
1046
+ text,
1047
+ textColor,
1048
+ bgColor,
1049
+ left,
1050
+ top,
1051
+ angle,
1052
+ scaleX,
1053
+ scaleY,
1054
+ zoomX,
1055
+ zoomY,
1056
+ textBasicInfo,
1057
+ fontFamily,
1058
+ fontAssetUrl
1059
+ // width,
1060
+ // height
1061
+ };
1062
+ active.set("visible", false);
1063
+ canvas.renderAll();
1064
+ intoTextEdit(textInfo);
1065
+ };
1066
+ const convertToJSON = (data) => {
1067
+ const centerPoint = data.getCenterPoint();
1068
+ return { ...data.toJSON(["clipData", "type"]), centerPoint };
1069
+ };
1070
+ const createImage = (file, emojiId) => {
1071
+ const url = file.resourcesType === "image" ? file.visibleUrl : "";
1072
+ return new Promise((resolve, reject) => {
1073
+ try {
1074
+ fabric.fabric.Image.fromURL(
1075
+ url,
1076
+ (img) => {
1077
+ const scaleX = canvasSize.width / 2 / file.width;
1078
+ img.set({
1079
+ width: file.width,
1080
+ height: file.height,
1081
+ scaleX,
1082
+ scaleY: scaleX,
1083
+ left: canvasSize.width / 2,
1084
+ top: canvasSize.height / 2,
1085
+ originX: "center",
1086
+ originY: "center",
1087
+ clipData: {
1088
+ id: uuid.v4(),
1089
+ isMute: file.hasAudio === "true" ? false : null,
1090
+ inPoint: Math.floor(frame / 30 * 1e6),
1091
+ inFrame: frame,
1092
+ type: "\u8868\u60C5\u5305",
1093
+ once: false,
1094
+ emojiId,
1095
+ fileUrl: file
1096
+ }
1097
+ });
1098
+ img.on("modified", () => {
1099
+ const fObj2 = convertToJSON(img);
1100
+ fObj2.src = "";
1101
+ vmmlConverterRef.current.updateClip(fObj2);
1102
+ });
1103
+ fc.add(img);
1104
+ onVideoChange(img.clipData);
1105
+ const fObj = convertToJSON(img);
1106
+ resolve(fObj);
1107
+ },
1108
+ {
1109
+ padding: 3
1110
+ }
1111
+ );
1112
+ } catch (err) {
1113
+ reject(err + "\u6DFB\u52A0\u8868\u60C5\u5305\u5931\u8D25");
1114
+ }
1115
+ });
1116
+ };
1117
+ const updateImage = (id, base64, fc2) => {
1118
+ const canvas = fc || fc2;
1119
+ if (canvas) {
1120
+ const imgs = canvas.getObjects().filter((item) => {
1121
+ var _a;
1122
+ return ((_a = item == null ? void 0 : item.clipData) == null ? void 0 : _a.type) === "\u8868\u60C5\u5305";
1123
+ });
1124
+ const target = imgs.find((item) => item.clipData.id === id);
1125
+ if (target) {
1126
+ target.setSrc(base64, (img) => {
1127
+ img.setCoords();
1128
+ canvas.renderAll();
1129
+ });
1130
+ }
1131
+ } else {
1132
+ waitFcTasks.current.push(updateImage.bind(void 0, id, base64));
1133
+ }
1134
+ };
1135
+ const createImageFromClip = (clip, fc2) => {
1136
+ const canvas = fc || fc2;
1137
+ if (canvas && canvasSize.width) {
1138
+ const url = /video/g.test(clip.videoClip.mimeType) ? "" : clip.videoClip.sourceUrl;
1139
+ fabric.fabric.Image.fromURL(url, (img) => {
1140
+ const { dimension, posParam } = clip.videoClip;
1141
+ const scaleX = posParam.scaleX / heightScaleRef.current;
1142
+ const scaleY = posParam.scaleY / widthScaleRef.current;
1143
+ const left = canvasSize.width * posParam.centerX;
1144
+ const top = canvasSize.height * posParam.centerY;
1145
+ const inFrame = vmmlUtils.getFrames(clip.inPoint, 30);
1146
+ const durationFrame = vmmlUtils.getFrames(clip.duration, 30);
1147
+ img.set({
1148
+ width: dimension.width,
1149
+ height: dimension.height,
1150
+ scaleX,
1151
+ scaleY,
1152
+ left,
1153
+ top,
1154
+ angle: posParam.rotationZ,
1155
+ originX: "center",
1156
+ originY: "center",
1157
+ clipData: {
1158
+ id: clip.id,
1159
+ isMute: null,
1160
+ inPoint: clip.inPoint,
1161
+ inFrame,
1162
+ type: "\u8868\u60C5\u5305",
1163
+ once: false,
1164
+ fileUrl: {
1165
+ duration: clip.duration
1166
+ },
1167
+ originClip: clip
1168
+ },
1169
+ visible: frame >= inFrame && frame < inFrame + durationFrame
1170
+ });
1171
+ canvas.add(img);
1172
+ img.on("modified", () => {
1173
+ const fObj = convertToJSON(img);
1174
+ fObj.src = "";
1175
+ vmmlConverterRef.current.updateClip(fObj);
1176
+ });
1177
+ });
1178
+ } else {
1179
+ waitFcTasks.current.push(createImageFromClip.bind(void 0, clip));
1180
+ }
1181
+ };
1182
+ const handleRedo = () => {
1183
+ history.redo();
1184
+ };
1185
+ const handleUndo = () => {
1186
+ history.undo();
1187
+ };
1188
+ const createTextFromClip = async (clip, fc2) => {
1189
+ const canvas = fc || fc2;
1190
+ if (canvas) {
1191
+ const { width, height } = vmml.template.dimension;
1192
+ const fontSize = vmmlUtils.getFontSize(width, height);
1193
+ const { textContent, backgroundColor, textColor, posParam, fontAssetUrl, alignType } = clip.textClip;
1194
+ const scaleX = posParam.scaleX * fontSize / 22 / widthScaleRef.current;
1195
+ const scaleY = posParam.scaleY * fontSize / 22 / heightScaleRef.current;
1196
+ const left = canvasSize.width * posParam.centerX;
1197
+ const top = canvasSize.height * posParam.centerY;
1198
+ const bgColor = backgroundColor ? vmmlUtils.argbToRgba(backgroundColor) : "transparent";
1199
+ const isAiError = textContent === "\u8BF7\u8F93\u5165\u6587\u6848" && textColor === "#00000000";
1200
+ const textFill = vmmlUtils.argbToRgba(isAiError ? "#ffffffff" : textColor || "#ffffffff");
1201
+ const textBasicInfo = {
1202
+ isBack: backgroundColor ? true : false,
1203
+ colorValue: textFill,
1204
+ colorName: "custom",
1205
+ textAlign: alignType === 1 ? "center" : alignType === 2 ? "right" : "left"
1206
+ };
1207
+ const textImgData = await createTextImg({ textContent, bgColor, textColor: textFill, fontAssetUrl, textBasicInfo });
1208
+ const fontJSON = localStorage.getItem("VMML_PLAYER_FONTSMAP");
1209
+ let fontMap = {};
1210
+ try {
1211
+ fontMap = fontJSON ? JSON.parse(fontJSON) : {};
1212
+ } catch {
1213
+ fontMap = {};
1214
+ }
1215
+ const fontFamily = fontMap[fontAssetUrl] || "";
1216
+ fabric.fabric.Image.fromURL(textImgData.base64Image, (imgData) => {
1217
+ imgData.set({
1218
+ left,
1219
+ top,
1220
+ width: textImgData.width,
1221
+ height: textImgData.height,
1222
+ scaleX,
1223
+ scaleY,
1224
+ angle: posParam.rotationZ,
1225
+ originX: "center",
1226
+ originY: "center",
1227
+ clipData: {
1228
+ id: uuid.v4(),
1229
+ inPoint: clip.inPoint,
1230
+ inFrame: vmmlUtils.getFrames(clip.inPoint, 30),
1231
+ type: "\u6587\u5B57",
1232
+ textColor: textFill,
1233
+ text: textContent,
1234
+ bgColor,
1235
+ originClip: clip,
1236
+ fontAssetUrl,
1237
+ fontFamily,
1238
+ textBasicInfo,
1239
+ isAiError,
1240
+ duration: clip.duration
1241
+ }
1242
+ });
1243
+ imgData.on("selected", (options) => {
1244
+ options.target.isSelected = -1;
1245
+ });
1246
+ imgData.on("moving", (options) => {
1247
+ options.transform.target.isSelected = 0;
1248
+ });
1249
+ imgData.on("modified", () => {
1250
+ const fObj = convertToJSON(imgData);
1251
+ if (fObj.clipData.isAiError) {
1252
+ fObj.clipData.textColor = "rgba(0, 0, 0, 0)";
1253
+ }
1254
+ vmmlConverterRef.current.updateClip(fObj);
1255
+ });
1256
+ canvas.add(imgData).renderAll();
1257
+ });
1258
+ } else {
1259
+ waitFcTasks.current.push(createTextFromClip.bind(void 0, clip));
1260
+ }
1261
+ };
1262
+ const embedFontInSVG = async (svgString, url) => {
1263
+ if (url) {
1264
+ const res = await vmmlUtils.urlToBlob({ url });
1265
+ const fontFace = `
1266
+ @font-face {
1267
+ font-family: 'font-${url}';
1268
+ src: url(${res});
1269
+ }
1270
+ `;
1271
+ const styleElement = `<style type="text/css"><![CDATA[${fontFace}]]></style>`;
1272
+ return svgString.replace("</svg>", `${styleElement}</svg>`);
1273
+ }
1274
+ return svgString;
1275
+ };
1276
+ const createTextImg = async ({ textContent, bgColor, textColor, fontAssetUrl = null, textBasicInfo }) => {
1277
+ const container = document.createElement("div");
1278
+ container.style.backgroundColor = bgColor;
1279
+ container.style.boxSizing = "content-box";
1280
+ container.style.display = "inline-block";
1281
+ container.style.textAlign = textBasicInfo.textAlign || "left";
1282
+ const lines = textContent.split("\n");
1283
+ lines.forEach((line) => {
1284
+ const p = document.createElement("p");
1285
+ p.style.color = textColor;
1286
+ p.style.fontSize = "22px";
1287
+ p.style.lineHeight = "22px";
1288
+ const font = fontAssetUrl ? `font-${fontAssetUrl}` : "sansMedium";
1289
+ p.style.fontFamily = font;
1290
+ p.style.whiteSpace = "nowrap";
1291
+ p.style.padding = "0";
1292
+ p.textContent = line || " ";
1293
+ container.appendChild(p);
1294
+ });
1295
+ container.style.padding = "6.5px 7px 6.5px 7px";
1296
+ container.style.borderRadius = "5px";
1297
+ document.body.appendChild(container);
1298
+ const { width, height } = container == null ? void 0 : container.getBoundingClientRect();
1299
+ const dataurl = await domToImage.toSvg(container);
1300
+ document.body.removeChild(container);
1301
+ const base64Image = await embedFontInSVG(dataurl, fontAssetUrl);
1302
+ return { base64Image, height, width };
1303
+ };
1304
+ const createText = async ({ textContent, bgColor, textColor, position, textBasicInfo, id }, fc2) => {
1305
+ const canvas = fc || fc2;
1306
+ const { left, top, angle, scaleX, scaleY, zoomX, zoomY } = position;
1307
+ const textImgData = await createTextImg({ textContent, bgColor, textColor, textBasicInfo });
1308
+ return new Promise((resolve, reject) => {
1309
+ fabric.fabric.Image.fromURL(textImgData.base64Image, (imgData) => {
1310
+ imgData.set({
1311
+ left,
1312
+ top,
1313
+ angle,
1314
+ width: textImgData.width,
1315
+ height: textImgData.height,
1316
+ scaleX,
1317
+ scaleY,
1318
+ clipData: {
1319
+ id: uuid.v4(),
1320
+ inPoint: Math.floor(frame / 30 * 1e6),
1321
+ inFrame: frame,
1322
+ type: "\u6587\u5B57",
1323
+ textBasicInfo,
1324
+ textColor,
1325
+ text: textContent,
1326
+ bgColor
1327
+ }
1328
+ });
1329
+ imgData.on("selected", (options) => {
1330
+ options.target.isSelected = -1;
1331
+ });
1332
+ imgData.on("moving", (options) => {
1333
+ options.transform.target.isSelected = 0;
1334
+ });
1335
+ imgData.on("modified", () => {
1336
+ const fObj = convertToJSON(imgData);
1337
+ vmmlConverterRef.current.updateClip(fObj);
1338
+ });
1339
+ canvas.centerObject(imgData);
1340
+ canvas.add(imgData);
1341
+ setTimeout(() => {
1342
+ canvas.renderAll();
1343
+ });
1344
+ onVideoChange(imgData.clipData);
1345
+ vmmlConverterRef.current.addTextClip(convertToJSON(imgData));
1346
+ resolve(true);
1347
+ });
1348
+ });
1349
+ };
1350
+ const updateText = async ({ id, textContent, bgColor, textColor, textBasicInfo, fontAssetUrl }) => {
1351
+ const textImgData = await createTextImg({ textContent, bgColor, textColor, fontAssetUrl, textBasicInfo });
1352
+ const target = fc.getObjects().find((item) => item.clipData.id === id);
1353
+ target.setSrc(textImgData.base64Image, (img) => {
1354
+ img.set({
1355
+ visible: true,
1356
+ clipData: {
1357
+ ...img.clipData,
1358
+ textBasicInfo,
1359
+ textColor,
1360
+ text: textContent,
1361
+ bgColor,
1362
+ isAiError: false
1363
+ }
1364
+ });
1365
+ img.setCoords();
1366
+ fc.renderAll();
1367
+ vmmlConverterRef.current.updateClip(convertToJSON(img));
1368
+ });
1369
+ };
1370
+ const changeObjectVisible = (id, visible = true) => {
1371
+ const target = fc.getObjects().find((item) => item.clipData.id === id);
1372
+ target.set({ visible });
1373
+ fc.renderAll();
1374
+ };
1375
+ const getfObjectNums = (type) => {
1376
+ if (fc) {
1377
+ const objects = fc.getObjects();
1378
+ return objects.filter((item) => item.clipData.type === type && !item.clipData.originClip).length;
1379
+ }
1380
+ };
1381
+ const getfcObject = () => {
1382
+ if (fc) {
1383
+ return fc.getObjects();
1384
+ }
1385
+ };
1386
+ const styles = react.useMemo(() => {
1387
+ return {
1388
+ position: "absolute",
1389
+ top: canvasSize.top,
1390
+ display: showCanvas ? "block" : "none"
1391
+ };
1392
+ }, [showCanvas]);
1393
+ react.useEffect(() => {
1394
+ if (!fc && canvasSize.width) {
1395
+ initCanvas();
1396
+ }
1397
+ return () => {
1398
+ if (fc) {
1399
+ fc.dispose();
1400
+ setFc(null);
1401
+ }
1402
+ };
1403
+ }, [canvasSize.width]);
1404
+ react.useEffect(() => {
1405
+ if (!previewState && fc) {
1406
+ fc.discardActiveObject();
1407
+ checkObjectInPoint();
1408
+ }
1409
+ }, [previewState]);
1410
+ react.useEffect(() => {
1411
+ if (fc) {
1412
+ if (dragState === 1) {
1413
+ fc.discardActiveObject();
1414
+ }
1415
+ }
1416
+ }, [fc, dragState]);
1417
+ react.useEffect(() => {
1418
+ if (canvasSize.width && canvasSize.height && !vmmlConverterRef.current) {
1419
+ vmmlConverterRef.current = new VmmlConverter_default({ vmml, canvasSize });
1420
+ }
1421
+ }, [canvasSize, vmml]);
1422
+ react.useEffect(() => {
1423
+ if (fc) {
1424
+ const historyClass2 = new HistoryClass(fc);
1425
+ setHistory(historyClass2);
1426
+ if (waitFcTasks.current.length) {
1427
+ waitFcTasks.current.forEach((item) => item(fc));
1428
+ waitFcTasks.current = [];
1429
+ }
1430
+ }
1431
+ }, [fc]);
1432
+ react.useImperativeHandle(ref, () => ({
1433
+ createImage,
1434
+ createText,
1435
+ updateText,
1436
+ handleRedo,
1437
+ handleUndo,
1438
+ getActions,
1439
+ getfObjectNums,
1440
+ updateImage,
1441
+ getfcObject,
1442
+ checkObjectInPoint,
1443
+ createImageFromClip,
1444
+ createTextFromClip,
1445
+ changeObjectVisible
1446
+ }));
1447
+ const getActions = () => {
1448
+ if (history) {
1449
+ return history.getActionType();
1450
+ }
1451
+ return [];
1452
+ };
1453
+ return /* @__PURE__ */ jsxRuntime.jsx("div", { style: styles, children: /* @__PURE__ */ jsxRuntime.jsx("canvas", { id: "canvas" }) });
1454
+ }
1455
+ );
1456
+ var EditorCanvas_default = EditorCanvas;
1457
+
1458
+ // src/assets/css/loading.scss
1459
+ var css2 = `.page-loader {
1460
+ position: absolute;
1461
+ top: 0;
1462
+ width: 100%;
1463
+ height: 100%;
1464
+ display: flex;
1465
+ justify-content: center;
1466
+ align-items: center;
1467
+ z-index: 100;
1468
+ overflow: hidden;
1469
+ }
1470
+ .page-loader .light {
1471
+ width: 75%;
1472
+ height: 100%;
1473
+ background: linear-gradient(90deg, rgba(255, 255, 255, 0), rgba(255, 255, 255, 0.15), rgba(255, 255, 255, 0.3), rgba(255, 255, 255, 0.15), rgba(255, 255, 255, 0));
1474
+ transform: skew(-45deg) translateX(-400%);
1475
+ animation: animate_light 1s infinite;
1476
+ }
1477
+
1478
+ @keyframes animate_light {
1479
+ 100% {
1480
+ transform: skew(-45deg) translateX(200%);
1481
+ }
1482
+ }
1483
+ /*# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VSb290IjoiRDpcXHByb2plY3RzXFx2bW1sLXBsYXllclxccGFja2FnZXNcXGVkaXRvclxcc3JjXFxhc3NldHNcXGNzcyIsInNvdXJjZXMiOlsibG9hZGluZy5zY3NzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUNBO0VBQ0U7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBOztBQUNBO0VBQ0U7RUFDQTtFQUNBO0VBT0E7RUFDQTs7O0FBSUo7RUFDRTtJQUNFIiwic291cmNlc0NvbnRlbnQiOlsiXHJcbi5wYWdlLWxvYWRlciB7XHJcbiAgcG9zaXRpb246IGFic29sdXRlO1xyXG4gIHRvcDogMDtcclxuICB3aWR0aDogMTAwJTtcclxuICBoZWlnaHQ6IDEwMCU7XHJcbiAgZGlzcGxheTogZmxleDtcclxuICBqdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjtcclxuICBhbGlnbi1pdGVtczogY2VudGVyO1xyXG4gIHotaW5kZXg6IDEwMDtcclxuICBvdmVyZmxvdzogaGlkZGVuO1xyXG4gIC5saWdodCB7XHJcbiAgICB3aWR0aDogNzUlO1xyXG4gICAgaGVpZ2h0OiAxMDAlO1xyXG4gICAgYmFja2dyb3VuZDogbGluZWFyLWdyYWRpZW50KDkwZGVnLFxyXG4gICAgICAgIHJnYmEoMjU1LCAyNTUsIDI1NSwgMCksXHJcbiAgICAgICAgcmdiYSgyNTUsIDI1NSwgMjU1LCAwLjE1KSxcclxuICAgICAgICByZ2JhKDI1NSwgMjU1LCAyNTUsIDAuMyksXHJcbiAgICAgICAgcmdiYSgyNTUsIDI1NSwgMjU1LCAwLjE1KSxcclxuICAgICAgICByZ2JhKDI1NSwgMjU1LCAyNTUsIDAuMCksXHJcbiAgICAgICk7XHJcbiAgICB0cmFuc2Zvcm06IHNrZXcoLTQ1ZGVnKSB0cmFuc2xhdGVYKC00MDAlKTtcclxuICAgIGFuaW1hdGlvbjogYW5pbWF0ZV9saWdodCAxcyBpbmZpbml0ZTtcclxuICB9XHJcbn1cclxuXHJcbkBrZXlmcmFtZXMgYW5pbWF0ZV9saWdodCB7XHJcbiAgMTAwJSB7XHJcbiAgICB0cmFuc2Zvcm06IHNrZXcoLTQ1ZGVnKSB0cmFuc2xhdGVYKDIwMCUpO1xyXG4gIH1cclxufSJdfQ== */`;
1484
+ document.head.appendChild(document.createElement("style")).appendChild(document.createTextNode(css2));
1485
+ var Loaidng = ({ show }) => {
1486
+ const styles = {
1487
+ display: show ? "flex" : "none"
1488
+ };
1489
+ return /* @__PURE__ */ jsxRuntime.jsx("div", { style: styles, className: "page-loader", children: /* @__PURE__ */ jsxRuntime.jsx("div", { className: "light" }) });
1490
+ };
1491
+ var Loading_default = Loaidng;
1492
+
1493
+ // src/assets/css/maxTextLayer.scss
1494
+ var css3 = `.container {
1495
+ width: 100vw;
1496
+ height: 100vh;
1497
+ position: fixed;
1498
+ left: 0;
1499
+ top: 0;
1500
+ display: flex;
1501
+ flex-flow: row nowrap;
1502
+ align-items: center;
1503
+ justify-content: center;
1504
+ }
1505
+ .container .main_text {
1506
+ background: #000000;
1507
+ border-radius: 16px;
1508
+ backdrop-filter: blur(40px);
1509
+ padding: 3.2vw;
1510
+ font-weight: 400;
1511
+ font-size: 4vw;
1512
+ color: #FFFFFF;
1513
+ line-height: 5.6vw;
1514
+ text-align: right;
1515
+ font-style: normal;
1516
+ }
1517
+ /*# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VSb290IjoiRDpcXHByb2plY3RzXFx2bW1sLXBsYXllclxccGFja2FnZXNcXGVkaXRvclxcc3JjXFxhc3NldHNcXGNzcyIsInNvdXJjZXMiOlsibWF4VGV4dExheWVyLnNjc3MiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBUUE7RUFDRTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7O0FBQ0E7RUFDRTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQSIsInNvdXJjZXNDb250ZW50IjpbIiR2bV9iYXNlOiA3NTA7XHJcblxyXG5AZnVuY3Rpb24gdm0oJHB4KSB7XHJcblxyXG4gICAgQHJldHVybiAoJHB4IC8gNzUwKSAqIDEwMHZ3O1xyXG5cclxufVxyXG5cclxuLmNvbnRhaW5lcntcclxuICB3aWR0aDogMTAwdnc7XHJcbiAgaGVpZ2h0OiAxMDB2aDtcclxuICBwb3NpdGlvbjogZml4ZWQ7XHJcbiAgbGVmdDogMDtcclxuICB0b3A6IDA7XHJcbiAgZGlzcGxheTogZmxleDtcclxuICBmbGV4LWZsb3c6IHJvdyBub3dyYXA7XHJcbiAgYWxpZ24taXRlbXM6IGNlbnRlcjtcclxuICBqdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjtcclxuICAubWFpbl90ZXh0e1xyXG4gICAgYmFja2dyb3VuZDogIzAwMDAwMDtcclxuICAgIGJvcmRlci1yYWRpdXM6IDE2cHg7XHJcbiAgICBiYWNrZHJvcC1maWx0ZXI6IGJsdXIoNDBweCk7XHJcbiAgICBwYWRkaW5nOiB2bSgyNCk7XHJcbiAgICBmb250LXdlaWdodDogNDAwO1xyXG4gICAgZm9udC1zaXplOiB2bSgzMCk7XHJcbiAgICBjb2xvcjogI0ZGRkZGRjtcclxuICAgIGxpbmUtaGVpZ2h0OiB2bSg0Mik7XHJcbiAgICB0ZXh0LWFsaWduOiByaWdodDtcclxuICAgIGZvbnQtc3R5bGU6IG5vcm1hbDtcclxuICB9XHJcbn0iXX0= */`;
1518
+ document.head.appendChild(document.createElement("style")).appendChild(document.createTextNode(css3));
1519
+ var MaxTextLayer = ({
1520
+ show = false,
1521
+ textLayerHide,
1522
+ text
1523
+ }) => {
1524
+ react.useEffect(() => {
1525
+ const timer = setTimeout(() => {
1526
+ textLayerHide();
1527
+ }, 2e3);
1528
+ return () => {
1529
+ clearTimeout(timer);
1530
+ };
1531
+ });
1532
+ return show && /* @__PURE__ */ jsxRuntime.jsx(jsxRuntime.Fragment, { children: /* @__PURE__ */ jsxRuntime.jsx("div", { className: "container", onClick: textLayerHide, children: /* @__PURE__ */ jsxRuntime.jsx("span", { className: "main_text", children: text }) }) });
1533
+ };
1534
+ var MaxTextLayer_default = MaxTextLayer;
1535
+
1536
+ // src/assets/css/editorTextMenu.scss
1537
+ var css4 = `@charset "UTF-8";
1538
+ .overlay {
1539
+ position: fixed;
1540
+ top: 0;
1541
+ left: 0;
1542
+ width: 100%;
1543
+ height: 100%;
1544
+ background-color: rgba(0, 0, 0, 0.5);
1545
+ display: flex;
1546
+ justify-content: center;
1547
+ align-items: center;
1548
+ color: white;
1549
+ font-size: 24px;
1550
+ overflow: hidden;
1551
+ }
1552
+ .overlay > .text-header {
1553
+ width: 100%;
1554
+ display: flex;
1555
+ justify-content: space-between;
1556
+ align-items: center;
1557
+ height: 11.467vw;
1558
+ padding-left: 4.4vw;
1559
+ padding-right: 3.2vw;
1560
+ box-sizing: border-box;
1561
+ position: fixed;
1562
+ top: 0;
1563
+ transition: all 0.01s;
1564
+ z-index: 16;
1565
+ }
1566
+ .overlay > .text-header > .close {
1567
+ width: 5.0666666667vw;
1568
+ height: 5.0666666667vw;
1569
+ }
1570
+ .overlay > .text-header > .close img {
1571
+ width: 100%;
1572
+ height: 100%;
1573
+ }
1574
+ .overlay > .text-header > .history-operate {
1575
+ height: 7.2vw;
1576
+ display: none;
1577
+ align-items: center;
1578
+ position: absolute;
1579
+ left: 50%;
1580
+ top: 50%;
1581
+ transform: translate(-50%, -50%);
1582
+ }
1583
+ .overlay > .text-header > .history-operate img {
1584
+ width: 4.667vw;
1585
+ height: 5.067vw;
1586
+ }
1587
+ .overlay > .text-header > .history-operate > img:last-child {
1588
+ margin-left: 8vw;
1589
+ }
1590
+ .overlay > .text-header > .next-button {
1591
+ display: flex;
1592
+ justify-content: center;
1593
+ align-items: center;
1594
+ width: 16vw;
1595
+ height: 7.2vw;
1596
+ line-height: 7.2vw;
1597
+ background: #1677FF;
1598
+ border-radius: 6.533vw;
1599
+ text-align: center;
1600
+ font-size: 3.2vw;
1601
+ color: #fff;
1602
+ border: 0;
1603
+ }
1604
+ .overlay .cover {
1605
+ position: fixed;
1606
+ bottom: 8vw;
1607
+ width: 100%;
1608
+ height: 10.6666666667vw;
1609
+ z-index: 999;
1610
+ transition: all 0.1s;
1611
+ }
1612
+ .overlay .text-input, .overlay .mappingarea {
1613
+ font-family: PingFangSC, PingFang SC;
1614
+ border: none;
1615
+ font-size: 22px;
1616
+ /* \u53D6\u6D88\u5916\u8FB9\u6846 */
1617
+ outline: none;
1618
+ background-color: rgba(0, 0, 0, 0);
1619
+ line-height: 30px;
1620
+ -ms-overflow-style: none; /* IE and Edge */
1621
+ scrollbar-width: none; /* Firefox */
1622
+ transition: all 0.1s;
1623
+ }
1624
+ .overlay .text-input::-webkit-scrollbar, .overlay .mappingarea::-webkit-scrollbar {
1625
+ display: none;
1626
+ }
1627
+ .overlay .text-input {
1628
+ padding-top: 1.0666666667vw;
1629
+ padding-bottom: 1.0666666667vw;
1630
+ padding-left: 1.6vw;
1631
+ padding-right: 1.3333333333vw;
1632
+ z-index: 10;
1633
+ width: 84vw;
1634
+ caret-color: #1677ff;
1635
+ position: absolute;
1636
+ top: 30%;
1637
+ left: 5%;
1638
+ height: 200px;
1639
+ word-break: break-all;
1640
+ }
1641
+ .overlay .mappingarea {
1642
+ padding-top: 1.0666666667vw;
1643
+ padding-bottom: 1.0666666667vw;
1644
+ padding-left: 1.6vw;
1645
+ padding-right: 1.3333333333vw;
1646
+ border-radius: 1.3333333333vw;
1647
+ border: 0;
1648
+ position: fixed;
1649
+ top: 30%;
1650
+ left: 5%;
1651
+ height: fit-content;
1652
+ max-height: 200px;
1653
+ color: transparent;
1654
+ overflow-y: scroll;
1655
+ z-index: 9;
1656
+ display: flex;
1657
+ flex-flow: column nowrap;
1658
+ box-sizing: content-box;
1659
+ }
1660
+ .overlay .mappingarea .mappingarea_span {
1661
+ font-size: 22px;
1662
+ max-width: 84vw;
1663
+ white-space: pre-wrap;
1664
+ word-break: break-all;
1665
+ }
1666
+ /*# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VSb290IjoiRDpcXHByb2plY3RzXFx2bW1sLXBsYXllclxccGFja2FnZXNcXGVkaXRvclxcc3JjXFxhc3NldHNcXGNzcyIsInNvdXJjZXMiOlsiZWRpdG9yVGV4dE1lbnUuc2NzcyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiO0FBT0E7RUFDRTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFHQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7O0FBRUE7RUFDRTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7O0FBQ0E7RUFDRTtFQUNBOztBQUVBO0VBQ0U7RUFDQTs7QUFJSjtFQUNFO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBOztBQUVBO0VBQ0U7RUFDQTs7QUFHRjtFQUNFOztBQUlKO0VBQ0U7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBOztBQUlKO0VBQ0U7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBOztBQUdGO0VBRUU7RUFDQTtFQUVBO0FBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFLQTtFQUNBO0VBQ0E7O0FBTEE7RUFDRTs7QUFNSjtFQUNFO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTs7QUFHRjtFQUNFO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7O0FBQ0E7RUFDRTtFQUNBO0VBQ0E7RUFDQSIsInNvdXJjZXNDb250ZW50IjpbIiR2bV9iYXNlOiA3NTA7XHJcblxyXG5AZnVuY3Rpb24gdm0oJHB4KSB7XHJcblxyXG4gICAgQHJldHVybiAoJHB4IC8gNzUwKSAqIDEwMHZ3O1xyXG5cclxufVxyXG4ub3ZlcmxheSB7XHJcbiAgcG9zaXRpb246IGZpeGVkO1xyXG4gIHRvcDogMDtcclxuICBsZWZ0OiAwO1xyXG4gIHdpZHRoOiAxMDAlO1xyXG4gIGhlaWdodDogMTAwJTtcclxuICBiYWNrZ3JvdW5kLWNvbG9yOiByZ2JhKDAsIDAsIDAsIDAuNSk7XHJcbiAgLy8gYmFja2Ryb3AtZmlsdGVyOiBibHVyKDEwcHgpO1xyXG4gIC8vIC13ZWJraXQtYmFja2Ryb3AtZmlsdGVyOiBibHVyKDEwcHgpO1xyXG4gIGRpc3BsYXk6IGZsZXg7XHJcbiAganVzdGlmeS1jb250ZW50OiBjZW50ZXI7XHJcbiAgYWxpZ24taXRlbXM6IGNlbnRlcjtcclxuICBjb2xvcjogd2hpdGU7XHJcbiAgZm9udC1zaXplOiAyNHB4O1xyXG4gIG92ZXJmbG93OiBoaWRkZW47XHJcbiAgLy8g6aG26YOoXHJcbiAgJj4udGV4dC1oZWFkZXIge1xyXG4gICAgd2lkdGg6IDEwMCU7XHJcbiAgICBkaXNwbGF5OiBmbGV4O1xyXG4gICAganVzdGlmeS1jb250ZW50OiBzcGFjZS1iZXR3ZWVuO1xyXG4gICAgYWxpZ24taXRlbXM6IGNlbnRlcjtcclxuICAgIGhlaWdodDogMTEuNDY3dnc7XHJcbiAgICBwYWRkaW5nLWxlZnQ6IDQuNHZ3O1xyXG4gICAgcGFkZGluZy1yaWdodDogMy4ydnc7XHJcbiAgICBib3gtc2l6aW5nOiBib3JkZXItYm94O1xyXG4gICAgcG9zaXRpb246IGZpeGVkO1xyXG4gICAgdG9wOiAwO1xyXG4gICAgdHJhbnNpdGlvbjogYWxsIDAuMDFzO1xyXG4gICAgei1pbmRleDoxNjtcclxuICAgICY+LmNsb3NlIHtcclxuICAgICAgd2lkdGg6IHZtKDM4KTtcclxuICAgICAgaGVpZ2h0OiB2bSgzOCk7XHJcblxyXG4gICAgICBpbWcge1xyXG4gICAgICAgIHdpZHRoOiAxMDAlO1xyXG4gICAgICAgIGhlaWdodDogMTAwJTtcclxuICAgICAgfVxyXG4gICAgfVxyXG5cclxuICAgICY+Lmhpc3Rvcnktb3BlcmF0ZSB7XHJcbiAgICAgIGhlaWdodDogNy4ydnc7XHJcbiAgICAgIGRpc3BsYXk6IG5vbmU7XHJcbiAgICAgIGFsaWduLWl0ZW1zOiBjZW50ZXI7XHJcbiAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTtcclxuICAgICAgbGVmdDogNTAlO1xyXG4gICAgICB0b3A6IDUwJTtcclxuICAgICAgdHJhbnNmb3JtOiB0cmFuc2xhdGUoLTUwJSwgLTUwJSk7XHJcblxyXG4gICAgICBpbWcge1xyXG4gICAgICAgIHdpZHRoOiA0LjY2N3Z3O1xyXG4gICAgICAgIGhlaWdodDogNS4wNjd2dztcclxuICAgICAgfVxyXG5cclxuICAgICAgJj5pbWc6bGFzdC1jaGlsZCB7XHJcbiAgICAgICAgbWFyZ2luLWxlZnQ6IDh2dztcclxuICAgICAgfVxyXG4gICAgfVxyXG5cclxuICAgICY+Lm5leHQtYnV0dG9uIHtcclxuICAgICAgZGlzcGxheTogZmxleDtcclxuICAgICAganVzdGlmeS1jb250ZW50OiBjZW50ZXI7XHJcbiAgICAgIGFsaWduLWl0ZW1zOiBjZW50ZXI7XHJcbiAgICAgIHdpZHRoOiAxNnZ3O1xyXG4gICAgICBoZWlnaHQ6IDcuMnZ3O1xyXG4gICAgICBsaW5lLWhlaWdodDogNy4ydnc7XHJcbiAgICAgIGJhY2tncm91bmQ6ICMxNjc3RkY7XHJcbiAgICAgIGJvcmRlci1yYWRpdXM6IDYuNTMzdnc7XHJcbiAgICAgIHRleHQtYWxpZ246IGNlbnRlcjtcclxuICAgICAgZm9udC1zaXplOiAzLjJ2dztcclxuICAgICAgY29sb3I6ICNmZmY7XHJcbiAgICAgIGJvcmRlcjogMDtcclxuICAgIH1cclxuICB9XHJcblxyXG4gIC5jb3ZlciB7XHJcbiAgICBwb3NpdGlvbjogZml4ZWQ7XHJcbiAgICBib3R0b206IHZtKDYwKTtcclxuICAgIHdpZHRoOiAxMDAlO1xyXG4gICAgaGVpZ2h0OnZtKDgwKTtcclxuICAgIHotaW5kZXg6IDk5OTtcclxuICAgIHRyYW5zaXRpb246IGFsbCAwLjFzO1xyXG4gIH1cclxuXHJcbiAgLnRleHQtaW5wdXQsLm1hcHBpbmdhcmVhe1xyXG4gICAgLy8gZm9udC1mYW1pbHk6O1xyXG4gICAgZm9udC1mYW1pbHk6IFBpbmdGYW5nU0MsIFBpbmdGYW5nIFNDO1xyXG4gICAgYm9yZGVyOiBub25lO1xyXG4gICAgLy8gZm9udC13ZWlnaHQ6IDYwMDtcclxuICAgIGZvbnQtc2l6ZTogMjJweDtcclxuICAgIC8qIOWPlua2iOWklui+ueahhiAqL1xyXG4gICAgb3V0bGluZTogbm9uZTtcclxuICAgIGJhY2tncm91bmQtY29sb3I6IHJnYmEoMCwgMCwgMCwgMCk7XHJcbiAgICBsaW5lLWhlaWdodDogMzBweDtcclxuICAgIC8vIOmakOiXj+a7muWKqOadoe+8jOS9huS7jeeEtuS/neaMgea7muWKqOWKn+iDvVxyXG4gICAgJjo6LXdlYmtpdC1zY3JvbGxiYXIgeyBcclxuICAgICAgZGlzcGxheTogbm9uZTsgXHJcbiAgICB9XHJcbiAgICAtbXMtb3ZlcmZsb3ctc3R5bGU6IG5vbmU7ICAvKiBJRSBhbmQgRWRnZSAqL1xyXG4gICAgc2Nyb2xsYmFyLXdpZHRoOiBub25lOyAgLyogRmlyZWZveCAqL1xyXG4gICAgdHJhbnNpdGlvbjogYWxsIDAuMXM7XHJcbiAgfVxyXG4gIC50ZXh0LWlucHV0e1xyXG4gICAgcGFkZGluZy10b3A6IHZtKDgpO1xyXG4gICAgcGFkZGluZy1ib3R0b206IHZtKDgpO1xyXG4gICAgcGFkZGluZy1sZWZ0OiB2bSgxMik7XHJcbiAgICBwYWRkaW5nLXJpZ2h0OiB2bSgxMCk7XHJcbiAgICB6LWluZGV4OiAxMDtcclxuICAgIHdpZHRoOiA4NHZ3O1xyXG4gICAgY2FyZXQtY29sb3I6ICMxNjc3RkZGRjtcclxuICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTtcclxuICAgIHRvcDogMzAlO1xyXG4gICAgbGVmdDogNSU7XHJcbiAgICBoZWlnaHQ6IDIwMHB4O1xyXG4gICAgd29yZC1icmVhazogYnJlYWstYWxsO1xyXG4gICAgLy8gcGFkZGluZzogdm0oMTgpO1xyXG4gIH1cclxuICAubWFwcGluZ2FyZWF7XHJcbiAgICBwYWRkaW5nLXRvcDogdm0oOCk7XHJcbiAgICBwYWRkaW5nLWJvdHRvbTogdm0oOCk7XHJcbiAgICBwYWRkaW5nLWxlZnQ6IHZtKDEyKTtcclxuICAgIHBhZGRpbmctcmlnaHQ6IHZtKDEwKTtcclxuICAgIGJvcmRlci1yYWRpdXM6IHZtKDEwKTtcclxuICAgIGJvcmRlcjowO1xyXG4gICAgcG9zaXRpb246IGZpeGVkO1xyXG4gICAgdG9wOiAzMCU7XHJcbiAgICBsZWZ0OiA1JTtcclxuICAgIGhlaWdodDogZml0LWNvbnRlbnQ7XHJcbiAgICBtYXgtaGVpZ2h0OiAyMDBweDtcclxuICAgIGNvbG9yOiB0cmFuc3BhcmVudDsgLy/orr7nva7popzoibLpgI/mmI7vvIzkv53or4Hog4zmma/popzoibJcclxuICAgIG92ZXJmbG93LXk6IHNjcm9sbDtcclxuICAgIHotaW5kZXg6IDk7XHJcbiAgICBkaXNwbGF5OiBmbGV4O1xyXG4gICAgZmxleC1mbG93OiBjb2x1bW4gbm93cmFwO1xyXG4gICAgYm94LXNpemluZzogY29udGVudC1ib3g7XHJcbiAgICAubWFwcGluZ2FyZWFfc3BhbntcclxuICAgICAgZm9udC1zaXplOiAyMnB4O1xyXG4gICAgICBtYXgtd2lkdGg6IDg0dnc7XHJcbiAgICAgIHdoaXRlLXNwYWNlOiBwcmUtd3JhcDtcclxuICAgICAgd29yZC1icmVhazogYnJlYWstYWxsO1xyXG4gICAgfVxyXG4gIH1cclxufSJdfQ== */`;
1667
+ document.head.appendChild(document.createElement("style")).appendChild(document.createTextNode(css4));
1668
+ var checkIPhoneSeries = () => {
1669
+ const screenWidth = window.screen.width;
1670
+ const screenHeight = window.screen.height;
1671
+ if (screenWidth === 320 && screenHeight === 480) {
1672
+ return "iPhone 4 or 4S";
1673
+ } else if (screenWidth === 375 && screenHeight === 667) {
1674
+ return "iPhone 6/7/8";
1675
+ } else if (screenWidth === 414 && screenHeight === 736) {
1676
+ return "iPhone 6/7/8 Plus";
1677
+ } else if (screenWidth === 375 && screenHeight === 812) {
1678
+ return "iPhone X/XS";
1679
+ } else if (screenWidth === 414 && screenHeight === 896) {
1680
+ return "iPhone XR/11";
1681
+ } else if (screenWidth === 414 && screenHeight === 844) {
1682
+ return "iPhone 12 mini";
1683
+ } else if (screenWidth === 414 && screenHeight === 915) {
1684
+ return "iPhone 13 Pro Max/12 Pro Max";
1685
+ } else if (screenWidth === 390 && screenHeight === 844) {
1686
+ return "iPhone 13 mini";
1687
+ } else {
1688
+ return "Unknown iPhone model";
1689
+ }
1690
+ };
1691
+ var iPhoneAdapter = (series) => {
1692
+ const seriesArr = ["iPhone 6/7/8 Plus", "iPhone 6/7/8"];
1693
+ return seriesArr.includes(series);
1694
+ };
1695
+ var watchKeyBoard = (callback) => {
1696
+ const focusInHandler = (e) => {
1697
+ callback(true);
1698
+ stopMove();
1699
+ };
1700
+ const focusOutHandler = (e) => {
1701
+ callback(false);
1702
+ };
1703
+ document.body.addEventListener("focusin", focusInHandler);
1704
+ document.body.addEventListener("focusout", focusOutHandler);
1705
+ return () => {
1706
+ document.body.removeEventListener("focusin", focusInHandler);
1707
+ document.body.removeEventListener("focusout", focusOutHandler);
1708
+ };
1709
+ };
1710
+ var stopMove = () => {
1711
+ const dom = document.getElementsByClassName("overlay")[0];
1712
+ const element = document.querySelector(".mappingarea");
1713
+ const stopScroll = (e) => {
1714
+ var _a, _b, _c;
1715
+ const lastTouchPositionX = 0;
1716
+ const lastTouchPositionY = 0;
1717
+ const currentTouchPositionX = e.touches[0].clientX;
1718
+ const currentTouchPositionY = e.touches[0].clientY;
1719
+ const deltaX = currentTouchPositionX - lastTouchPositionX;
1720
+ const deltaY = currentTouchPositionY - lastTouchPositionY;
1721
+ if (["text-header", "overlay", "text_bg_change"].includes((_a = e.target) == null ? void 0 : _a.className)) {
1722
+ e.preventDefault();
1723
+ }
1724
+ if (element) {
1725
+ const willOverflow = element.scrollHeight > element.clientHeight;
1726
+ if (willOverflow) {
1727
+ return;
1728
+ } else if (((_b = e.target) == null ? void 0 : _b.className.split(" ").includes("color-item")) || ((_c = e.target) == null ? void 0 : _c.className) === "text_color_change") {
1729
+ if (deltaX < 0 || deltaX > 0) {
1730
+ return;
1731
+ } else {
1732
+ e.preventDefault();
1733
+ }
1734
+ } else {
1735
+ if (Math.abs(deltaY) > Math.abs(deltaX)) {
1736
+ e.preventDefault();
1737
+ }
1738
+ }
1739
+ }
1740
+ e.preventDefault();
1741
+ };
1742
+ if (dom) {
1743
+ dom.addEventListener("touchmove", stopScroll);
1744
+ }
1745
+ };
1746
+ var onKeyBoardAction = (status, headerRef, textareaRef, coverRef, mappingareaRef, aimTop) => {
1747
+ if (vmmlUtils.isIOS()) {
1748
+ forIos(status, headerRef, textareaRef, coverRef);
1749
+ }
1750
+ };
1751
+ var forIos = (status, headerRef, textareaRef, coverRef, mappingareaRef) => {
1752
+ const series = checkIPhoneSeries();
1753
+ const isIPhoneAdapt = iPhoneAdapter(series);
1754
+ if (status) {
1755
+ const totalHeight = document.documentElement.clientHeight || document.body.clientHeight;
1756
+ const keyBoardHeight = totalHeight * 0.25;
1757
+ if (coverRef && textareaRef) {
1758
+ const textareaRefPos = textareaRef.getBoundingClientRect();
1759
+ const { height } = textareaRefPos;
1760
+ if (isIPhoneAdapt) {
1761
+ coverRef.style.bottom = `${keyBoardHeight + 50}px`;
1762
+ } else {
1763
+ coverRef.style.transform = `translateY(${-(height + 10)}px)`;
1764
+ }
1765
+ }
1766
+ } else {
1767
+ if (coverRef) {
1768
+ if (isIPhoneAdapt) {
1769
+ coverRef.style.bottom = `8vw`;
1770
+ } else {
1771
+ coverRef.style.transform = `translateY(0px)`;
1772
+ }
1773
+ }
1774
+ }
1775
+ };
1776
+
1777
+ // src/assets/css/colorSelector.scss
1778
+ var css5 = `@charset "UTF-8";
1779
+ .color-selector {
1780
+ width: 100%;
1781
+ height: 100%;
1782
+ display: flex;
1783
+ flex-flow: row nowrap;
1784
+ align-items: center;
1785
+ padding-right: 2.6666666667vw;
1786
+ }
1787
+ .color-selector .text_bg_change {
1788
+ width: 6.4vw;
1789
+ height: 6.4vw;
1790
+ flex: 0 0 auto;
1791
+ text-align: center;
1792
+ line-height: 6.4vw;
1793
+ padding: 0 4.8vw;
1794
+ margin-right: 4vw;
1795
+ border-right: 2px solid rgba(255, 255, 255, 0.4); /* \u8BBE\u7F6E\u5DE6\u8FB9\u6846\u7684\u5BBD\u5EA6\u3001\u6837\u5F0F\u548C\u989C\u8272 */
1796
+ }
1797
+ .color-selector .text_color_change {
1798
+ flex: 1 1 auto;
1799
+ display: flex;
1800
+ flex-flow: row nowrap;
1801
+ overflow-x: auto;
1802
+ white-space: nowrap;
1803
+ height: 100%;
1804
+ padding-right: 1.3333333333vw;
1805
+ align-items: center;
1806
+ -ms-overflow-style: none; /* IE and Edge */
1807
+ scrollbar-width: none; /* Firefox */
1808
+ }
1809
+ .color-selector .text_color_change > * {
1810
+ flex-shrink: 0;
1811
+ }
1812
+ .color-selector .text_color_change .color-item {
1813
+ width: 6.4vw;
1814
+ height: 6.4vw;
1815
+ border-radius: 50%;
1816
+ margin: 0 2vw;
1817
+ box-sizing: border-box;
1818
+ }
1819
+ .color-selector .text_color_change .black-border {
1820
+ border: 0.2666666667vw solid #333333;
1821
+ }
1822
+ .color-selector .text_color_change .current {
1823
+ box-shadow: 0 0 0 0.8vw #1677FF;
1824
+ }
1825
+ .color-selector .text_color_change::-webkit-scrollbar {
1826
+ display: none;
1827
+ }
1828
+ /*# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VSb290IjoiRDpcXHByb2plY3RzXFx2bW1sLXBsYXllclxccGFja2FnZXNcXGVkaXRvclxcc3JjXFxhc3NldHNcXGNzcyIsInNvdXJjZXMiOlsiY29sb3JTZWxlY3Rvci5zY3NzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7QUFRQTtFQUNFO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTs7QUFDQTtFQUNFO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7O0FBRUY7RUFDRTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBQ0E7RUFDQTtFQUNBO0VBc0JBO0VBQ0E7O0FBdEJBO0VBQ0U7O0FBRUY7RUFDRTtFQUNBO0VBQ0E7RUFDQTtFQUNBOztBQUVGO0VBQ0U7O0FBRUY7RUFFRTs7QUFHRjtFQUNJIiwic291cmNlc0NvbnRlbnQiOlsiJHZtX2Jhc2U6IDc1MDtcclxuXHJcbkBmdW5jdGlvbiB2bSgkcHgpIHtcclxuXHJcbiAgICBAcmV0dXJuICgkcHggLyA3NTApICogMTAwdnc7XHJcblxyXG59XHJcblxyXG4uY29sb3Itc2VsZWN0b3J7XHJcbiAgd2lkdGg6IDEwMCU7XHJcbiAgaGVpZ2h0OiAxMDAlO1xyXG4gIGRpc3BsYXk6IGZsZXg7XHJcbiAgZmxleC1mbG93OiByb3cgbm93cmFwO1xyXG4gIGFsaWduLWl0ZW1zOiBjZW50ZXI7XHJcbiAgcGFkZGluZy1yaWdodDogdm0oMjApO1xyXG4gIC50ZXh0X2JnX2NoYW5nZXtcclxuICAgIHdpZHRoOiB2bSg0OCk7XHJcbiAgICBoZWlnaHQ6IHZtKDQ4KTtcclxuICAgIGZsZXg6IDAgMCBhdXRvO1xyXG4gICAgdGV4dC1hbGlnbjogY2VudGVyO1xyXG4gICAgbGluZS1oZWlnaHQ6IHZtKDQ4KTtcclxuICAgIHBhZGRpbmc6MCB2bSgzNik7XHJcbiAgICBtYXJnaW4tcmlnaHQ6IHZtKDMwKTtcclxuICAgIGJvcmRlci1yaWdodDogMnB4IHNvbGlkICNGRkZGRkY2NjsgLyog6K6+572u5bem6L655qGG55qE5a695bqm44CB5qC35byP5ZKM6aKc6ImyICovXHJcbiAgfVxyXG4gIC50ZXh0X2NvbG9yX2NoYW5nZXtcclxuICAgIGZsZXg6IDEgMSBhdXRvO1xyXG4gICAgZGlzcGxheTogZmxleDtcclxuICAgIGZsZXgtZmxvdzogcm93IG5vd3JhcDtcclxuICAgIG92ZXJmbG93LXg6IGF1dG87IC8vIOWFgeiuuOaoquWQkea7muWKqFxyXG4gICAgd2hpdGUtc3BhY2U6IG5vd3JhcDsgLy8g56Gu5L+d5paH5pys5LiN5Lya5o2i6KGMXHJcbiAgICBoZWlnaHQ6MTAwJTtcclxuICAgIHBhZGRpbmctcmlnaHQ6IHZtKDEwKTtcclxuICAgIGFsaWduLWl0ZW1zOiBjZW50ZXI7XHJcbiAgICAmID4gKiB7XHJcbiAgICAgIGZsZXgtc2hyaW5rOiAwOyAvLyDpmLLmraLlrZDlhYPntKDnvKnlsI9cclxuICAgIH1cclxuICAgIC5jb2xvci1pdGVte1xyXG4gICAgICB3aWR0aDogdm0oNDgpO1xyXG4gICAgICBoZWlnaHQ6dm0oNDgpO1xyXG4gICAgICBib3JkZXItcmFkaXVzOiA1MCU7XHJcbiAgICAgIG1hcmdpbjogMCB2bSgxNSk7XHJcbiAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XHJcbiAgICB9XHJcbiAgICAuYmxhY2stYm9yZGVye1xyXG4gICAgICBib3JkZXI6dm0oMikgc29saWQgIzMzMzMzM0ZGXHJcbiAgICB9XHJcbiAgICAuY3VycmVudHtcclxuICAgICAgLy8gYm9yZGVyOiB2bSg2KSBzb2xpZCAjMTY3N0ZGO1xyXG4gICAgICBib3gtc2hhZG93OiAwIDAgMCB2bSg2KSAjMTY3N0ZGO1xyXG4gICAgfVxyXG4gICAgLy8g6ZqQ6JeP5rua5Yqo5p2h77yM5L2G5LuN54S25L+d5oyB5rua5Yqo5Yqf6IO9XHJcbiAgICAmOjotd2Via2l0LXNjcm9sbGJhciB7IFxyXG4gICAgICAgIGRpc3BsYXk6IG5vbmU7IFxyXG4gICAgfVxyXG4gICAgLW1zLW92ZXJmbG93LXN0eWxlOiBub25lOyAgLyogSUUgYW5kIEVkZ2UgKi9cclxuICAgIHNjcm9sbGJhci13aWR0aDogbm9uZTsgIC8qIEZpcmVmb3ggKi9cclxuICB9XHJcbn0iXX0= */`;
1829
+ document.head.appendChild(document.createElement("style")).appendChild(document.createTextNode(css5));
1830
+ var colorList = [
1831
+ { colorName: "white", colorValue: "rgb(255,255,255)" },
1832
+ { colorName: "black", colorValue: "rgb(0,0,0)" },
1833
+ { colorName: "gray", colorValue: "rgb(153,153,153)" },
1834
+ { colorName: "red", colorValue: "rgb(248,82,81)" },
1835
+ { colorName: "orange", colorValue: "rgb(250,158,60)" },
1836
+ { colorName: "yellow", colorValue: "rgb(255,196,0)" },
1837
+ { colorName: "lightGreen", colorValue: "rgb(145,212,0)" },
1838
+ { colorName: "green", colorValue: "rgb(0,181,212)" },
1839
+ { colorName: "lightBlue", colorValue: "rgb(0,183,244)" },
1840
+ { colorName: "blue", colorValue: "rgb(23,120,255)" },
1841
+ { colorName: "purple", colorValue: "rgb(82,95,255)" }
1842
+ ];
1843
+ var ColorSelector = react.forwardRef(({ onColorChange, onBackGroundChange }, ref) => {
1844
+ const [currentColorItem, setCurrentColorItem] = react.useState(colorList.find((color) => color.colorName === "red"));
1845
+ react.useState(null);
1846
+ const [isSetBack, setIsSetBack] = react.useState(false);
1847
+ const setColorClass = (item) => {
1848
+ const { colorName } = currentColorItem;
1849
+ const classes = [
1850
+ item.colorName === "black" && "black-border",
1851
+ item.colorName === colorName && "current",
1852
+ "color-item"
1853
+ ].filter(Boolean).join(" ");
1854
+ return classes;
1855
+ };
1856
+ const handleColorClick = (item) => {
1857
+ setCurrentColorItem(item);
1858
+ onColorChange(item);
1859
+ };
1860
+ const handleChangeBackGround = () => {
1861
+ const setBgStatus = new Promise((resolve, reject) => {
1862
+ setIsSetBack(!isSetBack);
1863
+ resolve();
1864
+ });
1865
+ setBgStatus.then(() => {
1866
+ onBackGroundChange(currentColorItem);
1867
+ });
1868
+ };
1869
+ const getBackState = () => {
1870
+ return isSetBack;
1871
+ };
1872
+ react.useImperativeHandle(ref, () => ({
1873
+ getBackState,
1874
+ setIsSetBack,
1875
+ setCurrentColorItem
1876
+ }));
1877
+ return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "color-selector", children: [
1878
+ /* @__PURE__ */ jsxRuntime.jsx(
1879
+ "div",
1880
+ {
1881
+ className: "text_bg_change",
1882
+ onClick: () => {
1883
+ handleChangeBackGround();
1884
+ },
1885
+ children: /* @__PURE__ */ jsxRuntime.jsx("img", { alt: "", src: isSetBack ? iconText2 : iconText1, style: { width: "100%", height: "100%" } })
1886
+ }
1887
+ ),
1888
+ /* @__PURE__ */ jsxRuntime.jsx("div", { className: "text_color_change", children: colorList.map((item) => {
1889
+ return /* @__PURE__ */ jsxRuntime.jsx(
1890
+ "div",
1891
+ {
1892
+ className: setColorClass(item),
1893
+ style: { backgroundColor: item.colorValue },
1894
+ onClick: () => {
1895
+ handleColorClick(item);
1896
+ }
1897
+ },
1898
+ item.colorName
1899
+ );
1900
+ }) })
1901
+ ] });
1902
+ });
1903
+ var ColorSelector_default = ColorSelector;
1904
+ var formatText = (text, maxLengthBase = 40) => {
1905
+ var _a;
1906
+ const newlineRegex = /(\r\n|\r|\n)/g;
1907
+ const matches = ((_a = text.match(newlineRegex)) == null ? void 0 : _a.length) || 0;
1908
+ const maxLength = maxLengthBase + matches;
1909
+ let trimmedText = text.substring(0, maxLength);
1910
+ if (text.length - matches === maxLengthBase) {
1911
+ trimmedText = trimmedText.replace(/(\r\n|\r|\n)+$/g, "");
1912
+ }
1913
+ return trimmedText;
1914
+ };
1915
+ var TextMenu = react.forwardRef(({ createText, textClose, textInfo, showTextButtons }, ref) => {
1916
+ const formRef = react.useRef(null);
1917
+ const headerRef = react.useRef(null);
1918
+ const textareaRef = react.useRef(null);
1919
+ const coverRef = react.useRef(null);
1920
+ const mappingarea = react.useRef(null);
1921
+ const [textContent, setTextContent] = react.useState("");
1922
+ const [bgColor, setBgColor] = react.useState("transparent");
1923
+ const [textColor, setTextColor] = react.useState("rgb(248,82,81)");
1924
+ const [textPos, setTextPos] = react.useState({ left: 0, top: 0, angle: 0, scaleX: 0.75, scaleY: 0.75, zoomX: 0, zoomY: 0 });
1925
+ const [textBasicInfo, setTextBasicInfo] = react.useState({
1926
+ colorName: "red",
1927
+ colorValue: "rgb(248,82,81)",
1928
+ isBack: false,
1929
+ textAlign: "left"
1930
+ });
1931
+ const colorSelectorRef = react.useRef(null);
1932
+ const [textContentOnShow, setTextContentOnShow] = react.useState([]);
1933
+ const [scrollYValue, setScrollYValue] = react.useState(() => {
1934
+ return Number.parseInt(localStorage.getItem("scrollYValue")) || null;
1935
+ });
1936
+ const scrollYValueRef = react.useRef(scrollYValue);
1937
+ react.useEffect(() => {
1938
+ const callback = (status) => {
1939
+ if (scrollYValueRef.current === null) {
1940
+ setTimeout(() => {
1941
+ const newScrollYValue = window.scrollY;
1942
+ setScrollYValue(newScrollYValue);
1943
+ scrollYValueRef.current = newScrollYValue;
1944
+ localStorage.setItem("scrollYValue", newScrollYValue.toString());
1945
+ }, 150);
1946
+ }
1947
+ setTimeout(() => {
1948
+ onKeyBoardAction(
1949
+ status,
1950
+ headerRef.current,
1951
+ textareaRef.current,
1952
+ coverRef.current,
1953
+ mappingarea.current
1954
+ );
1955
+ }, 200);
1956
+ };
1957
+ const removeListeners = watchKeyBoard(callback);
1958
+ return () => {
1959
+ removeListeners();
1960
+ };
1961
+ }, []);
1962
+ react.useEffect(() => {
1963
+ const syncScroll = () => {
1964
+ if (textareaRef.current && mappingarea.current) {
1965
+ const scrollPosition = textareaRef.current.scrollTop;
1966
+ mappingarea.current.scrollTop = scrollPosition;
1967
+ }
1968
+ };
1969
+ if (textareaRef.current) {
1970
+ textareaRef.current.addEventListener("scroll", syncScroll);
1971
+ textareaRef.current.addEventListener("input", syncScroll);
1972
+ }
1973
+ return () => {
1974
+ if (textareaRef.current) {
1975
+ textareaRef.current.removeEventListener("scroll", syncScroll);
1976
+ textareaRef.current.removeEventListener("input", syncScroll);
1977
+ }
1978
+ };
1979
+ }, []);
1980
+ react.useEffect(() => {
1981
+ let lines = [];
1982
+ if (textContent.includes("\r")) {
1983
+ lines = textContent.split("\r");
1984
+ } else {
1985
+ lines = textContent.split("\n");
1986
+ }
1987
+ setTextContentOnShow(lines);
1988
+ }, [textContent]);
1989
+ react.useEffect(() => {
1990
+ if (Object.keys(textInfo).length > 0) {
1991
+ setText(textInfo);
1992
+ } else {
1993
+ resetInfo();
1994
+ }
1995
+ }, [textInfo]);
1996
+ react.useEffect(() => {
1997
+ if (!vmmlUtils.isIOS()) {
1998
+ if (mappingarea.current && textareaRef.current) {
1999
+ textareaRef.current.style.position = "static";
2000
+ mappingarea.current.style.maxHeight = textareaRef.current.style.height = "50vh";
2001
+ mappingarea.current.style.maxWidth = getComputedStyle(textareaRef.current).width;
2002
+ textareaRef.current.focus();
2003
+ }
2004
+ } else {
2005
+ if (textareaRef.current) {
2006
+ textareaRef.current.focus();
2007
+ }
2008
+ }
2009
+ }, []);
2010
+ const handleOnChange = (e) => {
2011
+ const inputValue = e.target.value;
2012
+ setTextContent(formatText(inputValue));
2013
+ };
2014
+ const handleSubmit = (e) => {
2015
+ if (showTextButtons) {
2016
+ e.preventDefault();
2017
+ }
2018
+ if (formRef.current) {
2019
+ const formData = new FormData(formRef.current);
2020
+ const formJson = Object.fromEntries(formData.entries());
2021
+ const { input_content } = formJson;
2022
+ renderText(input_content);
2023
+ }
2024
+ };
2025
+ const handleChangeColor = (item) => {
2026
+ setColor(item);
2027
+ };
2028
+ const onBackGroundChange = (currentColorItem) => {
2029
+ setColor(currentColorItem);
2030
+ };
2031
+ const setColor = (colorItem) => {
2032
+ if (textareaRef.current) {
2033
+ textareaRef.current.focus();
2034
+ }
2035
+ const { current } = colorSelectorRef;
2036
+ const { colorName, colorValue } = colorItem;
2037
+ const isBack = current ? current.getBackState() : false;
2038
+ const textBasic = {
2039
+ colorName,
2040
+ colorValue,
2041
+ isBack,
2042
+ textAlign: textBasicInfo.textAlign
2043
+ };
2044
+ setTextBasicInfo(textBasic);
2045
+ if (!isBack) {
2046
+ setBgColor("transparent");
2047
+ setTextColor(colorValue);
2048
+ } else {
2049
+ setBgColor(colorValue);
2050
+ colorName === "white" || colorValue === "rgba(255, 255, 255, 1)" ? setTextColor("#000") : setTextColor("#fff");
2051
+ }
2052
+ };
2053
+ const setText = (textInfo2) => {
2054
+ const { bgColor: bgColor2, text, textColor: textColor2, left, top, angle, scaleX, scaleY, zoomX, zoomY, textBasicInfo: textBasicInfo2, width, height } = textInfo2;
2055
+ const { isBack, colorName, colorValue } = textBasicInfo2;
2056
+ const fillColor = text === "\u8BF7\u8F93\u5165\u6587\u6848" && textColor2 === "rgba(0, 0, 0, 0)" ? "rgba(255, 255, 255, 1)" : textColor2;
2057
+ setBgColor(bgColor2);
2058
+ setTextColor(fillColor);
2059
+ setTextContent(text);
2060
+ setTextBasicInfo(textBasicInfo2);
2061
+ setTextPos({ left, top, angle, scaleX, scaleY, zoomX, zoomY, width, height });
2062
+ const { current } = colorSelectorRef;
2063
+ if (!current) return;
2064
+ current.setIsSetBack(isBack);
2065
+ current.setCurrentColorItem({ colorName, colorValue });
2066
+ };
2067
+ const resetInfo = () => {
2068
+ setBgColor("transparent");
2069
+ setTextColor("rgb(248,82,81)");
2070
+ setTextContent("");
2071
+ setTextPos({ left: 0, top: 0, angle: 0, scaleX: 0.75, scaleY: 0.75, zoomX: 0, zoomY: 0 });
2072
+ };
2073
+ const close = () => {
2074
+ textClose(textInfo.id);
2075
+ };
2076
+ const renderText = (input_content) => {
2077
+ const { current } = mappingarea;
2078
+ if (current) {
2079
+ const computedStyle = window.getComputedStyle(current);
2080
+ const { width, height } = computedStyle;
2081
+ setTextPos(
2082
+ Object.assign(textPos, { width: Number(width.split("px")[0]), height: Number(height.split("px")[0]) })
2083
+ );
2084
+ }
2085
+ if (input_content && input_content.trim() !== "") {
2086
+ const { id, fontFamily, fontAssetUrl } = textInfo;
2087
+ createText({ textContent: input_content, bgColor, textColor, position: textPos, textBasicInfo, id, fontFamily, fontAssetUrl });
2088
+ } else {
2089
+ textClose(textInfo.id);
2090
+ }
2091
+ };
2092
+ react.useImperativeHandle(ref, () => ({
2093
+ setText,
2094
+ close,
2095
+ handleSubmit
2096
+ }));
2097
+ return /* @__PURE__ */ jsxRuntime.jsx("form", { method: "post", onSubmit: handleSubmit, ref: formRef, children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "overlay", children: [
2098
+ showTextButtons && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "text-header", ref: headerRef, children: [
2099
+ /* @__PURE__ */ jsxRuntime.jsx("div", { onClick: () => close(), className: "close", children: /* @__PURE__ */ jsxRuntime.jsx("img", { crossOrigin: "anonymous", src: closeIcon, alt: "close" }) }),
2100
+ /* @__PURE__ */ jsxRuntime.jsx("button", { type: "submit", className: "next-button", children: "\u5B8C\u6210" })
2101
+ ] }),
2102
+ !vmmlUtils.isIOS() && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "edit_container", style: {
2103
+ width: "100%",
2104
+ position: "relative",
2105
+ paddingLeft: "4.4vw",
2106
+ paddingRight: "3.2vw",
2107
+ display: "flex"
2108
+ }, children: [
2109
+ /* @__PURE__ */ jsxRuntime.jsx(
2110
+ "textarea",
2111
+ {
2112
+ ref: textareaRef,
2113
+ cols: 20,
2114
+ wrap: "hard",
2115
+ name: "input_content",
2116
+ className: "text-input",
2117
+ value: textContent,
2118
+ onChange: handleOnChange,
2119
+ style: { color: textColor, width: "94%", fontFamily: textInfo.fontFamily }
2120
+ }
2121
+ ),
2122
+ /* @__PURE__ */ jsxRuntime.jsx(
2123
+ "div",
2124
+ {
2125
+ className: "mappingarea",
2126
+ ref: mappingarea,
2127
+ contentEditable: true,
2128
+ suppressContentEditableWarning: true,
2129
+ style: {
2130
+ background: bgColor,
2131
+ position: "absolute",
2132
+ top: "0",
2133
+ zIndex: "-1",
2134
+ left: "4.4vw"
2135
+ },
2136
+ children: textContentOnShow.map((text, index) => {
2137
+ return /* @__PURE__ */ jsxRuntime.jsx("span", { className: "mappingarea_span", style: { maxWidth: "100%" }, children: text ? text : " " }, index);
2138
+ })
2139
+ }
2140
+ )
2141
+ ] }),
2142
+ vmmlUtils.isIOS() && /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
2143
+ /* @__PURE__ */ jsxRuntime.jsx(
2144
+ "textarea",
2145
+ {
2146
+ ref: textareaRef,
2147
+ cols: 20,
2148
+ wrap: "hard",
2149
+ name: "input_content",
2150
+ className: "text-input",
2151
+ value: textContent,
2152
+ onChange: handleOnChange,
2153
+ style: { color: textColor, fontFamily: textInfo.fontFamily }
2154
+ }
2155
+ ),
2156
+ /* @__PURE__ */ jsxRuntime.jsx(
2157
+ "div",
2158
+ {
2159
+ className: "mappingarea",
2160
+ ref: mappingarea,
2161
+ contentEditable: true,
2162
+ suppressContentEditableWarning: true,
2163
+ style: { background: bgColor },
2164
+ children: textContentOnShow.map((text, index) => {
2165
+ return /* @__PURE__ */ jsxRuntime.jsx("span", { className: "mappingarea_span", children: text ? text : " " }, index);
2166
+ })
2167
+ }
2168
+ )
2169
+ ] }),
2170
+ /* @__PURE__ */ jsxRuntime.jsx("div", { ref: coverRef, className: "cover", children: /* @__PURE__ */ jsxRuntime.jsx(
2171
+ ColorSelector_default,
2172
+ {
2173
+ ref: colorSelectorRef,
2174
+ onColorChange: handleChangeColor,
2175
+ onBackGroundChange
2176
+ }
2177
+ ) })
2178
+ ] }) });
2179
+ });
2180
+ var TextMenu_default = TextMenu;
2181
+ var VideoMenu = ({ createImage, videoMenus, menuState }) => {
2182
+ const [active, setActive] = react.useState();
2183
+ const [menus, setMenus] = react.useState([]);
2184
+ const [items, setItems] = react.useState([]);
2185
+ const onClickClass = ({ id, emojiList }) => {
2186
+ setActive(id);
2187
+ setItems(emojiList);
2188
+ };
2189
+ const onClickItem = ({ emojiId, fileUrl }) => {
2190
+ if (menuState === "video") {
2191
+ createImage(fileUrl, emojiId);
2192
+ }
2193
+ };
2194
+ react.useEffect(() => {
2195
+ setMenus(videoMenus);
2196
+ if (videoMenus.length) {
2197
+ onClickClass(videoMenus[0]);
2198
+ }
2199
+ }, [videoMenus]);
2200
+ return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: `editor-video-menu ${menuState === "video" ? "active" : ""}`, children: [
2201
+ /* @__PURE__ */ jsxRuntime.jsx("div", { className: "editor-video-menu-header", children: menus.map((item) => /* @__PURE__ */ jsxRuntime.jsx("div", { className: active === item.id ? "active" : "", onClick: () => onClickClass(item), children: item.classifyType }, item.id)) }),
2202
+ /* @__PURE__ */ jsxRuntime.jsx("div", { className: "editor-video-menu-itmes", children: items.map((item) => /* @__PURE__ */ jsxRuntime.jsx("div", { onClick: () => onClickItem(item), children: /* @__PURE__ */ jsxRuntime.jsx("img", { loading: "lazy", src: item.fileUrl.thumbnailUrl, alt: "\u7D20\u6750" }) }, item.emojiId)) })
2203
+ ] });
2204
+ };
2205
+ var VideoMenu_default = VideoMenu;
2206
+ var historyClass = new HistoryClass();
2207
+ var EditorFn = ({
2208
+ vmml,
2209
+ pauseFrame = 0,
2210
+ maxText = 10,
2211
+ maxVideo = 5,
2212
+ videoMenus = [],
2213
+ onMenuChange,
2214
+ showTextButtons = false,
2215
+ editableArray = [],
2216
+ templateId,
2217
+ strategyId,
2218
+ pauseWhenBuffering = false
2219
+ }, ref) => {
2220
+ var _a;
2221
+ vmml = vmmlUtils.convertVmmlTextScaleByForbidden(vmml);
2222
+ const textMenuRef = react.useRef(null);
2223
+ const vmmlPlayerRef = react.useRef();
2224
+ const canvasRef = react.useRef();
2225
+ const fps = 30;
2226
+ const once = react.useRef(false);
2227
+ const [player, setPlayer] = react.useState();
2228
+ const [loading, setLoading] = react.useState(true);
2229
+ const [frame, setFrame] = react.useState(pauseFrame);
2230
+ const [isPlaying, setIsPlaying] = react.useState(false);
2231
+ const [showCanvas, setShowCanvas] = react.useState(false);
2232
+ const [durationInFrames, setDurationInFrames] = react.useState(vmmlUtils.getFrames(((_a = vmml == null ? void 0 : vmml.template) == null ? void 0 : _a.duration) || 1, fps));
2233
+ const [previewState, setPreviewState] = react.useState(true);
2234
+ const [menuState, setMenuState] = react.useState("");
2235
+ const [canvasSize, setCanvasSize] = react.useState({ width: 0, height: 0, top: 0 });
2236
+ const [textInfo, setTextInfo] = react.useState({});
2237
+ const [isShowMaxTextLayer, setIsShowMaxTextLayer] = react.useState(false);
2238
+ const [buffering, setBuffering] = react.useState(false);
2239
+ const videoList = react.useRef([]);
2240
+ const [signList, setSignList] = react.useState([]);
2241
+ const [tips, setTips] = react.useState("");
2242
+ const [dragState, setDragState] = react.useState(0);
2243
+ const vmmlConverterRef = react.useRef(null);
2244
+ const [initFcObjs, setInitFcObjs] = react.useState([]);
2245
+ const vmmlFlag = react.useRef(false);
2246
+ const needPlay = react.useRef(true);
2247
+ const setVmml = () => {
2248
+ const { current } = vmmlPlayerRef;
2249
+ if (!current) return;
2250
+ if (!once.current) {
2251
+ current.setVmml(vmml, pauseFrame);
2252
+ } else {
2253
+ current.setVmml(vmml, Math.max(0, frame - 3));
2254
+ }
2255
+ };
2256
+ const hideLoading = () => {
2257
+ const { current } = vmmlPlayerRef;
2258
+ vmmlFlag.current = false;
2259
+ if (current && current.playerRef) {
2260
+ setPlayer(current.playerRef);
2261
+ current.unmute();
2262
+ if (!once.current) {
2263
+ once.current = true;
2264
+ } else {
2265
+ if (needPlay.current) {
2266
+ current.play();
2267
+ } else {
2268
+ needPlay.current = true;
2269
+ }
2270
+ }
2271
+ }
2272
+ setShowCanvas(false);
2273
+ setLoading(false);
2274
+ };
2275
+ const onClickMain = () => {
2276
+ if (buffering) return;
2277
+ const { current } = vmmlPlayerRef;
2278
+ if (current) {
2279
+ if (isPlaying) {
2280
+ intoEdit();
2281
+ } else {
2282
+ current.unmute();
2283
+ current.play();
2284
+ }
2285
+ }
2286
+ };
2287
+ const enterPreview = (canvas, hiddenMenu = false) => {
2288
+ if (hiddenMenu) {
2289
+ setMenuState("");
2290
+ } else {
2291
+ setMenuState("");
2292
+ setPreviewState(true);
2293
+ historyClass.onCanvasRoute(canvas);
2294
+ }
2295
+ };
2296
+ const onControlsClick = () => {
2297
+ if (previewState) {
2298
+ const { current } = vmmlPlayerRef;
2299
+ current.unmute();
2300
+ current.play();
2301
+ } else {
2302
+ setMenuState("");
2303
+ setPreviewState(true);
2304
+ }
2305
+ };
2306
+ const onClickMenu = (type) => {
2307
+ if (type === "text" && checkTextNum()) return;
2308
+ if (type === "video" && checkVideoNum()) return;
2309
+ if (previewState) {
2310
+ intoEdit();
2311
+ }
2312
+ setTextInfo({});
2313
+ setMenuState(type);
2314
+ };
2315
+ const checkTextNum = () => {
2316
+ const { current } = canvasRef;
2317
+ if (current) {
2318
+ const textNums = current.getfObjectNums("\u6587\u5B57");
2319
+ if (textNums >= maxText) {
2320
+ setTips(`\u6700\u591A\u6DFB\u52A0${maxText}\u4E2A\u6587\u5B57`);
2321
+ setIsShowMaxTextLayer(true);
2322
+ return true;
2323
+ }
2324
+ }
2325
+ return false;
2326
+ };
2327
+ const checkVideoNum = () => {
2328
+ const { current } = canvasRef;
2329
+ if (current) {
2330
+ const videoNum = current.getfObjectNums("\u8868\u60C5\u5305");
2331
+ if (videoNum >= maxVideo) {
2332
+ setTips(`\u6700\u591A\u6DFB\u52A0${maxVideo}\u4E2A\u8868\u60C5\u5305`);
2333
+ setIsShowMaxTextLayer(true);
2334
+ return true;
2335
+ }
2336
+ }
2337
+ return false;
2338
+ };
2339
+ const getfcObject = () => {
2340
+ const { current } = canvasRef;
2341
+ if (current) {
2342
+ return current.getfcObject();
2343
+ }
2344
+ return [];
2345
+ };
2346
+ const intoEdit = (frame2) => {
2347
+ const { current } = vmmlPlayerRef;
2348
+ if (current) {
2349
+ frame2 && current.seekTo(frame2);
2350
+ current.pause();
2351
+ if (canvasRef.current) {
2352
+ const { current: canvasC } = canvasRef;
2353
+ canvasC.checkObjectInPoint(frame2);
2354
+ }
2355
+ getAllVideoFrames();
2356
+ setShowCanvas(true);
2357
+ setPreviewState(false);
2358
+ }
2359
+ };
2360
+ const getAllVideoFrames = () => {
2361
+ const { current } = canvasRef;
2362
+ const doms = document.querySelectorAll("[data-clipid][data-cliptype=video][data-editorType],[data-editclip='true'][data-cliptype=video]");
2363
+ for (const item of Array.from(doms)) {
2364
+ const id = item.getAttribute("data-clipid");
2365
+ const video = item.querySelector("video");
2366
+ const base64 = vmmlUtils.takeScreenshot(video);
2367
+ current.updateImage(id, base64);
2368
+ }
2369
+ switchClipDisplay("none");
2370
+ };
2371
+ const switchClipDisplay = (display) => {
2372
+ const clips = document.querySelectorAll("[data-editorType],[data-editclip='true']");
2373
+ clips.forEach((clip) => {
2374
+ clip.style.display = display;
2375
+ });
2376
+ };
2377
+ const createImage = async (file, emojiId) => {
2378
+ const { current } = canvasRef;
2379
+ if (current && !checkVideoNum()) {
2380
+ const fObj = await current.createImage(file, emojiId);
2381
+ vmmlConverterRef.current.addVideoClip(fObj);
2382
+ setMenuState("");
2383
+ setPreviewState(true);
2384
+ }
2385
+ };
2386
+ const createText = async (data) => {
2387
+ const { current } = canvasRef;
2388
+ if (current) {
2389
+ const server = data.id ? "updateText" : "createText";
2390
+ await current[server](data);
2391
+ setMenuState("");
2392
+ }
2393
+ };
2394
+ const onVideoChange = (clipData) => {
2395
+ const index = videoList.current.findIndex((item) => item.id === clipData.id);
2396
+ if (index > -1) {
2397
+ videoList.current.splice(index, 1);
2398
+ } else {
2399
+ videoList.current.push(clipData);
2400
+ }
2401
+ setSignList([...videoList.current]);
2402
+ };
2403
+ const getActions = () => {
2404
+ const { current } = canvasRef;
2405
+ return current.getActions().length;
2406
+ };
2407
+ const textClose = (id) => {
2408
+ const { current } = canvasRef;
2409
+ id && current.changeObjectVisible(id);
2410
+ setMenuState("");
2411
+ };
2412
+ const intoTextEdit = (textInfo2) => {
2413
+ setMenuState("text");
2414
+ setTextInfo(textInfo2);
2415
+ };
2416
+ const onFrameUpdate = (e) => {
2417
+ setFrame(e.detail.frame);
2418
+ };
2419
+ const onPlay = () => {
2420
+ setIsPlaying(true);
2421
+ };
2422
+ const onPause = () => {
2423
+ setIsPlaying(false);
2424
+ };
2425
+ const onWaiting = () => {
2426
+ setShowCanvas(false);
2427
+ setPreviewState(true);
2428
+ setBuffering(true);
2429
+ };
2430
+ const onResume = () => {
2431
+ setBuffering(false);
2432
+ };
2433
+ const initCanEditClips = (tracks = []) => {
2434
+ if (editableArray.length) {
2435
+ const list = findEditClips(tracks);
2436
+ if (list.length) {
2437
+ const { current } = canvasRef;
2438
+ list.forEach((clip) => {
2439
+ if (clip.videoClip) {
2440
+ current.createImageFromClip(clip);
2441
+ } else {
2442
+ current.createTextFromClip(clip);
2443
+ }
2444
+ });
2445
+ }
2446
+ }
2447
+ };
2448
+ const findEditClips = (tracks = []) => {
2449
+ const list = [];
2450
+ tracks.forEach((track) => {
2451
+ track.clips.forEach((clip) => {
2452
+ if (editableArray.includes(clip.id)) {
2453
+ clip.edit = true;
2454
+ list.push(clip);
2455
+ }
2456
+ });
2457
+ });
2458
+ return list;
2459
+ };
2460
+ const initFcObjects = (tracks = []) => {
2461
+ const fcTracks = tracks.filter((item) => item.editorType);
2462
+ if (fcTracks.length) {
2463
+ const clips = fcTracks.map((item) => item.clips).flat().filter((item) => Reflect.has(item, "fObj"));
2464
+ const fObjs = clips.map((item) => item.fObj);
2465
+ setInitFcObjs(fObjs);
2466
+ fObjs.forEach((item) => {
2467
+ onVideoChange(item.clipData);
2468
+ });
2469
+ }
2470
+ };
2471
+ const getVmml = () => {
2472
+ try {
2473
+ const tracks = vmml.template.tracks.filter((item) => item.editorType === "\u6587\u5B57");
2474
+ tracks.forEach((track) => {
2475
+ track.clips.forEach((clip) => {
2476
+ clip.fObj.src = "";
2477
+ });
2478
+ });
2479
+ } catch {
2480
+ console.log("\u51FA\u9519\u4E86");
2481
+ }
2482
+ return vmml;
2483
+ };
2484
+ const getPlayer = () => {
2485
+ return player;
2486
+ };
2487
+ react.useEffect(() => {
2488
+ if (onMenuChange && typeof onMenuChange === "function") {
2489
+ onMenuChange(menuState);
2490
+ }
2491
+ }, [menuState]);
2492
+ react.useEffect(() => {
2493
+ if (previewState && !vmmlFlag.current) {
2494
+ vmmlFlag.current = true;
2495
+ setVmml();
2496
+ }
2497
+ }, [previewState]);
2498
+ react.useEffect(() => {
2499
+ if (canvasSize.width && canvasSize.height && !vmmlConverterRef.current && vmml) {
2500
+ vmmlConverterRef.current = new VmmlConverter_default({ vmml, canvasSize });
2501
+ }
2502
+ if (canvasSize.width) {
2503
+ initCanEditClips(vmml.template.tracks);
2504
+ }
2505
+ }, [canvasSize, vmml]);
2506
+ react.useEffect(() => {
2507
+ if (vmml) {
2508
+ initFcObjects(vmml.template.tracks);
2509
+ }
2510
+ }, [vmml]);
2511
+ react.useEffect(() => {
2512
+ if (!showCanvas) {
2513
+ switchClipDisplay("block");
2514
+ }
2515
+ }, [showCanvas]);
2516
+ react.useEffect(() => {
2517
+ if (player) {
2518
+ const parent = player.getContainerNode();
2519
+ if (!canvasSize.width) {
2520
+ const playerElement = parent == null ? void 0 : parent.children[0];
2521
+ const { width, height } = (playerElement == null ? void 0 : playerElement.getBoundingClientRect()) || {};
2522
+ setCanvasSize({ width, height, top: playerElement.offsetTop });
2523
+ }
2524
+ player.addEventListener("play", onPlay);
2525
+ player.addEventListener("pause", onPause);
2526
+ player.addEventListener("frameupdate", onFrameUpdate);
2527
+ player.addEventListener("waiting", onWaiting);
2528
+ player.addEventListener("resume", onResume);
2529
+ return () => {
2530
+ player.removeEventListener("play", onPlay);
2531
+ player.removeEventListener("pause", onPause);
2532
+ player.removeEventListener("frameupdate", onFrameUpdate);
2533
+ player.removeEventListener("waiting", onWaiting);
2534
+ player.removeEventListener("resume", onResume);
2535
+ };
2536
+ }
2537
+ }, [player]);
2538
+ react.useEffect(() => {
2539
+ if (dragState === 2) {
2540
+ needPlay.current = false;
2541
+ const { current } = vmmlPlayerRef;
2542
+ current.setVmml(vmml, frame, false);
2543
+ setShowCanvas(false);
2544
+ }
2545
+ if (dragState === 3 || dragState === 4) {
2546
+ setShowCanvas(true);
2547
+ setPreviewState(false);
2548
+ }
2549
+ }, [dragState]);
2550
+ react.useImperativeHandle(
2551
+ ref,
2552
+ () => ({
2553
+ getActions,
2554
+ getfcObject,
2555
+ getVmml,
2556
+ getPlayer,
2557
+ texteditClose,
2558
+ textFinish
2559
+ }),
2560
+ [vmml, player]
2561
+ );
2562
+ const texteditClose = () => {
2563
+ if (textMenuRef) {
2564
+ textMenuRef.current.close();
2565
+ }
2566
+ };
2567
+ const textFinish = () => {
2568
+ if (textMenuRef) {
2569
+ textMenuRef.current.handleSubmit();
2570
+ }
2571
+ };
2572
+ const menuStyles = react.useMemo(() => {
2573
+ if (loading) {
2574
+ return {
2575
+ opacity: 0.4,
2576
+ pointerEvents: "none"
2577
+ };
2578
+ }
2579
+ return {};
2580
+ }, [loading]);
2581
+ return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
2582
+ /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "editor", children: [
2583
+ /* @__PURE__ */ jsxRuntime.jsx("div", { className: "editor-vessel", onClick: () => {
2584
+ setMenuState("");
2585
+ }, children: /* @__PURE__ */ jsxRuntime.jsxs("section", { className: `main ${menuState === "text" ? "text-style" : ""}`, children: [
2586
+ /* @__PURE__ */ jsxRuntime.jsx("div", { className: "vessel", onClick: onClickMain, children: /* @__PURE__ */ jsxRuntime.jsx(
2587
+ vmmlPlayer.VmmlPlayer,
2588
+ {
2589
+ ref: vmmlPlayerRef,
2590
+ vmml,
2591
+ existenceBorderRadio: true,
2592
+ moveToBeginningWhenEnded: true,
2593
+ isEditorState: true,
2594
+ muted: true,
2595
+ fps,
2596
+ hideLoading,
2597
+ editableArray,
2598
+ premountFor: 40,
2599
+ pauseWhenBuffering
2600
+ }
2601
+ ) }),
2602
+ /* @__PURE__ */ jsxRuntime.jsx(
2603
+ EditorCanvas_default,
2604
+ {
2605
+ ref: canvasRef,
2606
+ previewState,
2607
+ showCanvas,
2608
+ canvasSize,
2609
+ enterPreview,
2610
+ intoTextEdit,
2611
+ frame,
2612
+ vmml,
2613
+ dragState,
2614
+ initFcObjs,
2615
+ onVideoChange
2616
+ }
2617
+ ),
2618
+ /* @__PURE__ */ jsxRuntime.jsx("div", { className: "controls-box", children: /* @__PURE__ */ jsxRuntime.jsx(
2619
+ Controls_default,
2620
+ {
2621
+ player,
2622
+ vmmlRef: vmmlPlayerRef,
2623
+ fps,
2624
+ durationInFrames,
2625
+ intoEdit,
2626
+ frame,
2627
+ isPlaying,
2628
+ setDragState,
2629
+ onControlsClick,
2630
+ signList
2631
+ }
2632
+ ) }),
2633
+ /* @__PURE__ */ jsxRuntime.jsx(Loading_default, { show: loading })
2634
+ ] }) }),
2635
+ /* @__PURE__ */ jsxRuntime.jsx("div", { className: "padding-box" }),
2636
+ /* @__PURE__ */ jsxRuntime.jsxs("section", { style: menuStyles, className: `footer ${menuState === "text" ? "text-style" : ""}`, children: [
2637
+ maxText > 0 && /* @__PURE__ */ jsxRuntime.jsxs(
2638
+ "div",
2639
+ {
2640
+ onClick: () => onClickMenu("text"),
2641
+ "data-aspm-click": "c375146.d480849",
2642
+ "data-aspm-expo": true,
2643
+ "data-aspm-param": `Template_Id=${templateId}^Strategy_Id=${strategyId}`,
2644
+ children: [
2645
+ /* @__PURE__ */ jsxRuntime.jsx("img", { src: wordIcon, alt: "word" }),
2646
+ /* @__PURE__ */ jsxRuntime.jsx("p", { children: "\u6587\u5B57" })
2647
+ ]
2648
+ }
2649
+ ),
2650
+ maxVideo > 0 && /* @__PURE__ */ jsxRuntime.jsxs(
2651
+ "div",
2652
+ {
2653
+ onClick: () => onClickMenu("video"),
2654
+ "data-aspm-click": "c375146.d480850",
2655
+ "data-aspm-expo": true,
2656
+ "data-aspm-param": `Template_Id=${templateId}^Strategy_Id=${strategyId}`,
2657
+ children: [
2658
+ /* @__PURE__ */ jsxRuntime.jsx("img", { src: emotionIcon, alt: "emotion" }),
2659
+ /* @__PURE__ */ jsxRuntime.jsx("p", { children: "\u8868\u60C5\u5305" })
2660
+ ]
2661
+ }
2662
+ )
2663
+ ] }),
2664
+ maxVideo > 0 && /* @__PURE__ */ jsxRuntime.jsx(VideoMenu_default, { menuState, createImage, videoMenus }),
2665
+ menuState === "text" && /* @__PURE__ */ jsxRuntime.jsx(TextMenu_default, { ref: textMenuRef, createText, textClose, textInfo, showTextButtons })
2666
+ ] }),
2667
+ /* @__PURE__ */ jsxRuntime.jsx(MaxTextLayer_default, { textLayerHide: () => setIsShowMaxTextLayer(false), show: isShowMaxTextLayer, text: tips })
2668
+ ] });
2669
+ };
2670
+ var forward = react.forwardRef;
2671
+ var Editor = forward(EditorFn);
2672
+
2673
+ exports.Editor = Editor;
2674
+ //# sourceMappingURL=index.js.map
2675
+ //# sourceMappingURL=index.js.map