aboutsummaryrefslogtreecommitdiff
path: root/sources/plugins/menu/plugin.js
diff options
context:
space:
mode:
Diffstat (limited to 'sources/plugins/menu/plugin.js')
-rw-r--r--sources/plugins/menu/plugin.js59
1 files changed, 43 insertions, 16 deletions
diff --git a/sources/plugins/menu/plugin.js b/sources/plugins/menu/plugin.js
index f5de4f9..3596e52 100644
--- a/sources/plugins/menu/plugin.js
+++ b/sources/plugins/menu/plugin.js
@@ -1,5 +1,5 @@
1/** 1/**
2 * @license Copyright (c) 2003-2016, CKSource - Frederico Knabben. All rights reserved. 2 * @license Copyright (c) 2003-2017, CKSource - Frederico Knabben. All rights reserved.
3 * For licensing, see LICENSE.md or http://ckeditor.com/license 3 * For licensing, see LICENSE.md or http://ckeditor.com/license
4 */ 4 */
5 5
@@ -41,10 +41,10 @@ CKEDITOR.plugins.add( 'menu', {
41 }; 41 };
42 42
43 /** 43 /**
44 * Adds one or more items from the specified definition array to the editor context menu. 44 * Adds one or more items from the specified definition object to the editor context menu.
45 * 45 *
46 * @method 46 * @method
47 * @param {Array} definitions List of definitions for each menu item as if {@link #addMenuItem} is called. 47 * @param {Object} definitions Object where keys are used as itemName and corresponding values as definition for a {@link #addMenuItem} call.
48 * @member CKEDITOR.editor 48 * @member CKEDITOR.editor
49 */ 49 */
50 editor.addMenuItems = function( definitions ) { 50 editor.addMenuItems = function( definitions ) {
@@ -85,12 +85,15 @@ CKEDITOR.plugins.add( 'menu', {
85 ' class="cke_menubutton cke_menubutton__{name} cke_menubutton_{state} {cls}" href="{href}"' + 85 ' class="cke_menubutton cke_menubutton__{name} cke_menubutton_{state} {cls}" href="{href}"' +
86 ' title="{title}"' + 86 ' title="{title}"' +
87 ' tabindex="-1"' + 87 ' tabindex="-1"' +
88 '_cke_focus=1' + 88 ' _cke_focus=1' +
89 ' hidefocus="true"' + 89 ' hidefocus="true"' +
90 ' role="{role}"' + 90 ' role="{role}"' +
91 ' aria-label="{label}"' +
92 ' aria-describedby="{id}_description"' +
91 ' aria-haspopup="{hasPopup}"' + 93 ' aria-haspopup="{hasPopup}"' +
92 ' aria-disabled="{disabled}"' + 94 ' aria-disabled="{disabled}"' +
93 ' {ariaChecked}'; 95 ' {ariaChecked}' +
96 ' draggable="false"';
94 97
95 // Some browsers don't cancel key events in the keydown but in the 98 // Some browsers don't cancel key events in the keydown but in the
96 // keypress. 99 // keypress.
@@ -99,11 +102,13 @@ CKEDITOR.plugins.add( 'menu', {
99 menuItemSource += ' onkeypress="return false;"'; 102 menuItemSource += ' onkeypress="return false;"';
100 103
101 // With Firefox, we need to force the button to redraw, otherwise it 104 // With Firefox, we need to force the button to redraw, otherwise it
102 // will remain in the focus state. 105 // will remain in the focus state. Also we some extra help to prevent dragging (http://dev.ckeditor.com/ticket/10373).
103 if ( CKEDITOR.env.gecko ) 106 if ( CKEDITOR.env.gecko ) {
104 menuItemSource += ' onblur="this.style.cssText = this.style.cssText;"'; 107 menuItemSource += ( ' onblur="this.style.cssText = this.style.cssText;"' +
108 ' ondragstart="return false;"' );
109 }
105 110
106 // #188 111 // http://dev.ckeditor.com/ticket/188
107 menuItemSource += ' onmouseover="CKEDITOR.tools.callFunction({hoverFn},{index});"' + 112 menuItemSource += ' onmouseover="CKEDITOR.tools.callFunction({hoverFn},{index});"' +
108 ' onmouseout="CKEDITOR.tools.callFunction({moveOutFn},{index});" ' + 113 ' onmouseout="CKEDITOR.tools.callFunction({moveOutFn},{index});" ' +
109 ( CKEDITOR.env.ie ? 'onclick="return false;" onmouseup' : 'onclick' ) + 114 ( CKEDITOR.env.ie ? 'onclick="return false;" onmouseup' : 'onclick' ) +
@@ -111,6 +116,7 @@ CKEDITOR.plugins.add( 'menu', {
111 '>'; 116 '>';
112 117
113 menuItemSource += 118 menuItemSource +=
119 //'' +
114 '<span class="cke_menubutton_inner">' + 120 '<span class="cke_menubutton_inner">' +
115 '<span class="cke_menubutton_icon">' + 121 '<span class="cke_menubutton_icon">' +
116 '<span class="cke_button_icon cke_button__{iconName}_icon" style="{iconStyle}"></span>' + 122 '<span class="cke_button_icon cke_button__{iconName}_icon" style="{iconStyle}"></span>' +
@@ -118,16 +124,22 @@ CKEDITOR.plugins.add( 'menu', {
118 '<span class="cke_menubutton_label">' + 124 '<span class="cke_menubutton_label">' +
119 '{label}' + 125 '{label}' +
120 '</span>' + 126 '</span>' +
127 '{shortcutHtml}' +
121 '{arrowHtml}' + 128 '{arrowHtml}' +
122 '</span>' + 129 '</span>' +
123 '</a></span>'; 130 '</a><span id="{id}_description" class="cke_voice_label" aria-hidden="false">{ariaShortcut}</span></span>';
124 131
125 var menuArrowSource = '<span class="cke_menuarrow">' + 132 var menuArrowSource = '<span class="cke_menuarrow">' +
126 '<span>{label}</span>' + 133 '<span>{label}</span>' +
127 '</span>'; 134 '</span>';
128 135
136 var menuShortcutSource = '<span class="cke_menubutton_label cke_menubutton_shortcut">' +
137 '{shortcut}' +
138 '</span>';
139
129 var menuItemTpl = CKEDITOR.addTemplate( 'menuItem', menuItemSource ), 140 var menuItemTpl = CKEDITOR.addTemplate( 'menuItem', menuItemSource ),
130 menuArrowTpl = CKEDITOR.addTemplate( 'menuArrow', menuArrowSource ); 141 menuArrowTpl = CKEDITOR.addTemplate( 'menuArrow', menuArrowSource ),
142 menuShortcutTpl = CKEDITOR.addTemplate( 'menuShortcut', menuShortcutSource );
131 143
132 /** 144 /**
133 * @class 145 * @class
@@ -246,7 +258,7 @@ CKEDITOR.plugins.add( 'menu', {
246 258
247 // Show the submenu. 259 // Show the submenu.
248 // This timeout is needed to give time for the sub-menu get 260 // This timeout is needed to give time for the sub-menu get
249 // focus when JAWS is running. (#9844) 261 // focus when JAWS is running. (http://dev.ckeditor.com/ticket/9844)
250 setTimeout( function() { 262 setTimeout( function() {
251 menu.show( element, 2 ); 263 menu.show( element, 2 );
252 }, 0 ); 264 }, 0 );
@@ -262,7 +274,7 @@ CKEDITOR.plugins.add( 'menu', {
262 add: function( item ) { 274 add: function( item ) {
263 // Later we may sort the items, but Array#sort is not stable in 275 // Later we may sort the items, but Array#sort is not stable in
264 // some browsers, here we're forcing the original sequence with 276 // some browsers, here we're forcing the original sequence with
265 // 'order' attribute if it hasn't been assigned. (#3868) 277 // 'order' attribute if it hasn't been assigned. (http://dev.ckeditor.com/ticket/3868)
266 if ( !item.order ) 278 if ( !item.order )
267 item.order = this.items.length; 279 item.order = this.items.length;
268 280
@@ -330,7 +342,7 @@ CKEDITOR.plugins.add( 'menu', {
330 keys[ CKEDITOR.SHIFT + 9 ] = 'prev'; // SHIFT + TAB 342 keys[ CKEDITOR.SHIFT + 9 ] = 'prev'; // SHIFT + TAB
331 keys[ ( editor.lang.dir == 'rtl' ? 37 : 39 ) ] = CKEDITOR.env.ie ? 'mouseup' : 'click'; // ARROW-RIGHT/ARROW-LEFT(rtl) 343 keys[ ( editor.lang.dir == 'rtl' ? 37 : 39 ) ] = CKEDITOR.env.ie ? 'mouseup' : 'click'; // ARROW-RIGHT/ARROW-LEFT(rtl)
332 keys[ 32 ] = CKEDITOR.env.ie ? 'mouseup' : 'click'; // SPACE 344 keys[ 32 ] = CKEDITOR.env.ie ? 'mouseup' : 'click'; // SPACE
333 CKEDITOR.env.ie && ( keys[ 13 ] = 'mouseup' ); // Manage ENTER, since onclick is blocked in IE (#8041). 345 CKEDITOR.env.ie && ( keys[ 13 ] = 'mouseup' ); // Manage ENTER, since onclick is blocked in IE (http://dev.ckeditor.com/ticket/8041).
334 346
335 element = this._.element = block.element; 347 element = this._.element = block.element;
336 348
@@ -462,7 +474,11 @@ CKEDITOR.plugins.add( 'menu', {
462 render: function( menu, index, output ) { 474 render: function( menu, index, output ) {
463 var id = menu.id + String( index ), 475 var id = menu.id + String( index ),
464 state = ( typeof this.state == 'undefined' ) ? CKEDITOR.TRISTATE_OFF : this.state, 476 state = ( typeof this.state == 'undefined' ) ? CKEDITOR.TRISTATE_OFF : this.state,
465 ariaChecked = ''; 477 ariaChecked = '',
478 editor = this.editor,
479 keystroke,
480 command,
481 shortcut;
466 482
467 var stateName = state == CKEDITOR.TRISTATE_ON ? 'on' : state == CKEDITOR.TRISTATE_DISABLED ? 'disabled' : 'off'; 483 var stateName = state == CKEDITOR.TRISTATE_ON ? 'on' : state == CKEDITOR.TRISTATE_DISABLED ? 'disabled' : 'off';
468 484
@@ -478,6 +494,15 @@ CKEDITOR.plugins.add( 'menu', {
478 if ( this.icon && !( /\./ ).test( this.icon ) ) 494 if ( this.icon && !( /\./ ).test( this.icon ) )
479 iconName = this.icon; 495 iconName = this.icon;
480 496
497 if ( this.command ) {
498 command = editor.getCommand( this.command );
499 keystroke = editor.getCommandKeystroke( command );
500
501 if ( keystroke ) {
502 shortcut = CKEDITOR.tools.keystrokeToString( editor.lang.common.keyboard, keystroke );
503 }
504 }
505
481 var params = { 506 var params = {
482 id: id, 507 id: id,
483 name: this.name, 508 name: this.name,
@@ -487,13 +512,15 @@ CKEDITOR.plugins.add( 'menu', {
487 state: stateName, 512 state: stateName,
488 hasPopup: hasSubMenu ? 'true' : 'false', 513 hasPopup: hasSubMenu ? 'true' : 'false',
489 disabled: state == CKEDITOR.TRISTATE_DISABLED, 514 disabled: state == CKEDITOR.TRISTATE_DISABLED,
490 title: this.label, 515 title: this.label + ( shortcut ? ' (' + shortcut.display + ')' : '' ),
516 ariaShortcut: shortcut ? editor.lang.common.keyboardShortcut + ' ' + shortcut.aria : '',
491 href: 'javascript:void(\'' + ( this.label || '' ).replace( "'" + '' ) + '\')', // jshint ignore:line 517 href: 'javascript:void(\'' + ( this.label || '' ).replace( "'" + '' ) + '\')', // jshint ignore:line
492 hoverFn: menu._.itemOverFn, 518 hoverFn: menu._.itemOverFn,
493 moveOutFn: menu._.itemOutFn, 519 moveOutFn: menu._.itemOutFn,
494 clickFn: menu._.itemClickFn, 520 clickFn: menu._.itemClickFn,
495 index: index, 521 index: index,
496 iconStyle: CKEDITOR.skin.getIconStyle( iconName, ( this.editor.lang.dir == 'rtl' ), iconName == this.icon ? null : this.icon, this.iconOffset ), 522 iconStyle: CKEDITOR.skin.getIconStyle( iconName, ( this.editor.lang.dir == 'rtl' ), iconName == this.icon ? null : this.icon, this.iconOffset ),
523 shortcutHtml: shortcut ? menuShortcutTpl.output( { shortcut: shortcut.display } ) : '',
497 arrowHtml: hasSubMenu ? menuArrowTpl.output( { label: arrowLabel } ) : '', 524 arrowHtml: hasSubMenu ? menuArrowTpl.output( { label: arrowLabel } ) : '',
498 role: this.role ? this.role : 'menuitem', 525 role: this.role ? this.role : 'menuitem',
499 ariaChecked: ariaChecked 526 ariaChecked: ariaChecked