@ckeditor/ckeditor5-font 48.2.0-alpha.7 → 48.3.0-alpha.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/index.js CHANGED
@@ -2,1658 +2,1672 @@
2
2
  * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
3
3
  * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
4
4
  */
5
- import { Command, Plugin } from '@ckeditor/ckeditor5-core/dist/index.js';
6
- import { ModelDocumentSelection, isLengthStyleValue, isPercentageStyleValue, addBackgroundStylesRules } from '@ckeditor/ckeditor5-engine/dist/index.js';
7
- import { ColorSelectorView, createDropdown, addListToDropdown, MenuBarMenuView, MenuBarMenuListView, MenuBarMenuListItemView, MenuBarMenuListItemButtonView, UIModel, normalizeColorOptions, getLocalizedColorOptions, focusChildOnDropdownOpen } from '@ckeditor/ckeditor5-ui/dist/index.js';
8
- import { Collection, CKEditorError } from '@ckeditor/ckeditor5-utils/dist/index.js';
9
- import { IconFontFamily, IconFontSize, IconFontColor, IconFontBackground } from '@ckeditor/ckeditor5-icons/dist/index.js';
5
+ import { Command, Plugin } from "@ckeditor/ckeditor5-core";
6
+ import { ModelDocumentSelection, addBackgroundStylesRules, isLengthStyleValue, isPercentageStyleValue } from "@ckeditor/ckeditor5-engine";
7
+ import { ColorSelectorView, MenuBarMenuListItemButtonView, MenuBarMenuListItemView, MenuBarMenuListView, MenuBarMenuView, UIModel, addListToDropdown, createDropdown, focusChildOnDropdownOpen, getLocalizedColorOptions, normalizeColorOptions } from "@ckeditor/ckeditor5-ui";
8
+ import { CKEditorError, Collection } from "@ckeditor/ckeditor5-utils";
9
+ import { IconFontBackground, IconFontColor, IconFontFamily, IconFontSize } from "@ckeditor/ckeditor5-icons";
10
10
 
11
11
  /**
12
- * The base font command.
13
- */ class FontCommand extends Command {
14
- /**
15
- * A model attribute on which this command operates.
16
- */ attributeKey;
17
- /**
18
- * Creates an instance of the command.
19
- *
20
- * @param editor Editor instance.
21
- * @param attributeKey The name of a model attribute on which this command operates.
22
- */ constructor(editor, attributeKey){
23
- super(editor);
24
- this.attributeKey = attributeKey;
25
- }
26
- /**
27
- * @inheritDoc
28
- */ refresh() {
29
- const model = this.editor.model;
30
- const doc = model.document;
31
- this.value = doc.selection.getAttribute(this.attributeKey);
32
- this.isEnabled = model.schema.checkAttributeInSelection(doc.selection, this.attributeKey);
33
- }
34
- /**
35
- * Executes the command. Applies the `value` of the {@link #attributeKey} to the selection.
36
- * If no `value` is passed, it removes the attribute from the selection.
37
- *
38
- * @param options Options for the executed command.
39
- * @param options.value The value to apply.
40
- * @fires execute
41
- */ execute(options = {}) {
42
- const model = this.editor.model;
43
- const document = model.document;
44
- const selection = document.selection;
45
- const value = options.value;
46
- const batch = options.batch;
47
- const updateAttribute = (writer)=>{
48
- if (selection.isCollapsed) {
49
- if (value) {
50
- writer.setSelectionAttribute(this.attributeKey, value);
51
- } else {
52
- writer.removeSelectionAttribute(this.attributeKey);
53
- }
54
- } else {
55
- const ranges = model.schema.getValidRanges(selection.getRanges(), this.attributeKey, {
56
- includeEmptyRanges: true
57
- });
58
- for (const range of ranges){
59
- let itemOrRange = range;
60
- let attributeKey = this.attributeKey;
61
- if (range.isCollapsed) {
62
- itemOrRange = range.start.parent;
63
- attributeKey = ModelDocumentSelection._getStoreAttributeKey(this.attributeKey);
64
- }
65
- if (value) {
66
- writer.setAttribute(attributeKey, value, itemOrRange);
67
- } else {
68
- writer.removeAttribute(attributeKey, itemOrRange);
69
- }
70
- }
71
- }
72
- };
73
- // In some scenarios, you may want to use a single undo step for multiple changes (e.g. in color picker).
74
- if (batch) {
75
- model.enqueueChange(batch, (writer)=>{
76
- updateAttribute(writer);
77
- });
78
- } else {
79
- model.change((writer)=>{
80
- updateAttribute(writer);
81
- });
82
- }
83
- }
84
- }
12
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
13
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
14
+ */
15
+ /**
16
+ * @module font/fontcommand
17
+ */
18
+ /**
19
+ * The base font command.
20
+ */
21
+ var FontCommand = class extends Command {
22
+ /**
23
+ * A model attribute on which this command operates.
24
+ */
25
+ attributeKey;
26
+ /**
27
+ * Creates an instance of the command.
28
+ *
29
+ * @param editor Editor instance.
30
+ * @param attributeKey The name of a model attribute on which this command operates.
31
+ */
32
+ constructor(editor, attributeKey) {
33
+ super(editor);
34
+ this.attributeKey = attributeKey;
35
+ }
36
+ /**
37
+ * @inheritDoc
38
+ */
39
+ refresh() {
40
+ const model = this.editor.model;
41
+ const doc = model.document;
42
+ this.value = doc.selection.getAttribute(this.attributeKey);
43
+ this.isEnabled = model.schema.checkAttributeInSelection(doc.selection, this.attributeKey);
44
+ }
45
+ /**
46
+ * Executes the command. Applies the `value` of the {@link #attributeKey} to the selection.
47
+ * If no `value` is passed, it removes the attribute from the selection.
48
+ *
49
+ * @param options Options for the executed command.
50
+ * @param options.value The value to apply.
51
+ * @fires execute
52
+ */
53
+ execute(options = {}) {
54
+ const model = this.editor.model;
55
+ const selection = model.document.selection;
56
+ const value = options.value;
57
+ const batch = options.batch;
58
+ const updateAttribute = (writer) => {
59
+ if (selection.isCollapsed) if (value) writer.setSelectionAttribute(this.attributeKey, value);
60
+ else writer.removeSelectionAttribute(this.attributeKey);
61
+ else {
62
+ const ranges = model.schema.getValidRanges(selection.getRanges(), this.attributeKey, { includeEmptyRanges: true });
63
+ for (const range of ranges) {
64
+ let itemOrRange = range;
65
+ let attributeKey = this.attributeKey;
66
+ if (range.isCollapsed) {
67
+ itemOrRange = range.start.parent;
68
+ attributeKey = ModelDocumentSelection._getStoreAttributeKey(this.attributeKey);
69
+ }
70
+ if (value) writer.setAttribute(attributeKey, value, itemOrRange);
71
+ else writer.removeAttribute(attributeKey, itemOrRange);
72
+ }
73
+ }
74
+ };
75
+ if (batch) model.enqueueChange(batch, (writer) => {
76
+ updateAttribute(writer);
77
+ });
78
+ else model.change((writer) => {
79
+ updateAttribute(writer);
80
+ });
81
+ }
82
+ };
85
83
 
