@next2d/display 1.17.4 → 1.18.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/TextField.js CHANGED
@@ -1,10 +1,10 @@
1
1
  import { InteractiveObject, Shape } from "@next2d/display";
2
- import { FocusEvent, Event as Next2DEvent, MouseEvent as Next2DMouseEvent } from "@next2d/events";
2
+ import { FocusEvent, Event as Next2DEvent } from "@next2d/events";
3
3
  import { Tween, Easing } from "@next2d/ui";
4
4
  import { TextFormat, parsePlainText, parseHtmlText } from "@next2d/text";
5
- import { Rectangle } from "@next2d/geom";
6
- import { $currentPlayer, $MOUSE_DOWN, $MOUSE_UP, $MOUSE_WHEEL, $PREFIX, $rendererWorker, $SCROLL, $TOUCH_END, $TOUCH_START, $document, $RegExp } from "@next2d/util";
7
- import { $cacheStore, $doUpdated, $clamp, $getArray, $intToRGBA, $isNaN, $Math, $requestAnimationFrame, $toColorInt, $poolFloat32Array6, $boundsMatrix, $multiplicationMatrix, $poolBoundsObject, $multiplicationColor, $Infinity, $Number, $poolArray, $poolFloat32Array8, $generateFontStyle, $devicePixelRatio, $getBoundsObject } from "@next2d/share";
5
+ import { Rectangle, Point } from "@next2d/geom";
6
+ import { $document, $rendererWorker, $getEventType, $TOUCH_MOVE, $MOUSE_MOVE, $textArea, $currentPlayer } from "@next2d/util";
7
+ import { $cacheStore, $doUpdated, $clamp, $getArray, $intToRGBA, $isNaN, $Math, $toColorInt, $poolFloat32Array6, $boundsMatrix, $multiplicationMatrix, $poolBoundsObject, $multiplicationColor, $Infinity, $Number, $poolArray, $poolFloat32Array8, $generateFontStyle, $getBoundsObject, $setTimeout, $clearTimeout } from "@next2d/share";
8
8
  /**
9
9
  * TextField クラスは、テキストの表示と入力用の表示オブジェクトを作成するために使用されます。
10
10
  * プロパティインスペクターを使用して、テキストフィールドにインスタンス名を付けることができます。
@@ -91,6 +91,24 @@ export class TextField extends InteractiveObject {
91
91
  * @private
92
92
  */
93
93
  this._$maxChars = 0;
94
+ /**
95
+ * @type {number}
96
+ * @default -1
97
+ * @private
98
+ */
99
+ this._$stopIndex = -1;
100
+ /**
101
+ * @type {number}
102
+ * @default -1
103
+ * @private
104
+ */
105
+ this._$compositionStartIndex = -1;
106
+ /**
107
+ * @type {number}
108
+ * @default -1
109
+ * @private
110
+ */
111
+ this._$compositionEndIndex = -1;
94
112
  // TextFormat
95
113
  const textFormat = new TextFormat();
96
114
  textFormat._$setDefault();
