Skip to content

Commit 1d4b560

Browse files
committed
Updated plugins text editor
1 parent b1c4279 commit 1d4b560

File tree

9 files changed

+265
-0
lines changed

9 files changed

+265
-0
lines changed
533 Bytes
Loading
576 Bytes
Loading
569 Bytes
Loading
549 Bytes
Loading
315 Bytes
Loading
564 Bytes
Loading
342 Bytes
Loading
348 Bytes
Loading
Lines changed: 265 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,265 @@
1+
/**
2+
* @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3+
* For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4+
*/
5+
6+
/**
7+
* @fileOverview Justify commands.
8+
*/
9+
10+
( function() {
11+
function getAlignment( element, useComputedState ) {
12+
13+
var align;
14+
if ( useComputedState )
15+
align = element.getComputedStyle( 'text-align' );
16+
else {
17+
while ( !element.hasAttribute || !( element.hasAttribute( 'align' ) || element.getStyle( 'text-align' ) ) ) {
18+
var parent = element.getParent();
19+
if ( !parent )
20+
break;
21+
element = parent;
22+
}
23+
align = element.getStyle( 'text-align' ) || element.getAttribute( 'align' ) || '';
24+
}
25+
26+
// Sometimes computed values doesn't tell.
27+
align && ( align = align.replace( /(?:-(?:moz|webkit)-)?(?:start|auto)/i, '' ) );
28+
29+
!align && useComputedState && ( align = element.getComputedStyle( 'direction' ) == 'rtl' ? 'right' : 'left' );
30+
31+
return align;
32+
}
33+
34+
function justifyCommand( editor, name, value ) {
35+
this.editor = editor;
36+
this.name = name;
37+
this.value = value;
38+
this.context = 'p';
39+
var classes = editor.config.justifyClasses,
40+
blockTag = editor.config.enterMode == CKEDITOR.ENTER_P ? 'p' : 'div';
41+
42+
if ( classes ) {
43+
switch ( value ) {
44+
case 'left':
45+
this.cssClassName = classes[ 0 ];
46+
break;
47+
case 'center':
48+
this.cssClassName = classes[ 1 ];
49+
break;
50+
case 'right':
51+
this.cssClassName = classes[ 2 ];
52+
break;
53+
case 'justify':
54+
this.cssClassName = classes[ 3 ];
55+
break;
56+
}
57+
58+
this.cssClassRegex = new RegExp( '(?:^|\\s+)(?:' + classes.join( '|' ) + ')(?=$|\\s)' );
59+
this.requiredContent = blockTag + '(' + this.cssClassName + ')';
60+
}
61+
else {
62+
this.requiredContent = blockTag + '{text-align}';
63+
}
64+
65+
this.allowedContent = {
66+
'caption div h1 h2 h3 h4 h5 h6 p pre td th li': {
67+
// Do not add elements, but only text-align style if element is validated by other rule.
68+
propertiesOnly: true,
69+
styles: this.cssClassName ? null : 'text-align',
70+
classes: this.cssClassName || null
71+
}
72+
};
73+
74+
// In enter mode BR we need to allow here for div, because when non other
75+
// feature allows div justify is the only plugin that uses it.
76+
if ( editor.config.enterMode == CKEDITOR.ENTER_BR )
77+
this.allowedContent.div = true;
78+
}
79+
80+
function onDirChanged( e ) {
81+
var editor = e.editor;
82+
83+
var range = editor.createRange();
84+
range.setStartBefore( e.data.node );
85+
range.setEndAfter( e.data.node );
86+
87+
var walker = new CKEDITOR.dom.walker( range ),
88+
node;
89+
90+
while ( ( node = walker.next() ) ) {
91+
if ( node.type == CKEDITOR.NODE_ELEMENT ) {
92+
// A child with the defined dir is to be ignored.
93+
if ( !node.equals( e.data.node ) && node.getDirection() ) {
94+
range.setStartAfter( node );
95+
walker = new CKEDITOR.dom.walker( range );
96+
continue;
97+
}
98+
99+
// Switch the alignment.
100+
var classes = editor.config.justifyClasses;
101+
if ( classes ) {
102+
// The left align class.
103+
if ( node.hasClass( classes[ 0 ] ) ) {
104+
node.removeClass( classes[ 0 ] );
105+
node.addClass( classes[ 2 ] );
106+
}
107+
// The right align class.
108+
else if ( node.hasClass( classes[ 2 ] ) ) {
109+
node.removeClass( classes[ 2 ] );
110+
node.addClass( classes[ 0 ] );
111+
}
112+
}
113+
114+
// Always switch CSS margins.
115+
var style = 'text-align';
116+
var align = node.getStyle( style );
117+
118+
if ( align == 'left' )
119+
node.setStyle( style, 'right' );
120+
else if ( align == 'right' )
121+
node.setStyle( style, 'left' );
122+
}
123+
}
124+
}
125+
126+
justifyCommand.prototype = {
127+
exec: function( editor ) {
128+
var selection = editor.getSelection(),
129+
enterMode = editor.config.enterMode;
130+
131+
if ( !selection )
132+
return;
133+
134+
var bookmarks = selection.createBookmarks(),
135+
ranges = selection.getRanges();
136+
137+
var cssClassName = this.cssClassName,
138+
iterator, block;
139+
140+
var useComputedState = editor.config.useComputedState;
141+
142+
for ( var i = ranges.length - 1; i >= 0; i-- ) {
143+
iterator = ranges[ i ].createIterator();
144+
iterator.enlargeBr = enterMode != CKEDITOR.ENTER_BR;
145+
146+
while ( ( block = iterator.getNextParagraph( enterMode == CKEDITOR.ENTER_P ? 'p' : 'div' ) ) ) {
147+
if ( block.isReadOnly() )
148+
continue;
149+
150+
// Check if style or class might be applied to currently processed element (#455).
151+
var tag = block.getName(),
152+
isAllowedTextAlign, isAllowedCssClass;
153+
154+
isAllowedTextAlign = editor.activeFilter.check( tag + '{text-align}' );
155+
isAllowedCssClass = editor.activeFilter.check( tag + '(' + cssClassName + ')' );
156+
157+
if ( !isAllowedCssClass && !isAllowedTextAlign ) {
158+
continue;
159+
}
160+
161+
block.removeAttribute( 'align' );
162+
block.removeStyle( 'text-align' );
163+
164+
// Remove any of the alignment classes from the className.
165+
var className = cssClassName && ( block.$.className = CKEDITOR.tools.ltrim( block.$.className.replace( this.cssClassRegex, '' ) ) );
166+
167+
var apply = ( this.state == CKEDITOR.TRISTATE_OFF ) && ( !useComputedState || ( getAlignment( block, true ) != this.value ) );
168+
169+
if ( cssClassName && isAllowedCssClass ) {
170+
// Append the desired class name.
171+
if ( apply )
172+
block.addClass( cssClassName );
173+
else if ( !className )
174+
block.removeAttribute( 'class' );
175+
} else if ( apply && isAllowedTextAlign ) {
176+
block.setStyle( 'text-align', this.value );
177+
}
178+
}
179+
180+
}
181+
182+
editor.focus();
183+
editor.forceNextSelectionCheck();
184+
selection.selectBookmarks( bookmarks );
185+
},
186+
187+
refresh: function( editor, path ) {
188+
var firstBlock = path.block || path.blockLimit,
189+
name = firstBlock.getName(),
190+
isEditable = firstBlock.equals( editor.editable() ),
191+
isStylable = this.cssClassName ? editor.activeFilter.check( name + '(' + this.cssClassName + ')' ) :
192+
editor.activeFilter.check( name + '{text-align}' );
193+
194+
// #455
195+
// 1. Check if we are directly in editbale. Justification should be always allowed, and not highlighted.
196+
// Checking situation `body > ul` where ul is selected and path.blockLimit returns editable.
197+
// 2. Check if current element can have applied specific class.
198+
// 3. Check if current element can have applied text-align style.
199+
if ( isEditable && !CKEDITOR.dtd.$list[ path.lastElement.getName() ] ) {
200+
this.setState( CKEDITOR.TRISTATE_OFF );
201+
} else if ( !isEditable && isStylable ) {
202+
// 2 & 3 in one condition.
203+
this.setState( getAlignment( firstBlock, this.editor.config.useComputedState ) == this.value ? CKEDITOR.TRISTATE_ON : CKEDITOR.TRISTATE_OFF );
204+
} else {
205+
this.setState( CKEDITOR.TRISTATE_DISABLED );
206+
}
207+
}
208+
};
209+
210+
CKEDITOR.plugins.add( 'justify', {
211+
icons: 'justifyblock,justifycenter,justifyleft,justifyright', // %REMOVE_LINE_CORE%
212+
hidpi: true, // %REMOVE_LINE_CORE%
213+
init: function( editor ) {
214+
if ( editor.blockless )
215+
return;
216+
217+
var left = new justifyCommand( editor, 'justifyleft', 'left' ),
218+
center = new justifyCommand( editor, 'justifycenter', 'center' ),
219+
right = new justifyCommand( editor, 'justifyright', 'right' ),
220+
justify = new justifyCommand( editor, 'justifyblock', 'justify' );
221+
222+
editor.addCommand( 'justifyleft', left );
223+
editor.addCommand( 'justifycenter', center );
224+
editor.addCommand( 'justifyright', right );
225+
editor.addCommand( 'justifyblock', justify );
226+
227+
if ( editor.ui.addButton ) {
228+
editor.ui.addButton( 'JustifyLeft', {
229+
label: editor.lang.common.alignLeft,
230+
command: 'justifyleft',
231+
toolbar: 'align,10'
232+
} );
233+
editor.ui.addButton( 'JustifyCenter', {
234+
label: editor.lang.common.center,
235+
command: 'justifycenter',
236+
toolbar: 'align,20'
237+
} );
238+
editor.ui.addButton( 'JustifyRight', {
239+
label: editor.lang.common.alignRight,
240+
command: 'justifyright',
241+
toolbar: 'align,30'
242+
} );
243+
editor.ui.addButton( 'JustifyBlock', {
244+
label: editor.lang.common.justify,
245+
command: 'justifyblock',
246+
toolbar: 'align,40'
247+
} );
248+
}
249+
editor.on( 'dirChanged', onDirChanged );
250+
}
251+
} );
252+
} )();
253+
254+
/**
255+
* List of classes to use for aligning the contents. If it's `null`, no classes will be used
256+
* and instead the corresponding CSS values will be used.
257+
*
258+
* The array should contain 4 members, in the following order: left, center, right, justify.
259+
*
260+
* // Use the classes 'AlignLeft', 'AlignCenter', 'AlignRight', 'AlignJustify'
261+
* config.justifyClasses = [ 'AlignLeft', 'AlignCenter', 'AlignRight', 'AlignJustify' ];
262+
*
263+
* @cfg {Array} [justifyClasses=null]
264+
* @member CKEDITOR.config
265+
*/

0 commit comments

Comments
 (0)