@ckeditor/ckeditor5-table 0.0.0-nightly-next-20251209.0 → 0.0.0-nightly-20251210.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/build/table.js +2 -2
- package/build/translations/af.js +1 -1
- package/build/translations/ar.js +1 -1
- package/build/translations/ast.js +1 -1
- package/build/translations/az.js +1 -1
- package/build/translations/be.js +1 -1
- package/build/translations/bg.js +1 -1
- package/build/translations/bn.js +1 -1
- package/build/translations/bs.js +1 -1
- package/build/translations/ca.js +1 -1
- package/build/translations/cs.js +1 -1
- package/build/translations/da.js +1 -1
- package/build/translations/de-ch.js +1 -1
- package/build/translations/de.js +1 -1
- package/build/translations/el.js +1 -1
- package/build/translations/en-au.js +1 -1
- package/build/translations/en-gb.js +1 -1
- package/build/translations/eo.js +1 -1
- package/build/translations/es-co.js +1 -1
- package/build/translations/es.js +1 -1
- package/build/translations/et.js +1 -1
- package/build/translations/eu.js +1 -1
- package/build/translations/fa.js +1 -1
- package/build/translations/fi.js +1 -1
- package/build/translations/fr.js +1 -1
- package/build/translations/gl.js +1 -1
- package/build/translations/gu.js +1 -1
- package/build/translations/he.js +1 -1
- package/build/translations/hi.js +1 -1
- package/build/translations/hr.js +1 -1
- package/build/translations/hu.js +1 -1
- package/build/translations/hy.js +1 -1
- package/build/translations/id.js +1 -1
- package/build/translations/it.js +1 -1
- package/build/translations/ja.js +1 -1
- package/build/translations/jv.js +1 -1
- package/build/translations/kk.js +1 -1
- package/build/translations/km.js +1 -1
- package/build/translations/kn.js +1 -1
- package/build/translations/ko.js +1 -1
- package/build/translations/ku.js +1 -1
- package/build/translations/lt.js +1 -1
- package/build/translations/lv.js +1 -1
- package/build/translations/ms.js +1 -1
- package/build/translations/nb.js +1 -1
- package/build/translations/ne.js +1 -1
- package/build/translations/nl.js +1 -1
- package/build/translations/no.js +1 -1
- package/build/translations/oc.js +1 -1
- package/build/translations/pl.js +1 -1
- package/build/translations/pt-br.js +1 -1
- package/build/translations/pt.js +1 -1
- package/build/translations/ro.js +1 -1
- package/build/translations/ru.js +1 -1
- package/build/translations/si.js +1 -1
- package/build/translations/sk.js +1 -1
- package/build/translations/sl.js +1 -1
- package/build/translations/sq.js +1 -1
- package/build/translations/sr-latn.js +1 -1
- package/build/translations/sr.js +1 -1
- package/build/translations/sv.js +1 -1
- package/build/translations/th.js +1 -1
- package/build/translations/ti.js +1 -1
- package/build/translations/tk.js +1 -1
- package/build/translations/tr.js +1 -1
- package/build/translations/tt.js +1 -1
- package/build/translations/ug.js +1 -1
- package/build/translations/uk.js +1 -1
- package/build/translations/ur.js +1 -1
- package/build/translations/uz.js +1 -1
- package/build/translations/vi.js +1 -1
- package/build/translations/zh-cn.js +1 -1
- package/build/translations/zh.js +1 -1
- package/ckeditor5-metadata.json +1 -10
- package/dist/index-content.css +30 -30
- package/dist/index-editor.css +194 -120
- package/dist/index.css +265 -167
- package/dist/index.css.map +1 -1
- package/dist/index.js +2219 -148
- package/dist/index.js.map +1 -1
- package/lang/contexts.json +4 -0
- package/package.json +9 -9
- package/src/augmentation.d.ts +7 -0
- package/src/converters/downcast.js +12 -3
- package/src/index.d.ts +4 -0
- package/src/index.js +5 -0
- package/src/tablecellproperties/tablecellpropertiesuiexperimental.d.ts +128 -0
- package/src/tablecellproperties/tablecellpropertiesuiexperimental.js +386 -0
- package/src/tablecellproperties/ui/tablecellpropertiesview.d.ts +0 -8
- package/src/tablecellproperties/ui/tablecellpropertiesview.js +10 -30
- package/src/tablecellproperties/ui/tablecellpropertiesviewexperimental.d.ts +237 -0
- package/src/tablecellproperties/ui/tablecellpropertiesviewexperimental.js +633 -0
- package/src/tableconfig.d.ts +4 -4
- package/src/tableproperties/tablepropertiesediting.js +147 -14
- package/src/tableproperties/tablepropertiesuiexperimental.d.ts +136 -0
- package/src/tableproperties/tablepropertiesuiexperimental.js +375 -0
- package/src/tableproperties/ui/tablepropertiesview.d.ts +0 -8
- package/src/tableproperties/ui/tablepropertiesview.js +37 -59
- package/src/tableproperties/ui/tablepropertiesviewexperimental.d.ts +216 -0
- package/src/tableproperties/ui/tablepropertiesviewexperimental.js +544 -0
- package/src/utils/ui/table-propertiesexperimental.d.ts +215 -0
- package/src/utils/ui/table-propertiesexperimental.js +391 -0
- package/theme/formrow-experimental.css +15 -0
- package/theme/formrow.css +0 -2
- package/theme/tableform-experimental.css +73 -0
- package/theme/tableform.css +5 -1
- package/theme/tableproperties-experimental.css +78 -0
- package/theme/tableproperties.css +0 -60
|
@@ -0,0 +1,375 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @license Copyright (c) 2003-2025, CKSource Holding sp. z o.o. All rights reserved.
|
|
3
|
+
* For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
|
|
4
|
+
*/
|
|
5
|
+
/**
|
|
6
|
+
* @module table/tableproperties/tablepropertiesuiexperimental
|
|
7
|
+
*/
|
|
8
|
+
/* istanbul ignore file -- @preserve */
|
|
9
|
+
import { Plugin } from 'ckeditor5/src/core.js';
|
|
10
|
+
import { IconTableProperties } from 'ckeditor5/src/icons.js';
|
|
11
|
+
import { ButtonView, ContextualBalloon, clickOutsideHandler, getLocalizedColorOptions, normalizeColorOptions } from 'ckeditor5/src/ui.js';
|
|
12
|
+
import { debounce } from 'es-toolkit/compat';
|
|
13
|
+
import { TablePropertiesViewExperimental } from './ui/tablepropertiesviewexperimental.js';
|
|
14
|
+
import { colorFieldValidator, getLocalizedColorErrorText, getLocalizedLengthErrorText, lengthFieldValidator, lineWidthFieldValidator, defaultColors } from '../utils/ui/table-properties.js';
|
|
15
|
+
import { getSelectionAffectedTableWidget } from '../utils/ui/widget.js';
|
|
16
|
+
import { getBalloonTablePositionData, repositionContextualBalloon } from '../utils/ui/contextualballoon.js';
|
|
17
|
+
import { getNormalizedDefaultProperties, getNormalizedDefaultTableProperties } from '../utils/table-properties.js';
|
|
18
|
+
const ERROR_TEXT_TIMEOUT = 500;
|
|
19
|
+
// Map of view properties and related commands.
|
|
20
|
+
const propertyToCommandMap = {
|
|
21
|
+
borderStyle: 'tableBorderStyle',
|
|
22
|
+
borderColor: 'tableBorderColor',
|
|
23
|
+
borderWidth: 'tableBorderWidth',
|
|
24
|
+
backgroundColor: 'tableBackgroundColor',
|
|
25
|
+
width: 'tableWidth',
|
|
26
|
+
height: 'tableHeight',
|
|
27
|
+
alignment: 'tableAlignment'
|
|
28
|
+
};
|
|
29
|
+
/**
|
|
30
|
+
* The table properties UI plugin. It introduces the `'tableProperties'` button
|
|
31
|
+
* that opens a form allowing to specify visual styling of an entire table.
|
|
32
|
+
*
|
|
33
|
+
* It uses the {@link module:ui/panel/balloon/contextualballoon~ContextualBalloon contextual balloon plugin}.
|
|
34
|
+
*/
|
|
35
|
+
export class TablePropertiesUIExperimental extends Plugin {
|
|
36
|
+
/**
|
|
37
|
+
* The default table properties.
|
|
38
|
+
*/
|
|
39
|
+
_defaultContentTableProperties;
|
|
40
|
+
/**
|
|
41
|
+
* The default layout table properties.
|
|
42
|
+
*/
|
|
43
|
+
_defaultLayoutTableProperties;
|
|
44
|
+
/**
|
|
45
|
+
* The contextual balloon plugin instance.
|
|
46
|
+
*/
|
|
47
|
+
_balloon;
|
|
48
|
+
/**
|
|
49
|
+
* The properties form view displayed inside the balloon.
|
|
50
|
+
*/
|
|
51
|
+
view = null;
|
|
52
|
+
/**
|
|
53
|
+
* The properties form view displayed inside the balloon (content table).
|
|
54
|
+
*/
|
|
55
|
+
_viewWithContentTableDefaults = null;
|
|
56
|
+
/**
|
|
57
|
+
* The properties form view displayed inside the balloon (layout table).
|
|
58
|
+
*/
|
|
59
|
+
_viewWithLayoutTableDefaults = null;
|
|
60
|
+
/**
|
|
61
|
+
* The batch used to undo all changes made by the form (which are live, as the user types)
|
|
62
|
+
* when "Cancel" was pressed. Each time the view is shown, a new batch is created.
|
|
63
|
+
*/
|
|
64
|
+
_undoStepBatch;
|
|
65
|
+
/**
|
|
66
|
+
* Flag used to indicate whether view is ready to execute update commands
|
|
67
|
+
* (it finished loading initial data).
|
|
68
|
+
*/
|
|
69
|
+
_isReady;
|
|
70
|
+
/**
|
|
71
|
+
* @inheritDoc
|
|
72
|
+
*/
|
|
73
|
+
static get requires() {
|
|
74
|
+
return [ContextualBalloon];
|
|
75
|
+
}
|
|
76
|
+
/**
|
|
77
|
+
* @inheritDoc
|
|
78
|
+
*/
|
|
79
|
+
static get pluginName() {
|
|
80
|
+
return 'TablePropertiesUIExperimental';
|
|
81
|
+
}
|
|
82
|
+
/**
|
|
83
|
+
* @inheritDoc
|
|
84
|
+
*/
|
|
85
|
+
static get isOfficialPlugin() {
|
|
86
|
+
return true;
|
|
87
|
+
}
|
|
88
|
+
/**
|
|
89
|
+
* @inheritDoc
|
|
90
|
+
*/
|
|
91
|
+
constructor(editor) {
|
|
92
|
+
super(editor);
|
|
93
|
+
editor.config.define('table.tableProperties', {
|
|
94
|
+
borderColors: defaultColors,
|
|
95
|
+
backgroundColors: defaultColors
|
|
96
|
+
});
|
|
97
|
+
}
|
|
98
|
+
/**
|
|
99
|
+
* @inheritDoc
|
|
100
|
+
*/
|
|
101
|
+
init() {
|
|
102
|
+
const editor = this.editor;
|
|
103
|
+
this._defaultContentTableProperties = getNormalizedDefaultTableProperties(editor.config.get('table.tableProperties.defaultProperties'), {
|
|
104
|
+
includeAlignmentProperty: true
|
|
105
|
+
});
|
|
106
|
+
this._defaultLayoutTableProperties = getNormalizedDefaultProperties();
|
|
107
|
+
this._balloon = editor.plugins.get(ContextualBalloon);
|
|
108
|
+
editor.ui.componentFactory.add('tableProperties', () => this._createTablePropertiesButton());
|
|
109
|
+
}
|
|
110
|
+
/**
|
|
111
|
+
* Creates the table properties button.
|
|
112
|
+
*
|
|
113
|
+
* @internal
|
|
114
|
+
*/
|
|
115
|
+
_createTablePropertiesButton() {
|
|
116
|
+
const editor = this.editor;
|
|
117
|
+
const t = editor.t;
|
|
118
|
+
const view = new ButtonView(editor.locale);
|
|
119
|
+
view.set({
|
|
120
|
+
label: t('Table properties'),
|
|
121
|
+
icon: IconTableProperties,
|
|
122
|
+
tooltip: true
|
|
123
|
+
});
|
|
124
|
+
this.listenTo(view, 'execute', () => this._showView());
|
|
125
|
+
const commands = Object.values(propertyToCommandMap)
|
|
126
|
+
.map(commandName => editor.commands.get(commandName));
|
|
127
|
+
view.bind('isEnabled').toMany(commands, 'isEnabled', (...areEnabled) => (areEnabled.some(isCommandEnabled => isCommandEnabled)));
|
|
128
|
+
return view;
|
|
129
|
+
}
|
|
130
|
+
/**
|
|
131
|
+
* @inheritDoc
|
|
132
|
+
*/
|
|
133
|
+
destroy() {
|
|
134
|
+
super.destroy();
|
|
135
|
+
// Destroy created UI components as they are not automatically destroyed.
|
|
136
|
+
// See https://github.com/ckeditor/ckeditor5/issues/1341.
|
|
137
|
+
if (this.view) {
|
|
138
|
+
this.view.destroy();
|
|
139
|
+
}
|
|
140
|
+
}
|
|
141
|
+
/**
|
|
142
|
+
* Creates the {@link module:table/tableproperties/ui/tablepropertiesview~TablePropertiesView} instance.
|
|
143
|
+
*
|
|
144
|
+
* @returns The table properties form view instance.
|
|
145
|
+
*/
|
|
146
|
+
_createPropertiesView(defaultTableProperties) {
|
|
147
|
+
const editor = this.editor;
|
|
148
|
+
const config = editor.config.get('table.tableProperties');
|
|
149
|
+
const borderColorsConfig = normalizeColorOptions(config.borderColors);
|
|
150
|
+
const localizedBorderColors = getLocalizedColorOptions(editor.locale, borderColorsConfig);
|
|
151
|
+
const backgroundColorsConfig = normalizeColorOptions(config.backgroundColors);
|
|
152
|
+
const localizedBackgroundColors = getLocalizedColorOptions(editor.locale, backgroundColorsConfig);
|
|
153
|
+
const hasColorPicker = config.colorPicker !== false;
|
|
154
|
+
const view = new TablePropertiesViewExperimental(editor.locale, {
|
|
155
|
+
borderColors: localizedBorderColors,
|
|
156
|
+
backgroundColors: localizedBackgroundColors,
|
|
157
|
+
defaultTableProperties,
|
|
158
|
+
colorPickerConfig: hasColorPicker ? (config.colorPicker || {}) : false
|
|
159
|
+
});
|
|
160
|
+
const t = editor.t;
|
|
161
|
+
// Render the view so its #element is available for the clickOutsideHandler.
|
|
162
|
+
view.render();
|
|
163
|
+
this.listenTo(view, 'submit', () => {
|
|
164
|
+
this._hideView();
|
|
165
|
+
});
|
|
166
|
+
this.listenTo(view, 'cancel', () => {
|
|
167
|
+
// https://github.com/ckeditor/ckeditor5/issues/6180
|
|
168
|
+
if (this._undoStepBatch.operations.length) {
|
|
169
|
+
editor.execute('undo', this._undoStepBatch);
|
|
170
|
+
}
|
|
171
|
+
this._hideView();
|
|
172
|
+
});
|
|
173
|
+
// Close the balloon on Esc key press.
|
|
174
|
+
view.keystrokes.set('Esc', (data, cancel) => {
|
|
175
|
+
this._hideView();
|
|
176
|
+
cancel();
|
|
177
|
+
});
|
|
178
|
+
// Close on click outside of balloon panel element.
|
|
179
|
+
clickOutsideHandler({
|
|
180
|
+
emitter: view,
|
|
181
|
+
activator: () => this._isViewInBalloon,
|
|
182
|
+
contextElements: [this._balloon.view.element],
|
|
183
|
+
callback: () => this._hideView()
|
|
184
|
+
});
|
|
185
|
+
const colorErrorText = getLocalizedColorErrorText(t);
|
|
186
|
+
const lengthErrorText = getLocalizedLengthErrorText(t);
|
|
187
|
+
// Create the "UI -> editor data" binding.
|
|
188
|
+
// These listeners update the editor data (via table commands) when any observable
|
|
189
|
+
// property of the view has changed. They also validate the value and display errors in the UI
|
|
190
|
+
// when necessary. This makes the view live, which means the changes are
|
|
191
|
+
// visible in the editing as soon as the user types or changes fields' values.
|
|
192
|
+
view.on('change:borderStyle', this._getPropertyChangeCallback('tableBorderStyle'));
|
|
193
|
+
view.on('change:borderColor', this._getValidatedPropertyChangeCallback({
|
|
194
|
+
viewField: view.borderColorInput,
|
|
195
|
+
commandName: 'tableBorderColor',
|
|
196
|
+
errorText: colorErrorText,
|
|
197
|
+
validator: colorFieldValidator
|
|
198
|
+
}));
|
|
199
|
+
view.on('change:borderWidth', this._getValidatedPropertyChangeCallback({
|
|
200
|
+
viewField: view.borderWidthInput,
|
|
201
|
+
commandName: 'tableBorderWidth',
|
|
202
|
+
errorText: lengthErrorText,
|
|
203
|
+
validator: lineWidthFieldValidator
|
|
204
|
+
}));
|
|
205
|
+
view.on('change:backgroundColor', this._getValidatedPropertyChangeCallback({
|
|
206
|
+
viewField: view.backgroundInput,
|
|
207
|
+
commandName: 'tableBackgroundColor',
|
|
208
|
+
errorText: colorErrorText,
|
|
209
|
+
validator: colorFieldValidator
|
|
210
|
+
}));
|
|
211
|
+
view.on('change:width', this._getValidatedPropertyChangeCallback({
|
|
212
|
+
viewField: view.widthInput,
|
|
213
|
+
commandName: 'tableWidth',
|
|
214
|
+
errorText: lengthErrorText,
|
|
215
|
+
validator: lengthFieldValidator
|
|
216
|
+
}));
|
|
217
|
+
view.on('change:height', this._getValidatedPropertyChangeCallback({
|
|
218
|
+
viewField: view.heightInput,
|
|
219
|
+
commandName: 'tableHeight',
|
|
220
|
+
errorText: lengthErrorText,
|
|
221
|
+
validator: lengthFieldValidator
|
|
222
|
+
}));
|
|
223
|
+
view.on('change:alignment', this._getPropertyChangeCallback('tableAlignment'));
|
|
224
|
+
return view;
|
|
225
|
+
}
|
|
226
|
+
/**
|
|
227
|
+
* In this method the "editor data -> UI" binding is happening.
|
|
228
|
+
*
|
|
229
|
+
* When executed, this method obtains selected table property values from various table commands
|
|
230
|
+
* and passes them to the {@link #view}.
|
|
231
|
+
*
|
|
232
|
+
* This way, the UI stays up–to–date with the editor data.
|
|
233
|
+
*/
|
|
234
|
+
_fillViewFormFromCommandValues() {
|
|
235
|
+
const commands = this.editor.commands;
|
|
236
|
+
const borderStyleCommand = commands.get('tableBorderStyle');
|
|
237
|
+
Object.entries(propertyToCommandMap)
|
|
238
|
+
.map(([property, commandName]) => {
|
|
239
|
+
const propertyKey = property;
|
|
240
|
+
const defaultValue = this.view === this._viewWithContentTableDefaults ?
|
|
241
|
+
this._defaultContentTableProperties[propertyKey] || '' :
|
|
242
|
+
this._defaultLayoutTableProperties[propertyKey] || '';
|
|
243
|
+
return [propertyKey, (commands.get(commandName).value || defaultValue)];
|
|
244
|
+
})
|
|
245
|
+
.forEach(([property, value]) => {
|
|
246
|
+
// Do not set the `border-color` and `border-width` fields if `border-style:none`.
|
|
247
|
+
if ((property === 'borderColor' || property === 'borderWidth') && borderStyleCommand.value === 'none') {
|
|
248
|
+
return;
|
|
249
|
+
}
|
|
250
|
+
this.view.set(property, value);
|
|
251
|
+
});
|
|
252
|
+
this._isReady = true;
|
|
253
|
+
}
|
|
254
|
+
/**
|
|
255
|
+
* Shows the {@link #view} in the {@link #_balloon}.
|
|
256
|
+
*
|
|
257
|
+
* **Note**: Each time a view is shown, the new {@link #_undoStepBatch} is created that contains
|
|
258
|
+
* all changes made to the document when the view is visible, allowing a single undo step
|
|
259
|
+
* for all of them.
|
|
260
|
+
*/
|
|
261
|
+
_showView() {
|
|
262
|
+
const editor = this.editor;
|
|
263
|
+
const viewTable = getSelectionAffectedTableWidget(editor.editing.view.document.selection);
|
|
264
|
+
const modelTable = viewTable && editor.editing.mapper.toModelElement(viewTable);
|
|
265
|
+
const useDefaults = !modelTable || modelTable.getAttribute('tableType') !== 'layout';
|
|
266
|
+
if (useDefaults && !this._viewWithContentTableDefaults) {
|
|
267
|
+
this._viewWithContentTableDefaults = this._createPropertiesView(this._defaultContentTableProperties);
|
|
268
|
+
}
|
|
269
|
+
else if (!useDefaults && !this._viewWithLayoutTableDefaults) {
|
|
270
|
+
this._viewWithLayoutTableDefaults = this._createPropertiesView(this._defaultLayoutTableProperties);
|
|
271
|
+
}
|
|
272
|
+
this.view = useDefaults ? this._viewWithContentTableDefaults : this._viewWithLayoutTableDefaults;
|
|
273
|
+
this.listenTo(editor.ui, 'update', () => {
|
|
274
|
+
this._updateView();
|
|
275
|
+
});
|
|
276
|
+
// Update the view with the model values.
|
|
277
|
+
this._fillViewFormFromCommandValues();
|
|
278
|
+
this._balloon.add({
|
|
279
|
+
view: this.view,
|
|
280
|
+
position: getBalloonTablePositionData(editor)
|
|
281
|
+
});
|
|
282
|
+
// Create a new batch. Clicking "Cancel" will undo this batch.
|
|
283
|
+
this._undoStepBatch = editor.model.createBatch();
|
|
284
|
+
// Basic a11y.
|
|
285
|
+
this.view.focus();
|
|
286
|
+
}
|
|
287
|
+
/**
|
|
288
|
+
* Removes the {@link #view} from the {@link #_balloon}.
|
|
289
|
+
*/
|
|
290
|
+
_hideView() {
|
|
291
|
+
const editor = this.editor;
|
|
292
|
+
this.stopListening(editor.ui, 'update');
|
|
293
|
+
this._isReady = false;
|
|
294
|
+
// Blur any input element before removing it from DOM to prevent issues in some browsers.
|
|
295
|
+
// See https://github.com/ckeditor/ckeditor5/issues/1501.
|
|
296
|
+
this.view.saveButtonView.focus();
|
|
297
|
+
this._balloon.remove(this.view);
|
|
298
|
+
// Make sure the focus is not lost in the process by putting it directly
|
|
299
|
+
// into the editing view.
|
|
300
|
+
this.editor.editing.view.focus();
|
|
301
|
+
}
|
|
302
|
+
/**
|
|
303
|
+
* Repositions the {@link #_balloon} or hides the {@link #view} if a table is no longer selected.
|
|
304
|
+
*/
|
|
305
|
+
_updateView() {
|
|
306
|
+
const editor = this.editor;
|
|
307
|
+
const viewDocument = editor.editing.view.document;
|
|
308
|
+
if (!getSelectionAffectedTableWidget(viewDocument.selection)) {
|
|
309
|
+
this._hideView();
|
|
310
|
+
}
|
|
311
|
+
else if (this._isViewVisible) {
|
|
312
|
+
repositionContextualBalloon(editor, 'table');
|
|
313
|
+
}
|
|
314
|
+
}
|
|
315
|
+
/**
|
|
316
|
+
* Returns `true` when the {@link #view} is the visible in the {@link #_balloon}.
|
|
317
|
+
*/
|
|
318
|
+
get _isViewVisible() {
|
|
319
|
+
return !!this.view && this._balloon.visibleView === this.view;
|
|
320
|
+
}
|
|
321
|
+
/**
|
|
322
|
+
* Returns `true` when the {@link #view} is in the {@link #_balloon}.
|
|
323
|
+
*/
|
|
324
|
+
get _isViewInBalloon() {
|
|
325
|
+
return !!this.view && this._balloon.hasView(this.view);
|
|
326
|
+
}
|
|
327
|
+
/**
|
|
328
|
+
* Creates a callback that when executed upon {@link #view view's} property change
|
|
329
|
+
* executes a related editor command with the new property value.
|
|
330
|
+
*
|
|
331
|
+
* If new value will be set to the default value, the command will not be executed.
|
|
332
|
+
*
|
|
333
|
+
* @param commandName The command that will be executed.
|
|
334
|
+
*/
|
|
335
|
+
_getPropertyChangeCallback(commandName) {
|
|
336
|
+
return (evt, propertyName, newValue) => {
|
|
337
|
+
// Do not execute the command on initial call (opening the table properties view).
|
|
338
|
+
if (!this._isReady) {
|
|
339
|
+
return;
|
|
340
|
+
}
|
|
341
|
+
this.editor.execute(commandName, {
|
|
342
|
+
value: newValue,
|
|
343
|
+
batch: this._undoStepBatch
|
|
344
|
+
});
|
|
345
|
+
};
|
|
346
|
+
}
|
|
347
|
+
/**
|
|
348
|
+
* Creates a callback that when executed upon {@link #view view's} property change:
|
|
349
|
+
* * executes a related editor command with the new property value if the value is valid,
|
|
350
|
+
* * or sets the error text next to the invalid field, if the value did not pass the validation.
|
|
351
|
+
*/
|
|
352
|
+
_getValidatedPropertyChangeCallback(options) {
|
|
353
|
+
const { commandName, viewField, validator, errorText } = options;
|
|
354
|
+
const setErrorTextDebounced = debounce(() => {
|
|
355
|
+
viewField.errorText = errorText;
|
|
356
|
+
}, ERROR_TEXT_TIMEOUT);
|
|
357
|
+
return (evt, propertyName, newValue) => {
|
|
358
|
+
setErrorTextDebounced.cancel();
|
|
359
|
+
// Do not execute the command on initial call (opening the table properties view).
|
|
360
|
+
if (!this._isReady) {
|
|
361
|
+
return;
|
|
362
|
+
}
|
|
363
|
+
if (validator(newValue)) {
|
|
364
|
+
this.editor.execute(commandName, {
|
|
365
|
+
value: newValue,
|
|
366
|
+
batch: this._undoStepBatch
|
|
367
|
+
});
|
|
368
|
+
viewField.errorText = null;
|
|
369
|
+
}
|
|
370
|
+
else {
|
|
371
|
+
setErrorTextDebounced();
|
|
372
|
+
}
|
|
373
|
+
};
|
|
374
|
+
}
|
|
375
|
+
}
|
|
@@ -142,10 +142,6 @@ export declare class TablePropertiesView extends View {
|
|
|
142
142
|
* The "Cancel" button view.
|
|
143
143
|
*/
|
|
144
144
|
cancelButtonView: ButtonView;
|
|
145
|
-
/**
|
|
146
|
-
* The Back button view displayed in the header.
|
|
147
|
-
*/
|
|
148
|
-
backButtonView: ButtonView;
|
|
149
145
|
/**
|
|
150
146
|
* A collection of views that can be focused in the form.
|
|
151
147
|
*/
|
|
@@ -205,10 +201,6 @@ export declare class TablePropertiesView extends View {
|
|
|
205
201
|
* * {@link #cancelButtonView}.
|
|
206
202
|
*/
|
|
207
203
|
private _createActionButtons;
|
|
208
|
-
/**
|
|
209
|
-
* Creates a back button view that cancels the form.
|
|
210
|
-
*/
|
|
211
|
-
private _createBackButton;
|
|
212
204
|
/**
|
|
213
205
|
* Provides localized labels for {@link #alignmentToolbar} buttons.
|
|
214
206
|
*/
|
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
*/
|
|
8
8
|
import { addListToDropdown, ButtonView, createLabeledDropdown, createLabeledInputText, FocusCycler, FormRowView, FormHeaderView, LabeledFieldView, LabelView, submitHandler, ToolbarView, View, ViewCollection } from 'ckeditor5/src/ui.js';
|
|
9
9
|
import { FocusTracker, KeystrokeHandler } from 'ckeditor5/src/utils.js';
|
|
10
|
-
import {
|
|
10
|
+
import { IconCancel, IconCheck, IconObjectCenter, IconObjectInlineLeft, IconObjectInlineRight } from 'ckeditor5/src/icons.js';
|
|
11
11
|
import { fillToolbar, getBorderStyleDefinitions, getBorderStyleLabels, getLabeledColorInputCreator } from '../../utils/ui/table-properties.js';
|
|
12
12
|
// eslint-disable-next-line ckeditor5-rules/ckeditor-imports
|
|
13
13
|
import '@ckeditor/ckeditor5-ui/theme/components/form/form.css';
|
|
@@ -71,10 +71,6 @@ export class TablePropertiesView extends View {
|
|
|
71
71
|
* The "Cancel" button view.
|
|
72
72
|
*/
|
|
73
73
|
cancelButtonView;
|
|
74
|
-
/**
|
|
75
|
-
* The Back button view displayed in the header.
|
|
76
|
-
*/
|
|
77
|
-
backButtonView;
|
|
78
74
|
/**
|
|
79
75
|
* A collection of views that can be focused in the form.
|
|
80
76
|
*/
|
|
@@ -119,7 +115,6 @@ export class TablePropertiesView extends View {
|
|
|
119
115
|
const { saveButtonView, cancelButtonView } = this._createActionButtons();
|
|
120
116
|
this.saveButtonView = saveButtonView;
|
|
121
117
|
this.cancelButtonView = cancelButtonView;
|
|
122
|
-
this.backButtonView = this._createBackButton();
|
|
123
118
|
this._focusables = new ViewCollection();
|
|
124
119
|
this._focusCycler = new FocusCycler({
|
|
125
120
|
focusables: this._focusables,
|
|
@@ -133,22 +128,29 @@ export class TablePropertiesView extends View {
|
|
|
133
128
|
}
|
|
134
129
|
});
|
|
135
130
|
// Form header.
|
|
136
|
-
|
|
131
|
+
this.children.add(new FormHeaderView(locale, {
|
|
137
132
|
label: this.t('Table properties')
|
|
138
|
-
});
|
|
139
|
-
headerView.children.add(this.backButtonView, 0);
|
|
140
|
-
this.children.add(headerView);
|
|
133
|
+
}));
|
|
141
134
|
// Border row.
|
|
142
135
|
this.children.add(new FormRowView(locale, {
|
|
143
136
|
labelView: borderRowLabel,
|
|
144
137
|
children: [
|
|
145
138
|
borderRowLabel,
|
|
146
139
|
borderStyleDropdown,
|
|
147
|
-
|
|
148
|
-
|
|
140
|
+
borderColorInput,
|
|
141
|
+
borderWidthInput
|
|
149
142
|
],
|
|
150
143
|
class: 'ck-table-form__border-row'
|
|
151
144
|
}));
|
|
145
|
+
// Background row.
|
|
146
|
+
this.children.add(new FormRowView(locale, {
|
|
147
|
+
labelView: backgroundRowLabel,
|
|
148
|
+
children: [
|
|
149
|
+
backgroundRowLabel,
|
|
150
|
+
backgroundInput
|
|
151
|
+
],
|
|
152
|
+
class: 'ck-table-form__background-row'
|
|
153
|
+
}));
|
|
152
154
|
this.children.add(new FormRowView(locale, {
|
|
153
155
|
children: [
|
|
154
156
|
// Dimensions row.
|
|
@@ -162,31 +164,22 @@ export class TablePropertiesView extends View {
|
|
|
162
164
|
],
|
|
163
165
|
class: 'ck-table-form__dimensions-row'
|
|
164
166
|
}),
|
|
165
|
-
//
|
|
167
|
+
// Alignment row.
|
|
166
168
|
new FormRowView(locale, {
|
|
167
|
-
labelView:
|
|
169
|
+
labelView: alignmentLabel,
|
|
168
170
|
children: [
|
|
169
|
-
|
|
170
|
-
|
|
171
|
+
alignmentLabel,
|
|
172
|
+
alignmentToolbar
|
|
171
173
|
],
|
|
172
|
-
class: 'ck-table-
|
|
174
|
+
class: 'ck-table-properties-form__alignment-row'
|
|
173
175
|
})
|
|
174
176
|
]
|
|
175
177
|
}));
|
|
176
|
-
// Alignment row.
|
|
177
|
-
this.children.add(new FormRowView(locale, {
|
|
178
|
-
labelView: alignmentLabel,
|
|
179
|
-
children: [
|
|
180
|
-
alignmentLabel,
|
|
181
|
-
alignmentToolbar
|
|
182
|
-
],
|
|
183
|
-
class: 'ck-table-properties-form__alignment-row'
|
|
184
|
-
}));
|
|
185
178
|
// Action row.
|
|
186
179
|
this.children.add(new FormRowView(locale, {
|
|
187
180
|
children: [
|
|
188
|
-
this.
|
|
189
|
-
this.
|
|
181
|
+
this.saveButtonView,
|
|
182
|
+
this.cancelButtonView
|
|
190
183
|
],
|
|
191
184
|
class: 'ck-table-form__action-row'
|
|
192
185
|
}));
|
|
@@ -221,15 +214,14 @@ export class TablePropertiesView extends View {
|
|
|
221
214
|
});
|
|
222
215
|
[
|
|
223
216
|
this.borderStyleDropdown,
|
|
224
|
-
this.borderWidthInput,
|
|
225
217
|
this.borderColorInput,
|
|
218
|
+
this.borderWidthInput,
|
|
219
|
+
this.backgroundInput,
|
|
226
220
|
this.widthInput,
|
|
227
221
|
this.heightInput,
|
|
228
|
-
this.backgroundInput,
|
|
229
222
|
this.alignmentToolbar,
|
|
230
|
-
this.cancelButtonView,
|
|
231
223
|
this.saveButtonView,
|
|
232
|
-
this.
|
|
224
|
+
this.cancelButtonView
|
|
233
225
|
].forEach(view => {
|
|
234
226
|
// Register the view as focusable.
|
|
235
227
|
this._focusables.add(view);
|
|
@@ -441,7 +433,7 @@ export class TablePropertiesView extends View {
|
|
|
441
433
|
const t = this.t;
|
|
442
434
|
// -- Label ---------------------------------------------------
|
|
443
435
|
const alignmentLabel = new LabelView(locale);
|
|
444
|
-
alignmentLabel.text = t('
|
|
436
|
+
alignmentLabel.text = t('Alignment');
|
|
445
437
|
// -- Toolbar ---------------------------------------------------
|
|
446
438
|
const alignmentToolbar = new ToolbarView(locale);
|
|
447
439
|
alignmentToolbar.set({
|
|
@@ -454,9 +446,7 @@ export class TablePropertiesView extends View {
|
|
|
454
446
|
icons: {
|
|
455
447
|
left: IconObjectInlineLeft,
|
|
456
448
|
center: IconObjectCenter,
|
|
457
|
-
right: IconObjectInlineRight
|
|
458
|
-
blockLeft: IconObjectLeft,
|
|
459
|
-
blockRight: IconObjectRight
|
|
449
|
+
right: IconObjectInlineRight
|
|
460
450
|
},
|
|
461
451
|
toolbar: alignmentToolbar,
|
|
462
452
|
labels: this._alignmentLabels,
|
|
@@ -488,7 +478,8 @@ export class TablePropertiesView extends View {
|
|
|
488
478
|
];
|
|
489
479
|
saveButtonView.set({
|
|
490
480
|
label: t('Save'),
|
|
491
|
-
|
|
481
|
+
icon: IconCheck,
|
|
482
|
+
class: 'ck-button-save',
|
|
492
483
|
type: 'submit',
|
|
493
484
|
withText: true
|
|
494
485
|
});
|
|
@@ -497,6 +488,8 @@ export class TablePropertiesView extends View {
|
|
|
497
488
|
});
|
|
498
489
|
cancelButtonView.set({
|
|
499
490
|
label: t('Cancel'),
|
|
491
|
+
icon: IconCancel,
|
|
492
|
+
class: 'ck-button-cancel',
|
|
500
493
|
withText: true
|
|
501
494
|
});
|
|
502
495
|
cancelButtonView.delegate('execute').to(this, 'cancel');
|
|
@@ -504,37 +497,22 @@ export class TablePropertiesView extends View {
|
|
|
504
497
|
saveButtonView, cancelButtonView
|
|
505
498
|
};
|
|
506
499
|
}
|
|
507
|
-
/**
|
|
508
|
-
* Creates a back button view that cancels the form.
|
|
509
|
-
*/
|
|
510
|
-
_createBackButton() {
|
|
511
|
-
const t = this.locale.t;
|
|
512
|
-
const backButton = new ButtonView(this.locale);
|
|
513
|
-
backButton.set({
|
|
514
|
-
class: 'ck-button-back',
|
|
515
|
-
label: t('Back'),
|
|
516
|
-
icon: IconPreviousArrow,
|
|
517
|
-
tooltip: true
|
|
518
|
-
});
|
|
519
|
-
backButton.delegate('execute').to(this, 'cancel');
|
|
520
|
-
return backButton;
|
|
521
|
-
}
|
|
522
500
|
/**
|
|
523
501
|
* Provides localized labels for {@link #alignmentToolbar} buttons.
|
|
524
502
|
*/
|
|
525
503
|
get _alignmentLabels() {
|
|
526
504
|
const locale = this.locale;
|
|
527
505
|
const t = this.t;
|
|
528
|
-
const
|
|
529
|
-
const
|
|
530
|
-
const
|
|
531
|
-
const center = t('Center table with no text wrapping');
|
|
532
|
-
const right = t('Align table to the right with text wrapping');
|
|
506
|
+
const left = t('Align table to the left');
|
|
507
|
+
const center = t('Center table');
|
|
508
|
+
const right = t('Align table to the right');
|
|
533
509
|
// Returns object with a proper order of labels.
|
|
534
510
|
if (locale.uiLanguageDirection === 'rtl') {
|
|
535
|
-
return { right,
|
|
511
|
+
return { right, center, left };
|
|
512
|
+
}
|
|
513
|
+
else {
|
|
514
|
+
return { left, center, right };
|
|
536
515
|
}
|
|
537
|
-
return { blockLeft, center, blockRight, left, right };
|
|
538
516
|
}
|
|
539
517
|
}
|
|
540
518
|
function isBorderStyleSet(value) {
|