@ckeditor/ckeditor5-table 39.0.1 → 40.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (229) hide show
  1. package/LICENSE.md +1 -1
  2. package/README.md +3 -3
  3. package/build/table.js +1 -1
  4. package/build/table.js.map +1 -0
  5. package/build/translations/hy.js +1 -0
  6. package/lang/translations/ar.po +1 -0
  7. package/lang/translations/az.po +1 -0
  8. package/lang/translations/bg.po +1 -0
  9. package/lang/translations/bn.po +1 -0
  10. package/lang/translations/ca.po +1 -0
  11. package/lang/translations/cs.po +1 -0
  12. package/lang/translations/da.po +1 -0
  13. package/lang/translations/de-ch.po +1 -0
  14. package/lang/translations/de.po +1 -0
  15. package/lang/translations/el.po +1 -0
  16. package/lang/translations/en-au.po +1 -0
  17. package/lang/translations/en-gb.po +1 -0
  18. package/lang/translations/en.po +1 -0
  19. package/lang/translations/es.po +1 -0
  20. package/lang/translations/et.po +1 -0
  21. package/lang/translations/fa.po +1 -0
  22. package/lang/translations/fi.po +1 -0
  23. package/lang/translations/fr.po +1 -0
  24. package/lang/translations/gl.po +1 -0
  25. package/lang/translations/he.po +1 -0
  26. package/lang/translations/hi.po +1 -0
  27. package/lang/translations/hr.po +1 -0
  28. package/lang/translations/hu.po +1 -0
  29. package/lang/translations/hy.po +262 -0
  30. package/lang/translations/id.po +1 -0
  31. package/lang/translations/it.po +1 -0
  32. package/lang/translations/ja.po +1 -0
  33. package/lang/translations/ko.po +1 -0
  34. package/lang/translations/ku.po +1 -0
  35. package/lang/translations/lt.po +1 -0
  36. package/lang/translations/lv.po +1 -0
  37. package/lang/translations/ms.po +1 -0
  38. package/lang/translations/nb.po +1 -0
  39. package/lang/translations/ne.po +1 -0
  40. package/lang/translations/nl.po +1 -0
  41. package/lang/translations/no.po +1 -0
  42. package/lang/translations/pl.po +1 -0
  43. package/lang/translations/pt-br.po +1 -0
  44. package/lang/translations/pt.po +1 -0
  45. package/lang/translations/ro.po +1 -0
  46. package/lang/translations/ru.po +1 -0
  47. package/lang/translations/sk.po +1 -0
  48. package/lang/translations/sl.po +1 -0
  49. package/lang/translations/sq.po +1 -0
  50. package/lang/translations/sr-latn.po +1 -0
  51. package/lang/translations/sr.po +1 -0
  52. package/lang/translations/sv.po +1 -0
  53. package/lang/translations/th.po +1 -0
  54. package/lang/translations/tk.po +1 -0
  55. package/lang/translations/tr.po +1 -0
  56. package/lang/translations/tt.po +1 -0
  57. package/lang/translations/ug.po +1 -0
  58. package/lang/translations/uk.po +1 -0
  59. package/lang/translations/ur.po +1 -0
  60. package/lang/translations/uz.po +1 -0
  61. package/lang/translations/vi.po +1 -0
  62. package/lang/translations/zh-cn.po +1 -0
  63. package/lang/translations/zh.po +1 -0
  64. package/package.json +2 -6
  65. package/src/augmentation.d.ts +76 -76
  66. package/src/augmentation.js +5 -5
  67. package/src/commands/insertcolumncommand.d.ts +55 -55
  68. package/src/commands/insertcolumncommand.js +67 -67
  69. package/src/commands/insertrowcommand.d.ts +54 -54
  70. package/src/commands/insertrowcommand.js +66 -66
  71. package/src/commands/inserttablecommand.d.ts +44 -44
  72. package/src/commands/inserttablecommand.js +69 -69
  73. package/src/commands/mergecellcommand.d.ts +68 -68
  74. package/src/commands/mergecellcommand.js +198 -198
  75. package/src/commands/mergecellscommand.d.ts +28 -28
  76. package/src/commands/mergecellscommand.js +94 -94
  77. package/src/commands/removecolumncommand.d.ts +29 -29
  78. package/src/commands/removecolumncommand.js +109 -109
  79. package/src/commands/removerowcommand.d.ts +29 -29
  80. package/src/commands/removerowcommand.js +82 -82
  81. package/src/commands/selectcolumncommand.d.ts +33 -33
  82. package/src/commands/selectcolumncommand.js +60 -60
  83. package/src/commands/selectrowcommand.d.ts +33 -33
  84. package/src/commands/selectrowcommand.js +56 -56
  85. package/src/commands/setheadercolumncommand.d.ts +50 -50
  86. package/src/commands/setheadercolumncommand.js +71 -71
  87. package/src/commands/setheaderrowcommand.d.ts +53 -53
  88. package/src/commands/setheaderrowcommand.js +79 -79
  89. package/src/commands/splitcellcommand.d.ts +43 -43
  90. package/src/commands/splitcellcommand.js +54 -54
  91. package/src/converters/downcast.d.ts +63 -63
  92. package/src/converters/downcast.js +146 -146
  93. package/src/converters/table-caption-post-fixer.d.ts +20 -20
  94. package/src/converters/table-caption-post-fixer.js +53 -53
  95. package/src/converters/table-cell-paragraph-post-fixer.d.ts +32 -32
  96. package/src/converters/table-cell-paragraph-post-fixer.js +107 -107
  97. package/src/converters/table-cell-refresh-handler.d.ts +18 -18
  98. package/src/converters/table-cell-refresh-handler.js +45 -45
  99. package/src/converters/table-headings-refresh-handler.d.ts +17 -17
  100. package/src/converters/table-headings-refresh-handler.js +49 -49
  101. package/src/converters/table-layout-post-fixer.d.ts +226 -226
  102. package/src/converters/table-layout-post-fixer.js +367 -367
  103. package/src/converters/tableproperties.d.ts +54 -54
  104. package/src/converters/tableproperties.js +159 -159
  105. package/src/converters/upcasttable.d.ts +49 -49
  106. package/src/converters/upcasttable.js +243 -243
  107. package/src/index.d.ts +60 -60
  108. package/src/index.js +30 -30
  109. package/src/plaintableoutput.d.ts +26 -26
  110. package/src/plaintableoutput.js +123 -123
  111. package/src/table.d.ts +40 -40
  112. package/src/table.js +44 -44
  113. package/src/tablecaption/tablecaptionediting.d.ts +63 -63
  114. package/src/tablecaption/tablecaptionediting.js +122 -122
  115. package/src/tablecaption/tablecaptionui.d.ts +21 -21
  116. package/src/tablecaption/tablecaptionui.js +57 -57
  117. package/src/tablecaption/toggletablecaptioncommand.d.ts +68 -68
  118. package/src/tablecaption/toggletablecaptioncommand.js +104 -104
  119. package/src/tablecaption/utils.d.ts +42 -42
  120. package/src/tablecaption/utils.js +67 -67
  121. package/src/tablecaption.d.ts +24 -24
  122. package/src/tablecaption.js +28 -28
  123. package/src/tablecellproperties/commands/tablecellbackgroundcolorcommand.d.ts +32 -32
  124. package/src/tablecellproperties/commands/tablecellbackgroundcolorcommand.js +30 -30
  125. package/src/tablecellproperties/commands/tablecellbordercolorcommand.d.ts +37 -37
  126. package/src/tablecellproperties/commands/tablecellbordercolorcommand.js +44 -44
  127. package/src/tablecellproperties/commands/tablecellborderstylecommand.d.ts +37 -37
  128. package/src/tablecellproperties/commands/tablecellborderstylecommand.js +44 -44
  129. package/src/tablecellproperties/commands/tablecellborderwidthcommand.d.ts +51 -51
  130. package/src/tablecellproperties/commands/tablecellborderwidthcommand.js +64 -64
  131. package/src/tablecellproperties/commands/tablecellheightcommand.d.ts +46 -46
  132. package/src/tablecellproperties/commands/tablecellheightcommand.js +51 -51
  133. package/src/tablecellproperties/commands/tablecellhorizontalalignmentcommand.d.ts +32 -32
  134. package/src/tablecellproperties/commands/tablecellhorizontalalignmentcommand.js +30 -30
  135. package/src/tablecellproperties/commands/tablecellpaddingcommand.d.ts +51 -51
  136. package/src/tablecellproperties/commands/tablecellpaddingcommand.js +64 -64
  137. package/src/tablecellproperties/commands/tablecellpropertycommand.d.ts +62 -62
  138. package/src/tablecellproperties/commands/tablecellpropertycommand.js +92 -92
  139. package/src/tablecellproperties/commands/tablecellverticalalignmentcommand.d.ts +40 -40
  140. package/src/tablecellproperties/commands/tablecellverticalalignmentcommand.js +38 -38
  141. package/src/tablecellproperties/tablecellpropertiesediting.d.ts +43 -43
  142. package/src/tablecellproperties/tablecellpropertiesediting.js +241 -241
  143. package/src/tablecellproperties/tablecellpropertiesui.d.ts +112 -112
  144. package/src/tablecellproperties/tablecellpropertiesui.js +330 -330
  145. package/src/tablecellproperties/ui/tablecellpropertiesview.d.ts +228 -228
  146. package/src/tablecellproperties/ui/tablecellpropertiesview.js +548 -539
  147. package/src/tablecellproperties.d.ts +30 -30
  148. package/src/tablecellproperties.js +34 -34
  149. package/src/tablecellwidth/commands/tablecellwidthcommand.d.ts +46 -46
  150. package/src/tablecellwidth/commands/tablecellwidthcommand.js +51 -51
  151. package/src/tablecellwidth/tablecellwidthediting.d.ts +29 -29
  152. package/src/tablecellwidth/tablecellwidthediting.js +45 -45
  153. package/src/tableclipboard.d.ts +65 -65
  154. package/src/tableclipboard.js +450 -450
  155. package/src/tablecolumnresize/constants.d.ts +20 -20
  156. package/src/tablecolumnresize/constants.js +20 -20
  157. package/src/tablecolumnresize/converters.d.ts +18 -18
  158. package/src/tablecolumnresize/converters.js +46 -45
  159. package/src/tablecolumnresize/tablecolumnresizeediting.d.ts +139 -139
  160. package/src/tablecolumnresize/tablecolumnresizeediting.js +583 -571
  161. package/src/tablecolumnresize/tablewidthscommand.d.ts +38 -38
  162. package/src/tablecolumnresize/tablewidthscommand.js +61 -61
  163. package/src/tablecolumnresize/utils.d.ts +148 -141
  164. package/src/tablecolumnresize/utils.js +358 -330
  165. package/src/tablecolumnresize.d.ts +26 -26
  166. package/src/tablecolumnresize.js +30 -30
  167. package/src/tableconfig.d.ts +343 -343
  168. package/src/tableconfig.js +5 -5
  169. package/src/tableediting.d.ts +98 -98
  170. package/src/tableediting.js +191 -191
  171. package/src/tablekeyboard.d.ts +68 -68
  172. package/src/tablekeyboard.js +279 -279
  173. package/src/tablemouse/mouseeventsobserver.d.ts +62 -62
  174. package/src/tablemouse/mouseeventsobserver.js +35 -35
  175. package/src/tablemouse.d.ts +48 -48
  176. package/src/tablemouse.js +172 -172
  177. package/src/tableproperties/commands/tablealignmentcommand.d.ts +32 -32
  178. package/src/tableproperties/commands/tablealignmentcommand.js +30 -30
  179. package/src/tableproperties/commands/tablebackgroundcolorcommand.d.ts +32 -32
  180. package/src/tableproperties/commands/tablebackgroundcolorcommand.js +30 -30
  181. package/src/tableproperties/commands/tablebordercolorcommand.d.ts +37 -37
  182. package/src/tableproperties/commands/tablebordercolorcommand.js +44 -44
  183. package/src/tableproperties/commands/tableborderstylecommand.d.ts +37 -37
  184. package/src/tableproperties/commands/tableborderstylecommand.js +44 -44
  185. package/src/tableproperties/commands/tableborderwidthcommand.d.ts +51 -51
  186. package/src/tableproperties/commands/tableborderwidthcommand.js +64 -64
  187. package/src/tableproperties/commands/tableheightcommand.d.ts +46 -46
  188. package/src/tableproperties/commands/tableheightcommand.js +54 -54
  189. package/src/tableproperties/commands/tablepropertycommand.d.ts +61 -61
  190. package/src/tableproperties/commands/tablepropertycommand.js +80 -80
  191. package/src/tableproperties/commands/tablewidthcommand.d.ts +46 -46
  192. package/src/tableproperties/commands/tablewidthcommand.js +54 -54
  193. package/src/tableproperties/tablepropertiesediting.d.ts +40 -40
  194. package/src/tableproperties/tablepropertiesediting.js +206 -206
  195. package/src/tableproperties/tablepropertiesui.d.ts +114 -114
  196. package/src/tableproperties/tablepropertiesui.js +321 -321
  197. package/src/tableproperties/ui/tablepropertiesview.d.ts +207 -207
  198. package/src/tableproperties/ui/tablepropertiesview.js +466 -457
  199. package/src/tableproperties.d.ts +30 -30
  200. package/src/tableproperties.js +34 -34
  201. package/src/tableselection.d.ts +107 -107
  202. package/src/tableselection.js +297 -297
  203. package/src/tabletoolbar.d.ts +32 -32
  204. package/src/tabletoolbar.js +57 -57
  205. package/src/tableui.d.ts +53 -53
  206. package/src/tableui.js +309 -309
  207. package/src/tableutils.d.ts +448 -448
  208. package/src/tableutils.js +1055 -1041
  209. package/src/tablewalker.d.ts +362 -323
  210. package/src/tablewalker.js +393 -333
  211. package/src/ui/colorinputview.d.ts +140 -140
  212. package/src/ui/colorinputview.js +271 -265
  213. package/src/ui/formrowview.d.ts +61 -61
  214. package/src/ui/formrowview.js +57 -57
  215. package/src/ui/inserttableview.d.ts +77 -77
  216. package/src/ui/inserttableview.js +169 -169
  217. package/src/utils/common.d.ts +42 -42
  218. package/src/utils/common.js +57 -57
  219. package/src/utils/structure.d.ts +245 -245
  220. package/src/utils/structure.js +426 -426
  221. package/src/utils/table-properties.d.ts +67 -67
  222. package/src/utils/table-properties.js +86 -86
  223. package/src/utils/ui/contextualballoon.d.ts +34 -34
  224. package/src/utils/ui/contextualballoon.js +106 -106
  225. package/src/utils/ui/table-properties.d.ts +195 -195
  226. package/src/utils/ui/table-properties.js +362 -362
  227. package/src/utils/ui/widget.d.ts +16 -16
  228. package/src/utils/ui/widget.js +38 -38
  229. package/theme/tablecolumnresize.css +8 -6