@@ -142,12 +160,6 @@ export class TextField extends InteractiveObject {
142
160
  * @private
143
161
  */
144
162
  this._$textData = null;
145
- /**
146
- * @type {HTMLTextAreaElement}
147
- * @default null
148
- * @private
149
- */
150
- this._$textarea = null;
151
163
  /**
152
164
  * @type {string}
153
165
  * @default TextFieldAutoSize.NONE
@@ -162,10 +174,28 @@ export class TextField extends InteractiveObject {
162
174
  this._$autoFontSize = false;
163
175
  /**
164
176
  * @type {boolean}
165
- * @default false
177
+ * @default true
178
+ * @private
179
+ */
180
+ this._$focusVisible = false;
181
+ /**
182
+ * @type {number}
183
+ * @default -1
184
+ * @private
185
+ */
186
+ this._$timerId = -1;
187
+ /**
188
+ * @type {number}
189
+ * @default -1
190
+ * @private
191
+ */
192
+ this._$focusIndex = -1;
193
+ /**
194
+ * @type {number}
195
+ * @default -1
166
196
  * @private
167
197
  */
168
- this._$textAreaActive = false;
198
+ this._$selectIndex = -1;
169
199
  /**
170
200
  * @type {boolean}
171
201
  * @default true
@@ -197,11 +227,11 @@ export class TextField extends InteractiveObject {
197
227
  */
198
228
  this._$focus = false;
199
229
  /**
200
- * @type {boolean}
201
- * @default false
230
+ * @type {string}
231
+ * @default ""
202
232
  * @private
203
233
  */
204
- this._$isComposing = false;
234
+ this._$copyText = "";
205
235
  /**
206
236
  * @type {number}
207
237
  * @default 0
@@ -215,11 +245,11 @@ export class TextField extends InteractiveObject {
215
245
  */
216
246
  this._$thicknessColor = 0;
217
247
  /**
218
- * @type {string}
219
- * @default "bottom"
248
+ * @type {array}
249
+ * @default null
220
250
  * @private
221
251
  */
222
- this._$verticalAlign = "bottom";
252
+ this._$textFormats = null;
223
253
  /**
224
254
  * @type {array}
225
255
  * @private
@@ -383,6 +413,87 @@ export class TextField extends InteractiveObject {
383
413
  this._$reset();
384
414
  }
385
415
  }
416
+ /**
417
+ * @description テキストの任意の表示終了位置の設定
418
+ * Setting an arbitrary display end position for text.
419
+ *
420
+ * @member {number}
421
+ * @default -1
422
+ * @public
423
+ */
424
+ get stopIndex() {
425
+ return this._$stopIndex;
426
+ }
427
+ set stopIndex(index) {
428
+ index |= 0;
429
+ if (this._$stopIndex === index) {
430
+ return;
431
+ }
432
+ this._$stopIndex = index;
433
+ const textData = this.getTextData();
434
+ if (!textData.textTable.length) {
435
+ return;
436
+ }
437
+ let currentTextWidth = 2;
438
+ let targetIndex = 0;
439
+ for (let idx = 0; idx < textData.textTable.length; ++idx) {
440
+ const textObject = textData.textTable[idx];
441
+ let countUp = false;
442
+ if (textObject.mode === "text") {
443
+ countUp = true;
444
+ currentTextWidth += textObject.w;
445
+ }
446
+ if (targetIndex >= index) {
447
+ targetIndex = idx;
448
+ break;
449
+ }
450
+ if (textObject.mode === "break") {
451
+ countUp = true;
452
+ // reset
453
+ this._$scrollX = 0;
454
+ currentTextWidth = 2;
455
+ }
456
+ if (countUp) {
457
+ targetIndex++;
458
+ }
459
+ }
460
+ const textObject = textData.textTable[targetIndex];
461
+ const line = textObject.line;
462
+ let currentTextHeight = 0;
463
+ for (let idx = 0; idx <= line; ++idx) {
464
+ currentTextHeight += textData.heightTable[idx];
465
+ }
466
+ const height = this.height;
467
+ let viewTextHeight = 0;
468
+ for (let idx = line; idx > -1; --idx) {
469
+ const lineHeight = textData.heightTable[idx];
470
+ if (height < viewTextHeight + lineHeight) {
471
+ break;
472
+ }
473
+ viewTextHeight += lineHeight;
474
+ }
475
+ if (currentTextHeight > height) {
476
+ const scaleY = (this.textHeight - height) / height;
477
+ this._$scrollY = $Math.min((currentTextHeight - viewTextHeight) / scaleY, height);
478
+ }
479
+ const width = this.width;
480
+ let viewTextWidth = 0;
481
+ for (let idx = targetIndex; idx > 0; --idx) {
482
+ const textObject = textData.textTable[idx];
483
+ if (textObject.mode !== "text") {
484
+ continue;
485
+ }
486
+ if (width < viewTextWidth + textObject.w) {
487
+ break;
488
+ }
489
+ viewTextWidth += textObject.w;
490
+ }
491
+ if (currentTextWidth > width) {
492
+ const scaleX = (this.textWidth - width) / width;
493
+ this._$scrollX = $Math.min((currentTextWidth - viewTextWidth) / scaleX, width + 0.5);
494
+ }
495
+ this._$doChanged();
496
+ }
386
497
  /**
387
498
  * @description テキストに適用するフォーマットを指定します。
388
499
  * Specifies the formatting to be applied to the text.
@@ -415,52 +526,26 @@ export class TextField extends InteractiveObject {
415
526
  if (this._$type !== "input") {
416
527
  return;
417
528
  }
418
- this._$focus = focus;
529
+ this._$focus = !!focus;
530
+ const name = this._$focus
531
+ ? FocusEvent.FOCUS_IN
532
+ : FocusEvent.FOCUS_OUT;
533
+ if (this.willTrigger(name)) {
534
+ this.dispatchEvent(new FocusEvent(name));
535
+ }
536
+ $textArea.value = "";
419
537
  if (this._$focus) {
420
- const player = $currentPlayer();
421
- const div = $document
422
- .getElementById(player.contentElementId);
423
- if (!div) {
424
- return;
425
- }
426
- this._$createTextAreaElement(player._$scale);
427
- // setup
428
- const element = this._$textarea;
429
- if (!element) {
430
- return;
431
- }
432
- const matrix = this._$transform.concatenatedMatrix;
433
- const bounds = this._$getBounds(null);
434
- const color = $intToRGBA($toColorInt(this._$defaultTextFormat.color), 100);
435
- element.style.color = `rgb(${color.R},${color.G},${color.B})`;
436
- element.style.left = `${(matrix.tx + bounds.xMin + player.x / player._$scale / $devicePixelRatio) * player._$scale}px`;
437
- element.style.top = `${(matrix.ty + bounds.yMin + player.y / player._$scale / $devicePixelRatio) * player._$scale}px`;
438
- element.style.width = `${$Math.ceil(this.width * player._$scale)}px`;
439
- element.style.height = `${$Math.ceil(this.height * player._$scale)}px`;
440
- // set text
441
- element.value = this.text;
442
- div.appendChild(element);
443
- $requestAnimationFrame(() => {
444
- element.focus();
445
- });
446
- this._$doChanged();
447
- $doUpdated();
448
- this._$textAreaActive = true;
449
- // focus in event
450
- if (this.willTrigger(FocusEvent.FOCUS_IN)) {
451
- this.dispatchEvent(new FocusEvent(FocusEvent.FOCUS_IN));
452
- }
538
+ $textArea.focus();
453
539
  }
454
540
  else {
455
- // execute
456
- if (this._$textarea) {
457
- this._$textarea.dispatchEvent(new Event(`${$PREFIX}_blur`));
458
- if (this.willTrigger(FocusEvent.FOCUS_OUT)) {
459
- this.dispatchEvent(new FocusEvent(FocusEvent.FOCUS_OUT));
460
- }
461
- this._$textarea.remove();
462
- }
541
+ this._$focusIndex = -1;
542
+ this._$selectIndex = -1;
543
+ this._$focusVisible = false;
544
+ $clearTimeout(this._$timerId);
545
+ $textArea.blur();
463
546
  }
547
+ this._$doChanged();
548
+ $doUpdated();
464
549
  }
465
550
  /**
466
551
  * @description テキストフィールドの内容を HTML で表します。
@@ -471,7 +556,44 @@ export class TextField extends InteractiveObject {
471
556
  * @public
472
557
  */
473
558
  get htmlText() {
474
- return this._$htmlText;
559
+ if (this._$htmlText) {
560
+ return this._$htmlText;
561
+ }
562
+ const textData = this.getTextData();
563
+ let prevTextFormat = textData.textTable[0].textFormat;
564
+ let htmlText = "<span";
565
+ const style = prevTextFormat._$toStyleString();
566
+ if (style) {
567
+ htmlText += ` style="${style}"`;
568
+ }
569
+ htmlText += ">";
570
+ for (let idx = 1; idx < textData.textTable.length; ++idx) {
571
+ const textObject = textData.textTable[idx];
572
+ if (textObject.mode === "wrap") {
573
+ continue;
574
+ }
575
+ if (textObject.mode === "break") {
576
+ htmlText += "<br>";
577
+ continue;
578
+ }
579
+ const textFormat = textObject.textFormat;
580
+ if (!prevTextFormat._$isSame(textFormat)) {
581
+ htmlText += "</span><span";
582
+ const style = textFormat._$toStyleString();
583
+ if (style) {
584
+ htmlText += ` style="${style}"`;
585
+ }
586
+ htmlText += ">";
587
+ // change
588
+ prevTextFormat = textFormat;
589
+ }
590
+ if (textObject.mode === "text") {
591
+ htmlText += textObject.text;
592
+ }
593
+ }
594
+ htmlText += "</span>";
595
+ this._$htmlText = htmlText;
596
+ return htmlText;
475
597
  }
476
598
  set htmlText(html_text) {
477
599
  if (this._$htmlText !== html_text) {
@@ -564,6 +686,17 @@ export class TextField extends InteractiveObject {
564
686
  set scrollEnabled(scroll_enabled) {
565
687
  this._$scrollEnabled = scroll_enabled;
566
688
  }
689
+ /**
690
+ * @description テキストの選択位置を返す
691
+ * Returns the text selection position
692
+ *
693
+ * @member {number}
694
+ * @readonly
695
+ * @public
696
+ */
697
+ get selectIndex() {
698
+ return this._$selectIndex;
699
+ }
567
700
  /**
568
701
  * @description テキストフィールドのスクロール垂直位置です。
569
702
  * The scroll vertical position of the text field.
@@ -584,7 +717,7 @@ export class TextField extends InteractiveObject {
584
717
  && this._$yScrollShape.hasLocalVariable("job")) {
585
718
  return;
586
719
  }
587
- scroll_x = $clamp(scroll_x, 0, this.width, 0);
720
+ scroll_x = $clamp(scroll_x, 0, this.width + 0.5, 0);
588
721
  if (this._$scrollX !== scroll_x) {
589
722
  const width = this.width;
590
723
  if (this._$xScrollShape && this.textWidth > width) {
@@ -593,8 +726,12 @@ export class TextField extends InteractiveObject {
593
726
  this._$xScrollShape.width = width * width / this.textWidth;
594
727
  const parent = this._$parent;
595
728
  if (parent) {
729
+ // start animation
730
+ if (this._$xScrollShape.hasLocalVariable("job")) {
731
+ this._$xScrollShape.getLocalVariable("job").stop();
732
+ }
596
733
  // view start
597
- Tween.add(this._$xScrollShape, { "alpha": 0 }, { "alpha": 0.8 }, 0, 0.3, Easing.outQuad);
734
+ this._$xScrollShape.alpha = 0.9;
598
735
  // set position
599
736
  this._$xScrollShape.x = this.x + 1
600
737
  + (width - 1 - this._$xScrollShape.width)
@@ -603,11 +740,7 @@ export class TextField extends InteractiveObject {
603
740
  this._$xScrollShape.y = this.y + this.height - this._$xScrollShape.height - 0.5;
604
741
  // added sprite
605
742
  parent.addChildAt(this._$xScrollShape, parent.getChildIndex(this) + 1);
606
- // start animation
607
- if (this._$xScrollShape.hasLocalVariable("job")) {
608
- this._$xScrollShape.getLocalVariable("job").stop();
609
- }
610
- const job = Tween.add(this._$xScrollShape, { "alpha": 0.8 }, { "alpha": 0 }, 0.2, 0.6, Easing.outQuad);
743
+ const job = Tween.add(this._$xScrollShape, { "alpha": 0.9 }, { "alpha": 0 }, 0.5, 0.2, Easing.outQuad);
611
744
  job.addEventListener(Next2DEvent.COMPLETE, (event) => {
612
745
  const shape = event.target.target;
613
746
  shape.deleteLocalVariable("job");
@@ -654,8 +787,12 @@ export class TextField extends InteractiveObject {
654
787
  this._$yScrollShape.height = height * height / this.textHeight;
655
788
  const parent = this._$parent;
656
789
  if (parent) {
790
+ // start animation
791
+ if (this._$yScrollShape.hasLocalVariable("job")) {
792
+ this._$yScrollShape.getLocalVariable("job").stop();
793
+ }
657
794
  // view start
658
- Tween.add(this._$yScrollShape, { "alpha": 0 }, { "alpha": 0.8 }, 0, 0.3, Easing.outQuad);
795
+ this._$yScrollShape.alpha = 0.9;
659
796
  // set position
660
797
  this._$yScrollShape.x = this.x + this.width - this._$yScrollShape.width - 0.5;
661
798
  this._$yScrollShape.y = this.y + 0.5
@@ -664,11 +801,7 @@ export class TextField extends InteractiveObject {
664
801
  * (this._$scrollY - 1);
665
802
  // added sprite
666
803
  parent.addChildAt(this._$yScrollShape, parent.getChildIndex(this) + 1);
667
- // start animation
668
- if (this._$yScrollShape.hasLocalVariable("job")) {
669
- this._$yScrollShape.getLocalVariable("job").stop();
670
- }
671
- const job = Tween.add(this._$yScrollShape, { "alpha": 0.8 }, { "alpha": 0 }, 0.2, 0.6, Easing.outQuad);
804
+ const job = Tween.add(this._$yScrollShape, { "alpha": 0.9 }, { "alpha": 0 }, 0.5, 0.2, Easing.outQuad);
672
805
  job.addEventListener(Next2DEvent.COMPLETE, (event) => {
673
806
  const shape = event.target.target;
674
807
  shape.deleteLocalVariable("job");
@@ -703,14 +836,16 @@ export class TextField extends InteractiveObject {
703
836
  let text = "";
704
837
  const textData = this.getTextData();
705
838
  for (let idx = 1; idx < textData.textTable.length; ++idx) {
706
- const object = textData.textTable[idx];
707
- switch (object.mode) {
839
+ const textObject = textData.textTable[idx];
840
+ switch (textObject.mode) {
708
841
  case "text":
709
- text += object.text;
842
+ text += textObject.text;
710
843
  break;
711
844
  case "break":
712
845
  text += "\r";
713
846
  break;
847
+ default:
848
+ continue;
714
849
  }
715
850
  }
716
851
  this._$rawHtmlText = text;
@@ -718,12 +853,18 @@ export class TextField extends InteractiveObject {
718
853
  }
719
854
  set text(text) {
720
855
  if (text === null) {
721
- text = "";
856
+ this._$text = "";
857
+ this._$htmlText = "";
858
+ this._$rawHtmlText = "";
859
+ this._$isHTML = false;
860
+ this._$reload();
861
+ return;
722
862
  }
723
863
  text = `${text}`;
724
864
  if (text !== this._$text) {
725
865
  this._$text = text;
726
866
  this._$htmlText = "";
867
+ this._$rawHtmlText = "";
727
868
  this._$isHTML = false;
728
869
  this._$reload();
729
870
  }
@@ -813,26 +954,6 @@ export class TextField extends InteractiveObject {
813
954
  }
814
955
  set type(type) {
815
956
  this._$type = type;
816
- if (type === "static") {
817
- this._$textarea = null;
818
- }
819
- }
820
- /**
821
- * @description 縦方向の揃え位置を指定するプロパティです。
822
- * This property specifies the vertical alignment position.
823
- *
824
- * @member {string}
825
- * @default "bottom"
826
- * @public
827
- */
828
- get verticalAlign() {
829
- return this._$verticalAlign;
830
- }
831
- set verticalAlign(vertical_align) {
832
- if (vertical_align !== this._$verticalAlign) {
833
- this._$verticalAlign = vertical_align;
834
- this._$reset();
835
- }
836
957
  }
837
958
  /**
838
959
  * @description テキストフィールドのテキストを折り返すかどうかを示すブール値です。
@@ -1027,7 +1148,8 @@ export class TextField extends InteractiveObject {
1027
1148
  "width": this.width,
1028
1149
  "multiline": this._$multiline,
1029
1150
  "wordWrap": this._$wordWrap,
1030
- "subFontSize": sub_font_size
1151
+ "subFontSize": sub_font_size,
1152
+ "textFormats": this._$textFormats
1031
1153
  });
1032
1154
  }
1033
1155
  else {
@@ -1035,7 +1157,8 @@ export class TextField extends InteractiveObject {
1035
1157
  "width": this.width,
1036
1158
  "multiline": this._$multiline,
1037
1159
  "wordWrap": this._$wordWrap,
1038
- "subFontSize": sub_font_size
1160
+ "subFontSize": sub_font_size,
1161
+ "textFormats": this._$textFormats
1039
1162
  });
1040
1163
  }
1041
1164
  return this._$textData;
@@ -1043,121 +1166,865 @@ export class TextField extends InteractiveObject {
1043
1166
  /**
1044
1167
  * @return {void}
1045
1168
  * @method
1046
- * @private
1169
+ * @public
1047
1170
  */
1048
- _$reset() {
1049
- this._$textData = null;
1050
- this._$doChanged();
1051
- $doUpdated();
1052
- // cache clear
1053
- $cacheStore.removeCache(this._$instanceId);
1171
+ selectAll() {
1172
+ const textData = this.getTextData();
1173
+ if (!textData.textTable.length) {
1174
+ return;
1175
+ }
1176
+ this._$selectIndex = 1;
1177
+ this._$focusIndex = textData.textTable.length;
1054
1178
  }
1055
1179
  /**
1056
1180
  * @return {void}
1057
1181
  * @method
1058
- * @private
1182
+ * @public
1059
1183
  */
1060
- _$reload() {
1061
- this._$reset();
1062
- this.getTextData();
1063
- if (this._$autoSize === "none" && this._$autoFontSize) {
1064
- let maxFontSize = 0;
1065
- const textData = this.getTextData();
1066
- for (let idx = 0; idx < textData.textTable.length; ++idx) {
1067
- const textObject = textData.textTable[idx];
1068
- maxFontSize = $Math.max(maxFontSize, textObject.textFormat.size || 0);
1069
- }
1070
- let subSize = 1;
1071
- if (this.width && this.textWidth) {
1072
- while (maxFontSize > subSize
1073
- && this.textWidth + 4 > this.width) {
1074
- this._$reset();
1075
- this.getTextData(subSize++);
1076
- }
1184
+ copy() {
1185
+ if (this._$focusIndex === -1 || this._$selectIndex === -1) {
1186
+ return;
1187
+ }
1188
+ let text = "";
1189
+ const minIndex = $Math.min(this._$focusIndex, this._$selectIndex);
1190
+ const maxIndex = $Math.max(this._$focusIndex, this._$selectIndex) + 1;
1191
+ const textData = this.getTextData();
1192
+ for (let idx = minIndex; idx < maxIndex; ++idx) {
1193
+ const textObject = textData.textTable[idx];
1194
+ if (!textObject || textObject.mode === "wrap") {
1195
+ continue;
1077
1196
  }
1078
- if (this.height && this.textHeight) {
1079
- while (maxFontSize > subSize
1080
- && this.textHeight + 4 > this.height) {
1081
- this._$reset();
1082
- this.getTextData(subSize++);
1083
- }
1197
+ switch (textObject.mode) {
1198
+ case "text":
1199
+ text += textObject.text;
1200
+ break;
1201
+ case "break":
1202
+ text += "\n";
1203
+ break;
1084
1204
  }
1085
1205
  }
1086
- this._$resize();
1206
+ this._$copyText = text;
1087
1207
  }
1088
1208
  /**
1089
1209
  * @return {void}
1090
1210
  * @method
1091
- * @private
1211
+ * @public
1092
1212
  */
1093
- _$resize() {
1094
- // update bounds
1095
- if (this._$autoSize !== "none") {
1096
- const tf = this._$defaultTextFormat;
1097
- const width = this.textWidth + 4 + tf._$widthMargin();
1098
- if (this._$wordWrap) {
1099
- this._$bounds.xMax = this._$originBounds.xMax;
1100
- this._$bounds.xMin = this._$originBounds.xMin;
1101
- }
1102
- else {
1103
- switch (this._$autoSize) {
1104
- case "left":
1105
- this._$bounds.xMax = width + this._$bounds.xMin;
1106
- break;
1107
- case "center":
1108
- this._$bounds.xMax = width + this._$bounds.xMin;
1109
- break;
1110
- case "right":
1111
- this._$bounds.xMax = this._$originBounds.xMax
1112
- - (this._$originBounds.xMax - this._$originBounds.xMin
1113
- - (width - this._$originBounds.xMin));
1114
- break;
1115
- default:
1116
- break;
1117
- }
1118
- }
1119
- // set height
1120
- this._$bounds.yMax = this.textHeight + this._$originBounds.yMin;
1121
- }
1122
- else {
1123
- if (this._$scrollEnabled) {
1124
- if (!this._$xScrollShape) {
1125
- this._$xScrollShape = new Shape();
1126
- this
1127
- ._$xScrollShape
1128
- .graphics
1129
- .beginFill("#000", 0.3)
1130
- .drawRoundRect(0, 0, 3, 3, 3);
1131
- this
1132
- ._$xScrollShape
1133
- .scale9Grid = new Rectangle(1.5, 1.5, 0.1, 0.1);
1134
- }
1135
- if (!this._$yScrollShape) {
1136
- this._$yScrollShape = new Shape();
1137
- this
1138
- ._$yScrollShape
1139
- .graphics
1140
- .beginFill("#000", 0.3)
1141
- .drawRoundRect(0, 0, 3, 3, 3);
1142
- this
1143
- ._$yScrollShape
1144
- .scale9Grid = new Rectangle(1.5, 1.5, 0.1, 0.1);
1145
- }
1146
- }
1213
+ paste() {
1214
+ if (!this._$copyText || this._$focusIndex === -1) {
1215
+ return;
1147
1216
  }
1217
+ this.insertText(this._$copyText);
1148
1218
  }
1149
1219
  /**
1150
- * @param {object} text_object
1151
- * @param {number} width
1152
- * @return {number}
1220
+ * @return {void}
1153
1221
  * @method
1154
- * @private
1222
+ * @public
1155
1223
  */
1156
- _$getAlignOffset(text_object, width) {
1157
- // default
1158
- const lineWidth = this
1159
- .getTextData()
1160
- .getLineWidth(text_object.line);
1224
+ arrowUp() {
1225
+ if (this._$focusIndex === -1) {
1226
+ return;
1227
+ }
1228
+ const textData = this.getTextData();
1229
+ if (!textData.textTable.length) {
1230
+ return;
1231
+ }
1232
+ const index = textData.textTable.length === this._$focusIndex
1233
+ ? this._$focusIndex - 1
1234
+ : this._$focusIndex;
1235
+ const textObject = textData.textTable[index];
1236
+ if (!textObject.line) {
1237
+ return;
1238
+ }
1239
+ const line = textObject.mode === "text"
1240
+ ? textObject.line
1241
+ : textObject.line - 1;
1242
+ let currentWidth = 2;
1243
+ for (let idx = 1; idx < textData.textTable.length; ++idx) {
1244
+ const textObject = textData.textTable[idx];
1245
+ if (this._$focusIndex === idx) {
1246
+ if (textObject.mode === "text") {
1247
+ currentWidth += textObject.w / 2;
1248
+ }
1249
+ break;
1250
+ }
1251
+ if (textObject.line > line) {
1252
+ break;
1253
+ }
1254
+ if (textObject.line !== line || textObject.mode !== "text") {
1255
+ continue;
1256
+ }
1257
+ currentWidth += textObject.w;
1258
+ }
1259
+ let textWidth = 2;
1260
+ const targetLine = line - 1;
1261
+ for (let idx = 1; idx < textData.textTable.length; ++idx) {
1262
+ const textObject = textData.textTable[idx];
1263
+ if (textObject.line > targetLine) {
1264
+ this._$focusIndex = textObject.mode === "text" ? idx - 1 : idx;
1265
+ this._$selectIndex = -1;
1266
+ $clearTimeout(this._$timerId);
1267
+ this._$blinking();
1268
+ return;
1269
+ }
1270
+ if (textObject.line !== targetLine || textObject.mode !== "text") {
1271
+ continue;
1272
+ }
1273
+ textWidth += textObject.w;
1274
+ if (textWidth > currentWidth) {
1275
+ this._$focusIndex = idx;
1276
+ this._$selectIndex = -1;
1277
+ $clearTimeout(this._$timerId);
1278
+ this._$blinking();
1279
+ return;
1280
+ }
1281
+ }
1282
+ }
1283
+ /**
1284
+ * @return {void}
1285
+ * @method
1286
+ * @public
1287
+ */
1288
+ arrowDown() {
1289
+ if (this._$focusIndex === -1) {
1290
+ return;
1291
+ }
1292
+ const textData = this.getTextData();
1293
+ if (!textData.textTable.length) {
1294
+ return;
1295
+ }
1296
+ const textObject = textData.textTable[this._$focusIndex];
1297
+ const line = textObject.mode === "text"
1298
+ ? textObject.line
1299
+ : textObject.line - 1;
1300
+ if (line === textData.lineTable.length - 1) {
1301
+ return;
1302
+ }
1303
+ let currentWidth = 2;
1304
+ for (let idx = 1; idx < textData.textTable.length; ++idx) {
1305
+ const textObject = textData.textTable[idx];
1306
+ if (this._$focusIndex === idx) {
1307
+ if (textObject.mode === "text") {
1308
+ currentWidth += textObject.w / 2;
1309
+ }
1310
+ break;
1311
+ }
1312
+ if (textObject.line > line) {
1313
+ break;
1314
+ }
1315
+ if (textObject.line !== line || textObject.mode !== "text") {
1316
+ continue;
1317
+ }
1318
+ currentWidth += textObject.w;
1319
+ }
1320
+ let textWidth = 2;
1321
+ const targetLine = line + 1;
1322
+ for (let idx = 1; idx < textData.textTable.length; ++idx) {
1323
+ const textObject = textData.textTable[idx];
1324
+ if (textObject.line > targetLine) {
1325
+ this._$focusIndex = textObject.mode === "text" ? idx - 1 : idx;
1326
+ this._$selectIndex = -1;
1327
+ $clearTimeout(this._$timerId);
1328
+ this._$blinking();
1329
+ return;
1330
+ }
1331
+ if (textObject.line !== targetLine || textObject.mode !== "text") {
1332
+ continue;
1333
+ }
1334
+ textWidth += textObject.w;
1335
+ if (textWidth > currentWidth) {
1336
+ this._$focusIndex = idx;
1337
+ this._$selectIndex = -1;
1338
+ $clearTimeout(this._$timerId);
1339
+ this._$blinking();
1340
+ return;
1341
+ }
1342
+ }
1343
+ this._$focusIndex = textData.textTable.length;
1344
+ this._$selectIndex = -1;
1345
+ $clearTimeout(this._$timerId);
1346
+ this._$blinking();
1347
+ }
1348
+ /**
1349
+ * @return {void}
1350
+ * @method
1351
+ * @public
1352
+ */
1353
+ arrowLeft() {
1354
+ if (!this._$focusIndex) {
1355
+ return;
1356
+ }
1357
+ const textData = this.getTextData();
1358
+ if (textData.textTable.length && this._$focusIndex < 2) {
1359
+ this._$focusIndex = 1;
1360
+ return;
1361
+ }
1362
+ this._$focusIndex--;
1363
+ this._$selectIndex = -1;
1364
+ $clearTimeout(this._$timerId);
1365
+ this._$blinking();
1366
+ }
1367
+ /**
1368
+ * @return {void}
1369
+ * @method
1370
+ * @public
1371
+ */
1372
+ arrowRight() {
1373
+ const textData = this.getTextData();
1374
+ if (textData.textTable.length === this._$focusIndex) {
1375
+ return;
1376
+ }
1377
+ this._$focusIndex++;
1378
+ this._$selectIndex = -1;
1379
+ $clearTimeout(this._$timerId);
1380
+ this._$blinking();
1381
+ }
1382
+ /**
1383
+ * @return {void}
1384
+ * @method
1385
+ * @public
1386
+ */
1387
+ deleteText() {
1388
+ if (this._$compositionStartIndex > -1) {
1389
+ return;
1390
+ }
1391
+ let minIndex = 0;
1392
+ let maxIndex = 0;
1393
+ if (this._$selectIndex > -1) {
1394
+ minIndex = $Math.min(this._$focusIndex, this._$selectIndex);
1395
+ maxIndex = $Math.max(this._$focusIndex, this._$selectIndex) + 1;
1396
+ this._$focusIndex = minIndex;
1397
+ }
1398
+ else {
1399
+ if (2 > this._$focusIndex) {
1400
+ return;
1401
+ }
1402
+ this._$focusIndex--;
1403
+ }
1404
+ const textData = this.getTextData();
1405
+ const textObject = textData.textTable[this._$focusIndex];
1406
+ if (textObject && textObject.mode === "wrap") {
1407
+ this._$focusIndex--;
1408
+ }
1409
+ const textFormats = $getArray();
1410
+ let newText = "";
1411
+ for (let idx = 1; idx < textData.textTable.length; ++idx) {
1412
+ const textObject = textData.textTable[idx];
1413
+ if (this._$focusIndex === idx || minIndex <= idx && maxIndex > idx) {
1414
+ continue;
1415
+ }
1416
+ switch (textObject.mode) {
1417
+ case "break":
1418
+ textFormats.push(textObject.textFormat);
1419
+ newText += "\n";
1420
+ break;
1421
+ case "text":
1422
+ textFormats.push(textObject.textFormat);
1423
+ newText += textObject.text;
1424
+ break;
1425
+ default:
1426
+ continue;
1427
+ }
1428
+ }
1429
+ if (textData.textTable.length === this._$focusIndex) {
1430
+ textFormats.pop();
1431
+ newText = newText.slice(0, -1);
1432
+ }
1433
+ this._$selectIndex = -1;
1434
+ if (!newText) {
1435
+ // reset
1436
+ this.text = null;
1437
+ this._$scrollX = 0;
1438
+ this._$scrollY = 0;
1439
+ this._$focusIndex = 0;
1440
+ }
1441
+ else {
1442
+ const beforeTextWidth = this.textWidth;
1443
+ const beforeTextHeight = this.textHeight;
1444
+ this._$textFormats = textFormats;
1445
+ this.text = newText;
1446
+ if (this._$scrollX > 0) {
1447
+ const textWidth = this.textWidth;
1448
+ const width = this.width;
1449
+ switch (true) {
1450
+ case width > textWidth:
1451
+ this._$scrollY = 0;
1452
+ break;
1453
+ case beforeTextWidth !== textWidth:
1454
+ this._$scrollY -= (beforeTextWidth - textWidth)
1455
+ / (textWidth / width);
1456
+ break;
1457
+ default:
1458
+ break;
1459
+ }
1460
+ }
1461
+ if (this._$scrollY > 0) {
1462
+ const textHeight = this.textHeight;
1463
+ const height = this.height;
1464
+ switch (true) {
1465
+ case height > textHeight:
1466
+ this._$scrollY = 0;
1467
+ break;
1468
+ case beforeTextHeight !== textHeight:
1469
+ this._$scrollY -= (beforeTextHeight - textHeight)
1470
+ / (textHeight / height);
1471
+ break;
1472
+ default:
1473
+ break;
1474
+ }
1475
+ }
1476
+ // reset
1477
+ this._$textFormats = null;
1478
+ $poolArray(textFormats);
1479
+ }
1480
+ }
1481
+ /**
1482
+ * @return {void}
1483
+ * @method
1484
+ * @public
1485
+ */
1486
+ compositionStart() {
1487
+ this._$compositionStartIndex = this._$focusIndex;
1488
+ }
1489
+ /**
1490
+ * @param {string} texts
1491
+ * @return {void}
1492
+ * @method
1493
+ * @public
1494
+ */
1495
+ compositionUpdate(texts) {
1496
+ if (this._$compositionEndIndex > -1) {
1497
+ const cacheIndex = this._$compositionStartIndex;
1498
+ this._$focusIndex = this._$compositionStartIndex;
1499
+ this._$selectIndex = this._$compositionEndIndex - 1;
1500
+ this._$compositionStartIndex = -1;
1501
+ this.deleteText();
1502
+ // reset
1503
+ this._$compositionStartIndex = cacheIndex;
1504
+ this._$selectIndex = -1;
1505
+ }
1506
+ let textData = this.getTextData();
1507
+ const textFormats = $getArray();
1508
+ const length = texts.length;
1509
+ let newText = "";
1510
+ if (!textData.textTable.length) {
1511
+ newText = texts;
1512
+ this._$focusIndex = 1;
1513
+ this._$compositionStartIndex = 1;
1514
+ }
1515
+ else {
1516
+ for (let idx = 1; idx < textData.textTable.length; ++idx) {
1517
+ const textObject = textData.textTable[idx];
1518
+ if (this._$compositionStartIndex === idx) {
1519
+ for (let idx = 0; idx < length; ++idx) {
1520
+ textFormats.push(textObject.textFormat._$clone());
1521
+ newText += texts[idx];
1522
+ }
1523
+ }
1524
+ switch (textObject.mode) {
1525
+ case "break":
1526
+ textFormats.push(textObject.textFormat);
1527
+ newText += "\n";
1528
+ break;
1529
+ case "text":
1530
+ textFormats.push(textObject.textFormat);
1531
+ newText += textObject.text;
1532
+ break;
1533
+ default:
1534
+ continue;
1535
+ }
1536
+ }
1537
+ // last text
1538
+ if (this._$compositionStartIndex === textData.textTable.length) {
1539
+ const textObject = textData.textTable[this._$compositionStartIndex - 1];
1540
+ for (let idx = 0; idx < length; ++idx) {
1541
+ textFormats.push(textObject.textFormat._$clone());
1542
+ newText += texts[idx];
1543
+ }
1544
+ }
1545
+ }
1546
+ // update
1547
+ if (textFormats.length) {
1548
+ this._$textFormats = textFormats;
1549
+ }
1550
+ this.text = newText;
1551
+ // reset
1552
+ this._$textFormats = null;
1553
+ $poolArray(textFormats);
1554
+ textData = this.getTextData();
1555
+ let index = this._$compositionStartIndex + length;
1556
+ for (let idx = this._$compositionStartIndex; idx < index; ++idx) {
1557
+ const textObject = textData.textTable[idx];
1558
+ if (!textObject) {
1559
+ break;
1560
+ }
1561
+ textObject.textFormat.underline = true;
1562
+ if (textObject.mode === "wrap") {
1563
+ if (idx === this._$compositionStartIndex) {
1564
+ let subIndex = 1;
1565
+ for (;;) {
1566
+ const textObject = textData.textTable[idx - subIndex];
1567
+ if (!textObject) {
1568
+ break;
1569
+ }
1570
+ if (textObject.mode === "text") {
1571
+ textObject.textFormat.underline = true;
1572
+ break;
1573
+ }
1574
+ subIndex++;
1575
+ }
1576
+ }
1577
+ if (idx > this._$compositionStartIndex) {
1578
+ index++;
1579
+ }
1580
+ }
1581
+ }
1582
+ this._$compositionEndIndex = this._$focusIndex = index;
1583
+ // move textarea element
1584
+ const player = $currentPlayer();
1585
+ const lastIndex = $Math.min(textData.textTable.length - 1, this._$compositionEndIndex);
1586
+ const textObject = textData.textTable[lastIndex];
1587
+ if (textObject) {
1588
+ const line = textObject.line;
1589
+ let offsetHeight = 0;
1590
+ for (let idx = 0; idx < line; ++idx) {
1591
+ offsetHeight += textData.heightTable[idx];
1592
+ }
1593
+ const verticalAlign = textData.ascentTable[line];
1594
+ let offsetWidth = 0;
1595
+ let targetIndex = this._$compositionEndIndex;
1596
+ for (;;) {
1597
+ const textObject = textData.textTable[targetIndex--];
1598
+ if (!textObject || textObject.line !== line) {
1599
+ break;
1600
+ }
1601
+ offsetWidth += textObject.w;
1602
+ }
1603
+ const lineObject = textData.lineTable[line];
1604
+ const offsetAlign = this._$getAlignOffset(lineObject, this.width);
1605
+ const point = this.localToGlobal(new Point(offsetWidth + offsetAlign, offsetHeight + verticalAlign));
1606
+ const div = $document
1607
+ .getElementById(player.contentElementId);
1608
+ let left = point.x * player._$scale;
1609
+ let top = point.y * player._$scale;
1610
+ if (div) {
1611
+ const rect = div.getBoundingClientRect();
1612
+ left += rect.left;
1613
+ top += rect.top;
1614
+ }
1615
+ $textArea.style.left = `${left}px`;
1616
+ $textArea.style.top = `${top}px`;
1617
+ }
1618
+ }
1619
+ /**
1620
+ * @return {void}
1621
+ * @method
1622
+ * @public
1623
+ */
1624
+ compositionEnd() {
1625
+ if (this._$compositionEndIndex > -1) {
1626
+ const textData = this.getTextData();
1627
+ for (let idx = this._$compositionStartIndex; idx < this._$compositionEndIndex; ++idx) {
1628
+ const textObject = textData.textTable[idx];
1629
+ textObject.textFormat.underline = false;
1630
+ }
1631
+ this._$focusIndex = this._$compositionEndIndex;
1632
+ }
1633
+ $textArea.blur();
1634
+ $textArea.value = "";
1635
+ if (this._$focus) {
1636
+ $textArea.focus();
1637
+ }
1638
+ this._$selectIndex = -1;
1639
+ this._$compositionStartIndex = -1;
1640
+ this._$compositionEndIndex = -1;
1641
+ }
1642
+ /**
1643
+ * @param {string} text
1644
+ * @return {void}
1645
+ * @method
1646
+ * @public
1647
+ */
1648
+ insertText(texts) {
1649
+ if (this._$focusIndex === -1
1650
+ || this._$compositionStartIndex > -1) {
1651
+ return;
1652
+ }
1653
+ if (this._$selectIndex > -1) {
1654
+ this.deleteText();
1655
+ }
1656
+ const textData = this.getTextData();
1657
+ const textFormats = $getArray();
1658
+ let newText = "";
1659
+ for (let idx = 1; idx < textData.textTable.length; ++idx) {
1660
+ const textObject = textData.textTable[idx];
1661
+ if (this._$focusIndex === idx) {
1662
+ for (let idx = 0; idx < texts.length; ++idx) {
1663
+ textFormats.push(textObject.textFormat);
1664
+ newText += texts[idx];
1665
+ }
1666
+ }
1667
+ switch (textObject.mode) {
1668
+ case "break":
1669
+ textFormats.push(textObject.textFormat);
1670
+ newText += "\n";
1671
+ break;
1672
+ case "text":
1673
+ textFormats.push(textObject.textFormat);
1674
+ newText += textObject.text;
1675
+ break;
1676
+ default:
1677
+ continue;
1678
+ }
1679
+ }
1680
+ if (textData.textTable.length === this._$focusIndex) {
1681
+ let textFormat;
1682
+ if (textData.textTable.length) {
1683
+ const textObject = textData.textTable[textData.textTable.length - 1];
1684
+ textFormat = textObject.textFormat._$clone();
1685
+ }
1686
+ else {
1687
+ textFormat = this.defaultTextFormat;
1688
+ this._$focusIndex++;
1689
+ }
1690
+ for (let idx = 0; idx < texts.length; ++idx) {
1691
+ textFormats.push(textFormat._$clone());
1692
+ newText += texts[idx];
1693
+ }
1694
+ }
1695
+ // update
1696
+ this._$textFormats = textFormats;
1697
+ this.text = newText;
1698
+ // reset
1699
+ this._$textFormats = null;
1700
+ $poolArray(textFormats);
1701
+ this._$focusIndex += texts.length;
1702
+ this._$selectIndex = -1;
1703
+ $textArea.value = "";
1704
+ }
1705
+ /**
1706
+ * @return {void}
1707
+ * @method
1708
+ * @private
1709
+ */
1710
+ _$reset() {
1711
+ this._$textData = null;
1712
+ this._$doChanged();
1713
+ $doUpdated();
1714
+ // cache clear
1715
+ $cacheStore.removeCache(this._$instanceId);
1716
+ }
1717
+ /**
1718
+ * @return {void}
1719
+ * @method
1720
+ * @private
1721
+ */
1722
+ _$reload() {
1723
+ this._$reset();
1724
+ this.getTextData();
1725
+ if (this._$autoSize === "none" && this._$autoFontSize) {
1726
+ let maxFontSize = 0;
1727
+ const textData = this.getTextData();
1728
+ for (let idx = 0; idx < textData.textTable.length; ++idx) {
1729
+ const textObject = textData.textTable[idx];
1730
+ maxFontSize = $Math.max(maxFontSize, textObject.textFormat.size || 0);
1731
+ }
1732
+ let subSize = 1;
1733
+ if (this.width && this.textWidth) {
1734
+ while (maxFontSize > subSize
1735
+ && this.textWidth + 4 > this.width) {
1736
+ this._$reset();
1737
+ this.getTextData(subSize++);
1738
+ }
1739
+ }
1740
+ if (this.height && this.textHeight) {
1741
+ while (maxFontSize > subSize
1742
+ && this.textHeight + 4 > this.height) {
1743
+ this._$reset();
1744
+ this.getTextData(subSize++);
1745
+ }
1746
+ }
1747
+ }
1748
+ this._$resize();
1749
+ }
1750
+ /**
1751
+ * @return {void}
1752
+ * @method
1753
+ * @private
1754
+ */
1755
+ _$blinking() {
1756
+ this._$focusVisible = !this._$focusVisible;
1757
+ this._$doChanged();
1758
+ $doUpdated();
1759
+ this._$timerId = +$setTimeout(() => {
1760
+ this._$blinking();
1761
+ }, 500);
1762
+ this._$timerId |= 0;
1763
+ }
1764
+ /**
1765
+ * @param {number} stage_x
1766
+ * @param {number} stage_y
1767
+ * @return {void}
1768
+ * @method
1769
+ * @private
1770
+ */
1771
+ _$setIndex(stage_x, stage_y) {
1772
+ if (this._$type !== "input") {
1773
+ return;
1774
+ }
1775
+ const textData = this.getTextData();
1776
+ if (!textData.textTable.length) {
1777
+ this._$focusIndex = 0;
1778
+ this._$selectIndex = -1;
1779
+ this.setBlinkingTimer();
1780
+ return;
1781
+ }
1782
+ const width = this.width;
1783
+ const height = this.height;
1784
+ let tx = 0;
1785
+ if (this._$scrollX > 0) {
1786
+ tx += this._$scrollX * (this.textWidth - width) / width;
1787
+ }
1788
+ let ty = 0;
1789
+ if (this._$scrollY) {
1790
+ ty += this._$scrollY * (this.textHeight - height) / height;
1791
+ }
1792
+ const eventType = $getEventType();
1793
+ const point = this.globalToLocal(new Point(stage_x, stage_y));
1794
+ const x = point.x + tx;
1795
+ const y = point.y + ty;
1796
+ let w = 2;
1797
+ let yMin = 2;
1798
+ let yMax = yMin + textData.heightTable[0];
1799
+ for (let idx = 1; idx < textData.textTable.length; ++idx) {
1800
+ const textObject = textData.textTable[idx];
1801
+ switch (textObject.mode) {
1802
+ case "break":
1803
+ case "wrap":
1804
+ if (x > w && y > yMin
1805
+ && yMax > y
1806
+ && width > x) {
1807
+ const index = idx;
1808
+ switch (eventType) {
1809
+ case $TOUCH_MOVE:
1810
+ case $MOUSE_MOVE:
1811
+ if (this._$selectIndex !== index && this._$focusIndex === index) {
1812
+ this._$selectIndex = index;
1813
+ if (this._$focusIndex !== index) {
1814
+ this._$focusVisible = false;
1815
+ $clearTimeout(this._$timerId);
1816
+ this._$doChanged();
1817
+ $doUpdated();
1818
+ }
1819
+ }
1820
+ break;
1821
+ default:
1822
+ if (this._$focusIndex !== index || this._$selectIndex > -1) {
1823
+ this._$focusIndex = index;
1824
+ this._$selectIndex = -1;
1825
+ this.setBlinkingTimer();
1826
+ }
1827
+ break;
1828
+ }
1829
+ return;
1830
+ }
1831
+ w = 2;
1832
+ yMin += textData.heightTable[textObject.line - 1];
1833
+ yMax = yMin + textData.heightTable[textObject.line];
1834
+ break;
1835
+ case "text":
1836
+ if (idx === textData.textTable.length - 1
1837
+ && x > w && y > yMin && yMax > y
1838
+ && width > x) {
1839
+ const index = textData.textTable.length;
1840
+ switch (eventType) {
1841
+ case $TOUCH_MOVE:
1842
+ case $MOUSE_MOVE:
1843
+ if (this._$selectIndex !== index) {
1844
+ this._$selectIndex = index;
1845
+ if (this._$focusIndex !== index) {
1846
+ this._$focusVisible = false;
1847
+ $clearTimeout(this._$timerId);
1848
+ this._$doChanged();
1849
+ $doUpdated();
1850
+ }
1851
+ }
1852
+ break;
1853
+ default:
1854
+ if (this._$focusIndex !== index || this._$selectIndex > -1) {
1855
+ this._$focusIndex = index;
1856
+ this._$selectIndex = -1;
1857
+ this.setBlinkingTimer();
1858
+ }
1859
+ break;
1860
+ }
1861
+ return;
1862
+ }
1863
+ if (x > w && y > yMin
1864
+ && yMax > y
1865
+ && w + textObject.w > x) {
1866
+ let index = idx;
1867
+ switch (eventType) {
1868
+ case $TOUCH_MOVE:
1869
+ case $MOUSE_MOVE:
1870
+ if (this._$focusIndex > index) { // left
1871
+ if (this._$focusIndex === index + 1) {
1872
+ if (w + textObject.w / 2 < x) {
1873
+ index = -1;
1874
+ }
1875
+ }
1876
+ else {
1877
+ if (w + textObject.w / 2 < x) {
1878
+ index += 1;
1879
+ }
1880
+ }
1881
+ }
1882
+ else { // right
1883
+ if (this._$focusIndex === index) {
1884
+ if (w + textObject.w / 2 > x) {
1885
+ index = -1;
1886
+ }
1887
+ }
1888
+ else {
1889
+ if (w + textObject.w / 2 > x) {
1890
+ index -= 1;
1891
+ }
1892
+ }
1893
+ }
1894
+ if (this._$selectIndex !== index) {
1895
+ this._$selectIndex = index;
1896
+ if (this._$selectIndex > -1) {
1897
+ this._$focusVisible = false;
1898
+ $clearTimeout(this._$timerId);
1899
+ }
1900
+ this._$doChanged();
1901
+ $doUpdated();
1902
+ }
1903
+ break;
1904
+ default:
1905
+ if (w + textObject.w / 2 < x) {
1906
+ const textObject = textData.textTable[index + 1];
1907
+ if (!textObject || textObject.mode === "text") {
1908
+ index += 1;
1909
+ }
1910
+ }
1911
+ if (this._$focusIndex !== index || this._$selectIndex > -1) {
1912
+ this._$focusIndex = index;
1913
+ this._$selectIndex = -1;
1914
+ this.setBlinkingTimer();
1915
+ }
1916
+ break;
1917
+ }
1918
+ return;
1919
+ }
1920
+ w += textObject.w;
1921
+ break;
1922
+ default:
1923
+ break;
1924
+ }
1925
+ }
1926
+ switch (eventType) {
1927
+ case $TOUCH_MOVE:
1928
+ case $MOUSE_MOVE:
1929
+ // reset
1930
+ this._$focusIndex = -1;
1931
+ this._$selectIndex = -1;
1932
+ break;
1933
+ default:
1934
+ this._$focusIndex = textData.textTable.length;
1935
+ this._$selectIndex = -1;
1936
+ this.setBlinkingTimer();
1937
+ break;
1938
+ }
1939
+ }
1940
+ /**
1941
+ * @return {void}
1942
+ * @method
1943
+ * @private
1944
+ */
1945
+ setBlinkingTimer() {
1946
+ this._$focusVisible = false;
1947
+ this._$doChanged();
1948
+ $doUpdated();
1949
+ $clearTimeout(this._$timerId);
1950
+ this._$timerId = +$setTimeout(() => {
1951
+ this._$blinking();
1952
+ }, 500);
1953
+ this._$timerId |= 0;
1954
+ }
1955
+ /**
1956
+ * @return {void}
1957
+ * @method
1958
+ * @private
1959
+ */
1960
+ _$resize() {
1961
+ // update bounds
1962
+ if (this._$autoSize !== "none") {
1963
+ const tf = this._$defaultTextFormat;
1964
+ const width = this.textWidth + 4 + tf._$widthMargin();
1965
+ if (this._$wordWrap) {
1966
+ this._$bounds.xMax = this._$originBounds.xMax;
1967
+ this._$bounds.xMin = this._$originBounds.xMin;
1968
+ }
1969
+ else {
1970
+ switch (this._$autoSize) {
1971
+ case "left":
1972
+ this._$bounds.xMax = width + this._$bounds.xMin;
1973
+ break;
1974
+ case "center":
1975
+ this._$bounds.xMax = width + this._$bounds.xMin;
1976
+ break;
1977
+ case "right":
1978
+ this._$bounds.xMax = this._$originBounds.xMax
1979
+ - (this._$originBounds.xMax - this._$originBounds.xMin
1980
+ - (width - this._$originBounds.xMin));
1981
+ break;
1982
+ default:
1983
+ break;
1984
+ }
1985
+ }
1986
+ // set height
1987
+ this._$bounds.yMax = this.textHeight + this._$originBounds.yMin;
1988
+ }
1989
+ else {
1990
+ if (this._$scrollEnabled) {
1991
+ if (!this._$xScrollShape) {
1992
+ this._$xScrollShape = new Shape();
1993
+ this
1994
+ ._$xScrollShape
1995
+ .graphics
1996
+ .beginFill("#000", 0.3)
1997
+ .drawRoundRect(0, 0, 3, 3, 3);
1998
+ this
1999
+ ._$xScrollShape
2000
+ .scale9Grid = new Rectangle(1.5, 1.5, 0.1, 0.1);
2001
+ }
2002
+ if (!this._$yScrollShape) {
2003
+ this._$yScrollShape = new Shape();
2004
+ this
2005
+ ._$yScrollShape
2006
+ .graphics
2007
+ .beginFill("#000", 0.3)
2008
+ .drawRoundRect(0, 0, 3, 3, 3);
2009
+ this
2010
+ ._$yScrollShape
2011
+ .scale9Grid = new Rectangle(1.5, 1.5, 0.1, 0.1);
2012
+ }
2013
+ }
2014
+ }
2015
+ }
2016
+ /**
2017
+ * @param {object} text_object
2018
+ * @param {number} width
2019
+ * @return {number}
2020
+ * @method
2021
+ * @private
2022
+ */
2023
+ _$getAlignOffset(text_object, width) {
2024
+ // default
2025
+ const lineWidth = this
2026
+ .getTextData()
2027
+ .getLineWidth(text_object.line);
1161
2028
  const textFormat = text_object.textFormat;
1162
2029
  const leftMargin = textFormat.leftMargin || 0;
1163
2030
  if (!this._$wordWrap && lineWidth > width) {
@@ -1326,10 +2193,13 @@ export class TextField extends InteractiveObject {
1326
2193
  * @private
1327
2194
  */
1328
2195
  _$draw(context, matrix, color_transform) {
1329
- if (!this._$visible || this._$textAreaActive) {
2196
+ if (!this._$visible) {
1330
2197
  return;
1331
2198
  }
1332
- if (!this._$background && !this._$border && !this.text) {
2199
+ if (this._$focusIndex === -1
2200
+ && !this._$background
2201
+ && !this._$border
2202
+ && !this.text) {
1333
2203
  return;
1334
2204
  }
1335
2205
  let multiColor = color_transform;
@@ -1483,16 +2353,16 @@ export class TextField extends InteractiveObject {
1483
2353
  ctx.lineTo(2, height - 2);
1484
2354
  ctx.lineTo(2, 2);
1485
2355
  ctx.clip();
1486
- let ty = 2;
1487
- if (this._$scrollY > 0) {
1488
- const scaleY = (this.textHeight - this.height) / this.height;
1489
- ty += -this._$scrollY * scaleY;
1490
- }
1491
2356
  let tx = 2;
1492
2357
  if (this._$scrollX > 0) {
1493
2358
  const scaleX = (this.textWidth - this.width) / this.width;
1494
2359
  tx += -this._$scrollX * scaleX;
1495
2360
  }
2361
+ let ty = 2;
2362
+ if (this._$scrollY > 0) {
2363
+ const scaleY = (this.textHeight - this.height) / this.height;
2364
+ ty += -this._$scrollY * scaleY;
2365
+ }
1496
2366
  ctx.setTransform(xScale, 0, 0, yScale, tx * xScale, ty * yScale);
1497
2367
  ctx.beginPath();
1498
2368
  this._$doDraw(ctx, multiColor, width / xScale, lineWidth);
@@ -1569,6 +2439,69 @@ export class TextField extends InteractiveObject {
1569
2439
  _$doDraw(context, color_transform, width, line_width) {
1570
2440
  // init
1571
2441
  const textData = this.getTextData();
2442
+ if (!textData.textTable.length
2443
+ && this._$focusIndex > -1
2444
+ && this._$focusVisible) {
2445
+ const textFormat = this._$defaultTextFormat;
2446
+ const rgb = $intToRGBA(textFormat.color || 0);
2447
+ const alpha = $Math.max(0, $Math.min(rgb.A * 255 + color_transform[7], 255)) / 255;
2448
+ context.strokeStyle = `rgba(${rgb.R},${rgb.G},${rgb.B},${alpha})`;
2449
+ context.beginPath();
2450
+ context.moveTo(0, 0);
2451
+ context.lineTo(0, 0 + (textFormat.size || 12));
2452
+ context.stroke();
2453
+ return;
2454
+ }
2455
+ if (this._$selectIndex > -1 && this._$focusIndex > -1) {
2456
+ const range = textData.textTable.length - 1;
2457
+ let minIndex = 0;
2458
+ let maxIndex = 0;
2459
+ if (this._$focusIndex <= this._$selectIndex) {
2460
+ minIndex = $Math.min(this._$focusIndex, range);
2461
+ maxIndex = $Math.min(this._$selectIndex, range);
2462
+ }
2463
+ else {
2464
+ minIndex = $Math.min(this._$selectIndex, range);
2465
+ maxIndex = $Math.min(this._$focusIndex - 1, range);
2466
+ }
2467
+ const textObject = textData.textTable[minIndex];
2468
+ const lineObject = textData.lineTable[textObject.line];
2469
+ const offsetAlign = this._$getAlignOffset(lineObject, width);
2470
+ let x = 0;
2471
+ if (minIndex && textObject.mode === "text") {
2472
+ let idx = minIndex;
2473
+ while (idx) {
2474
+ const textObject = textData.textTable[--idx];
2475
+ if (textObject.mode !== "text") {
2476
+ break;
2477
+ }
2478
+ x += textObject.w;
2479
+ }
2480
+ }
2481
+ context.fillStyle = "#b4d7ff";
2482
+ let w = 0;
2483
+ for (let idx = minIndex; idx <= maxIndex; ++idx) {
2484
+ const textObject = textData.textTable[idx];
2485
+ if (textObject.mode === "text") {
2486
+ w += textObject.w;
2487
+ if (idx !== maxIndex) {
2488
+ continue;
2489
+ }
2490
+ }
2491
+ let y = 0;
2492
+ const line = textObject.mode === "text"
2493
+ ? textObject.line
2494
+ : textObject.line - 1;
2495
+ for (let idx = 0; idx < line; ++idx) {
2496
+ y += textData.heightTable[idx];
2497
+ }
2498
+ context.beginPath();
2499
+ context.rect(x, y, w + offsetAlign, textData.heightTable[line]);
2500
+ context.fill();
2501
+ x = 0;
2502
+ w = 0;
2503
+ }
2504
+ }
1572
2505
  const tw = this.width;
1573
2506
  let scrollX = 0;
1574
2507
  if (this._$scrollX > 0) {
@@ -1589,8 +2522,15 @@ export class TextField extends InteractiveObject {
1589
2522
  let offsetAlign = 0;
1590
2523
  let verticalAlign = 0;
1591
2524
  let skip = false;
2525
+ let currentIndex = -1;
1592
2526
  for (let idx = 0; idx < textData.textTable.length; ++idx) {
1593
2527
  const textObject = textData.textTable[idx];
2528
+ if (textObject.mode === "text" || textObject.mode === "break") {
2529
+ currentIndex++;
2530
+ if (this._$stopIndex > -1 && currentIndex > this._$stopIndex) {
2531
+ break;
2532
+ }
2533
+ }
1594
2534
  if (skip && textObject.mode === "text") {
1595
2535
  continue;
1596
2536
  }
@@ -1612,6 +2552,34 @@ export class TextField extends InteractiveObject {
1612
2552
  const rgb = $intToRGBA(textFormat.color || 0);
1613
2553
  const alpha = $Math.max(0, $Math.min(rgb.A * 255 + color_transform[7], 255)) / 255;
1614
2554
  context.fillStyle = `rgba(${rgb.R},${rgb.G},${rgb.B},${alpha})`;
2555
+ // focus line
2556
+ if (this._$focusVisible && this._$focusIndex === idx) {
2557
+ const x = offsetWidth + offsetAlign + 0.1;
2558
+ let line = textObject.line;
2559
+ let h = textObject.y;
2560
+ let y = textData.ascentTable[line];
2561
+ if (textObject.mode !== "text") {
2562
+ h = textObject.mode === "break"
2563
+ ? textObject.h
2564
+ : textData.ascentTable[line - 1];
2565
+ if (line > 0 && !textData.ascentTable[line - 1]) {
2566
+ line = textObject.line;
2567
+ y = textData.ascentTable[line - 1];
2568
+ }
2569
+ else {
2570
+ line = textObject.line - 1;
2571
+ y = textData.ascentTable[line];
2572
+ }
2573
+ }
2574
+ for (let idx = 0; idx < line; ++idx) {
2575
+ y += textData.heightTable[idx];
2576
+ }
2577
+ context.strokeStyle = `rgba(${rgb.R},${rgb.G},${rgb.B},${alpha})`;
2578
+ context.beginPath();
2579
+ context.moveTo(x, y);
2580
+ context.lineTo(x, y - h);
2581
+ context.stroke();
2582
+ }
1615
2583
  if (this._$thickness) {
1616
2584
  const rgb = $intToRGBA(this._$thicknessColor);
1617
2585
  const alpha = $Math.max(0, $Math.min(rgb.A * 255 + color_transform[7], 255)) / 255;
@@ -1625,7 +2593,7 @@ export class TextField extends InteractiveObject {
1625
2593
  // reset width
1626
2594
  offsetWidth = 0;
1627
2595
  if (line) {
1628
- offsetHeight += textData.heightTable[line - 1] + 1;
2596
+ offsetHeight += textData.heightTable[line - 1];
1629
2597
  }
1630
2598
  if (scrollY > offsetHeight + textData.heightTable[line]) {
1631
2599
  skip = true;
@@ -1647,8 +2615,8 @@ export class TextField extends InteractiveObject {
1647
2615
  context.lineWidth = line_width;
1648
2616
  context.strokeStyle = `rgba(${rgb.R},${rgb.G},${rgb.B},${alpha})`;
1649
2617
  context.beginPath();
1650
- context.moveTo(x, y + 1);
1651
- context.lineTo(x + textObject.w, y + 1);
2618
+ context.moveTo(x, y + 2);
2619
+ context.lineTo(x + textObject.w, y + 2);
1652
2620
  context.stroke();
1653
2621
  }
1654
2622
  if (this._$thickness) {
@@ -1670,6 +2638,26 @@ export class TextField extends InteractiveObject {
1670
2638
  // break;
1671
2639
  }
1672
2640
  }
2641
+ if (this._$focusVisible && this._$focusIndex >= textData.textTable.length) {
2642
+ const textObject = textData.textTable[this._$focusIndex - 1];
2643
+ if (textObject) {
2644
+ const rgb = $intToRGBA(textObject.textFormat.color || 0);
2645
+ const alpha = $Math.max(0, $Math.min(rgb.A * 255 + color_transform[7], 255)) / 255;
2646
+ context.strokeStyle = `rgba(${rgb.R},${rgb.G},${rgb.B},${alpha})`;
2647
+ const x = offsetWidth + offsetAlign + 0.1;
2648
+ const y = offsetHeight + verticalAlign;
2649
+ context.beginPath();
2650
+ if (textObject.mode === "text") {
2651
+ context.moveTo(x, y - textObject.y);
2652
+ context.lineTo(x, y);
2653
+ }
2654
+ else {
2655
+ context.moveTo(x, y + textObject.h);
2656
+ context.lineTo(x, y);
2657
+ }
2658
+ context.stroke();
2659
+ }
2660
+ }
1673
2661
  }
1674
2662
  /**
1675
2663
  * @param {CanvasRenderingContext2D} context
@@ -1723,215 +2711,6 @@ export class TextField extends InteractiveObject {
1723
2711
  }
1724
2712
  return context.isPointInPath(options.x, options.y);
1725
2713
  }
1726
- /**
1727
- * @param {number} scale
1728
- * @return {void}
1729
- * @method
1730
- * @private
1731
- */
1732
- _$createTextAreaElement(scale) {
1733
- // new text area
1734
- if (!this._$textarea) {
1735
- this._$textarea = $document.createElement("textarea");
1736
- this._$textarea.value = this.text;
1737
- this._$textarea.id = `${$PREFIX}_TextField_${this._$instanceId}`;
1738
- if (!this._$wordWrap) {
1739
- this._$textarea.wrap = "off";
1740
- }
1741
- const textFormat = this._$defaultTextFormat;
1742
- // setup
1743
- let style = "";
1744
- style += "position: absolute;";
1745
- style += "outline: 0;";
1746
- style += `padding: 2px 2px 2px ${$Math.max(3, textFormat.leftMargin || 0)}px;`;
1747
- style += "margin: 0;";
1748
- style += "appearance: none;";
1749
- style += "resize: none;";
1750
- style += "overflow: hidden;";
1751
- style += `z-index: ${0x7fffffff};`;
1752
- style += "vertical-align: top;";
1753
- this._$textarea.setAttribute("style", style);
1754
- // add blur event
1755
- this._$textarea.addEventListener(`${$PREFIX}_blur`, (event) => {
1756
- // set new text
1757
- const element = event.target;
1758
- let value = element.value;
1759
- if (value && this._$restrict) {
1760
- let pattern = this._$restrict;
1761
- if (pattern[0] !== "[") {
1762
- pattern = "[" + pattern;
1763
- }
1764
- if (pattern[pattern.length - 1] !== "]") {
1765
- pattern += "]";
1766
- }
1767
- const found = value.match(new $RegExp(pattern, "gm"));
1768
- value = found ? found.join("") : "";
1769
- }
1770
- const player = $currentPlayer();
1771
- const div = $document.getElementById(player.contentElementId);
1772
- if (div) {
1773
- const element = $document.getElementById(`${$PREFIX}_TextField_${this._$instanceId}`);
1774
- if (element) {
1775
- element.remove();
1776
- }
1777
- }
1778
- this.text = value;
1779
- this._$focus = false;
1780
- this._$textAreaActive = false;
1781
- this._$doChanged();
1782
- $doUpdated();
1783
- });
1784
- // input event
1785
- this._$textarea.addEventListener("input", (event) => {
1786
- // set new text
1787
- const element = event.target;
1788
- const player = $currentPlayer();
1789
- let value = element.value;
1790
- // SafariではInputEvent.isComposingがundefined
1791
- if (this._$restrict && !this._$isComposing && value) {
1792
- let pattern = this._$restrict;
1793
- if (pattern[0] !== "[") {
1794
- pattern = "[" + pattern;
1795
- }
1796
- if (pattern[pattern.length - 1] !== "]") {
1797
- pattern += "]";
1798
- }
1799
- const found = value.match(new $RegExp(pattern, "gm"));
1800
- value = found ? found.join("") : "";
1801
- }
1802
- if (!this._$isComposing && this.text !== value) {
1803
- // update
1804
- this.text = value;
1805
- element.value = value;
1806
- if (this.willTrigger(Next2DEvent.CHANGE)) {
1807
- this.dispatchEvent(new Next2DEvent(Next2DEvent.CHANGE, true));
1808
- }
1809
- // setup
1810
- // const element = this._$textarea;
1811
- const matrix = this._$transform.concatenatedMatrix;
1812
- const bounds = this._$getBounds(null);
1813
- element.style.left = `${$Math.floor((matrix.tx + bounds.xMin + player.x / player._$scale / $devicePixelRatio) * player._$scale)}px`;
1814
- element.style.top = `${$Math.floor((matrix.ty + bounds.yMin + player.y / player._$scale / $devicePixelRatio) * player._$scale)}px`;
1815
- element.style.width = `${$Math.ceil((this.width - 1) * player._$scale)}px`;
1816
- element.style.height = `${$Math.ceil((this.height - 1) * player._$scale)}px`;
1817
- }
1818
- });
1819
- // IME入力開始時のevent
1820
- this._$textarea.addEventListener("compositionstart", () => {
1821
- this._$isComposing = true;
1822
- });
1823
- // IME入力確定時のevent
1824
- this._$textarea.addEventListener("compositionend", (event) => {
1825
- this._$isComposing = false;
1826
- const element = event.target;
1827
- let value = element.value;
1828
- if (!this._$restrict || !value) {
1829
- return;
1830
- }
1831
- let pattern = this._$restrict;
1832
- if (pattern[0] !== "[") {
1833
- pattern = "[" + pattern;
1834
- }
1835
- if (pattern[pattern.length - 1] !== "]") {
1836
- pattern += "]";
1837
- }
1838
- const found = value.match(new $RegExp(pattern, "gm"));
1839
- value = found ? found.join("") : "";
1840
- // update
1841
- this.text = value;
1842
- element.value = value;
1843
- });
1844
- // add click event
1845
- this._$textarea.addEventListener("click", () => {
1846
- if (this.willTrigger(Next2DMouseEvent.CLICK)) {
1847
- this.dispatchEvent(new Next2DMouseEvent(Next2DMouseEvent.CLICK));
1848
- }
1849
- });
1850
- // add mousewheel event
1851
- this._$textarea.addEventListener($MOUSE_WHEEL, (event) => {
1852
- this.scrollY += event.deltaY;
1853
- });
1854
- // add scroll event
1855
- this._$textarea.addEventListener($SCROLL, (event) => {
1856
- const element = event.target;
1857
- this.scrollY = element.scrollTop;
1858
- });
1859
- // down event
1860
- this._$textarea.addEventListener($TOUCH_START, () => {
1861
- const player = $currentPlayer();
1862
- player._$state = "down";
1863
- });
1864
- // up event
1865
- this._$textarea.addEventListener($TOUCH_END, () => {
1866
- const player = $currentPlayer();
1867
- player._$state = "up";
1868
- });
1869
- // down event
1870
- this._$textarea.addEventListener($MOUSE_DOWN, () => {
1871
- const player = $currentPlayer();
1872
- player._$state = "down";
1873
- });
1874
- // up event
1875
- this._$textarea.addEventListener($MOUSE_UP, () => {
1876
- const player = $currentPlayer();
1877
- player._$state = "up";
1878
- });
1879
- }
1880
- // change style
1881
- const tf = this._$defaultTextFormat;
1882
- const fontSize = tf.size
1883
- ? $Math.ceil(tf.size * scale * this._$transform.concatenatedMatrix.d)
1884
- : 0;
1885
- this._$textarea.style.fontSize = `${fontSize}px`;
1886
- this._$textarea.style.fontFamily = tf.font || "Times New Roman";
1887
- this._$textarea.style.lineHeight = `${(fontSize + $Math.max(0, tf.leading || 0)) / fontSize}em`;
1888
- if (this._$autoSize !== "none") {
1889
- this._$textarea.style.textAlign = "center";
1890
- }
1891
- else {
1892
- this._$textarea.style.textAlign = tf.align || "none";
1893
- }
1894
- this._$textarea.addEventListener("keydown", (event) => {
1895
- const element = event.target;
1896
- let value = element.value;
1897
- // SafariではInputEvent.isComposingがundefined
1898
- if (this._$restrict && !this._$isComposing && value) {
1899
- let pattern = this._$restrict;
1900
- if (pattern[0] !== "[") {
1901
- pattern = "[" + pattern;
1902
- }
1903
- if (pattern[pattern.length - 1] !== "]") {
1904
- pattern += "]";
1905
- }
1906
- const found = value.match(new $RegExp(pattern, "gm"));
1907
- value = found ? found.join("") : "";
1908
- }
1909
- // update
1910
- if (!this._$isComposing) {
1911
- this.text = value;
1912
- element.value = value;
1913
- }
1914
- // enter off
1915
- if (event.code === "Enter" && !this._$multiline) {
1916
- return false;
1917
- }
1918
- });
1919
- const style = this._$textarea.style;
1920
- if (this._$border) {
1921
- style.border = `solid 1px #${this.borderColor.toString(16)}`;
1922
- }
1923
- else {
1924
- style.border = "none";
1925
- }
1926
- if (this._$border || this._$background) {
1927
- style.backgroundColor = `#${this.backgroundColor.toString(16)}`;
1928
- }
1929
- else {
1930
- style.backgroundColor = "transparent";
1931
- }
1932
- //reset
1933
- this._$textarea.maxLength = this._$maxChars ? this._$maxChars : 0x7fffffff;
1934
- }
1935
2714
  /**
1936
2715
  * @return {void}
1937
2716
  * @method
@@ -1955,7 +2734,6 @@ export class TextField extends InteractiveObject {
1955
2734
  "limitWidth": this.width,
1956
2735
  "limitHeight": this.height,
1957
2736
  "textHeight": this.textHeight,
1958
- "verticalAlign": this._$verticalAlign,
1959
2737
  "autoSize": this._$autoSize,
1960
2738
  "wordWrap": this._$wordWrap,
1961
2739
  "border": this._$border,
@@ -1997,7 +2775,6 @@ export class TextField extends InteractiveObject {
1997
2775
  return;
1998
2776
  }
1999
2777
  const message = this._$createMessage();
2000
- message.textAreaActive = this._$textAreaActive;
2001
2778
  const bounds = this._$getBounds(null);
2002
2779
  message.xMin = bounds.xMin;
2003
2780
  message.yMin = bounds.yMin;
@@ -2008,7 +2785,6 @@ export class TextField extends InteractiveObject {
2008
2785
  message.limitWidth = this.width;
2009
2786
  message.limitHeight = this.height;
2010
2787
  message.textHeight = this.textHeight;
2011
- message.verticalAlign = this._$verticalAlign;
2012
2788
  message.autoSize = this._$autoSize;
2013
2789
  message.wordWrap = this._$wordWrap;
2014
2790
  message.border = this._$border;