86
84
  /**
87
- * The name of the font size plugin.
88
- */ const FONT_SIZE = 'fontSize';
89
- /**
90
- * The name of the font family plugin.
91
- */ const FONT_FAMILY = 'fontFamily';
92
- /**
93
- * The name of the font color plugin.
94
- */ const FONT_COLOR = 'fontColor';
95
- /**
96
- * The name of the font background color plugin.
97
- */ const FONT_BACKGROUND_COLOR = 'fontBackgroundColor';
98
- /**
99
- * Builds a proper converter definition out of input data.
100
- *
101
- * @internal
102
- */ function buildDefinition(modelAttributeKey, options) {
103
- const definition = {
104
- model: {
105
- key: modelAttributeKey,
106
- values: []
107
- },
108
- view: {},
109
- upcastAlso: {}
110
- };
111
- for (const option of options){
112
- definition.model.values.push(option.model);
113
- definition.view[option.model] = option.view;
114
- if (option.upcastAlso) {
115
- definition.upcastAlso[option.model] = option.upcastAlso;
116
- }
117
- }
118
- return definition;
85
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
86
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
87
+ */
88
+ /**
89
+ * The name of the font size plugin.
90
+ */
91
+ const FONT_SIZE = "fontSize";
92
+ /**
93
+ * The name of the font family plugin.
94
+ */
95
+ const FONT_FAMILY = "fontFamily";
96
+ /**
97
+ * The name of the font color plugin.
98
+ */
99
+ const FONT_COLOR = "fontColor";
100
+ /**
101
+ * The name of the font background color plugin.
102
+ */
103
+ const FONT_BACKGROUND_COLOR = "fontBackgroundColor";
104
+ /**
105
+ * Builds a proper converter definition out of input data.
106
+ *
107
+ * @internal
108
+ */
109
+ function buildDefinition(modelAttributeKey, options) {
110
+ const definition = {
111
+ model: {
112
+ key: modelAttributeKey,
113
+ values: []
114
+ },
115
+ view: {},
116
+ upcastAlso: {}
117
+ };
118
+ for (const option of options) {
119
+ definition.model.values.push(option.model);
120
+ definition.view[option.model] = option.view;
121
+ if (option.upcastAlso) definition.upcastAlso[option.model] = option.upcastAlso;
122
+ }
123
+ return definition;
119
124
  }
120
125
  /**
121
- * A {@link module:font/fontcolor~FontColor font color} and
122
- * {@link module:font/fontbackgroundcolor~FontBackgroundColor font background color} helper
123
- * responsible for upcasting data to the model.
124
- *
125
- * **Note**: The `styleAttr` parameter should be either `'color'` or `'background-color'`.
126
- *
127
- * @internal
128
- */ function renderUpcastAttribute(styleAttr) {
129
- return (viewElement)=>normalizeColorCode(viewElement.getStyle(styleAttr));
126
+ * A {@link module:font/fontcolor~FontColor font color} and
127
+ * {@link module:font/fontbackgroundcolor~FontBackgroundColor font background color} helper
128
+ * responsible for upcasting data to the model.
129
+ *
130
+ * **Note**: The `styleAttr` parameter should be either `'color'` or `'background-color'`.
131
+ *
132
+ * @internal
133
+ */
134
+ function renderUpcastAttribute(styleAttr) {
135
+ return (viewElement) => normalizeColorCode(viewElement.getStyle(styleAttr));
130
136
  }
131
137
  /**
132
- * A {@link module:font/fontcolor~FontColor font color} and
133
- * {@link module:font/fontbackgroundcolor~FontBackgroundColor font background color} helper
134
- * responsible for downcasting a color attribute to a `<span>` element.
135
- *
136
- * **Note**: The `styleAttr` parameter should be either `'color'` or `'background-color'`.
137
- *
138
- * @internal
139
- */ function renderDowncastElement(styleAttr) {
140
- return (modelAttributeValue, { writer })=>writer.createAttributeElement('span', {
141
- style: `${styleAttr}:${modelAttributeValue}`
142
- }, {
143
- priority: 7
144
- });
138
+ * A {@link module:font/fontcolor~FontColor font color} and
139
+ * {@link module:font/fontbackgroundcolor~FontBackgroundColor font background color} helper
140
+ * responsible for downcasting a color attribute to a `<span>` element.
141
+ *
142
+ * **Note**: The `styleAttr` parameter should be either `'color'` or `'background-color'`.
143
+ *
144
+ * @internal
145
+ */
146
+ function renderDowncastElement(styleAttr) {
147
+ return (modelAttributeValue, { writer }) => writer.createAttributeElement("span", { style: `${styleAttr}:${modelAttributeValue}` }, { priority: 7 });
145
148
  }
146
149
  /**
147
- * A helper that adds {@link module:ui/colorselector/colorselectorview~ColorSelectorView} to the color dropdown with proper initial values.
148
- *
149
- * @param options Configuration options
150
- * @param options.dropdownView The dropdown view to which a {@link module:ui/colorselector/colorselectorview~ColorSelectorView}
151
- * will be added.
152
- * @param options.colors An array with definitions representing colors to be displayed in the color selector.
153
- * @param options.columns The number of columns in the color grid.
154
- * @param options.removeButtonLabel The label for the button responsible for removing the color.
155
- * @param options.colorPickerLabel The label for the color picker button.
156
- * @param options.documentColorsLabel The label for the section with document colors.
157
- * @param options.documentColorsCount The number of document colors inside the dropdown.
158
- * @param options.colorPickerViewConfig Configuration of the color picker view.
159
- * @returns The new color selector view.
160
- * @internal
161
- */ function addColorSelectorToDropdown({ dropdownView, colors, columns, removeButtonLabel, colorPickerLabel, documentColorsLabel, documentColorsCount, colorPickerViewConfig }) {
162
- const locale = dropdownView.locale;
163
- const colorSelectorView = new ColorSelectorView(locale, {
164
- colors,
165
- columns,
166
- removeButtonLabel,
167
- colorPickerLabel,
168
- documentColorsLabel,
169
- documentColorsCount,
170
- colorPickerViewConfig
171
- });
172
- dropdownView.colorSelectorView = colorSelectorView;
173
- dropdownView.panelView.children.add(colorSelectorView);
174
- return colorSelectorView;
150
+ * A helper that adds {@link module:ui/colorselector/colorselectorview~ColorSelectorView} to the color dropdown with proper initial values.
151
+ *
152
+ * @param options Configuration options
153
+ * @param options.dropdownView The dropdown view to which a {@link module:ui/colorselector/colorselectorview~ColorSelectorView}
154
+ * will be added.
155
+ * @param options.colors An array with definitions representing colors to be displayed in the color selector.
156
+ * @param options.columns The number of columns in the color grid.
157
+ * @param options.removeButtonLabel The label for the button responsible for removing the color.
158
+ * @param options.colorPickerLabel The label for the color picker button.
159
+ * @param options.documentColorsLabel The label for the section with document colors.
160
+ * @param options.documentColorsCount The number of document colors inside the dropdown.
161
+ * @param options.colorPickerViewConfig Configuration of the color picker view.
162
+ * @returns The new color selector view.
163
+ * @internal
164
+ */
165
+ function addColorSelectorToDropdown({ dropdownView, colors, columns, removeButtonLabel, colorPickerLabel, documentColorsLabel, documentColorsCount, colorPickerViewConfig }) {
166
+ const locale = dropdownView.locale;
167
+ const colorSelectorView = new ColorSelectorView(locale, {
168
+ colors,
169
+ columns,
170
+ removeButtonLabel,
171
+ colorPickerLabel,
172
+ documentColorsLabel,
173
+ documentColorsCount,
174
+ colorPickerViewConfig
175
+ });
176
+ dropdownView.colorSelectorView = colorSelectorView;
177
+ dropdownView.panelView.children.add(colorSelectorView);
178
+ return colorSelectorView;
175
179
  }
176
180
  /**
177
- * Fixes the color value string.
178
- */ function normalizeColorCode(value) {
179
- return value.replace(/\s/g, '');
181
+ * Fixes the color value string.
182
+ */
183
+ function normalizeColorCode(value) {
184
+ return value.replace(/\s/g, "");
180
185
  }
181
186
 
182
187
  /**
183
- * The font family command. It is used by {@link module:font/fontfamily/fontfamilyediting~FontFamilyEditing}
184
- * to apply the font family.
185
- *
186
- * ```ts
187
- * editor.execute( 'fontFamily', { value: 'Arial' } );
188
- * ```
189
- *
190
- * **Note**: Executing the command without the value removes the attribute from the model.
191
- */ class FontFamilyCommand extends FontCommand {
192
- /**
193
- * @inheritDoc
194
- */ constructor(editor){
195
- super(editor, FONT_FAMILY);
196
- }
197
- }
188
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
189
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
190
+ */
191
+ /**
192
+ * The font family command. It is used by {@link module:font/fontfamily/fontfamilyediting~FontFamilyEditing}
193
+ * to apply the font family.
194
+ *
195
+ * ```ts
196
+ * editor.execute( 'fontFamily', { value: 'Arial' } );
197
+ * ```
198
+ *
199
+ * **Note**: Executing the command without the value removes the attribute from the model.
200
+ */
201
+ var FontFamilyCommand = class extends FontCommand {
202
+ /**
203
+ * @inheritDoc
204
+ */
205
+ constructor(editor) {
206
+ super(editor, FONT_FAMILY);
207
+ }
208
+ };
198
209
 
199
210
  /**
200
- * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
201
- * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
202
- */ /**
203
- * @module font/fontfamily/utils
204
- */ /**
205
- * Normalizes the {@link module:font/fontconfig~FontFamilyConfig#options configuration options}
206
- * to the {@link module:font/fontconfig~FontFamilyOption} format.
207
- *
208
- * @param configuredOptions An array of options taken from the configuration.
209
- * @internal
210
- */ function normalizeOptions$1(configuredOptions) {
211
- // Convert options to objects.
212
- return configuredOptions.map(getOptionDefinition$1)// Filter out undefined values that `getOptionDefinition` might return.
213
- .filter((option)=>option !== undefined);
211
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
212
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
213
+ */
214
+ /**
215
+ * Normalizes the {@link module:font/fontconfig~FontFamilyConfig#options configuration options}
216
+ * to the {@link module:font/fontconfig~FontFamilyOption} format.
217
+ *
218
+ * @param configuredOptions An array of options taken from the configuration.
219
+ * @internal
220
+ */
221
+ function normalizeOptions(configuredOptions) {
222
+ return configuredOptions.map(getOptionDefinition$1).filter((option) => option !== void 0);
214
223
  }
215
224
  /**
216
- * Normalizes the CSS `font-family` property value to an array of unquoted and trimmed font faces.
217
- *
218
- * @internal
219
- */ function normalizeFontFamilies(fontDefinition) {
220
- return fontDefinition.replace(/["']/g, '').split(',').map((name)=>name.trim());
225
+ * Normalizes the CSS `font-family` property value to an array of unquoted and trimmed font faces.
226
+ *
227
+ * @internal
228
+ */
229
+ function normalizeFontFamilies(fontDefinition) {
230
+ return fontDefinition.replace(/["']/g, "").split(",").map((name) => name.trim());
221
231
  }
222
232
  /**
223
- * Returns an option definition either created from string shortcut.
224
- * If object is passed then this method will return it without alternating it. Returns undefined for item than cannot be parsed.
225
- *
226
- */ function getOptionDefinition$1(option) {
227
- // Treat any object as full item definition provided by user in configuration.
228
- if (typeof option === 'object') {
229
- return option;
230
- }
231
- // Handle 'default' string as a special case. It will be used to remove the fontFamily attribute.
232
- if (option === 'default') {
233
- return {
234
- title: 'Default',
235
- model: undefined
236
- };
237
- }
238
- // Ignore values that we cannot parse to a definition.
239
- if (typeof option !== 'string') {
240
- return undefined;
241
- }
242
- // Return font family definition from font string.
243
- return generateFontPreset(option);
233
+ * Returns an option definition either created from string shortcut.
234
+ * If object is passed then this method will return it without alternating it. Returns undefined for item than cannot be parsed.
235
+ *
236
+ */
237
+ function getOptionDefinition$1(option) {
238
+ if (typeof option === "object") return option;
239
+ if (option === "default") return {
240
+ title: "Default",
241
+ model: void 0
242
+ };
243
+ if (typeof option !== "string") return;
244
+ return generateFontPreset(option);
244
245
  }
245
246
  /**
246
- * Creates a predefined preset for pixel size. It deconstructs font-family like string into full configuration option.
247
- * A font definition is passed as coma delimited set of font family names. Font names might be quoted.
248
- *
249
- * @param fontDefinition A font definition form configuration.
250
- */ function generateFontPreset(fontDefinition) {
251
- // Remove quotes from font names. They will be normalized later.
252
- const fontNames = normalizeFontFamilies(fontDefinition);
253
- // The first matched font name will be used as dropdown list item title and as model value.
254
- const firstFontName = fontNames[0];
255
- // CSS-compatible font names.
256
- const cssFontNames = fontNames.map(normalizeFontNameForCSS).join(', ');
257
- return {
258
- title: firstFontName,
259
- model: cssFontNames,
260
- view: {
261
- name: 'span',
262
- styles: {
263
- 'font-family': cssFontNames
264
- },
265
- priority: 7
266
- }
267
- };
247
+ * Creates a predefined preset for pixel size. It deconstructs font-family like string into full configuration option.
248
+ * A font definition is passed as coma delimited set of font family names. Font names might be quoted.
249
+ *
250
+ * @param fontDefinition A font definition form configuration.
251
+ */
252
+ function generateFontPreset(fontDefinition) {
253
+ const fontNames = normalizeFontFamilies(fontDefinition);
254
+ const firstFontName = fontNames[0];
255
+ const cssFontNames = fontNames.map(normalizeFontNameForCSS).join(", ");
256
+ return {
257
+ title: firstFontName,
258
+ model: cssFontNames,
259
+ view: {
260
+ name: "span",
261
+ styles: { "font-family": cssFontNames },
262
+ priority: 7
263
+ }
264
+ };
268
265
  }
269
266
  /**
270
- * Normalizes font name for the style attribute. It adds braces (') if font name contains spaces.
271
- */ function normalizeFontNameForCSS(fontName) {
272
- fontName = fontName.trim();
273
- // Compound font names should be quoted.
274
- if (fontName.indexOf(' ') > 0) {
275
- fontName = `'${fontName}'`;
276
- }
277
- return fontName;
267
+ * Normalizes font name for the style attribute. It adds braces (') if font name contains spaces.
268
+ */
269
+ function normalizeFontNameForCSS(fontName) {
270
+ fontName = fontName.trim();
271
+ if (fontName.indexOf(" ") > 0) fontName = `'${fontName}'`;
272
+ return fontName;
278
273
  }
279
274
 
280
275
  /**
281
- * The font family editing feature.
282
- *
283
- * It introduces the {@link module:font/fontfamily/fontfamilycommand~FontFamilyCommand command} and
284
- * the `fontFamily` attribute in the {@link module:engine/model/model~Model model} which renders
285
- * in the {@link module:engine/view/view view} as an inline `<span>` element (`<span style="font-family: Arial">`),
286
- * depending on the {@link module:font/fontconfig~FontFamilyConfig configuration}.
287
- */ class FontFamilyEditing extends Plugin {
288
- /**
289
- * @inheritDoc
290
- */ static get pluginName() {
291
- return 'FontFamilyEditing';
292
- }
293
- /**
294
- * @inheritDoc
295
- */ static get isOfficialPlugin() {
296
- return true;
297
- }
298
- /**
299
- * @inheritDoc
300
- */ constructor(editor){
301
- super(editor);
302
- // Define default configuration using font families shortcuts.
303
- editor.config.define(FONT_FAMILY, {
304
- options: [
305
- 'default',
306
- 'Arial, Helvetica, sans-serif',
307
- 'Courier New, Courier, monospace',
308
- 'Georgia, serif',
309
- 'Lucida Sans Unicode, Lucida Grande, sans-serif',
310
- 'Tahoma, Geneva, sans-serif',
311
- 'Times New Roman, Times, serif',
312
- 'Trebuchet MS, Helvetica, sans-serif',
313
- 'Verdana, Geneva, sans-serif'
314
- ],
315
- supportAllValues: false
316
- });
317
- }
318
- /**
319
- * @inheritDoc
320
- */ init() {
321
- const editor = this.editor;
322
- // Allow fontFamily attribute on text nodes.
323
- editor.model.schema.extend('$text', {
324
- allowAttributes: FONT_FAMILY
325
- });
326
- editor.model.schema.setAttributeProperties(FONT_FAMILY, {
327
- isFormatting: true,
328
- copyOnEnter: true
329
- });
330
- // Get configured font family options without "default" option.
331
- const options = normalizeOptions$1(editor.config.get('fontFamily.options')).filter((item)=>item.model);
332
- const definition = buildDefinition(FONT_FAMILY, options);
333
- // Set-up the two-way conversion.
334
- if (editor.config.get('fontFamily.supportAllValues')) {
335
- this._prepareAnyValueConverters();
336
- this._prepareCompatibilityConverter();
337
- } else {
338
- editor.conversion.attributeToElement(definition);
339
- }
340
- editor.commands.add(FONT_FAMILY, new FontFamilyCommand(editor));
341
- }
342
- /**
343
- * These converters enable keeping any value found as `style="font-family: *"` as a value of an attribute on a text even
344
- * if it is not defined in the plugin configuration.
345
- */ _prepareAnyValueConverters() {
346
- const editor = this.editor;
347
- editor.conversion.for('downcast').attributeToElement({
348
- model: FONT_FAMILY,
349
- view: (attributeValue, { writer })=>{
350
- return writer.createAttributeElement('span', {
351
- style: 'font-family:' + attributeValue
352
- }, {
353
- priority: 7
354
- });
355
- }
356
- });
357
- editor.conversion.for('upcast').elementToAttribute({
358
- model: {
359
- key: FONT_FAMILY,
360
- value: (viewElement)=>viewElement.getStyle('font-family')
361
- },
362
- view: {
363
- name: 'span',
364
- styles: {
365
- 'font-family': /.*/
366
- }
367
- }
368
- });
369
- }
370
- /**
371
- * Adds support for legacy `<font face="..">` formatting.
372
- */ _prepareCompatibilityConverter() {
373
- const editor = this.editor;
374
- editor.conversion.for('upcast').elementToAttribute({
375
- view: {
376
- name: 'font',
377
- attributes: {
378
- 'face': /.*/
379
- }
380
- },
381
- model: {
382
- key: FONT_FAMILY,
383
- value: (viewElement)=>viewElement.getAttribute('face')
384
- }
385
- });
386
- }
387
- }
276
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
277
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
278
+ */
279
+ /**
280
+ * @module font/fontfamily/fontfamilyediting
281
+ */
282
+ /**
283
+ * The font family editing feature.
284
+ *
285
+ * It introduces the {@link module:font/fontfamily/fontfamilycommand~FontFamilyCommand command} and
286
+ * the `fontFamily` attribute in the {@link module:engine/model/model~Model model} which renders
287
+ * in the {@link module:engine/view/view view} as an inline `<span>` element (`<span style="font-family: Arial">`),
288
+ * depending on the {@link module:font/fontconfig~FontFamilyConfig configuration}.
289
+ */
290
+ var FontFamilyEditing = class extends Plugin {
291
+ /**
292
+ * @inheritDoc
293
+ */
294
+ static get pluginName() {
295
+ return "FontFamilyEditing";
296
+ }
297
+ /**
298
+ * @inheritDoc
299
+ */
300
+ static get isOfficialPlugin() {
301
+ return true;
302
+ }
303
+ /**
304
+ * @inheritDoc
305
+ */
306
+ constructor(editor) {
307
+ super(editor);
308
+ editor.config.define(FONT_FAMILY, {
309
+ options: [
310
+ "default",
311
+ "Arial, Helvetica, sans-serif",
312
+ "Courier New, Courier, monospace",
313
+ "Georgia, serif",
314
+ "Lucida Sans Unicode, Lucida Grande, sans-serif",
315
+ "Tahoma, Geneva, sans-serif",
316
+ "Times New Roman, Times, serif",
317
+ "Trebuchet MS, Helvetica, sans-serif",
318
+ "Verdana, Geneva, sans-serif"
319
+ ],
320
+ supportAllValues: false
321
+ });
322
+ }
323
+ /**
324
+ * @inheritDoc
325
+ */
326
+ init() {
327
+ const editor = this.editor;
328
+ editor.model.schema.extend("$text", { allowAttributes: FONT_FAMILY });
329
+ editor.model.schema.setAttributeProperties(FONT_FAMILY, {
330
+ isFormatting: true,
331
+ copyOnEnter: true
332
+ });
333
+ const definition = buildDefinition(FONT_FAMILY, normalizeOptions(editor.config.get("fontFamily.options")).filter((item) => item.model));
334
+ if (editor.config.get("fontFamily.supportAllValues")) {
335
+ this._prepareAnyValueConverters();
336
+ this._prepareCompatibilityConverter();
337
+ } else editor.conversion.attributeToElement(definition);
338
+ editor.commands.add(FONT_FAMILY, new FontFamilyCommand(editor));
339
+ }
340
+ /**
341
+ * These converters enable keeping any value found as `style="font-family: *"` as a value of an attribute on a text even
342
+ * if it is not defined in the plugin configuration.
343
+ */
344
+ _prepareAnyValueConverters() {
345
+ const editor = this.editor;
346
+ editor.conversion.for("downcast").attributeToElement({
347
+ model: FONT_FAMILY,
348
+ view: (attributeValue, { writer }) => {
349
+ return writer.createAttributeElement("span", { style: "font-family:" + attributeValue }, { priority: 7 });
350
+ }
351
+ });
352
+ editor.conversion.for("upcast").elementToAttribute({
353
+ model: {
354
+ key: FONT_FAMILY,
355
+ value: (viewElement) => viewElement.getStyle("font-family")
356
+ },
357
+ view: {
358
+ name: "span",
359
+ styles: { "font-family": /.*/ }
360
+ }
361
+ });
362
+ }
363
+ /**
364
+ * Adds support for legacy `<font face="..">` formatting.
365
+ */
366
+ _prepareCompatibilityConverter() {
367
+ this.editor.conversion.for("upcast").elementToAttribute({
368
+ view: {
369
+ name: "font",
370
+ attributes: { "face": /.*/ }
371
+ },
372
+ model: {
373
+ key: FONT_FAMILY,
374
+ value: (viewElement) => viewElement.getAttribute("face")
375
+ }
376
+ });
377
+ }
378
+ };
388
379
 
389
380
  /**
390
- * The font family UI plugin. It introduces the `'fontFamily'` dropdown.
391
- */ class FontFamilyUI extends Plugin {
392
- /**
393
- * @inheritDoc
394
- */ static get pluginName() {
395
- return 'FontFamilyUI';
396
- }
397
- /**
398
- * @inheritDoc
399
- */ static get isOfficialPlugin() {
400
- return true;
401
- }
402
- /**
403
- * @inheritDoc
404
- */ init() {
405
- const editor = this.editor;
406
- const t = editor.t;
407
- const options = this._getLocalizedOptions();
408
- const command = editor.commands.get(FONT_FAMILY);
409
- const accessibleLabel = t('Font Family');
410
- const listOptions = _prepareListOptions$1(options, command);
411
- // Register UI component.
412
- editor.ui.componentFactory.add(FONT_FAMILY, (locale)=>{
413
- const dropdownView = createDropdown(locale);
414
- addListToDropdown(dropdownView, listOptions, {
415
- role: 'menu',
416
- ariaLabel: accessibleLabel
417
- });
418
- dropdownView.buttonView.set({
419
- label: accessibleLabel,
420
- icon: IconFontFamily,
421
- tooltip: true
422
- });
423
- dropdownView.extendTemplate({
424
- attributes: {
425
- class: 'ck-font-family-dropdown'
426
- }
427
- });
428
- dropdownView.bind('isEnabled').to(command);
429
- // Execute command when an item from the dropdown is selected.
430
- this.listenTo(dropdownView, 'execute', (evt)=>{
431
- editor.execute(evt.source.commandName, {
432
- value: evt.source.commandParam
433
- });
434
- editor.editing.view.focus();
435
- });
436
- return dropdownView;
437
- });
438
- editor.ui.componentFactory.add(`menuBar:${FONT_FAMILY}`, (locale)=>{
439
- const menuView = new MenuBarMenuView(locale);
440
- menuView.buttonView.set({
441
- label: accessibleLabel,
442
- icon: IconFontFamily
443
- });
444
- menuView.bind('isEnabled').to(command);
445
- const listView = new MenuBarMenuListView(locale);
446
- for (const definition of listOptions){
447
- const listItemView = new MenuBarMenuListItemView(locale, menuView);
448
- const buttonView = new MenuBarMenuListItemButtonView(locale);
449
- buttonView.set({
450
- role: 'menuitemradio',
451
- isToggleable: true
452
- });
453
- buttonView.bind(...Object.keys(definition.model)).to(definition.model);
454
- buttonView.delegate('execute').to(menuView);
455
- buttonView.on('execute', ()=>{
456
- editor.execute(definition.model.commandName, {
457
- value: definition.model.commandParam
458
- });
459
- editor.editing.view.focus();
460
- });
461
- listItemView.children.add(buttonView);
462
- listView.items.add(listItemView);
463
- }
464
- menuView.panelView.children.add(listView);
465
- return menuView;
466
- });
467
- }
468
- /**
469
- * Returns options as defined in `config.fontFamily.options` but processed to account for
470
- * editor localization, i.e. to display {@link module:font/fontconfig~FontFamilyOption}
471
- * in the correct language.
472
- *
473
- * Note: The reason behind this method is that there is no way to use {@link module:utils/locale~Locale#t}
474
- * when the user configuration is defined because the editor does not exist yet.
475
- */ _getLocalizedOptions() {
476
- const editor = this.editor;
477
- const t = editor.t;
478
- const options = normalizeOptions$1(editor.config.get(FONT_FAMILY).options);
479
- return options.map((option)=>{
480
- // The only title to localize is "Default" others are font names.
481
- if (option.title === 'Default') {
482
- option.title = t('Default');
483
- }
484
- return option;
485
- });
486
- }
487
- }
381
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
382
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
383
+ */
384
+ /**
385
+ * @module font/fontfamily/fontfamilyui
386
+ */
387
+ /**
388
+ * The font family UI plugin. It introduces the `'fontFamily'` dropdown.
389
+ */
390
+ var FontFamilyUI = class extends Plugin {
391
+ /**
392
+ * @inheritDoc
393
+ */
394
+ static get pluginName() {
395
+ return "FontFamilyUI";
396
+ }
397
+ /**
398
+ * @inheritDoc
399
+ */
400
+ static get isOfficialPlugin() {
401
+ return true;
402
+ }
403
+ /**
404
+ * @inheritDoc
405
+ */
406
+ init() {
407
+ const editor = this.editor;
408
+ const t = editor.t;
409
+ const options = this._getLocalizedOptions();
410
+ const command = editor.commands.get(FONT_FAMILY);
411
+ const accessibleLabel = t("Font Family");
412
+ const listOptions = _prepareListOptions$1(options, command);
413
+ editor.ui.componentFactory.add(FONT_FAMILY, (locale) => {
414
+ const dropdownView = createDropdown(locale);
415
+ addListToDropdown(dropdownView, listOptions, {
416
+ role: "menu",
417
+ ariaLabel: accessibleLabel
418
+ });
419
+ dropdownView.buttonView.set({
420
+ label: accessibleLabel,
421
+ icon: IconFontFamily,
422
+ tooltip: true
423
+ });
424
+ dropdownView.extendTemplate({ attributes: { class: "ck-font-family-dropdown" } });
425
+ dropdownView.bind("isEnabled").to(command);
426
+ this.listenTo(dropdownView, "execute", (evt) => {
427
+ editor.execute(evt.source.commandName, { value: evt.source.commandParam });
428
+ editor.editing.view.focus();
429
+ });
430
+ return dropdownView;
431
+ });
432
+ editor.ui.componentFactory.add(`menuBar:${FONT_FAMILY}`, (locale) => {
433
+ const menuView = new MenuBarMenuView(locale);
434
+ menuView.buttonView.set({
435
+ label: accessibleLabel,
436
+ icon: IconFontFamily
437
+ });
438
+ menuView.bind("isEnabled").to(command);
439
+ const listView = new MenuBarMenuListView(locale);
440
+ for (const definition of listOptions) {
441
+ const listItemView = new MenuBarMenuListItemView(locale, menuView);
442
+ const buttonView = new MenuBarMenuListItemButtonView(locale);
443
+ buttonView.set({
444
+ role: "menuitemradio",
445
+ isToggleable: true
446
+ });
447
+ buttonView.bind(...Object.keys(definition.model)).to(definition.model);
448
+ buttonView.delegate("execute").to(menuView);
449
+ buttonView.on("execute", () => {
450
+ editor.execute(definition.model.commandName, { value: definition.model.commandParam });
451
+ editor.editing.view.focus();
452
+ });
453
+ listItemView.children.add(buttonView);
454
+ listView.items.add(listItemView);
455
+ }
456
+ menuView.panelView.children.add(listView);
457
+ return menuView;
458
+ });
459
+ }
460
+ /**
461
+ * Returns options as defined in `config.fontFamily.options` but processed to account for
462
+ * editor localization, i.e. to display {@link module:font/fontconfig~FontFamilyOption}
463
+ * in the correct language.
464
+ *
465
+ * Note: The reason behind this method is that there is no way to use {@link module:utils/locale~Locale#t}
466
+ * when the user configuration is defined because the editor does not exist yet.
467
+ */
468
+ _getLocalizedOptions() {
469
+ const editor = this.editor;
470
+ const t = editor.t;
471
+ return normalizeOptions(editor.config.get(FONT_FAMILY).options).map((option) => {
472
+ if (option.title === "Default") option.title = t("Default");
473
+ return option;
474
+ });
475
+ }
476
+ };
488
477
  /**
489
- * Prepares FontFamily dropdown items.
490
- */ function _prepareListOptions$1(options, command) {
491
- const itemDefinitions = new Collection();
492
- // Create dropdown items.
493
- for (const option of options){
494
- const def = {
495
- type: 'button',
496
- model: new UIModel({
497
- commandName: FONT_FAMILY,
498
- commandParam: option.model,
499
- label: option.title,
500
- role: 'menuitemradio',
501
- withText: true
502
- })
503
- };
504
- def.model.bind('isOn').to(command, 'value', (value)=>{
505
- // "Default" or check in strict font-family converters mode.
506
- if (value === option.model) {
507
- return true;
508
- }
509
- if (!value || !option.model) {
510
- return false;
511
- }
512
- const valueNormalized = normalizeFontFamilies(value)[0].toLowerCase();
513
- const optionNormalized = normalizeFontFamilies(option.model)[0].toLowerCase();
514
- return valueNormalized === optionNormalized;
515
- });
516
- // Try to set a dropdown list item style.
517
- if (option.view && typeof option.view !== 'string' && option.view.styles) {
518
- def.model.set('labelStyle', `font-family: ${option.view.styles['font-family']}`);
519
- }
520
- itemDefinitions.add(def);
521
- }
522
- return itemDefinitions;
478
+ * Prepares FontFamily dropdown items.
479
+ */
480
+ function _prepareListOptions$1(options, command) {
481
+ const itemDefinitions = new Collection();
482
+ for (const option of options) {
483
+ const def = {
484
+ type: "button",
485
+ model: new UIModel({
486
+ commandName: FONT_FAMILY,
487
+ commandParam: option.model,
488
+ label: option.title,
489
+ role: "menuitemradio",
490
+ withText: true
491
+ })
492
+ };
493
+ def.model.bind("isOn").to(command, "value", (value) => {
494
+ if (value === option.model) return true;
495
+ if (!value || !option.model) return false;
496
+ return normalizeFontFamilies(value)[0].toLowerCase() === normalizeFontFamilies(option.model)[0].toLowerCase();
497
+ });
498
+ if (option.view && typeof option.view !== "string" && option.view.styles) def.model.set("labelStyle", `font-family: ${option.view.styles["font-family"]}`);
499
+ itemDefinitions.add(def);
500
+ }
501
+ return itemDefinitions;
523
502
  }
524
503
 
525
504
  /**
526
- * The font family plugin.
527
- *
528
- * For a detailed overview, check the {@glink features/font font feature} documentatiom
529
- * and the {@glink api/font package page}.
530
- *
531
- * This is a "glue" plugin which loads the {@link module:font/fontfamily/fontfamilyediting~FontFamilyEditing} and
532
- * {@link module:font/fontfamily/fontfamilyui~FontFamilyUI} features in the editor.
533
- */ class FontFamily extends Plugin {
534
- /**
535
- * @inheritDoc
536
- */ static get requires() {
537
- return [
538
- FontFamilyEditing,
539
- FontFamilyUI
540
- ];
541
- }
542
- /**
543
- * @inheritDoc
544
- */ static get pluginName() {
545
- return 'FontFamily';
546
- }
547
- /**
548
- * @inheritDoc
549
- */ static get isOfficialPlugin() {
550
- return true;
551
- }
552
- }
505
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
506
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
507
+ */
508
+ /**
509
+ * @module font/fontfamily
510
+ */
511
+ /**
512
+ * The font family plugin.
513
+ *
514
+ * For a detailed overview, check the {@glink features/font font feature} documentatiom
515
+ * and the {@glink api/font package page}.
516
+ *
517
+ * This is a "glue" plugin which loads the {@link module:font/fontfamily/fontfamilyediting~FontFamilyEditing} and
518
+ * {@link module:font/fontfamily/fontfamilyui~FontFamilyUI} features in the editor.
519
+ */
520
+ var FontFamily = class extends Plugin {
521
+ /**
522
+ * @inheritDoc
523
+ */
524
+ static get requires() {
525
+ return [FontFamilyEditing, FontFamilyUI];
526
+ }
527
+ /**
528
+ * @inheritDoc
529
+ */
530
+ static get pluginName() {
531
+ return "FontFamily";
532
+ }
533
+ /**
534
+ * @inheritDoc
535
+ */
536
+ static get isOfficialPlugin() {
537
+ return true;
538
+ }
539
+ };
553
540
 
554
541
  /**
555
- * The font size command. It is used by {@link module:font/fontsize/fontsizeediting~FontSizeEditing}
556
- * to apply the font size.
557
- *
558
- * ```ts
559
- * editor.execute( 'fontSize', { value: 'small' } );
560
- * ```
561
- *
562
- * **Note**: Executing the command without the value removes the attribute from the model.
563
- */ class FontSizeCommand extends FontCommand {
564
- /**
565
- * @inheritDoc
566
- */ constructor(editor){
567
- super(editor, FONT_SIZE);
568
- }
569
- }
542
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
543
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
544
+ */
545
+ /**
546
+ * The font size command. It is used by {@link module:font/fontsize/fontsizeediting~FontSizeEditing}
547
+ * to apply the font size.
548
+ *
549
+ * ```ts
550
+ * editor.execute( 'fontSize', { value: 'small' } );
551
+ * ```
552
+ *
553
+ * **Note**: Executing the command without the value removes the attribute from the model.
554
+ */
555
+ var FontSizeCommand = class extends FontCommand {
556
+ /**
557
+ * @inheritDoc
558
+ */
559
+ constructor(editor) {
560
+ super(editor, FONT_SIZE);
561
+ }
562
+ };
570
563
 
571
564
  /**
572
- * Normalizes and translates the {@link module:font/fontconfig~FontSizeConfig#options configuration options}
573
- * to the {@link module:font/fontconfig~FontSizeOption} format.
574
- *
575
- * @param configuredOptions An array of options taken from the configuration.
576
- * @internal
577
- */ function normalizeOptions(configuredOptions) {
578
- // Convert options to objects.
579
- return configuredOptions.map((item)=>getOptionDefinition(item))// Filter out undefined values that `getOptionDefinition` might return.
580
- .filter((option)=>option !== undefined);
565
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
566
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
567
+ */
568
+ /**
569
+ * @module font/fontsize/utils
570
+ */
571
+ /**
572
+ * Normalizes and translates the {@link module:font/fontconfig~FontSizeConfig#options configuration options}
573
+ * to the {@link module:font/fontconfig~FontSizeOption} format.
574
+ *
575
+ * @param configuredOptions An array of options taken from the configuration.
576
+ * @internal
577
+ */
578
+ function normalizeOptions$1(configuredOptions) {
579
+ return configuredOptions.map((item) => getOptionDefinition(item)).filter((option) => option !== void 0);
581
580
  }
582
- // Default named presets map. Always create a new instance of the preset object in order to avoid modifying references.
583
581
  const namedPresets = {
584
- get tiny () {
585
- return {
586
- title: 'Tiny',
587
- model: 'tiny',
588
- view: {
589
- name: 'span',
590
- classes: 'text-tiny',
591
- priority: 7
592
- }
593
- };
594
- },
595
- get small () {
596
- return {
597
- title: 'Small',
598
- model: 'small',
599
- view: {
600
- name: 'span',
601
- classes: 'text-small',
602
- priority: 7
603
- }
604
- };
605
- },
606
- get big () {
607
- return {
608
- title: 'Big',
609
- model: 'big',
610
- view: {
611
- name: 'span',
612
- classes: 'text-big',
613
- priority: 7
614
- }
615
- };
616
- },
617
- get huge () {
618
- return {
619
- title: 'Huge',
620
- model: 'huge',
621
- view: {
622
- name: 'span',
623
- classes: 'text-huge',
624
- priority: 7
625
- }
626
- };
627
- }
582
+ get tiny() {
583
+ return {
584
+ title: "Tiny",
585
+ model: "tiny",
586
+ view: {
587
+ name: "span",
588
+ classes: "text-tiny",
589
+ priority: 7
590
+ }
591
+ };
592
+ },
593
+ get small() {
594
+ return {
595
+ title: "Small",
596
+ model: "small",
597
+ view: {
598
+ name: "span",
599
+ classes: "text-small",
600
+ priority: 7
601
+ }
602
+ };
603
+ },
604
+ get big() {
605
+ return {
606
+ title: "Big",
607
+ model: "big",
608
+ view: {
609
+ name: "span",
610
+ classes: "text-big",
611
+ priority: 7
612
+ }
613
+ };
614
+ },
615
+ get huge() {
616
+ return {
617
+ title: "Huge",
618
+ model: "huge",
619
+ view: {
620
+ name: "span",
621
+ classes: "text-huge",
622
+ priority: 7
623
+ }
624
+ };
625
+ }
628
626
  };
629
627
  /**
630
- * Returns an option definition either from preset or creates one from number shortcut.
631
- * If object is passed then this method will return it without alternating it. Returns undefined for item than cannot be parsed.
632
- */ function getOptionDefinition(option) {
633
- if (typeof option === 'number') {
634
- option = String(option);
635
- }
636
- // Check whether passed option is a full item definition provided by user in configuration.
637
- if (typeof option === 'object' && isFullItemDefinition(option)) {
638
- return attachPriority(option);
639
- }
640
- const preset = findPreset(option);
641
- // Item is a named preset.
642
- if (preset) {
643
- return attachPriority(preset);
644
- }
645
- // 'Default' font size. It will be used to remove the fontSize attribute.
646
- if (option === 'default') {
647
- return {
648
- model: undefined,
649
- title: 'Default'
650
- };
651
- }
652
- // At this stage we probably have numerical value to generate a preset so parse it's value.
653
- // Discard any faulty values.
654
- if (isNumericalDefinition(option)) {
655
- return undefined;
656
- }
657
- // Return font size definition from size value.
658
- return generatePixelPreset(option);
628
+ * Returns an option definition either from preset or creates one from number shortcut.
629
+ * If object is passed then this method will return it without alternating it. Returns undefined for item than cannot be parsed.
630
+ */
631
+ function getOptionDefinition(option) {
632
+ if (typeof option === "number") option = String(option);
633
+ if (typeof option === "object" && isFullItemDefinition(option)) return attachPriority(option);
634
+ const preset = findPreset(option);
635
+ if (preset) return attachPriority(preset);
636
+ if (option === "default") return {
637
+ model: void 0,
638
+ title: "Default"
639
+ };
640
+ if (isNumericalDefinition(option)) return;
641
+ return generatePixelPreset(option);
659
642
  }
660
643
  /**
661
- * Creates a predefined preset for pixel size.
662
- * @param definition Font size in pixels.
663
- * @returns
664
- */ function generatePixelPreset(definition) {
665
- // Extend a short (numeric value) definition.
666
- if (typeof definition === 'string') {
667
- definition = {
668
- title: definition,
669
- model: `${parseFloat(definition)}px`
670
- };
671
- }
672
- definition.view = {
673
- name: 'span',
674
- styles: {
675
- 'font-size': definition.model
676
- }
677
- };
678
- return attachPriority(definition);
644
+ * Creates a predefined preset for pixel size.
645
+ * @param definition Font size in pixels.
646
+ * @returns
647
+ */
648
+ function generatePixelPreset(definition) {
649
+ if (typeof definition === "string") definition = {
650
+ title: definition,
651
+ model: `${parseFloat(definition)}px`
652
+ };
653
+ definition.view = {
654
+ name: "span",
655
+ styles: { "font-size": definition.model }
656
+ };
657
+ return attachPriority(definition);
679
658
  }
680
659
  /**
681
- * Adds the priority to the view element definition if missing. It's required due to https://github.com/ckeditor/ckeditor5/issues/2291
682
- */ function attachPriority(definition) {
683
- if (definition.view && typeof definition.view !== 'string' && !definition.view.priority) {
684
- definition.view.priority = 7;
685
- }
686
- return definition;
660
+ * Adds the priority to the view element definition if missing. It's required due to https://github.com/ckeditor/ckeditor5/issues/2291
661
+ */
662
+ function attachPriority(definition) {
663
+ if (definition.view && typeof definition.view !== "string" && !definition.view.priority) definition.view.priority = 7;
664
+ return definition;
687
665
  }
688
666
  /**
689
- * Returns a prepared preset definition. If passed an object, a name of preset should be defined as `model` value.
690
- *
691
- * @param definition.model A preset name.
692
- */ function findPreset(definition) {
693
- return typeof definition === 'string' ? namedPresets[definition] : namedPresets[definition.model];
667
+ * Returns a prepared preset definition. If passed an object, a name of preset should be defined as `model` value.
668
+ *
669
+ * @param definition.model A preset name.
670
+ */
671
+ function findPreset(definition) {
672
+ return typeof definition === "string" ? namedPresets[definition] : namedPresets[definition.model];
694
673
  }
695
674
  /**
696
- * We treat `definition` as completed if it is an object that contains `title`, `model` and `view` values.
697
- */ function isFullItemDefinition(definition) {
698
- return definition.title && definition.model && definition.view;
675
+ * We treat `definition` as completed if it is an object that contains `title`, `model` and `view` values.
676
+ */
677
+ function isFullItemDefinition(definition) {
678
+ return definition.title && definition.model && definition.view;
699
679
  }
700
680
  function isNumericalDefinition(definition) {
701
- let numberValue;
702
- if (typeof definition === 'object') {
703
- if (!definition.model) {
704
- /**
705
- * Provided value as an option for {@link module:font/fontsize~FontSize} seems to invalid.
706
- *
707
- * See valid examples described in the {@link module:font/fontconfig~FontSizeConfig#options plugin configuration}.
708
- *
709
- * @error font-size-invalid-definition
710
- */ throw new CKEditorError('font-size-invalid-definition', null, definition);
711
- } else {
712
- numberValue = parseFloat(definition.model);
713
- }
714
- } else {
715
- numberValue = parseFloat(definition);
716
- }
717
- return isNaN(numberValue);
681
+ let numberValue;
682
+ if (typeof definition === "object") if (!definition.model)
683
+ /**
684
+ * Provided value as an option for {@link module:font/fontsize~FontSize} seems to invalid.
685
+ *
686
+ * See valid examples described in the {@link module:font/fontconfig~FontSizeConfig#options plugin configuration}.
687
+ *
688
+ * @error font-size-invalid-definition
689
+ */
690
+ throw new CKEditorError("font-size-invalid-definition", null, definition);
691
+ else numberValue = parseFloat(definition.model);
692
+ else numberValue = parseFloat(definition);
693
+ return isNaN(numberValue);
718
694
  }
719
695
 
720
- // Mapping of `<font size="..">` styling to CSS's `font-size` values.
696
+ /**
697
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
698
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
699
+ */
700
+ /**
701
+ * @module font/fontsize/fontsizeediting
702
+ */
721
703
  const styleFontSize = [
722
- 'x-small',
723
- 'x-small',
724
- 'small',
725
- 'medium',
726
- 'large',
727
- 'x-large',
728
- 'xx-large',
729
- 'xxx-large'
704
+ "x-small",
705
+ "x-small",
706
+ "small",
707
+ "medium",
708
+ "large",
709
+ "x-large",
710
+ "xx-large",
711
+ "xxx-large"
730
712
  ];
731
713
  /**
732
- * The font size editing feature.
733
- *
734
- * It introduces the {@link module:font/fontsize/fontsizecommand~FontSizeCommand command} and the `fontSize`
735
- * attribute in the {@link module:engine/model/model~Model model} which renders in the {@link module:engine/view/view view}
736
- * as a `<span>` element with either:
737
- * * a style attribute (`<span style="font-size:12px">...</span>`),
738
- * * or a class attribute (`<span class="text-small">...</span>`)
739
- *
740
- * depending on the {@link module:font/fontconfig~FontSizeConfig configuration}.
741
- */ class FontSizeEditing extends Plugin {
742
- /**
743
- * @inheritDoc
744
- */ static get pluginName() {
745
- return 'FontSizeEditing';
746
- }
747
- /**
748
- * @inheritDoc
749
- */ static get isOfficialPlugin() {
750
- return true;
751
- }
752
- /**
753
- * @inheritDoc
754
- */ constructor(editor){
755
- super(editor);
756
- // Define default configuration using named presets.
757
- editor.config.define(FONT_SIZE, {
758
- options: [
759
- 'tiny',
760
- 'small',
761
- 'default',
762
- 'big',
763
- 'huge'
764
- ],
765
- supportAllValues: false
766
- });
767
- }
768
- /**
769
- * @inheritDoc
770
- */ init() {
771
- const editor = this.editor;
772
- // Allow fontSize attribute on text nodes.
773
- editor.model.schema.extend('$text', {
774
- allowAttributes: FONT_SIZE
775
- });
776
- editor.model.schema.setAttributeProperties(FONT_SIZE, {
777
- isFormatting: true,
778
- copyOnEnter: true
779
- });
780
- const supportAllValues = editor.config.get('fontSize.supportAllValues');
781
- // Define view to model conversion.
782
- const options = normalizeOptions(this.editor.config.get('fontSize.options')).filter((item)=>item.model);
783
- const definition = buildDefinition(FONT_SIZE, options);
784
- // Set-up the two-way conversion.
785
- if (supportAllValues) {
786
- this._prepareAnyValueConverters(definition);
787
- this._prepareCompatibilityConverter();
788
- } else {
789
- editor.conversion.attributeToElement(definition);
790
- }
791
- // Add FontSize command.
792
- editor.commands.add(FONT_SIZE, new FontSizeCommand(editor));
793
- }
794
- /**
795
- * These converters enable keeping any value found as `style="font-size: *"` as a value of an attribute on a text even
796
- * if it is not defined in the plugin configuration.
797
- *
798
- * @param definition Converter definition out of input data.
799
- */ _prepareAnyValueConverters(definition) {
800
- const editor = this.editor;
801
- // If `fontSize.supportAllValues=true`, we do not allow to use named presets in the plugin's configuration.
802
- const presets = definition.model.values.filter((value)=>{
803
- return !isLengthStyleValue(String(value)) && !isPercentageStyleValue(String(value));
804
- });
805
- if (presets.length) {
806
- /**
807
- * If {@link module:font/fontconfig~FontSizeConfig#supportAllValues `config.fontSize.supportAllValues`} is `true`,
808
- * you need to use numerical values as font size options.
809
- *
810
- * See valid examples described in the {@link module:font/fontconfig~FontSizeConfig#options plugin configuration}.
811
- *
812
- * @error font-size-invalid-use-of-named-presets
813
- * @param {Array.<string>} presets Invalid values.
814
- */ throw new CKEditorError('font-size-invalid-use-of-named-presets', null, {
815
- presets
816
- });
817
- }
818
- editor.conversion.for('downcast').attributeToElement({
819
- model: FONT_SIZE,
820
- view: (attributeValue, { writer })=>{
821
- if (!attributeValue) {
822
- return;
823
- }
824
- return writer.createAttributeElement('span', {
825
- style: 'font-size:' + attributeValue
826
- }, {
827
- priority: 7
828
- });
829
- }
830
- });
831
- editor.conversion.for('upcast').elementToAttribute({
832
- model: {
833
- key: FONT_SIZE,
834
- value: (viewElement)=>viewElement.getStyle('font-size')
835
- },
836
- view: {
837
- name: 'span',
838
- styles: {
839
- 'font-size': /.*/
840
- }
841
- }
842
- });
843
- }
844
- /**
845
- * Adds support for legacy `<font size="..">` formatting.
846
- */ _prepareCompatibilityConverter() {
847
- const editor = this.editor;
848
- editor.conversion.for('upcast').elementToAttribute({
849
- view: {
850
- name: 'font',
851
- attributes: {
852
- // Documentation mentions sizes from 1 to 7. To handle old content we support all values
853
- // up to 999 but clamp it to the valid range. Why 999? It should cover accidental values
854
- // similar to percentage, e.g. 100%, 200% which could be the usual mistake for font size.
855
- 'size': /^[+-]?\d{1,3}$/
856
- }
857
- },
858
- model: {
859
- key: FONT_SIZE,
860
- value: (viewElement)=>{
861
- const value = viewElement.getAttribute('size');
862
- const isRelative = value[0] === '-' || value[0] === '+';
863
- let size = parseInt(value, 10);
864
- if (isRelative) {
865
- // Add relative size (which can be negative) to the default size = 3.
866
- size = 3 + size;
867
- }
868
- const maxSize = styleFontSize.length - 1;
869
- const clampedSize = Math.min(Math.max(size, 0), maxSize);
870
- return styleFontSize[clampedSize];
871
- }
872
- }
873
- });
874
- }
875
- }
714
+ * The font size editing feature.
715
+ *
716
+ * It introduces the {@link module:font/fontsize/fontsizecommand~FontSizeCommand command} and the `fontSize`
717
+ * attribute in the {@link module:engine/model/model~Model model} which renders in the {@link module:engine/view/view view}
718
+ * as a `<span>` element with either:
719
+ * * a style attribute (`<span style="font-size:12px">...</span>`),
720
+ * * or a class attribute (`<span class="text-small">...</span>`)
721
+ *
722
+ * depending on the {@link module:font/fontconfig~FontSizeConfig configuration}.
723
+ */
724
+ var FontSizeEditing = class extends Plugin {
725
+ /**
726
+ * @inheritDoc
727
+ */
728
+ static get pluginName() {
729
+ return "FontSizeEditing";
730
+ }
731
+ /**
732
+ * @inheritDoc
733
+ */
734
+ static get isOfficialPlugin() {
735
+ return true;
736
+ }
737
+ /**
738
+ * @inheritDoc
739
+ */
740
+ constructor(editor) {
741
+ super(editor);
742
+ editor.config.define(FONT_SIZE, {
743
+ options: [
744
+ "tiny",
745
+ "small",
746
+ "default",
747
+ "big",
748
+ "huge"
749
+ ],
750
+ supportAllValues: false
751
+ });
752
+ }
753
+ /**
754
+ * @inheritDoc
755
+ */
756
+ init() {
757
+ const editor = this.editor;
758
+ editor.model.schema.extend("$text", { allowAttributes: FONT_SIZE });
759
+ editor.model.schema.setAttributeProperties(FONT_SIZE, {
760
+ isFormatting: true,
761
+ copyOnEnter: true
762
+ });
763
+ const supportAllValues = editor.config.get("fontSize.supportAllValues");
764
+ const definition = buildDefinition(FONT_SIZE, normalizeOptions$1(this.editor.config.get("fontSize.options")).filter((item) => item.model));
765
+ if (supportAllValues) {
766
+ this._prepareAnyValueConverters(definition);
767
+ this._prepareCompatibilityConverter();
768
+ } else editor.conversion.attributeToElement(definition);
769
+ editor.commands.add(FONT_SIZE, new FontSizeCommand(editor));
770
+ }
771
+ /**
772
+ * These converters enable keeping any value found as `style="font-size: *"` as a value of an attribute on a text even
773
+ * if it is not defined in the plugin configuration.
774
+ *
775
+ * @param definition Converter definition out of input data.
776
+ */
777
+ _prepareAnyValueConverters(definition) {
778
+ const editor = this.editor;
779
+ const presets = definition.model.values.filter((value) => {
780
+ return !isLengthStyleValue(String(value)) && !isPercentageStyleValue(String(value));
781
+ });
782
+ if (presets.length)
783
+ /**
784
+ * If {@link module:font/fontconfig~FontSizeConfig#supportAllValues `config.fontSize.supportAllValues`} is `true`,
785
+ * you need to use numerical values as font size options.
786
+ *
787
+ * See valid examples described in the {@link module:font/fontconfig~FontSizeConfig#options plugin configuration}.
788
+ *
789
+ * @error font-size-invalid-use-of-named-presets
790
+ * @param {Array.<string>} presets Invalid values.
791
+ */
792
+ throw new CKEditorError("font-size-invalid-use-of-named-presets", null, { presets });
793
+ editor.conversion.for("downcast").attributeToElement({
794
+ model: FONT_SIZE,
795
+ view: (attributeValue, { writer }) => {
796
+ if (!attributeValue) return;
797
+ return writer.createAttributeElement("span", { style: "font-size:" + attributeValue }, { priority: 7 });
798
+ }
799
+ });
800
+ editor.conversion.for("upcast").elementToAttribute({
801
+ model: {
802
+ key: FONT_SIZE,
803
+ value: (viewElement) => viewElement.getStyle("font-size")
804
+ },
805
+ view: {
806
+ name: "span",
807
+ styles: { "font-size": /.*/ }
808
+ }
809
+ });
810
+ }
811
+ /**
812
+ * Adds support for legacy `<font size="..">` formatting.
813
+ */
814
+ _prepareCompatibilityConverter() {
815
+ this.editor.conversion.for("upcast").elementToAttribute({
816
+ view: {
817
+ name: "font",
818
+ attributes: { "size": /^[+-]?\d{1,3}$/ }
819
+ },
820
+ model: {
821
+ key: FONT_SIZE,
822
+ value: (viewElement) => {
823
+ const value = viewElement.getAttribute("size");
824
+ const isRelative = value[0] === "-" || value[0] === "+";
825
+ let size = parseInt(value, 10);
826
+ if (isRelative) size = 3 + size;
827
+ const maxSize = styleFontSize.length - 1;
828
+ return styleFontSize[Math.min(Math.max(size, 0), maxSize)];
829
+ }
830
+ }
831
+ });
832
+ }
833
+ };
876
834
 
877
835
  /**
878
- * The font size UI plugin. It introduces the `'fontSize'` dropdown.
879
- */ class FontSizeUI extends Plugin {
880
- /**
881
- * @inheritDoc
882
- */ static get pluginName() {
883
- return 'FontSizeUI';
884
- }
885
- /**
886
- * @inheritDoc
887
- */ static get isOfficialPlugin() {
888
- return true;
889
- }
890
- /**
891
- * @inheritDoc
892
- */ init() {
893
- const editor = this.editor;
894
- const t = editor.t;
895
- const options = this._getLocalizedOptions();
896
- const command = editor.commands.get(FONT_SIZE);
897
- const accessibleLabel = t('Font Size');
898
- const listOptions = _prepareListOptions(options, command);
899
- // Register UI component.
900
- editor.ui.componentFactory.add(FONT_SIZE, (locale)=>{
901
- const dropdownView = createDropdown(locale);
902
- addListToDropdown(dropdownView, listOptions, {
903
- role: 'menu',
904
- ariaLabel: accessibleLabel
905
- });
906
- // Create dropdown model.
907
- dropdownView.buttonView.set({
908
- label: accessibleLabel,
909
- icon: IconFontSize,
910
- tooltip: true
911
- });
912
- dropdownView.extendTemplate({
913
- attributes: {
914
- class: [
915
- 'ck-font-size-dropdown'
916
- ]
917
- }
918
- });
919
- dropdownView.bind('isEnabled').to(command);
920
- // Execute command when an item from the dropdown is selected.
921
- this.listenTo(dropdownView, 'execute', (evt)=>{
922
- editor.execute(evt.source.commandName, {
923
- value: evt.source.commandParam
924
- });
925
- editor.editing.view.focus();
926
- });
927
- return dropdownView;
928
- });
929
- editor.ui.componentFactory.add(`menuBar:${FONT_SIZE}`, (locale)=>{
930
- const menuView = new MenuBarMenuView(locale);
931
- menuView.buttonView.set({
932
- label: accessibleLabel,
933
- icon: IconFontSize
934
- });
935
- menuView.bind('isEnabled').to(command);
936
- const listView = new MenuBarMenuListView(locale);
937
- for (const definition of listOptions){
938
- const listItemView = new MenuBarMenuListItemView(locale, menuView);
939
- const buttonView = new MenuBarMenuListItemButtonView(locale);
940
- buttonView.set({
941
- role: 'menuitemradio',
942
- isToggleable: true
943
- });
944
- buttonView.bind(...Object.keys(definition.model)).to(definition.model);
945
- buttonView.delegate('execute').to(menuView);
946
- buttonView.on('execute', ()=>{
947
- editor.execute(definition.model.commandName, {
948
- value: definition.model.commandParam
949
- });
950
- editor.editing.view.focus();
951
- });
952
- listItemView.children.add(buttonView);
953
- listView.items.add(listItemView);
954
- }
955
- menuView.panelView.children.add(listView);
956
- return menuView;
957
- });
958
- }
959
- /**
960
- * Returns options as defined in `config.fontSize.options` but processed to account for
961
- * editor localization, i.e. to display {@link module:font/fontconfig~FontSizeOption}
962
- * in the correct language.
963
- *
964
- * Note: The reason behind this method is that there is no way to use {@link module:utils/locale~Locale#t}
965
- * when the user configuration is defined because the editor does not exist yet.
966
- */ _getLocalizedOptions() {
967
- const editor = this.editor;
968
- const t = editor.t;
969
- const localizedTitles = {
970
- Default: t('Default'),
971
- Tiny: t('Tiny'),
972
- Small: t('Small'),
973
- Big: t('Big'),
974
- Huge: t('Huge')
975
- };
976
- const options = normalizeOptions(editor.config.get(FONT_SIZE).options);
977
- return options.map((option)=>{
978
- const title = localizedTitles[option.title];
979
- if (title && title != option.title) {
980
- // Clone the option to avoid altering the original `namedPresets` from `./utils.js`.
981
- option = Object.assign({}, option, {
982
- title
983
- });
984
- }
985
- return option;
986
- });
987
- }
988
- }
836
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
837
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
838
+ */
839
+ /**
840
+ * @module font/fontsize/fontsizeui
841
+ */
842
+ /**
843
+ * The font size UI plugin. It introduces the `'fontSize'` dropdown.
844
+ */
845
+ var FontSizeUI = class extends Plugin {
846
+ /**
847
+ * @inheritDoc
848
+ */
849
+ static get pluginName() {
850
+ return "FontSizeUI";
851
+ }
852
+ /**
853
+ * @inheritDoc
854
+ */
855
+ static get isOfficialPlugin() {
856
+ return true;
857
+ }
858
+ /**
859
+ * @inheritDoc
860
+ */
861
+ init() {
862
+ const editor = this.editor;
863
+ const t = editor.t;
864
+ const options = this._getLocalizedOptions();
865
+ const command = editor.commands.get(FONT_SIZE);
866
+ const accessibleLabel = t("Font Size");
867
+ const listOptions = _prepareListOptions(options, command);
868
+ editor.ui.componentFactory.add(FONT_SIZE, (locale) => {
869
+ const dropdownView = createDropdown(locale);
870
+ addListToDropdown(dropdownView, listOptions, {
871
+ role: "menu",
872
+ ariaLabel: accessibleLabel
873
+ });
874
+ dropdownView.buttonView.set({
875
+ label: accessibleLabel,
876
+ icon: IconFontSize,
877
+ tooltip: true
878
+ });
879
+ dropdownView.extendTemplate({ attributes: { class: ["ck-font-size-dropdown"] } });
880
+ dropdownView.bind("isEnabled").to(command);
881
+ this.listenTo(dropdownView, "execute", (evt) => {
882
+ editor.execute(evt.source.commandName, { value: evt.source.commandParam });
883
+ editor.editing.view.focus();
884
+ });
885
+ return dropdownView;
886
+ });
887
+ editor.ui.componentFactory.add(`menuBar:${FONT_SIZE}`, (locale) => {
888
+ const menuView = new MenuBarMenuView(locale);
889
+ menuView.buttonView.set({
890
+ label: accessibleLabel,
891
+ icon: IconFontSize
892
+ });
893
+ menuView.bind("isEnabled").to(command);
894
+ const listView = new MenuBarMenuListView(locale);
895
+ for (const definition of listOptions) {
896
+ const listItemView = new MenuBarMenuListItemView(locale, menuView);
897
+ const buttonView = new MenuBarMenuListItemButtonView(locale);
898
+ buttonView.set({
899
+ role: "menuitemradio",
900
+ isToggleable: true
901
+ });
902
+ buttonView.bind(...Object.keys(definition.model)).to(definition.model);
903
+ buttonView.delegate("execute").to(menuView);
904
+ buttonView.on("execute", () => {
905
+ editor.execute(definition.model.commandName, { value: definition.model.commandParam });
906
+ editor.editing.view.focus();
907
+ });
908
+ listItemView.children.add(buttonView);
909
+ listView.items.add(listItemView);
910
+ }
911
+ menuView.panelView.children.add(listView);
912
+ return menuView;
913
+ });
914
+ }
915
+ /**
916
+ * Returns options as defined in `config.fontSize.options` but processed to account for
917
+ * editor localization, i.e. to display {@link module:font/fontconfig~FontSizeOption}
918
+ * in the correct language.
919
+ *
920
+ * Note: The reason behind this method is that there is no way to use {@link module:utils/locale~Locale#t}
921
+ * when the user configuration is defined because the editor does not exist yet.
922
+ */
923
+ _getLocalizedOptions() {
924
+ const editor = this.editor;
925
+ const t = editor.t;
926
+ const localizedTitles = {
927
+ Default: t("Default"),
928
+ Tiny: t("Tiny"),
929
+ Small: t("Small"),
930
+ Big: t("Big"),
931
+ Huge: t("Huge")
932
+ };
933
+ return normalizeOptions$1(editor.config.get(FONT_SIZE).options).map((option) => {
934
+ const title = localizedTitles[option.title];
935
+ if (title && title != option.title) option = Object.assign({}, option, { title });
936
+ return option;
937
+ });
938
+ }
939
+ };
989
940
  /**
990
- * Prepares FontSize dropdown items.
991
- */ function _prepareListOptions(options, command) {
992
- const itemDefinitions = new Collection();
993
- for (const option of options){
994
- const def = {
995
- type: 'button',
996
- model: new UIModel({
997
- commandName: FONT_SIZE,
998
- commandParam: option.model,
999
- label: option.title,
1000
- class: 'ck-fontsize-option',
1001
- role: 'menuitemradio',
1002
- withText: true
1003
- })
1004
- };
1005
- if (option.view && typeof option.view !== 'string') {
1006
- if (option.view.styles) {
1007
- def.model.set('labelStyle', `font-size:${option.view.styles['font-size']}`);
1008
- }
1009
- if (option.view.classes) {
1010
- def.model.set('class', `${def.model.class} ${option.view.classes}`);
1011
- }
1012
- }
1013
- def.model.bind('isOn').to(command, 'value', (value)=>value === option.model);
1014
- // Add the option to the collection.
1015
- itemDefinitions.add(def);
1016
- }
1017
- return itemDefinitions;
941
+ * Prepares FontSize dropdown items.
942
+ */
943
+ function _prepareListOptions(options, command) {
944
+ const itemDefinitions = new Collection();
945
+ for (const option of options) {
946
+ const def = {
947
+ type: "button",
948
+ model: new UIModel({
949
+ commandName: FONT_SIZE,
950
+ commandParam: option.model,
951
+ label: option.title,
952
+ class: "ck-fontsize-option",
953
+ role: "menuitemradio",
954
+ withText: true
955
+ })
956
+ };
957
+ if (option.view && typeof option.view !== "string") {
958
+ if (option.view.styles) def.model.set("labelStyle", `font-size:${option.view.styles["font-size"]}`);
959
+ if (option.view.classes) def.model.set("class", `${def.model.class} ${option.view.classes}`);
960
+ }
961
+ def.model.bind("isOn").to(command, "value", (value) => value === option.model);
962
+ itemDefinitions.add(def);
963
+ }
964
+ return itemDefinitions;
1018
965
  }
1019
966
 
1020
967
  /**
1021
- * The font size plugin.
1022
- *
1023
- * For a detailed overview, check the {@glink features/font font feature} documentation
1024
- * and the {@glink api/font package page}.
1025
- *
1026
- * This is a "glue" plugin which loads the {@link module:font/fontsize/fontsizeediting~FontSizeEditing} and
1027
- * {@link module:font/fontsize/fontsizeui~FontSizeUI} features in the editor.
1028
- */ class FontSize extends Plugin {
1029
- /**
1030
- * @inheritDoc
1031
- */ static get requires() {
1032
- return [
1033
- FontSizeEditing,
1034
- FontSizeUI
1035
- ];
1036
- }
1037
- /**
1038
- * @inheritDoc
1039
- */ static get pluginName() {
1040
- return 'FontSize';
1041
- }
1042
- /**
1043
- * @inheritDoc
1044
- */ static get isOfficialPlugin() {
1045
- return true;
1046
- }
1047
- /**
1048
- * Normalizes and translates the {@link module:font/fontconfig~FontSizeConfig#options configuration options}
1049
- * to the {@link module:font/fontconfig~FontSizeOption} format.
1050
- *
1051
- * @param options An array of options taken from the configuration.
1052
- */ normalizeSizeOptions(options) {
1053
- return normalizeOptions(options);
1054
- }
1055
- }
968
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
969
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
970
+ */
971
+ /**
972
+ * @module font/fontsize
973
+ */
974
+ /**
975
+ * The font size plugin.
976
+ *
977
+ * For a detailed overview, check the {@glink features/font font feature} documentation
978
+ * and the {@glink api/font package page}.
979
+ *
980
+ * This is a "glue" plugin which loads the {@link module:font/fontsize/fontsizeediting~FontSizeEditing} and
981
+ * {@link module:font/fontsize/fontsizeui~FontSizeUI} features in the editor.
982
+ */
983
+ var FontSize = class extends Plugin {
984
+ /**
985
+ * @inheritDoc
986
+ */
987
+ static get requires() {
988
+ return [FontSizeEditing, FontSizeUI];
989
+ }
990
+ /**
991
+ * @inheritDoc
992
+ */
993
+ static get pluginName() {
994
+ return "FontSize";
995
+ }
996
+ /**
997
+ * @inheritDoc
998
+ */
999
+ static get isOfficialPlugin() {
1000
+ return true;
1001
+ }
1002
+ /**
1003
+ * Normalizes and translates the {@link module:font/fontconfig~FontSizeConfig#options configuration options}
1004
+ * to the {@link module:font/fontconfig~FontSizeOption} format.
1005
+ *
1006
+ * @param options An array of options taken from the configuration.
1007
+ */
1008
+ normalizeSizeOptions(options) {
1009
+ return normalizeOptions$1(options);
1010
+ }
1011
+ };
1056
1012
 
1057
1013
  /**
1058
- * The font color command. It is used by {@link module:font/fontcolor/fontcolorediting~FontColorEditing}
1059
- * to apply the font color.
1060
- *
1061
- * ```ts
1062
- * editor.execute( 'fontColor', { value: 'rgb(250, 20, 20)' } );
1063
- * ```
1064
- *
1065
- * **Note**: Executing the command with the `null` value removes the attribute from the model.
1066
- */ class FontColorCommand extends FontCommand {
1067
- /**
1068
- * @inheritDoc
1069
- */ constructor(editor){
1070
- super(editor, FONT_COLOR);
1071
- }
1072
- }
1014
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
1015
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
1016
+ */
1017
+ /**
1018
+ * The font color command. It is used by {@link module:font/fontcolor/fontcolorediting~FontColorEditing}
1019
+ * to apply the font color.
1020
+ *
1021
+ * ```ts
1022
+ * editor.execute( 'fontColor', { value: 'rgb(250, 20, 20)' } );
1023
+ * ```
1024
+ *
1025
+ * **Note**: Executing the command with the `null` value removes the attribute from the model.
1026
+ */
1027
+ var FontColorCommand = class extends FontCommand {
1028
+ /**
1029
+ * @inheritDoc
1030
+ */
1031
+ constructor(editor) {
1032
+ super(editor, FONT_COLOR);
1033
+ }
1034
+ };
1073
1035
 
1074
1036
  /**
1075
- * The font color editing feature.
1076
- *
1077
- * It introduces the {@link module:font/fontcolor/fontcolorcommand~FontColorCommand command} and
1078
- * the `fontColor` attribute in the {@link module:engine/model/model~Model model} which renders
1079
- * in the {@link module:engine/view/view view} as a `<span>` element (`<span style="color: ...">`),
1080
- * depending on the {@link module:font/fontconfig~FontColorConfig configuration}.
1081
- */ class FontColorEditing extends Plugin {
1082
- /**
1083
- * @inheritDoc
1084
- */ static get pluginName() {
1085
- return 'FontColorEditing';
1086
- }
1087
- /**
1088
- * @inheritDoc
1089
- */ static get isOfficialPlugin() {
1090
- return true;
1091
- }
1092
- /**
1093
- * @inheritDoc
1094
- */ constructor(editor){
1095
- super(editor);
1096
- editor.config.define(FONT_COLOR, {
1097
- colors: [
1098
- {
1099
- color: 'hsl(0, 0%, 0%)',
1100
- label: 'Black'
1101
- },
1102
- {
1103
- color: 'hsl(0, 0%, 30%)',
1104
- label: 'Dim grey'
1105
- },
1106
- {
1107
- color: 'hsl(0, 0%, 60%)',
1108
- label: 'Grey'
1109
- },
1110
- {
1111
- color: 'hsl(0, 0%, 90%)',
1112
- label: 'Light grey'
1113
- },
1114
- {
1115
- color: 'hsl(0, 0%, 100%)',
1116
- label: 'White',
1117
- hasBorder: true
1118
- },
1119
- {
1120
- color: 'hsl(0, 75%, 60%)',
1121
- label: 'Red'
1122
- },
1123
- {
1124
- color: 'hsl(30, 75%, 60%)',
1125
- label: 'Orange'
1126
- },
1127
- {
1128
- color: 'hsl(60, 75%, 60%)',
1129
- label: 'Yellow'
1130
- },
1131
- {
1132
- color: 'hsl(90, 75%, 60%)',
1133
- label: 'Light green'
1134
- },
1135
- {
1136
- color: 'hsl(120, 75%, 60%)',
1137
- label: 'Green'
1138
- },
1139
- {
1140
- color: 'hsl(150, 75%, 60%)',
1141
- label: 'Aquamarine'
1142
- },
1143
- {
1144
- color: 'hsl(180, 75%, 60%)',
1145
- label: 'Turquoise'
1146
- },
1147
- {
1148
- color: 'hsl(210, 75%, 60%)',
1149
- label: 'Light blue'
1150
- },
1151
- {
1152
- color: 'hsl(240, 75%, 60%)',
1153
- label: 'Blue'
1154
- },
1155
- {
1156
- color: 'hsl(270, 75%, 60%)',
1157
- label: 'Purple'
1158
- }
1159
- ],
1160
- columns: 5
1161
- });
1162
- editor.conversion.for('upcast').elementToAttribute({
1163
- view: {
1164
- name: 'span',
1165
- styles: {
1166
- 'color': /[\s\S]+/
1167
- }
1168
- },
1169
- model: {
1170
- key: FONT_COLOR,
1171
- value: renderUpcastAttribute('color')
1172
- }
1173
- });
1174
- // Support legacy `<font color="..">` formatting.
1175
- editor.conversion.for('upcast').elementToAttribute({
1176
- view: {
1177
- name: 'font',
1178
- attributes: {
1179
- 'color': /^#?\w+$/
1180
- }
1181
- },
1182
- model: {
1183
- key: FONT_COLOR,
1184
- value: (viewElement)=>viewElement.getAttribute('color')
1185
- }
1186
- });
1187
- editor.conversion.for('downcast').attributeToElement({
1188
- model: FONT_COLOR,
1189
- view: renderDowncastElement('color')
1190
- });
1191
- editor.commands.add(FONT_COLOR, new FontColorCommand(editor));
1192
- // Allow the font color attribute on text nodes.
1193
- editor.model.schema.extend('$text', {
1194
- allowAttributes: FONT_COLOR
1195
- });
1196
- editor.model.schema.setAttributeProperties(FONT_COLOR, {
1197
- isFormatting: true,
1198
- copyOnEnter: true
1199
- });
1200
- }
1201
- }
1037
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
1038
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
1039
+ */
1040
+ /**
1041
+ * @module font/fontcolor/fontcolorediting
1042
+ */
1043
+ /**
1044
+ * The font color editing feature.
1045
+ *
1046
+ * It introduces the {@link module:font/fontcolor/fontcolorcommand~FontColorCommand command} and
1047
+ * the `fontColor` attribute in the {@link module:engine/model/model~Model model} which renders
1048
+ * in the {@link module:engine/view/view view} as a `<span>` element (`<span style="color: ...">`),
1049
+ * depending on the {@link module:font/fontconfig~FontColorConfig configuration}.
1050
+ */
1051
+ var FontColorEditing = class extends Plugin {
1052
+ /**
1053
+ * @inheritDoc
1054
+ */
1055
+ static get pluginName() {
1056
+ return "FontColorEditing";
1057
+ }
1058
+ /**
1059
+ * @inheritDoc
1060
+ */
1061
+ static get isOfficialPlugin() {
1062
+ return true;
1063
+ }
1064
+ /**
1065
+ * @inheritDoc
1066
+ */
1067
+ constructor(editor) {
1068
+ super(editor);
1069
+ editor.config.define(FONT_COLOR, {
1070
+ colors: [
1071
+ {
1072
+ color: "hsl(0, 0%, 0%)",
1073
+ label: "Black"
1074
+ },
1075
+ {
1076
+ color: "hsl(0, 0%, 30%)",
1077
+ label: "Dim grey"
1078
+ },
1079
+ {
1080
+ color: "hsl(0, 0%, 60%)",
1081
+ label: "Grey"
1082
+ },
1083
+ {
1084
+ color: "hsl(0, 0%, 90%)",
1085
+ label: "Light grey"
1086
+ },
1087
+ {
1088
+ color: "hsl(0, 0%, 100%)",
1089
+ label: "White",
1090
+ hasBorder: true
1091
+ },
1092
+ {
1093
+ color: "hsl(0, 75%, 60%)",
1094
+ label: "Red"
1095
+ },
1096
+ {
1097
+ color: "hsl(30, 75%, 60%)",
1098
+ label: "Orange"
1099
+ },
1100
+ {
1101
+ color: "hsl(60, 75%, 60%)",
1102
+ label: "Yellow"
1103
+ },
1104
+ {
1105
+ color: "hsl(90, 75%, 60%)",
1106
+ label: "Light green"
1107
+ },
1108
+ {
1109
+ color: "hsl(120, 75%, 60%)",
1110
+ label: "Green"
1111
+ },
1112
+ {
1113
+ color: "hsl(150, 75%, 60%)",
1114
+ label: "Aquamarine"
1115
+ },
1116
+ {
1117
+ color: "hsl(180, 75%, 60%)",
1118
+ label: "Turquoise"
1119
+ },
1120
+ {
1121
+ color: "hsl(210, 75%, 60%)",
1122
+ label: "Light blue"
1123
+ },
1124
+ {
1125
+ color: "hsl(240, 75%, 60%)",
1126
+ label: "Blue"
1127
+ },
1128
+ {
1129
+ color: "hsl(270, 75%, 60%)",
1130
+ label: "Purple"
1131
+ }
1132
+ ],
1133
+ columns: 5
1134
+ });
1135
+ editor.conversion.for("upcast").elementToAttribute({
1136
+ view: {
1137
+ name: "span",
1138
+ styles: { "color": /[\s\S]+/ }
1139
+ },
1140
+ model: {
1141
+ key: FONT_COLOR,
1142
+ value: renderUpcastAttribute("color")
1143
+ }
1144
+ });
1145
+ editor.conversion.for("upcast").elementToAttribute({
1146
+ view: {
1147
+ name: "font",
1148
+ attributes: { "color": /^#?\w+$/ }
1149
+ },
1150
+ model: {
1151
+ key: FONT_COLOR,
1152
+ value: (viewElement) => viewElement.getAttribute("color")
1153
+ }
1154
+ });
1155
+ editor.conversion.for("downcast").attributeToElement({
1156
+ model: FONT_COLOR,
1157
+ view: renderDowncastElement("color")
1158
+ });
1159
+ editor.commands.add(FONT_COLOR, new FontColorCommand(editor));
1160
+ editor.model.schema.extend("$text", { allowAttributes: FONT_COLOR });
1161
+ editor.model.schema.setAttributeProperties(FONT_COLOR, {
1162
+ isFormatting: true,
1163
+ copyOnEnter: true
1164
+ });
1165
+ }
1166
+ };
1202
1167
 
1203
1168
  /**
1204
- * The color UI plugin which isolates the common logic responsible for displaying dropdowns with color grids.
1205
- *
1206
- * It is used to create the `'fontBackgroundColor'` and `'fontColor'` dropdowns, each hosting
1207
- * a {@link module:ui/colorselector/colorselectorview~ColorSelectorView}.
1208
- */ class FontColorUIBase extends Plugin {
1209
- /**
1210
- * The name of the command which will be executed when a color tile is clicked.
1211
- */ commandName;
1212
- /**
1213
- * The name of this component in the {@link module:ui/componentfactory~ComponentFactory}.
1214
- * Also the configuration scope name in `editor.config`.
1215
- */ componentName;
1216
- /**
1217
- * The SVG icon used by the dropdown.
1218
- */ icon;
1219
- /**
1220
- * The label used by the dropdown.
1221
- */ dropdownLabel;
1222
- /**
1223
- * The number of columns in the color grid.
1224
- */ columns;
1225
- /**
1226
- * Creates a plugin which introduces a dropdown with a pre–configured
1227
- * {@link module:ui/colorselector/colorselectorview~ColorSelectorView}.
1228
- *
1229
- * @param editor An editor instance.
1230
- * @param config The configuration object.
1231
- * @param config.commandName The name of the command which will be executed when a color tile is clicked.
1232
- * @param config.componentName The name of the dropdown in the {@link module:ui/componentfactory~ComponentFactory}
1233
- * and the configuration scope name in `editor.config`.
1234
- * @param config.icon The SVG icon used by the dropdown.
1235
- * @param config.dropdownLabel The label used by the dropdown.
1236
- */ constructor(editor, { commandName, componentName, icon, dropdownLabel }){
1237
- super(editor);
1238
- this.commandName = commandName;
1239
- this.componentName = componentName;
1240
- this.icon = icon;
1241
- this.dropdownLabel = dropdownLabel;
1242
- this.columns = editor.config.get(`${this.componentName}.columns`);
1243
- }
1244
- /**
1169
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
1170
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
1171
+ */
1172
+ /**
1173
+ * @module font/ui/colorui
1174
+ */
1175
+ /**
1176
+ * The color UI plugin which isolates the common logic responsible for displaying dropdowns with color grids.
1177
+ *
1178
+ * It is used to create the `'fontBackgroundColor'` and `'fontColor'` dropdowns, each hosting
1179
+ * a {@link module:ui/colorselector/colorselectorview~ColorSelectorView}.
1180
+ */
1181
+ var FontColorUIBase = class extends Plugin {
1182
+ /**
1183
+ * The name of the command which will be executed when a color tile is clicked.
1184
+ */
1185
+ commandName;
1186
+ /**
1187
+ * The name of this component in the {@link module:ui/componentfactory~ComponentFactory}.
1188
+ * Also the configuration scope name in `editor.config`.
1189
+ */
1190
+ componentName;
1191
+ /**
1192
+ * The SVG icon used by the dropdown.
1193
+ */
1194
+ icon;
1195
+ /**
1196
+ * The label used by the dropdown.
1197
+ */
1198
+ dropdownLabel;
1199
+ /**
1200
+ * The number of columns in the color grid.
1201
+ */
1202
+ columns;
1203
+ /**
1204
+ * Creates a plugin which introduces a dropdown with a pre–configured
1205
+ * {@link module:ui/colorselector/colorselectorview~ColorSelectorView}.
1206
+ *
1207
+ * @param editor An editor instance.
1208
+ * @param config The configuration object.
1209
+ * @param config.commandName The name of the command which will be executed when a color tile is clicked.
1210
+ * @param config.componentName The name of the dropdown in the {@link module:ui/componentfactory~ComponentFactory}
1211
+ * and the configuration scope name in `editor.config`.
1212
+ * @param config.icon The SVG icon used by the dropdown.
1213
+ * @param config.dropdownLabel The label used by the dropdown.
1214
+ */
1215
+ constructor(editor, { commandName, componentName, icon, dropdownLabel }) {
1216
+ super(editor);
1217
+ this.commandName = commandName;
1218
+ this.componentName = componentName;
1219
+ this.icon = icon;
1220
+ this.dropdownLabel = dropdownLabel;
1221
+ this.columns = editor.config.get(`${this.componentName}.columns`);
1222
+ }
1223
+ /**
1245
1224
  * @inheritDoc
1246
- */ init() {
1247
- const editor = this.editor;
1248
- const locale = editor.locale;
1249
- const t = locale.t;
1250
- const command = editor.commands.get(this.commandName);
1251
- const componentConfig = editor.config.get(this.componentName);
1252
- const colorsConfig = normalizeColorOptions(componentConfig.colors);
1253
- const localizedColors = getLocalizedColorOptions(locale, colorsConfig);
1254
- const documentColorsCount = componentConfig.documentColors;
1255
- const hasColorPicker = componentConfig.colorPicker !== false;
1256
- // Register the UI component.
1257
- editor.ui.componentFactory.add(this.componentName, (locale)=>{
1258
- const dropdownView = createDropdown(locale);
1259
- // Font color dropdown rendering is deferred once it gets open to improve performance.
1260
- // See https://github.com/ckeditor/ckeditor5/issues/6192.
1261
- let dropdownContentRendered = false;
1262
- const colorSelectorView = addColorSelectorToDropdown({
1263
- dropdownView,
1264
- colors: localizedColors.map((option)=>({
1265
- label: option.label,
1266
- color: option.model,
1267
- options: {
1268
- hasBorder: option.hasBorder
1269
- }
1270
- })),
1271
- columns: this.columns,
1272
- removeButtonLabel: t('Remove color'),
1273
- colorPickerLabel: t('Color picker'),
1274
- documentColorsLabel: documentColorsCount !== 0 ? t('Document colors') : '',
1275
- documentColorsCount: documentColorsCount === undefined ? this.columns : documentColorsCount,
1276
- colorPickerViewConfig: hasColorPicker ? componentConfig.colorPicker || {} : false
1277
- });
1278
- colorSelectorView.bind('selectedColor').to(command, 'value');
1279
- dropdownView.buttonView.set({
1280
- label: this.dropdownLabel,
1281
- icon: this.icon,
1282
- tooltip: true
1283
- });
1284
- dropdownView.extendTemplate({
1285
- attributes: {
1286
- class: 'ck-color-ui-dropdown'
1287
- }
1288
- });
1289
- dropdownView.bind('isEnabled').to(command);
1290
- colorSelectorView.on('execute', (evt, data)=>{
1291
- if (dropdownView.isOpen) {
1292
- editor.execute(this.commandName, {
1293
- value: data.value,
1294
- batch: this._undoStepBatch
1295
- });
1296
- }
1297
- if (data.source !== 'colorPicker') {
1298
- editor.editing.view.focus();
1299
- }
1300
- if (data.source === 'colorPickerSaveButton') {
1301
- dropdownView.isOpen = false;
1302
- }
1303
- });
1304
- colorSelectorView.on('colorPicker:show', ()=>{
1305
- this._undoStepBatch = editor.model.createBatch();
1306
- });
1307
- colorSelectorView.on('colorPicker:cancel', ()=>{
1308
- if (this._undoStepBatch.operations.length) {
1309
- // We need to close the dropdown before the undo batch.
1310
- // Otherwise, FontColorUIBase treats undo as a selected color change,
1311
- // propagating the update to the whole selection.
1312
- // That's an issue if spans with various colors were selected.
1313
- dropdownView.isOpen = false;
1314
- editor.execute('undo', this._undoStepBatch);
1315
- }
1316
- editor.editing.view.focus();
1317
- });
1318
- dropdownView.on('change:isOpen', (evt, name, isVisible)=>{
1319
- if (!dropdownContentRendered) {
1320
- dropdownContentRendered = true;
1321
- dropdownView.colorSelectorView.appendUI();
1322
- }
1323
- if (isVisible) {
1324
- if (documentColorsCount !== 0) {
1325
- colorSelectorView.updateDocumentColors(editor.model, this.componentName);
1326
- }
1327
- colorSelectorView.updateSelectedColors();
1328
- colorSelectorView.showColorGridsFragment();
1329
- }
1330
- });
1331
- // Accessibility: focus the first active color when opening the dropdown.
1332
- focusChildOnDropdownOpen(dropdownView, ()=>dropdownView.colorSelectorView.colorGridsFragmentView.staticColorsGrid.items.find((item)=>item.isOn));
1333
- return dropdownView;
1334
- });
1335
- // Register menu bar button..
1336
- editor.ui.componentFactory.add(`menuBar:${this.componentName}`, (locale)=>{
1337
- const menuView = new MenuBarMenuView(locale);
1338
- menuView.buttonView.set({
1339
- label: this.dropdownLabel,
1340
- icon: this.icon
1341
- });
1342
- menuView.bind('isEnabled').to(command);
1343
- // Font color sub-menu rendering is deferred once it gets open to improve performance.
1344
- // See https://github.com/ckeditor/ckeditor5/issues/6192.
1345
- let contentRendered = false;
1346
- const colorSelectorView = new ColorSelectorView(locale, {
1347
- colors: localizedColors.map((option)=>({
1348
- label: option.label,
1349
- color: option.model,
1350
- options: {
1351
- hasBorder: option.hasBorder
1352
- }
1353
- })),
1354
- columns: this.columns,
1355
- removeButtonLabel: t('Remove color'),
1356
- colorPickerLabel: t('Color picker'),
1357
- documentColorsLabel: documentColorsCount !== 0 ? t('Document colors') : '',
1358
- documentColorsCount: documentColorsCount === undefined ? this.columns : documentColorsCount,
1359
- colorPickerViewConfig: false
1360
- });
1361
- colorSelectorView.bind('selectedColor').to(command, 'value');
1362
- colorSelectorView.delegate('execute').to(menuView);
1363
- colorSelectorView.on('execute', (evt, data)=>{
1364
- editor.execute(this.commandName, {
1365
- value: data.value,
1366
- batch: this._undoStepBatch
1367
- });
1368
- editor.editing.view.focus();
1369
- });
1370
- menuView.on('change:isOpen', (evt, name, isVisible)=>{
1371
- if (!contentRendered) {
1372
- contentRendered = true;
1373
- colorSelectorView.appendUI();
1374
- }
1375
- if (isVisible) {
1376
- if (documentColorsCount !== 0) {
1377
- colorSelectorView.updateDocumentColors(editor.model, this.componentName);
1378
- }
1379
- colorSelectorView.updateSelectedColors();
1380
- colorSelectorView.showColorGridsFragment();
1381
- }
1382
- });
1383
- menuView.panelView.children.add(colorSelectorView);
1384
- return menuView;
1385
- });
1386
- }
1387
- }
1225
+ */
1226
+ init() {
1227
+ const editor = this.editor;
1228
+ const locale = editor.locale;
1229
+ const t = locale.t;
1230
+ const command = editor.commands.get(this.commandName);
1231
+ const componentConfig = editor.config.get(this.componentName);
1232
+ const localizedColors = getLocalizedColorOptions(locale, normalizeColorOptions(componentConfig.colors));
1233
+ const documentColorsCount = componentConfig.documentColors;
1234
+ const hasColorPicker = componentConfig.colorPicker !== false;
1235
+ editor.ui.componentFactory.add(this.componentName, (locale) => {
1236
+ const dropdownView = createDropdown(locale);
1237
+ let dropdownContentRendered = false;
1238
+ const colorSelectorView = addColorSelectorToDropdown({
1239
+ dropdownView,
1240
+ colors: localizedColors.map((option) => ({
1241
+ label: option.label,
1242
+ color: option.model,
1243
+ options: { hasBorder: option.hasBorder }
1244
+ })),
1245
+ columns: this.columns,
1246
+ removeButtonLabel: t("Remove color"),
1247
+ colorPickerLabel: t("Color picker"),
1248
+ documentColorsLabel: documentColorsCount !== 0 ? t("Document colors") : "",
1249
+ documentColorsCount: documentColorsCount === void 0 ? this.columns : documentColorsCount,
1250
+ colorPickerViewConfig: hasColorPicker ? componentConfig.colorPicker || {} : false
1251
+ });
1252
+ colorSelectorView.bind("selectedColor").to(command, "value");
1253
+ dropdownView.buttonView.set({
1254
+ label: this.dropdownLabel,
1255
+ icon: this.icon,
1256
+ tooltip: true
1257
+ });
1258
+ dropdownView.extendTemplate({ attributes: { class: "ck-color-ui-dropdown" } });
1259
+ dropdownView.bind("isEnabled").to(command);
1260
+ colorSelectorView.on("execute", (evt, data) => {
1261
+ if (dropdownView.isOpen) editor.execute(this.commandName, {
1262
+ value: data.value,
1263
+ batch: this._undoStepBatch
1264
+ });
1265
+ if (data.source !== "colorPicker") editor.editing.view.focus();
1266
+ if (data.source === "colorPickerSaveButton") dropdownView.isOpen = false;
1267
+ });
1268
+ colorSelectorView.on("colorPicker:show", () => {
1269
+ this._undoStepBatch = editor.model.createBatch();
1270
+ });
1271
+ colorSelectorView.on("colorPicker:cancel", () => {
1272
+ if (this._undoStepBatch.operations.length) {
1273
+ dropdownView.isOpen = false;
1274
+ editor.execute("undo", this._undoStepBatch);
1275
+ }
1276
+ editor.editing.view.focus();
1277
+ });
1278
+ dropdownView.on("change:isOpen", (evt, name, isVisible) => {
1279
+ if (!dropdownContentRendered) {
1280
+ dropdownContentRendered = true;
1281
+ dropdownView.colorSelectorView.appendUI();
1282
+ }
1283
+ if (isVisible) {
1284
+ if (documentColorsCount !== 0) colorSelectorView.updateDocumentColors(editor.model, this.componentName);
1285
+ colorSelectorView.updateSelectedColors();
1286
+ colorSelectorView.showColorGridsFragment();
1287
+ }
1288
+ });
1289
+ focusChildOnDropdownOpen(dropdownView, () => dropdownView.colorSelectorView.colorGridsFragmentView.staticColorsGrid.items.find((item) => item.isOn));
1290
+ return dropdownView;
1291
+ });
1292
+ editor.ui.componentFactory.add(`menuBar:${this.componentName}`, (locale) => {
1293
+ const menuView = new MenuBarMenuView(locale);
1294
+ menuView.buttonView.set({
1295
+ label: this.dropdownLabel,
1296
+ icon: this.icon
1297
+ });
1298
+ menuView.bind("isEnabled").to(command);
1299
+ let contentRendered = false;
1300
+ const colorSelectorView = new ColorSelectorView(locale, {
1301
+ colors: localizedColors.map((option) => ({
1302
+ label: option.label,
1303
+ color: option.model,
1304
+ options: { hasBorder: option.hasBorder }
1305
+ })),
1306
+ columns: this.columns,
1307
+ removeButtonLabel: t("Remove color"),
1308
+ colorPickerLabel: t("Color picker"),
1309
+ documentColorsLabel: documentColorsCount !== 0 ? t("Document colors") : "",
1310
+ documentColorsCount: documentColorsCount === void 0 ? this.columns : documentColorsCount,
1311
+ colorPickerViewConfig: false
1312
+ });
1313
+ colorSelectorView.bind("selectedColor").to(command, "value");
1314
+ colorSelectorView.delegate("execute").to(menuView);
1315
+ colorSelectorView.on("execute", (evt, data) => {
1316
+ editor.execute(this.commandName, {
1317
+ value: data.value,
1318
+ batch: this._undoStepBatch
1319
+ });
1320
+ editor.editing.view.focus();
1321
+ });
1322
+ menuView.on("change:isOpen", (evt, name, isVisible) => {
1323
+ if (!contentRendered) {
1324
+ contentRendered = true;
1325
+ colorSelectorView.appendUI();
1326
+ }
1327
+ if (isVisible) {
1328
+ if (documentColorsCount !== 0) colorSelectorView.updateDocumentColors(editor.model, this.componentName);
1329
+ colorSelectorView.updateSelectedColors();
1330
+ colorSelectorView.showColorGridsFragment();
1331
+ }
1332
+ });
1333
+ menuView.panelView.children.add(colorSelectorView);
1334
+ return menuView;
1335
+ });
1336
+ }
1337
+ };
1388
1338
 
1389
1339
  /**
1390
- * The font color UI plugin. It introduces the `'fontColor'` dropdown.
1391
- */ class FontColorUI extends FontColorUIBase {
1392
- /**
1393
- * @inheritDoc
1394
- */ constructor(editor){
1395
- const t = editor.locale.t;
1396
- super(editor, {
1397
- commandName: FONT_COLOR,
1398
- componentName: FONT_COLOR,
1399
- icon: IconFontColor,
1400
- dropdownLabel: t('Font Color')
1401
- });
1402
- }
1403
- /**
1404
- * @inheritDoc
1405
- */ static get pluginName() {
1406
- return 'FontColorUI';
1407
- }
1408
- }
1340
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
1341
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
1342
+ */
1343
+ /**
1344
+ * @module font/fontcolor/fontcolorui
1345
+ */
1346
+ /**
1347
+ * The font color UI plugin. It introduces the `'fontColor'` dropdown.
1348
+ */
1349
+ var FontColorUI = class extends FontColorUIBase {
1350
+ /**
1351
+ * @inheritDoc
1352
+ */
1353
+ constructor(editor) {
1354
+ const t = editor.locale.t;
1355
+ super(editor, {
1356
+ commandName: FONT_COLOR,
1357
+ componentName: FONT_COLOR,
1358
+ icon: IconFontColor,
1359
+ dropdownLabel: t("Font Color")
1360
+ });
1361
+ }
1362
+ /**
1363
+ * @inheritDoc
1364
+ */
1365
+ static get pluginName() {
1366
+ return "FontColorUI";
1367
+ }
1368
+ };
1409
1369
 
1410
1370
  /**
1411
- * The font color plugin.
1412
- *
1413
- * For a detailed overview, check the {@glink features/font font feature} documentation
1414
- * and the {@glink api/font package page}.
1415
- *
1416
- * This is a "glue" plugin which loads the {@link module:font/fontcolor/fontcolorediting~FontColorEditing} and
1417
- * {@link module:font/fontcolor/fontcolorui~FontColorUI} features in the editor.
1418
- */ class FontColor extends Plugin {
1419
- /**
1420
- * @inheritDoc
1421
- */ static get requires() {
1422
- return [
1423
- FontColorEditing,
1424
- FontColorUI
1425
- ];
1426
- }
1427
- /**
1428
- * @inheritDoc
1429
- */ static get pluginName() {
1430
- return 'FontColor';
1431
- }
1432
- /**
1433
- * @inheritDoc
1434
- */ static get isOfficialPlugin() {
1435
- return true;
1436
- }
1437
- }
1371
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
1372
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
1373
+ */
1374
+ /**
1375
+ * @module font/fontcolor
1376
+ */
1377
+ /**
1378
+ * The font color plugin.
1379
+ *
1380
+ * For a detailed overview, check the {@glink features/font font feature} documentation
1381
+ * and the {@glink api/font package page}.
1382
+ *
1383
+ * This is a "glue" plugin which loads the {@link module:font/fontcolor/fontcolorediting~FontColorEditing} and
1384
+ * {@link module:font/fontcolor/fontcolorui~FontColorUI} features in the editor.
1385
+ */
1386
+ var FontColor = class extends Plugin {
1387
+ /**
1388
+ * @inheritDoc
1389
+ */
1390
+ static get requires() {
1391
+ return [FontColorEditing, FontColorUI];
1392
+ }
1393
+ /**
1394
+ * @inheritDoc
1395
+ */
1396
+ static get pluginName() {
1397
+ return "FontColor";
1398
+ }
1399
+ /**
1400
+ * @inheritDoc
1401
+ */
1402
+ static get isOfficialPlugin() {
1403
+ return true;
1404
+ }
1405
+ };
1438
1406
 
1439
1407
  /**
1440
- * The font background color command. It is used by
1441
- * {@link module:font/fontbackgroundcolor/fontbackgroundcolorediting~FontBackgroundColorEditing}
1442
- * to apply the font background color.
1443
- *
1444
- * ```ts
1445
- * editor.execute( 'fontBackgroundColor', { value: 'rgb(250, 20, 20)' } );
1446
- * ```
1447
- *
1448
- * **Note**: Executing the command with the `null` value removes the attribute from the model.
1449
- */ class FontBackgroundColorCommand extends FontCommand {
1450
- /**
1451
- * @inheritDoc
1452
- */ constructor(editor){
1453
- super(editor, FONT_BACKGROUND_COLOR);
1454
- }
1455
- }
1408
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
1409
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
1410
+ */
1411
+ /**
1412
+ * The font background color command. It is used by
1413
+ * {@link module:font/fontbackgroundcolor/fontbackgroundcolorediting~FontBackgroundColorEditing}
1414
+ * to apply the font background color.
1415
+ *
1416
+ * ```ts
1417
+ * editor.execute( 'fontBackgroundColor', { value: 'rgb(250, 20, 20)' } );
1418
+ * ```
1419
+ *
1420
+ * **Note**: Executing the command with the `null` value removes the attribute from the model.
1421
+ */
1422
+ var FontBackgroundColorCommand = class extends FontCommand {
1423
+ /**
1424
+ * @inheritDoc
1425
+ */
1426
+ constructor(editor) {
1427
+ super(editor, FONT_BACKGROUND_COLOR);
1428
+ }
1429
+ };
1456
1430
 
1457
1431
  /**
1458
- * The font background color editing feature.
1459
- *
1460
- * It introduces the {@link module:font/fontbackgroundcolor/fontbackgroundcolorcommand~FontBackgroundColorCommand command} and
1461
- * the `fontBackgroundColor` attribute in the {@link module:engine/model/model~Model model} which renders
1462
- * in the {@link module:engine/view/view view} as a `<span>` element (`<span style="background-color: ...">`),
1463
- * depending on the {@link module:font/fontconfig~FontColorConfig configuration}.
1464
- */ class FontBackgroundColorEditing extends Plugin {
1465
- /**
1466
- * @inheritDoc
1467
- */ static get pluginName() {
1468
- return 'FontBackgroundColorEditing';
1469
- }
1470
- /**
1471
- * @inheritDoc
1472
- */ static get isOfficialPlugin() {
1473
- return true;
1474
- }
1475
- /**
1476
- * @inheritDoc
1477
- */ constructor(editor){
1478
- super(editor);
1479
- editor.config.define(FONT_BACKGROUND_COLOR, {
1480
- colors: [
1481
- {
1482
- color: 'hsl(0, 0%, 0%)',
1483
- label: 'Black'
1484
- },
1485
- {
1486
- color: 'hsl(0, 0%, 30%)',
1487
- label: 'Dim grey'
1488
- },
1489
- {
1490
- color: 'hsl(0, 0%, 60%)',
1491
- label: 'Grey'
1492
- },
1493
- {
1494
- color: 'hsl(0, 0%, 90%)',
1495
- label: 'Light grey'
1496
- },
1497
- {
1498
- color: 'hsl(0, 0%, 100%)',
1499
- label: 'White',
1500
- hasBorder: true
1501
- },
1502
- {
1503
- color: 'hsl(0, 75%, 60%)',
1504
- label: 'Red'
1505
- },
1506
- {
1507
- color: 'hsl(30, 75%, 60%)',
1508
- label: 'Orange'
1509
- },
1510
- {
1511
- color: 'hsl(60, 75%, 60%)',
1512
- label: 'Yellow'
1513
- },
1514
- {
1515
- color: 'hsl(90, 75%, 60%)',
1516
- label: 'Light green'
1517
- },
1518
- {
1519
- color: 'hsl(120, 75%, 60%)',
1520
- label: 'Green'
1521
- },
1522
- {
1523
- color: 'hsl(150, 75%, 60%)',
1524
- label: 'Aquamarine'
1525
- },
1526
- {
1527
- color: 'hsl(180, 75%, 60%)',
1528
- label: 'Turquoise'
1529
- },
1530
- {
1531
- color: 'hsl(210, 75%, 60%)',
1532
- label: 'Light blue'
1533
- },
1534
- {
1535
- color: 'hsl(240, 75%, 60%)',
1536
- label: 'Blue'
1537
- },
1538
- {
1539
- color: 'hsl(270, 75%, 60%)',
1540
- label: 'Purple'
1541
- }
1542
- ],
1543
- columns: 5
1544
- });
1545
- editor.data.addStyleProcessorRules(addBackgroundStylesRules);
1546
- editor.conversion.for('upcast').elementToAttribute({
1547
- view: {
1548
- name: 'span',
1549
- styles: {
1550
- 'background-color': /[\s\S]+/
1551
- }
1552
- },
1553
- model: {
1554
- key: FONT_BACKGROUND_COLOR,
1555
- value: renderUpcastAttribute('background-color')
1556
- }
1557
- });
1558
- editor.conversion.for('downcast').attributeToElement({
1559
- model: FONT_BACKGROUND_COLOR,
1560
- view: renderDowncastElement('background-color')
1561
- });
1562
- editor.commands.add(FONT_BACKGROUND_COLOR, new FontBackgroundColorCommand(editor));
1563
- // Allow the font backgroundColor attribute on text nodes.
1564
- editor.model.schema.extend('$text', {
1565
- allowAttributes: FONT_BACKGROUND_COLOR
1566
- });
1567
- editor.model.schema.setAttributeProperties(FONT_BACKGROUND_COLOR, {
1568
- isFormatting: true,
1569
- copyOnEnter: true
1570
- });
1571
- }
1572
- }
1432
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
1433
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
1434
+ */
1435
+ /**
1436
+ * @module font/fontbackgroundcolor/fontbackgroundcolorediting
1437
+ */
1438
+ /**
1439
+ * The font background color editing feature.
1440
+ *
1441
+ * It introduces the {@link module:font/fontbackgroundcolor/fontbackgroundcolorcommand~FontBackgroundColorCommand command} and
1442
+ * the `fontBackgroundColor` attribute in the {@link module:engine/model/model~Model model} which renders
1443
+ * in the {@link module:engine/view/view view} as a `<span>` element (`<span style="background-color: ...">`),
1444
+ * depending on the {@link module:font/fontconfig~FontColorConfig configuration}.
1445
+ */
1446
+ var FontBackgroundColorEditing = class extends Plugin {
1447
+ /**
1448
+ * @inheritDoc
1449
+ */
1450
+ static get pluginName() {
1451
+ return "FontBackgroundColorEditing";
1452
+ }
1453
+ /**
1454
+ * @inheritDoc
1455
+ */
1456
+ static get isOfficialPlugin() {
1457
+ return true;
1458
+ }
1459
+ /**
1460
+ * @inheritDoc
1461
+ */
1462
+ constructor(editor) {
1463
+ super(editor);
1464
+ editor.config.define(FONT_BACKGROUND_COLOR, {
1465
+ colors: [
1466
+ {
1467
+ color: "hsl(0, 0%, 0%)",
1468
+ label: "Black"
1469
+ },
1470
+ {
1471
+ color: "hsl(0, 0%, 30%)",
1472
+ label: "Dim grey"
1473
+ },
1474
+ {
1475
+ color: "hsl(0, 0%, 60%)",
1476
+ label: "Grey"
1477
+ },
1478
+ {
1479
+ color: "hsl(0, 0%, 90%)",
1480
+ label: "Light grey"
1481
+ },
1482
+ {
1483
+ color: "hsl(0, 0%, 100%)",
1484
+ label: "White",
1485
+ hasBorder: true
1486
+ },
1487
+ {
1488
+ color: "hsl(0, 75%, 60%)",
1489
+ label: "Red"
1490
+ },
1491
+ {
1492
+ color: "hsl(30, 75%, 60%)",
1493
+ label: "Orange"
1494
+ },
1495
+ {
1496
+ color: "hsl(60, 75%, 60%)",
1497
+ label: "Yellow"
1498
+ },
1499
+ {
1500
+ color: "hsl(90, 75%, 60%)",
1501
+ label: "Light green"
1502
+ },
1503
+ {
1504
+ color: "hsl(120, 75%, 60%)",
1505
+ label: "Green"
1506
+ },
1507
+ {
1508
+ color: "hsl(150, 75%, 60%)",
1509
+ label: "Aquamarine"
1510
+ },
1511
+ {
1512
+ color: "hsl(180, 75%, 60%)",
1513
+ label: "Turquoise"
1514
+ },
1515
+ {
1516
+ color: "hsl(210, 75%, 60%)",
1517
+ label: "Light blue"
1518
+ },
1519
+ {
1520
+ color: "hsl(240, 75%, 60%)",
1521
+ label: "Blue"
1522
+ },
1523
+ {
1524
+ color: "hsl(270, 75%, 60%)",
1525
+ label: "Purple"
1526
+ }
1527
+ ],
1528
+ columns: 5
1529
+ });
1530
+ editor.data.addStyleProcessorRules(addBackgroundStylesRules);
1531
+ editor.conversion.for("upcast").elementToAttribute({
1532
+ view: {
1533
+ name: "span",
1534
+ styles: { "background-color": /[\s\S]+/ }
1535
+ },
1536
+ model: {
1537
+ key: FONT_BACKGROUND_COLOR,
1538
+ value: renderUpcastAttribute("background-color")
1539
+ }
1540
+ });
1541
+ editor.conversion.for("downcast").attributeToElement({
1542
+ model: FONT_BACKGROUND_COLOR,
1543
+ view: renderDowncastElement("background-color")
1544
+ });
1545
+ editor.commands.add(FONT_BACKGROUND_COLOR, new FontBackgroundColorCommand(editor));
1546
+ editor.model.schema.extend("$text", { allowAttributes: FONT_BACKGROUND_COLOR });
1547
+ editor.model.schema.setAttributeProperties(FONT_BACKGROUND_COLOR, {
1548
+ isFormatting: true,
1549
+ copyOnEnter: true
1550
+ });
1551
+ }
1552
+ };
1573
1553
 
1574
1554
  /**
1575
- * The font background color UI plugin. It introduces the `'fontBackgroundColor'` dropdown.
1576
- */ class FontBackgroundColorUI extends FontColorUIBase {
1577
- /**
1578
- * @inheritDoc
1579
- */ constructor(editor){
1580
- const t = editor.locale.t;
1581
- super(editor, {
1582
- commandName: FONT_BACKGROUND_COLOR,
1583
- componentName: FONT_BACKGROUND_COLOR,
1584
- icon: IconFontBackground,
1585
- dropdownLabel: t('Font Background Color')
1586
- });
1587
- }
1588
- /**
1589
- * @inheritDoc
1590
- */ static get pluginName() {
1591
- return 'FontBackgroundColorUI';
1592
- }
1593
- }
1555
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
1556
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
1557
+ */
1558
+ /**
1559
+ * @module font/fontbackgroundcolor/fontbackgroundcolorui
1560
+ */
1561
+ /**
1562
+ * The font background color UI plugin. It introduces the `'fontBackgroundColor'` dropdown.
1563
+ */
1564
+ var FontBackgroundColorUI = class extends FontColorUIBase {
1565
+ /**
1566
+ * @inheritDoc
1567
+ */
1568
+ constructor(editor) {
1569
+ const t = editor.locale.t;
1570
+ super(editor, {
1571
+ commandName: FONT_BACKGROUND_COLOR,
1572
+ componentName: FONT_BACKGROUND_COLOR,
1573
+ icon: IconFontBackground,
1574
+ dropdownLabel: t("Font Background Color")
1575
+ });
1576
+ }
1577
+ /**
1578
+ * @inheritDoc
1579
+ */
1580
+ static get pluginName() {
1581
+ return "FontBackgroundColorUI";
1582
+ }
1583
+ };
1594
1584
 
1595
1585
  /**
1596
- * The font background color plugin.
1597
- *
1598
- * For a detailed overview, check the {@glink features/font font feature} documentation
1599
- * and the {@glink api/font package page}.
1600
- *
1601
- * This is a "glue" plugin which loads
1602
- * the {@link module:font/fontbackgroundcolor/fontbackgroundcolorediting~FontBackgroundColorEditing} and
1603
- * {@link module:font/fontbackgroundcolor/fontbackgroundcolorui~FontBackgroundColorUI} features in the editor.
1604
- */ class FontBackgroundColor extends Plugin {
1605
- /**
1606
- * @inheritDoc
1607
- */ static get requires() {
1608
- return [
1609
- FontBackgroundColorEditing,
1610
- FontBackgroundColorUI
1611
- ];
1612
- }
1613
- /**
1614
- * @inheritDoc
1615
- */ static get pluginName() {
1616
- return 'FontBackgroundColor';
1617
- }
1618
- /**
1619
- * @inheritDoc
1620
- */ static get isOfficialPlugin() {
1621
- return true;
1622
- }
1623
- }
1586
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
1587
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
1588
+ */
1589
+ /**
1590
+ * @module font/fontbackgroundcolor
1591
+ */
1592
+ /**
1593
+ * The font background color plugin.
1594
+ *
1595
+ * For a detailed overview, check the {@glink features/font font feature} documentation
1596
+ * and the {@glink api/font package page}.
1597
+ *
1598
+ * This is a "glue" plugin which loads
1599
+ * the {@link module:font/fontbackgroundcolor/fontbackgroundcolorediting~FontBackgroundColorEditing} and
1600
+ * {@link module:font/fontbackgroundcolor/fontbackgroundcolorui~FontBackgroundColorUI} features in the editor.
1601
+ */
1602
+ var FontBackgroundColor = class extends Plugin {
1603
+ /**
1604
+ * @inheritDoc
1605
+ */
1606
+ static get requires() {
1607
+ return [FontBackgroundColorEditing, FontBackgroundColorUI];
1608
+ }
1609
+ /**
1610
+ * @inheritDoc
1611
+ */
1612
+ static get pluginName() {
1613
+ return "FontBackgroundColor";
1614
+ }
1615
+ /**
1616
+ * @inheritDoc
1617
+ */
1618
+ static get isOfficialPlugin() {
1619
+ return true;
1620
+ }
1621
+ };
1624
1622
 
1625
1623
  /**
1626
- * A plugin that enables a set of text styling features:
1627
- *
1628
- * * {@link module:font/fontsize~FontSize},
1629
- * * {@link module:font/fontfamily~FontFamily}.
1630
- * * {@link module:font/fontcolor~FontColor},
1631
- * * {@link module:font/fontbackgroundcolor~FontBackgroundColor}.
1632
- *
1633
- * For a detailed overview, check the {@glink features/font Font feature} documentation
1634
- * and the {@glink api/font package page}.
1635
- */ class Font extends Plugin {
1636
- /**
1637
- * @inheritDoc
1638
- */ static get requires() {
1639
- return [
1640
- FontFamily,
1641
- FontSize,
1642
- FontColor,
1643
- FontBackgroundColor
1644
- ];
1645
- }
1646
- /**
1647
- * @inheritDoc
1648
- */ static get pluginName() {
1649
- return 'Font';
1650
- }
1651
- /**
1652
- * @inheritDoc
1653
- */ static get isOfficialPlugin() {
1654
- return true;
1655
- }
1656
- }
1624
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
1625
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
1626
+ */
1627
+ /**
1628
+ * @module font/font
1629
+ */
1630
+ /**
1631
+ * A plugin that enables a set of text styling features:
1632
+ *
1633
+ * * {@link module:font/fontsize~FontSize},
1634
+ * * {@link module:font/fontfamily~FontFamily}.
1635
+ * * {@link module:font/fontcolor~FontColor},
1636
+ * * {@link module:font/fontbackgroundcolor~FontBackgroundColor}.
1637
+ *
1638
+ * For a detailed overview, check the {@glink features/font Font feature} documentation
1639
+ * and the {@glink api/font package page}.
1640
+ */
1641
+ var Font = class extends Plugin {
1642
+ /**
1643
+ * @inheritDoc
1644
+ */
1645
+ static get requires() {
1646
+ return [
1647
+ FontFamily,
1648
+ FontSize,
1649
+ FontColor,
1650
+ FontBackgroundColor
1651
+ ];
1652
+ }
1653
+ /**
1654
+ * @inheritDoc
1655
+ */
1656
+ static get pluginName() {
1657
+ return "Font";
1658
+ }
1659
+ /**
1660
+ * @inheritDoc
1661
+ */
1662
+ static get isOfficialPlugin() {
1663
+ return true;
1664
+ }
1665
+ };
1666
+
1667
+ /**
1668
+ * @license Copyright (c) 2003-2026, CKSource Holding sp. z o.o. All rights reserved.
1669
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-licensing-options
1670
+ */
1657
1671
 
1658
- export { Font, FontBackgroundColor, FontBackgroundColorCommand, FontBackgroundColorEditing, FontBackgroundColorUI, FontColor, FontColorCommand, FontColorEditing, FontColorUI, FontColorUIBase, FontCommand, FontFamily, FontFamilyCommand, FontFamilyEditing, FontFamilyUI, FontSize, FontSizeCommand, FontSizeEditing, FontSizeUI, addColorSelectorToDropdown as _addFontColorSelectorToDropdown, buildDefinition as _buildFontDefinition, normalizeOptions$1 as _normalizeFontFamilyOptions, normalizeOptions as _normalizeFontSizeOptions, renderDowncastElement as _renderDowncastFontElement, renderUpcastAttribute as _renderUpcastFontColorAttribute };
1659
- //# sourceMappingURL=index.js.map
1672
+ export { Font, FontBackgroundColor, FontBackgroundColorCommand, FontBackgroundColorEditing, FontBackgroundColorUI, FontColor, FontColorCommand, FontColorEditing, FontColorUI, FontColorUIBase, FontCommand, FontFamily, FontFamilyCommand, FontFamilyEditing, FontFamilyUI, FontSize, FontSizeCommand, FontSizeEditing, FontSizeUI, addColorSelectorToDropdown as _addFontColorSelectorToDropdown, buildDefinition as _buildFontDefinition, normalizeOptions as _normalizeFontFamilyOptions, normalizeOptions$1 as _normalizeFontSizeOptions, renderDowncastElement as _renderDowncastFontElement, renderUpcastAttribute as _renderUpcastFontColorAttribute };
1673
+ //# sourceMappingURL=index.js.map