@@ -1,265 +1,271 @@
1
- /**
2
- * @license Copyright (c) 2003-2023, CKSource Holding sp. z o.o. All rights reserved.
3
- * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
- */
5
- /**
6
- * @module table/ui/colorinputview
7
- */
8
- import { View, InputTextView, createDropdown, FocusCycler, ViewCollection, ColorSelectorView } from 'ckeditor5/src/ui';
9
- import { FocusTracker, KeystrokeHandler } from 'ckeditor5/src/utils';
10
- import '../../theme/colorinput.css';
11
- /**
12
- * The color input view class. It allows the user to type in a color (hex, rgb, etc.)
13
- * or choose it from the configurable color palette with a preview.
14
- *
15
- * @internal
16
- */
17
- export default class ColorInputView extends View {
18
- /**
19
- * Creates an instance of the color input view.
20
- *
21
- * @param locale The locale instance.
22
- * @param options The input options.
23
- * @param options.colorDefinitions The colors to be displayed in the palette inside the input's dropdown.
24
- * @param options.columns The number of columns in which the colors will be displayed.
25
- * @param options.defaultColorValue If specified, the color input view will replace the "Remove color" button with
26
- * the "Restore default" button. Instead of clearing the input field, the default color value will be set.
27
- */
28
- constructor(locale, options) {
29
- super(locale);
30
- this.set('value', '');
31
- this.set('isReadOnly', false);
32
- this.set('isFocused', false);
33
- this.set('isEmpty', true);
34
- this.options = options;
35
- this.focusTracker = new FocusTracker();
36
- this._focusables = new ViewCollection();
37
- this.dropdownView = this._createDropdownView();
38
- this.inputView = this._createInputTextView();
39
- this.keystrokes = new KeystrokeHandler();
40
- this._stillTyping = false;
41
- this._focusCycler = new FocusCycler({
42
- focusables: this._focusables,
43
- focusTracker: this.focusTracker,
44
- keystrokeHandler: this.keystrokes,
45
- actions: {
46
- // Navigate items backwards using the <kbd>Shift</kbd> + <kbd>Tab</kbd> keystroke.
47
- focusPrevious: 'shift + tab',
48
- // Navigate items forwards using the <kbd>Tab</kbd> key.
49
- focusNext: 'tab'
50
- }
51
- });
52
- this.setTemplate({
53
- tag: 'div',
54
- attributes: {
55
- class: [
56
- 'ck',
57
- 'ck-input-color'
58
- ]
59
- },
60
- children: [
61
- this.dropdownView,
62
- this.inputView
63
- ]
64
- });
65
- this.on('change:value', (evt, name, inputValue) => this._setInputValue(inputValue));
66
- }
67
- /**
68
- * @inheritDoc
69
- */
70
- render() {
71
- super.render();
72
- // Start listening for the keystrokes coming from the dropdown panel view.
73
- this.keystrokes.listenTo(this.dropdownView.panelView.element);
74
- }
75
- /**
76
- * Focuses the input.
77
- */
78
- focus() {
79
- this.inputView.focus();
80
- }
81
- /**
82
- * @inheritDoc
83
- */
84
- destroy() {
85
- super.destroy();
86
- this.focusTracker.destroy();
87
- this.keystrokes.destroy();
88
- }
89
- /**
90
- * Creates and configures the {@link #dropdownView}.
91
- */
92
- _createDropdownView() {
93
- const locale = this.locale;
94
- const t = locale.t;
95
- const bind = this.bindTemplate;
96
- const colorSelector = this._createColorSelector(locale);
97
- const dropdown = createDropdown(locale);
98
- const colorPreview = new View();
99
- colorPreview.setTemplate({
100
- tag: 'span',
101
- attributes: {
102
- class: [
103
- 'ck',
104
- 'ck-input-color__button__preview'
105
- ],
106
- style: {
107
- backgroundColor: bind.to('value')
108
- }
109
- },
110
- children: [{
111
- tag: 'span',
112
- attributes: {
113
- class: [
114
- 'ck',
115
- 'ck-input-color__button__preview__no-color-indicator',
116
- bind.if('value', 'ck-hidden', value => value != '')
117
- ]
118
- }
119
- }]
120
- });
121
- dropdown.buttonView.extendTemplate({
122
- attributes: {
123
- class: 'ck-input-color__button'
124
- }
125
- });
126
- dropdown.buttonView.children.add(colorPreview);
127
- dropdown.buttonView.label = t('Color picker');
128
- dropdown.buttonView.tooltip = true;
129
- dropdown.panelPosition = locale.uiLanguageDirection === 'rtl' ? 'se' : 'sw';
130
- dropdown.panelView.children.add(colorSelector);
131
- dropdown.bind('isEnabled').to(this, 'isReadOnly', value => !value);
132
- this._focusables.add(colorSelector);
133
- this.focusTracker.add(colorSelector.element);
134
- dropdown.on('change:isOpen', (evt, name, isVisible) => {
135
- if (isVisible) {
136
- colorSelector.updateSelectedColors();
137
- colorSelector.showColorGridsFragment();
138
- }
139
- });
140
- return dropdown;
141
- }
142
- /**
143
- * Creates and configures an instance of {@link module:ui/inputtext/inputtextview~InputTextView}.
144
- *
145
- * @returns A configured instance to be set as {@link #inputView}.
146
- */
147
- _createInputTextView() {
148
- const locale = this.locale;
149
- const inputView = new InputTextView(locale);
150
- inputView.extendTemplate({
151
- on: {
152
- blur: inputView.bindTemplate.to('blur')
153
- }
154
- });
155
- inputView.value = this.value;
156
- inputView.bind('isReadOnly', 'hasError').to(this);
157
- this.bind('isFocused', 'isEmpty').to(inputView);
158
- inputView.on('input', () => {
159
- const inputValue = inputView.element.value;
160
- // Check if the value matches one of our defined colors' label.
161
- const mappedColor = this.options.colorDefinitions.find(def => inputValue === def.label);
162
- this._stillTyping = true;
163
- this.value = mappedColor && mappedColor.color || inputValue;
164
- });
165
- inputView.on('blur', () => {
166
- this._stillTyping = false;
167
- this._setInputValue(inputView.element.value);
168
- });
169
- inputView.delegate('input').to(this);
170
- return inputView;
171
- }
172
- /**
173
- * Creates and configures the panel with "color grid" and "color picker" inside the {@link #dropdownView}.
174
- */
175
- _createColorSelector(locale) {
176
- const t = locale.t;
177
- const defaultColor = this.options.defaultColorValue || '';
178
- const removeColorButtonLabel = defaultColor ? t('Restore default') : t('Remove color');
179
- const colorSelector = new ColorSelectorView(locale, {
180
- colors: this.options.colorDefinitions,
181
- columns: this.options.columns,
182
- removeButtonLabel: removeColorButtonLabel,
183
- colorPickerLabel: t('Color picker'),
184
- colorPickerViewConfig: this.options.colorPickerConfig === false ? false : {
185
- ...this.options.colorPickerConfig,
186
- hideInput: true
187
- }
188
- });
189
- colorSelector.appendUI();
190
- colorSelector.on('execute', (evt, data) => {
191
- if (data.source === 'colorPickerSaveButton') {
192
- this.dropdownView.isOpen = false;
193
- return;
194
- }
195
- this.value = data.value || defaultColor;
196
- // Trigger the listener that actually applies the set value.
197
- this.fire('input');
198
- if (data.source !== 'colorPicker') {
199
- this.dropdownView.isOpen = false;
200
- }
201
- });
202
- /**
203
- * Color is saved before changes in color picker. In case "cancel button" is pressed
204
- * this color will be applied.
205
- */
206
- let backupColor = this.value;
207
- colorSelector.on('colorPicker:cancel', () => {
208
- /**
209
- * Revert color to previous value before changes in color picker.
210
- */
211
- this.value = backupColor;
212
- this.fire('input');
213
- this.dropdownView.isOpen = false;
214
- });
215
- colorSelector.colorGridsFragmentView.colorPickerButtonView.on('execute', () => {
216
- /**
217
- * Save color value before changes in color picker.
218
- */
219
- backupColor = this.value;
220
- });
221
- colorSelector.bind('selectedColor').to(this, 'value');
222
- return colorSelector;
223
- }
224
- /**
225
- * Sets {@link #inputView}'s value property to the color value or color label,
226
- * if there is one and the user is not typing.
227
- *
228
- * Handles cases like:
229
- *
230
- * * Someone picks the color in the grid.
231
- * * The color is set from the plugin level.
232
- *
233
- * @param inputValue Color value to be set.
234
- */
235
- _setInputValue(inputValue) {
236
- if (!this._stillTyping) {
237
- const normalizedInputValue = normalizeColor(inputValue);
238
- // Check if the value matches one of our defined colors.
239
- const mappedColor = this.options.colorDefinitions.find(def => normalizedInputValue === normalizeColor(def.color));
240
- if (mappedColor) {
241
- this.inputView.value = mappedColor.label;
242
- }
243
- else {
244
- this.inputView.value = inputValue || '';
245
- }
246
- }
247
- }
248
- }
249
- /**
250
- * Normalizes color value, by stripping extensive whitespace.
251
- * For example., transforms:
252
- * * ` rgb( 25 50 0 )` to `rgb(25 50 0)`,
253
- * * "\t rgb( 25 , 50,0 ) " to `rgb(25 50 0)`.
254
- *
255
- * @param colorString The value to be normalized.
256
- */
257
- function normalizeColor(colorString) {
258
- return colorString
259
- // Remove any whitespace right after `(` or `,`.
260
- .replace(/([(,])\s+/g, '$1')
261
- // Remove any whitespace at the beginning or right before the end, `)`, `,`, or another whitespace.
262
- .replace(/^\s+|\s+(?=[),\s]|$)/g, '')
263
- // Then, replace `,` or whitespace with a single space.
264
- .replace(/,|\s/g, ' ');
265
- }
1
+ /**
2
+ * @license Copyright (c) 2003-2023, CKSource Holding sp. z o.o. All rights reserved.
3
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
+ */
5
+ /**
6
+ * @module table/ui/colorinputview
7
+ */
8
+ import { View, InputTextView, createDropdown, FocusCycler, ViewCollection, ColorSelectorView } from 'ckeditor5/src/ui';
9
+ import { FocusTracker, KeystrokeHandler } from 'ckeditor5/src/utils';
10
+ import '../../theme/colorinput.css';
11
+ /**
12
+ * The color input view class. It allows the user to type in a color (hex, rgb, etc.)
13
+ * or choose it from the configurable color palette with a preview.
14
+ *
15
+ * @internal
16
+ */
17
+ export default class ColorInputView extends View {
18
+ /**
19
+ * Creates an instance of the color input view.
20
+ *
21
+ * @param locale The locale instance.
22
+ * @param options The input options.
23
+ * @param options.colorDefinitions The colors to be displayed in the palette inside the input's dropdown.
24
+ * @param options.columns The number of columns in which the colors will be displayed.
25
+ * @param options.defaultColorValue If specified, the color input view will replace the "Remove color" button with
26
+ * the "Restore default" button. Instead of clearing the input field, the default color value will be set.
27
+ */
28
+ constructor(locale, options) {
29
+ super(locale);
30
+ this.set('value', '');
31
+ this.set('isReadOnly', false);
32
+ this.set('isFocused', false);
33
+ this.set('isEmpty', true);
34
+ this.options = options;
35
+ this.focusTracker = new FocusTracker();
36
+ this._focusables = new ViewCollection();
37
+ this.dropdownView = this._createDropdownView();
38
+ this.inputView = this._createInputTextView();
39
+ this.keystrokes = new KeystrokeHandler();
40
+ this._stillTyping = false;
41
+ this.focusCycler = new FocusCycler({
42
+ focusables: this._focusables,
43
+ focusTracker: this.focusTracker,
44
+ keystrokeHandler: this.keystrokes,
45
+ actions: {
46
+ // Navigate items backwards using the <kbd>Shift</kbd> + <kbd>Tab</kbd> keystroke.
47
+ focusPrevious: 'shift + tab',
48
+ // Navigate items forwards using the <kbd>Tab</kbd> key.
49
+ focusNext: 'tab'
50
+ }
51
+ });
52
+ this.setTemplate({
53
+ tag: 'div',
54
+ attributes: {
55
+ class: [
56
+ 'ck',
57
+ 'ck-input-color'
58
+ ]
59
+ },
60
+ children: [
61
+ this.dropdownView,
62
+ this.inputView
63
+ ]
64
+ });
65
+ this.on('change:value', (evt, name, inputValue) => this._setInputValue(inputValue));
66
+ }
67
+ /**
68
+ * @inheritDoc
69
+ */
70
+ render() {
71
+ super.render();
72
+ [this.inputView, this.dropdownView.buttonView].forEach(view => {
73
+ this.focusTracker.add(view.element);
74
+ this._focusables.add(view);
75
+ });
76
+ this.keystrokes.listenTo(this.element);
77
+ }
78
+ /**
79
+ * Focuses the view.
80
+ */
81
+ focus(direction) {
82
+ if (direction === -1) {
83
+ this.focusCycler.focusLast();
84
+ }
85
+ else {
86
+ this.focusCycler.focusFirst();
87
+ }
88
+ }
89
+ /**
90
+ * @inheritDoc
91
+ */
92
+ destroy() {
93
+ super.destroy();
94
+ this.focusTracker.destroy();
95
+ this.keystrokes.destroy();
96
+ }
97
+ /**
98
+ * Creates and configures the {@link #dropdownView}.
99
+ */
100
+ _createDropdownView() {
101
+ const locale = this.locale;
102
+ const t = locale.t;
103
+ const bind = this.bindTemplate;
104
+ const colorSelector = this._createColorSelector(locale);
105
+ const dropdown = createDropdown(locale);
106
+ const colorPreview = new View();
107
+ colorPreview.setTemplate({
108
+ tag: 'span',
109
+ attributes: {
110
+ class: [
111
+ 'ck',
112
+ 'ck-input-color__button__preview'
113
+ ],
114
+ style: {
115
+ backgroundColor: bind.to('value')
116
+ }
117
+ },
118
+ children: [{
119
+ tag: 'span',
120
+ attributes: {
121
+ class: [
122
+ 'ck',
123
+ 'ck-input-color__button__preview__no-color-indicator',
124
+ bind.if('value', 'ck-hidden', value => value != '')
125
+ ]
126
+ }
127
+ }]
128
+ });
129
+ dropdown.buttonView.extendTemplate({
130
+ attributes: {
131
+ class: 'ck-input-color__button'
132
+ }
133
+ });
134
+ dropdown.buttonView.children.add(colorPreview);
135
+ dropdown.buttonView.label = t('Color picker');
136
+ dropdown.buttonView.tooltip = true;
137
+ dropdown.panelPosition = locale.uiLanguageDirection === 'rtl' ? 'se' : 'sw';
138
+ dropdown.panelView.children.add(colorSelector);
139
+ dropdown.bind('isEnabled').to(this, 'isReadOnly', value => !value);
140
+ dropdown.on('change:isOpen', (evt, name, isVisible) => {
141
+ if (isVisible) {
142
+ colorSelector.updateSelectedColors();
143
+ colorSelector.showColorGridsFragment();
144
+ }
145
+ });
146
+ return dropdown;
147
+ }
148
+ /**
149
+ * Creates and configures an instance of {@link module:ui/inputtext/inputtextview~InputTextView}.
150
+ *
151
+ * @returns A configured instance to be set as {@link #inputView}.
152
+ */
153
+ _createInputTextView() {
154
+ const locale = this.locale;
155
+ const inputView = new InputTextView(locale);
156
+ inputView.extendTemplate({
157
+ on: {
158
+ blur: inputView.bindTemplate.to('blur')
159
+ }
160
+ });
161
+ inputView.value = this.value;
162
+ inputView.bind('isReadOnly', 'hasError').to(this);
163
+ this.bind('isFocused', 'isEmpty').to(inputView);
164
+ inputView.on('input', () => {
165
+ const inputValue = inputView.element.value;
166
+ // Check if the value matches one of our defined colors' label.
167
+ const mappedColor = this.options.colorDefinitions.find(def => inputValue === def.label);
168
+ this._stillTyping = true;
169
+ this.value = mappedColor && mappedColor.color || inputValue;
170
+ });
171
+ inputView.on('blur', () => {
172
+ this._stillTyping = false;
173
+ this._setInputValue(inputView.element.value);
174
+ });
175
+ inputView.delegate('input').to(this);
176
+ return inputView;
177
+ }
178
+ /**
179
+ * Creates and configures the panel with "color grid" and "color picker" inside the {@link #dropdownView}.
180
+ */
181
+ _createColorSelector(locale) {
182
+ const t = locale.t;
183
+ const defaultColor = this.options.defaultColorValue || '';
184
+ const removeColorButtonLabel = defaultColor ? t('Restore default') : t('Remove color');
185
+ const colorSelector = new ColorSelectorView(locale, {
186
+ colors: this.options.colorDefinitions,
187
+ columns: this.options.columns,
188
+ removeButtonLabel: removeColorButtonLabel,
189
+ colorPickerLabel: t('Color picker'),
190
+ colorPickerViewConfig: this.options.colorPickerConfig === false ? false : {
191
+ ...this.options.colorPickerConfig,
192
+ hideInput: true
193
+ }
194
+ });
195
+ colorSelector.appendUI();
196
+ colorSelector.on('execute', (evt, data) => {
197
+ if (data.source === 'colorPickerSaveButton') {
198
+ this.dropdownView.isOpen = false;
199
+ return;
200
+ }
201
+ this.value = data.value || defaultColor;
202
+ // Trigger the listener that actually applies the set value.
203
+ this.fire('input');
204
+ if (data.source !== 'colorPicker') {
205
+ this.dropdownView.isOpen = false;
206
+ }
207
+ });
208
+ /**
209
+ * Color is saved before changes in color picker. In case "cancel button" is pressed
210
+ * this color will be applied.
211
+ */
212
+ let backupColor = this.value;
213
+ colorSelector.on('colorPicker:cancel', () => {
214
+ /**
215
+ * Revert color to previous value before changes in color picker.
216
+ */
217
+ this.value = backupColor;
218
+ this.fire('input');
219
+ this.dropdownView.isOpen = false;
220
+ });
221
+ colorSelector.colorGridsFragmentView.colorPickerButtonView.on('execute', () => {
222
+ /**
223
+ * Save color value before changes in color picker.
224
+ */
225
+ backupColor = this.value;
226
+ });
227
+ colorSelector.bind('selectedColor').to(this, 'value');
228
+ return colorSelector;
229
+ }
230
+ /**
231
+ * Sets {@link #inputView}'s value property to the color value or color label,
232
+ * if there is one and the user is not typing.
233
+ *
234
+ * Handles cases like:
235
+ *
236
+ * * Someone picks the color in the grid.
237
+ * * The color is set from the plugin level.
238
+ *
239
+ * @param inputValue Color value to be set.
240
+ */
241
+ _setInputValue(inputValue) {
242
+ if (!this._stillTyping) {
243
+ const normalizedInputValue = normalizeColor(inputValue);
244
+ // Check if the value matches one of our defined colors.
245
+ const mappedColor = this.options.colorDefinitions.find(def => normalizedInputValue === normalizeColor(def.color));
246
+ if (mappedColor) {
247
+ this.inputView.value = mappedColor.label;
248
+ }
249
+ else {
250
+ this.inputView.value = inputValue || '';
251
+ }
252
+ }
253
+ }
254
+ }
255
+ /**
256
+ * Normalizes color value, by stripping extensive whitespace.
257
+ * For example., transforms:
258
+ * * ` rgb( 25 50 0 )` to `rgb(25 50 0)`,
259
+ * * "\t rgb( 25 , 50,0 ) " to `rgb(25 50 0)`.
260
+ *
261
+ * @param colorString The value to be normalized.
262
+ */
263
+ function normalizeColor(colorString) {
264
+ return colorString
265
+ // Remove any whitespace right after `(` or `,`.
266
+ .replace(/([(,])\s+/g, '$1')
267
+ // Remove any whitespace at the beginning or right before the end, `)`, `,`, or another whitespace.
268
+ .replace(/^\s+|\s+(?=[),\s]|$)/g, '')
269
+ // Then, replace `,` or whitespace with a single space.
270
+ .replace(/,|\s/g, ' ');
271
+ }