1(function () {
2var inlite = (function (domGlobals) {
3 'use strict';
4
5 var global = tinymce.util.Tools.resolve('tinymce.ThemeManager');
6
7 var global$1 = tinymce.util.Tools.resolve('tinymce.Env');
8
9 var global$2 = tinymce.util.Tools.resolve('tinymce.dom.DOMUtils');
10
11 var global$3 = tinymce.util.Tools.resolve('tinymce.util.Delay');
12
13 var flatten = function (arr) {
14 return arr.reduce(function (results, item) {
15 return Array.isArray(item) ? results.concat(flatten(item)) : results.concat(item);
16 }, []);
17 };
18 var DeepFlatten = { flatten: flatten };
19
20 var result = function (id, rect) {
21 return {
22 id: id,
23 rect: rect
24 };
25 };
26 var match = function (editor, matchers) {
27 for (var i = 0; i < matchers.length; i++) {
28 var f = matchers[i];
29 var result_1 = f(editor);
30 if (result_1) {
31 return result_1;
32 }
33 }
34 return null;
35 };
36 var Matcher = {
37 match: match,
38 result: result
39 };
40
41 var fromClientRect = function (clientRect) {
42 return {
43 x: clientRect.left,
44 y: clientRect.top,
45 w: clientRect.width,
46 h: clientRect.height
47 };
48 };
49 var toClientRect = function (geomRect) {
50 return {
51 left: geomRect.x,
52 top: geomRect.y,
53 width: geomRect.w,
54 height: geomRect.h,
55 right: geomRect.x + geomRect.w,
56 bottom: geomRect.y + geomRect.h
57 };
58 };
59 var Convert = {
60 fromClientRect: fromClientRect,
61 toClientRect: toClientRect
62 };
63
64 var toAbsolute = function (rect) {
65 var vp = global$2.DOM.getViewPort();
66 return {
67 x: rect.x + vp.x,
68 y: rect.y + vp.y,
69 w: rect.w,
70 h: rect.h
71 };
72 };
73 var measureElement = function (elm) {
74 var clientRect = elm.getBoundingClientRect();
75 return toAbsolute({
76 x: clientRect.left,
77 y: clientRect.top,
78 w: Math.max(elm.clientWidth, elm.offsetWidth),
79 h: Math.max(elm.clientHeight, elm.offsetHeight)
80 });
81 };
82 var getElementRect = function (editor, elm) {
83 return measureElement(elm);
84 };
85 var getPageAreaRect = function (editor) {
86 return measureElement(editor.getElement().ownerDocument.body);
87 };
88 var getContentAreaRect = function (editor) {
89 return measureElement(editor.getContentAreaContainer() || editor.getBody());
90 };
91 var getSelectionRect = function (editor) {
92 var clientRect = editor.selection.getBoundingClientRect();
93 return clientRect ? toAbsolute(Convert.fromClientRect(clientRect)) : null;
94 };
95 var Measure = {
96 getElementRect: getElementRect,
97 getPageAreaRect: getPageAreaRect,
98 getContentAreaRect: getContentAreaRect,
99 getSelectionRect: getSelectionRect
100 };
101
102 var element = function (element, predicateIds) {
103 return function (editor) {
104 for (var i = 0; i < predicateIds.length; i++) {
105 if (predicateIds[i].predicate(element)) {
106 var result = Matcher.result(predicateIds[i].id, Measure.getElementRect(editor, element));
107 return result;
108 }
109 }
110 return null;
111 };
112 };
113 var parent = function (elements, predicateIds) {
114 return function (editor) {
115 for (var i = 0; i < elements.length; i++) {
116 for (var x = 0; x < predicateIds.length; x++) {
117 if (predicateIds[x].predicate(elements[i])) {
118 return Matcher.result(predicateIds[x].id, Measure.getElementRect(editor, elements[i]));
119 }
120 }
121 }
122 return null;
123 };
124 };
125 var ElementMatcher = {
126 element: element,
127 parent: parent
128 };
129
130 var global$4 = tinymce.util.Tools.resolve('tinymce.util.Tools');
131
132 var create = function (id, predicate) {
133 return {
134 id: id,
135 predicate: predicate
136 };
137 };
138 var fromContextToolbars = function (toolbars) {
139 return global$4.map(toolbars, function (toolbar) {
140 return create(toolbar.id, toolbar.predicate);
141 });
142 };
143 var PredicateId = {
144 create: create,
145 fromContextToolbars: fromContextToolbars
146 };
147
148 var textSelection = function (id) {
149 return function (editor) {
150 if (!editor.selection.isCollapsed()) {
151 var result = Matcher.result(id, Measure.getSelectionRect(editor));
152 return result;
153 }
154 return null;
155 };
156 };
157 var emptyTextBlock = function (elements, id) {
158 return function (editor) {
159 var i;
160 var textBlockElementsMap = editor.schema.getTextBlockElements();
161 for (i = 0; i < elements.length; i++) {
162 if (elements[i].nodeName === 'TABLE') {
163 return null;
164 }
165 }
166 for (i = 0; i < elements.length; i++) {
167 if (elements[i].nodeName in textBlockElementsMap) {
168 if (editor.dom.isEmpty(elements[i])) {
169 return Matcher.result(id, Measure.getSelectionRect(editor));
170 }
171 return null;
172 }
173 }
174 return null;
175 };
176 };
177 var SelectionMatcher = {
178 textSelection: textSelection,
179 emptyTextBlock: emptyTextBlock
180 };
181
182 var fireSkinLoaded = function (editor) {
183 editor.fire('SkinLoaded');
184 };
185 var fireBeforeRenderUI = function (editor) {
186 return editor.fire('BeforeRenderUI');
187 };
188 var Events = {
189 fireSkinLoaded: fireSkinLoaded,
190 fireBeforeRenderUI: fireBeforeRenderUI
191 };
192
193 var global$5 = tinymce.util.Tools.resolve('tinymce.EditorManager');
194
195 var isType = function (type) {
196 return function (value) {
197 return typeof value === type;
198 };
199 };
200 var isArray = function (value) {
201 return Array.isArray(value);
202 };
203 var isNull = function (value) {
204 return value === null;
205 };
206 var isObject = function (predicate) {
207 return function (value) {
208 return !isNull(value) && !isArray(value) && predicate(value);
209 };
210 };
211 var isString = function (value) {
212 return isType('string')(value);
213 };
214 var isNumber = function (value) {
215 return isType('number')(value);
216 };
217 var isFunction = function (value) {
218 return isType('function')(value);
219 };
220 var isBoolean = function (value) {
221 return isType('boolean')(value);
222 };
223 var Type = {
224 isString: isString,
225 isNumber: isNumber,
226 isBoolean: isBoolean,
227 isFunction: isFunction,
228 isObject: isObject(isType('object')),
229 isNull: isNull,
230 isArray: isArray
231 };
232
233 var validDefaultOrDie = function (value, predicate) {
234 if (predicate(value)) {
235 return true;
236 }
237 throw new Error('Default value doesn\'t match requested type.');
238 };
239 var getByTypeOr = function (predicate) {
240 return function (editor, name, defaultValue) {
241 var settings = editor.settings;
242 validDefaultOrDie(defaultValue, predicate);
243 return name in settings && predicate(settings[name]) ? settings[name] : defaultValue;
244 };
245 };
246 var splitNoEmpty = function (str, delim) {
247 return str.split(delim).filter(function (item) {
248 return item.length > 0;
249 });
250 };
251 var itemsToArray = function (value, defaultValue) {
252 var stringToItemsArray = function (value) {
253 return typeof value === 'string' ? splitNoEmpty(value, /[ ,]/) : value;
254 };
255 var boolToItemsArray = function (value, defaultValue) {
256 return value === false ? [] : defaultValue;
257 };
258 if (Type.isArray(value)) {
259 return value;
260 } else if (Type.isString(value)) {
261 return stringToItemsArray(value);
262 } else if (Type.isBoolean(value)) {
263 return boolToItemsArray(value, defaultValue);
264 }
265 return defaultValue;
266 };
267 var getToolbarItemsOr = function (predicate) {
268 return function (editor, name, defaultValue) {
269 var value = name in editor.settings ? editor.settings[name] : defaultValue;
270 validDefaultOrDie(defaultValue, predicate);
271 return itemsToArray(value, defaultValue);
272 };
273 };
274 var EditorSettings = {
275 getStringOr: getByTypeOr(Type.isString),
276 getBoolOr: getByTypeOr(Type.isBoolean),
277 getNumberOr: getByTypeOr(Type.isNumber),
278 getHandlerOr: getByTypeOr(Type.isFunction),
279 getToolbarItemsOr: getToolbarItemsOr(Type.isArray)
280 };
281
282 var global$6 = tinymce.util.Tools.resolve('tinymce.geom.Rect');
283
284 var result$1 = function (rect, position) {
285 return {
286 rect: rect,
287 position: position
288 };
289 };
290 var moveTo = function (rect, toRect) {
291 return {
292 x: toRect.x,
293 y: toRect.y,
294 w: rect.w,
295 h: rect.h
296 };
297 };
298 var calcByPositions = function (testPositions1, testPositions2, targetRect, contentAreaRect, panelRect) {
299 var relPos, relRect, outputPanelRect;
300 var paddedContentRect = {
301 x: contentAreaRect.x,
302 y: contentAreaRect.y,
303 w: contentAreaRect.w + (contentAreaRect.w < panelRect.w + targetRect.w ? panelRect.w : 0),
304 h: contentAreaRect.h + (contentAreaRect.h < panelRect.h + targetRect.h ? panelRect.h : 0)
305 };
306 relPos = global$6.findBestRelativePosition(panelRect, targetRect, paddedContentRect, testPositions1);
307 targetRect = global$6.clamp(targetRect, paddedContentRect);
308 if (relPos) {
309 relRect = global$6.relativePosition(panelRect, targetRect, relPos);
310 outputPanelRect = moveTo(panelRect, relRect);
311 return result$1(outputPanelRect, relPos);
312 }
313 targetRect = global$6.intersect(paddedContentRect, targetRect);
314 if (targetRect) {
315 relPos = global$6.findBestRelativePosition(panelRect, targetRect, paddedContentRect, testPositions2);
316 if (relPos) {
317 relRect = global$6.relativePosition(panelRect, targetRect, relPos);
318 outputPanelRect = moveTo(panelRect, relRect);
319 return result$1(outputPanelRect, relPos);
320 }
321 outputPanelRect = moveTo(panelRect, targetRect);
322 return result$1(outputPanelRect, relPos);
323 }
324 return null;
325 };
326 var calcInsert = function (targetRect, contentAreaRect, panelRect) {
327 return calcByPositions([
328 'cr-cl',
329 'cl-cr'
330 ], [
331 'bc-tc',
332 'bl-tl',
333 'br-tr'
334 ], targetRect, contentAreaRect, panelRect);
335 };
336 var calc = function (targetRect, contentAreaRect, panelRect) {
337 return calcByPositions([
338 'tc-bc',
339 'bc-tc',
340 'tl-bl',
341 'bl-tl',
342 'tr-br',
343 'br-tr',
344 'cr-cl',
345 'cl-cr'
346 ], [
347 'bc-tc',
348 'bl-tl',
349 'br-tr',
350 'cr-cl'
351 ], targetRect, contentAreaRect, panelRect);
352 };
353 var userConstrain = function (handler, targetRect, contentAreaRect, panelRect) {
354 var userConstrainedPanelRect;
355 if (typeof handler === 'function') {
356 userConstrainedPanelRect = handler({
357 elementRect: Convert.toClientRect(targetRect),
358 contentAreaRect: Convert.toClientRect(contentAreaRect),
359 panelRect: Convert.toClientRect(panelRect)
360 });
361 return Convert.fromClientRect(userConstrainedPanelRect);
362 }
363 return panelRect;
364 };
365 var defaultHandler = function (rects) {
366 return rects.panelRect;
367 };
368 var Layout = {
369 calcInsert: calcInsert,
370 calc: calc,
371 userConstrain: userConstrain,
372 defaultHandler: defaultHandler
373 };
374
375 var toAbsoluteUrl = function (editor, url) {
376 return editor.documentBaseURI.toAbsolute(url);
377 };
378 var urlFromName = function (name) {
379 var prefix = global$5.baseURL + '/skins/';
380 return name ? prefix + name : prefix + 'lightgray';
381 };
382 var getTextSelectionToolbarItems = function (editor) {
383 return EditorSettings.getToolbarItemsOr(editor, 'selection_toolbar', [
384 'bold',
385 'italic',
386 '|',
387 'quicklink',
388 'h2',
389 'h3',
390 'blockquote'
391 ]);
392 };
393 var getInsertToolbarItems = function (editor) {
394 return EditorSettings.getToolbarItemsOr(editor, 'insert_toolbar', [
395 'quickimage',
396 'quicktable'
397 ]);
398 };
399 var getPositionHandler = function (editor) {
400 return EditorSettings.getHandlerOr(editor, 'inline_toolbar_position_handler', Layout.defaultHandler);
401 };
402 var getSkinUrl = function (editor) {
403 var settings = editor.settings;
404 return settings.skin_url ? toAbsoluteUrl(editor, settings.skin_url) : urlFromName(settings.skin);
405 };
406 var isSkinDisabled = function (editor) {
407 return editor.settings.skin === false;
408 };
409 var Settings = {
410 getTextSelectionToolbarItems: getTextSelectionToolbarItems,
411 getInsertToolbarItems: getInsertToolbarItems,
412 getPositionHandler: getPositionHandler,
413 getSkinUrl: getSkinUrl,
414 isSkinDisabled: isSkinDisabled
415 };
416
417 var fireSkinLoaded$1 = function (editor, callback) {
418 var done = function () {
419 editor._skinLoaded = true;
420 Events.fireSkinLoaded(editor);
421 callback();
422 };
423 if (editor.initialized) {
424 done();
425 } else {
426 editor.on('init', done);
427 }
428 };
429 var load = function (editor, callback) {
430 var skinUrl = Settings.getSkinUrl(editor);
431 var done = function () {
432 fireSkinLoaded$1(editor, callback);
433 };
434 if (Settings.isSkinDisabled(editor)) {
435 done();
436 } else {
437 global$2.DOM.styleSheetLoader.load(skinUrl + '/skin.min.css', done);
438 editor.contentCSS.push(skinUrl + '/content.inline.min.css');
439 }
440 };
441 var SkinLoader = { load: load };
442
443 var getSelectionElements = function (editor) {
444 var node = editor.selection.getNode();
445 var elms = editor.dom.getParents(node, '*');
446 return elms;
447 };
448 var createToolbar = function (editor, selector, id, items) {
449 var selectorPredicate = function (elm) {
450 return editor.dom.is(elm, selector);
451 };
452 return {
453 predicate: selectorPredicate,
454 id: id,
455 items: items
456 };
457 };
458 var getToolbars = function (editor) {
459 var contextToolbars = editor.contextToolbars;
460 return DeepFlatten.flatten([
461 contextToolbars ? contextToolbars : [],
462 createToolbar(editor, 'img', 'image', 'alignleft aligncenter alignright')
463 ]);
464 };
465 var findMatchResult = function (editor, toolbars) {
466 var result, elements, contextToolbarsPredicateIds;
467 elements = getSelectionElements(editor);
468 contextToolbarsPredicateIds = PredicateId.fromContextToolbars(toolbars);
469 result = Matcher.match(editor, [
470 ElementMatcher.element(elements[0], contextToolbarsPredicateIds),
471 SelectionMatcher.textSelection('text'),
472 SelectionMatcher.emptyTextBlock(elements, 'insert'),
473 ElementMatcher.parent(elements, contextToolbarsPredicateIds)
474 ]);
475 return result && result.rect ? result : null;
476 };
477 var editorHasFocus = function (editor) {
478 return domGlobals.document.activeElement === editor.getBody();
479 };
480 var togglePanel = function (editor, panel) {
481 var toggle = function () {
482 var toolbars = getToolbars(editor);
483 var result = findMatchResult(editor, toolbars);
484 if (result) {
485 panel.show(editor, result.id, result.rect, toolbars);
486 } else {
487 panel.hide();
488 }
489 };
490 return function () {
491 if (!editor.removed && editorHasFocus(editor)) {
492 toggle();
493 }
494 };
495 };
496 var repositionPanel = function (editor, panel) {
497 return function () {
498 var toolbars = getToolbars(editor);
499 var result = findMatchResult(editor, toolbars);
500 if (result) {
501 panel.reposition(editor, result.id, result.rect);
502 }
503 };
504 };
505 var ignoreWhenFormIsVisible = function (editor, panel, f) {
506 return function () {
507 if (!editor.removed && !panel.inForm()) {
508 f();
509 }
510 };
511 };
512 var bindContextualToolbarsEvents = function (editor, panel) {
513 var throttledTogglePanel = global$3.throttle(togglePanel(editor, panel), 0);
514 var throttledTogglePanelWhenNotInForm = global$3.throttle(ignoreWhenFormIsVisible(editor, panel, togglePanel(editor, panel)), 0);
515 var reposition = repositionPanel(editor, panel);
516 editor.on('blur hide ObjectResizeStart', panel.hide);
517 editor.on('click', throttledTogglePanel);
518 editor.on('nodeChange mouseup', throttledTogglePanelWhenNotInForm);
519 editor.on('ResizeEditor keyup', throttledTogglePanel);
520 editor.on('ResizeWindow', reposition);
521 global$2.DOM.bind(global$1.container, 'scroll', reposition);
522 editor.on('remove', function () {
523 global$2.DOM.unbind(global$1.container, 'scroll', reposition);
524 panel.remove();
525 });
526 editor.shortcuts.add('Alt+F10,F10', '', panel.focus);
527 };
528 var overrideLinkShortcut = function (editor, panel) {
529 editor.shortcuts.remove('meta+k');
530 editor.shortcuts.add('meta+k', '', function () {
531 var toolbars = getToolbars(editor);
532 var result = Matcher.match(editor, [SelectionMatcher.textSelection('quicklink')]);
533 if (result) {
534 panel.show(editor, result.id, result.rect, toolbars);
535 }
536 });
537 };
538 var renderInlineUI = function (editor, panel) {
539 SkinLoader.load(editor, function () {
540 bindContextualToolbarsEvents(editor, panel);
541 overrideLinkShortcut(editor, panel);
542 });
543 return {};
544 };
545 var fail = function (message) {
546 throw new Error(message);
547 };
548 var renderUI = function (editor, panel) {
549 return editor.inline ? renderInlineUI(editor, panel) : fail('inlite theme only supports inline mode.');
550 };
551 var Render = { renderUI: renderUI };
552
553 var noop = function () {
554 };
555 var constant = function (value) {
556 return function () {
557 return value;
558 };
559 };
560 var never = constant(false);
561 var always = constant(true);
562
563 var none = function () {
564 return NONE;
565 };
566 var NONE = function () {
567 var eq = function (o) {
568 return o.isNone();
569 };
570 var call = function (thunk) {
571 return thunk();
572 };
573 var id = function (n) {
574 return n;
575 };
576 var me = {
577 fold: function (n, s) {
578 return n();
579 },
580 is: never,
581 isSome: never,
582 isNone: always,
583 getOr: id,
584 getOrThunk: call,
585 getOrDie: function (msg) {
586 throw new Error(msg || 'error: getOrDie called on none.');
587 },
588 getOrNull: constant(null),
589 getOrUndefined: constant(undefined),
590 or: id,
591 orThunk: call,
592 map: none,
593 each: noop,
594 bind: none,
595 exists: never,
596 forall: always,
597 filter: none,
598 equals: eq,
599 equals_: eq,
600 toArray: function () {
601 return [];
602 },
603 toString: constant('none()')
604 };
605 if (Object.freeze) {
606 Object.freeze(me);
607 }
608 return me;
609 }();
610 var some = function (a) {
611 var constant_a = constant(a);
612 var self = function () {
613 return me;
614 };
615 var bind = function (f) {
616 return f(a);
617 };
618 var me = {
619 fold: function (n, s) {
620 return s(a);
621 },
622 is: function (v) {
623 return a === v;
624 },
625 isSome: always,
626 isNone: never,
627 getOr: constant_a,
628 getOrThunk: constant_a,
629 getOrDie: constant_a,
630 getOrNull: constant_a,
631 getOrUndefined: constant_a,
632 or: self,
633 orThunk: self,
634 map: function (f) {
635 return some(f(a));
636 },
637 each: function (f) {
638 f(a);
639 },
640 bind: bind,
641 exists: bind,
642 forall: bind,
643 filter: function (f) {
644 return f(a) ? me : NONE;
645 },
646 toArray: function () {
647 return [a];
648 },
649 toString: function () {
650 return 'some(' + a + ')';
651 },
652 equals: function (o) {
653 return o.is(a);
654 },
655 equals_: function (o, elementEq) {
656 return o.fold(never, function (b) {
657 return elementEq(a, b);
658 });
659 }
660 };
661 return me;
662 };
663 var from = function (value) {
664 return value === null || value === undefined ? NONE : some(value);
665 };
666 var Option = {
667 some: some,
668 none: none,
669 from: from
670 };
671
672 var typeOf = function (x) {
673 if (x === null) {
674 return 'null';
675 }
676 var t = typeof x;
677 if (t === 'object' && (Array.prototype.isPrototypeOf(x) || x.constructor && x.constructor.name === 'Array')) {
678 return 'array';
679 }
680 if (t === 'object' && (String.prototype.isPrototypeOf(x) || x.constructor && x.constructor.name === 'String')) {
681 return 'string';
682 }
683 return t;
684 };
685 var isType$1 = function (type) {
686 return function (value) {
687 return typeOf(value) === type;
688 };
689 };
690 var isArray$1 = isType$1('array');
691 var isFunction$1 = isType$1('function');
692 var isNumber$1 = isType$1('number');
693
694 var nativeSlice = Array.prototype.slice;
695 var nativeIndexOf = Array.prototype.indexOf;
696 var nativePush = Array.prototype.push;
697 var rawIndexOf = function (ts, t) {
698 return nativeIndexOf.call(ts, t);
699 };
700 var indexOf = function (xs, x) {
701 var r = rawIndexOf(xs, x);
702 return r === -1 ? Option.none() : Option.some(r);
703 };
704 var exists = function (xs, pred) {
705 for (var i = 0, len = xs.length; i < len; i++) {
706 var x = xs[i];
707 if (pred(x, i)) {
708 return true;
709 }
710 }
711 return false;
712 };
713 var map = function (xs, f) {
714 var len = xs.length;
715 var r = new Array(len);
716 for (var i = 0; i < len; i++) {
717 var x = xs[i];
718 r[i] = f(x, i);
719 }
720 return r;
721 };
722 var each = function (xs, f) {
723 for (var i = 0, len = xs.length; i < len; i++) {
724 var x = xs[i];
725 f(x, i);
726 }
727 };
728 var filter = function (xs, pred) {
729 var r = [];
730 for (var i = 0, len = xs.length; i < len; i++) {
731 var x = xs[i];
732 if (pred(x, i)) {
733 r.push(x);
734 }
735 }
736 return r;
737 };
738 var foldl = function (xs, f, acc) {
739 each(xs, function (x) {
740 acc = f(acc, x);
741 });
742 return acc;
743 };
744 var find = function (xs, pred) {
745 for (var i = 0, len = xs.length; i < len; i++) {
746 var x = xs[i];
747 if (pred(x, i)) {
748 return Option.some(x);
749 }
750 }
751 return Option.none();
752 };
753 var flatten$1 = function (xs) {
754 var r = [];
755 for (var i = 0, len = xs.length; i < len; ++i) {
756 if (!isArray$1(xs[i])) {
757 throw new Error('Arr.flatten item ' + i + ' was not an array, input: ' + xs);
758 }
759 nativePush.apply(r, xs[i]);
760 }
761 return r;
762 };
763 var from$1 = isFunction$1(Array.from) ? Array.from : function (x) {
764 return nativeSlice.call(x);
765 };
766
767 var count = 0;
768 var funcs = {
769 id: function () {
770 return 'mceu_' + count++;
771 },
772 create: function (name, attrs, children) {
773 var elm = domGlobals.document.createElement(name);
774 global$2.DOM.setAttribs(elm, attrs);
775 if (typeof children === 'string') {
776 elm.innerHTML = children;
777 } else {
778 global$4.each(children, function (child) {
779 if (child.nodeType) {
780 elm.appendChild(child);
781 }
782 });
783 }
784 return elm;
785 },
786 createFragment: function (html) {
787 return global$2.DOM.createFragment(html);
788 },
789 getWindowSize: function () {
790 return global$2.DOM.getViewPort();
791 },
792 getSize: function (elm) {
793 var width, height;
794 if (elm.getBoundingClientRect) {
795 var rect = elm.getBoundingClientRect();
796 width = Math.max(rect.width || rect.right - rect.left, elm.offsetWidth);
797 height = Math.max(rect.height || rect.bottom - rect.bottom, elm.offsetHeight);
798 } else {
799 width = elm.offsetWidth;
800 height = elm.offsetHeight;
801 }
802 return {
803 width: width,
804 height: height
805 };
806 },
807 getPos: function (elm, root) {
808 return global$2.DOM.getPos(elm, root || funcs.getContainer());
809 },
810 getContainer: function () {
811 return global$1.container ? global$1.container : domGlobals.document.body;
812 },
813 getViewPort: function (win) {
814 return global$2.DOM.getViewPort(win);
815 },
816 get: function (id) {
817 return domGlobals.document.getElementById(id);
818 },
819 addClass: function (elm, cls) {
820 return global$2.DOM.addClass(elm, cls);
821 },
822 removeClass: function (elm, cls) {
823 return global$2.DOM.removeClass(elm, cls);
824 },
825 hasClass: function (elm, cls) {
826 return global$2.DOM.hasClass(elm, cls);
827 },
828 toggleClass: function (elm, cls, state) {
829 return global$2.DOM.toggleClass(elm, cls, state);
830 },
831 css: function (elm, name, value) {
832 return global$2.DOM.setStyle(elm, name, value);
833 },
834 getRuntimeStyle: function (elm, name) {
835 return global$2.DOM.getStyle(elm, name, true);
836 },
837 on: function (target, name, callback, scope) {
838 return global$2.DOM.bind(target, name, callback, scope);
839 },
840 off: function (target, name, callback) {
841 return global$2.DOM.unbind(target, name, callback);
842 },
843 fire: function (target, name, args) {
844 return global$2.DOM.fire(target, name, args);
845 },
846 innerHtml: function (elm, html) {
847 global$2.DOM.setHTML(elm, html);
848 }
849 };
850
851 var global$7 = tinymce.util.Tools.resolve('tinymce.dom.DomQuery');
852
853 var global$8 = tinymce.util.Tools.resolve('tinymce.util.Class');
854
855 var global$9 = tinymce.util.Tools.resolve('tinymce.util.EventDispatcher');
856
857 var BoxUtils = {
858 parseBox: function (value) {
859 var len;
860 var radix = 10;
861 if (!value) {
862 return;
863 }
864 if (typeof value === 'number') {
865 value = value || 0;
866 return {
867 top: value,
868 left: value,
869 bottom: value,
870 right: value
871 };
872 }
873 value = value.split(' ');
874 len = value.length;
875 if (len === 1) {
876 value[1] = value[2] = value[3] = value[0];
877 } else if (len === 2) {
878 value[2] = value[0];
879 value[3] = value[1];
880 } else if (len === 3) {
881 value[3] = value[1];
882 }
883 return {
884 top: parseInt(value[0], radix) || 0,
885 right: parseInt(value[1], radix) || 0,
886 bottom: parseInt(value[2], radix) || 0,
887 left: parseInt(value[3], radix) || 0
888 };
889 },
890 measureBox: function (elm, prefix) {
891 function getStyle(name) {
892 var defaultView = elm.ownerDocument.defaultView;
893 if (defaultView) {
894 var computedStyle = defaultView.getComputedStyle(elm, null);
895 if (computedStyle) {
896 name = name.replace(/[A-Z]/g, function (a) {
897 return '-' + a;
898 });
899 return computedStyle.getPropertyValue(name);
900 } else {
901 return null;
902 }
903 }
904 return elm.currentStyle[name];
905 }
906 function getSide(name) {
907 var val = parseFloat(getStyle(name));
908 return isNaN(val) ? 0 : val;
909 }
910 return {
911 top: getSide(prefix + 'TopWidth'),
912 right: getSide(prefix + 'RightWidth'),
913 bottom: getSide(prefix + 'BottomWidth'),
914 left: getSide(prefix + 'LeftWidth')
915 };
916 }
917 };
918
919 function noop$1() {
920 }
921 function ClassList(onchange) {
922 this.cls = [];
923 this.cls._map = {};
924 this.onchange = onchange || noop$1;
925 this.prefix = '';
926 }
927 global$4.extend(ClassList.prototype, {
928 add: function (cls) {
929 if (cls && !this.contains(cls)) {
930 this.cls._map[cls] = true;
931 this.cls.push(cls);
932 this._change();
933 }
934 return this;
935 },
936 remove: function (cls) {
937 if (this.contains(cls)) {
938 var i = void 0;
939 for (i = 0; i < this.cls.length; i++) {
940 if (this.cls[i] === cls) {
941 break;
942 }
943 }
944 this.cls.splice(i, 1);
945 delete this.cls._map[cls];
946 this._change();
947 }
948 return this;
949 },
950 toggle: function (cls, state) {
951 var curState = this.contains(cls);
952 if (curState !== state) {
953 if (curState) {
954 this.remove(cls);
955 } else {
956 this.add(cls);
957 }
958 this._change();
959 }
960 return this;
961 },
962 contains: function (cls) {
963 return !!this.cls._map[cls];
964 },
965 _change: function () {
966 delete this.clsValue;
967 this.onchange.call(this);
968 }
969 });
970 ClassList.prototype.toString = function () {
971 var value;
972 if (this.clsValue) {
973 return this.clsValue;
974 }
975 value = '';
976 for (var i = 0; i < this.cls.length; i++) {
977 if (i > 0) {
978 value += ' ';
979 }
980 value += this.prefix + this.cls[i];
981 }
982 return value;
983 };
984
985 function unique(array) {
986 var uniqueItems = [];
987 var i = array.length, item;
988 while (i--) {
989 item = array[i];
990 if (!item.__checked) {
991 uniqueItems.push(item);
992 item.__checked = 1;
993 }
994 }
995 i = uniqueItems.length;
996 while (i--) {
997 delete uniqueItems[i].__checked;
998 }
999 return uniqueItems;
1000 }
1001 var expression = /^([\w\\*]+)?(?:#([\w\-\\]+))?(?:\.([\w\\\.]+))?(?:\[\@?([\w\\]+)([\^\$\*!~]?=)([\w\\]+)\])?(?:\:(.+))?/i;
1002 var chunker = /((?:\((?:\([^()]+\)|[^()]+)+\)|\[(?:\[[^\[\]]*\]|['"][^'"]*['"]|[^\[\]'"]+)+\]|\\.|[^ >+~,(\[\\]+)+|[>+~])(\s*,\s*)?((?:.|\r|\n)*)/g;
1003 var whiteSpace = /^\s*|\s*$/g;
1004 var Collection;
1005 var Selector = global$8.extend({
1006 init: function (selector) {
1007 var match = this.match;
1008 function compileNameFilter(name) {
1009 if (name) {
1010 name = name.toLowerCase();
1011 return function (item) {
1012 return name === '*' || item.type === name;
1013 };
1014 }
1015 }
1016 function compileIdFilter(id) {
1017 if (id) {
1018 return function (item) {
1019 return item._name === id;
1020 };
1021 }
1022 }
1023 function compileClassesFilter(classes) {
1024 if (classes) {
1025 classes = classes.split('.');
1026 return function (item) {
1027 var i = classes.length;
1028 while (i--) {
1029 if (!item.classes.contains(classes[i])) {
1030 return false;
1031 }
1032 }
1033 return true;
1034 };
1035 }
1036 }
1037 function compileAttrFilter(name, cmp, check) {
1038 if (name) {
1039 return function (item) {
1040 var value = item[name] ? item[name]() : '';
1041 return !cmp ? !!check : cmp === '=' ? value === check : cmp === '*=' ? value.indexOf(check) >= 0 : cmp === '~=' ? (' ' + value + ' ').indexOf(' ' + check + ' ') >= 0 : cmp === '!=' ? value !== check : cmp === '^=' ? value.indexOf(check) === 0 : cmp === '$=' ? value.substr(value.length - check.length) === check : false;
1042 };
1043 }
1044 }
1045 function compilePsuedoFilter(name) {
1046 var notSelectors;
1047 if (name) {
1048 name = /(?:not\((.+)\))|(.+)/i.exec(name);
1049 if (!name[1]) {
1050 name = name[2];
1051 return function (item, index, length) {
1052 return name === 'first' ? index === 0 : name === 'last' ? index === length - 1 : name === 'even' ? index % 2 === 0 : name === 'odd' ? index % 2 === 1 : item[name] ? item[name]() : false;
1053 };
1054 }
1055 notSelectors = parseChunks(name[1], []);
1056 return function (item) {
1057 return !match(item, notSelectors);
1058 };
1059 }
1060 }
1061 function compile(selector, filters, direct) {
1062 var parts;
1063 function add(filter) {
1064 if (filter) {
1065 filters.push(filter);
1066 }
1067 }
1068 parts = expression.exec(selector.replace(whiteSpace, ''));
1069 add(compileNameFilter(parts[1]));
1070 add(compileIdFilter(parts[2]));
1071 add(compileClassesFilter(parts[3]));
1072 add(compileAttrFilter(parts[4], parts[5], parts[6]));
1073 add(compilePsuedoFilter(parts[7]));
1074 filters.pseudo = !!parts[7];
1075 filters.direct = direct;
1076 return filters;
1077 }
1078 function parseChunks(selector, selectors) {
1079 var parts = [];
1080 var extra, matches, i;
1081 do {
1082 chunker.exec('');
1083 matches = chunker.exec(selector);
1084 if (matches) {
1085 selector = matches[3];
1086 parts.push(matches[1]);
1087 if (matches[2]) {
1088 extra = matches[3];
1089 break;
1090 }
1091 }
1092 } while (matches);
1093 if (extra) {
1094 parseChunks(extra, selectors);
1095 }
1096 selector = [];
1097 for (i = 0; i < parts.length; i++) {
1098 if (parts[i] !== '>') {
1099 selector.push(compile(parts[i], [], parts[i - 1] === '>'));
1100 }
1101 }
1102 selectors.push(selector);
1103 return selectors;
1104 }
1105 this._selectors = parseChunks(selector, []);
1106 },
1107 match: function (control, selectors) {
1108 var i, l, si, sl, selector, fi, fl, filters, index, length, siblings, count, item;
1109 selectors = selectors || this._selectors;
1110 for (i = 0, l = selectors.length; i < l; i++) {
1111 selector = selectors[i];
1112 sl = selector.length;
1113 item = control;
1114 count = 0;
1115 for (si = sl - 1; si >= 0; si--) {
1116 filters = selector[si];
1117 while (item) {
1118 if (filters.pseudo) {
1119 siblings = item.parent().items();
1120 index = length = siblings.length;
1121 while (index--) {
1122 if (siblings[index] === item) {
1123 break;
1124 }
1125 }
1126 }
1127 for (fi = 0, fl = filters.length; fi < fl; fi++) {
1128 if (!filters[fi](item, index, length)) {
1129 fi = fl + 1;
1130 break;
1131 }
1132 }
1133 if (fi === fl) {
1134 count++;
1135 break;
1136 } else {
1137 if (si === sl - 1) {
1138 break;
1139 }
1140 }
1141 item = item.parent();
1142 }
1143 }
1144 if (count === sl) {
1145 return true;
1146 }
1147 }
1148 return false;
1149 },
1150 find: function (container) {
1151 var matches = [], i, l;
1152 var selectors = this._selectors;
1153 function collect(items, selector, index) {
1154 var i, l, fi, fl, item;
1155 var filters = selector[index];
1156 for (i = 0, l = items.length; i < l; i++) {
1157 item = items[i];
1158 for (fi = 0, fl = filters.length; fi < fl; fi++) {
1159 if (!filters[fi](item, i, l)) {
1160 fi = fl + 1;
1161 break;
1162 }
1163 }
1164 if (fi === fl) {
1165 if (index === selector.length - 1) {
1166 matches.push(item);
1167 } else {
1168 if (item.items) {
1169 collect(item.items(), selector, index + 1);
1170 }
1171 }
1172 } else if (filters.direct) {
1173 return;
1174 }
1175 if (item.items) {
1176 collect(item.items(), selector, index);
1177 }
1178 }
1179 }
1180 if (container.items) {
1181 for (i = 0, l = selectors.length; i < l; i++) {
1182 collect(container.items(), selectors[i], 0);
1183 }
1184 if (l > 1) {
1185 matches = unique(matches);
1186 }
1187 }
1188 if (!Collection) {
1189 Collection = Selector.Collection;
1190 }
1191 return new Collection(matches);
1192 }
1193 });
1194
1195 var Collection$1, proto;
1196 var push = Array.prototype.push, slice = Array.prototype.slice;
1197 proto = {
1198 length: 0,
1199 init: function (items) {
1200 if (items) {
1201 this.add(items);
1202 }
1203 },
1204 add: function (items) {
1205 var self = this;
1206 if (!global$4.isArray(items)) {
1207 if (items instanceof Collection$1) {
1208 self.add(items.toArray());
1209 } else {
1210 push.call(self, items);
1211 }
1212 } else {
1213 push.apply(self, items);
1214 }
1215 return self;
1216 },
1217 set: function (items) {
1218 var self = this;
1219 var len = self.length;
1220 var i;
1221 self.length = 0;
1222 self.add(items);
1223 for (i = self.length; i < len; i++) {
1224 delete self[i];
1225 }
1226 return self;
1227 },
1228 filter: function (selector) {
1229 var self = this;
1230 var i, l;
1231 var matches = [];
1232 var item, match;
1233 if (typeof selector === 'string') {
1234 selector = new Selector(selector);
1235 match = function (item) {
1236 return selector.match(item);
1237 };
1238 } else {
1239 match = selector;
1240 }
1241 for (i = 0, l = self.length; i < l; i++) {
1242 item = self[i];
1243 if (match(item)) {
1244 matches.push(item);
1245 }
1246 }
1247 return new Collection$1(matches);
1248 },
1249 slice: function () {
1250 return new Collection$1(slice.apply(this, arguments));
1251 },
1252 eq: function (index) {
1253 return index === -1 ? this.slice(index) : this.slice(index, +index + 1);
1254 },
1255 each: function (callback) {
1256 global$4.each(this, callback);
1257 return this;
1258 },
1259 toArray: function () {
1260 return global$4.toArray(this);
1261 },
1262 indexOf: function (ctrl) {
1263 var self = this;
1264 var i = self.length;
1265 while (i--) {
1266 if (self[i] === ctrl) {
1267 break;
1268 }
1269 }
1270 return i;
1271 },
1272 reverse: function () {
1273 return new Collection$1(global$4.toArray(this).reverse());
1274 },
1275 hasClass: function (cls) {
1276 return this[0] ? this[0].classes.contains(cls) : false;
1277 },
1278 prop: function (name, value) {
1279 var self = this;
1280 var item;
1281 if (value !== undefined) {
1282 self.each(function (item) {
1283 if (item[name]) {
1284 item[name](value);
1285 }
1286 });
1287 return self;
1288 }
1289 item = self[0];
1290 if (item && item[name]) {
1291 return item[name]();
1292 }
1293 },
1294 exec: function (name) {
1295 var self = this, args = global$4.toArray(arguments).slice(1);
1296 self.each(function (item) {
1297 if (item[name]) {
1298 item[name].apply(item, args);
1299 }
1300 });
1301 return self;
1302 },
1303 remove: function () {
1304 var i = this.length;
1305 while (i--) {
1306 this[i].remove();
1307 }
1308 return this;
1309 },
1310 addClass: function (cls) {
1311 return this.each(function (item) {
1312 item.classes.add(cls);
1313 });
1314 },
1315 removeClass: function (cls) {
1316 return this.each(function (item) {
1317 item.classes.remove(cls);
1318 });
1319 }
1320 };
1321 global$4.each('fire on off show hide append prepend before after reflow'.split(' '), function (name) {
1322 proto[name] = function () {
1323 var args = global$4.toArray(arguments);
1324 this.each(function (ctrl) {
1325 if (name in ctrl) {
1326 ctrl[name].apply(ctrl, args);
1327 }
1328 });
1329 return this;
1330 };
1331 });
1332 global$4.each('text name disabled active selected checked visible parent value data'.split(' '), function (name) {
1333 proto[name] = function (value) {
1334 return this.prop(name, value);
1335 };
1336 });
1337 Collection$1 = global$8.extend(proto);
1338 Selector.Collection = Collection$1;
1339 var Collection$2 = Collection$1;
1340
1341 var Binding = function (settings) {
1342 this.create = settings.create;
1343 };
1344 Binding.create = function (model, name) {
1345 return new Binding({
1346 create: function (otherModel, otherName) {
1347 var bindings;
1348 var fromSelfToOther = function (e) {
1349 otherModel.set(otherName, e.value);
1350 };
1351 var fromOtherToSelf = function (e) {
1352 model.set(name, e.value);
1353 };
1354 otherModel.on('change:' + otherName, fromOtherToSelf);
1355 model.on('change:' + name, fromSelfToOther);
1356 bindings = otherModel._bindings;
1357 if (!bindings) {
1358 bindings = otherModel._bindings = [];
1359 otherModel.on('destroy', function () {
1360 var i = bindings.length;
1361 while (i--) {
1362 bindings[i]();
1363 }
1364 });
1365 }
1366 bindings.push(function () {
1367 model.off('change:' + name, fromSelfToOther);
1368 });
1369 return model.get(name);
1370 }
1371 });
1372 };
1373
1374 var global$a = tinymce.util.Tools.resolve('tinymce.util.Observable');
1375
1376 function isNode(node) {
1377 return node.nodeType > 0;
1378 }
1379 function isEqual(a, b) {
1380 var k, checked;
1381 if (a === b) {
1382 return true;
1383 }
1384 if (a === null || b === null) {
1385 return a === b;
1386 }
1387 if (typeof a !== 'object' || typeof b !== 'object') {
1388 return a === b;
1389 }
1390 if (global$4.isArray(b)) {
1391 if (a.length !== b.length) {
1392 return false;
1393 }
1394 k = a.length;
1395 while (k--) {
1396 if (!isEqual(a[k], b[k])) {
1397 return false;
1398 }
1399 }
1400 }
1401 if (isNode(a) || isNode(b)) {
1402 return a === b;
1403 }
1404 checked = {};
1405 for (k in b) {
1406 if (!isEqual(a[k], b[k])) {
1407 return false;
1408 }
1409 checked[k] = true;
1410 }
1411 for (k in a) {
1412 if (!checked[k] && !isEqual(a[k], b[k])) {
1413 return false;
1414 }
1415 }
1416 return true;
1417 }
1418 var ObservableObject = global$8.extend({
1419 Mixins: [global$a],
1420 init: function (data) {
1421 var name, value;
1422 data = data || {};
1423 for (name in data) {
1424 value = data[name];
1425 if (value instanceof Binding) {
1426 data[name] = value.create(this, name);
1427 }
1428 }
1429 this.data = data;
1430 },
1431 set: function (name, value) {
1432 var key, args;
1433 var oldValue = this.data[name];
1434 if (value instanceof Binding) {
1435 value = value.create(this, name);
1436 }
1437 if (typeof name === 'object') {
1438 for (key in name) {
1439 this.set(key, name[key]);
1440 }
1441 return this;
1442 }
1443 if (!isEqual(oldValue, value)) {
1444 this.data[name] = value;
1445 args = {
1446 target: this,
1447 name: name,
1448 value: value,
1449 oldValue: oldValue
1450 };
1451 this.fire('change:' + name, args);
1452 this.fire('change', args);
1453 }
1454 return this;
1455 },
1456 get: function (name) {
1457 return this.data[name];
1458 },
1459 has: function (name) {
1460 return name in this.data;
1461 },
1462 bind: function (name) {
1463 return Binding.create(this, name);
1464 },
1465 destroy: function () {
1466 this.fire('destroy');
1467 }
1468 });
1469
1470 var dirtyCtrls = {}, animationFrameRequested;
1471 var ReflowQueue = {
1472 add: function (ctrl) {
1473 var parent = ctrl.parent();
1474 if (parent) {
1475 if (!parent._layout || parent._layout.isNative()) {
1476 return;
1477 }
1478 if (!dirtyCtrls[parent._id]) {
1479 dirtyCtrls[parent._id] = parent;
1480 }
1481 if (!animationFrameRequested) {
1482 animationFrameRequested = true;
1483 global$3.requestAnimationFrame(function () {
1484 var id, ctrl;
1485 animationFrameRequested = false;
1486 for (id in dirtyCtrls) {
1487 ctrl = dirtyCtrls[id];
1488 if (ctrl.state.get('rendered')) {
1489 ctrl.reflow();
1490 }
1491 }
1492 dirtyCtrls = {};
1493 }, domGlobals.document.body);
1494 }
1495 }
1496 },
1497 remove: function (ctrl) {
1498 if (dirtyCtrls[ctrl._id]) {
1499 delete dirtyCtrls[ctrl._id];
1500 }
1501 }
1502 };
1503
1504 var getUiContainerDelta = function (ctrl) {
1505 var uiContainer = getUiContainer(ctrl);
1506 if (uiContainer && global$2.DOM.getStyle(uiContainer, 'position', true) !== 'static') {
1507 var containerPos = global$2.DOM.getPos(uiContainer);
1508 var dx = uiContainer.scrollLeft - containerPos.x;
1509 var dy = uiContainer.scrollTop - containerPos.y;
1510 return Option.some({
1511 x: dx,
1512 y: dy
1513 });
1514 } else {
1515 return Option.none();
1516 }
1517 };
1518 var setUiContainer = function (editor, ctrl) {
1519 var uiContainer = global$2.DOM.select(editor.settings.ui_container)[0];
1520 ctrl.getRoot().uiContainer = uiContainer;
1521 };
1522 var getUiContainer = function (ctrl) {
1523 return ctrl ? ctrl.getRoot().uiContainer : null;
1524 };
1525 var inheritUiContainer = function (fromCtrl, toCtrl) {
1526 return toCtrl.uiContainer = getUiContainer(fromCtrl);
1527 };
1528 var UiContainer = {
1529 getUiContainerDelta: getUiContainerDelta,
1530 setUiContainer: setUiContainer,
1531 getUiContainer: getUiContainer,
1532 inheritUiContainer: inheritUiContainer
1533 };
1534
1535 var hasMouseWheelEventSupport = 'onmousewheel' in domGlobals.document;
1536 var hasWheelEventSupport = false;
1537 var classPrefix = 'mce-';
1538 var Control, idCounter = 0;
1539 var proto$1 = {
1540 Statics: { classPrefix: classPrefix },
1541 isRtl: function () {
1542 return Control.rtl;
1543 },
1544 classPrefix: classPrefix,
1545 init: function (settings) {
1546 var self = this;
1547 var classes, defaultClasses;
1548 function applyClasses(classes) {
1549 var i;
1550 classes = classes.split(' ');
1551 for (i = 0; i < classes.length; i++) {
1552 self.classes.add(classes[i]);
1553 }
1554 }
1555 self.settings = settings = global$4.extend({}, self.Defaults, settings);
1556 self._id = settings.id || 'mceu_' + idCounter++;
1557 self._aria = { role: settings.role };
1558 self._elmCache = {};
1559 self.$ = global$7;
1560 self.state = new ObservableObject({
1561 visible: true,
1562 active: false,
1563 disabled: false,
1564 value: ''
1565 });
1566 self.data = new ObservableObject(settings.data);
1567 self.classes = new ClassList(function () {
1568 if (self.state.get('rendered')) {
1569 self.getEl().className = this.toString();
1570 }
1571 });
1572 self.classes.prefix = self.classPrefix;
1573 classes = settings.classes;
1574 if (classes) {
1575 if (self.Defaults) {
1576 defaultClasses = self.Defaults.classes;
1577 if (defaultClasses && classes !== defaultClasses) {
1578 applyClasses(defaultClasses);
1579 }
1580 }
1581 applyClasses(classes);
1582 }
1583 global$4.each('title text name visible disabled active value'.split(' '), function (name) {
1584 if (name in settings) {
1585 self[name](settings[name]);
1586 }
1587 });
1588 self.on('click', function () {
1589 if (self.disabled()) {
1590 return false;
1591 }
1592 });
1593 self.settings = settings;
1594 self.borderBox = BoxUtils.parseBox(settings.border);
1595 self.paddingBox = BoxUtils.parseBox(settings.padding);
1596 self.marginBox = BoxUtils.parseBox(settings.margin);
1597 if (settings.hidden) {
1598 self.hide();
1599 }
1600 },
1601 Properties: 'parent,name',
1602 getContainerElm: function () {
1603 var uiContainer = UiContainer.getUiContainer(this);
1604 return uiContainer ? uiContainer : funcs.getContainer();
1605 },
1606 getParentCtrl: function (elm) {
1607 var ctrl;
1608 var lookup = this.getRoot().controlIdLookup;
1609 while (elm && lookup) {
1610 ctrl = lookup[elm.id];
1611 if (ctrl) {
1612 break;
1613 }
1614 elm = elm.parentNode;
1615 }
1616 return ctrl;
1617 },
1618 initLayoutRect: function () {
1619 var self = this;
1620 var settings = self.settings;
1621 var borderBox, layoutRect;
1622 var elm = self.getEl();
1623 var width, height, minWidth, minHeight, autoResize;
1624 var startMinWidth, startMinHeight, initialSize;
1625 borderBox = self.borderBox = self.borderBox || BoxUtils.measureBox(elm, 'border');
1626 self.paddingBox = self.paddingBox || BoxUtils.measureBox(elm, 'padding');
1627 self.marginBox = self.marginBox || BoxUtils.measureBox(elm, 'margin');
1628 initialSize = funcs.getSize(elm);
1629 startMinWidth = settings.minWidth;
1630 startMinHeight = settings.minHeight;
1631 minWidth = startMinWidth || initialSize.width;
1632 minHeight = startMinHeight || initialSize.height;
1633 width = settings.width;
1634 height = settings.height;
1635 autoResize = settings.autoResize;
1636 autoResize = typeof autoResize !== 'undefined' ? autoResize : !width && !height;
1637 width = width || minWidth;
1638 height = height || minHeight;
1639 var deltaW = borderBox.left + borderBox.right;
1640 var deltaH = borderBox.top + borderBox.bottom;
1641 var maxW = settings.maxWidth || 65535;
1642 var maxH = settings.maxHeight || 65535;
1643 self._layoutRect = layoutRect = {
1644 x: settings.x || 0,
1645 y: settings.y || 0,
1646 w: width,
1647 h: height,
1648 deltaW: deltaW,
1649 deltaH: deltaH,
1650 contentW: width - deltaW,
1651 contentH: height - deltaH,
1652 innerW: width - deltaW,
1653 innerH: height - deltaH,
1654 startMinWidth: startMinWidth || 0,
1655 startMinHeight: startMinHeight || 0,
1656 minW: Math.min(minWidth, maxW),
1657 minH: Math.min(minHeight, maxH),
1658 maxW: maxW,
1659 maxH: maxH,
1660 autoResize: autoResize,
1661 scrollW: 0
1662 };
1663 self._lastLayoutRect = {};
1664 return layoutRect;
1665 },
1666 layoutRect: function (newRect) {
1667 var self = this;
1668 var curRect = self._layoutRect, lastLayoutRect, size, deltaWidth, deltaHeight, repaintControls;
1669 if (!curRect) {
1670 curRect = self.initLayoutRect();
1671 }
1672 if (newRect) {
1673 deltaWidth = curRect.deltaW;
1674 deltaHeight = curRect.deltaH;
1675 if (newRect.x !== undefined) {
1676 curRect.x = newRect.x;
1677 }
1678 if (newRect.y !== undefined) {
1679 curRect.y = newRect.y;
1680 }
1681 if (newRect.minW !== undefined) {
1682 curRect.minW = newRect.minW;
1683 }
1684 if (newRect.minH !== undefined) {
1685 curRect.minH = newRect.minH;
1686 }
1687 size = newRect.w;
1688 if (size !== undefined) {
1689 size = size < curRect.minW ? curRect.minW : size;
1690 size = size > curRect.maxW ? curRect.maxW : size;
1691 curRect.w = size;
1692 curRect.innerW = size - deltaWidth;
1693 }
1694 size = newRect.h;
1695 if (size !== undefined) {
1696 size = size < curRect.minH ? curRect.minH : size;
1697 size = size > curRect.maxH ? curRect.maxH : size;
1698 curRect.h = size;
1699 curRect.innerH = size - deltaHeight;
1700 }
1701 size = newRect.innerW;
1702 if (size !== undefined) {
1703 size = size < curRect.minW - deltaWidth ? curRect.minW - deltaWidth : size;
1704 size = size > curRect.maxW - deltaWidth ? curRect.maxW - deltaWidth : size;
1705 curRect.innerW = size;
1706 curRect.w = size + deltaWidth;
1707 }
1708 size = newRect.innerH;
1709 if (size !== undefined) {
1710 size = size < curRect.minH - deltaHeight ? curRect.minH - deltaHeight : size;
1711 size = size > curRect.maxH - deltaHeight ? curRect.maxH - deltaHeight : size;
1712 curRect.innerH = size;
1713 curRect.h = size + deltaHeight;
1714 }
1715 if (newRect.contentW !== undefined) {
1716 curRect.contentW = newRect.contentW;
1717 }
1718 if (newRect.contentH !== undefined) {
1719 curRect.contentH = newRect.contentH;
1720 }
1721 lastLayoutRect = self._lastLayoutRect;
1722 if (lastLayoutRect.x !== curRect.x || lastLayoutRect.y !== curRect.y || lastLayoutRect.w !== curRect.w || lastLayoutRect.h !== curRect.h) {
1723 repaintControls = Control.repaintControls;
1724 if (repaintControls) {
1725 if (repaintControls.map && !repaintControls.map[self._id]) {
1726 repaintControls.push(self);
1727 repaintControls.map[self._id] = true;
1728 }
1729 }
1730 lastLayoutRect.x = curRect.x;
1731 lastLayoutRect.y = curRect.y;
1732 lastLayoutRect.w = curRect.w;
1733 lastLayoutRect.h = curRect.h;
1734 }
1735 return self;
1736 }
1737 return curRect;
1738 },
1739 repaint: function () {
1740 var self = this;
1741 var style, bodyStyle, bodyElm, rect, borderBox;
1742 var borderW, borderH, lastRepaintRect, round, value;
1743 round = !domGlobals.document.createRange ? Math.round : function (value) {
1744 return value;
1745 };
1746 style = self.getEl().style;
1747 rect = self._layoutRect;
1748 lastRepaintRect = self._lastRepaintRect || {};
1749 borderBox = self.borderBox;
1750 borderW = borderBox.left + borderBox.right;
1751 borderH = borderBox.top + borderBox.bottom;
1752 if (rect.x !== lastRepaintRect.x) {
1753 style.left = round(rect.x) + 'px';
1754 lastRepaintRect.x = rect.x;
1755 }
1756 if (rect.y !== lastRepaintRect.y) {
1757 style.top = round(rect.y) + 'px';
1758 lastRepaintRect.y = rect.y;
1759 }
1760 if (rect.w !== lastRepaintRect.w) {
1761 value = round(rect.w - borderW);
1762 style.width = (value >= 0 ? value : 0) + 'px';
1763 lastRepaintRect.w = rect.w;
1764 }
1765 if (rect.h !== lastRepaintRect.h) {
1766 value = round(rect.h - borderH);
1767 style.height = (value >= 0 ? value : 0) + 'px';
1768 lastRepaintRect.h = rect.h;
1769 }
1770 if (self._hasBody && rect.innerW !== lastRepaintRect.innerW) {
1771 value = round(rect.innerW);
1772 bodyElm = self.getEl('body');
1773 if (bodyElm) {
1774 bodyStyle = bodyElm.style;
1775 bodyStyle.width = (value >= 0 ? value : 0) + 'px';
1776 }
1777 lastRepaintRect.innerW = rect.innerW;
1778 }
1779 if (self._hasBody && rect.innerH !== lastRepaintRect.innerH) {
1780 value = round(rect.innerH);
1781 bodyElm = bodyElm || self.getEl('body');
1782 if (bodyElm) {
1783 bodyStyle = bodyStyle || bodyElm.style;
1784 bodyStyle.height = (value >= 0 ? value : 0) + 'px';
1785 }
1786 lastRepaintRect.innerH = rect.innerH;
1787 }
1788 self._lastRepaintRect = lastRepaintRect;
1789 self.fire('repaint', {}, false);
1790 },
1791 updateLayoutRect: function () {
1792 var self = this;
1793 self.parent()._lastRect = null;
1794 funcs.css(self.getEl(), {
1795 width: '',
1796 height: ''
1797 });
1798 self._layoutRect = self._lastRepaintRect = self._lastLayoutRect = null;
1799 self.initLayoutRect();
1800 },
1801 on: function (name, callback) {
1802 var self = this;
1803 function resolveCallbackName(name) {
1804 var callback, scope;
1805 if (typeof name !== 'string') {
1806 return name;
1807 }
1808 return function (e) {
1809 if (!callback) {
1810 self.parentsAndSelf().each(function (ctrl) {
1811 var callbacks = ctrl.settings.callbacks;
1812 if (callbacks && (callback = callbacks[name])) {
1813 scope = ctrl;
1814 return false;
1815 }
1816 });
1817 }
1818 if (!callback) {
1819 e.action = name;
1820 this.fire('execute', e);
1821 return;
1822 }
1823 return callback.call(scope, e);
1824 };
1825 }
1826 getEventDispatcher(self).on(name, resolveCallbackName(callback));
1827 return self;
1828 },
1829 off: function (name, callback) {
1830 getEventDispatcher(this).off(name, callback);
1831 return this;
1832 },
1833 fire: function (name, args, bubble) {
1834 var self = this;
1835 args = args || {};
1836 if (!args.control) {
1837 args.control = self;
1838 }
1839 args = getEventDispatcher(self).fire(name, args);
1840 if (bubble !== false && self.parent) {
1841 var parent = self.parent();
1842 while (parent && !args.isPropagationStopped()) {
1843 parent.fire(name, args, false);
1844 parent = parent.parent();
1845 }
1846 }
1847 return args;
1848 },
1849 hasEventListeners: function (name) {
1850 return getEventDispatcher(this).has(name);
1851 },
1852 parents: function (selector) {
1853 var self = this;
1854 var ctrl, parents = new Collection$2();
1855 for (ctrl = self.parent(); ctrl; ctrl = ctrl.parent()) {
1856 parents.add(ctrl);
1857 }
1858 if (selector) {
1859 parents = parents.filter(selector);
1860 }
1861 return parents;
1862 },
1863 parentsAndSelf: function (selector) {
1864 return new Collection$2(this).add(this.parents(selector));
1865 },
1866 next: function () {
1867 var parentControls = this.parent().items();
1868 return parentControls[parentControls.indexOf(this) + 1];
1869 },
1870 prev: function () {
1871 var parentControls = this.parent().items();
1872 return parentControls[parentControls.indexOf(this) - 1];
1873 },
1874 innerHtml: function (html) {
1875 this.$el.html(html);
1876 return this;
1877 },
1878 getEl: function (suffix) {
1879 var id = suffix ? this._id + '-' + suffix : this._id;
1880 if (!this._elmCache[id]) {
1881 this._elmCache[id] = global$7('#' + id)[0];
1882 }
1883 return this._elmCache[id];
1884 },
1885 show: function () {
1886 return this.visible(true);
1887 },
1888 hide: function () {
1889 return this.visible(false);
1890 },
1891 focus: function () {
1892 try {
1893 this.getEl().focus();
1894 } catch (ex) {
1895 }
1896 return this;
1897 },
1898 blur: function () {
1899 this.getEl().blur();
1900 return this;
1901 },
1902 aria: function (name, value) {
1903 var self = this, elm = self.getEl(self.ariaTarget);
1904 if (typeof value === 'undefined') {
1905 return self._aria[name];
1906 }
1907 self._aria[name] = value;
1908 if (self.state.get('rendered')) {
1909 elm.setAttribute(name === 'role' ? name : 'aria-' + name, value);
1910 }
1911 return self;
1912 },
1913 encode: function (text, translate) {
1914 if (translate !== false) {
1915 text = this.translate(text);
1916 }
1917 return (text || '').replace(/[&<>"]/g, function (match) {
1918 return '&#' + match.charCodeAt(0) + ';';
1919 });
1920 },
1921 translate: function (text) {
1922 return Control.translate ? Control.translate(text) : text;
1923 },
1924 before: function (items) {
1925 var self = this, parent = self.parent();
1926 if (parent) {
1927 parent.insert(items, parent.items().indexOf(self), true);
1928 }
1929 return self;
1930 },
1931 after: function (items) {
1932 var self = this, parent = self.parent();
1933 if (parent) {
1934 parent.insert(items, parent.items().indexOf(self));
1935 }
1936 return self;
1937 },
1938 remove: function () {
1939 var self = this;
1940 var elm = self.getEl();
1941 var parent = self.parent();
1942 var newItems, i;
1943 if (self.items) {
1944 var controls = self.items().toArray();
1945 i = controls.length;
1946 while (i--) {
1947 controls[i].remove();
1948 }
1949 }
1950 if (parent && parent.items) {
1951 newItems = [];
1952 parent.items().each(function (item) {
1953 if (item !== self) {
1954 newItems.push(item);
1955 }
1956 });
1957 parent.items().set(newItems);
1958 parent._lastRect = null;
1959 }
1960 if (self._eventsRoot && self._eventsRoot === self) {
1961 global$7(elm).off();
1962 }
1963 var lookup = self.getRoot().controlIdLookup;
1964 if (lookup) {
1965 delete lookup[self._id];
1966 }
1967 if (elm && elm.parentNode) {
1968 elm.parentNode.removeChild(elm);
1969 }
1970 self.state.set('rendered', false);
1971 self.state.destroy();
1972 self.fire('remove');
1973 return self;
1974 },
1975 renderBefore: function (elm) {
1976 global$7(elm).before(this.renderHtml());
1977 this.postRender();
1978 return this;
1979 },
1980 renderTo: function (elm) {
1981 global$7(elm || this.getContainerElm()).append(this.renderHtml());
1982 this.postRender();
1983 return this;
1984 },
1985 preRender: function () {
1986 },
1987 render: function () {
1988 },
1989 renderHtml: function () {
1990 return '<div id="' + this._id + '" class="' + this.classes + '"></div>';
1991 },
1992 postRender: function () {
1993 var self = this;
1994 var settings = self.settings;
1995 var elm, box, parent, name, parentEventsRoot;
1996 self.$el = global$7(self.getEl());
1997 self.state.set('rendered', true);
1998 for (name in settings) {
1999 if (name.indexOf('on') === 0) {
2000 self.on(name.substr(2), settings[name]);
2001 }
2002 }
2003 if (self._eventsRoot) {
2004 for (parent = self.parent(); !parentEventsRoot && parent; parent = parent.parent()) {
2005 parentEventsRoot = parent._eventsRoot;
2006 }
2007 if (parentEventsRoot) {
2008 for (name in parentEventsRoot._nativeEvents) {
2009 self._nativeEvents[name] = true;
2010 }
2011 }
2012 }
2013 bindPendingEvents(self);
2014 if (settings.style) {
2015 elm = self.getEl();
2016 if (elm) {
2017 elm.setAttribute('style', settings.style);
2018 elm.style.cssText = settings.style;
2019 }
2020 }
2021 if (self.settings.border) {
2022 box = self.borderBox;
2023 self.$el.css({
2024 'border-top-width': box.top,
2025 'border-right-width': box.right,
2026 'border-bottom-width': box.bottom,
2027 'border-left-width': box.left
2028 });
2029 }
2030 var root = self.getRoot();
2031 if (!root.controlIdLookup) {
2032 root.controlIdLookup = {};
2033 }
2034 root.controlIdLookup[self._id] = self;
2035 for (var key in self._aria) {
2036 self.aria(key, self._aria[key]);
2037 }
2038 if (self.state.get('visible') === false) {
2039 self.getEl().style.display = 'none';
2040 }
2041 self.bindStates();
2042 self.state.on('change:visible', function (e) {
2043 var state = e.value;
2044 var parentCtrl;
2045 if (self.state.get('rendered')) {
2046 self.getEl().style.display = state === false ? 'none' : '';
2047 self.getEl().getBoundingClientRect();
2048 }
2049 parentCtrl = self.parent();
2050 if (parentCtrl) {
2051 parentCtrl._lastRect = null;
2052 }
2053 self.fire(state ? 'show' : 'hide');
2054 ReflowQueue.add(self);
2055 });
2056 self.fire('postrender', {}, false);
2057 },
2058 bindStates: function () {
2059 },
2060 scrollIntoView: function (align) {
2061 function getOffset(elm, rootElm) {
2062 var x, y, parent = elm;
2063 x = y = 0;
2064 while (parent && parent !== rootElm && parent.nodeType) {
2065 x += parent.offsetLeft || 0;
2066 y += parent.offsetTop || 0;
2067 parent = parent.offsetParent;
2068 }
2069 return {
2070 x: x,
2071 y: y
2072 };
2073 }
2074 var elm = this.getEl(), parentElm = elm.parentNode;
2075 var x, y, width, height, parentWidth, parentHeight;
2076 var pos = getOffset(elm, parentElm);
2077 x = pos.x;
2078 y = pos.y;
2079 width = elm.offsetWidth;
2080 height = elm.offsetHeight;
2081 parentWidth = parentElm.clientWidth;
2082 parentHeight = parentElm.clientHeight;
2083 if (align === 'end') {
2084 x -= parentWidth - width;
2085 y -= parentHeight - height;
2086 } else if (align === 'center') {
2087 x -= parentWidth / 2 - width / 2;
2088 y -= parentHeight / 2 - height / 2;
2089 }
2090 parentElm.scrollLeft = x;
2091 parentElm.scrollTop = y;
2092 return this;
2093 },
2094 getRoot: function () {
2095 var ctrl = this, rootControl;
2096 var parents = [];
2097 while (ctrl) {
2098 if (ctrl.rootControl) {
2099 rootControl = ctrl.rootControl;
2100 break;
2101 }
2102 parents.push(ctrl);
2103 rootControl = ctrl;
2104 ctrl = ctrl.parent();
2105 }
2106 if (!rootControl) {
2107 rootControl = this;
2108 }
2109 var i = parents.length;
2110 while (i--) {
2111 parents[i].rootControl = rootControl;
2112 }
2113 return rootControl;
2114 },
2115 reflow: function () {
2116 ReflowQueue.remove(this);
2117 var parent = this.parent();
2118 if (parent && parent._layout && !parent._layout.isNative()) {
2119 parent.reflow();
2120 }
2121 return this;
2122 }
2123 };
2124 global$4.each('text title visible disabled active value'.split(' '), function (name) {
2125 proto$1[name] = function (value) {
2126 if (arguments.length === 0) {
2127 return this.state.get(name);
2128 }
2129 if (typeof value !== 'undefined') {
2130 this.state.set(name, value);
2131 }
2132 return this;
2133 };
2134 });
2135 Control = global$8.extend(proto$1);
2136 function getEventDispatcher(obj) {
2137 if (!obj._eventDispatcher) {
2138 obj._eventDispatcher = new global$9({
2139 scope: obj,
2140 toggleEvent: function (name, state) {
2141 if (state && global$9.isNative(name)) {
2142 if (!obj._nativeEvents) {
2143 obj._nativeEvents = {};
2144 }
2145 obj._nativeEvents[name] = true;
2146 if (obj.state.get('rendered')) {
2147 bindPendingEvents(obj);
2148 }
2149 }
2150 }
2151 });
2152 }
2153 return obj._eventDispatcher;
2154 }
2155 function bindPendingEvents(eventCtrl) {
2156 var i, l, parents, eventRootCtrl, nativeEvents, name;
2157 function delegate(e) {
2158 var control = eventCtrl.getParentCtrl(e.target);
2159 if (control) {
2160 control.fire(e.type, e);
2161 }
2162 }
2163 function mouseLeaveHandler() {
2164 var ctrl = eventRootCtrl._lastHoverCtrl;
2165 if (ctrl) {
2166 ctrl.fire('mouseleave', { target: ctrl.getEl() });
2167 ctrl.parents().each(function (ctrl) {
2168 ctrl.fire('mouseleave', { target: ctrl.getEl() });
2169 });
2170 eventRootCtrl._lastHoverCtrl = null;
2171 }
2172 }
2173 function mouseEnterHandler(e) {
2174 var ctrl = eventCtrl.getParentCtrl(e.target), lastCtrl = eventRootCtrl._lastHoverCtrl, idx = 0, i, parents, lastParents;
2175 if (ctrl !== lastCtrl) {
2176 eventRootCtrl._lastHoverCtrl = ctrl;
2177 parents = ctrl.parents().toArray().reverse();
2178 parents.push(ctrl);
2179 if (lastCtrl) {
2180 lastParents = lastCtrl.parents().toArray().reverse();
2181 lastParents.push(lastCtrl);
2182 for (idx = 0; idx < lastParents.length; idx++) {
2183 if (parents[idx] !== lastParents[idx]) {
2184 break;
2185 }
2186 }
2187 for (i = lastParents.length - 1; i >= idx; i--) {
2188 lastCtrl = lastParents[i];
2189 lastCtrl.fire('mouseleave', { target: lastCtrl.getEl() });
2190 }
2191 }
2192 for (i = idx; i < parents.length; i++) {
2193 ctrl = parents[i];
2194 ctrl.fire('mouseenter', { target: ctrl.getEl() });
2195 }
2196 }
2197 }
2198 function fixWheelEvent(e) {
2199 e.preventDefault();
2200 if (e.type === 'mousewheel') {
2201 e.deltaY = -1 / 40 * e.wheelDelta;
2202 if (e.wheelDeltaX) {
2203 e.deltaX = -1 / 40 * e.wheelDeltaX;
2204 }
2205 } else {
2206 e.deltaX = 0;
2207 e.deltaY = e.detail;
2208 }
2209 e = eventCtrl.fire('wheel', e);
2210 }
2211 nativeEvents = eventCtrl._nativeEvents;
2212 if (nativeEvents) {
2213 parents = eventCtrl.parents().toArray();
2214 parents.unshift(eventCtrl);
2215 for (i = 0, l = parents.length; !eventRootCtrl && i < l; i++) {
2216 eventRootCtrl = parents[i]._eventsRoot;
2217 }
2218 if (!eventRootCtrl) {
2219 eventRootCtrl = parents[parents.length - 1] || eventCtrl;
2220 }
2221 eventCtrl._eventsRoot = eventRootCtrl;
2222 for (l = i, i = 0; i < l; i++) {
2223 parents[i]._eventsRoot = eventRootCtrl;
2224 }
2225 var eventRootDelegates = eventRootCtrl._delegates;
2226 if (!eventRootDelegates) {
2227 eventRootDelegates = eventRootCtrl._delegates = {};
2228 }
2229 for (name in nativeEvents) {
2230 if (!nativeEvents) {
2231 return false;
2232 }
2233 if (name === 'wheel' && !hasWheelEventSupport) {
2234 if (hasMouseWheelEventSupport) {
2235 global$7(eventCtrl.getEl()).on('mousewheel', fixWheelEvent);
2236 } else {
2237 global$7(eventCtrl.getEl()).on('DOMMouseScroll', fixWheelEvent);
2238 }
2239 continue;
2240 }
2241 if (name === 'mouseenter' || name === 'mouseleave') {
2242 if (!eventRootCtrl._hasMouseEnter) {
2243 global$7(eventRootCtrl.getEl()).on('mouseleave', mouseLeaveHandler).on('mouseover', mouseEnterHandler);
2244 eventRootCtrl._hasMouseEnter = 1;
2245 }
2246 } else if (!eventRootDelegates[name]) {
2247 global$7(eventRootCtrl.getEl()).on(name, delegate);
2248 eventRootDelegates[name] = true;
2249 }
2250 nativeEvents[name] = false;
2251 }
2252 }
2253 }
2254 var Control$1 = Control;
2255
2256 var isStatic = function (elm) {
2257 return funcs.getRuntimeStyle(elm, 'position') === 'static';
2258 };
2259 var isFixed = function (ctrl) {
2260 return ctrl.state.get('fixed');
2261 };
2262 function calculateRelativePosition(ctrl, targetElm, rel) {
2263 var ctrlElm, pos, x, y, selfW, selfH, targetW, targetH, viewport, size;
2264 viewport = getWindowViewPort();
2265 pos = funcs.getPos(targetElm, UiContainer.getUiContainer(ctrl));
2266 x = pos.x;
2267 y = pos.y;
2268 if (isFixed(ctrl) && isStatic(domGlobals.document.body)) {
2269 x -= viewport.x;
2270 y -= viewport.y;
2271 }
2272 ctrlElm = ctrl.getEl();
2273 size = funcs.getSize(ctrlElm);
2274 selfW = size.width;
2275 selfH = size.height;
2276 size = funcs.getSize(targetElm);
2277 targetW = size.width;
2278 targetH = size.height;
2279 rel = (rel || '').split('');
2280 if (rel[0] === 'b') {
2281 y += targetH;
2282 }
2283 if (rel[1] === 'r') {
2284 x += targetW;
2285 }
2286 if (rel[0] === 'c') {
2287 y += Math.round(targetH / 2);
2288 }
2289 if (rel[1] === 'c') {
2290 x += Math.round(targetW / 2);
2291 }
2292 if (rel[3] === 'b') {
2293 y -= selfH;
2294 }
2295 if (rel[4] === 'r') {
2296 x -= selfW;
2297 }
2298 if (rel[3] === 'c') {
2299 y -= Math.round(selfH / 2);
2300 }
2301 if (rel[4] === 'c') {
2302 x -= Math.round(selfW / 2);
2303 }
2304 return {
2305 x: x,
2306 y: y,
2307 w: selfW,
2308 h: selfH
2309 };
2310 }
2311 var getUiContainerViewPort = function (customUiContainer) {
2312 return {
2313 x: 0,
2314 y: 0,
2315 w: customUiContainer.scrollWidth - 1,
2316 h: customUiContainer.scrollHeight - 1
2317 };
2318 };
2319 var getWindowViewPort = function () {
2320 var win = domGlobals.window;
2321 var x = Math.max(win.pageXOffset, domGlobals.document.body.scrollLeft, domGlobals.document.documentElement.scrollLeft);
2322 var y = Math.max(win.pageYOffset, domGlobals.document.body.scrollTop, domGlobals.document.documentElement.scrollTop);
2323 var w = win.innerWidth || domGlobals.document.documentElement.clientWidth;
2324 var h = win.innerHeight || domGlobals.document.documentElement.clientHeight;
2325 return {
2326 x: x,
2327 y: y,
2328 w: w,
2329 h: h
2330 };
2331 };
2332 var getViewPortRect = function (ctrl) {
2333 var customUiContainer = UiContainer.getUiContainer(ctrl);
2334 return customUiContainer && !isFixed(ctrl) ? getUiContainerViewPort(customUiContainer) : getWindowViewPort();
2335 };
2336 var Movable = {
2337 testMoveRel: function (elm, rels) {
2338 var viewPortRect = getViewPortRect(this);
2339 for (var i = 0; i < rels.length; i++) {
2340 var pos = calculateRelativePosition(this, elm, rels[i]);
2341 if (isFixed(this)) {
2342 if (pos.x > 0 && pos.x + pos.w < viewPortRect.w && pos.y > 0 && pos.y + pos.h < viewPortRect.h) {
2343 return rels[i];
2344 }
2345 } else {
2346 if (pos.x > viewPortRect.x && pos.x + pos.w < viewPortRect.w + viewPortRect.x && pos.y > viewPortRect.y && pos.y + pos.h < viewPortRect.h + viewPortRect.y) {
2347 return rels[i];
2348 }
2349 }
2350 }
2351 return rels[0];
2352 },
2353 moveRel: function (elm, rel) {
2354 if (typeof rel !== 'string') {
2355 rel = this.testMoveRel(elm, rel);
2356 }
2357 var pos = calculateRelativePosition(this, elm, rel);
2358 return this.moveTo(pos.x, pos.y);
2359 },
2360 moveBy: function (dx, dy) {
2361 var self = this, rect = self.layoutRect();
2362 self.moveTo(rect.x + dx, rect.y + dy);
2363 return self;
2364 },
2365 moveTo: function (x, y) {
2366 var self = this;
2367 function constrain(value, max, size) {
2368 if (value < 0) {
2369 return 0;
2370 }
2371 if (value + size > max) {
2372 value = max - size;
2373 return value < 0 ? 0 : value;
2374 }
2375 return value;
2376 }
2377 if (self.settings.constrainToViewport) {
2378 var viewPortRect = getViewPortRect(this);
2379 var layoutRect = self.layoutRect();
2380 x = constrain(x, viewPortRect.w + viewPortRect.x, layoutRect.w);
2381 y = constrain(y, viewPortRect.h + viewPortRect.y, layoutRect.h);
2382 }
2383 var uiContainer = UiContainer.getUiContainer(self);
2384 if (uiContainer && isStatic(uiContainer) && !isFixed(self)) {
2385 x -= uiContainer.scrollLeft;
2386 y -= uiContainer.scrollTop;
2387 }
2388 if (uiContainer) {
2389 x += 1;
2390 y += 1;
2391 }
2392 if (self.state.get('rendered')) {
2393 self.layoutRect({
2394 x: x,
2395 y: y
2396 }).repaint();
2397 } else {
2398 self.settings.x = x;
2399 self.settings.y = y;
2400 }
2401 self.fire('move', {
2402 x: x,
2403 y: y
2404 });
2405 return self;
2406 }
2407 };
2408
2409 var Tooltip = Control$1.extend({
2410 Mixins: [Movable],
2411 Defaults: { classes: 'widget tooltip tooltip-n' },
2412 renderHtml: function () {
2413 var self = this, prefix = self.classPrefix;
2414 return '<div id="' + self._id + '" class="' + self.classes + '" role="presentation">' + '<div class="' + prefix + 'tooltip-arrow"></div>' + '<div class="' + prefix + 'tooltip-inner">' + self.encode(self.state.get('text')) + '</div>' + '</div>';
2415 },
2416 bindStates: function () {
2417 var self = this;
2418 self.state.on('change:text', function (e) {
2419 self.getEl().lastChild.innerHTML = self.encode(e.value);
2420 });
2421 return self._super();
2422 },
2423 repaint: function () {
2424 var self = this;
2425 var style, rect;
2426 style = self.getEl().style;
2427 rect = self._layoutRect;
2428 style.left = rect.x + 'px';
2429 style.top = rect.y + 'px';
2430 style.zIndex = 65535 + 65535;
2431 }
2432 });
2433
2434 var Widget = Control$1.extend({
2435 init: function (settings) {
2436 var self = this;
2437 self._super(settings);
2438 settings = self.settings;
2439 self.canFocus = true;
2440 if (settings.tooltip && Widget.tooltips !== false) {
2441 self.on('mouseenter', function (e) {
2442 var tooltip = self.tooltip().moveTo(-65535);
2443 if (e.control === self) {
2444 var rel = tooltip.text(settings.tooltip).show().testMoveRel(self.getEl(), [
2445 'bc-tc',
2446 'bc-tl',
2447 'bc-tr'
2448 ]);
2449 tooltip.classes.toggle('tooltip-n', rel === 'bc-tc');
2450 tooltip.classes.toggle('tooltip-nw', rel === 'bc-tl');
2451 tooltip.classes.toggle('tooltip-ne', rel === 'bc-tr');
2452 tooltip.moveRel(self.getEl(), rel);
2453 } else {
2454 tooltip.hide();
2455 }
2456 });
2457 self.on('mouseleave mousedown click', function () {
2458 self.tooltip().remove();
2459 self._tooltip = null;
2460 });
2461 }
2462 self.aria('label', settings.ariaLabel || settings.tooltip);
2463 },
2464 tooltip: function () {
2465 if (!this._tooltip) {
2466 this._tooltip = new Tooltip({ type: 'tooltip' });
2467 UiContainer.inheritUiContainer(this, this._tooltip);
2468 this._tooltip.renderTo();
2469 }
2470 return this._tooltip;
2471 },
2472 postRender: function () {
2473 var self = this, settings = self.settings;
2474 self._super();
2475 if (!self.parent() && (settings.width || settings.height)) {
2476 self.initLayoutRect();
2477 self.repaint();
2478 }
2479 if (settings.autofocus) {
2480 self.focus();
2481 }
2482 },
2483 bindStates: function () {
2484 var self = this;
2485 function disable(state) {
2486 self.aria('disabled', state);
2487 self.classes.toggle('disabled', state);
2488 }
2489 function active(state) {
2490 self.aria('pressed', state);
2491 self.classes.toggle('active', state);
2492 }
2493 self.state.on('change:disabled', function (e) {
2494 disable(e.value);
2495 });
2496 self.state.on('change:active', function (e) {
2497 active(e.value);
2498 });
2499 if (self.state.get('disabled')) {
2500 disable(true);
2501 }
2502 if (self.state.get('active')) {
2503 active(true);
2504 }
2505 return self._super();
2506 },
2507 remove: function () {
2508 this._super();
2509 if (this._tooltip) {
2510 this._tooltip.remove();
2511 this._tooltip = null;
2512 }
2513 }
2514 });
2515
2516 var Progress = Widget.extend({
2517 Defaults: { value: 0 },
2518 init: function (settings) {
2519 var self = this;
2520 self._super(settings);
2521 self.classes.add('progress');
2522 if (!self.settings.filter) {
2523 self.settings.filter = function (value) {
2524 return Math.round(value);
2525 };
2526 }
2527 },
2528 renderHtml: function () {
2529 var self = this, id = self._id, prefix = this.classPrefix;
2530 return '<div id="' + id + '" class="' + self.classes + '">' + '<div class="' + prefix + 'bar-container">' + '<div class="' + prefix + 'bar"></div>' + '</div>' + '<div class="' + prefix + 'text">0%</div>' + '</div>';
2531 },
2532 postRender: function () {
2533 var self = this;
2534 self._super();
2535 self.value(self.settings.value);
2536 return self;
2537 },
2538 bindStates: function () {
2539 var self = this;
2540 function setValue(value) {
2541 value = self.settings.filter(value);
2542 self.getEl().lastChild.innerHTML = value + '%';
2543 self.getEl().firstChild.firstChild.style.width = value + '%';
2544 }
2545 self.state.on('change:value', function (e) {
2546 setValue(e.value);
2547 });
2548 setValue(self.state.get('value'));
2549 return self._super();
2550 }
2551 });
2552
2553 var updateLiveRegion = function (ctx, text) {
2554 ctx.getEl().lastChild.textContent = text + (ctx.progressBar ? ' ' + ctx.progressBar.value() + '%' : '');
2555 };
2556 var Notification = Control$1.extend({
2557 Mixins: [Movable],
2558 Defaults: { classes: 'widget notification' },
2559 init: function (settings) {
2560 var self = this;
2561 self._super(settings);
2562 self.maxWidth = settings.maxWidth;
2563 if (settings.text) {
2564 self.text(settings.text);
2565 }
2566 if (settings.icon) {
2567 self.icon = settings.icon;
2568 }
2569 if (settings.color) {
2570 self.color = settings.color;
2571 }
2572 if (settings.type) {
2573 self.classes.add('notification-' + settings.type);
2574 }
2575 if (settings.timeout && (settings.timeout < 0 || settings.timeout > 0) && !settings.closeButton) {
2576 self.closeButton = false;
2577 } else {
2578 self.classes.add('has-close');
2579 self.closeButton = true;
2580 }
2581 if (settings.progressBar) {
2582 self.progressBar = new Progress();
2583 }
2584 self.on('click', function (e) {
2585 if (e.target.className.indexOf(self.classPrefix + 'close') !== -1) {
2586 self.close();
2587 }
2588 });
2589 },
2590 renderHtml: function () {
2591 var self = this;
2592 var prefix = self.classPrefix;
2593 var icon = '', closeButton = '', progressBar = '', notificationStyle = '';
2594 if (self.icon) {
2595 icon = '<i class="' + prefix + 'ico' + ' ' + prefix + 'i-' + self.icon + '"></i>';
2596 }
2597 notificationStyle = ' style="max-width: ' + self.maxWidth + 'px;' + (self.color ? 'background-color: ' + self.color + ';"' : '"');
2598 if (self.closeButton) {
2599 closeButton = '<button type="button" class="' + prefix + 'close" aria-hidden="true">\xD7</button>';
2600 }
2601 if (self.progressBar) {
2602 progressBar = self.progressBar.renderHtml();
2603 }
2604 return '<div id="' + self._id + '" class="' + self.classes + '"' + notificationStyle + ' role="presentation">' + icon + '<div class="' + prefix + 'notification-inner">' + self.state.get('text') + '</div>' + progressBar + closeButton + '<div style="clip: rect(1px, 1px, 1px, 1px);height: 1px;overflow: hidden;position: absolute;width: 1px;"' + ' aria-live="assertive" aria-relevant="additions" aria-atomic="true"></div>' + '</div>';
2605 },
2606 postRender: function () {
2607 var self = this;
2608 global$3.setTimeout(function () {
2609 self.$el.addClass(self.classPrefix + 'in');
2610 updateLiveRegion(self, self.state.get('text'));
2611 }, 100);
2612 return self._super();
2613 },
2614 bindStates: function () {
2615 var self = this;
2616 self.state.on('change:text', function (e) {
2617 self.getEl().firstChild.innerHTML = e.value;
2618 updateLiveRegion(self, e.value);
2619 });
2620 if (self.progressBar) {
2621 self.progressBar.bindStates();
2622 self.progressBar.state.on('change:value', function (e) {
2623 updateLiveRegion(self, self.state.get('text'));
2624 });
2625 }
2626 return self._super();
2627 },
2628 close: function () {
2629 var self = this;
2630 if (!self.fire('close').isDefaultPrevented()) {
2631 self.remove();
2632 }
2633 return self;
2634 },
2635 repaint: function () {
2636 var self = this;
2637 var style, rect;
2638 style = self.getEl().style;
2639 rect = self._layoutRect;
2640 style.left = rect.x + 'px';
2641 style.top = rect.y + 'px';
2642 style.zIndex = 65535 - 1;
2643 }
2644 });
2645
2646 function NotificationManagerImpl (editor) {
2647 var getEditorContainer = function (editor) {
2648 return editor.inline ? editor.getElement() : editor.getContentAreaContainer();
2649 };
2650 var getContainerWidth = function () {
2651 var container = getEditorContainer(editor);
2652 return funcs.getSize(container).width;
2653 };
2654 var prePositionNotifications = function (notifications) {
2655 each(notifications, function (notification) {
2656 notification.moveTo(0, 0);
2657 });
2658 };
2659 var positionNotifications = function (notifications) {
2660 if (notifications.length > 0) {
2661 var firstItem = notifications.slice(0, 1)[0];
2662 var container = getEditorContainer(editor);
2663 firstItem.moveRel(container, 'tc-tc');
2664 each(notifications, function (notification, index) {
2665 if (index > 0) {
2666 notification.moveRel(notifications[index - 1].getEl(), 'bc-tc');
2667 }
2668 });
2669 }
2670 };
2671 var reposition = function (notifications) {
2672 prePositionNotifications(notifications);
2673 positionNotifications(notifications);
2674 };
2675 var open = function (args, closeCallback) {
2676 var extendedArgs = global$4.extend(args, { maxWidth: getContainerWidth() });
2677 var notif = new Notification(extendedArgs);
2678 notif.args = extendedArgs;
2679 if (extendedArgs.timeout > 0) {
2680 notif.timer = setTimeout(function () {
2681 notif.close();
2682 closeCallback();
2683 }, extendedArgs.timeout);
2684 }
2685 notif.on('close', function () {
2686 closeCallback();
2687 });
2688 notif.renderTo();
2689 return notif;
2690 };
2691 var close = function (notification) {
2692 notification.close();
2693 };
2694 var getArgs = function (notification) {
2695 return notification.args;
2696 };
2697 return {
2698 open: open,
2699 close: close,
2700 reposition: reposition,
2701 getArgs: getArgs
2702 };
2703 }
2704
2705 function getDocumentSize(doc) {
2706 var documentElement, body, scrollWidth, clientWidth;
2707 var offsetWidth, scrollHeight, clientHeight, offsetHeight;
2708 var max = Math.max;
2709 documentElement = doc.documentElement;
2710 body = doc.body;
2711 scrollWidth = max(documentElement.scrollWidth, body.scrollWidth);
2712 clientWidth = max(documentElement.clientWidth, body.clientWidth);
2713 offsetWidth = max(documentElement.offsetWidth, body.offsetWidth);
2714 scrollHeight = max(documentElement.scrollHeight, body.scrollHeight);
2715 clientHeight = max(documentElement.clientHeight, body.clientHeight);
2716 offsetHeight = max(documentElement.offsetHeight, body.offsetHeight);
2717 return {
2718 width: scrollWidth < offsetWidth ? clientWidth : scrollWidth,
2719 height: scrollHeight < offsetHeight ? clientHeight : scrollHeight
2720 };
2721 }
2722 function updateWithTouchData(e) {
2723 var keys, i;
2724 if (e.changedTouches) {
2725 keys = 'screenX screenY pageX pageY clientX clientY'.split(' ');
2726 for (i = 0; i < keys.length; i++) {
2727 e[keys[i]] = e.changedTouches[0][keys[i]];
2728 }
2729 }
2730 }
2731 function DragHelper (id, settings) {
2732 var $eventOverlay;
2733 var doc = settings.document || domGlobals.document;
2734 var downButton;
2735 var start, stop, drag, startX, startY;
2736 settings = settings || {};
2737 var handleElement = doc.getElementById(settings.handle || id);
2738 start = function (e) {
2739 var docSize = getDocumentSize(doc);
2740 var handleElm, cursor;
2741 updateWithTouchData(e);
2742 e.preventDefault();
2743 downButton = e.button;
2744 handleElm = handleElement;
2745 startX = e.screenX;
2746 startY = e.screenY;
2747 if (domGlobals.window.getComputedStyle) {
2748 cursor = domGlobals.window.getComputedStyle(handleElm, null).getPropertyValue('cursor');
2749 } else {
2750 cursor = handleElm.runtimeStyle.cursor;
2751 }
2752 $eventOverlay = global$7('<div></div>').css({
2753 position: 'absolute',
2754 top: 0,
2755 left: 0,
2756 width: docSize.width,
2757 height: docSize.height,
2758 zIndex: 2147483647,
2759 opacity: 0.0001,
2760 cursor: cursor
2761 }).appendTo(doc.body);
2762 global$7(doc).on('mousemove touchmove', drag).on('mouseup touchend', stop);
2763 settings.start(e);
2764 };
2765 drag = function (e) {
2766 updateWithTouchData(e);
2767 if (e.button !== downButton) {
2768 return stop(e);
2769 }
2770 e.deltaX = e.screenX - startX;
2771 e.deltaY = e.screenY - startY;
2772 e.preventDefault();
2773 settings.drag(e);
2774 };
2775 stop = function (e) {
2776 updateWithTouchData(e);
2777 global$7(doc).off('mousemove touchmove', drag).off('mouseup touchend', stop);
2778 $eventOverlay.remove();
2779 if (settings.stop) {
2780 settings.stop(e);
2781 }
2782 };
2783 this.destroy = function () {
2784 global$7(handleElement).off();
2785 };
2786 global$7(handleElement).on('mousedown touchstart', start);
2787 }
2788
2789 var global$b = tinymce.util.Tools.resolve('tinymce.ui.Factory');
2790
2791 var hasTabstopData = function (elm) {
2792 return elm.getAttribute('data-mce-tabstop') ? true : false;
2793 };
2794 function KeyboardNavigation (settings) {
2795 var root = settings.root;
2796 var focusedElement, focusedControl;
2797 function isElement(node) {
2798 return node && node.nodeType === 1;
2799 }
2800 try {
2801 focusedElement = domGlobals.document.activeElement;
2802 } catch (ex) {
2803 focusedElement = domGlobals.document.body;
2804 }
2805 focusedControl = root.getParentCtrl(focusedElement);
2806 function getRole(elm) {
2807 elm = elm || focusedElement;
2808 if (isElement(elm)) {
2809 return elm.getAttribute('role');
2810 }
2811 return null;
2812 }
2813 function getParentRole(elm) {
2814 var role, parent = elm || focusedElement;
2815 while (parent = parent.parentNode) {
2816 if (role = getRole(parent)) {
2817 return role;
2818 }
2819 }
2820 }
2821 function getAriaProp(name) {
2822 var elm = focusedElement;
2823 if (isElement(elm)) {
2824 return elm.getAttribute('aria-' + name);
2825 }
2826 }
2827 function isTextInputElement(elm) {
2828 var tagName = elm.tagName.toUpperCase();
2829 return tagName === 'INPUT' || tagName === 'TEXTAREA' || tagName === 'SELECT';
2830 }
2831 function canFocus(elm) {
2832 if (isTextInputElement(elm) && !elm.hidden) {
2833 return true;
2834 }
2835 if (hasTabstopData(elm)) {
2836 return true;
2837 }
2838 if (/^(button|menuitem|checkbox|tab|menuitemcheckbox|option|gridcell|slider)$/.test(getRole(elm))) {
2839 return true;
2840 }
2841 return false;
2842 }
2843 function getFocusElements(elm) {
2844 var elements = [];
2845 function collect(elm) {
2846 if (elm.nodeType !== 1 || elm.style.display === 'none' || elm.disabled) {
2847 return;
2848 }
2849 if (canFocus(elm)) {
2850 elements.push(elm);
2851 }
2852 for (var i = 0; i < elm.childNodes.length; i++) {
2853 collect(elm.childNodes[i]);
2854 }
2855 }
2856 collect(elm || root.getEl());
2857 return elements;
2858 }
2859 function getNavigationRoot(targetControl) {
2860 var navigationRoot, controls;
2861 targetControl = targetControl || focusedControl;
2862 controls = targetControl.parents().toArray();
2863 controls.unshift(targetControl);
2864 for (var i = 0; i < controls.length; i++) {
2865 navigationRoot = controls[i];
2866 if (navigationRoot.settings.ariaRoot) {
2867 break;
2868 }
2869 }
2870 return navigationRoot;
2871 }
2872 function focusFirst(targetControl) {
2873 var navigationRoot = getNavigationRoot(targetControl);
2874 var focusElements = getFocusElements(navigationRoot.getEl());
2875 if (navigationRoot.settings.ariaRemember && 'lastAriaIndex' in navigationRoot) {
2876 moveFocusToIndex(navigationRoot.lastAriaIndex, focusElements);
2877 } else {
2878 moveFocusToIndex(0, focusElements);
2879 }
2880 }
2881 function moveFocusToIndex(idx, elements) {
2882 if (idx < 0) {
2883 idx = elements.length - 1;
2884 } else if (idx >= elements.length) {
2885 idx = 0;
2886 }
2887 if (elements[idx]) {
2888 elements[idx].focus();
2889 }
2890 return idx;
2891 }
2892 function moveFocus(dir, elements) {
2893 var idx = -1;
2894 var navigationRoot = getNavigationRoot();
2895 elements = elements || getFocusElements(navigationRoot.getEl());
2896 for (var i = 0; i < elements.length; i++) {
2897 if (elements[i] === focusedElement) {
2898 idx = i;
2899 }
2900 }
2901 idx += dir;
2902 navigationRoot.lastAriaIndex = moveFocusToIndex(idx, elements);
2903 }
2904 function left() {
2905 var parentRole = getParentRole();
2906 if (parentRole === 'tablist') {
2907 moveFocus(-1, getFocusElements(focusedElement.parentNode));
2908 } else if (focusedControl.parent().submenu) {
2909 cancel();
2910 } else {
2911 moveFocus(-1);
2912 }
2913 }
2914 function right() {
2915 var role = getRole(), parentRole = getParentRole();
2916 if (parentRole === 'tablist') {
2917 moveFocus(1, getFocusElements(focusedElement.parentNode));
2918 } else if (role === 'menuitem' && parentRole === 'menu' && getAriaProp('haspopup')) {
2919 enter();
2920 } else {
2921 moveFocus(1);
2922 }
2923 }
2924 function up() {
2925 moveFocus(-1);
2926 }
2927 function down() {
2928 var role = getRole(), parentRole = getParentRole();
2929 if (role === 'menuitem' && parentRole === 'menubar') {
2930 enter();
2931 } else if (role === 'button' && getAriaProp('haspopup')) {
2932 enter({ key: 'down' });
2933 } else {
2934 moveFocus(1);
2935 }
2936 }
2937 function tab(e) {
2938 var parentRole = getParentRole();
2939 if (parentRole === 'tablist') {
2940 var elm = getFocusElements(focusedControl.getEl('body'))[0];
2941 if (elm) {
2942 elm.focus();
2943 }
2944 } else {
2945 moveFocus(e.shiftKey ? -1 : 1);
2946 }
2947 }
2948 function cancel() {
2949 focusedControl.fire('cancel');
2950 }
2951 function enter(aria) {
2952 aria = aria || {};
2953 focusedControl.fire('click', {
2954 target: focusedElement,
2955 aria: aria
2956 });
2957 }
2958 root.on('keydown', function (e) {
2959 function handleNonTabOrEscEvent(e, handler) {
2960 if (isTextInputElement(focusedElement) || hasTabstopData(focusedElement)) {
2961 return;
2962 }
2963 if (getRole(focusedElement) === 'slider') {
2964 return;
2965 }
2966 if (handler(e) !== false) {
2967 e.preventDefault();
2968 }
2969 }
2970 if (e.isDefaultPrevented()) {
2971 return;
2972 }
2973 switch (e.keyCode) {
2974 case 37:
2975 handleNonTabOrEscEvent(e, left);
2976 break;
2977 case 39:
2978 handleNonTabOrEscEvent(e, right);
2979 break;
2980 case 38:
2981 handleNonTabOrEscEvent(e, up);
2982 break;
2983 case 40:
2984 handleNonTabOrEscEvent(e, down);
2985 break;
2986 case 27:
2987 cancel();
2988 break;
2989 case 14:
2990 case 13:
2991 case 32:
2992 handleNonTabOrEscEvent(e, enter);
2993 break;
2994 case 9:
2995 tab(e);
2996 e.preventDefault();
2997 break;
2998 }
2999 });
3000 root.on('focusin', function (e) {
3001 focusedElement = e.target;
3002 focusedControl = e.control;
3003 });
3004 return { focusFirst: focusFirst };
3005 }
3006
3007 var selectorCache = {};
3008 var Container = Control$1.extend({
3009 init: function (settings) {
3010 var self = this;
3011 self._super(settings);
3012 settings = self.settings;
3013 if (settings.fixed) {
3014 self.state.set('fixed', true);
3015 }
3016 self._items = new Collection$2();
3017 if (self.isRtl()) {
3018 self.classes.add('rtl');
3019 }
3020 self.bodyClasses = new ClassList(function () {
3021 if (self.state.get('rendered')) {
3022 self.getEl('body').className = this.toString();
3023 }
3024 });
3025 self.bodyClasses.prefix = self.classPrefix;
3026 self.classes.add('container');
3027 self.bodyClasses.add('container-body');
3028 if (settings.containerCls) {
3029 self.classes.add(settings.containerCls);
3030 }
3031 self._layout = global$b.create((settings.layout || '') + 'layout');
3032 if (self.settings.items) {
3033 self.add(self.settings.items);
3034 } else {
3035 self.add(self.render());
3036 }
3037 self._hasBody = true;
3038 },
3039 items: function () {
3040 return this._items;
3041 },
3042 find: function (selector) {
3043 selector = selectorCache[selector] = selectorCache[selector] || new Selector(selector);
3044 return selector.find(this);
3045 },
3046 add: function (items) {
3047 var self = this;
3048 self.items().add(self.create(items)).parent(self);
3049 return self;
3050 },
3051 focus: function (keyboard) {
3052 var self = this;
3053 var focusCtrl, keyboardNav, items;
3054 if (keyboard) {
3055 keyboardNav = self.keyboardNav || self.parents().eq(-1)[0].keyboardNav;
3056 if (keyboardNav) {
3057 keyboardNav.focusFirst(self);
3058 return;
3059 }
3060 }
3061 items = self.find('*');
3062 if (self.statusbar) {
3063 items.add(self.statusbar.items());
3064 }
3065 items.each(function (ctrl) {
3066 if (ctrl.settings.autofocus) {
3067 focusCtrl = null;
3068 return false;
3069 }
3070 if (ctrl.canFocus) {
3071 focusCtrl = focusCtrl || ctrl;
3072 }
3073 });
3074 if (focusCtrl) {
3075 focusCtrl.focus();
3076 }
3077 return self;
3078 },
3079 replace: function (oldItem, newItem) {
3080 var ctrlElm;
3081 var items = this.items();
3082 var i = items.length;
3083 while (i--) {
3084 if (items[i] === oldItem) {
3085 items[i] = newItem;
3086 break;
3087 }
3088 }
3089 if (i >= 0) {
3090 ctrlElm = newItem.getEl();
3091 if (ctrlElm) {
3092 ctrlElm.parentNode.removeChild(ctrlElm);
3093 }
3094 ctrlElm = oldItem.getEl();
3095 if (ctrlElm) {
3096 ctrlElm.parentNode.removeChild(ctrlElm);
3097 }
3098 }
3099 newItem.parent(this);
3100 },
3101 create: function (items) {
3102 var self = this;
3103 var settings;
3104 var ctrlItems = [];
3105 if (!global$4.isArray(items)) {
3106 items = [items];
3107 }
3108 global$4.each(items, function (item) {
3109 if (item) {
3110 if (!(item instanceof Control$1)) {
3111 if (typeof item === 'string') {
3112 item = { type: item };
3113 }
3114 settings = global$4.extend({}, self.settings.defaults, item);
3115 item.type = settings.type = settings.type || item.type || self.settings.defaultType || (settings.defaults ? settings.defaults.type : null);
3116 item = global$b.create(settings);
3117 }
3118 ctrlItems.push(item);
3119 }
3120 });
3121 return ctrlItems;
3122 },
3123 renderNew: function () {
3124 var self = this;
3125 self.items().each(function (ctrl, index) {
3126 var containerElm;
3127 ctrl.parent(self);
3128 if (!ctrl.state.get('rendered')) {
3129 containerElm = self.getEl('body');
3130 if (containerElm.hasChildNodes() && index <= containerElm.childNodes.length - 1) {
3131 global$7(containerElm.childNodes[index]).before(ctrl.renderHtml());
3132 } else {
3133 global$7(containerElm).append(ctrl.renderHtml());
3134 }
3135 ctrl.postRender();
3136 ReflowQueue.add(ctrl);
3137 }
3138 });
3139 self._layout.applyClasses(self.items().filter(':visible'));
3140 self._lastRect = null;
3141 return self;
3142 },
3143 append: function (items) {
3144 return this.add(items).renderNew();
3145 },
3146 prepend: function (items) {
3147 var self = this;
3148 self.items().set(self.create(items).concat(self.items().toArray()));
3149 return self.renderNew();
3150 },
3151 insert: function (items, index, before) {
3152 var self = this;
3153 var curItems, beforeItems, afterItems;
3154 items = self.create(items);
3155 curItems = self.items();
3156 if (!before && index < curItems.length - 1) {
3157 index += 1;
3158 }
3159 if (index >= 0 && index < curItems.length) {
3160 beforeItems = curItems.slice(0, index).toArray();
3161 afterItems = curItems.slice(index).toArray();
3162 curItems.set(beforeItems.concat(items, afterItems));
3163 }
3164 return self.renderNew();
3165 },
3166 fromJSON: function (data) {
3167 var self = this;
3168 for (var name in data) {
3169 self.find('#' + name).value(data[name]);
3170 }
3171 return self;
3172 },
3173 toJSON: function () {
3174 var self = this, data = {};
3175 self.find('*').each(function (ctrl) {
3176 var name = ctrl.name(), value = ctrl.value();
3177 if (name && typeof value !== 'undefined') {
3178 data[name] = value;
3179 }
3180 });
3181 return data;
3182 },
3183 renderHtml: function () {
3184 var self = this, layout = self._layout, role = this.settings.role;
3185 self.preRender();
3186 layout.preRender(self);
3187 return '<div id="' + self._id + '" class="' + self.classes + '"' + (role ? ' role="' + this.settings.role + '"' : '') + '>' + '<div id="' + self._id + '-body" class="' + self.bodyClasses + '">' + (self.settings.html || '') + layout.renderHtml(self) + '</div>' + '</div>';
3188 },
3189 postRender: function () {
3190 var self = this;
3191 var box;
3192 self.items().exec('postRender');
3193 self._super();
3194 self._layout.postRender(self);
3195 self.state.set('rendered', true);
3196 if (self.settings.style) {
3197 self.$el.css(self.settings.style);
3198 }
3199 if (self.settings.border) {
3200 box = self.borderBox;
3201 self.$el.css({
3202 'border-top-width': box.top,
3203 'border-right-width': box.right,
3204 'border-bottom-width': box.bottom,
3205 'border-left-width': box.left
3206 });
3207 }
3208 if (!self.parent()) {
3209 self.keyboardNav = KeyboardNavigation({ root: self });
3210 }
3211 return self;
3212 },
3213 initLayoutRect: function () {
3214 var self = this, layoutRect = self._super();
3215 self._layout.recalc(self);
3216 return layoutRect;
3217 },
3218 recalc: function () {
3219 var self = this;
3220 var rect = self._layoutRect;
3221 var lastRect = self._lastRect;
3222 if (!lastRect || lastRect.w !== rect.w || lastRect.h !== rect.h) {
3223 self._layout.recalc(self);
3224 rect = self.layoutRect();
3225 self._lastRect = {
3226 x: rect.x,
3227 y: rect.y,
3228 w: rect.w,
3229 h: rect.h
3230 };
3231 return true;
3232 }
3233 },
3234 reflow: function () {
3235 var i;
3236 ReflowQueue.remove(this);
3237 if (this.visible()) {
3238 Control$1.repaintControls = [];
3239 Control$1.repaintControls.map = {};
3240 this.recalc();
3241 i = Control$1.repaintControls.length;
3242 while (i--) {
3243 Control$1.repaintControls[i].repaint();
3244 }
3245 if (this.settings.layout !== 'flow' && this.settings.layout !== 'stack') {
3246 this.repaint();
3247 }
3248 Control$1.repaintControls = [];
3249 }
3250 return this;
3251 }
3252 });
3253
3254 var Scrollable = {
3255 init: function () {
3256 var self = this;
3257 self.on('repaint', self.renderScroll);
3258 },
3259 renderScroll: function () {
3260 var self = this, margin = 2;
3261 function repaintScroll() {
3262 var hasScrollH, hasScrollV, bodyElm;
3263 function repaintAxis(axisName, posName, sizeName, contentSizeName, hasScroll, ax) {
3264 var containerElm, scrollBarElm, scrollThumbElm;
3265 var containerSize, scrollSize, ratio, rect;
3266 var posNameLower, sizeNameLower;
3267 scrollBarElm = self.getEl('scroll' + axisName);
3268 if (scrollBarElm) {
3269 posNameLower = posName.toLowerCase();
3270 sizeNameLower = sizeName.toLowerCase();
3271 global$7(self.getEl('absend')).css(posNameLower, self.layoutRect()[contentSizeName] - 1);
3272 if (!hasScroll) {
3273 global$7(scrollBarElm).css('display', 'none');
3274 return;
3275 }
3276 global$7(scrollBarElm).css('display', 'block');
3277 containerElm = self.getEl('body');
3278 scrollThumbElm = self.getEl('scroll' + axisName + 't');
3279 containerSize = containerElm['client' + sizeName] - margin * 2;
3280 containerSize -= hasScrollH && hasScrollV ? scrollBarElm['client' + ax] : 0;
3281 scrollSize = containerElm['scroll' + sizeName];
3282 ratio = containerSize / scrollSize;
3283 rect = {};
3284 rect[posNameLower] = containerElm['offset' + posName] + margin;
3285 rect[sizeNameLower] = containerSize;
3286 global$7(scrollBarElm).css(rect);
3287 rect = {};
3288 rect[posNameLower] = containerElm['scroll' + posName] * ratio;
3289 rect[sizeNameLower] = containerSize * ratio;
3290 global$7(scrollThumbElm).css(rect);
3291 }
3292 }
3293 bodyElm = self.getEl('body');
3294 hasScrollH = bodyElm.scrollWidth > bodyElm.clientWidth;
3295 hasScrollV = bodyElm.scrollHeight > bodyElm.clientHeight;
3296 repaintAxis('h', 'Left', 'Width', 'contentW', hasScrollH, 'Height');
3297 repaintAxis('v', 'Top', 'Height', 'contentH', hasScrollV, 'Width');
3298 }
3299 function addScroll() {
3300 function addScrollAxis(axisName, posName, sizeName, deltaPosName, ax) {
3301 var scrollStart;
3302 var axisId = self._id + '-scroll' + axisName, prefix = self.classPrefix;
3303 global$7(self.getEl()).append('<div id="' + axisId + '" class="' + prefix + 'scrollbar ' + prefix + 'scrollbar-' + axisName + '">' + '<div id="' + axisId + 't" class="' + prefix + 'scrollbar-thumb"></div>' + '</div>');
3304 self.draghelper = new DragHelper(axisId + 't', {
3305 start: function () {
3306 scrollStart = self.getEl('body')['scroll' + posName];
3307 global$7('#' + axisId).addClass(prefix + 'active');
3308 },
3309 drag: function (e) {
3310 var ratio, hasScrollH, hasScrollV, containerSize;
3311 var layoutRect = self.layoutRect();
3312 hasScrollH = layoutRect.contentW > layoutRect.innerW;
3313 hasScrollV = layoutRect.contentH > layoutRect.innerH;
3314 containerSize = self.getEl('body')['client' + sizeName] - margin * 2;
3315 containerSize -= hasScrollH && hasScrollV ? self.getEl('scroll' + axisName)['client' + ax] : 0;
3316 ratio = containerSize / self.getEl('body')['scroll' + sizeName];
3317 self.getEl('body')['scroll' + posName] = scrollStart + e['delta' + deltaPosName] / ratio;
3318 },
3319 stop: function () {
3320 global$7('#' + axisId).removeClass(prefix + 'active');
3321 }
3322 });
3323 }
3324 self.classes.add('scroll');
3325 addScrollAxis('v', 'Top', 'Height', 'Y', 'Width');
3326 addScrollAxis('h', 'Left', 'Width', 'X', 'Height');
3327 }
3328 if (self.settings.autoScroll) {
3329 if (!self._hasScroll) {
3330 self._hasScroll = true;
3331 addScroll();
3332 self.on('wheel', function (e) {
3333 var bodyEl = self.getEl('body');
3334 bodyEl.scrollLeft += (e.deltaX || 0) * 10;
3335 bodyEl.scrollTop += e.deltaY * 10;
3336 repaintScroll();
3337 });
3338 global$7(self.getEl('body')).on('scroll', repaintScroll);
3339 }
3340 repaintScroll();
3341 }
3342 }
3343 };
3344
3345 var Panel = Container.extend({
3346 Defaults: {
3347 layout: 'fit',
3348 containerCls: 'panel'
3349 },
3350 Mixins: [Scrollable],
3351 renderHtml: function () {
3352 var self = this;
3353 var layout = self._layout;
3354 var innerHtml = self.settings.html;
3355 self.preRender();
3356 layout.preRender(self);
3357 if (typeof innerHtml === 'undefined') {
3358 innerHtml = '<div id="' + self._id + '-body" class="' + self.bodyClasses + '">' + layout.renderHtml(self) + '</div>';
3359 } else {
3360 if (typeof innerHtml === 'function') {
3361 innerHtml = innerHtml.call(self);
3362 }
3363 self._hasBody = false;
3364 }
3365 return '<div id="' + self._id + '" class="' + self.classes + '" hidefocus="1" tabindex="-1" role="group">' + (self._preBodyHtml || '') + innerHtml + '</div>';
3366 }
3367 });
3368
3369 var Resizable = {
3370 resizeToContent: function () {
3371 this._layoutRect.autoResize = true;
3372 this._lastRect = null;
3373 this.reflow();
3374 },
3375 resizeTo: function (w, h) {
3376 if (w <= 1 || h <= 1) {
3377 var rect = funcs.getWindowSize();
3378 w = w <= 1 ? w * rect.w : w;
3379 h = h <= 1 ? h * rect.h : h;
3380 }
3381 this._layoutRect.autoResize = false;
3382 return this.layoutRect({
3383 minW: w,
3384 minH: h,
3385 w: w,
3386 h: h
3387 }).reflow();
3388 },
3389 resizeBy: function (dw, dh) {
3390 var self = this, rect = self.layoutRect();
3391 return self.resizeTo(rect.w + dw, rect.h + dh);
3392 }
3393 };
3394
3395 var documentClickHandler, documentScrollHandler, windowResizeHandler;
3396 var visiblePanels = [];
3397 var zOrder = [];
3398 var hasModal;
3399 function isChildOf(ctrl, parent) {
3400 while (ctrl) {
3401 if (ctrl === parent) {
3402 return true;
3403 }
3404 ctrl = ctrl.parent();
3405 }
3406 }
3407 function skipOrHidePanels(e) {
3408 var i = visiblePanels.length;
3409 while (i--) {
3410 var panel = visiblePanels[i], clickCtrl = panel.getParentCtrl(e.target);
3411 if (panel.settings.autohide) {
3412 if (clickCtrl) {
3413 if (isChildOf(clickCtrl, panel) || panel.parent() === clickCtrl) {
3414 continue;
3415 }
3416 }
3417 e = panel.fire('autohide', { target: e.target });
3418 if (!e.isDefaultPrevented()) {
3419 panel.hide();
3420 }
3421 }
3422 }
3423 }
3424 function bindDocumentClickHandler() {
3425 if (!documentClickHandler) {
3426 documentClickHandler = function (e) {
3427 if (e.button === 2) {
3428 return;
3429 }
3430 skipOrHidePanels(e);
3431 };
3432 global$7(domGlobals.document).on('click touchstart', documentClickHandler);
3433 }
3434 }
3435 function bindDocumentScrollHandler() {
3436 if (!documentScrollHandler) {
3437 documentScrollHandler = function () {
3438 var i;
3439 i = visiblePanels.length;
3440 while (i--) {
3441 repositionPanel$1(visiblePanels[i]);
3442 }
3443 };
3444 global$7(domGlobals.window).on('scroll', documentScrollHandler);
3445 }
3446 }
3447 function bindWindowResizeHandler() {
3448 if (!windowResizeHandler) {
3449 var docElm_1 = domGlobals.document.documentElement;
3450 var clientWidth_1 = docElm_1.clientWidth, clientHeight_1 = docElm_1.clientHeight;
3451 windowResizeHandler = function () {
3452 if (!domGlobals.document.all || clientWidth_1 !== docElm_1.clientWidth || clientHeight_1 !== docElm_1.clientHeight) {
3453 clientWidth_1 = docElm_1.clientWidth;
3454 clientHeight_1 = docElm_1.clientHeight;
3455 FloatPanel.hideAll();
3456 }
3457 };
3458 global$7(domGlobals.window).on('resize', windowResizeHandler);
3459 }
3460 }
3461 function repositionPanel$1(panel) {
3462 var scrollY = funcs.getViewPort().y;
3463 function toggleFixedChildPanels(fixed, deltaY) {
3464 var parent;
3465 for (var i = 0; i < visiblePanels.length; i++) {
3466 if (visiblePanels[i] !== panel) {
3467 parent = visiblePanels[i].parent();
3468 while (parent && (parent = parent.parent())) {
3469 if (parent === panel) {
3470 visiblePanels[i].fixed(fixed).moveBy(0, deltaY).repaint();
3471 }
3472 }
3473 }
3474 }
3475 }
3476 if (panel.settings.autofix) {
3477 if (!panel.state.get('fixed')) {
3478 panel._autoFixY = panel.layoutRect().y;
3479 if (panel._autoFixY < scrollY) {
3480 panel.fixed(true).layoutRect({ y: 0 }).repaint();
3481 toggleFixedChildPanels(true, scrollY - panel._autoFixY);
3482 }
3483 } else {
3484 if (panel._autoFixY > scrollY) {
3485 panel.fixed(false).layoutRect({ y: panel._autoFixY }).repaint();
3486 toggleFixedChildPanels(false, panel._autoFixY - scrollY);
3487 }
3488 }
3489 }
3490 }
3491 function addRemove(add, ctrl) {
3492 var i, zIndex = FloatPanel.zIndex || 65535, topModal;
3493 if (add) {
3494 zOrder.push(ctrl);
3495 } else {
3496 i = zOrder.length;
3497 while (i--) {
3498 if (zOrder[i] === ctrl) {
3499 zOrder.splice(i, 1);
3500 }
3501 }
3502 }
3503 if (zOrder.length) {
3504 for (i = 0; i < zOrder.length; i++) {
3505 if (zOrder[i].modal) {
3506 zIndex++;
3507 topModal = zOrder[i];
3508 }
3509 zOrder[i].getEl().style.zIndex = zIndex;
3510 zOrder[i].zIndex = zIndex;
3511 zIndex++;
3512 }
3513 }
3514 var modalBlockEl = global$7('#' + ctrl.classPrefix + 'modal-block', ctrl.getContainerElm())[0];
3515 if (topModal) {
3516 global$7(modalBlockEl).css('z-index', topModal.zIndex - 1);
3517 } else if (modalBlockEl) {
3518 modalBlockEl.parentNode.removeChild(modalBlockEl);
3519 hasModal = false;
3520 }
3521 FloatPanel.currentZIndex = zIndex;
3522 }
3523 var FloatPanel = Panel.extend({
3524 Mixins: [
3525 Movable,
3526 Resizable
3527 ],
3528 init: function (settings) {
3529 var self = this;
3530 self._super(settings);
3531 self._eventsRoot = self;
3532 self.classes.add('floatpanel');
3533 if (settings.autohide) {
3534 bindDocumentClickHandler();
3535 bindWindowResizeHandler();
3536 visiblePanels.push(self);
3537 }
3538 if (settings.autofix) {
3539 bindDocumentScrollHandler();
3540 self.on('move', function () {
3541 repositionPanel$1(this);
3542 });
3543 }
3544 self.on('postrender show', function (e) {
3545 if (e.control === self) {
3546 var $modalBlockEl_1;
3547 var prefix_1 = self.classPrefix;
3548 if (self.modal && !hasModal) {
3549 $modalBlockEl_1 = global$7('#' + prefix_1 + 'modal-block', self.getContainerElm());
3550 if (!$modalBlockEl_1[0]) {
3551 $modalBlockEl_1 = global$7('<div id="' + prefix_1 + 'modal-block" class="' + prefix_1 + 'reset ' + prefix_1 + 'fade"></div>').appendTo(self.getContainerElm());
3552 }
3553 global$3.setTimeout(function () {
3554 $modalBlockEl_1.addClass(prefix_1 + 'in');
3555 global$7(self.getEl()).addClass(prefix_1 + 'in');
3556 });
3557 hasModal = true;
3558 }
3559 addRemove(true, self);
3560 }
3561 });
3562 self.on('show', function () {
3563 self.parents().each(function (ctrl) {
3564 if (ctrl.state.get('fixed')) {
3565 self.fixed(true);
3566 return false;
3567 }
3568 });
3569 });
3570 if (settings.popover) {
3571 self._preBodyHtml = '<div class="' + self.classPrefix + 'arrow"></div>';
3572 self.classes.add('popover').add('bottom').add(self.isRtl() ? 'end' : 'start');
3573 }
3574 self.aria('label', settings.ariaLabel);
3575 self.aria('labelledby', self._id);
3576 self.aria('describedby', self.describedBy || self._id + '-none');
3577 },
3578 fixed: function (state) {
3579 var self = this;
3580 if (self.state.get('fixed') !== state) {
3581 if (self.state.get('rendered')) {
3582 var viewport = funcs.getViewPort();
3583 if (state) {
3584 self.layoutRect().y -= viewport.y;
3585 } else {
3586 self.layoutRect().y += viewport.y;
3587 }
3588 }
3589 self.classes.toggle('fixed', state);
3590 self.state.set('fixed', state);
3591 }
3592 return self;
3593 },
3594 show: function () {
3595 var self = this;
3596 var i;
3597 var state = self._super();
3598 i = visiblePanels.length;
3599 while (i--) {
3600 if (visiblePanels[i] === self) {
3601 break;
3602 }
3603 }
3604 if (i === -1) {
3605 visiblePanels.push(self);
3606 }
3607 return state;
3608 },
3609 hide: function () {
3610 removeVisiblePanel(this);
3611 addRemove(false, this);
3612 return this._super();
3613 },
3614 hideAll: function () {
3615 FloatPanel.hideAll();
3616 },
3617 close: function () {
3618 var self = this;
3619 if (!self.fire('close').isDefaultPrevented()) {
3620 self.remove();
3621 addRemove(false, self);
3622 }
3623 return self;
3624 },
3625 remove: function () {
3626 removeVisiblePanel(this);
3627 this._super();
3628 },
3629 postRender: function () {
3630 var self = this;
3631 if (self.settings.bodyRole) {
3632 this.getEl('body').setAttribute('role', self.settings.bodyRole);
3633 }
3634 return self._super();
3635 }
3636 });
3637 FloatPanel.hideAll = function () {
3638 var i = visiblePanels.length;
3639 while (i--) {
3640 var panel = visiblePanels[i];
3641 if (panel && panel.settings.autohide) {
3642 panel.hide();
3643 visiblePanels.splice(i, 1);
3644 }
3645 }
3646 };
3647 function removeVisiblePanel(panel) {
3648 var i;
3649 i = visiblePanels.length;
3650 while (i--) {
3651 if (visiblePanels[i] === panel) {
3652 visiblePanels.splice(i, 1);
3653 }
3654 }
3655 i = zOrder.length;
3656 while (i--) {
3657 if (zOrder[i] === panel) {
3658 zOrder.splice(i, 1);
3659 }
3660 }
3661 }
3662
3663 var windows = [];
3664 var oldMetaValue = '';
3665 function toggleFullScreenState(state) {
3666 var noScaleMetaValue = 'width=device-width,initial-scale=1.0,user-scalable=0,minimum-scale=1.0,maximum-scale=1.0';
3667 var viewport = global$7('meta[name=viewport]')[0], contentValue;
3668 if (global$1.overrideViewPort === false) {
3669 return;
3670 }
3671 if (!viewport) {
3672 viewport = domGlobals.document.createElement('meta');
3673 viewport.setAttribute('name', 'viewport');
3674 domGlobals.document.getElementsByTagName('head')[0].appendChild(viewport);
3675 }
3676 contentValue = viewport.getAttribute('content');
3677 if (contentValue && typeof oldMetaValue !== 'undefined') {
3678 oldMetaValue = contentValue;
3679 }
3680 viewport.setAttribute('content', state ? noScaleMetaValue : oldMetaValue);
3681 }
3682 function toggleBodyFullScreenClasses(classPrefix, state) {
3683 if (checkFullscreenWindows() && state === false) {
3684 global$7([
3685 domGlobals.document.documentElement,
3686 domGlobals.document.body
3687 ]).removeClass(classPrefix + 'fullscreen');
3688 }
3689 }
3690 function checkFullscreenWindows() {
3691 for (var i = 0; i < windows.length; i++) {
3692 if (windows[i]._fullscreen) {
3693 return true;
3694 }
3695 }
3696 return false;
3697 }
3698 function handleWindowResize() {
3699 if (!global$1.desktop) {
3700 var lastSize_1 = {
3701 w: domGlobals.window.innerWidth,
3702 h: domGlobals.window.innerHeight
3703 };
3704 global$3.setInterval(function () {
3705 var w = domGlobals.window.innerWidth, h = domGlobals.window.innerHeight;
3706 if (lastSize_1.w !== w || lastSize_1.h !== h) {
3707 lastSize_1 = {
3708 w: w,
3709 h: h
3710 };
3711 global$7(domGlobals.window).trigger('resize');
3712 }
3713 }, 100);
3714 }
3715 function reposition() {
3716 var i;
3717 var rect = funcs.getWindowSize();
3718 var layoutRect;
3719 for (i = 0; i < windows.length; i++) {
3720 layoutRect = windows[i].layoutRect();
3721 windows[i].moveTo(windows[i].settings.x || Math.max(0, rect.w / 2 - layoutRect.w / 2), windows[i].settings.y || Math.max(0, rect.h / 2 - layoutRect.h / 2));
3722 }
3723 }
3724 global$7(domGlobals.window).on('resize', reposition);
3725 }
3726 var Window = FloatPanel.extend({
3727 modal: true,
3728 Defaults: {
3729 border: 1,
3730 layout: 'flex',
3731 containerCls: 'panel',
3732 role: 'dialog',
3733 callbacks: {
3734 submit: function () {
3735 this.fire('submit', { data: this.toJSON() });
3736 },
3737 close: function () {
3738 this.close();
3739 }
3740 }
3741 },
3742 init: function (settings) {
3743 var self = this;
3744 self._super(settings);
3745 if (self.isRtl()) {
3746 self.classes.add('rtl');
3747 }
3748 self.classes.add('window');
3749 self.bodyClasses.add('window-body');
3750 self.state.set('fixed', true);
3751 if (settings.buttons) {
3752 self.statusbar = new Panel({
3753 layout: 'flex',
3754 border: '1 0 0 0',
3755 spacing: 3,
3756 padding: 10,
3757 align: 'center',
3758 pack: self.isRtl() ? 'start' : 'end',
3759 defaults: { type: 'button' },
3760 items: settings.buttons
3761 });
3762 self.statusbar.classes.add('foot');
3763 self.statusbar.parent(self);
3764 }
3765 self.on('click', function (e) {
3766 var closeClass = self.classPrefix + 'close';
3767 if (funcs.hasClass(e.target, closeClass) || funcs.hasClass(e.target.parentNode, closeClass)) {
3768 self.close();
3769 }
3770 });
3771 self.on('cancel', function () {
3772 self.close();
3773 });
3774 self.on('move', function (e) {
3775 if (e.control === self) {
3776 FloatPanel.hideAll();
3777 }
3778 });
3779 self.aria('describedby', self.describedBy || self._id + '-none');
3780 self.aria('label', settings.title);
3781 self._fullscreen = false;
3782 },
3783 recalc: function () {
3784 var self = this;
3785 var statusbar = self.statusbar;
3786 var layoutRect, width, x, needsRecalc;
3787 if (self._fullscreen) {
3788 self.layoutRect(funcs.getWindowSize());
3789 self.layoutRect().contentH = self.layoutRect().innerH;
3790 }
3791 self._super();
3792 layoutRect = self.layoutRect();
3793 if (self.settings.title && !self._fullscreen) {
3794 width = layoutRect.headerW;
3795 if (width > layoutRect.w) {
3796 x = layoutRect.x - Math.max(0, width / 2);
3797 self.layoutRect({
3798 w: width,
3799 x: x
3800 });
3801 needsRecalc = true;
3802 }
3803 }
3804 if (statusbar) {
3805 statusbar.layoutRect({ w: self.layoutRect().innerW }).recalc();
3806 width = statusbar.layoutRect().minW + layoutRect.deltaW;
3807 if (width > layoutRect.w) {
3808 x = layoutRect.x - Math.max(0, width - layoutRect.w);
3809 self.layoutRect({
3810 w: width,
3811 x: x
3812 });
3813 needsRecalc = true;
3814 }
3815 }
3816 if (needsRecalc) {
3817 self.recalc();
3818 }
3819 },
3820 initLayoutRect: function () {
3821 var self = this;
3822 var layoutRect = self._super();
3823 var deltaH = 0, headEl;
3824 if (self.settings.title && !self._fullscreen) {
3825 headEl = self.getEl('head');
3826 var size = funcs.getSize(headEl);
3827 layoutRect.headerW = size.width;
3828 layoutRect.headerH = size.height;
3829 deltaH += layoutRect.headerH;
3830 }
3831 if (self.statusbar) {
3832 deltaH += self.statusbar.layoutRect().h;
3833 }
3834 layoutRect.deltaH += deltaH;
3835 layoutRect.minH += deltaH;
3836 layoutRect.h += deltaH;
3837 var rect = funcs.getWindowSize();
3838 layoutRect.x = self.settings.x || Math.max(0, rect.w / 2 - layoutRect.w / 2);
3839 layoutRect.y = self.settings.y || Math.max(0, rect.h / 2 - layoutRect.h / 2);
3840 return layoutRect;
3841 },
3842 renderHtml: function () {
3843 var self = this, layout = self._layout, id = self._id, prefix = self.classPrefix;
3844 var settings = self.settings;
3845 var headerHtml = '', footerHtml = '', html = settings.html;
3846 self.preRender();
3847 layout.preRender(self);
3848 if (settings.title) {
3849 headerHtml = '<div id="' + id + '-head" class="' + prefix + 'window-head">' + '<div id="' + id + '-title" class="' + prefix + 'title">' + self.encode(settings.title) + '</div>' + '<div id="' + id + '-dragh" class="' + prefix + 'dragh"></div>' + '<button type="button" class="' + prefix + 'close" aria-hidden="true">' + '<i class="mce-ico mce-i-remove"></i>' + '</button>' + '</div>';
3850 }
3851 if (settings.url) {
3852 html = '<iframe src="' + settings.url + '" tabindex="-1"></iframe>';
3853 }
3854 if (typeof html === 'undefined') {
3855 html = layout.renderHtml(self);
3856 }
3857 if (self.statusbar) {
3858 footerHtml = self.statusbar.renderHtml();
3859 }
3860 return '<div id="' + id + '" class="' + self.classes + '" hidefocus="1">' + '<div class="' + self.classPrefix + 'reset" role="application">' + headerHtml + '<div id="' + id + '-body" class="' + self.bodyClasses + '">' + html + '</div>' + footerHtml + '</div>' + '</div>';
3861 },
3862 fullscreen: function (state) {
3863 var self = this;
3864 var documentElement = domGlobals.document.documentElement;
3865 var slowRendering;
3866 var prefix = self.classPrefix;
3867 var layoutRect;
3868 if (state !== self._fullscreen) {
3869 global$7(domGlobals.window).on('resize', function () {
3870 var time;
3871 if (self._fullscreen) {
3872 if (!slowRendering) {
3873 time = new Date().getTime();
3874 var rect = funcs.getWindowSize();
3875 self.moveTo(0, 0).resizeTo(rect.w, rect.h);
3876 if (new Date().getTime() - time > 50) {
3877 slowRendering = true;
3878 }
3879 } else {
3880 if (!self._timer) {
3881 self._timer = global$3.setTimeout(function () {
3882 var rect = funcs.getWindowSize();
3883 self.moveTo(0, 0).resizeTo(rect.w, rect.h);
3884 self._timer = 0;
3885 }, 50);
3886 }
3887 }
3888 }
3889 });
3890 layoutRect = self.layoutRect();
3891 self._fullscreen = state;
3892 if (!state) {
3893 self.borderBox = BoxUtils.parseBox(self.settings.border);
3894 self.getEl('head').style.display = '';
3895 layoutRect.deltaH += layoutRect.headerH;
3896 global$7([
3897 documentElement,
3898 domGlobals.document.body
3899 ]).removeClass(prefix + 'fullscreen');
3900 self.classes.remove('fullscreen');
3901 self.moveTo(self._initial.x, self._initial.y).resizeTo(self._initial.w, self._initial.h);
3902 } else {
3903 self._initial = {
3904 x: layoutRect.x,
3905 y: layoutRect.y,
3906 w: layoutRect.w,
3907 h: layoutRect.h
3908 };
3909 self.borderBox = BoxUtils.parseBox('0');
3910 self.getEl('head').style.display = 'none';
3911 layoutRect.deltaH -= layoutRect.headerH + 2;
3912 global$7([
3913 documentElement,
3914 domGlobals.document.body
3915 ]).addClass(prefix + 'fullscreen');
3916 self.classes.add('fullscreen');
3917 var rect = funcs.getWindowSize();
3918 self.moveTo(0, 0).resizeTo(rect.w, rect.h);
3919 }
3920 }
3921 return self.reflow();
3922 },
3923 postRender: function () {
3924 var self = this;
3925 var startPos;
3926 setTimeout(function () {
3927 self.classes.add('in');
3928 self.fire('open');
3929 }, 0);
3930 self._super();
3931 if (self.statusbar) {
3932 self.statusbar.postRender();
3933 }
3934 self.focus();
3935 this.dragHelper = new DragHelper(self._id + '-dragh', {
3936 start: function () {
3937 startPos = {
3938 x: self.layoutRect().x,
3939 y: self.layoutRect().y
3940 };
3941 },
3942 drag: function (e) {
3943 self.moveTo(startPos.x + e.deltaX, startPos.y + e.deltaY);
3944 }
3945 });
3946 self.on('submit', function (e) {
3947 if (!e.isDefaultPrevented()) {
3948 self.close();
3949 }
3950 });
3951 windows.push(self);
3952 toggleFullScreenState(true);
3953 },
3954 submit: function () {
3955 return this.fire('submit', { data: this.toJSON() });
3956 },
3957 remove: function () {
3958 var self = this;
3959 var i;
3960 self.dragHelper.destroy();
3961 self._super();
3962 if (self.statusbar) {
3963 this.statusbar.remove();
3964 }
3965 toggleBodyFullScreenClasses(self.classPrefix, false);
3966 i = windows.length;
3967 while (i--) {
3968 if (windows[i] === self) {
3969 windows.splice(i, 1);
3970 }
3971 }
3972 toggleFullScreenState(windows.length > 0);
3973 },
3974 getContentWindow: function () {
3975 var ifr = this.getEl().getElementsByTagName('iframe')[0];
3976 return ifr ? ifr.contentWindow : null;
3977 }
3978 });
3979 handleWindowResize();
3980
3981 var MessageBox = Window.extend({
3982 init: function (settings) {
3983 settings = {
3984 border: 1,
3985 padding: 20,
3986 layout: 'flex',
3987 pack: 'center',
3988 align: 'center',
3989 containerCls: 'panel',
3990 autoScroll: true,
3991 buttons: {
3992 type: 'button',
3993 text: 'Ok',
3994 action: 'ok'
3995 },
3996 items: {
3997 type: 'label',
3998 multiline: true,
3999 maxWidth: 500,
4000 maxHeight: 200
4001 }
4002 };
4003 this._super(settings);
4004 },
4005 Statics: {
4006 OK: 1,
4007 OK_CANCEL: 2,
4008 YES_NO: 3,
4009 YES_NO_CANCEL: 4,
4010 msgBox: function (settings) {
4011 var buttons;
4012 var callback = settings.callback || function () {
4013 };
4014 function createButton(text, status, primary) {
4015 return {
4016 type: 'button',
4017 text: text,
4018 subtype: primary ? 'primary' : '',
4019 onClick: function (e) {
4020 e.control.parents()[1].close();
4021 callback(status);
4022 }
4023 };
4024 }
4025 switch (settings.buttons) {
4026 case MessageBox.OK_CANCEL:
4027 buttons = [
4028 createButton('Ok', true, true),
4029 createButton('Cancel', false)
4030 ];
4031 break;
4032 case MessageBox.YES_NO:
4033 case MessageBox.YES_NO_CANCEL:
4034 buttons = [
4035 createButton('Yes', 1, true),
4036 createButton('No', 0)
4037 ];
4038 if (settings.buttons === MessageBox.YES_NO_CANCEL) {
4039 buttons.push(createButton('Cancel', -1));
4040 }
4041 break;
4042 default:
4043 buttons = [createButton('Ok', true, true)];
4044 break;
4045 }
4046 return new Window({
4047 padding: 20,
4048 x: settings.x,
4049 y: settings.y,
4050 minWidth: 300,
4051 minHeight: 100,
4052 layout: 'flex',
4053 pack: 'center',
4054 align: 'center',
4055 buttons: buttons,
4056 title: settings.title,
4057 role: 'alertdialog',
4058 items: {
4059 type: 'label',
4060 multiline: true,
4061 maxWidth: 500,
4062 maxHeight: 200,
4063 text: settings.text
4064 },
4065 onPostRender: function () {
4066 this.aria('describedby', this.items()[0]._id);
4067 },
4068 onClose: settings.onClose,
4069 onCancel: function () {
4070 callback(false);
4071 }
4072 }).renderTo(domGlobals.document.body).reflow();
4073 },
4074 alert: function (settings, callback) {
4075 if (typeof settings === 'string') {
4076 settings = { text: settings };
4077 }
4078 settings.callback = callback;
4079 return MessageBox.msgBox(settings);
4080 },
4081 confirm: function (settings, callback) {
4082 if (typeof settings === 'string') {
4083 settings = { text: settings };
4084 }
4085 settings.callback = callback;
4086 settings.buttons = MessageBox.OK_CANCEL;
4087 return MessageBox.msgBox(settings);
4088 }
4089 }
4090 });
4091
4092 function WindowManagerImpl (editor) {
4093 var open = function (args, params, closeCallback) {
4094 var win;
4095 args.title = args.title || ' ';
4096 args.url = args.url || args.file;
4097 if (args.url) {
4098 args.width = parseInt(args.width || 320, 10);
4099 args.height = parseInt(args.height || 240, 10);
4100 }
4101 if (args.body) {
4102 args.items = {
4103 defaults: args.defaults,
4104 type: args.bodyType || 'form',
4105 items: args.body,
4106 data: args.data,
4107 callbacks: args.commands
4108 };
4109 }
4110 if (!args.url && !args.buttons) {
4111 args.buttons = [
4112 {
4113 text: 'Ok',
4114 subtype: 'primary',
4115 onclick: function () {
4116 win.find('form')[0].submit();
4117 }
4118 },
4119 {
4120 text: 'Cancel',
4121 onclick: function () {
4122 win.close();
4123 }
4124 }
4125 ];
4126 }
4127 win = new Window(args);
4128 win.on('close', function () {
4129 closeCallback(win);
4130 });
4131 if (args.data) {
4132 win.on('postRender', function () {
4133 this.find('*').each(function (ctrl) {
4134 var name = ctrl.name();
4135 if (name in args.data) {
4136 ctrl.value(args.data[name]);
4137 }
4138 });
4139 });
4140 }
4141 win.features = args || {};
4142 win.params = params || {};
4143 win = win.renderTo(domGlobals.document.body).reflow();
4144 return win;
4145 };
4146 var alert = function (message, choiceCallback, closeCallback) {
4147 var win;
4148 win = MessageBox.alert(message, function () {
4149 choiceCallback();
4150 });
4151 win.on('close', function () {
4152 closeCallback(win);
4153 });
4154 return win;
4155 };
4156 var confirm = function (message, choiceCallback, closeCallback) {
4157 var win;
4158 win = MessageBox.confirm(message, function (state) {
4159 choiceCallback(state);
4160 });
4161 win.on('close', function () {
4162 closeCallback(win);
4163 });
4164 return win;
4165 };
4166 var close = function (window) {
4167 window.close();
4168 };
4169 var getParams = function (window) {
4170 return window.params;
4171 };
4172 var setParams = function (window, params) {
4173 window.params = params;
4174 };
4175 return {
4176 open: open,
4177 alert: alert,
4178 confirm: confirm,
4179 close: close,
4180 getParams: getParams,
4181 setParams: setParams
4182 };
4183 }
4184
4185 var get = function (editor, panel) {
4186 var renderUI = function () {
4187 return Render.renderUI(editor, panel);
4188 };
4189 return {
4190 renderUI: renderUI,
4191 getNotificationManagerImpl: function () {
4192 return NotificationManagerImpl(editor);
4193 },
4194 getWindowManagerImpl: function () {
4195 return WindowManagerImpl();
4196 }
4197 };
4198 };
4199 var ThemeApi = { get: get };
4200
4201 var Global = typeof domGlobals.window !== 'undefined' ? domGlobals.window : Function('return this;')();
4202
4203 var path = function (parts, scope) {
4204 var o = scope !== undefined && scope !== null ? scope : Global;
4205 for (var i = 0; i < parts.length && o !== undefined && o !== null; ++i) {
4206 o = o[parts[i]];
4207 }
4208 return o;
4209 };
4210 var resolve = function (p, scope) {
4211 var parts = p.split('.');
4212 return path(parts, scope);
4213 };
4214
4215 var unsafe = function (name, scope) {
4216 return resolve(name, scope);
4217 };
4218 var getOrDie = function (name, scope) {
4219 var actual = unsafe(name, scope);
4220 if (actual === undefined || actual === null) {
4221 throw new Error(name + ' not available on this browser');
4222 }
4223 return actual;
4224 };
4225 var Global$1 = { getOrDie: getOrDie };
4226
4227 function FileReader () {
4228 var f = Global$1.getOrDie('FileReader');
4229 return new f();
4230 }
4231
4232 var global$c = tinymce.util.Tools.resolve('tinymce.util.Promise');
4233
4234 var blobToBase64 = function (blob) {
4235 return new global$c(function (resolve) {
4236 var reader = FileReader();
4237 reader.onloadend = function () {
4238 resolve(reader.result.split(',')[1]);
4239 };
4240 reader.readAsDataURL(blob);
4241 });
4242 };
4243 var Conversions = { blobToBase64: blobToBase64 };
4244
4245 var pickFile = function () {
4246 return new global$c(function (resolve) {
4247 var fileInput;
4248 fileInput = domGlobals.document.createElement('input');
4249 fileInput.type = 'file';
4250 fileInput.style.position = 'fixed';
4251 fileInput.style.left = 0;
4252 fileInput.style.top = 0;
4253 fileInput.style.opacity = 0.001;
4254 domGlobals.document.body.appendChild(fileInput);
4255 fileInput.onchange = function (e) {
4256 resolve(Array.prototype.slice.call(e.target.files));
4257 };
4258 fileInput.click();
4259 fileInput.parentNode.removeChild(fileInput);
4260 });
4261 };
4262 var Picker = { pickFile: pickFile };
4263
4264 var count$1 = 0;
4265 var seed = function () {
4266 var rnd = function () {
4267 return Math.round(Math.random() * 4294967295).toString(36);
4268 };
4269 return 's' + Date.now().toString(36) + rnd() + rnd() + rnd();
4270 };
4271 var uuid = function (prefix) {
4272 return prefix + count$1++ + seed();
4273 };
4274 var Uuid = { uuid: uuid };
4275
4276 var create$1 = function (dom, rng) {
4277 var bookmark = {};
4278 function setupEndPoint(start) {
4279 var offsetNode, container, offset;
4280 container = rng[start ? 'startContainer' : 'endContainer'];
4281 offset = rng[start ? 'startOffset' : 'endOffset'];
4282 if (container.nodeType === 1) {
4283 offsetNode = dom.create('span', { 'data-mce-type': 'bookmark' });
4284 if (container.hasChildNodes()) {
4285 offset = Math.min(offset, container.childNodes.length - 1);
4286 if (start) {
4287 container.insertBefore(offsetNode, container.childNodes[offset]);
4288 } else {
4289 dom.insertAfter(offsetNode, container.childNodes[offset]);
4290 }
4291 } else {
4292 container.appendChild(offsetNode);
4293 }
4294 container = offsetNode;
4295 offset = 0;
4296 }
4297 bookmark[start ? 'startContainer' : 'endContainer'] = container;
4298 bookmark[start ? 'startOffset' : 'endOffset'] = offset;
4299 }
4300 setupEndPoint(true);
4301 if (!rng.collapsed) {
4302 setupEndPoint();
4303 }
4304 return bookmark;
4305 };
4306 var resolve$1 = function (dom, bookmark) {
4307 function restoreEndPoint(start) {
4308 var container, offset, node;
4309 function nodeIndex(container) {
4310 var node = container.parentNode.firstChild, idx = 0;
4311 while (node) {
4312 if (node === container) {
4313 return idx;
4314 }
4315 if (node.nodeType !== 1 || node.getAttribute('data-mce-type') !== 'bookmark') {
4316 idx++;
4317 }
4318 node = node.nextSibling;
4319 }
4320 return -1;
4321 }
4322 container = node = bookmark[start ? 'startContainer' : 'endContainer'];
4323 offset = bookmark[start ? 'startOffset' : 'endOffset'];
4324 if (!container) {
4325 return;
4326 }
4327 if (container.nodeType === 1) {
4328 offset = nodeIndex(container);
4329 container = container.parentNode;
4330 dom.remove(node);
4331 }
4332 bookmark[start ? 'startContainer' : 'endContainer'] = container;
4333 bookmark[start ? 'startOffset' : 'endOffset'] = offset;
4334 }
4335 restoreEndPoint(true);
4336 restoreEndPoint();
4337 var rng = dom.createRng();
4338 rng.setStart(bookmark.startContainer, bookmark.startOffset);
4339 if (bookmark.endContainer) {
4340 rng.setEnd(bookmark.endContainer, bookmark.endOffset);
4341 }
4342 return rng;
4343 };
4344 var Bookmark = {
4345 create: create$1,
4346 resolve: resolve$1
4347 };
4348
4349 var global$d = tinymce.util.Tools.resolve('tinymce.dom.TreeWalker');
4350
4351 var global$e = tinymce.util.Tools.resolve('tinymce.dom.RangeUtils');
4352
4353 var getSelectedElements = function (rootElm, startNode, endNode) {
4354 var walker, node;
4355 var elms = [];
4356 walker = new global$d(startNode, rootElm);
4357 for (node = startNode; node; node = walker.next()) {
4358 if (node.nodeType === 1) {
4359 elms.push(node);
4360 }
4361 if (node === endNode) {
4362 break;
4363 }
4364 }
4365 return elms;
4366 };
4367 var unwrapElements = function (editor, elms) {
4368 var bookmark, dom, selection;
4369 dom = editor.dom;
4370 selection = editor.selection;
4371 bookmark = Bookmark.create(dom, selection.getRng());
4372 global$4.each(elms, function (elm) {
4373 editor.dom.remove(elm, true);
4374 });
4375 selection.setRng(Bookmark.resolve(dom, bookmark));
4376 };
4377 var isLink = function (elm) {
4378 return elm.nodeName === 'A' && elm.hasAttribute('href');
4379 };
4380 var getParentAnchorOrSelf = function (dom, elm) {
4381 var anchorElm = dom.getParent(elm, isLink);
4382 return anchorElm ? anchorElm : elm;
4383 };
4384 var getSelectedAnchors = function (editor) {
4385 var startElm, endElm, rootElm, anchorElms, selection, dom, rng;
4386 selection = editor.selection;
4387 dom = editor.dom;
4388 rng = selection.getRng();
4389 startElm = getParentAnchorOrSelf(dom, global$e.getNode(rng.startContainer, rng.startOffset));
4390 endElm = global$e.getNode(rng.endContainer, rng.endOffset);
4391 rootElm = editor.getBody();
4392 anchorElms = global$4.grep(getSelectedElements(rootElm, startElm, endElm), isLink);
4393 return anchorElms;
4394 };
4395 var unlinkSelection = function (editor) {
4396 unwrapElements(editor, getSelectedAnchors(editor));
4397 };
4398 var Unlink = { unlinkSelection: unlinkSelection };
4399
4400 var createTableHtml = function (cols, rows) {
4401 var x, y, html;
4402 html = '<table data-mce-id="mce" style="width: 100%">';
4403 html += '<tbody>';
4404 for (y = 0; y < rows; y++) {
4405 html += '<tr>';
4406 for (x = 0; x < cols; x++) {
4407 html += '<td><br></td>';
4408 }
4409 html += '</tr>';
4410 }
4411 html += '</tbody>';
4412 html += '</table>';
4413 return html;
4414 };
4415 var getInsertedElement = function (editor) {
4416 var elms = editor.dom.select('*[data-mce-id]');
4417 return elms[0];
4418 };
4419 var insertTableHtml = function (editor, cols, rows) {
4420 editor.undoManager.transact(function () {
4421 var tableElm, cellElm;
4422 editor.insertContent(createTableHtml(cols, rows));
4423 tableElm = getInsertedElement(editor);
4424 tableElm.removeAttribute('data-mce-id');
4425 cellElm = editor.dom.select('td,th', tableElm);
4426 editor.selection.setCursorLocation(cellElm[0], 0);
4427 });
4428 };
4429 var insertTable = function (editor, cols, rows) {
4430 editor.plugins.table ? editor.plugins.table.insertTable(cols, rows) : insertTableHtml(editor, cols, rows);
4431 };
4432 var formatBlock = function (editor, formatName) {
4433 editor.execCommand('FormatBlock', false, formatName);
4434 };
4435 var insertBlob = function (editor, base64, blob) {
4436 var blobCache, blobInfo;
4437 blobCache = editor.editorUpload.blobCache;
4438 blobInfo = blobCache.create(Uuid.uuid('mceu'), blob, base64);
4439 blobCache.add(blobInfo);
4440 editor.insertContent(editor.dom.createHTML('img', { src: blobInfo.blobUri() }));
4441 };
4442 var collapseSelectionToEnd = function (editor) {
4443 editor.selection.collapse(false);
4444 };
4445 var unlink = function (editor) {
4446 editor.focus();
4447 Unlink.unlinkSelection(editor);
4448 collapseSelectionToEnd(editor);
4449 };
4450 var changeHref = function (editor, elm, url) {
4451 editor.focus();
4452 editor.dom.setAttrib(elm, 'href', url);
4453 collapseSelectionToEnd(editor);
4454 };
4455 var insertLink = function (editor, url) {
4456 editor.execCommand('mceInsertLink', false, { href: url });
4457 collapseSelectionToEnd(editor);
4458 };
4459 var updateOrInsertLink = function (editor, url) {
4460 var elm = editor.dom.getParent(editor.selection.getStart(), 'a[href]');
4461 elm ? changeHref(editor, elm, url) : insertLink(editor, url);
4462 };
4463 var createLink = function (editor, url) {
4464 url.trim().length === 0 ? unlink(editor) : updateOrInsertLink(editor, url);
4465 };
4466 var Actions = {
4467 insertTable: insertTable,
4468 formatBlock: formatBlock,
4469 insertBlob: insertBlob,
4470 createLink: createLink,
4471 unlink: unlink
4472 };
4473
4474 var addHeaderButtons = function (editor) {
4475 var formatBlock = function (name) {
4476 return function () {
4477 Actions.formatBlock(editor, name);
4478 };
4479 };
4480 for (var i = 1; i < 6; i++) {
4481 var name = 'h' + i;
4482 editor.addButton(name, {
4483 text: name.toUpperCase(),
4484 tooltip: 'Heading ' + i,
4485 stateSelector: name,
4486 onclick: formatBlock(name),
4487 onPostRender: function () {
4488 var span = this.getEl().firstChild.firstChild;
4489 span.style.fontWeight = 'bold';
4490 }
4491 });
4492 }
4493 };
4494 var addToEditor = function (editor, panel) {
4495 editor.addButton('quicklink', {
4496 icon: 'link',
4497 tooltip: 'Insert/Edit link',
4498 stateSelector: 'a[href]',
4499 onclick: function () {
4500 panel.showForm(editor, 'quicklink');
4501 }
4502 });
4503 editor.addButton('quickimage', {
4504 icon: 'image',
4505 tooltip: 'Insert image',
4506 onclick: function () {
4507 Picker.pickFile().then(function (files) {
4508 var blob = files[0];
4509 Conversions.blobToBase64(blob).then(function (base64) {
4510 Actions.insertBlob(editor, base64, blob);
4511 });
4512 });
4513 }
4514 });
4515 editor.addButton('quicktable', {
4516 icon: 'table',
4517 tooltip: 'Insert table',
4518 onclick: function () {
4519 panel.hide();
4520 Actions.insertTable(editor, 2, 2);
4521 }
4522 });
4523 addHeaderButtons(editor);
4524 };
4525 var Buttons = { addToEditor: addToEditor };
4526
4527 var getUiContainerDelta$1 = function () {
4528 var uiContainer = global$1.container;
4529 if (uiContainer && global$2.DOM.getStyle(uiContainer, 'position', true) !== 'static') {
4530 var containerPos = global$2.DOM.getPos(uiContainer);
4531 var dx = containerPos.x - uiContainer.scrollLeft;
4532 var dy = containerPos.y - uiContainer.scrollTop;
4533 return Option.some({
4534 x: dx,
4535 y: dy
4536 });
4537 } else {
4538 return Option.none();
4539 }
4540 };
4541 var UiContainer$1 = { getUiContainerDelta: getUiContainerDelta$1 };
4542
4543 var isDomainLike = function (href) {
4544 return /^www\.|\.(com|org|edu|gov|uk|net|ca|de|jp|fr|au|us|ru|ch|it|nl|se|no|es|mil)$/i.test(href.trim());
4545 };
4546 var isAbsolute = function (href) {
4547 return /^https?:\/\//.test(href.trim());
4548 };
4549 var UrlType = {
4550 isDomainLike: isDomainLike,
4551 isAbsolute: isAbsolute
4552 };
4553
4554 var focusFirstTextBox = function (form) {
4555 form.find('textbox').eq(0).each(function (ctrl) {
4556 ctrl.focus();
4557 });
4558 };
4559 var createForm = function (name, spec) {
4560 var form = global$b.create(global$4.extend({
4561 type: 'form',
4562 layout: 'flex',
4563 direction: 'row',
4564 padding: 5,
4565 name: name,
4566 spacing: 3
4567 }, spec));
4568 form.on('show', function () {
4569 focusFirstTextBox(form);
4570 });
4571 return form;
4572 };
4573 var toggleVisibility = function (ctrl, state) {
4574 return state ? ctrl.show() : ctrl.hide();
4575 };
4576 var askAboutPrefix = function (editor, href) {
4577 return new global$c(function (resolve) {
4578 editor.windowManager.confirm('The URL you entered seems to be an external link. Do you want to add the required http:// prefix?', function (result) {
4579 var output = result === true ? 'http://' + href : href;
4580 resolve(output);
4581 });
4582 });
4583 };
4584 var convertLinkToAbsolute = function (editor, href) {
4585 return !UrlType.isAbsolute(href) && UrlType.isDomainLike(href) ? askAboutPrefix(editor, href) : global$c.resolve(href);
4586 };
4587 var createQuickLinkForm = function (editor, hide) {
4588 var attachState = {};
4589 var unlink = function () {
4590 editor.focus();
4591 Actions.unlink(editor);
4592 hide();
4593 };
4594 var onChangeHandler = function (e) {
4595 var meta = e.meta;
4596 if (meta && meta.attach) {
4597 attachState = {
4598 href: this.value(),
4599 attach: meta.attach
4600 };
4601 }
4602 };
4603 var onShowHandler = function (e) {
4604 if (e.control === this) {
4605 var elm = void 0, linkurl = '';
4606 elm = editor.dom.getParent(editor.selection.getStart(), 'a[href]');
4607 if (elm) {
4608 linkurl = editor.dom.getAttrib(elm, 'href');
4609 }
4610 this.fromJSON({ linkurl: linkurl });
4611 toggleVisibility(this.find('#unlink'), elm);
4612 this.find('#linkurl')[0].focus();
4613 }
4614 };
4615 return createForm('quicklink', {
4616 items: [
4617 {
4618 type: 'button',
4619 name: 'unlink',
4620 icon: 'unlink',
4621 onclick: unlink,
4622 tooltip: 'Remove link'
4623 },
4624 {
4625 type: 'filepicker',
4626 name: 'linkurl',
4627 placeholder: 'Paste or type a link',
4628 filetype: 'file',
4629 onchange: onChangeHandler
4630 },
4631 {
4632 type: 'button',
4633 icon: 'checkmark',
4634 subtype: 'primary',
4635 tooltip: 'Ok',
4636 onclick: 'submit'
4637 }
4638 ],
4639 onshow: onShowHandler,
4640 onsubmit: function (e) {
4641 convertLinkToAbsolute(editor, e.data.linkurl).then(function (url) {
4642 editor.undoManager.transact(function () {
4643 if (url === attachState.href) {
4644 attachState.attach();
4645 attachState = {};
4646 }
4647 Actions.createLink(editor, url);
4648 });
4649 hide();
4650 });
4651 }
4652 });
4653 };
4654 var Forms = { createQuickLinkForm: createQuickLinkForm };
4655
4656 var getSelectorStateResult = function (itemName, item) {
4657 var result = function (selector, handler) {
4658 return {
4659 selector: selector,
4660 handler: handler
4661 };
4662 };
4663 var activeHandler = function (state) {
4664 item.active(state);
4665 };
4666 var disabledHandler = function (state) {
4667 item.disabled(state);
4668 };
4669 if (item.settings.stateSelector) {
4670 return result(item.settings.stateSelector, activeHandler);
4671 }
4672 if (item.settings.disabledStateSelector) {
4673 return result(item.settings.disabledStateSelector, disabledHandler);
4674 }
4675 return null;
4676 };
4677 var bindSelectorChanged = function (editor, itemName, item) {
4678 return function () {
4679 var result = getSelectorStateResult(itemName, item);
4680 if (result !== null) {
4681 editor.selection.selectorChanged(result.selector, result.handler);
4682 }
4683 };
4684 };
4685 var itemsToArray$1 = function (items) {
4686 if (Type.isArray(items)) {
4687 return items;
4688 } else if (Type.isString(items)) {
4689 return items.split(/[ ,]/);
4690 }
4691 return [];
4692 };
4693 var create$2 = function (editor, name, items) {
4694 var toolbarItems = [];
4695 var buttonGroup;
4696 if (!items) {
4697 return;
4698 }
4699 global$4.each(itemsToArray$1(items), function (item) {
4700 if (item === '|') {
4701 buttonGroup = null;
4702 } else {
4703 if (editor.buttons[item]) {
4704 if (!buttonGroup) {
4705 buttonGroup = {
4706 type: 'buttongroup',
4707 items: []
4708 };
4709 toolbarItems.push(buttonGroup);
4710 }
4711 var button = editor.buttons[item];
4712 if (Type.isFunction(button)) {
4713 button = button();
4714 }
4715 button.type = button.type || 'button';
4716 button = global$b.create(button);
4717 button.on('postRender', bindSelectorChanged(editor, item, button));
4718 buttonGroup.items.push(button);
4719 }
4720 }
4721 });
4722 return global$b.create({
4723 type: 'toolbar',
4724 layout: 'flow',
4725 name: name,
4726 items: toolbarItems
4727 });
4728 };
4729 var Toolbar = { create: create$2 };
4730
4731 var create$3 = function () {
4732 var panel, currentRect;
4733 var createToolbars = function (editor, toolbars) {
4734 return global$4.map(toolbars, function (toolbar) {
4735 return Toolbar.create(editor, toolbar.id, toolbar.items);
4736 });
4737 };
4738 var hasToolbarItems = function (toolbar) {
4739 return toolbar.items().length > 0;
4740 };
4741 var create = function (editor, toolbars) {
4742 var items = createToolbars(editor, toolbars).concat([
4743 Toolbar.create(editor, 'text', Settings.getTextSelectionToolbarItems(editor)),
4744 Toolbar.create(editor, 'insert', Settings.getInsertToolbarItems(editor)),
4745 Forms.createQuickLinkForm(editor, hide)
4746 ]);
4747 return global$b.create({
4748 type: 'floatpanel',
4749 role: 'dialog',
4750 classes: 'tinymce tinymce-inline arrow',
4751 ariaLabel: 'Inline toolbar',
4752 layout: 'flex',
4753 direction: 'column',
4754 align: 'stretch',
4755 autohide: false,
4756 autofix: true,
4757 fixed: true,
4758 border: 1,
4759 items: global$4.grep(items, hasToolbarItems),
4760 oncancel: function () {
4761 editor.focus();
4762 }
4763 });
4764 };
4765 var showPanel = function (panel) {
4766 if (panel) {
4767 panel.show();
4768 }
4769 };
4770 var movePanelTo = function (panel, pos) {
4771 panel.moveTo(pos.x, pos.y);
4772 };
4773 var togglePositionClass = function (panel, relPos) {
4774 relPos = relPos ? relPos.substr(0, 2) : '';
4775 global$4.each({
4776 t: 'down',
4777 b: 'up',
4778 c: 'center'
4779 }, function (cls, pos) {
4780 panel.classes.toggle('arrow-' + cls, pos === relPos.substr(0, 1));
4781 });
4782 if (relPos === 'cr') {
4783 panel.classes.toggle('arrow-left', true);
4784 panel.classes.toggle('arrow-right', false);
4785 } else if (relPos === 'cl') {
4786 panel.classes.toggle('arrow-left', false);
4787 panel.classes.toggle('arrow-right', true);
4788 } else {
4789 global$4.each({
4790 l: 'left',
4791 r: 'right'
4792 }, function (cls, pos) {
4793 panel.classes.toggle('arrow-' + cls, pos === relPos.substr(1, 1));
4794 });
4795 }
4796 };
4797 var showToolbar = function (panel, id) {
4798 var toolbars = panel.items().filter('#' + id);
4799 if (toolbars.length > 0) {
4800 toolbars[0].show();
4801 panel.reflow();
4802 return true;
4803 }
4804 return false;
4805 };
4806 var repositionPanelAt = function (panel, id, editor, targetRect) {
4807 var contentAreaRect, panelRect, result, userConstainHandler;
4808 userConstainHandler = Settings.getPositionHandler(editor);
4809 contentAreaRect = Measure.getContentAreaRect(editor);
4810 panelRect = global$2.DOM.getRect(panel.getEl());
4811 if (id === 'insert') {
4812 result = Layout.calcInsert(targetRect, contentAreaRect, panelRect);
4813 } else {
4814 result = Layout.calc(targetRect, contentAreaRect, panelRect);
4815 }
4816 if (result) {
4817 var delta = UiContainer$1.getUiContainerDelta().getOr({
4818 x: 0,
4819 y: 0
4820 });
4821 var transposedPanelRect = {
4822 x: result.rect.x - delta.x,
4823 y: result.rect.y - delta.y,
4824 w: result.rect.w,
4825 h: result.rect.h
4826 };
4827 currentRect = targetRect;
4828 movePanelTo(panel, Layout.userConstrain(userConstainHandler, targetRect, contentAreaRect, transposedPanelRect));
4829 togglePositionClass(panel, result.position);
4830 return true;
4831 } else {
4832 return false;
4833 }
4834 };
4835 var showPanelAt = function (panel, id, editor, targetRect) {
4836 showPanel(panel);
4837 panel.items().hide();
4838 if (!showToolbar(panel, id)) {
4839 hide();
4840 return;
4841 }
4842 if (repositionPanelAt(panel, id, editor, targetRect) === false) {
4843 hide();
4844 }
4845 };
4846 var hasFormVisible = function () {
4847 return panel.items().filter('form:visible').length > 0;
4848 };
4849 var showForm = function (editor, id) {
4850 if (panel) {
4851 panel.items().hide();
4852 if (!showToolbar(panel, id)) {
4853 hide();
4854 return;
4855 }
4856 var contentAreaRect = void 0, panelRect = void 0, result = void 0, userConstainHandler = void 0;
4857 showPanel(panel);
4858 panel.items().hide();
4859 showToolbar(panel, id);
4860 userConstainHandler = Settings.getPositionHandler(editor);
4861 contentAreaRect = Measure.getContentAreaRect(editor);
4862 panelRect = global$2.DOM.getRect(panel.getEl());
4863 result = Layout.calc(currentRect, contentAreaRect, panelRect);
4864 if (result) {
4865 panelRect = result.rect;
4866 movePanelTo(panel, Layout.userConstrain(userConstainHandler, currentRect, contentAreaRect, panelRect));
4867 togglePositionClass(panel, result.position);
4868 }
4869 }
4870 };
4871 var show = function (editor, id, targetRect, toolbars) {
4872 if (!panel) {
4873 Events.fireBeforeRenderUI(editor);
4874 panel = create(editor, toolbars);
4875 panel.renderTo().reflow().moveTo(targetRect.x, targetRect.y);
4876 editor.nodeChanged();
4877 }
4878 showPanelAt(panel, id, editor, targetRect);
4879 };
4880 var reposition = function (editor, id, targetRect) {
4881 if (panel) {
4882 repositionPanelAt(panel, id, editor, targetRect);
4883 }
4884 };
4885 var hide = function () {
4886 if (panel) {
4887 panel.hide();
4888 }
4889 };
4890 var focus = function () {
4891 if (panel) {
4892 panel.find('toolbar:visible').eq(0).each(function (item) {
4893 item.focus(true);
4894 });
4895 }
4896 };
4897 var remove = function () {
4898 if (panel) {
4899 panel.remove();
4900 panel = null;
4901 }
4902 };
4903 var inForm = function () {
4904 return panel && panel.visible() && hasFormVisible();
4905 };
4906 return {
4907 show: show,
4908 showForm: showForm,
4909 reposition: reposition,
4910 inForm: inForm,
4911 hide: hide,
4912 focus: focus,
4913 remove: remove
4914 };
4915 };
4916
4917 var Layout$1 = global$8.extend({
4918 Defaults: {
4919 firstControlClass: 'first',
4920 lastControlClass: 'last'
4921 },
4922 init: function (settings) {
4923 this.settings = global$4.extend({}, this.Defaults, settings);
4924 },
4925 preRender: function (container) {
4926 container.bodyClasses.add(this.settings.containerClass);
4927 },
4928 applyClasses: function (items) {
4929 var self = this;
4930 var settings = self.settings;
4931 var firstClass, lastClass, firstItem, lastItem;
4932 firstClass = settings.firstControlClass;
4933 lastClass = settings.lastControlClass;
4934 items.each(function (item) {
4935 item.classes.remove(firstClass).remove(lastClass).add(settings.controlClass);
4936 if (item.visible()) {
4937 if (!firstItem) {
4938 firstItem = item;
4939 }
4940 lastItem = item;
4941 }
4942 });
4943 if (firstItem) {
4944 firstItem.classes.add(firstClass);
4945 }
4946 if (lastItem) {
4947 lastItem.classes.add(lastClass);
4948 }
4949 },
4950 renderHtml: function (container) {
4951 var self = this;
4952 var html = '';
4953 self.applyClasses(container.items());
4954 container.items().each(function (item) {
4955 html += item.renderHtml();
4956 });
4957 return html;
4958 },
4959 recalc: function () {
4960 },
4961 postRender: function () {
4962 },
4963 isNative: function () {
4964 return false;
4965 }
4966 });
4967
4968 var AbsoluteLayout = Layout$1.extend({
4969 Defaults: {
4970 containerClass: 'abs-layout',
4971 controlClass: 'abs-layout-item'
4972 },
4973 recalc: function (container) {
4974 container.items().filter(':visible').each(function (ctrl) {
4975 var settings = ctrl.settings;
4976 ctrl.layoutRect({
4977 x: settings.x,
4978 y: settings.y,
4979 w: settings.w,
4980 h: settings.h
4981 });
4982 if (ctrl.recalc) {
4983 ctrl.recalc();
4984 }
4985 });
4986 },
4987 renderHtml: function (container) {
4988 return '<div id="' + container._id + '-absend" class="' + container.classPrefix + 'abs-end"></div>' + this._super(container);
4989 }
4990 });
4991
4992 var Button = Widget.extend({
4993 Defaults: {
4994 classes: 'widget btn',
4995 role: 'button'
4996 },
4997 init: function (settings) {
4998 var self = this;
4999 var size;
5000 self._super(settings);
5001 settings = self.settings;
5002 size = self.settings.size;
5003 self.on('click mousedown', function (e) {
5004 e.preventDefault();
5005 });
5006 self.on('touchstart', function (e) {
5007 self.fire('click', e);
5008 e.preventDefault();
5009 });
5010 if (settings.subtype) {
5011 self.classes.add(settings.subtype);
5012 }
5013 if (size) {
5014 self.classes.add('btn-' + size);
5015 }
5016 if (settings.icon) {
5017 self.icon(settings.icon);
5018 }
5019 },
5020 icon: function (icon) {
5021 if (!arguments.length) {
5022 return this.state.get('icon');
5023 }
5024 this.state.set('icon', icon);
5025 return this;
5026 },
5027 repaint: function () {
5028 var btnElm = this.getEl().firstChild;
5029 var btnStyle;
5030 if (btnElm) {
5031 btnStyle = btnElm.style;
5032 btnStyle.width = btnStyle.height = '100%';
5033 }
5034 this._super();
5035 },
5036 renderHtml: function () {
5037 var self = this, id = self._id, prefix = self.classPrefix;
5038 var icon = self.state.get('icon'), image;
5039 var text = self.state.get('text');
5040 var textHtml = '';
5041 var ariaPressed;
5042 var settings = self.settings;
5043 image = settings.image;
5044 if (image) {
5045 icon = 'none';
5046 if (typeof image !== 'string') {
5047 image = domGlobals.window.getSelection ? image[0] : image[1];
5048 }
5049 image = ' style="background-image: url(\'' + image + '\')"';
5050 } else {
5051 image = '';
5052 }
5053 if (text) {
5054 self.classes.add('btn-has-text');
5055 textHtml = '<span class="' + prefix + 'txt">' + self.encode(text) + '</span>';
5056 }
5057 icon = icon ? prefix + 'ico ' + prefix + 'i-' + icon : '';
5058 ariaPressed = typeof settings.active === 'boolean' ? ' aria-pressed="' + settings.active + '"' : '';
5059 return '<div id="' + id + '" class="' + self.classes + '" tabindex="-1"' + ariaPressed + '>' + '<button id="' + id + '-button" role="presentation" type="button" tabindex="-1">' + (icon ? '<i class="' + icon + '"' + image + '></i>' : '') + textHtml + '</button>' + '</div>';
5060 },
5061 bindStates: function () {
5062 var self = this, $ = self.$, textCls = self.classPrefix + 'txt';
5063 function setButtonText(text) {
5064 var $span = $('span.' + textCls, self.getEl());
5065 if (text) {
5066 if (!$span[0]) {
5067 $('button:first', self.getEl()).append('<span class="' + textCls + '"></span>');
5068 $span = $('span.' + textCls, self.getEl());
5069 }
5070 $span.html(self.encode(text));
5071 } else {
5072 $span.remove();
5073 }
5074 self.classes.toggle('btn-has-text', !!text);
5075 }
5076 self.state.on('change:text', function (e) {
5077 setButtonText(e.value);
5078 });
5079 self.state.on('change:icon', function (e) {
5080 var icon = e.value;
5081 var prefix = self.classPrefix;
5082 self.settings.icon = icon;
5083 icon = icon ? prefix + 'ico ' + prefix + 'i-' + self.settings.icon : '';
5084 var btnElm = self.getEl().firstChild;
5085 var iconElm = btnElm.getElementsByTagName('i')[0];
5086 if (icon) {
5087 if (!iconElm || iconElm !== btnElm.firstChild) {
5088 iconElm = domGlobals.document.createElement('i');
5089 btnElm.insertBefore(iconElm, btnElm.firstChild);
5090 }
5091 iconElm.className = icon;
5092 } else if (iconElm) {
5093 btnElm.removeChild(iconElm);
5094 }
5095 setButtonText(self.state.get('text'));
5096 });
5097 return self._super();
5098 }
5099 });
5100
5101 var BrowseButton = Button.extend({
5102 init: function (settings) {
5103 var self = this;
5104 settings = global$4.extend({
5105 text: 'Browse...',
5106 multiple: false,
5107 accept: null
5108 }, settings);
5109 self._super(settings);
5110 self.classes.add('browsebutton');
5111 if (settings.multiple) {
5112 self.classes.add('multiple');
5113 }
5114 },
5115 postRender: function () {
5116 var self = this;
5117 var input = funcs.create('input', {
5118 type: 'file',
5119 id: self._id + '-browse',
5120 accept: self.settings.accept
5121 });
5122 self._super();
5123 global$7(input).on('change', function (e) {
5124 var files = e.target.files;
5125 self.value = function () {
5126 if (!files.length) {
5127 return null;
5128 } else if (self.settings.multiple) {
5129 return files;
5130 } else {
5131 return files[0];
5132 }
5133 };
5134 e.preventDefault();
5135 if (files.length) {
5136 self.fire('change', e);
5137 }
5138 });
5139 global$7(input).on('click', function (e) {
5140 e.stopPropagation();
5141 });
5142 global$7(self.getEl('button')).on('click touchstart', function (e) {
5143 e.stopPropagation();
5144 input.click();
5145 e.preventDefault();
5146 });
5147 self.getEl().appendChild(input);
5148 },
5149 remove: function () {
5150 global$7(this.getEl('button')).off();
5151 global$7(this.getEl('input')).off();
5152 this._super();
5153 }
5154 });
5155
5156 var ButtonGroup = Container.extend({
5157 Defaults: {
5158 defaultType: 'button',
5159 role: 'group'
5160 },
5161 renderHtml: function () {
5162 var self = this, layout = self._layout;
5163 self.classes.add('btn-group');
5164 self.preRender();
5165 layout.preRender(self);
5166 return '<div id="' + self._id + '" class="' + self.classes + '">' + '<div id="' + self._id + '-body">' + (self.settings.html || '') + layout.renderHtml(self) + '</div>' + '</div>';
5167 }
5168 });
5169
5170 var Checkbox = Widget.extend({
5171 Defaults: {
5172 classes: 'checkbox',
5173 role: 'checkbox',
5174 checked: false
5175 },
5176 init: function (settings) {
5177 var self = this;
5178 self._super(settings);
5179 self.on('click mousedown', function (e) {
5180 e.preventDefault();
5181 });
5182 self.on('click', function (e) {
5183 e.preventDefault();
5184 if (!self.disabled()) {
5185 self.checked(!self.checked());
5186 }
5187 });
5188 self.checked(self.settings.checked);
5189 },
5190 checked: function (state) {
5191 if (!arguments.length) {
5192 return this.state.get('checked');
5193 }
5194 this.state.set('checked', state);
5195 return this;
5196 },
5197 value: function (state) {
5198 if (!arguments.length) {
5199 return this.checked();
5200 }
5201 return this.checked(state);
5202 },
5203 renderHtml: function () {
5204 var self = this, id = self._id, prefix = self.classPrefix;
5205 return '<div id="' + id + '" class="' + self.classes + '" unselectable="on" aria-labelledby="' + id + '-al" tabindex="-1">' + '<i class="' + prefix + 'ico ' + prefix + 'i-checkbox"></i>' + '<span id="' + id + '-al" class="' + prefix + 'label">' + self.encode(self.state.get('text')) + '</span>' + '</div>';
5206 },
5207 bindStates: function () {
5208 var self = this;
5209 function checked(state) {
5210 self.classes.toggle('checked', state);
5211 self.aria('checked', state);
5212 }
5213 self.state.on('change:text', function (e) {
5214 self.getEl('al').firstChild.data = self.translate(e.value);
5215 });
5216 self.state.on('change:checked change:value', function (e) {
5217 self.fire('change');
5218 checked(e.value);
5219 });
5220 self.state.on('change:icon', function (e) {
5221 var icon = e.value;
5222 var prefix = self.classPrefix;
5223 if (typeof icon === 'undefined') {
5224 return self.settings.icon;
5225 }
5226 self.settings.icon = icon;
5227 icon = icon ? prefix + 'ico ' + prefix + 'i-' + self.settings.icon : '';
5228 var btnElm = self.getEl().firstChild;
5229 var iconElm = btnElm.getElementsByTagName('i')[0];
5230 if (icon) {
5231 if (!iconElm || iconElm !== btnElm.firstChild) {
5232 iconElm = domGlobals.document.createElement('i');
5233 btnElm.insertBefore(iconElm, btnElm.firstChild);
5234 }
5235 iconElm.className = icon;
5236 } else if (iconElm) {
5237 btnElm.removeChild(iconElm);
5238 }
5239 });
5240 if (self.state.get('checked')) {
5241 checked(true);
5242 }
5243 return self._super();
5244 }
5245 });
5246
5247 var global$f = tinymce.util.Tools.resolve('tinymce.util.VK');
5248
5249 var ComboBox = Widget.extend({
5250 init: function (settings) {
5251 var self = this;
5252 self._super(settings);
5253 settings = self.settings;
5254 self.classes.add('combobox');
5255 self.subinput = true;
5256 self.ariaTarget = 'inp';
5257 settings.menu = settings.menu || settings.values;
5258 if (settings.menu) {
5259 settings.icon = 'caret';
5260 }
5261 self.on('click', function (e) {
5262 var elm = e.target;
5263 var root = self.getEl();
5264 if (!global$7.contains(root, elm) && elm !== root) {
5265 return;
5266 }
5267 while (elm && elm !== root) {
5268 if (elm.id && elm.id.indexOf('-open') !== -1) {
5269 self.fire('action');
5270 if (settings.menu) {
5271 self.showMenu();
5272 if (e.aria) {
5273 self.menu.items()[0].focus();
5274 }
5275 }
5276 }
5277 elm = elm.parentNode;
5278 }
5279 });
5280 self.on('keydown', function (e) {
5281 var rootControl;
5282 if (e.keyCode === 13 && e.target.nodeName === 'INPUT') {
5283 e.preventDefault();
5284 self.parents().reverse().each(function (ctrl) {
5285 if (ctrl.toJSON) {
5286 rootControl = ctrl;
5287 return false;
5288 }
5289 });
5290 self.fire('submit', { data: rootControl.toJSON() });
5291 }
5292 });
5293 self.on('keyup', function (e) {
5294 if (e.target.nodeName === 'INPUT') {
5295 var oldValue = self.state.get('value');
5296 var newValue = e.target.value;
5297 if (newValue !== oldValue) {
5298 self.state.set('value', newValue);
5299 self.fire('autocomplete', e);
5300 }
5301 }
5302 });
5303 self.on('mouseover', function (e) {
5304 var tooltip = self.tooltip().moveTo(-65535);
5305 if (self.statusLevel() && e.target.className.indexOf(self.classPrefix + 'status') !== -1) {
5306 var statusMessage = self.statusMessage() || 'Ok';
5307 var rel = tooltip.text(statusMessage).show().testMoveRel(e.target, [
5308 'bc-tc',
5309 'bc-tl',
5310 'bc-tr'
5311 ]);
5312 tooltip.classes.toggle('tooltip-n', rel === 'bc-tc');
5313 tooltip.classes.toggle('tooltip-nw', rel === 'bc-tl');
5314 tooltip.classes.toggle('tooltip-ne', rel === 'bc-tr');
5315 tooltip.moveRel(e.target, rel);
5316 }
5317 });
5318 },
5319 statusLevel: function (value) {
5320 if (arguments.length > 0) {
5321 this.state.set('statusLevel', value);
5322 }
5323 return this.state.get('statusLevel');
5324 },
5325 statusMessage: function (value) {
5326 if (arguments.length > 0) {
5327 this.state.set('statusMessage', value);
5328 }
5329 return this.state.get('statusMessage');
5330 },
5331 showMenu: function () {
5332 var self = this;
5333 var settings = self.settings;
5334 var menu;
5335 if (!self.menu) {
5336 menu = settings.menu || [];
5337 if (menu.length) {
5338 menu = {
5339 type: 'menu',
5340 items: menu
5341 };
5342 } else {
5343 menu.type = menu.type || 'menu';
5344 }
5345 self.menu = global$b.create(menu).parent(self).renderTo(self.getContainerElm());
5346 self.fire('createmenu');
5347 self.menu.reflow();
5348 self.menu.on('cancel', function (e) {
5349 if (e.control === self.menu) {
5350 self.focus();
5351 }
5352 });
5353 self.menu.on('show hide', function (e) {
5354 e.control.items().each(function (ctrl) {
5355 ctrl.active(ctrl.value() === self.value());
5356 });
5357 }).fire('show');
5358 self.menu.on('select', function (e) {
5359 self.value(e.control.value());
5360 });
5361 self.on('focusin', function (e) {
5362 if (e.target.tagName.toUpperCase() === 'INPUT') {
5363 self.menu.hide();
5364 }
5365 });
5366 self.aria('expanded', true);
5367 }
5368 self.menu.show();
5369 self.menu.layoutRect({ w: self.layoutRect().w });
5370 self.menu.moveRel(self.getEl(), self.isRtl() ? [
5371 'br-tr',
5372 'tr-br'
5373 ] : [
5374 'bl-tl',
5375 'tl-bl'
5376 ]);
5377 },
5378 focus: function () {
5379 this.getEl('inp').focus();
5380 },
5381 repaint: function () {
5382 var self = this, elm = self.getEl(), openElm = self.getEl('open'), rect = self.layoutRect();
5383 var width, lineHeight, innerPadding = 0;
5384 var inputElm = elm.firstChild;
5385 if (self.statusLevel() && self.statusLevel() !== 'none') {
5386 innerPadding = parseInt(funcs.getRuntimeStyle(inputElm, 'padding-right'), 10) - parseInt(funcs.getRuntimeStyle(inputElm, 'padding-left'), 10);
5387 }
5388 if (openElm) {
5389 width = rect.w - funcs.getSize(openElm).width - 10;
5390 } else {
5391 width = rect.w - 10;
5392 }
5393 var doc = domGlobals.document;
5394 if (doc.all && (!doc.documentMode || doc.documentMode <= 8)) {
5395 lineHeight = self.layoutRect().h - 2 + 'px';
5396 }
5397 global$7(inputElm).css({
5398 width: width - innerPadding,
5399 lineHeight: lineHeight
5400 });
5401 self._super();
5402 return self;
5403 },
5404 postRender: function () {
5405 var self = this;
5406 global$7(this.getEl('inp')).on('change', function (e) {
5407 self.state.set('value', e.target.value);
5408 self.fire('change', e);
5409 });
5410 return self._super();
5411 },
5412 renderHtml: function () {
5413 var self = this, id = self._id, settings = self.settings, prefix = self.classPrefix;
5414 var value = self.state.get('value') || '';
5415 var icon, text, openBtnHtml = '', extraAttrs = '', statusHtml = '';
5416 if ('spellcheck' in settings) {
5417 extraAttrs += ' spellcheck="' + settings.spellcheck + '"';
5418 }
5419 if (settings.maxLength) {
5420 extraAttrs += ' maxlength="' + settings.maxLength + '"';
5421 }
5422 if (settings.size) {
5423 extraAttrs += ' size="' + settings.size + '"';
5424 }
5425 if (settings.subtype) {
5426 extraAttrs += ' type="' + settings.subtype + '"';
5427 }
5428 statusHtml = '<i id="' + id + '-status" class="mce-status mce-ico" style="display: none"></i>';
5429 if (self.disabled()) {
5430 extraAttrs += ' disabled="disabled"';
5431 }
5432 icon = settings.icon;
5433 if (icon && icon !== 'caret') {
5434 icon = prefix + 'ico ' + prefix + 'i-' + settings.icon;
5435 }
5436 text = self.state.get('text');
5437 if (icon || text) {
5438 openBtnHtml = '<div id="' + id + '-open" class="' + prefix + 'btn ' + prefix + 'open" tabIndex="-1" role="button">' + '<button id="' + id + '-action" type="button" hidefocus="1" tabindex="-1">' + (icon !== 'caret' ? '<i class="' + icon + '"></i>' : '<i class="' + prefix + 'caret"></i>') + (text ? (icon ? ' ' : '') + text : '') + '</button>' + '</div>';
5439 self.classes.add('has-open');
5440 }
5441 return '<div id="' + id + '" class="' + self.classes + '">' + '<input id="' + id + '-inp" class="' + prefix + 'textbox" value="' + self.encode(value, false) + '" hidefocus="1"' + extraAttrs + ' placeholder="' + self.encode(settings.placeholder) + '" />' + statusHtml + openBtnHtml + '</div>';
5442 },
5443 value: function (value) {
5444 if (arguments.length) {
5445 this.state.set('value', value);
5446 return this;
5447 }
5448 if (this.state.get('rendered')) {
5449 this.state.set('value', this.getEl('inp').value);
5450 }
5451 return this.state.get('value');
5452 },
5453 showAutoComplete: function (items, term) {
5454 var self = this;
5455 if (items.length === 0) {
5456 self.hideMenu();
5457 return;
5458 }
5459 var insert = function (value, title) {
5460 return function () {
5461 self.fire('selectitem', {
5462 title: title,
5463 value: value
5464 });
5465 };
5466 };
5467 if (self.menu) {
5468 self.menu.items().remove();
5469 } else {
5470 self.menu = global$b.create({
5471 type: 'menu',
5472 classes: 'combobox-menu',
5473 layout: 'flow'
5474 }).parent(self).renderTo();
5475 }
5476 global$4.each(items, function (item) {
5477 self.menu.add({
5478 text: item.title,
5479 url: item.previewUrl,
5480 match: term,
5481 classes: 'menu-item-ellipsis',
5482 onclick: insert(item.value, item.title)
5483 });
5484 });
5485 self.menu.renderNew();
5486 self.hideMenu();
5487 self.menu.on('cancel', function (e) {
5488 if (e.control.parent() === self.menu) {
5489 e.stopPropagation();
5490 self.focus();
5491 self.hideMenu();
5492 }
5493 });
5494 self.menu.on('select', function () {
5495 self.focus();
5496 });
5497 var maxW = self.layoutRect().w;
5498 self.menu.layoutRect({
5499 w: maxW,
5500 minW: 0,
5501 maxW: maxW
5502 });
5503 self.menu.repaint();
5504 self.menu.reflow();
5505 self.menu.show();
5506 self.menu.moveRel(self.getEl(), self.isRtl() ? [
5507 'br-tr',
5508 'tr-br'
5509 ] : [
5510 'bl-tl',
5511 'tl-bl'
5512 ]);
5513 },
5514 hideMenu: function () {
5515 if (this.menu) {
5516 this.menu.hide();
5517 }
5518 },
5519 bindStates: function () {
5520 var self = this;
5521 self.state.on('change:value', function (e) {
5522 if (self.getEl('inp').value !== e.value) {
5523 self.getEl('inp').value = e.value;
5524 }
5525 });
5526 self.state.on('change:disabled', function (e) {
5527 self.getEl('inp').disabled = e.value;
5528 });
5529 self.state.on('change:statusLevel', function (e) {
5530 var statusIconElm = self.getEl('status');
5531 var prefix = self.classPrefix, value = e.value;
5532 funcs.css(statusIconElm, 'display', value === 'none' ? 'none' : '');
5533 funcs.toggleClass(statusIconElm, prefix + 'i-checkmark', value === 'ok');
5534 funcs.toggleClass(statusIconElm, prefix + 'i-warning', value === 'warn');
5535 funcs.toggleClass(statusIconElm, prefix + 'i-error', value === 'error');
5536 self.classes.toggle('has-status', value !== 'none');
5537 self.repaint();
5538 });
5539 funcs.on(self.getEl('status'), 'mouseleave', function () {
5540 self.tooltip().hide();
5541 });
5542 self.on('cancel', function (e) {
5543 if (self.menu && self.menu.visible()) {
5544 e.stopPropagation();
5545 self.hideMenu();
5546 }
5547 });
5548 var focusIdx = function (idx, menu) {
5549 if (menu && menu.items().length > 0) {
5550 menu.items().eq(idx)[0].focus();
5551 }
5552 };
5553 self.on('keydown', function (e) {
5554 var keyCode = e.keyCode;
5555 if (e.target.nodeName === 'INPUT') {
5556 if (keyCode === global$f.DOWN) {
5557 e.preventDefault();
5558 self.fire('autocomplete');
5559 focusIdx(0, self.menu);
5560 } else if (keyCode === global$f.UP) {
5561 e.preventDefault();
5562 focusIdx(-1, self.menu);
5563 }
5564 }
5565 });
5566 return self._super();
5567 },
5568 remove: function () {
5569 global$7(this.getEl('inp')).off();
5570 if (this.menu) {
5571 this.menu.remove();
5572 }
5573 this._super();
5574 }
5575 });
5576
5577 var ColorBox = ComboBox.extend({
5578 init: function (settings) {
5579 var self = this;
5580 settings.spellcheck = false;
5581 if (settings.onaction) {
5582 settings.icon = 'none';
5583 }
5584 self._super(settings);
5585 self.classes.add('colorbox');
5586 self.on('change keyup postrender', function () {
5587 self.repaintColor(self.value());
5588 });
5589 },
5590 repaintColor: function (value) {
5591 var openElm = this.getEl('open');
5592 var elm = openElm ? openElm.getElementsByTagName('i')[0] : null;
5593 if (elm) {
5594 try {
5595 elm.style.background = value;
5596 } catch (ex) {
5597 }
5598 }
5599 },
5600 bindStates: function () {
5601 var self = this;
5602 self.state.on('change:value', function (e) {
5603 if (self.state.get('rendered')) {
5604 self.repaintColor(e.value);
5605 }
5606 });
5607 return self._super();
5608 }
5609 });
5610
5611 var PanelButton = Button.extend({
5612 showPanel: function () {
5613 var self = this, settings = self.settings;
5614 self.classes.add('opened');
5615 if (!self.panel) {
5616 var panelSettings = settings.panel;
5617 if (panelSettings.type) {
5618 panelSettings = {
5619 layout: 'grid',
5620 items: panelSettings
5621 };
5622 }
5623 panelSettings.role = panelSettings.role || 'dialog';
5624 panelSettings.popover = true;
5625 panelSettings.autohide = true;
5626 panelSettings.ariaRoot = true;
5627 self.panel = new FloatPanel(panelSettings).on('hide', function () {
5628 self.classes.remove('opened');
5629 }).on('cancel', function (e) {
5630 e.stopPropagation();
5631 self.focus();
5632 self.hidePanel();
5633 }).parent(self).renderTo(self.getContainerElm());
5634 self.panel.fire('show');
5635 self.panel.reflow();
5636 } else {
5637 self.panel.show();
5638 }
5639 var rtlRels = [
5640 'bc-tc',
5641 'bc-tl',
5642 'bc-tr'
5643 ];
5644 var ltrRels = [
5645 'bc-tc',
5646 'bc-tr',
5647 'bc-tl',
5648 'tc-bc',
5649 'tc-br',
5650 'tc-bl'
5651 ];
5652 var rel = self.panel.testMoveRel(self.getEl(), settings.popoverAlign || (self.isRtl() ? rtlRels : ltrRels));
5653 self.panel.classes.toggle('start', rel.substr(-1) === 'l');
5654 self.panel.classes.toggle('end', rel.substr(-1) === 'r');
5655 var isTop = rel.substr(0, 1) === 't';
5656 self.panel.classes.toggle('bottom', !isTop);
5657 self.panel.classes.toggle('top', isTop);
5658 self.panel.moveRel(self.getEl(), rel);
5659 },
5660 hidePanel: function () {
5661 var self = this;
5662 if (self.panel) {
5663 self.panel.hide();
5664 }
5665 },
5666 postRender: function () {
5667 var self = this;
5668 self.aria('haspopup', true);
5669 self.on('click', function (e) {
5670 if (e.control === self) {
5671 if (self.panel && self.panel.visible()) {
5672 self.hidePanel();
5673 } else {
5674 self.showPanel();
5675 self.panel.focus(!!e.aria);
5676 }
5677 }
5678 });
5679 return self._super();
5680 },
5681 remove: function () {
5682 if (this.panel) {
5683 this.panel.remove();
5684 this.panel = null;
5685 }
5686 return this._super();
5687 }
5688 });
5689
5690 var DOM = global$2.DOM;
5691 var ColorButton = PanelButton.extend({
5692 init: function (settings) {
5693 this._super(settings);
5694 this.classes.add('splitbtn');
5695 this.classes.add('colorbutton');
5696 },
5697 color: function (color) {
5698 if (color) {
5699 this._color = color;
5700 this.getEl('preview').style.backgroundColor = color;
5701 return this;
5702 }
5703 return this._color;
5704 },
5705 resetColor: function () {
5706 this._color = null;
5707 this.getEl('preview').style.backgroundColor = null;
5708 return this;
5709 },
5710 renderHtml: function () {
5711 var self = this, id = self._id, prefix = self.classPrefix, text = self.state.get('text');
5712 var icon = self.settings.icon ? prefix + 'ico ' + prefix + 'i-' + self.settings.icon : '';
5713 var image = self.settings.image ? ' style="background-image: url(\'' + self.settings.image + '\')"' : '';
5714 var textHtml = '';
5715 if (text) {
5716 self.classes.add('btn-has-text');
5717 textHtml = '<span class="' + prefix + 'txt">' + self.encode(text) + '</span>';
5718 }
5719 return '<div id="' + id + '" class="' + self.classes + '" role="button" tabindex="-1" aria-haspopup="true">' + '<button role="presentation" hidefocus="1" type="button" tabindex="-1">' + (icon ? '<i class="' + icon + '"' + image + '></i>' : '') + '<span id="' + id + '-preview" class="' + prefix + 'preview"></span>' + textHtml + '</button>' + '<button type="button" class="' + prefix + 'open" hidefocus="1" tabindex="-1">' + ' <i class="' + prefix + 'caret"></i>' + '</button>' + '</div>';
5720 },
5721 postRender: function () {
5722 var self = this, onClickHandler = self.settings.onclick;
5723 self.on('click', function (e) {
5724 if (e.aria && e.aria.key === 'down') {
5725 return;
5726 }
5727 if (e.control === self && !DOM.getParent(e.target, '.' + self.classPrefix + 'open')) {
5728 e.stopImmediatePropagation();
5729 onClickHandler.call(self, e);
5730 }
5731 });
5732 delete self.settings.onclick;
5733 return self._super();
5734 }
5735 });
5736
5737 var global$g = tinymce.util.Tools.resolve('tinymce.util.Color');
5738
5739 var ColorPicker = Widget.extend({
5740 Defaults: { classes: 'widget colorpicker' },
5741 init: function (settings) {
5742 this._super(settings);
5743 },
5744 postRender: function () {
5745 var self = this;
5746 var color = self.color();
5747 var hsv, hueRootElm, huePointElm, svRootElm, svPointElm;
5748 hueRootElm = self.getEl('h');
5749 huePointElm = self.getEl('hp');
5750 svRootElm = self.getEl('sv');
5751 svPointElm = self.getEl('svp');
5752 function getPos(elm, event) {
5753 var pos = funcs.getPos(elm);
5754 var x, y;
5755 x = event.pageX - pos.x;
5756 y = event.pageY - pos.y;
5757 x = Math.max(0, Math.min(x / elm.clientWidth, 1));
5758 y = Math.max(0, Math.min(y / elm.clientHeight, 1));
5759 return {
5760 x: x,
5761 y: y
5762 };
5763 }
5764 function updateColor(hsv, hueUpdate) {
5765 var hue = (360 - hsv.h) / 360;
5766 funcs.css(huePointElm, { top: hue * 100 + '%' });
5767 if (!hueUpdate) {
5768 funcs.css(svPointElm, {
5769 left: hsv.s + '%',
5770 top: 100 - hsv.v + '%'
5771 });
5772 }
5773 svRootElm.style.background = global$g({
5774 s: 100,
5775 v: 100,
5776 h: hsv.h
5777 }).toHex();
5778 self.color().parse({
5779 s: hsv.s,
5780 v: hsv.v,
5781 h: hsv.h
5782 });
5783 }
5784 function updateSaturationAndValue(e) {
5785 var pos;
5786 pos = getPos(svRootElm, e);
5787 hsv.s = pos.x * 100;
5788 hsv.v = (1 - pos.y) * 100;
5789 updateColor(hsv);
5790 self.fire('change');
5791 }
5792 function updateHue(e) {
5793 var pos;
5794 pos = getPos(hueRootElm, e);
5795 hsv = color.toHsv();
5796 hsv.h = (1 - pos.y) * 360;
5797 updateColor(hsv, true);
5798 self.fire('change');
5799 }
5800 self._repaint = function () {
5801 hsv = color.toHsv();
5802 updateColor(hsv);
5803 };
5804 self._super();
5805 self._svdraghelper = new DragHelper(self._id + '-sv', {
5806 start: updateSaturationAndValue,
5807 drag: updateSaturationAndValue
5808 });
5809 self._hdraghelper = new DragHelper(self._id + '-h', {
5810 start: updateHue,
5811 drag: updateHue
5812 });
5813 self._repaint();
5814 },
5815 rgb: function () {
5816 return this.color().toRgb();
5817 },
5818 value: function (value) {
5819 var self = this;
5820 if (arguments.length) {
5821 self.color().parse(value);
5822 if (self._rendered) {
5823 self._repaint();
5824 }
5825 } else {
5826 return self.color().toHex();
5827 }
5828 },
5829 color: function () {
5830 if (!this._color) {
5831 this._color = global$g();
5832 }
5833 return this._color;
5834 },
5835 renderHtml: function () {
5836 var self = this;
5837 var id = self._id;
5838 var prefix = self.classPrefix;
5839 var hueHtml;
5840 var stops = '#ff0000,#ff0080,#ff00ff,#8000ff,#0000ff,#0080ff,#00ffff,#00ff80,#00ff00,#80ff00,#ffff00,#ff8000,#ff0000';
5841 function getOldIeFallbackHtml() {
5842 var i, l, html = '', gradientPrefix, stopsList;
5843 gradientPrefix = 'filter:progid:DXImageTransform.Microsoft.gradient(GradientType=0,startColorstr=';
5844 stopsList = stops.split(',');
5845 for (i = 0, l = stopsList.length - 1; i < l; i++) {
5846 html += '<div class="' + prefix + 'colorpicker-h-chunk" style="' + 'height:' + 100 / l + '%;' + gradientPrefix + stopsList[i] + ',endColorstr=' + stopsList[i + 1] + ');' + '-ms-' + gradientPrefix + stopsList[i] + ',endColorstr=' + stopsList[i + 1] + ')' + '"></div>';
5847 }
5848 return html;
5849 }
5850 var gradientCssText = 'background: -ms-linear-gradient(top,' + stops + ');' + 'background: linear-gradient(to bottom,' + stops + ');';
5851 hueHtml = '<div id="' + id + '-h" class="' + prefix + 'colorpicker-h" style="' + gradientCssText + '">' + getOldIeFallbackHtml() + '<div id="' + id + '-hp" class="' + prefix + 'colorpicker-h-marker"></div>' + '</div>';
5852 return '<div id="' + id + '" class="' + self.classes + '">' + '<div id="' + id + '-sv" class="' + prefix + 'colorpicker-sv">' + '<div class="' + prefix + 'colorpicker-overlay1">' + '<div class="' + prefix + 'colorpicker-overlay2">' + '<div id="' + id + '-svp" class="' + prefix + 'colorpicker-selector1">' + '<div class="' + prefix + 'colorpicker-selector2"></div>' + '</div>' + '</div>' + '</div>' + '</div>' + hueHtml + '</div>';
5853 }
5854 });
5855
5856 var DropZone = Widget.extend({
5857 init: function (settings) {
5858 var self = this;
5859 settings = global$4.extend({
5860 height: 100,
5861 text: 'Drop an image here',
5862 multiple: false,
5863 accept: null
5864 }, settings);
5865 self._super(settings);
5866 self.classes.add('dropzone');
5867 if (settings.multiple) {
5868 self.classes.add('multiple');
5869 }
5870 },
5871 renderHtml: function () {
5872 var self = this;
5873 var attrs, elm;
5874 var cfg = self.settings;
5875 attrs = {
5876 id: self._id,
5877 hidefocus: '1'
5878 };
5879 elm = funcs.create('div', attrs, '<span>' + this.translate(cfg.text) + '</span>');
5880 if (cfg.height) {
5881 funcs.css(elm, 'height', cfg.height + 'px');
5882 }
5883 if (cfg.width) {
5884 funcs.css(elm, 'width', cfg.width + 'px');
5885 }
5886 elm.className = self.classes;
5887 return elm.outerHTML;
5888 },
5889 postRender: function () {
5890 var self = this;
5891 var toggleDragClass = function (e) {
5892 e.preventDefault();
5893 self.classes.toggle('dragenter');
5894 self.getEl().className = self.classes;
5895 };
5896 var filter = function (files) {
5897 var accept = self.settings.accept;
5898 if (typeof accept !== 'string') {
5899 return files;
5900 }
5901 var re = new RegExp('(' + accept.split(/\s*,\s*/).join('|') + ')$', 'i');
5902 return global$4.grep(files, function (file) {
5903 return re.test(file.name);
5904 });
5905 };
5906 self._super();
5907 self.$el.on('dragover', function (e) {
5908 e.preventDefault();
5909 });
5910 self.$el.on('dragenter', toggleDragClass);
5911 self.$el.on('dragleave', toggleDragClass);
5912 self.$el.on('drop', function (e) {
5913 e.preventDefault();
5914 if (self.state.get('disabled')) {
5915 return;
5916 }
5917 var files = filter(e.dataTransfer.files);
5918 self.value = function () {
5919 if (!files.length) {
5920 return null;
5921 } else if (self.settings.multiple) {
5922 return files;
5923 } else {
5924 return files[0];
5925 }
5926 };
5927 if (files.length) {
5928 self.fire('change', e);
5929 }
5930 });
5931 },
5932 remove: function () {
5933 this.$el.off();
5934 this._super();
5935 }
5936 });
5937
5938 var Path = Widget.extend({
5939 init: function (settings) {
5940 var self = this;
5941 if (!settings.delimiter) {
5942 settings.delimiter = '\xBB';
5943 }
5944 self._super(settings);
5945 self.classes.add('path');
5946 self.canFocus = true;
5947 self.on('click', function (e) {
5948 var index;
5949 var target = e.target;
5950 if (index = target.getAttribute('data-index')) {
5951 self.fire('select', {
5952 value: self.row()[index],
5953 index: index
5954 });
5955 }
5956 });
5957 self.row(self.settings.row);
5958 },
5959 focus: function () {
5960 var self = this;
5961 self.getEl().firstChild.focus();
5962 return self;
5963 },
5964 row: function (row) {
5965 if (!arguments.length) {
5966 return this.state.get('row');
5967 }
5968 this.state.set('row', row);
5969 return this;
5970 },
5971 renderHtml: function () {
5972 var self = this;
5973 return '<div id="' + self._id + '" class="' + self.classes + '">' + self._getDataPathHtml(self.state.get('row')) + '</div>';
5974 },
5975 bindStates: function () {
5976 var self = this;
5977 self.state.on('change:row', function (e) {
5978 self.innerHtml(self._getDataPathHtml(e.value));
5979 });
5980 return self._super();
5981 },
5982 _getDataPathHtml: function (data) {
5983 var self = this;
5984 var parts = data || [];
5985 var i, l, html = '';
5986 var prefix = self.classPrefix;
5987 for (i = 0, l = parts.length; i < l; i++) {
5988 html += (i > 0 ? '<div class="' + prefix + 'divider" aria-hidden="true"> ' + self.settings.delimiter + ' </div>' : '') + '<div role="button" class="' + prefix + 'path-item' + (i === l - 1 ? ' ' + prefix + 'last' : '') + '" data-index="' + i + '" tabindex="-1" id="' + self._id + '-' + i + '" aria-level="' + (i + 1) + '">' + parts[i].name + '</div>';
5989 }
5990 if (!html) {
5991 html = '<div class="' + prefix + 'path-item">\xA0</div>';
5992 }
5993 return html;
5994 }
5995 });
5996
5997 var ElementPath = Path.extend({
5998 postRender: function () {
5999 var self = this, editor = self.settings.editor;
6000 function isHidden(elm) {
6001 if (elm.nodeType === 1) {
6002 if (elm.nodeName === 'BR' || !!elm.getAttribute('data-mce-bogus')) {
6003 return true;
6004 }
6005 if (elm.getAttribute('data-mce-type') === 'bookmark') {
6006 return true;
6007 }
6008 }
6009 return false;
6010 }
6011 if (editor.settings.elementpath !== false) {
6012 self.on('select', function (e) {
6013 editor.focus();
6014 editor.selection.select(this.row()[e.index].element);
6015 editor.nodeChanged();
6016 });
6017 editor.on('nodeChange', function (e) {
6018 var outParents = [];
6019 var parents = e.parents;
6020 var i = parents.length;
6021 while (i--) {
6022 if (parents[i].nodeType === 1 && !isHidden(parents[i])) {
6023 var args = editor.fire('ResolveName', {
6024 name: parents[i].nodeName.toLowerCase(),
6025 target: parents[i]
6026 });
6027 if (!args.isDefaultPrevented()) {
6028 outParents.push({
6029 name: args.name,
6030 element: parents[i]
6031 });
6032 }
6033 if (args.isPropagationStopped()) {
6034 break;
6035 }
6036 }
6037 }
6038 self.row(outParents);
6039 });
6040 }
6041 return self._super();
6042 }
6043 });
6044
6045 var FormItem = Container.extend({
6046 Defaults: {
6047 layout: 'flex',
6048 align: 'center',
6049 defaults: { flex: 1 }
6050 },
6051 renderHtml: function () {
6052 var self = this, layout = self._layout, prefix = self.classPrefix;
6053 self.classes.add('formitem');
6054 layout.preRender(self);
6055 return '<div id="' + self._id + '" class="' + self.classes + '" hidefocus="1" tabindex="-1">' + (self.settings.title ? '<div id="' + self._id + '-title" class="' + prefix + 'title">' + self.settings.title + '</div>' : '') + '<div id="' + self._id + '-body" class="' + self.bodyClasses + '">' + (self.settings.html || '') + layout.renderHtml(self) + '</div>' + '</div>';
6056 }
6057 });
6058
6059 var Form = Container.extend({
6060 Defaults: {
6061 containerCls: 'form',
6062 layout: 'flex',
6063 direction: 'column',
6064 align: 'stretch',
6065 flex: 1,
6066 padding: 15,
6067 labelGap: 30,
6068 spacing: 10,
6069 callbacks: {
6070 submit: function () {
6071 this.submit();
6072 }
6073 }
6074 },
6075 preRender: function () {
6076 var self = this, items = self.items();
6077 if (!self.settings.formItemDefaults) {
6078 self.settings.formItemDefaults = {
6079 layout: 'flex',
6080 autoResize: 'overflow',
6081 defaults: { flex: 1 }
6082 };
6083 }
6084 items.each(function (ctrl) {
6085 var formItem;
6086 var label = ctrl.settings.label;
6087 if (label) {
6088 formItem = new FormItem(global$4.extend({
6089 items: {
6090 type: 'label',
6091 id: ctrl._id + '-l',
6092 text: label,
6093 flex: 0,
6094 forId: ctrl._id,
6095 disabled: ctrl.disabled()
6096 }
6097 }, self.settings.formItemDefaults));
6098 formItem.type = 'formitem';
6099 ctrl.aria('labelledby', ctrl._id + '-l');
6100 if (typeof ctrl.settings.flex === 'undefined') {
6101 ctrl.settings.flex = 1;
6102 }
6103 self.replace(ctrl, formItem);
6104 formItem.add(ctrl);
6105 }
6106 });
6107 },
6108 submit: function () {
6109 return this.fire('submit', { data: this.toJSON() });
6110 },
6111 postRender: function () {
6112 var self = this;
6113 self._super();
6114 self.fromJSON(self.settings.data);
6115 },
6116 bindStates: function () {
6117 var self = this;
6118 self._super();
6119 function recalcLabels() {
6120 var maxLabelWidth = 0;
6121 var labels = [];
6122 var i, labelGap, items;
6123 if (self.settings.labelGapCalc === false) {
6124 return;
6125 }
6126 if (self.settings.labelGapCalc === 'children') {
6127 items = self.find('formitem');
6128 } else {
6129 items = self.items();
6130 }
6131 items.filter('formitem').each(function (item) {
6132 var labelCtrl = item.items()[0], labelWidth = labelCtrl.getEl().clientWidth;
6133 maxLabelWidth = labelWidth > maxLabelWidth ? labelWidth : maxLabelWidth;
6134 labels.push(labelCtrl);
6135 });
6136 labelGap = self.settings.labelGap || 0;
6137 i = labels.length;
6138 while (i--) {
6139 labels[i].settings.minWidth = maxLabelWidth + labelGap;
6140 }
6141 }
6142 self.on('show', recalcLabels);
6143 recalcLabels();
6144 }
6145 });
6146
6147 var FieldSet = Form.extend({
6148 Defaults: {
6149 containerCls: 'fieldset',
6150 layout: 'flex',
6151 direction: 'column',
6152 align: 'stretch',
6153 flex: 1,
6154 padding: '25 15 5 15',
6155 labelGap: 30,
6156 spacing: 10,
6157 border: 1
6158 },
6159 renderHtml: function () {
6160 var self = this, layout = self._layout, prefix = self.classPrefix;
6161 self.preRender();
6162 layout.preRender(self);
6163 return '<fieldset id="' + self._id + '" class="' + self.classes + '" hidefocus="1" tabindex="-1">' + (self.settings.title ? '<legend id="' + self._id + '-title" class="' + prefix + 'fieldset-title">' + self.settings.title + '</legend>' : '') + '<div id="' + self._id + '-body" class="' + self.bodyClasses + '">' + (self.settings.html || '') + layout.renderHtml(self) + '</div>' + '</fieldset>';
6164 }
6165 });
6166
6167 var unique$1 = 0;
6168 var generate = function (prefix) {
6169 var date = new Date();
6170 var time = date.getTime();
6171 var random = Math.floor(Math.random() * 1000000000);
6172 unique$1++;
6173 return prefix + '_' + random + unique$1 + String(time);
6174 };
6175
6176 var fromHtml = function (html, scope) {
6177 var doc = scope || domGlobals.document;
6178 var div = doc.createElement('div');
6179 div.innerHTML = html;
6180 if (!div.hasChildNodes() || div.childNodes.length > 1) {
6181 domGlobals.console.error('HTML does not have a single root node', html);
6182 throw new Error('HTML must have a single root node');
6183 }
6184 return fromDom(div.childNodes[0]);
6185 };
6186 var fromTag = function (tag, scope) {
6187 var doc = scope || domGlobals.document;
6188 var node = doc.createElement(tag);
6189 return fromDom(node);
6190 };
6191 var fromText = function (text, scope) {
6192 var doc = scope || domGlobals.document;
6193 var node = doc.createTextNode(text);
6194 return fromDom(node);
6195 };
6196 var fromDom = function (node) {
6197 if (node === null || node === undefined) {
6198 throw new Error('Node cannot be null or undefined');
6199 }
6200 return { dom: constant(node) };
6201 };
6202 var fromPoint = function (docElm, x, y) {
6203 var doc = docElm.dom();
6204 return Option.from(doc.elementFromPoint(x, y)).map(fromDom);
6205 };
6206 var Element = {
6207 fromHtml: fromHtml,
6208 fromTag: fromTag,
6209 fromText: fromText,
6210 fromDom: fromDom,
6211 fromPoint: fromPoint
6212 };
6213
6214 var cached = function (f) {
6215 var called = false;
6216 var r;
6217 return function () {
6218 var args = [];
6219 for (var _i = 0; _i < arguments.length; _i++) {
6220 args[_i] = arguments[_i];
6221 }
6222 if (!called) {
6223 called = true;
6224 r = f.apply(null, args);
6225 }
6226 return r;
6227 };
6228 };
6229
6230 var ATTRIBUTE = domGlobals.Node.ATTRIBUTE_NODE;
6231 var CDATA_SECTION = domGlobals.Node.CDATA_SECTION_NODE;
6232 var COMMENT = domGlobals.Node.COMMENT_NODE;
6233 var DOCUMENT = domGlobals.Node.DOCUMENT_NODE;
6234 var DOCUMENT_TYPE = domGlobals.Node.DOCUMENT_TYPE_NODE;
6235 var DOCUMENT_FRAGMENT = domGlobals.Node.DOCUMENT_FRAGMENT_NODE;
6236 var ELEMENT = domGlobals.Node.ELEMENT_NODE;
6237 var TEXT = domGlobals.Node.TEXT_NODE;
6238 var PROCESSING_INSTRUCTION = domGlobals.Node.PROCESSING_INSTRUCTION_NODE;
6239 var ENTITY_REFERENCE = domGlobals.Node.ENTITY_REFERENCE_NODE;
6240 var ENTITY = domGlobals.Node.ENTITY_NODE;
6241 var NOTATION = domGlobals.Node.NOTATION_NODE;
6242
6243 var Immutable = function () {
6244 var fields = [];
6245 for (var _i = 0; _i < arguments.length; _i++) {
6246 fields[_i] = arguments[_i];
6247 }
6248 return function () {
6249 var values = [];
6250 for (var _i = 0; _i < arguments.length; _i++) {
6251 values[_i] = arguments[_i];
6252 }
6253 if (fields.length !== values.length) {
6254 throw new Error('Wrong number of arguments to struct. Expected "[' + fields.length + ']", got ' + values.length + ' arguments');
6255 }
6256 var struct = {};
6257 each(fields, function (name, i) {
6258 struct[name] = constant(values[i]);
6259 });
6260 return struct;
6261 };
6262 };
6263
6264 var node = function () {
6265 var f = Global$1.getOrDie('Node');
6266 return f;
6267 };
6268 var compareDocumentPosition = function (a, b, match) {
6269 return (a.compareDocumentPosition(b) & match) !== 0;
6270 };
6271 var documentPositionPreceding = function (a, b) {
6272 return compareDocumentPosition(a, b, node().DOCUMENT_POSITION_PRECEDING);
6273 };
6274 var documentPositionContainedBy = function (a, b) {
6275 return compareDocumentPosition(a, b, node().DOCUMENT_POSITION_CONTAINED_BY);
6276 };
6277 var Node = {
6278 documentPositionPreceding: documentPositionPreceding,
6279 documentPositionContainedBy: documentPositionContainedBy
6280 };
6281
6282 var firstMatch = function (regexes, s) {
6283 for (var i = 0; i < regexes.length; i++) {
6284 var x = regexes[i];
6285 if (x.test(s)) {
6286 return x;
6287 }
6288 }
6289 return undefined;
6290 };
6291 var find$1 = function (regexes, agent) {
6292 var r = firstMatch(regexes, agent);
6293 if (!r) {
6294 return {
6295 major: 0,
6296 minor: 0
6297 };
6298 }
6299 var group = function (i) {
6300 return Number(agent.replace(r, '$' + i));
6301 };
6302 return nu(group(1), group(2));
6303 };
6304 var detect = function (versionRegexes, agent) {
6305 var cleanedAgent = String(agent).toLowerCase();
6306 if (versionRegexes.length === 0) {
6307 return unknown();
6308 }
6309 return find$1(versionRegexes, cleanedAgent);
6310 };
6311 var unknown = function () {
6312 return nu(0, 0);
6313 };
6314 var nu = function (major, minor) {
6315 return {
6316 major: major,
6317 minor: minor
6318 };
6319 };
6320 var Version = {
6321 nu: nu,
6322 detect: detect,
6323 unknown: unknown
6324 };
6325
6326 var edge = 'Edge';
6327 var chrome = 'Chrome';
6328 var ie = 'IE';
6329 var opera = 'Opera';
6330 var firefox = 'Firefox';
6331 var safari = 'Safari';
6332 var isBrowser = function (name, current) {
6333 return function () {
6334 return current === name;
6335 };
6336 };
6337 var unknown$1 = function () {
6338 return nu$1({
6339 current: undefined,
6340 version: Version.unknown()
6341 });
6342 };
6343 var nu$1 = function (info) {
6344 var current = info.current;
6345 var version = info.version;
6346 return {
6347 current: current,
6348 version: version,
6349 isEdge: isBrowser(edge, current),
6350 isChrome: isBrowser(chrome, current),
6351 isIE: isBrowser(ie, current),
6352 isOpera: isBrowser(opera, current),
6353 isFirefox: isBrowser(firefox, current),
6354 isSafari: isBrowser(safari, current)
6355 };
6356 };
6357 var Browser = {
6358 unknown: unknown$1,
6359 nu: nu$1,
6360 edge: constant(edge),
6361 chrome: constant(chrome),
6362 ie: constant(ie),
6363 opera: constant(opera),
6364 firefox: constant(firefox),
6365 safari: constant(safari)
6366 };
6367
6368 var windows$1 = 'Windows';
6369 var ios = 'iOS';
6370 var android = 'Android';
6371 var linux = 'Linux';
6372 var osx = 'OSX';
6373 var solaris = 'Solaris';
6374 var freebsd = 'FreeBSD';
6375 var isOS = function (name, current) {
6376 return function () {
6377 return current === name;
6378 };
6379 };
6380 var unknown$2 = function () {
6381 return nu$2({
6382 current: undefined,
6383 version: Version.unknown()
6384 });
6385 };
6386 var nu$2 = function (info) {
6387 var current = info.current;
6388 var version = info.version;
6389 return {
6390 current: current,
6391 version: version,
6392 isWindows: isOS(windows$1, current),
6393 isiOS: isOS(ios, current),
6394 isAndroid: isOS(android, current),
6395 isOSX: isOS(osx, current),
6396 isLinux: isOS(linux, current),
6397 isSolaris: isOS(solaris, current),
6398 isFreeBSD: isOS(freebsd, current)
6399 };
6400 };
6401 var OperatingSystem = {
6402 unknown: unknown$2,
6403 nu: nu$2,
6404 windows: constant(windows$1),
6405 ios: constant(ios),
6406 android: constant(android),
6407 linux: constant(linux),
6408 osx: constant(osx),
6409 solaris: constant(solaris),
6410 freebsd: constant(freebsd)
6411 };
6412
6413 var DeviceType = function (os, browser, userAgent) {
6414 var isiPad = os.isiOS() && /ipad/i.test(userAgent) === true;
6415 var isiPhone = os.isiOS() && !isiPad;
6416 var isAndroid3 = os.isAndroid() && os.version.major === 3;
6417 var isAndroid4 = os.isAndroid() && os.version.major === 4;
6418 var isTablet = isiPad || isAndroid3 || isAndroid4 && /mobile/i.test(userAgent) === true;
6419 var isTouch = os.isiOS() || os.isAndroid();
6420 var isPhone = isTouch && !isTablet;
6421 var iOSwebview = browser.isSafari() && os.isiOS() && /safari/i.test(userAgent) === false;
6422 return {
6423 isiPad: constant(isiPad),
6424 isiPhone: constant(isiPhone),
6425 isTablet: constant(isTablet),
6426 isPhone: constant(isPhone),
6427 isTouch: constant(isTouch),
6428 isAndroid: os.isAndroid,
6429 isiOS: os.isiOS,
6430 isWebView: constant(iOSwebview)
6431 };
6432 };
6433
6434 var detect$1 = function (candidates, userAgent) {
6435 var agent = String(userAgent).toLowerCase();
6436 return find(candidates, function (candidate) {
6437 return candidate.search(agent);
6438 });
6439 };
6440 var detectBrowser = function (browsers, userAgent) {
6441 return detect$1(browsers, userAgent).map(function (browser) {
6442 var version = Version.detect(browser.versionRegexes, userAgent);
6443 return {
6444 current: browser.name,
6445 version: version
6446 };
6447 });
6448 };
6449 var detectOs = function (oses, userAgent) {
6450 return detect$1(oses, userAgent).map(function (os) {
6451 var version = Version.detect(os.versionRegexes, userAgent);
6452 return {
6453 current: os.name,
6454 version: version
6455 };
6456 });
6457 };
6458 var UaString = {
6459 detectBrowser: detectBrowser,
6460 detectOs: detectOs
6461 };
6462
6463 var contains = function (str, substr) {
6464 return str.indexOf(substr) !== -1;
6465 };
6466
6467 var normalVersionRegex = /.*?version\/\ ?([0-9]+)\.([0-9]+).*/;
6468 var checkContains = function (target) {
6469 return function (uastring) {
6470 return contains(uastring, target);
6471 };
6472 };
6473 var browsers = [
6474 {
6475 name: 'Edge',
6476 versionRegexes: [/.*?edge\/ ?([0-9]+)\.([0-9]+)$/],
6477 search: function (uastring) {
6478 return contains(uastring, 'edge/') && contains(uastring, 'chrome') && contains(uastring, 'safari') && contains(uastring, 'applewebkit');
6479 }
6480 },
6481 {
6482 name: 'Chrome',
6483 versionRegexes: [
6484 /.*?chrome\/([0-9]+)\.([0-9]+).*/,
6485 normalVersionRegex
6486 ],
6487 search: function (uastring) {
6488 return contains(uastring, 'chrome') && !contains(uastring, 'chromeframe');
6489 }
6490 },
6491 {
6492 name: 'IE',
6493 versionRegexes: [
6494 /.*?msie\ ?([0-9]+)\.([0-9]+).*/,
6495 /.*?rv:([0-9]+)\.([0-9]+).*/
6496 ],
6497 search: function (uastring) {
6498 return contains(uastring, 'msie') || contains(uastring, 'trident');
6499 }
6500 },
6501 {
6502 name: 'Opera',
6503 versionRegexes: [
6504 normalVersionRegex,
6505 /.*?opera\/([0-9]+)\.([0-9]+).*/
6506 ],
6507 search: checkContains('opera')
6508 },
6509 {
6510 name: 'Firefox',
6511 versionRegexes: [/.*?firefox\/\ ?([0-9]+)\.([0-9]+).*/],
6512 search: checkContains('firefox')
6513 },
6514 {
6515 name: 'Safari',
6516 versionRegexes: [
6517 normalVersionRegex,
6518 /.*?cpu os ([0-9]+)_([0-9]+).*/
6519 ],
6520 search: function (uastring) {
6521 return (contains(uastring, 'safari') || contains(uastring, 'mobile/')) && contains(uastring, 'applewebkit');
6522 }
6523 }
6524 ];
6525 var oses = [
6526 {
6527 name: 'Windows',
6528 search: checkContains('win'),
6529 versionRegexes: [/.*?windows\ nt\ ?([0-9]+)\.([0-9]+).*/]
6530 },
6531 {
6532 name: 'iOS',
6533 search: function (uastring) {
6534 return contains(uastring, 'iphone') || contains(uastring, 'ipad');
6535 },
6536 versionRegexes: [
6537 /.*?version\/\ ?([0-9]+)\.([0-9]+).*/,
6538 /.*cpu os ([0-9]+)_([0-9]+).*/,
6539 /.*cpu iphone os ([0-9]+)_([0-9]+).*/
6540 ]
6541 },
6542 {
6543 name: 'Android',
6544 search: checkContains('android'),
6545 versionRegexes: [/.*?android\ ?([0-9]+)\.([0-9]+).*/]
6546 },
6547 {
6548 name: 'OSX',
6549 search: checkContains('os x'),
6550 versionRegexes: [/.*?os\ x\ ?([0-9]+)_([0-9]+).*/]
6551 },
6552 {
6553 name: 'Linux',
6554 search: checkContains('linux'),
6555 versionRegexes: []
6556 },
6557 {
6558 name: 'Solaris',
6559 search: checkContains('sunos'),
6560 versionRegexes: []
6561 },
6562 {
6563 name: 'FreeBSD',
6564 search: checkContains('freebsd'),
6565 versionRegexes: []
6566 }
6567 ];
6568 var PlatformInfo = {
6569 browsers: constant(browsers),
6570 oses: constant(oses)
6571 };
6572
6573 var detect$2 = function (userAgent) {
6574 var browsers = PlatformInfo.browsers();
6575 var oses = PlatformInfo.oses();
6576 var browser = UaString.detectBrowser(browsers, userAgent).fold(Browser.unknown, Browser.nu);
6577 var os = UaString.detectOs(oses, userAgent).fold(OperatingSystem.unknown, OperatingSystem.nu);
6578 var deviceType = DeviceType(os, browser, userAgent);
6579 return {
6580 browser: browser,
6581 os: os,
6582 deviceType: deviceType
6583 };
6584 };
6585 var PlatformDetection = { detect: detect$2 };
6586
6587 var detect$3 = cached(function () {
6588 var userAgent = domGlobals.navigator.userAgent;
6589 return PlatformDetection.detect(userAgent);
6590 });
6591 var PlatformDetection$1 = { detect: detect$3 };
6592
6593 var ELEMENT$1 = ELEMENT;
6594 var DOCUMENT$1 = DOCUMENT;
6595 var bypassSelector = function (dom) {
6596 return dom.nodeType !== ELEMENT$1 && dom.nodeType !== DOCUMENT$1 || dom.childElementCount === 0;
6597 };
6598 var all = function (selector, scope) {
6599 var base = scope === undefined ? domGlobals.document : scope.dom();
6600 return bypassSelector(base) ? [] : map(base.querySelectorAll(selector), Element.fromDom);
6601 };
6602 var one = function (selector, scope) {
6603 var base = scope === undefined ? domGlobals.document : scope.dom();
6604 return bypassSelector(base) ? Option.none() : Option.from(base.querySelector(selector)).map(Element.fromDom);
6605 };
6606
6607 var regularContains = function (e1, e2) {
6608 var d1 = e1.dom();
6609 var d2 = e2.dom();
6610 return d1 === d2 ? false : d1.contains(d2);
6611 };
6612 var ieContains = function (e1, e2) {
6613 return Node.documentPositionContainedBy(e1.dom(), e2.dom());
6614 };
6615 var browser = PlatformDetection$1.detect().browser;
6616 var contains$1 = browser.isIE() ? ieContains : regularContains;
6617
6618 var spot = Immutable('element', 'offset');
6619
6620 var descendants = function (scope, selector) {
6621 return all(selector, scope);
6622 };
6623
6624 var trim = global$4.trim;
6625 var hasContentEditableState = function (value) {
6626 return function (node) {
6627 if (node && node.nodeType === 1) {
6628 if (node.contentEditable === value) {
6629 return true;
6630 }
6631 if (node.getAttribute('data-mce-contenteditable') === value) {
6632 return true;
6633 }
6634 }
6635 return false;
6636 };
6637 };
6638 var isContentEditableTrue = hasContentEditableState('true');
6639 var isContentEditableFalse = hasContentEditableState('false');
6640 var create$4 = function (type, title, url, level, attach) {
6641 return {
6642 type: type,
6643 title: title,
6644 url: url,
6645 level: level,
6646 attach: attach
6647 };
6648 };
6649 var isChildOfContentEditableTrue = function (node) {
6650 while (node = node.parentNode) {
6651 var value = node.contentEditable;
6652 if (value && value !== 'inherit') {
6653 return isContentEditableTrue(node);
6654 }
6655 }
6656 return false;
6657 };
6658 var select = function (selector, root) {
6659 return map(descendants(Element.fromDom(root), selector), function (element) {
6660 return element.dom();
6661 });
6662 };
6663 var getElementText = function (elm) {
6664 return elm.innerText || elm.textContent;
6665 };
6666 var getOrGenerateId = function (elm) {
6667 return elm.id ? elm.id : generate('h');
6668 };
6669 var isAnchor = function (elm) {
6670 return elm && elm.nodeName === 'A' && (elm.id || elm.name);
6671 };
6672 var isValidAnchor = function (elm) {
6673 return isAnchor(elm) && isEditable(elm);
6674 };
6675 var isHeader = function (elm) {
6676 return elm && /^(H[1-6])$/.test(elm.nodeName);
6677 };
6678 var isEditable = function (elm) {
6679 return isChildOfContentEditableTrue(elm) && !isContentEditableFalse(elm);
6680 };
6681 var isValidHeader = function (elm) {
6682 return isHeader(elm) && isEditable(elm);
6683 };
6684 var getLevel = function (elm) {
6685 return isHeader(elm) ? parseInt(elm.nodeName.substr(1), 10) : 0;
6686 };
6687 var headerTarget = function (elm) {
6688 var headerId = getOrGenerateId(elm);
6689 var attach = function () {
6690 elm.id = headerId;
6691 };
6692 return create$4('header', getElementText(elm), '#' + headerId, getLevel(elm), attach);
6693 };
6694 var anchorTarget = function (elm) {
6695 var anchorId = elm.id || elm.name;
6696 var anchorText = getElementText(elm);
6697 return create$4('anchor', anchorText ? anchorText : '#' + anchorId, '#' + anchorId, 0, noop);
6698 };
6699 var getHeaderTargets = function (elms) {
6700 return map(filter(elms, isValidHeader), headerTarget);
6701 };
6702 var getAnchorTargets = function (elms) {
6703 return map(filter(elms, isValidAnchor), anchorTarget);
6704 };
6705 var getTargetElements = function (elm) {
6706 var elms = select('h1,h2,h3,h4,h5,h6,a:not([href])', elm);
6707 return elms;
6708 };
6709 var hasTitle = function (target) {
6710 return trim(target.title).length > 0;
6711 };
6712 var find$2 = function (elm) {
6713 var elms = getTargetElements(elm);
6714 return filter(getHeaderTargets(elms).concat(getAnchorTargets(elms)), hasTitle);
6715 };
6716 var LinkTargets = { find: find$2 };
6717
6718 var getActiveEditor = function () {
6719 return window.tinymce ? window.tinymce.activeEditor : global$5.activeEditor;
6720 };
6721 var history = {};
6722 var HISTORY_LENGTH = 5;
6723 var clearHistory = function () {
6724 history = {};
6725 };
6726 var toMenuItem = function (target) {
6727 return {
6728 title: target.title,
6729 value: {
6730 title: { raw: target.title },
6731 url: target.url,
6732 attach: target.attach
6733 }
6734 };
6735 };
6736 var toMenuItems = function (targets) {
6737 return global$4.map(targets, toMenuItem);
6738 };
6739 var staticMenuItem = function (title, url) {
6740 return {
6741 title: title,
6742 value: {
6743 title: title,
6744 url: url,
6745 attach: noop
6746 }
6747 };
6748 };
6749 var isUniqueUrl = function (url, targets) {
6750 var foundTarget = exists(targets, function (target) {
6751 return target.url === url;
6752 });
6753 return !foundTarget;
6754 };
6755 var getSetting = function (editorSettings, name, defaultValue) {
6756 var value = name in editorSettings ? editorSettings[name] : defaultValue;
6757 return value === false ? null : value;
6758 };
6759 var createMenuItems = function (term, targets, fileType, editorSettings) {
6760 var separator = { title: '-' };
6761 var fromHistoryMenuItems = function (history) {
6762 var historyItems = history.hasOwnProperty(fileType) ? history[fileType] : [];
6763 var uniqueHistory = filter(historyItems, function (url) {
6764 return isUniqueUrl(url, targets);
6765 });
6766 return global$4.map(uniqueHistory, function (url) {
6767 return {
6768 title: url,
6769 value: {
6770 title: url,
6771 url: url,
6772 attach: noop
6773 }
6774 };
6775 });
6776 };
6777 var fromMenuItems = function (type) {
6778 var filteredTargets = filter(targets, function (target) {
6779 return target.type === type;
6780 });
6781 return toMenuItems(filteredTargets);
6782 };
6783 var anchorMenuItems = function () {
6784 var anchorMenuItems = fromMenuItems('anchor');
6785 var topAnchor = getSetting(editorSettings, 'anchor_top', '#top');
6786 var bottomAchor = getSetting(editorSettings, 'anchor_bottom', '#bottom');
6787 if (topAnchor !== null) {
6788 anchorMenuItems.unshift(staticMenuItem('<top>', topAnchor));
6789 }
6790 if (bottomAchor !== null) {
6791 anchorMenuItems.push(staticMenuItem('<bottom>', bottomAchor));
6792 }
6793 return anchorMenuItems;
6794 };
6795 var join = function (items) {
6796 return foldl(items, function (a, b) {
6797 var bothEmpty = a.length === 0 || b.length === 0;
6798 return bothEmpty ? a.concat(b) : a.concat(separator, b);
6799 }, []);
6800 };
6801 if (editorSettings.typeahead_urls === false) {
6802 return [];
6803 }
6804 return fileType === 'file' ? join([
6805 filterByQuery(term, fromHistoryMenuItems(history)),
6806 filterByQuery(term, fromMenuItems('header')),
6807 filterByQuery(term, anchorMenuItems())
6808 ]) : filterByQuery(term, fromHistoryMenuItems(history));
6809 };
6810 var addToHistory = function (url, fileType) {
6811 var items = history[fileType];
6812 if (!/^https?/.test(url)) {
6813 return;
6814 }
6815 if (items) {
6816 if (indexOf(items, url).isNone()) {
6817 history[fileType] = items.slice(0, HISTORY_LENGTH).concat(url);
6818 }
6819 } else {
6820 history[fileType] = [url];
6821 }
6822 };
6823 var filterByQuery = function (term, menuItems) {
6824 var lowerCaseTerm = term.toLowerCase();
6825 var result = global$4.grep(menuItems, function (item) {
6826 return item.title.toLowerCase().indexOf(lowerCaseTerm) !== -1;
6827 });
6828 return result.length === 1 && result[0].title === term ? [] : result;
6829 };
6830 var getTitle = function (linkDetails) {
6831 var title = linkDetails.title;
6832 return title.raw ? title.raw : title;
6833 };
6834 var setupAutoCompleteHandler = function (ctrl, editorSettings, bodyElm, fileType) {
6835 var autocomplete = function (term) {
6836 var linkTargets = LinkTargets.find(bodyElm);
6837 var menuItems = createMenuItems(term, linkTargets, fileType, editorSettings);
6838 ctrl.showAutoComplete(menuItems, term);
6839 };
6840 ctrl.on('autocomplete', function () {
6841 autocomplete(ctrl.value());
6842 });
6843 ctrl.on('selectitem', function (e) {
6844 var linkDetails = e.value;
6845 ctrl.value(linkDetails.url);
6846 var title = getTitle(linkDetails);
6847 if (fileType === 'image') {
6848 ctrl.fire('change', {
6849 meta: {
6850 alt: title,
6851 attach: linkDetails.attach
6852 }
6853 });
6854 } else {
6855 ctrl.fire('change', {
6856 meta: {
6857 text: title,
6858 attach: linkDetails.attach
6859 }
6860 });
6861 }
6862 ctrl.focus();
6863 });
6864 ctrl.on('click', function (e) {
6865 if (ctrl.value().length === 0 && e.target.nodeName === 'INPUT') {
6866 autocomplete('');
6867 }
6868 });
6869 ctrl.on('PostRender', function () {
6870 ctrl.getRoot().on('submit', function (e) {
6871 if (!e.isDefaultPrevented()) {
6872 addToHistory(ctrl.value(), fileType);
6873 }
6874 });
6875 });
6876 };
6877 var statusToUiState = function (result) {
6878 var status = result.status, message = result.message;
6879 if (status === 'valid') {
6880 return {
6881 status: 'ok',
6882 message: message
6883 };
6884 } else if (status === 'unknown') {
6885 return {
6886 status: 'warn',
6887 message: message
6888 };
6889 } else if (status === 'invalid') {
6890 return {
6891 status: 'warn',
6892 message: message
6893 };
6894 } else {
6895 return {
6896 status: 'none',
6897 message: ''
6898 };
6899 }
6900 };
6901 var setupLinkValidatorHandler = function (ctrl, editorSettings, fileType) {
6902 var validatorHandler = editorSettings.filepicker_validator_handler;
6903 if (validatorHandler) {
6904 var validateUrl_1 = function (url) {
6905 if (url.length === 0) {
6906 ctrl.statusLevel('none');
6907 return;
6908 }
6909 validatorHandler({
6910 url: url,
6911 type: fileType
6912 }, function (result) {
6913 var uiState = statusToUiState(result);
6914 ctrl.statusMessage(uiState.message);
6915 ctrl.statusLevel(uiState.status);
6916 });
6917 };
6918 ctrl.state.on('change:value', function (e) {
6919 validateUrl_1(e.value);
6920 });
6921 }
6922 };
6923 var FilePicker = ComboBox.extend({
6924 Statics: { clearHistory: clearHistory },
6925 init: function (settings) {
6926 var self = this, editor = getActiveEditor(), editorSettings = editor.settings;
6927 var actionCallback, fileBrowserCallback, fileBrowserCallbackTypes;
6928 var fileType = settings.filetype;
6929 settings.spellcheck = false;
6930 fileBrowserCallbackTypes = editorSettings.file_picker_types || editorSettings.file_browser_callback_types;
6931 if (fileBrowserCallbackTypes) {
6932 fileBrowserCallbackTypes = global$4.makeMap(fileBrowserCallbackTypes, /[, ]/);
6933 }
6934 if (!fileBrowserCallbackTypes || fileBrowserCallbackTypes[fileType]) {
6935 fileBrowserCallback = editorSettings.file_picker_callback;
6936 if (fileBrowserCallback && (!fileBrowserCallbackTypes || fileBrowserCallbackTypes[fileType])) {
6937 actionCallback = function () {
6938 var meta = self.fire('beforecall').meta;
6939 meta = global$4.extend({ filetype: fileType }, meta);
6940 fileBrowserCallback.call(editor, function (value, meta) {
6941 self.value(value).fire('change', { meta: meta });
6942 }, self.value(), meta);
6943 };
6944 } else {
6945 fileBrowserCallback = editorSettings.file_browser_callback;
6946 if (fileBrowserCallback && (!fileBrowserCallbackTypes || fileBrowserCallbackTypes[fileType])) {
6947 actionCallback = function () {
6948 fileBrowserCallback(self.getEl('inp').id, self.value(), fileType, window);
6949 };
6950 }
6951 }
6952 }
6953 if (actionCallback) {
6954 settings.icon = 'browse';
6955 settings.onaction = actionCallback;
6956 }
6957 self._super(settings);
6958 self.classes.add('filepicker');
6959 setupAutoCompleteHandler(self, editorSettings, editor.getBody(), fileType);
6960 setupLinkValidatorHandler(self, editorSettings, fileType);
6961 }
6962 });
6963
6964 var FitLayout = AbsoluteLayout.extend({
6965 recalc: function (container) {
6966 var contLayoutRect = container.layoutRect(), paddingBox = container.paddingBox;
6967 container.items().filter(':visible').each(function (ctrl) {
6968 ctrl.layoutRect({
6969 x: paddingBox.left,
6970 y: paddingBox.top,
6971 w: contLayoutRect.innerW - paddingBox.right - paddingBox.left,
6972 h: contLayoutRect.innerH - paddingBox.top - paddingBox.bottom
6973 });
6974 if (ctrl.recalc) {
6975 ctrl.recalc();
6976 }
6977 });
6978 }
6979 });
6980
6981 var FlexLayout = AbsoluteLayout.extend({
6982 recalc: function (container) {
6983 var i, l, items, contLayoutRect, contPaddingBox, contSettings, align, pack, spacing, totalFlex, availableSpace, direction;
6984 var ctrl, ctrlLayoutRect, ctrlSettings, flex;
6985 var maxSizeItems = [];
6986 var size, maxSize, ratio, rect, pos, maxAlignEndPos;
6987 var sizeName, minSizeName, posName, maxSizeName, beforeName, innerSizeName, deltaSizeName, contentSizeName;
6988 var alignAxisName, alignInnerSizeName, alignSizeName, alignMinSizeName, alignBeforeName, alignAfterName;
6989 var alignDeltaSizeName, alignContentSizeName;
6990 var max = Math.max, min = Math.min;
6991 items = container.items().filter(':visible');
6992 contLayoutRect = container.layoutRect();
6993 contPaddingBox = container.paddingBox;
6994 contSettings = container.settings;
6995 direction = container.isRtl() ? contSettings.direction || 'row-reversed' : contSettings.direction;
6996 align = contSettings.align;
6997 pack = container.isRtl() ? contSettings.pack || 'end' : contSettings.pack;
6998 spacing = contSettings.spacing || 0;
6999 if (direction === 'row-reversed' || direction === 'column-reverse') {
7000 items = items.set(items.toArray().reverse());
7001 direction = direction.split('-')[0];
7002 }
7003 if (direction === 'column') {
7004 posName = 'y';
7005 sizeName = 'h';
7006 minSizeName = 'minH';
7007 maxSizeName = 'maxH';
7008 innerSizeName = 'innerH';
7009 beforeName = 'top';
7010 deltaSizeName = 'deltaH';
7011 contentSizeName = 'contentH';
7012 alignBeforeName = 'left';
7013 alignSizeName = 'w';
7014 alignAxisName = 'x';
7015 alignInnerSizeName = 'innerW';
7016 alignMinSizeName = 'minW';
7017 alignAfterName = 'right';
7018 alignDeltaSizeName = 'deltaW';
7019 alignContentSizeName = 'contentW';
7020 } else {
7021 posName = 'x';
7022 sizeName = 'w';
7023 minSizeName = 'minW';
7024 maxSizeName = 'maxW';
7025 innerSizeName = 'innerW';
7026 beforeName = 'left';
7027 deltaSizeName = 'deltaW';
7028 contentSizeName = 'contentW';
7029 alignBeforeName = 'top';
7030 alignSizeName = 'h';
7031 alignAxisName = 'y';
7032 alignInnerSizeName = 'innerH';
7033 alignMinSizeName = 'minH';
7034 alignAfterName = 'bottom';
7035 alignDeltaSizeName = 'deltaH';
7036 alignContentSizeName = 'contentH';
7037 }
7038 availableSpace = contLayoutRect[innerSizeName] - contPaddingBox[beforeName] - contPaddingBox[beforeName];
7039 maxAlignEndPos = totalFlex = 0;
7040 for (i = 0, l = items.length; i < l; i++) {
7041 ctrl = items[i];
7042 ctrlLayoutRect = ctrl.layoutRect();
7043 ctrlSettings = ctrl.settings;
7044 flex = ctrlSettings.flex;
7045 availableSpace -= i < l - 1 ? spacing : 0;
7046 if (flex > 0) {
7047 totalFlex += flex;
7048 if (ctrlLayoutRect[maxSizeName]) {
7049 maxSizeItems.push(ctrl);
7050 }
7051 ctrlLayoutRect.flex = flex;
7052 }
7053 availableSpace -= ctrlLayoutRect[minSizeName];
7054 size = contPaddingBox[alignBeforeName] + ctrlLayoutRect[alignMinSizeName] + contPaddingBox[alignAfterName];
7055 if (size > maxAlignEndPos) {
7056 maxAlignEndPos = size;
7057 }
7058 }
7059 rect = {};
7060 if (availableSpace < 0) {
7061 rect[minSizeName] = contLayoutRect[minSizeName] - availableSpace + contLayoutRect[deltaSizeName];
7062 } else {
7063 rect[minSizeName] = contLayoutRect[innerSizeName] - availableSpace + contLayoutRect[deltaSizeName];
7064 }
7065 rect[alignMinSizeName] = maxAlignEndPos + contLayoutRect[alignDeltaSizeName];
7066 rect[contentSizeName] = contLayoutRect[innerSizeName] - availableSpace;
7067 rect[alignContentSizeName] = maxAlignEndPos;
7068 rect.minW = min(rect.minW, contLayoutRect.maxW);
7069 rect.minH = min(rect.minH, contLayoutRect.maxH);
7070 rect.minW = max(rect.minW, contLayoutRect.startMinWidth);
7071 rect.minH = max(rect.minH, contLayoutRect.startMinHeight);
7072 if (contLayoutRect.autoResize && (rect.minW !== contLayoutRect.minW || rect.minH !== contLayoutRect.minH)) {
7073 rect.w = rect.minW;
7074 rect.h = rect.minH;
7075 container.layoutRect(rect);
7076 this.recalc(container);
7077 if (container._lastRect === null) {
7078 var parentCtrl = container.parent();
7079 if (parentCtrl) {
7080 parentCtrl._lastRect = null;
7081 parentCtrl.recalc();
7082 }
7083 }
7084 return;
7085 }
7086 ratio = availableSpace / totalFlex;
7087 for (i = 0, l = maxSizeItems.length; i < l; i++) {
7088 ctrl = maxSizeItems[i];
7089 ctrlLayoutRect = ctrl.layoutRect();
7090 maxSize = ctrlLayoutRect[maxSizeName];
7091 size = ctrlLayoutRect[minSizeName] + ctrlLayoutRect.flex * ratio;
7092 if (size > maxSize) {
7093 availableSpace -= ctrlLayoutRect[maxSizeName] - ctrlLayoutRect[minSizeName];
7094 totalFlex -= ctrlLayoutRect.flex;
7095 ctrlLayoutRect.flex = 0;
7096 ctrlLayoutRect.maxFlexSize = maxSize;
7097 } else {
7098 ctrlLayoutRect.maxFlexSize = 0;
7099 }
7100 }
7101 ratio = availableSpace / totalFlex;
7102 pos = contPaddingBox[beforeName];
7103 rect = {};
7104 if (totalFlex === 0) {
7105 if (pack === 'end') {
7106 pos = availableSpace + contPaddingBox[beforeName];
7107 } else if (pack === 'center') {
7108 pos = Math.round(contLayoutRect[innerSizeName] / 2 - (contLayoutRect[innerSizeName] - availableSpace) / 2) + contPaddingBox[beforeName];
7109 if (pos < 0) {
7110 pos = contPaddingBox[beforeName];
7111 }
7112 } else if (pack === 'justify') {
7113 pos = contPaddingBox[beforeName];
7114 spacing = Math.floor(availableSpace / (items.length - 1));
7115 }
7116 }
7117 rect[alignAxisName] = contPaddingBox[alignBeforeName];
7118 for (i = 0, l = items.length; i < l; i++) {
7119 ctrl = items[i];
7120 ctrlLayoutRect = ctrl.layoutRect();
7121 size = ctrlLayoutRect.maxFlexSize || ctrlLayoutRect[minSizeName];
7122 if (align === 'center') {
7123 rect[alignAxisName] = Math.round(contLayoutRect[alignInnerSizeName] / 2 - ctrlLayoutRect[alignSizeName] / 2);
7124 } else if (align === 'stretch') {
7125 rect[alignSizeName] = max(ctrlLayoutRect[alignMinSizeName] || 0, contLayoutRect[alignInnerSizeName] - contPaddingBox[alignBeforeName] - contPaddingBox[alignAfterName]);
7126 rect[alignAxisName] = contPaddingBox[alignBeforeName];
7127 } else if (align === 'end') {
7128 rect[alignAxisName] = contLayoutRect[alignInnerSizeName] - ctrlLayoutRect[alignSizeName] - contPaddingBox.top;
7129 }
7130 if (ctrlLayoutRect.flex > 0) {
7131 size += ctrlLayoutRect.flex * ratio;
7132 }
7133 rect[sizeName] = size;
7134 rect[posName] = pos;
7135 ctrl.layoutRect(rect);
7136 if (ctrl.recalc) {
7137 ctrl.recalc();
7138 }
7139 pos += size + spacing;
7140 }
7141 }
7142 });
7143
7144 var FlowLayout = Layout$1.extend({
7145 Defaults: {
7146 containerClass: 'flow-layout',
7147 controlClass: 'flow-layout-item',
7148 endClass: 'break'
7149 },
7150 recalc: function (container) {
7151 container.items().filter(':visible').each(function (ctrl) {
7152 if (ctrl.recalc) {
7153 ctrl.recalc();
7154 }
7155 });
7156 },
7157 isNative: function () {
7158 return true;
7159 }
7160 });
7161
7162 var descendant = function (scope, selector) {
7163 return one(selector, scope);
7164 };
7165
7166 var toggleFormat = function (editor, fmt) {
7167 return function () {
7168 editor.execCommand('mceToggleFormat', false, fmt);
7169 };
7170 };
7171 var addFormatChangedListener = function (editor, name, changed) {
7172 var handler = function (state) {
7173 changed(state, name);
7174 };
7175 if (editor.formatter) {
7176 editor.formatter.formatChanged(name, handler);
7177 } else {
7178 editor.on('init', function () {
7179 editor.formatter.formatChanged(name, handler);
7180 });
7181 }
7182 };
7183 var postRenderFormatToggle = function (editor, name) {
7184 return function (e) {
7185 addFormatChangedListener(editor, name, function (state) {
7186 e.control.active(state);
7187 });
7188 };
7189 };
7190
7191 var register = function (editor) {
7192 var alignFormats = [
7193 'alignleft',
7194 'aligncenter',
7195 'alignright',
7196 'alignjustify'
7197 ];
7198 var defaultAlign = 'alignleft';
7199 var alignMenuItems = [
7200 {
7201 text: 'Left',
7202 icon: 'alignleft',
7203 onclick: toggleFormat(editor, 'alignleft')
7204 },
7205 {
7206 text: 'Center',
7207 icon: 'aligncenter',
7208 onclick: toggleFormat(editor, 'aligncenter')
7209 },
7210 {
7211 text: 'Right',
7212 icon: 'alignright',
7213 onclick: toggleFormat(editor, 'alignright')
7214 },
7215 {
7216 text: 'Justify',
7217 icon: 'alignjustify',
7218 onclick: toggleFormat(editor, 'alignjustify')
7219 }
7220 ];
7221 editor.addMenuItem('align', {
7222 text: 'Align',
7223 menu: alignMenuItems
7224 });
7225 editor.addButton('align', {
7226 type: 'menubutton',
7227 icon: defaultAlign,
7228 menu: alignMenuItems,
7229 onShowMenu: function (e) {
7230 var menu = e.control.menu;
7231 global$4.each(alignFormats, function (formatName, idx) {
7232 menu.items().eq(idx).each(function (item) {
7233 return item.active(editor.formatter.match(formatName));
7234 });
7235 });
7236 },
7237 onPostRender: function (e) {
7238 var ctrl = e.control;
7239 global$4.each(alignFormats, function (formatName, idx) {
7240 addFormatChangedListener(editor, formatName, function (state) {
7241 ctrl.icon(defaultAlign);
7242 if (state) {
7243 ctrl.icon(formatName);
7244 }
7245 });
7246 });
7247 }
7248 });
7249 global$4.each({
7250 alignleft: [
7251 'Align left',
7252 'JustifyLeft'
7253 ],
7254 aligncenter: [
7255 'Align center',
7256 'JustifyCenter'
7257 ],
7258 alignright: [
7259 'Align right',
7260 'JustifyRight'
7261 ],
7262 alignjustify: [
7263 'Justify',
7264 'JustifyFull'
7265 ],
7266 alignnone: [
7267 'No alignment',
7268 'JustifyNone'
7269 ]
7270 }, function (item, name) {
7271 editor.addButton(name, {
7272 active: false,
7273 tooltip: item[0],
7274 cmd: item[1],
7275 onPostRender: postRenderFormatToggle(editor, name)
7276 });
7277 });
7278 };
7279 var Align = { register: register };
7280
7281 var getFirstFont = function (fontFamily) {
7282 return fontFamily ? fontFamily.split(',')[0] : '';
7283 };
7284 var findMatchingValue = function (items, fontFamily) {
7285 var font = fontFamily ? fontFamily.toLowerCase() : '';
7286 var value;
7287 global$4.each(items, function (item) {
7288 if (item.value.toLowerCase() === font) {
7289 value = item.value;
7290 }
7291 });
7292 global$4.each(items, function (item) {
7293 if (!value && getFirstFont(item.value).toLowerCase() === getFirstFont(font).toLowerCase()) {
7294 value = item.value;
7295 }
7296 });
7297 return value;
7298 };
7299 var createFontNameListBoxChangeHandler = function (editor, items) {
7300 return function () {
7301 var self = this;
7302 self.state.set('value', null);
7303 editor.on('init nodeChange', function (e) {
7304 var fontFamily = editor.queryCommandValue('FontName');
7305 var match = findMatchingValue(items, fontFamily);
7306 self.value(match ? match : null);
7307 if (!match && fontFamily) {
7308 self.text(getFirstFont(fontFamily));
7309 }
7310 });
7311 };
7312 };
7313 var createFormats = function (formats) {
7314 formats = formats.replace(/;$/, '').split(';');
7315 var i = formats.length;
7316 while (i--) {
7317 formats[i] = formats[i].split('=');
7318 }
7319 return formats;
7320 };
7321 var getFontItems = function (editor) {
7322 var defaultFontsFormats = 'Andale Mono=andale mono,monospace;' + 'Arial=arial,helvetica,sans-serif;' + 'Arial Black=arial black,sans-serif;' + 'Book Antiqua=book antiqua,palatino,serif;' + 'Comic Sans MS=comic sans ms,sans-serif;' + 'Courier New=courier new,courier,monospace;' + 'Georgia=georgia,palatino,serif;' + 'Helvetica=helvetica,arial,sans-serif;' + 'Impact=impact,sans-serif;' + 'Symbol=symbol;' + 'Tahoma=tahoma,arial,helvetica,sans-serif;' + 'Terminal=terminal,monaco,monospace;' + 'Times New Roman=times new roman,times,serif;' + 'Trebuchet MS=trebuchet ms,geneva,sans-serif;' + 'Verdana=verdana,geneva,sans-serif;' + 'Webdings=webdings;' + 'Wingdings=wingdings,zapf dingbats';
7323 var fonts = createFormats(editor.settings.font_formats || defaultFontsFormats);
7324 return global$4.map(fonts, function (font) {
7325 return {
7326 text: { raw: font[0] },
7327 value: font[1],
7328 textStyle: font[1].indexOf('dings') === -1 ? 'font-family:' + font[1] : ''
7329 };
7330 });
7331 };
7332 var registerButtons = function (editor) {
7333 editor.addButton('fontselect', function () {
7334 var items = getFontItems(editor);
7335 return {
7336 type: 'listbox',
7337 text: 'Font Family',
7338 tooltip: 'Font Family',
7339 values: items,
7340 fixedWidth: true,
7341 onPostRender: createFontNameListBoxChangeHandler(editor, items),
7342 onselect: function (e) {
7343 if (e.control.settings.value) {
7344 editor.execCommand('FontName', false, e.control.settings.value);
7345 }
7346 }
7347 };
7348 });
7349 };
7350 var register$1 = function (editor) {
7351 registerButtons(editor);
7352 };
7353 var FontSelect = { register: register$1 };
7354
7355 var round = function (number, precision) {
7356 var factor = Math.pow(10, precision);
7357 return Math.round(number * factor) / factor;
7358 };
7359 var toPt = function (fontSize, precision) {
7360 if (/[0-9.]+px$/.test(fontSize)) {
7361 return round(parseInt(fontSize, 10) * 72 / 96, precision || 0) + 'pt';
7362 }
7363 return fontSize;
7364 };
7365 var findMatchingValue$1 = function (items, pt, px) {
7366 var value;
7367 global$4.each(items, function (item) {
7368 if (item.value === px) {
7369 value = px;
7370 } else if (item.value === pt) {
7371 value = pt;
7372 }
7373 });
7374 return value;
7375 };
7376 var createFontSizeListBoxChangeHandler = function (editor, items) {
7377 return function () {
7378 var self = this;
7379 editor.on('init nodeChange', function (e) {
7380 var px, pt, precision, match;
7381 px = editor.queryCommandValue('FontSize');
7382 if (px) {
7383 for (precision = 3; !match && precision >= 0; precision--) {
7384 pt = toPt(px, precision);
7385 match = findMatchingValue$1(items, pt, px);
7386 }
7387 }
7388 self.value(match ? match : null);
7389 if (!match) {
7390 self.text(pt);
7391 }
7392 });
7393 };
7394 };
7395 var getFontSizeItems = function (editor) {
7396 var defaultFontsizeFormats = '8pt 10pt 12pt 14pt 18pt 24pt 36pt';
7397 var fontsizeFormats = editor.settings.fontsize_formats || defaultFontsizeFormats;
7398 return global$4.map(fontsizeFormats.split(' '), function (item) {
7399 var text = item, value = item;
7400 var values = item.split('=');
7401 if (values.length > 1) {
7402 text = values[0];
7403 value = values[1];
7404 }
7405 return {
7406 text: text,
7407 value: value
7408 };
7409 });
7410 };
7411 var registerButtons$1 = function (editor) {
7412 editor.addButton('fontsizeselect', function () {
7413 var items = getFontSizeItems(editor);
7414 return {
7415 type: 'listbox',
7416 text: 'Font Sizes',
7417 tooltip: 'Font Sizes',
7418 values: items,
7419 fixedWidth: true,
7420 onPostRender: createFontSizeListBoxChangeHandler(editor, items),
7421 onclick: function (e) {
7422 if (e.control.settings.value) {
7423 editor.execCommand('FontSize', false, e.control.settings.value);
7424 }
7425 }
7426 };
7427 });
7428 };
7429 var register$2 = function (editor) {
7430 registerButtons$1(editor);
7431 };
7432 var FontSizeSelect = { register: register$2 };
7433
7434 var hideMenuObjects = function (editor, menu) {
7435 var count = menu.length;
7436 global$4.each(menu, function (item) {
7437 if (item.menu) {
7438 item.hidden = hideMenuObjects(editor, item.menu) === 0;
7439 }
7440 var formatName = item.format;
7441 if (formatName) {
7442 item.hidden = !editor.formatter.canApply(formatName);
7443 }
7444 if (item.hidden) {
7445 count--;
7446 }
7447 });
7448 return count;
7449 };
7450 var hideFormatMenuItems = function (editor, menu) {
7451 var count = menu.items().length;
7452 menu.items().each(function (item) {
7453 if (item.menu) {
7454 item.visible(hideFormatMenuItems(editor, item.menu) > 0);
7455 }
7456 if (!item.menu && item.settings.menu) {
7457 item.visible(hideMenuObjects(editor, item.settings.menu) > 0);
7458 }
7459 var formatName = item.settings.format;
7460 if (formatName) {
7461 item.visible(editor.formatter.canApply(formatName));
7462 }
7463 if (!item.visible()) {
7464 count--;
7465 }
7466 });
7467 return count;
7468 };
7469 var createFormatMenu = function (editor) {
7470 var count = 0;
7471 var newFormats = [];
7472 var defaultStyleFormats = [
7473 {
7474 title: 'Headings',
7475 items: [
7476 {
7477 title: 'Heading 1',
7478 format: 'h1'
7479 },
7480 {
7481 title: 'Heading 2',
7482 format: 'h2'
7483 },
7484 {
7485 title: 'Heading 3',
7486 format: 'h3'
7487 },
7488 {
7489 title: 'Heading 4',
7490 format: 'h4'
7491 },
7492 {
7493 title: 'Heading 5',
7494 format: 'h5'
7495 },
7496 {
7497 title: 'Heading 6',
7498 format: 'h6'
7499 }
7500 ]
7501 },
7502 {
7503 title: 'Inline',
7504 items: [
7505 {
7506 title: 'Bold',
7507 icon: 'bold',
7508 format: 'bold'
7509 },
7510 {
7511 title: 'Italic',
7512 icon: 'italic',
7513 format: 'italic'
7514 },
7515 {
7516 title: 'Underline',
7517 icon: 'underline',
7518 format: 'underline'
7519 },
7520 {
7521 title: 'Strikethrough',
7522 icon: 'strikethrough',
7523 format: 'strikethrough'
7524 },
7525 {
7526 title: 'Superscript',
7527 icon: 'superscript',
7528 format: 'superscript'
7529 },
7530 {
7531 title: 'Subscript',
7532 icon: 'subscript',
7533 format: 'subscript'
7534 },
7535 {
7536 title: 'Code',
7537 icon: 'code',
7538 format: 'code'
7539 }
7540 ]
7541 },
7542 {
7543 title: 'Blocks',
7544 items: [
7545 {
7546 title: 'Paragraph',
7547 format: 'p'
7548 },
7549 {
7550 title: 'Blockquote',
7551 format: 'blockquote'
7552 },
7553 {
7554 title: 'Div',
7555 format: 'div'
7556 },
7557 {
7558 title: 'Pre',
7559 format: 'pre'
7560 }
7561 ]
7562 },
7563 {
7564 title: 'Alignment',
7565 items: [
7566 {
7567 title: 'Left',
7568 icon: 'alignleft',
7569 format: 'alignleft'
7570 },
7571 {
7572 title: 'Center',
7573 icon: 'aligncenter',
7574 format: 'aligncenter'
7575 },
7576 {
7577 title: 'Right',
7578 icon: 'alignright',
7579 format: 'alignright'
7580 },
7581 {
7582 title: 'Justify',
7583 icon: 'alignjustify',
7584 format: 'alignjustify'
7585 }
7586 ]
7587 }
7588 ];
7589 var createMenu = function (formats) {
7590 var menu = [];
7591 if (!formats) {
7592 return;
7593 }
7594 global$4.each(formats, function (format) {
7595 var menuItem = {
7596 text: format.title,
7597 icon: format.icon
7598 };
7599 if (format.items) {
7600 menuItem.menu = createMenu(format.items);
7601 } else {
7602 var formatName = format.format || 'custom' + count++;
7603 if (!format.format) {
7604 format.name = formatName;
7605 newFormats.push(format);
7606 }
7607 menuItem.format = formatName;
7608 menuItem.cmd = format.cmd;
7609 }
7610 menu.push(menuItem);
7611 });
7612 return menu;
7613 };
7614 var createStylesMenu = function () {
7615 var menu;
7616 if (editor.settings.style_formats_merge) {
7617 if (editor.settings.style_formats) {
7618 menu = createMenu(defaultStyleFormats.concat(editor.settings.style_formats));
7619 } else {
7620 menu = createMenu(defaultStyleFormats);
7621 }
7622 } else {
7623 menu = createMenu(editor.settings.style_formats || defaultStyleFormats);
7624 }
7625 return menu;
7626 };
7627 editor.on('init', function () {
7628 global$4.each(newFormats, function (format) {
7629 editor.formatter.register(format.name, format);
7630 });
7631 });
7632 return {
7633 type: 'menu',
7634 items: createStylesMenu(),
7635 onPostRender: function (e) {
7636 editor.fire('renderFormatsMenu', { control: e.control });
7637 },
7638 itemDefaults: {
7639 preview: true,
7640 textStyle: function () {
7641 if (this.settings.format) {
7642 return editor.formatter.getCssText(this.settings.format);
7643 }
7644 },
7645 onPostRender: function () {
7646 var self = this;
7647 self.parent().on('show', function () {
7648 var formatName, command;
7649 formatName = self.settings.format;
7650 if (formatName) {
7651 self.disabled(!editor.formatter.canApply(formatName));
7652 self.active(editor.formatter.match(formatName));
7653 }
7654 command = self.settings.cmd;
7655 if (command) {
7656 self.active(editor.queryCommandState(command));
7657 }
7658 });
7659 },
7660 onclick: function () {
7661 if (this.settings.format) {
7662 toggleFormat(editor, this.settings.format)();
7663 }
7664 if (this.settings.cmd) {
7665 editor.execCommand(this.settings.cmd);
7666 }
7667 }
7668 }
7669 };
7670 };
7671 var registerMenuItems = function (editor, formatMenu) {
7672 editor.addMenuItem('formats', {
7673 text: 'Formats',
7674 menu: formatMenu
7675 });
7676 };
7677 var registerButtons$2 = function (editor, formatMenu) {
7678 editor.addButton('styleselect', {
7679 type: 'menubutton',
7680 text: 'Formats',
7681 menu: formatMenu,
7682 onShowMenu: function () {
7683 if (editor.settings.style_formats_autohide) {
7684 hideFormatMenuItems(editor, this.menu);
7685 }
7686 }
7687 });
7688 };
7689 var register$3 = function (editor) {
7690 var formatMenu = createFormatMenu(editor);
7691 registerMenuItems(editor, formatMenu);
7692 registerButtons$2(editor, formatMenu);
7693 };
7694 var Formats = { register: register$3 };
7695
7696 var defaultBlocks = 'Paragraph=p;' + 'Heading 1=h1;' + 'Heading 2=h2;' + 'Heading 3=h3;' + 'Heading 4=h4;' + 'Heading 5=h5;' + 'Heading 6=h6;' + 'Preformatted=pre';
7697 var createFormats$1 = function (formats) {
7698 formats = formats.replace(/;$/, '').split(';');
7699 var i = formats.length;
7700 while (i--) {
7701 formats[i] = formats[i].split('=');
7702 }
7703 return formats;
7704 };
7705 var createListBoxChangeHandler = function (editor, items, formatName) {
7706 return function () {
7707 var self = this;
7708 editor.on('nodeChange', function (e) {
7709 var formatter = editor.formatter;
7710 var value = null;
7711 global$4.each(e.parents, function (node) {
7712 global$4.each(items, function (item) {
7713 if (formatName) {
7714 if (formatter.matchNode(node, formatName, { value: item.value })) {
7715 value = item.value;
7716 }
7717 } else {
7718 if (formatter.matchNode(node, item.value)) {
7719 value = item.value;
7720 }
7721 }
7722 if (value) {
7723 return false;
7724 }
7725 });
7726 if (value) {
7727 return false;
7728 }
7729 });
7730 self.value(value);
7731 });
7732 };
7733 };
7734 var lazyFormatSelectBoxItems = function (editor, blocks) {
7735 return function () {
7736 var items = [];
7737 global$4.each(blocks, function (block) {
7738 items.push({
7739 text: block[0],
7740 value: block[1],
7741 textStyle: function () {
7742 return editor.formatter.getCssText(block[1]);
7743 }
7744 });
7745 });
7746 return {
7747 type: 'listbox',
7748 text: blocks[0][0],
7749 values: items,
7750 fixedWidth: true,
7751 onselect: function (e) {
7752 if (e.control) {
7753 var fmt = e.control.value();
7754 toggleFormat(editor, fmt)();
7755 }
7756 },
7757 onPostRender: createListBoxChangeHandler(editor, items)
7758 };
7759 };
7760 };
7761 var buildMenuItems = function (editor, blocks) {
7762 return global$4.map(blocks, function (block) {
7763 return {
7764 text: block[0],
7765 onclick: toggleFormat(editor, block[1]),
7766 textStyle: function () {
7767 return editor.formatter.getCssText(block[1]);
7768 }
7769 };
7770 });
7771 };
7772 var register$4 = function (editor) {
7773 var blocks = createFormats$1(editor.settings.block_formats || defaultBlocks);
7774 editor.addMenuItem('blockformats', {
7775 text: 'Blocks',
7776 menu: buildMenuItems(editor, blocks)
7777 });
7778 editor.addButton('formatselect', lazyFormatSelectBoxItems(editor, blocks));
7779 };
7780 var FormatSelect = { register: register$4 };
7781
7782 var createCustomMenuItems = function (editor, names) {
7783 var items, nameList;
7784 if (typeof names === 'string') {
7785 nameList = names.split(' ');
7786 } else if (global$4.isArray(names)) {
7787 return flatten$1(global$4.map(names, function (names) {
7788 return createCustomMenuItems(editor, names);
7789 }));
7790 }
7791 items = global$4.grep(nameList, function (name) {
7792 return name === '|' || name in editor.menuItems;
7793 });
7794 return global$4.map(items, function (name) {
7795 return name === '|' ? { text: '-' } : editor.menuItems[name];
7796 });
7797 };
7798 var isSeparator = function (menuItem) {
7799 return menuItem && menuItem.text === '-';
7800 };
7801 var trimMenuItems = function (menuItems) {
7802 var menuItems2 = filter(menuItems, function (menuItem, i) {
7803 return !isSeparator(menuItem) || !isSeparator(menuItems[i - 1]);
7804 });
7805 return filter(menuItems2, function (menuItem, i) {
7806 return !isSeparator(menuItem) || i > 0 && i < menuItems2.length - 1;
7807 });
7808 };
7809 var createContextMenuItems = function (editor, context) {
7810 var outputMenuItems = [{ text: '-' }];
7811 var menuItems = global$4.grep(editor.menuItems, function (menuItem) {
7812 return menuItem.context === context;
7813 });
7814 global$4.each(menuItems, function (menuItem) {
7815 if (menuItem.separator === 'before') {
7816 outputMenuItems.push({ text: '|' });
7817 }
7818 if (menuItem.prependToContext) {
7819 outputMenuItems.unshift(menuItem);
7820 } else {
7821 outputMenuItems.push(menuItem);
7822 }
7823 if (menuItem.separator === 'after') {
7824 outputMenuItems.push({ text: '|' });
7825 }
7826 });
7827 return outputMenuItems;
7828 };
7829 var createInsertMenu = function (editor) {
7830 var insertButtonItems = editor.settings.insert_button_items;
7831 if (insertButtonItems) {
7832 return trimMenuItems(createCustomMenuItems(editor, insertButtonItems));
7833 } else {
7834 return trimMenuItems(createContextMenuItems(editor, 'insert'));
7835 }
7836 };
7837 var registerButtons$3 = function (editor) {
7838 editor.addButton('insert', {
7839 type: 'menubutton',
7840 icon: 'insert',
7841 menu: [],
7842 oncreatemenu: function () {
7843 this.menu.add(createInsertMenu(editor));
7844 this.menu.renderNew();
7845 }
7846 });
7847 };
7848 var register$5 = function (editor) {
7849 registerButtons$3(editor);
7850 };
7851 var InsertButton = { register: register$5 };
7852
7853 var registerFormatButtons = function (editor) {
7854 global$4.each({
7855 bold: 'Bold',
7856 italic: 'Italic',
7857 underline: 'Underline',
7858 strikethrough: 'Strikethrough',
7859 subscript: 'Subscript',
7860 superscript: 'Superscript'
7861 }, function (text, name) {
7862 editor.addButton(name, {
7863 active: false,
7864 tooltip: text,
7865 onPostRender: postRenderFormatToggle(editor, name),
7866 onclick: toggleFormat(editor, name)
7867 });
7868 });
7869 };
7870 var registerCommandButtons = function (editor) {
7871 global$4.each({
7872 outdent: [
7873 'Decrease indent',
7874 'Outdent'
7875 ],
7876 indent: [
7877 'Increase indent',
7878 'Indent'
7879 ],
7880 cut: [
7881 'Cut',
7882 'Cut'
7883 ],
7884 copy: [
7885 'Copy',
7886 'Copy'
7887 ],
7888 paste: [
7889 'Paste',
7890 'Paste'
7891 ],
7892 help: [
7893 'Help',
7894 'mceHelp'
7895 ],
7896 selectall: [
7897 'Select all',
7898 'SelectAll'
7899 ],
7900 visualaid: [
7901 'Visual aids',
7902 'mceToggleVisualAid'
7903 ],
7904 newdocument: [
7905 'New document',
7906 'mceNewDocument'
7907 ],
7908 removeformat: [
7909 'Clear formatting',
7910 'RemoveFormat'
7911 ],
7912 remove: [
7913 'Remove',
7914 'Delete'
7915 ]
7916 }, function (item, name) {
7917 editor.addButton(name, {
7918 tooltip: item[0],
7919 cmd: item[1]
7920 });
7921 });
7922 };
7923 var registerCommandToggleButtons = function (editor) {
7924 global$4.each({
7925 blockquote: [
7926 'Blockquote',
7927 'mceBlockQuote'
7928 ],
7929 subscript: [
7930 'Subscript',
7931 'Subscript'
7932 ],
7933 superscript: [
7934 'Superscript',
7935 'Superscript'
7936 ]
7937 }, function (item, name) {
7938 editor.addButton(name, {
7939 active: false,
7940 tooltip: item[0],
7941 cmd: item[1],
7942 onPostRender: postRenderFormatToggle(editor, name)
7943 });
7944 });
7945 };
7946 var registerButtons$4 = function (editor) {
7947 registerFormatButtons(editor);
7948 registerCommandButtons(editor);
7949 registerCommandToggleButtons(editor);
7950 };
7951 var registerMenuItems$1 = function (editor) {
7952 global$4.each({
7953 bold: [
7954 'Bold',
7955 'Bold',
7956 'Meta+B'
7957 ],
7958 italic: [
7959 'Italic',
7960 'Italic',
7961 'Meta+I'
7962 ],
7963 underline: [
7964 'Underline',
7965 'Underline',
7966 'Meta+U'
7967 ],
7968 strikethrough: [
7969 'Strikethrough',
7970 'Strikethrough'
7971 ],
7972 subscript: [
7973 'Subscript',
7974 'Subscript'
7975 ],
7976 superscript: [
7977 'Superscript',
7978 'Superscript'
7979 ],
7980 removeformat: [
7981 'Clear formatting',
7982 'RemoveFormat'
7983 ],
7984 newdocument: [
7985 'New document',
7986 'mceNewDocument'
7987 ],
7988 cut: [
7989 'Cut',
7990 'Cut',
7991 'Meta+X'
7992 ],
7993 copy: [
7994 'Copy',
7995 'Copy',
7996 'Meta+C'
7997 ],
7998 paste: [
7999 'Paste',
8000 'Paste',
8001 'Meta+V'
8002 ],
8003 selectall: [
8004 'Select all',
8005 'SelectAll',
8006 'Meta+A'
8007 ]
8008 }, function (item, name) {
8009 editor.addMenuItem(name, {
8010 text: item[0],
8011 icon: name,
8012 shortcut: item[2],
8013 cmd: item[1]
8014 });
8015 });
8016 editor.addMenuItem('codeformat', {
8017 text: 'Code',
8018 icon: 'code',
8019 onclick: toggleFormat(editor, 'code')
8020 });
8021 };
8022 var register$6 = function (editor) {
8023 registerButtons$4(editor);
8024 registerMenuItems$1(editor);
8025 };
8026 var SimpleControls = { register: register$6 };
8027
8028 var toggleUndoRedoState = function (editor, type) {
8029 return function () {
8030 var self = this;
8031 var checkState = function () {
8032 var typeFn = type === 'redo' ? 'hasRedo' : 'hasUndo';
8033 return editor.undoManager ? editor.undoManager[typeFn]() : false;
8034 };
8035 self.disabled(!checkState());
8036 editor.on('Undo Redo AddUndo TypingUndo ClearUndos SwitchMode', function () {
8037 self.disabled(editor.readonly || !checkState());
8038 });
8039 };
8040 };
8041 var registerMenuItems$2 = function (editor) {
8042 editor.addMenuItem('undo', {
8043 text: 'Undo',
8044 icon: 'undo',
8045 shortcut: 'Meta+Z',
8046 onPostRender: toggleUndoRedoState(editor, 'undo'),
8047 cmd: 'undo'
8048 });
8049 editor.addMenuItem('redo', {
8050 text: 'Redo',
8051 icon: 'redo',
8052 shortcut: 'Meta+Y',
8053 onPostRender: toggleUndoRedoState(editor, 'redo'),
8054 cmd: 'redo'
8055 });
8056 };
8057 var registerButtons$5 = function (editor) {
8058 editor.addButton('undo', {
8059 tooltip: 'Undo',
8060 onPostRender: toggleUndoRedoState(editor, 'undo'),
8061 cmd: 'undo'
8062 });
8063 editor.addButton('redo', {
8064 tooltip: 'Redo',
8065 onPostRender: toggleUndoRedoState(editor, 'redo'),
8066 cmd: 'redo'
8067 });
8068 };
8069 var register$7 = function (editor) {
8070 registerMenuItems$2(editor);
8071 registerButtons$5(editor);
8072 };
8073 var UndoRedo = { register: register$7 };
8074
8075 var toggleVisualAidState = function (editor) {
8076 return function () {
8077 var self = this;
8078 editor.on('VisualAid', function (e) {
8079 self.active(e.hasVisual);
8080 });
8081 self.active(editor.hasVisual);
8082 };
8083 };
8084 var registerMenuItems$3 = function (editor) {
8085 editor.addMenuItem('visualaid', {
8086 text: 'Visual aids',
8087 selectable: true,
8088 onPostRender: toggleVisualAidState(editor),
8089 cmd: 'mceToggleVisualAid'
8090 });
8091 };
8092 var register$8 = function (editor) {
8093 registerMenuItems$3(editor);
8094 };
8095 var VisualAid = { register: register$8 };
8096
8097 var setupEnvironment = function () {
8098 Widget.tooltips = !global$1.iOS;
8099 Control$1.translate = function (text) {
8100 return global$5.translate(text);
8101 };
8102 };
8103 var setupUiContainer = function (editor) {
8104 if (editor.settings.ui_container) {
8105 global$1.container = descendant(Element.fromDom(domGlobals.document.body), editor.settings.ui_container).fold(constant(null), function (elm) {
8106 return elm.dom();
8107 });
8108 }
8109 };
8110 var setupRtlMode = function (editor) {
8111 if (editor.rtl) {
8112 Control$1.rtl = true;
8113 }
8114 };
8115 var setupHideFloatPanels = function (editor) {
8116 editor.on('mousedown progressstate', function () {
8117 FloatPanel.hideAll();
8118 });
8119 };
8120 var setup = function (editor) {
8121 setupRtlMode(editor);
8122 setupHideFloatPanels(editor);
8123 setupUiContainer(editor);
8124 setupEnvironment();
8125 FormatSelect.register(editor);
8126 Align.register(editor);
8127 SimpleControls.register(editor);
8128 UndoRedo.register(editor);
8129 FontSizeSelect.register(editor);
8130 FontSelect.register(editor);
8131 Formats.register(editor);
8132 VisualAid.register(editor);
8133 InsertButton.register(editor);
8134 };
8135 var FormatControls = { setup: setup };
8136
8137 var GridLayout = AbsoluteLayout.extend({
8138 recalc: function (container) {
8139 var settings, rows, cols, items, contLayoutRect, width, height, rect, ctrlLayoutRect, ctrl, x, y, posX, posY, ctrlSettings, contPaddingBox, align, spacingH, spacingV, alignH, alignV, maxX, maxY;
8140 var colWidths = [];
8141 var rowHeights = [];
8142 var ctrlMinWidth, ctrlMinHeight, availableWidth, availableHeight, reverseRows, idx;
8143 settings = container.settings;
8144 items = container.items().filter(':visible');
8145 contLayoutRect = container.layoutRect();
8146 cols = settings.columns || Math.ceil(Math.sqrt(items.length));
8147 rows = Math.ceil(items.length / cols);
8148 spacingH = settings.spacingH || settings.spacing || 0;
8149 spacingV = settings.spacingV || settings.spacing || 0;
8150 alignH = settings.alignH || settings.align;
8151 alignV = settings.alignV || settings.align;
8152 contPaddingBox = container.paddingBox;
8153 reverseRows = 'reverseRows' in settings ? settings.reverseRows : container.isRtl();
8154 if (alignH && typeof alignH === 'string') {
8155 alignH = [alignH];
8156 }
8157 if (alignV && typeof alignV === 'string') {
8158 alignV = [alignV];
8159 }
8160 for (x = 0; x < cols; x++) {
8161 colWidths.push(0);
8162 }
8163 for (y = 0; y < rows; y++) {
8164 rowHeights.push(0);
8165 }
8166 for (y = 0; y < rows; y++) {
8167 for (x = 0; x < cols; x++) {
8168 ctrl = items[y * cols + x];
8169 if (!ctrl) {
8170 break;
8171 }
8172 ctrlLayoutRect = ctrl.layoutRect();
8173 ctrlMinWidth = ctrlLayoutRect.minW;
8174 ctrlMinHeight = ctrlLayoutRect.minH;
8175 colWidths[x] = ctrlMinWidth > colWidths[x] ? ctrlMinWidth : colWidths[x];
8176 rowHeights[y] = ctrlMinHeight > rowHeights[y] ? ctrlMinHeight : rowHeights[y];
8177 }
8178 }
8179 availableWidth = contLayoutRect.innerW - contPaddingBox.left - contPaddingBox.right;
8180 for (maxX = 0, x = 0; x < cols; x++) {
8181 maxX += colWidths[x] + (x > 0 ? spacingH : 0);
8182 availableWidth -= (x > 0 ? spacingH : 0) + colWidths[x];
8183 }
8184 availableHeight = contLayoutRect.innerH - contPaddingBox.top - contPaddingBox.bottom;
8185 for (maxY = 0, y = 0; y < rows; y++) {
8186 maxY += rowHeights[y] + (y > 0 ? spacingV : 0);
8187 availableHeight -= (y > 0 ? spacingV : 0) + rowHeights[y];
8188 }
8189 maxX += contPaddingBox.left + contPaddingBox.right;
8190 maxY += contPaddingBox.top + contPaddingBox.bottom;
8191 rect = {};
8192 rect.minW = maxX + (contLayoutRect.w - contLayoutRect.innerW);
8193 rect.minH = maxY + (contLayoutRect.h - contLayoutRect.innerH);
8194 rect.contentW = rect.minW - contLayoutRect.deltaW;
8195 rect.contentH = rect.minH - contLayoutRect.deltaH;
8196 rect.minW = Math.min(rect.minW, contLayoutRect.maxW);
8197 rect.minH = Math.min(rect.minH, contLayoutRect.maxH);
8198 rect.minW = Math.max(rect.minW, contLayoutRect.startMinWidth);
8199 rect.minH = Math.max(rect.minH, contLayoutRect.startMinHeight);
8200 if (contLayoutRect.autoResize && (rect.minW !== contLayoutRect.minW || rect.minH !== contLayoutRect.minH)) {
8201 rect.w = rect.minW;
8202 rect.h = rect.minH;
8203 container.layoutRect(rect);
8204 this.recalc(container);
8205 if (container._lastRect === null) {
8206 var parentCtrl = container.parent();
8207 if (parentCtrl) {
8208 parentCtrl._lastRect = null;
8209 parentCtrl.recalc();
8210 }
8211 }
8212 return;
8213 }
8214 if (contLayoutRect.autoResize) {
8215 rect = container.layoutRect(rect);
8216 rect.contentW = rect.minW - contLayoutRect.deltaW;
8217 rect.contentH = rect.minH - contLayoutRect.deltaH;
8218 }
8219 var flexV;
8220 if (settings.packV === 'start') {
8221 flexV = 0;
8222 } else {
8223 flexV = availableHeight > 0 ? Math.floor(availableHeight / rows) : 0;
8224 }
8225 var totalFlex = 0;
8226 var flexWidths = settings.flexWidths;
8227 if (flexWidths) {
8228 for (x = 0; x < flexWidths.length; x++) {
8229 totalFlex += flexWidths[x];
8230 }
8231 } else {
8232 totalFlex = cols;
8233 }
8234 var ratio = availableWidth / totalFlex;
8235 for (x = 0; x < cols; x++) {
8236 colWidths[x] += flexWidths ? flexWidths[x] * ratio : ratio;
8237 }
8238 posY = contPaddingBox.top;
8239 for (y = 0; y < rows; y++) {
8240 posX = contPaddingBox.left;
8241 height = rowHeights[y] + flexV;
8242 for (x = 0; x < cols; x++) {
8243 if (reverseRows) {
8244 idx = y * cols + cols - 1 - x;
8245 } else {
8246 idx = y * cols + x;
8247 }
8248 ctrl = items[idx];
8249 if (!ctrl) {
8250 break;
8251 }
8252 ctrlSettings = ctrl.settings;
8253 ctrlLayoutRect = ctrl.layoutRect();
8254 width = Math.max(colWidths[x], ctrlLayoutRect.startMinWidth);
8255 ctrlLayoutRect.x = posX;
8256 ctrlLayoutRect.y = posY;
8257 align = ctrlSettings.alignH || (alignH ? alignH[x] || alignH[0] : null);
8258 if (align === 'center') {
8259 ctrlLayoutRect.x = posX + width / 2 - ctrlLayoutRect.w / 2;
8260 } else if (align === 'right') {
8261 ctrlLayoutRect.x = posX + width - ctrlLayoutRect.w;
8262 } else if (align === 'stretch') {
8263 ctrlLayoutRect.w = width;
8264 }
8265 align = ctrlSettings.alignV || (alignV ? alignV[x] || alignV[0] : null);
8266 if (align === 'center') {
8267 ctrlLayoutRect.y = posY + height / 2 - ctrlLayoutRect.h / 2;
8268 } else if (align === 'bottom') {
8269 ctrlLayoutRect.y = posY + height - ctrlLayoutRect.h;
8270 } else if (align === 'stretch') {
8271 ctrlLayoutRect.h = height;
8272 }
8273 ctrl.layoutRect(ctrlLayoutRect);
8274 posX += width + spacingH;
8275 if (ctrl.recalc) {
8276 ctrl.recalc();
8277 }
8278 }
8279 posY += height + spacingV;
8280 }
8281 }
8282 });
8283
8284 var Iframe = Widget.extend({
8285 renderHtml: function () {
8286 var self = this;
8287 self.classes.add('iframe');
8288 self.canFocus = false;
8289 return '<iframe id="' + self._id + '" class="' + self.classes + '" tabindex="-1" src="' + (self.settings.url || 'javascript:\'\'') + '" frameborder="0"></iframe>';
8290 },
8291 src: function (src) {
8292 this.getEl().src = src;
8293 },
8294 html: function (html, callback) {
8295 var self = this, body = this.getEl().contentWindow.document.body;
8296 if (!body) {
8297 global$3.setTimeout(function () {
8298 self.html(html);
8299 });
8300 } else {
8301 body.innerHTML = html;
8302 if (callback) {
8303 callback();
8304 }
8305 }
8306 return this;
8307 }
8308 });
8309
8310 var InfoBox = Widget.extend({
8311 init: function (settings) {
8312 var self = this;
8313 self._super(settings);
8314 self.classes.add('widget').add('infobox');
8315 self.canFocus = false;
8316 },
8317 severity: function (level) {
8318 this.classes.remove('error');
8319 this.classes.remove('warning');
8320 this.classes.remove('success');
8321 this.classes.add(level);
8322 },
8323 help: function (state) {
8324 this.state.set('help', state);
8325 },
8326 renderHtml: function () {
8327 var self = this, prefix = self.classPrefix;
8328 return '<div id="' + self._id + '" class="' + self.classes + '">' + '<div id="' + self._id + '-body">' + self.encode(self.state.get('text')) + '<button role="button" tabindex="-1">' + '<i class="' + prefix + 'ico ' + prefix + 'i-help"></i>' + '</button>' + '</div>' + '</div>';
8329 },
8330 bindStates: function () {
8331 var self = this;
8332 self.state.on('change:text', function (e) {
8333 self.getEl('body').firstChild.data = self.encode(e.value);
8334 if (self.state.get('rendered')) {
8335 self.updateLayoutRect();
8336 }
8337 });
8338 self.state.on('change:help', function (e) {
8339 self.classes.toggle('has-help', e.value);
8340 if (self.state.get('rendered')) {
8341 self.updateLayoutRect();
8342 }
8343 });
8344 return self._super();
8345 }
8346 });
8347
8348 var Label = Widget.extend({
8349 init: function (settings) {
8350 var self = this;
8351 self._super(settings);
8352 self.classes.add('widget').add('label');
8353 self.canFocus = false;
8354 if (settings.multiline) {
8355 self.classes.add('autoscroll');
8356 }
8357 if (settings.strong) {
8358 self.classes.add('strong');
8359 }
8360 },
8361 initLayoutRect: function () {
8362 var self = this, layoutRect = self._super();
8363 if (self.settings.multiline) {
8364 var size = funcs.getSize(self.getEl());
8365 if (size.width > layoutRect.maxW) {
8366 layoutRect.minW = layoutRect.maxW;
8367 self.classes.add('multiline');
8368 }
8369 self.getEl().style.width = layoutRect.minW + 'px';
8370 layoutRect.startMinH = layoutRect.h = layoutRect.minH = Math.min(layoutRect.maxH, funcs.getSize(self.getEl()).height);
8371 }
8372 return layoutRect;
8373 },
8374 repaint: function () {
8375 var self = this;
8376 if (!self.settings.multiline) {
8377 self.getEl().style.lineHeight = self.layoutRect().h + 'px';
8378 }
8379 return self._super();
8380 },
8381 severity: function (level) {
8382 this.classes.remove('error');
8383 this.classes.remove('warning');
8384 this.classes.remove('success');
8385 this.classes.add(level);
8386 },
8387 renderHtml: function () {
8388 var self = this;
8389 var targetCtrl, forName, forId = self.settings.forId;
8390 var text = self.settings.html ? self.settings.html : self.encode(self.state.get('text'));
8391 if (!forId && (forName = self.settings.forName)) {
8392 targetCtrl = self.getRoot().find('#' + forName)[0];
8393 if (targetCtrl) {
8394 forId = targetCtrl._id;
8395 }
8396 }
8397 if (forId) {
8398 return '<label id="' + self._id + '" class="' + self.classes + '"' + (forId ? ' for="' + forId + '"' : '') + '>' + text + '</label>';
8399 }
8400 return '<span id="' + self._id + '" class="' + self.classes + '">' + text + '</span>';
8401 },
8402 bindStates: function () {
8403 var self = this;
8404 self.state.on('change:text', function (e) {
8405 self.innerHtml(self.encode(e.value));
8406 if (self.state.get('rendered')) {
8407 self.updateLayoutRect();
8408 }
8409 });
8410 return self._super();
8411 }
8412 });
8413
8414 var Toolbar$1 = Container.extend({
8415 Defaults: {
8416 role: 'toolbar',
8417 layout: 'flow'
8418 },
8419 init: function (settings) {
8420 var self = this;
8421 self._super(settings);
8422 self.classes.add('toolbar');
8423 },
8424 postRender: function () {
8425 var self = this;
8426 self.items().each(function (ctrl) {
8427 ctrl.classes.add('toolbar-item');
8428 });
8429 return self._super();
8430 }
8431 });
8432
8433 var MenuBar = Toolbar$1.extend({
8434 Defaults: {
8435 role: 'menubar',
8436 containerCls: 'menubar',
8437 ariaRoot: true,
8438 defaults: { type: 'menubutton' }
8439 }
8440 });
8441
8442 function isChildOf$1(node, parent) {
8443 while (node) {
8444 if (parent === node) {
8445 return true;
8446 }
8447 node = node.parentNode;
8448 }
8449 return false;
8450 }
8451 var MenuButton = Button.extend({
8452 init: function (settings) {
8453 var self = this;
8454 self._renderOpen = true;
8455 self._super(settings);
8456 settings = self.settings;
8457 self.classes.add('menubtn');
8458 if (settings.fixedWidth) {
8459 self.classes.add('fixed-width');
8460 }
8461 self.aria('haspopup', true);
8462 self.state.set('menu', settings.menu || self.render());
8463 },
8464 showMenu: function (toggle) {
8465 var self = this;
8466 var menu;
8467 if (self.menu && self.menu.visible() && toggle !== false) {
8468 return self.hideMenu();
8469 }
8470 if (!self.menu) {
8471 menu = self.state.get('menu') || [];
8472 self.classes.add('opened');
8473 if (menu.length) {
8474 menu = {
8475 type: 'menu',
8476 animate: true,
8477 items: menu
8478 };
8479 } else {
8480 menu.type = menu.type || 'menu';
8481 menu.animate = true;
8482 }
8483 if (!menu.renderTo) {
8484 self.menu = global$b.create(menu).parent(self).renderTo();
8485 } else {
8486 self.menu = menu.parent(self).show().renderTo();
8487 }
8488 self.fire('createmenu');
8489 self.menu.reflow();
8490 self.menu.on('cancel', function (e) {
8491 if (e.control.parent() === self.menu) {
8492 e.stopPropagation();
8493 self.focus();
8494 self.hideMenu();
8495 }
8496 });
8497 self.menu.on('select', function () {
8498 self.focus();
8499 });
8500 self.menu.on('show hide', function (e) {
8501 if (e.type === 'hide' && e.control.parent() === self) {
8502 self.classes.remove('opened-under');
8503 }
8504 if (e.control === self.menu) {
8505 self.activeMenu(e.type === 'show');
8506 self.classes.toggle('opened', e.type === 'show');
8507 }
8508 self.aria('expanded', e.type === 'show');
8509 }).fire('show');
8510 }
8511 self.menu.show();
8512 self.menu.layoutRect({ w: self.layoutRect().w });
8513 self.menu.repaint();
8514 self.menu.moveRel(self.getEl(), self.isRtl() ? [
8515 'br-tr',
8516 'tr-br'
8517 ] : [
8518 'bl-tl',
8519 'tl-bl'
8520 ]);
8521 var menuLayoutRect = self.menu.layoutRect();
8522 var selfBottom = self.$el.offset().top + self.layoutRect().h;
8523 if (selfBottom > menuLayoutRect.y && selfBottom < menuLayoutRect.y + menuLayoutRect.h) {
8524 self.classes.add('opened-under');
8525 }
8526 self.fire('showmenu');
8527 },
8528 hideMenu: function () {
8529 var self = this;
8530 if (self.menu) {
8531 self.menu.items().each(function (item) {
8532 if (item.hideMenu) {
8533 item.hideMenu();
8534 }
8535 });
8536 self.menu.hide();
8537 }
8538 },
8539 activeMenu: function (state) {
8540 this.classes.toggle('active', state);
8541 },
8542 renderHtml: function () {
8543 var self = this, id = self._id, prefix = self.classPrefix;
8544 var icon = self.settings.icon, image;
8545 var text = self.state.get('text');
8546 var textHtml = '';
8547 image = self.settings.image;
8548 if (image) {
8549 icon = 'none';
8550 if (typeof image !== 'string') {
8551 image = domGlobals.window.getSelection ? image[0] : image[1];
8552 }
8553 image = ' style="background-image: url(\'' + image + '\')"';
8554 } else {
8555 image = '';
8556 }
8557 if (text) {
8558 self.classes.add('btn-has-text');
8559 textHtml = '<span class="' + prefix + 'txt">' + self.encode(text) + '</span>';
8560 }
8561 icon = self.settings.icon ? prefix + 'ico ' + prefix + 'i-' + icon : '';
8562 self.aria('role', self.parent() instanceof MenuBar ? 'menuitem' : 'button');
8563 return '<div id="' + id + '" class="' + self.classes + '" tabindex="-1" aria-labelledby="' + id + '">' + '<button id="' + id + '-open" role="presentation" type="button" tabindex="-1">' + (icon ? '<i class="' + icon + '"' + image + '></i>' : '') + textHtml + ' <i class="' + prefix + 'caret"></i>' + '</button>' + '</div>';
8564 },
8565 postRender: function () {
8566 var self = this;
8567 self.on('click', function (e) {
8568 if (e.control === self && isChildOf$1(e.target, self.getEl())) {
8569 self.focus();
8570 self.showMenu(!e.aria);
8571 if (e.aria) {
8572 self.menu.items().filter(':visible')[0].focus();
8573 }
8574 }
8575 });
8576 self.on('mouseenter', function (e) {
8577 var overCtrl = e.control;
8578 var parent = self.parent();
8579 var hasVisibleSiblingMenu;
8580 if (overCtrl && parent && overCtrl instanceof MenuButton && overCtrl.parent() === parent) {
8581 parent.items().filter('MenuButton').each(function (ctrl) {
8582 if (ctrl.hideMenu && ctrl !== overCtrl) {
8583 if (ctrl.menu && ctrl.menu.visible()) {
8584 hasVisibleSiblingMenu = true;
8585 }
8586 ctrl.hideMenu();
8587 }
8588 });
8589 if (hasVisibleSiblingMenu) {
8590 overCtrl.focus();
8591 overCtrl.showMenu();
8592 }
8593 }
8594 });
8595 return self._super();
8596 },
8597 bindStates: function () {
8598 var self = this;
8599 self.state.on('change:menu', function () {
8600 if (self.menu) {
8601 self.menu.remove();
8602 }
8603 self.menu = null;
8604 });
8605 return self._super();
8606 },
8607 remove: function () {
8608 this._super();
8609 if (this.menu) {
8610 this.menu.remove();
8611 }
8612 }
8613 });
8614
8615 function Throbber (elm, inline) {
8616 var self = this;
8617 var state;
8618 var classPrefix = Control$1.classPrefix;
8619 var timer;
8620 self.show = function (time, callback) {
8621 function render() {
8622 if (state) {
8623 global$7(elm).append('<div class="' + classPrefix + 'throbber' + (inline ? ' ' + classPrefix + 'throbber-inline' : '') + '"></div>');
8624 if (callback) {
8625 callback();
8626 }
8627 }
8628 }
8629 self.hide();
8630 state = true;
8631 if (time) {
8632 timer = global$3.setTimeout(render, time);
8633 } else {
8634 render();
8635 }
8636 return self;
8637 };
8638 self.hide = function () {
8639 var child = elm.lastChild;
8640 global$3.clearTimeout(timer);
8641 if (child && child.className.indexOf('throbber') !== -1) {
8642 child.parentNode.removeChild(child);
8643 }
8644 state = false;
8645 return self;
8646 };
8647 }
8648
8649 var Menu = FloatPanel.extend({
8650 Defaults: {
8651 defaultType: 'menuitem',
8652 border: 1,
8653 layout: 'stack',
8654 role: 'application',
8655 bodyRole: 'menu',
8656 ariaRoot: true
8657 },
8658 init: function (settings) {
8659 var self = this;
8660 settings.autohide = true;
8661 settings.constrainToViewport = true;
8662 if (typeof settings.items === 'function') {
8663 settings.itemsFactory = settings.items;
8664 settings.items = [];
8665 }
8666 if (settings.itemDefaults) {
8667 var items = settings.items;
8668 var i = items.length;
8669 while (i--) {
8670 items[i] = global$4.extend({}, settings.itemDefaults, items[i]);
8671 }
8672 }
8673 self._super(settings);
8674 self.classes.add('menu');
8675 if (settings.animate && global$1.ie !== 11) {
8676 self.classes.add('animate');
8677 }
8678 },
8679 repaint: function () {
8680 this.classes.toggle('menu-align', true);
8681 this._super();
8682 this.getEl().style.height = '';
8683 this.getEl('body').style.height = '';
8684 return this;
8685 },
8686 cancel: function () {
8687 var self = this;
8688 self.hideAll();
8689 self.fire('select');
8690 },
8691 load: function () {
8692 var self = this;
8693 var time, factory;
8694 function hideThrobber() {
8695 if (self.throbber) {
8696 self.throbber.hide();
8697 self.throbber = null;
8698 }
8699 }
8700 factory = self.settings.itemsFactory;
8701 if (!factory) {
8702 return;
8703 }
8704 if (!self.throbber) {
8705 self.throbber = new Throbber(self.getEl('body'), true);
8706 if (self.items().length === 0) {
8707 self.throbber.show();
8708 self.fire('loading');
8709 } else {
8710 self.throbber.show(100, function () {
8711 self.items().remove();
8712 self.fire('loading');
8713 });
8714 }
8715 self.on('hide close', hideThrobber);
8716 }
8717 self.requestTime = time = new Date().getTime();
8718 self.settings.itemsFactory(function (items) {
8719 if (items.length === 0) {
8720 self.hide();
8721 return;
8722 }
8723 if (self.requestTime !== time) {
8724 return;
8725 }
8726 self.getEl().style.width = '';
8727 self.getEl('body').style.width = '';
8728 hideThrobber();
8729 self.items().remove();
8730 self.getEl('body').innerHTML = '';
8731 self.add(items);
8732 self.renderNew();
8733 self.fire('loaded');
8734 });
8735 },
8736 hideAll: function () {
8737 var self = this;
8738 this.find('menuitem').exec('hideMenu');
8739 return self._super();
8740 },
8741 preRender: function () {
8742 var self = this;
8743 self.items().each(function (ctrl) {
8744 var settings = ctrl.settings;
8745 if (settings.icon || settings.image || settings.selectable) {
8746 self._hasIcons = true;
8747 return false;
8748 }
8749 });
8750 if (self.settings.itemsFactory) {
8751 self.on('postrender', function () {
8752 if (self.settings.itemsFactory) {
8753 self.load();
8754 }
8755 });
8756 }
8757 self.on('show hide', function (e) {
8758 if (e.control === self) {
8759 if (e.type === 'show') {
8760 global$3.setTimeout(function () {
8761 self.classes.add('in');
8762 }, 0);
8763 } else {
8764 self.classes.remove('in');
8765 }
8766 }
8767 });
8768 return self._super();
8769 }
8770 });
8771
8772 var ListBox = MenuButton.extend({
8773 init: function (settings) {
8774 var self = this;
8775 var values, selected, selectedText, lastItemCtrl;
8776 function setSelected(menuValues) {
8777 for (var i = 0; i < menuValues.length; i++) {
8778 selected = menuValues[i].selected || settings.value === menuValues[i].value;
8779 if (selected) {
8780 selectedText = selectedText || menuValues[i].text;
8781 self.state.set('value', menuValues[i].value);
8782 return true;
8783 }
8784 if (menuValues[i].menu) {
8785 if (setSelected(menuValues[i].menu)) {
8786 return true;
8787 }
8788 }
8789 }
8790 }
8791 self._super(settings);
8792 settings = self.settings;
8793 self._values = values = settings.values;
8794 if (values) {
8795 if (typeof settings.value !== 'undefined') {
8796 setSelected(values);
8797 }
8798 if (!selected && values.length > 0) {
8799 selectedText = values[0].text;
8800 self.state.set('value', values[0].value);
8801 }
8802 self.state.set('menu', values);
8803 }
8804 self.state.set('text', settings.text || selectedText);
8805 self.classes.add('listbox');
8806 self.on('select', function (e) {
8807 var ctrl = e.control;
8808 if (lastItemCtrl) {
8809 e.lastControl = lastItemCtrl;
8810 }
8811 if (settings.multiple) {
8812 ctrl.active(!ctrl.active());
8813 } else {
8814 self.value(e.control.value());
8815 }
8816 lastItemCtrl = ctrl;
8817 });
8818 },
8819 value: function (value) {
8820 if (arguments.length === 0) {
8821 return this.state.get('value');
8822 }
8823 if (typeof value === 'undefined') {
8824 return this;
8825 }
8826 function valueExists(values) {
8827 return exists(values, function (a) {
8828 return a.menu ? valueExists(a.menu) : a.value === value;
8829 });
8830 }
8831 if (this.settings.values) {
8832 if (valueExists(this.settings.values)) {
8833 this.state.set('value', value);
8834 } else if (value === null) {
8835 this.state.set('value', null);
8836 }
8837 } else {
8838 this.state.set('value', value);
8839 }
8840 return this;
8841 },
8842 bindStates: function () {
8843 var self = this;
8844 function activateMenuItemsByValue(menu, value) {
8845 if (menu instanceof Menu) {
8846 menu.items().each(function (ctrl) {
8847 if (!ctrl.hasMenus()) {
8848 ctrl.active(ctrl.value() === value);
8849 }
8850 });
8851 }
8852 }
8853 function getSelectedItem(menuValues, value) {
8854 var selectedItem;
8855 if (!menuValues) {
8856 return;
8857 }
8858 for (var i = 0; i < menuValues.length; i++) {
8859 if (menuValues[i].value === value) {
8860 return menuValues[i];
8861 }
8862 if (menuValues[i].menu) {
8863 selectedItem = getSelectedItem(menuValues[i].menu, value);
8864 if (selectedItem) {
8865 return selectedItem;
8866 }
8867 }
8868 }
8869 }
8870 self.on('show', function (e) {
8871 activateMenuItemsByValue(e.control, self.value());
8872 });
8873 self.state.on('change:value', function (e) {
8874 var selectedItem = getSelectedItem(self.state.get('menu'), e.value);
8875 if (selectedItem) {
8876 self.text(selectedItem.text);
8877 } else {
8878 self.text(self.settings.text);
8879 }
8880 });
8881 return self._super();
8882 }
8883 });
8884
8885 var toggleTextStyle = function (ctrl, state) {
8886 var textStyle = ctrl._textStyle;
8887 if (textStyle) {
8888 var textElm = ctrl.getEl('text');
8889 textElm.setAttribute('style', textStyle);
8890 if (state) {
8891 textElm.style.color = '';
8892 textElm.style.backgroundColor = '';
8893 }
8894 }
8895 };
8896 var MenuItem = Widget.extend({
8897 Defaults: {
8898 border: 0,
8899 role: 'menuitem'
8900 },
8901 init: function (settings) {
8902 var self = this;
8903 var text;
8904 self._super(settings);
8905 settings = self.settings;
8906 self.classes.add('menu-item');
8907 if (settings.menu) {
8908 self.classes.add('menu-item-expand');
8909 }
8910 if (settings.preview) {
8911 self.classes.add('menu-item-preview');
8912 }
8913 text = self.state.get('text');
8914 if (text === '-' || text === '|') {
8915 self.classes.add('menu-item-sep');
8916 self.aria('role', 'separator');
8917 self.state.set('text', '-');
8918 }
8919 if (settings.selectable) {
8920 self.aria('role', 'menuitemcheckbox');
8921 self.classes.add('menu-item-checkbox');
8922 settings.icon = 'selected';
8923 }
8924 if (!settings.preview && !settings.selectable) {
8925 self.classes.add('menu-item-normal');
8926 }
8927 self.on('mousedown', function (e) {
8928 e.preventDefault();
8929 });
8930 if (settings.menu && !settings.ariaHideMenu) {
8931 self.aria('haspopup', true);
8932 }
8933 },
8934 hasMenus: function () {
8935 return !!this.settings.menu;
8936 },
8937 showMenu: function () {
8938 var self = this;
8939 var settings = self.settings;
8940 var menu;
8941 var parent = self.parent();
8942 parent.items().each(function (ctrl) {
8943 if (ctrl !== self) {
8944 ctrl.hideMenu();
8945 }
8946 });
8947 if (settings.menu) {
8948 menu = self.menu;
8949 if (!menu) {
8950 menu = settings.menu;
8951 if (menu.length) {
8952 menu = {
8953 type: 'menu',
8954 items: menu
8955 };
8956 } else {
8957 menu.type = menu.type || 'menu';
8958 }
8959 if (parent.settings.itemDefaults) {
8960 menu.itemDefaults = parent.settings.itemDefaults;
8961 }
8962 menu = self.menu = global$b.create(menu).parent(self).renderTo();
8963 menu.reflow();
8964 menu.on('cancel', function (e) {
8965 e.stopPropagation();
8966 self.focus();
8967 menu.hide();
8968 });
8969 menu.on('show hide', function (e) {
8970 if (e.control.items) {
8971 e.control.items().each(function (ctrl) {
8972 ctrl.active(ctrl.settings.selected);
8973 });
8974 }
8975 }).fire('show');
8976 menu.on('hide', function (e) {
8977 if (e.control === menu) {
8978 self.classes.remove('selected');
8979 }
8980 });
8981 menu.submenu = true;
8982 } else {
8983 menu.show();
8984 }
8985 menu._parentMenu = parent;
8986 menu.classes.add('menu-sub');
8987 var rel = menu.testMoveRel(self.getEl(), self.isRtl() ? [
8988 'tl-tr',
8989 'bl-br',
8990 'tr-tl',
8991 'br-bl'
8992 ] : [
8993 'tr-tl',
8994 'br-bl',
8995 'tl-tr',
8996 'bl-br'
8997 ]);
8998 menu.moveRel(self.getEl(), rel);
8999 menu.rel = rel;
9000 rel = 'menu-sub-' + rel;
9001 menu.classes.remove(menu._lastRel).add(rel);
9002 menu._lastRel = rel;
9003 self.classes.add('selected');
9004 self.aria('expanded', true);
9005 }
9006 },
9007 hideMenu: function () {
9008 var self = this;
9009 if (self.menu) {
9010 self.menu.items().each(function (item) {
9011 if (item.hideMenu) {
9012 item.hideMenu();
9013 }
9014 });
9015 self.menu.hide();
9016 self.aria('expanded', false);
9017 }
9018 return self;
9019 },
9020 renderHtml: function () {
9021 var self = this;
9022 var id = self._id;
9023 var settings = self.settings;
9024 var prefix = self.classPrefix;
9025 var text = self.state.get('text');
9026 var icon = self.settings.icon, image = '', shortcut = settings.shortcut;
9027 var url = self.encode(settings.url), iconHtml = '';
9028 function convertShortcut(shortcut) {
9029 var i, value, replace = {};
9030 if (global$1.mac) {
9031 replace = {
9032 alt: '⌥',
9033 ctrl: '⌘',
9034 shift: '⇧',
9035 meta: '⌘'
9036 };
9037 } else {
9038 replace = { meta: 'Ctrl' };
9039 }
9040 shortcut = shortcut.split('+');
9041 for (i = 0; i < shortcut.length; i++) {
9042 value = replace[shortcut[i].toLowerCase()];
9043 if (value) {
9044 shortcut[i] = value;
9045 }
9046 }
9047 return shortcut.join('+');
9048 }
9049 function escapeRegExp(str) {
9050 return str.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
9051 }
9052 function markMatches(text) {
9053 var match = settings.match || '';
9054 return match ? text.replace(new RegExp(escapeRegExp(match), 'gi'), function (match) {
9055 return '!mce~match[' + match + ']mce~match!';
9056 }) : text;
9057 }
9058 function boldMatches(text) {
9059 return text.replace(new RegExp(escapeRegExp('!mce~match['), 'g'), '<b>').replace(new RegExp(escapeRegExp(']mce~match!'), 'g'), '</b>');
9060 }
9061 if (icon) {
9062 self.parent().classes.add('menu-has-icons');
9063 }
9064 if (settings.image) {
9065 image = ' style="background-image: url(\'' + settings.image + '\')"';
9066 }
9067 if (shortcut) {
9068 shortcut = convertShortcut(shortcut);
9069 }
9070 icon = prefix + 'ico ' + prefix + 'i-' + (self.settings.icon || 'none');
9071 iconHtml = text !== '-' ? '<i class="' + icon + '"' + image + '></i>\xA0' : '';
9072 text = boldMatches(self.encode(markMatches(text)));
9073 url = boldMatches(self.encode(markMatches(url)));
9074 return '<div id="' + id + '" class="' + self.classes + '" tabindex="-1">' + iconHtml + (text !== '-' ? '<span id="' + id + '-text" class="' + prefix + 'text">' + text + '</span>' : '') + (shortcut ? '<div id="' + id + '-shortcut" class="' + prefix + 'menu-shortcut">' + shortcut + '</div>' : '') + (settings.menu ? '<div class="' + prefix + 'caret"></div>' : '') + (url ? '<div class="' + prefix + 'menu-item-link">' + url + '</div>' : '') + '</div>';
9075 },
9076 postRender: function () {
9077 var self = this, settings = self.settings;
9078 var textStyle = settings.textStyle;
9079 if (typeof textStyle === 'function') {
9080 textStyle = textStyle.call(this);
9081 }
9082 if (textStyle) {
9083 var textElm = self.getEl('text');
9084 if (textElm) {
9085 textElm.setAttribute('style', textStyle);
9086 self._textStyle = textStyle;
9087 }
9088 }
9089 self.on('mouseenter click', function (e) {
9090 if (e.control === self) {
9091 if (!settings.menu && e.type === 'click') {
9092 self.fire('select');
9093 global$3.requestAnimationFrame(function () {
9094 self.parent().hideAll();
9095 });
9096 } else {
9097 self.showMenu();
9098 if (e.aria) {
9099 self.menu.focus(true);
9100 }
9101 }
9102 }
9103 });
9104 self._super();
9105 return self;
9106 },
9107 hover: function () {
9108 var self = this;
9109 self.parent().items().each(function (ctrl) {
9110 ctrl.classes.remove('selected');
9111 });
9112 self.classes.toggle('selected', true);
9113 return self;
9114 },
9115 active: function (state) {
9116 toggleTextStyle(this, state);
9117 if (typeof state !== 'undefined') {
9118 this.aria('checked', state);
9119 }
9120 return this._super(state);
9121 },
9122 remove: function () {
9123 this._super();
9124 if (this.menu) {
9125 this.menu.remove();
9126 }
9127 }
9128 });
9129
9130 var Radio = Checkbox.extend({
9131 Defaults: {
9132 classes: 'radio',
9133 role: 'radio'
9134 }
9135 });
9136
9137 var ResizeHandle = Widget.extend({
9138 renderHtml: function () {
9139 var self = this, prefix = self.classPrefix;
9140 self.classes.add('resizehandle');
9141 if (self.settings.direction === 'both') {
9142 self.classes.add('resizehandle-both');
9143 }
9144 self.canFocus = false;
9145 return '<div id="' + self._id + '" class="' + self.classes + '">' + '<i class="' + prefix + 'ico ' + prefix + 'i-resize"></i>' + '</div>';
9146 },
9147 postRender: function () {
9148 var self = this;
9149 self._super();
9150 self.resizeDragHelper = new DragHelper(this._id, {
9151 start: function () {
9152 self.fire('ResizeStart');
9153 },
9154 drag: function (e) {
9155 if (self.settings.direction !== 'both') {
9156 e.deltaX = 0;
9157 }
9158 self.fire('Resize', e);
9159 },
9160 stop: function () {
9161 self.fire('ResizeEnd');
9162 }
9163 });
9164 },
9165 remove: function () {
9166 if (this.resizeDragHelper) {
9167 this.resizeDragHelper.destroy();
9168 }
9169 return this._super();
9170 }
9171 });
9172
9173 function createOptions(options) {
9174 var strOptions = '';
9175 if (options) {
9176 for (var i = 0; i < options.length; i++) {
9177 strOptions += '<option value="' + options[i] + '">' + options[i] + '</option>';
9178 }
9179 }
9180 return strOptions;
9181 }
9182 var SelectBox = Widget.extend({
9183 Defaults: {
9184 classes: 'selectbox',
9185 role: 'selectbox',
9186 options: []
9187 },
9188 init: function (settings) {
9189 var self = this;
9190 self._super(settings);
9191 if (self.settings.size) {
9192 self.size = self.settings.size;
9193 }
9194 if (self.settings.options) {
9195 self._options = self.settings.options;
9196 }
9197 self.on('keydown', function (e) {
9198 var rootControl;
9199 if (e.keyCode === 13) {
9200 e.preventDefault();
9201 self.parents().reverse().each(function (ctrl) {
9202 if (ctrl.toJSON) {
9203 rootControl = ctrl;
9204 return false;
9205 }
9206 });
9207 self.fire('submit', { data: rootControl.toJSON() });
9208 }
9209 });
9210 },
9211 options: function (state) {
9212 if (!arguments.length) {
9213 return this.state.get('options');
9214 }
9215 this.state.set('options', state);
9216 return this;
9217 },
9218 renderHtml: function () {
9219 var self = this;
9220 var options, size = '';
9221 options = createOptions(self._options);
9222 if (self.size) {
9223 size = ' size = "' + self.size + '"';
9224 }
9225 return '<select id="' + self._id + '" class="' + self.classes + '"' + size + '>' + options + '</select>';
9226 },
9227 bindStates: function () {
9228 var self = this;
9229 self.state.on('change:options', function (e) {
9230 self.getEl().innerHTML = createOptions(e.value);
9231 });
9232 return self._super();
9233 }
9234 });
9235
9236 function constrain(value, minVal, maxVal) {
9237 if (value < minVal) {
9238 value = minVal;
9239 }
9240 if (value > maxVal) {
9241 value = maxVal;
9242 }
9243 return value;
9244 }
9245 function setAriaProp(el, name, value) {
9246 el.setAttribute('aria-' + name, value);
9247 }
9248 function updateSliderHandle(ctrl, value) {
9249 var maxHandlePos, shortSizeName, sizeName, stylePosName, styleValue, handleEl;
9250 if (ctrl.settings.orientation === 'v') {
9251 stylePosName = 'top';
9252 sizeName = 'height';
9253 shortSizeName = 'h';
9254 } else {
9255 stylePosName = 'left';
9256 sizeName = 'width';
9257 shortSizeName = 'w';
9258 }
9259 handleEl = ctrl.getEl('handle');
9260 maxHandlePos = (ctrl.layoutRect()[shortSizeName] || 100) - funcs.getSize(handleEl)[sizeName];
9261 styleValue = maxHandlePos * ((value - ctrl._minValue) / (ctrl._maxValue - ctrl._minValue)) + 'px';
9262 handleEl.style[stylePosName] = styleValue;
9263 handleEl.style.height = ctrl.layoutRect().h + 'px';
9264 setAriaProp(handleEl, 'valuenow', value);
9265 setAriaProp(handleEl, 'valuetext', '' + ctrl.settings.previewFilter(value));
9266 setAriaProp(handleEl, 'valuemin', ctrl._minValue);
9267 setAriaProp(handleEl, 'valuemax', ctrl._maxValue);
9268 }
9269 var Slider = Widget.extend({
9270 init: function (settings) {
9271 var self = this;
9272 if (!settings.previewFilter) {
9273 settings.previewFilter = function (value) {
9274 return Math.round(value * 100) / 100;
9275 };
9276 }
9277 self._super(settings);
9278 self.classes.add('slider');
9279 if (settings.orientation === 'v') {
9280 self.classes.add('vertical');
9281 }
9282 self._minValue = isNumber$1(settings.minValue) ? settings.minValue : 0;
9283 self._maxValue = isNumber$1(settings.maxValue) ? settings.maxValue : 100;
9284 self._initValue = self.state.get('value');
9285 },
9286 renderHtml: function () {
9287 var self = this, id = self._id, prefix = self.classPrefix;
9288 return '<div id="' + id + '" class="' + self.classes + '">' + '<div id="' + id + '-handle" class="' + prefix + 'slider-handle" role="slider" tabindex="-1"></div>' + '</div>';
9289 },
9290 reset: function () {
9291 this.value(this._initValue).repaint();
9292 },
9293 postRender: function () {
9294 var self = this;
9295 var minValue, maxValue, screenCordName, stylePosName, sizeName, shortSizeName;
9296 function toFraction(min, max, val) {
9297 return (val + min) / (max - min);
9298 }
9299 function fromFraction(min, max, val) {
9300 return val * (max - min) - min;
9301 }
9302 function handleKeyboard(minValue, maxValue) {
9303 function alter(delta) {
9304 var value;
9305 value = self.value();
9306 value = fromFraction(minValue, maxValue, toFraction(minValue, maxValue, value) + delta * 0.05);
9307 value = constrain(value, minValue, maxValue);
9308 self.value(value);
9309 self.fire('dragstart', { value: value });
9310 self.fire('drag', { value: value });
9311 self.fire('dragend', { value: value });
9312 }
9313 self.on('keydown', function (e) {
9314 switch (e.keyCode) {
9315 case 37:
9316 case 38:
9317 alter(-1);
9318 break;
9319 case 39:
9320 case 40:
9321 alter(1);
9322 break;
9323 }
9324 });
9325 }
9326 function handleDrag(minValue, maxValue, handleEl) {
9327 var startPos, startHandlePos, maxHandlePos, handlePos, value;
9328 self._dragHelper = new DragHelper(self._id, {
9329 handle: self._id + '-handle',
9330 start: function (e) {
9331 startPos = e[screenCordName];
9332 startHandlePos = parseInt(self.getEl('handle').style[stylePosName], 10);
9333 maxHandlePos = (self.layoutRect()[shortSizeName] || 100) - funcs.getSize(handleEl)[sizeName];
9334 self.fire('dragstart', { value: value });
9335 },
9336 drag: function (e) {
9337 var delta = e[screenCordName] - startPos;
9338 handlePos = constrain(startHandlePos + delta, 0, maxHandlePos);
9339 handleEl.style[stylePosName] = handlePos + 'px';
9340 value = minValue + handlePos / maxHandlePos * (maxValue - minValue);
9341 self.value(value);
9342 self.tooltip().text('' + self.settings.previewFilter(value)).show().moveRel(handleEl, 'bc tc');
9343 self.fire('drag', { value: value });
9344 },
9345 stop: function () {
9346 self.tooltip().hide();
9347 self.fire('dragend', { value: value });
9348 }
9349 });
9350 }
9351 minValue = self._minValue;
9352 maxValue = self._maxValue;
9353 if (self.settings.orientation === 'v') {
9354 screenCordName = 'screenY';
9355 stylePosName = 'top';
9356 sizeName = 'height';
9357 shortSizeName = 'h';
9358 } else {
9359 screenCordName = 'screenX';
9360 stylePosName = 'left';
9361 sizeName = 'width';
9362 shortSizeName = 'w';
9363 }
9364 self._super();
9365 handleKeyboard(minValue, maxValue);
9366 handleDrag(minValue, maxValue, self.getEl('handle'));
9367 },
9368 repaint: function () {
9369 this._super();
9370 updateSliderHandle(this, this.value());
9371 },
9372 bindStates: function () {
9373 var self = this;
9374 self.state.on('change:value', function (e) {
9375 updateSliderHandle(self, e.value);
9376 });
9377 return self._super();
9378 }
9379 });
9380
9381 var Spacer = Widget.extend({
9382 renderHtml: function () {
9383 var self = this;
9384 self.classes.add('spacer');
9385 self.canFocus = false;
9386 return '<div id="' + self._id + '" class="' + self.classes + '"></div>';
9387 }
9388 });
9389
9390 var SplitButton = MenuButton.extend({
9391 Defaults: {
9392 classes: 'widget btn splitbtn',
9393 role: 'button'
9394 },
9395 repaint: function () {
9396 var self = this;
9397 var elm = self.getEl();
9398 var rect = self.layoutRect();
9399 var mainButtonElm, menuButtonElm;
9400 self._super();
9401 mainButtonElm = elm.firstChild;
9402 menuButtonElm = elm.lastChild;
9403 global$7(mainButtonElm).css({
9404 width: rect.w - funcs.getSize(menuButtonElm).width,
9405 height: rect.h - 2
9406 });
9407 global$7(menuButtonElm).css({ height: rect.h - 2 });
9408 return self;
9409 },
9410 activeMenu: function (state) {
9411 var self = this;
9412 global$7(self.getEl().lastChild).toggleClass(self.classPrefix + 'active', state);
9413 },
9414 renderHtml: function () {
9415 var self = this;
9416 var id = self._id;
9417 var prefix = self.classPrefix;
9418 var image;
9419 var icon = self.state.get('icon');
9420 var text = self.state.get('text');
9421 var settings = self.settings;
9422 var textHtml = '', ariaPressed;
9423 image = settings.image;
9424 if (image) {
9425 icon = 'none';
9426 if (typeof image !== 'string') {
9427 image = domGlobals.window.getSelection ? image[0] : image[1];
9428 }
9429 image = ' style="background-image: url(\'' + image + '\')"';
9430 } else {
9431 image = '';
9432 }
9433 icon = settings.icon ? prefix + 'ico ' + prefix + 'i-' + icon : '';
9434 if (text) {
9435 self.classes.add('btn-has-text');
9436 textHtml = '<span class="' + prefix + 'txt">' + self.encode(text) + '</span>';
9437 }
9438 ariaPressed = typeof settings.active === 'boolean' ? ' aria-pressed="' + settings.active + '"' : '';
9439 return '<div id="' + id + '" class="' + self.classes + '" role="button"' + ariaPressed + ' tabindex="-1">' + '<button type="button" hidefocus="1" tabindex="-1">' + (icon ? '<i class="' + icon + '"' + image + '></i>' : '') + textHtml + '</button>' + '<button type="button" class="' + prefix + 'open" hidefocus="1" tabindex="-1">' + (self._menuBtnText ? (icon ? '\xA0' : '') + self._menuBtnText : '') + ' <i class="' + prefix + 'caret"></i>' + '</button>' + '</div>';
9440 },
9441 postRender: function () {
9442 var self = this, onClickHandler = self.settings.onclick;
9443 self.on('click', function (e) {
9444 var node = e.target;
9445 if (e.control === this) {
9446 while (node) {
9447 if (e.aria && e.aria.key !== 'down' || node.nodeName === 'BUTTON' && node.className.indexOf('open') === -1) {
9448 e.stopImmediatePropagation();
9449 if (onClickHandler) {
9450 onClickHandler.call(this, e);
9451 }
9452 return;
9453 }
9454 node = node.parentNode;
9455 }
9456 }
9457 });
9458 delete self.settings.onclick;
9459 return self._super();
9460 }
9461 });
9462
9463 var StackLayout = FlowLayout.extend({
9464 Defaults: {
9465 containerClass: 'stack-layout',
9466 controlClass: 'stack-layout-item',
9467 endClass: 'break'
9468 },
9469 isNative: function () {
9470 return true;
9471 }
9472 });
9473
9474 var TabPanel = Panel.extend({
9475 Defaults: {
9476 layout: 'absolute',
9477 defaults: { type: 'panel' }
9478 },
9479 activateTab: function (idx) {
9480 var activeTabElm;
9481 if (this.activeTabId) {
9482 activeTabElm = this.getEl(this.activeTabId);
9483 global$7(activeTabElm).removeClass(this.classPrefix + 'active');
9484 activeTabElm.setAttribute('aria-selected', 'false');
9485 }
9486 this.activeTabId = 't' + idx;
9487 activeTabElm = this.getEl('t' + idx);
9488 activeTabElm.setAttribute('aria-selected', 'true');
9489 global$7(activeTabElm).addClass(this.classPrefix + 'active');
9490 this.items()[idx].show().fire('showtab');
9491 this.reflow();
9492 this.items().each(function (item, i) {
9493 if (idx !== i) {
9494 item.hide();
9495 }
9496 });
9497 },
9498 renderHtml: function () {
9499 var self = this;
9500 var layout = self._layout;
9501 var tabsHtml = '';
9502 var prefix = self.classPrefix;
9503 self.preRender();
9504 layout.preRender(self);
9505 self.items().each(function (ctrl, i) {
9506 var id = self._id + '-t' + i;
9507 ctrl.aria('role', 'tabpanel');
9508 ctrl.aria('labelledby', id);
9509 tabsHtml += '<div id="' + id + '" class="' + prefix + 'tab" ' + 'unselectable="on" role="tab" aria-controls="' + ctrl._id + '" aria-selected="false" tabIndex="-1">' + self.encode(ctrl.settings.title) + '</div>';
9510 });
9511 return '<div id="' + self._id + '" class="' + self.classes + '" hidefocus="1" tabindex="-1">' + '<div id="' + self._id + '-head" class="' + prefix + 'tabs" role="tablist">' + tabsHtml + '</div>' + '<div id="' + self._id + '-body" class="' + self.bodyClasses + '">' + layout.renderHtml(self) + '</div>' + '</div>';
9512 },
9513 postRender: function () {
9514 var self = this;
9515 self._super();
9516 self.settings.activeTab = self.settings.activeTab || 0;
9517 self.activateTab(self.settings.activeTab);
9518 this.on('click', function (e) {
9519 var targetParent = e.target.parentNode;
9520 if (targetParent && targetParent.id === self._id + '-head') {
9521 var i = targetParent.childNodes.length;
9522 while (i--) {
9523 if (targetParent.childNodes[i] === e.target) {
9524 self.activateTab(i);
9525 }
9526 }
9527 }
9528 });
9529 },
9530 initLayoutRect: function () {
9531 var self = this;
9532 var rect, minW, minH;
9533 minW = funcs.getSize(self.getEl('head')).width;
9534 minW = minW < 0 ? 0 : minW;
9535 minH = 0;
9536 self.items().each(function (item) {
9537 minW = Math.max(minW, item.layoutRect().minW);
9538 minH = Math.max(minH, item.layoutRect().minH);
9539 });
9540 self.items().each(function (ctrl) {
9541 ctrl.settings.x = 0;
9542 ctrl.settings.y = 0;
9543 ctrl.settings.w = minW;
9544 ctrl.settings.h = minH;
9545 ctrl.layoutRect({
9546 x: 0,
9547 y: 0,
9548 w: minW,
9549 h: minH
9550 });
9551 });
9552 var headH = funcs.getSize(self.getEl('head')).height;
9553 self.settings.minWidth = minW;
9554 self.settings.minHeight = minH + headH;
9555 rect = self._super();
9556 rect.deltaH += headH;
9557 rect.innerH = rect.h - rect.deltaH;
9558 return rect;
9559 }
9560 });
9561
9562 var TextBox = Widget.extend({
9563 init: function (settings) {
9564 var self = this;
9565 self._super(settings);
9566 self.classes.add('textbox');
9567 if (settings.multiline) {
9568 self.classes.add('multiline');
9569 } else {
9570 self.on('keydown', function (e) {
9571 var rootControl;
9572 if (e.keyCode === 13) {
9573 e.preventDefault();
9574 self.parents().reverse().each(function (ctrl) {
9575 if (ctrl.toJSON) {
9576 rootControl = ctrl;
9577 return false;
9578 }
9579 });
9580 self.fire('submit', { data: rootControl.toJSON() });
9581 }
9582 });
9583 self.on('keyup', function (e) {
9584 self.state.set('value', e.target.value);
9585 });
9586 }
9587 },
9588 repaint: function () {
9589 var self = this;
9590 var style, rect, borderBox, borderW, borderH = 0, lastRepaintRect;
9591 style = self.getEl().style;
9592 rect = self._layoutRect;
9593 lastRepaintRect = self._lastRepaintRect || {};
9594 var doc = domGlobals.document;
9595 if (!self.settings.multiline && doc.all && (!doc.documentMode || doc.documentMode <= 8)) {
9596 style.lineHeight = rect.h - borderH + 'px';
9597 }
9598 borderBox = self.borderBox;
9599 borderW = borderBox.left + borderBox.right + 8;
9600 borderH = borderBox.top + borderBox.bottom + (self.settings.multiline ? 8 : 0);
9601 if (rect.x !== lastRepaintRect.x) {
9602 style.left = rect.x + 'px';
9603 lastRepaintRect.x = rect.x;
9604 }
9605 if (rect.y !== lastRepaintRect.y) {
9606 style.top = rect.y + 'px';
9607 lastRepaintRect.y = rect.y;
9608 }
9609 if (rect.w !== lastRepaintRect.w) {
9610 style.width = rect.w - borderW + 'px';
9611 lastRepaintRect.w = rect.w;
9612 }
9613 if (rect.h !== lastRepaintRect.h) {
9614 style.height = rect.h - borderH + 'px';
9615 lastRepaintRect.h = rect.h;
9616 }
9617 self._lastRepaintRect = lastRepaintRect;
9618 self.fire('repaint', {}, false);
9619 return self;
9620 },
9621 renderHtml: function () {
9622 var self = this;
9623 var settings = self.settings;
9624 var attrs, elm;
9625 attrs = {
9626 id: self._id,
9627 hidefocus: '1'
9628 };
9629 global$4.each([
9630 'rows',
9631 'spellcheck',
9632 'maxLength',
9633 'size',
9634 'readonly',
9635 'min',
9636 'max',
9637 'step',
9638 'list',
9639 'pattern',
9640 'placeholder',
9641 'required',
9642 'multiple'
9643 ], function (name) {
9644 attrs[name] = settings[name];
9645 });
9646 if (self.disabled()) {
9647 attrs.disabled = 'disabled';
9648 }
9649 if (settings.subtype) {
9650 attrs.type = settings.subtype;
9651 }
9652 elm = funcs.create(settings.multiline ? 'textarea' : 'input', attrs);
9653 elm.value = self.state.get('value');
9654 elm.className = self.classes.toString();
9655 return elm.outerHTML;
9656 },
9657 value: function (value) {
9658 if (arguments.length) {
9659 this.state.set('value', value);
9660 return this;
9661 }
9662 if (this.state.get('rendered')) {
9663 this.state.set('value', this.getEl().value);
9664 }
9665 return this.state.get('value');
9666 },
9667 postRender: function () {
9668 var self = this;
9669 self.getEl().value = self.state.get('value');
9670 self._super();
9671 self.$el.on('change', function (e) {
9672 self.state.set('value', e.target.value);
9673 self.fire('change', e);
9674 });
9675 },
9676 bindStates: function () {
9677 var self = this;
9678 self.state.on('change:value', function (e) {
9679 if (self.getEl().value !== e.value) {
9680 self.getEl().value = e.value;
9681 }
9682 });
9683 self.state.on('change:disabled', function (e) {
9684 self.getEl().disabled = e.value;
9685 });
9686 return self._super();
9687 },
9688 remove: function () {
9689 this.$el.off();
9690 this._super();
9691 }
9692 });
9693
9694 var getApi = function () {
9695 return {
9696 Selector: Selector,
9697 Collection: Collection$2,
9698 ReflowQueue: ReflowQueue,
9699 Control: Control$1,
9700 Factory: global$b,
9701 KeyboardNavigation: KeyboardNavigation,
9702 Container: Container,
9703 DragHelper: DragHelper,
9704 Scrollable: Scrollable,
9705 Panel: Panel,
9706 Movable: Movable,
9707 Resizable: Resizable,
9708 FloatPanel: FloatPanel,
9709 Window: Window,
9710 MessageBox: MessageBox,
9711 Tooltip: Tooltip,
9712 Widget: Widget,
9713 Progress: Progress,
9714 Notification: Notification,
9715 Layout: Layout$1,
9716 AbsoluteLayout: AbsoluteLayout,
9717 Button: Button,
9718 ButtonGroup: ButtonGroup,
9719 Checkbox: Checkbox,
9720 ComboBox: ComboBox,
9721 ColorBox: ColorBox,
9722 PanelButton: PanelButton,
9723 ColorButton: ColorButton,
9724 ColorPicker: ColorPicker,
9725 Path: Path,
9726 ElementPath: ElementPath,
9727 FormItem: FormItem,
9728 Form: Form,
9729 FieldSet: FieldSet,
9730 FilePicker: FilePicker,
9731 FitLayout: FitLayout,
9732 FlexLayout: FlexLayout,
9733 FlowLayout: FlowLayout,
9734 FormatControls: FormatControls,
9735 GridLayout: GridLayout,
9736 Iframe: Iframe,
9737 InfoBox: InfoBox,
9738 Label: Label,
9739 Toolbar: Toolbar$1,
9740 MenuBar: MenuBar,
9741 MenuButton: MenuButton,
9742 MenuItem: MenuItem,
9743 Throbber: Throbber,
9744 Menu: Menu,
9745 ListBox: ListBox,
9746 Radio: Radio,
9747 ResizeHandle: ResizeHandle,
9748 SelectBox: SelectBox,
9749 Slider: Slider,
9750 Spacer: Spacer,
9751 SplitButton: SplitButton,
9752 StackLayout: StackLayout,
9753 TabPanel: TabPanel,
9754 TextBox: TextBox,
9755 DropZone: DropZone,
9756 BrowseButton: BrowseButton
9757 };
9758 };
9759 var appendTo = function (target) {
9760 if (target.ui) {
9761 global$4.each(getApi(), function (ref, key) {
9762 target.ui[key] = ref;
9763 });
9764 } else {
9765 target.ui = getApi();
9766 }
9767 };
9768 var registerToFactory = function () {
9769 global$4.each(getApi(), function (ref, key) {
9770 global$b.add(key, ref);
9771 });
9772 };
9773 var Api = {
9774 appendTo: appendTo,
9775 registerToFactory: registerToFactory
9776 };
9777
9778 Api.registerToFactory();
9779 Api.appendTo(window.tinymce ? window.tinymce : {});
9780 global.add('inlite', function (editor) {
9781 var panel = create$3();
9782 FormatControls.setup(editor);
9783 Buttons.addToEditor(editor, panel);
9784 return ThemeApi.get(editor, panel);
9785 });
9786 function Theme () {
9787 }
9788
9789 return Theme;
9790
9791}(window));
9792})();
9793