spiderfw 0.6.38 → 0.6.39
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +13 -5
- data/CHANGELOG +23 -0
- data/VERSION +1 -1
- data/apps/core/admin/views/admin.layout.shtml +6 -0
- data/apps/core/auth/controllers/login_controller.rb +1 -1
- data/apps/core/components/assets.rb +55 -6
- data/apps/core/components/public/bootstrap/scss/_variables.scss +5 -2
- data/apps/core/components/public/bootstrap/scss/bootstrap.css +942 -236
- data/apps/core/components/public/bootstrap/scss/responsive.css +187 -30
- data/apps/core/components/public/css/tinymce/skins/lightgray/AbsoluteLayout.less +17 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Animations.less +10 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Button.less +172 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/ButtonGroup.less +71 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Checkbox.less +49 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/ColorBox.less +6 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/ColorButton.less +72 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/ColorPicker.less +80 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/ComboBox.less +39 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Container.less +9 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Content.Inline.less +4 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Content.Objects.less +166 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Content.less +27 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/CropRect.less +54 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/FieldSet.less +15 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/FitLayout.less +9 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/FloatPanel.less +69 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/FlowLayout.less +36 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Icons.Ie7.less +136 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Icons.less +180 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Iframe.less +6 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/ImagePanel.less +20 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/InfoBox.less +71 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Label.less +38 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/ListBox.less +26 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Menu.less +34 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/MenuBar.less +32 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/MenuButton.less +34 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/MenuItem.less +142 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Mixins.less +54 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Notification.less +144 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Panel.less +7 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Path.less +45 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Progress.less +34 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Radio.less +1 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Reset.less +32 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/ResizeHandle.less +18 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Scrollable.less +44 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/SelectBox.less +6 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Slider.less +29 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Spacer.less +5 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/SplitButton.less +49 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/StackLayout.less +5 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/TabPanel.less +44 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/TextBox.less +41 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Throbber.less +19 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/TinyMCE.less +159 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/ToolTip.less +129 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Variables.less +214 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/Window.less +127 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/content.inline.min.css +1 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/content.min.css +1 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/fonts/readme.md +1 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/fonts/tinymce-small.eot +0 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/fonts/tinymce-small.json +1277 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/fonts/tinymce-small.svg +63 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/fonts/tinymce-small.ttf +0 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/fonts/tinymce-small.woff +0 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/fonts/tinymce.eot +0 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/fonts/tinymce.json +3381 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/fonts/tinymce.svg +129 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/fonts/tinymce.ttf +0 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/fonts/tinymce.woff +0 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/img/anchor.gif +0 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/img/loader.gif +0 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/img/object.gif +0 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/img/trans.gif +0 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/skin.dev.less +46 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/skin.ie7.dev.less +46 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/skin.ie7.less +2542 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/skin.ie7.min.css +1 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/skin.less +2586 -0
- data/apps/core/components/public/css/tinymce/skins/lightgray/skin.min.css +1 -0
- data/apps/core/components/public/js/bootbox_2/bootbox.js +551 -0
- data/apps/core/components/public/js/jquery/jquery-ui-1.9.2/ui/i18n/jquery.ui.datepicker-it-min.js +4 -0
- data/apps/core/components/public/js/spider.js +7 -3
- data/apps/core/components/public/js/tinymce/classes/AddOnManager.js +265 -0
- data/apps/core/components/public/js/tinymce/classes/Compat.js +90 -0
- data/apps/core/components/public/js/tinymce/classes/DragDropOverrides.js +224 -0
- data/apps/core/components/public/js/tinymce/classes/Editor.js +2221 -0
- data/apps/core/components/public/js/tinymce/classes/EditorCommands.js +1028 -0
- data/apps/core/components/public/js/tinymce/classes/EditorManager.js +715 -0
- data/apps/core/components/public/js/tinymce/classes/EditorObservable.js +204 -0
- data/apps/core/components/public/js/tinymce/classes/EditorUpload.js +191 -0
- data/apps/core/components/public/js/tinymce/classes/EnterKey.js +676 -0
- data/apps/core/components/public/js/tinymce/classes/Env.js +177 -0
- data/apps/core/components/public/js/tinymce/classes/FocusManager.js +266 -0
- data/apps/core/components/public/js/tinymce/classes/ForceBlocks.js +138 -0
- data/apps/core/components/public/js/tinymce/classes/Formatter.js +2378 -0
- data/apps/core/components/public/js/tinymce/classes/LegacyInput.js +82 -0
- data/apps/core/components/public/js/tinymce/classes/Mode.js +54 -0
- data/apps/core/components/public/js/tinymce/classes/NodeChange.js +154 -0
- data/apps/core/components/public/js/tinymce/classes/NotificationManager.js +156 -0
- data/apps/core/components/public/js/tinymce/classes/Register.js +34 -0
- data/apps/core/components/public/js/tinymce/classes/SelectionOverrides.js +810 -0
- data/apps/core/components/public/js/tinymce/classes/Shortcuts.js +172 -0
- data/apps/core/components/public/js/tinymce/classes/UndoManager.js +346 -0
- data/apps/core/components/public/js/tinymce/classes/WindowManager.js +278 -0
- data/apps/core/components/public/js/tinymce/classes/caret/CaretBookmark.js +263 -0
- data/apps/core/components/public/js/tinymce/classes/caret/CaretCandidate.js +86 -0
- data/apps/core/components/public/js/tinymce/classes/caret/CaretContainer.js +151 -0
- data/apps/core/components/public/js/tinymce/classes/caret/CaretPosition.js +371 -0
- data/apps/core/components/public/js/tinymce/classes/caret/CaretUtils.js +302 -0
- data/apps/core/components/public/js/tinymce/classes/caret/CaretWalker.js +215 -0
- data/apps/core/components/public/js/tinymce/classes/caret/FakeCaret.js +192 -0
- data/apps/core/components/public/js/tinymce/classes/caret/LineUtils.js +135 -0
- data/apps/core/components/public/js/tinymce/classes/caret/LineWalker.js +166 -0
- data/apps/core/components/public/js/tinymce/classes/data/Binding.js +79 -0
- data/apps/core/components/public/js/tinymce/classes/data/ObservableArray.js +196 -0
- data/apps/core/components/public/js/tinymce/classes/data/ObservableObject.js +194 -0
- data/apps/core/components/public/js/tinymce/classes/dom/BookmarkManager.js +456 -0
- data/apps/core/components/public/js/tinymce/classes/dom/ControlSelection.js +634 -0
- data/apps/core/components/public/js/tinymce/classes/dom/DOMUtils.js +1853 -0
- data/apps/core/components/public/js/tinymce/classes/dom/Dimensions.js +64 -0
- data/apps/core/components/public/js/tinymce/classes/dom/DomQuery.js +1578 -0
- data/apps/core/components/public/js/tinymce/classes/dom/ElementUtils.js +118 -0
- data/apps/core/components/public/js/tinymce/classes/dom/EventUtils.js +583 -0
- data/apps/core/components/public/js/tinymce/classes/dom/NodePath.js +50 -0
- data/apps/core/components/public/js/tinymce/classes/dom/NodeType.js +110 -0
- data/apps/core/components/public/js/tinymce/classes/dom/Range.js +785 -0
- data/apps/core/components/public/js/tinymce/classes/dom/RangeUtils.js +628 -0
- data/apps/core/components/public/js/tinymce/classes/dom/ScriptLoader.js +254 -0
- data/apps/core/components/public/js/tinymce/classes/dom/Selection.js +1008 -0
- data/apps/core/components/public/js/tinymce/classes/dom/Serializer.js +506 -0
- data/apps/core/components/public/js/tinymce/classes/dom/Sizzle.jQuery.js +23 -0
- data/apps/core/components/public/js/tinymce/classes/dom/Sizzle.js +2039 -0
- data/apps/core/components/public/js/tinymce/classes/dom/StyleSheetLoader.js +190 -0
- data/apps/core/components/public/js/tinymce/classes/dom/TreeWalker.js +127 -0
- data/apps/core/components/public/js/tinymce/classes/dom/TridentSelection.js +508 -0
- data/apps/core/components/public/js/tinymce/classes/file/BlobCache.js +72 -0
- data/apps/core/components/public/js/tinymce/classes/file/Conversions.js +106 -0
- data/apps/core/components/public/js/tinymce/classes/file/ImageScanner.js +145 -0
- data/apps/core/components/public/js/tinymce/classes/file/Uploader.js +193 -0
- data/apps/core/components/public/js/tinymce/classes/fmt/Hooks.js +66 -0
- data/apps/core/components/public/js/tinymce/classes/fmt/Preview.js +151 -0
- data/apps/core/components/public/js/tinymce/classes/geom/ClientRect.js +136 -0
- data/apps/core/components/public/js/tinymce/classes/geom/Rect.js +214 -0
- data/apps/core/components/public/js/tinymce/classes/html/DomParser.js +822 -0
- data/apps/core/components/public/js/tinymce/classes/html/Entities.js +268 -0
- data/apps/core/components/public/js/tinymce/classes/html/Node.js +496 -0
- data/apps/core/components/public/js/tinymce/classes/html/SaxParser.js +474 -0
- data/apps/core/components/public/js/tinymce/classes/html/Schema.js +1004 -0
- data/apps/core/components/public/js/tinymce/classes/html/Serializer.js +158 -0
- data/apps/core/components/public/js/tinymce/classes/html/Styles.js +363 -0
- data/apps/core/components/public/js/tinymce/classes/html/Writer.js +199 -0
- data/apps/core/components/public/js/tinymce/classes/jquery.tinymce.js +377 -0
- data/apps/core/components/public/js/tinymce/classes/text/ExtendingChar.js +53 -0
- data/apps/core/components/public/js/tinymce/classes/text/Zwsp.js +36 -0
- data/apps/core/components/public/js/tinymce/classes/ui/AbsoluteLayout.js +63 -0
- data/apps/core/components/public/js/tinymce/classes/ui/BoxUtils.js +98 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Button.js +199 -0
- data/apps/core/components/public/js/tinymce/classes/ui/ButtonGroup.js +62 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Checkbox.js +162 -0
- data/apps/core/components/public/js/tinymce/classes/ui/ClassList.js +149 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Collection.js +438 -0
- data/apps/core/components/public/js/tinymce/classes/ui/ColorBox.js +72 -0
- data/apps/core/components/public/js/tinymce/classes/ui/ColorButton.js +124 -0
- data/apps/core/components/public/js/tinymce/classes/ui/ColorPicker.js +206 -0
- data/apps/core/components/public/js/tinymce/classes/ui/ComboBox.js +306 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Container.js +506 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Control.js +1301 -0
- data/apps/core/components/public/js/tinymce/classes/ui/DomUtils.js +107 -0
- data/apps/core/components/public/js/tinymce/classes/ui/DragHelper.js +144 -0
- data/apps/core/components/public/js/tinymce/classes/ui/ElementPath.js +79 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Factory.js +105 -0
- data/apps/core/components/public/js/tinymce/classes/ui/FieldSet.js +59 -0
- data/apps/core/components/public/js/tinymce/classes/ui/FilePicker.js +85 -0
- data/apps/core/components/public/js/tinymce/classes/ui/FitLayout.js +48 -0
- data/apps/core/components/public/js/tinymce/classes/ui/FlexLayout.js +246 -0
- data/apps/core/components/public/js/tinymce/classes/ui/FloatPanel.js +409 -0
- data/apps/core/components/public/js/tinymce/classes/ui/FlowLayout.js +46 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Form.js +157 -0
- data/apps/core/components/public/js/tinymce/classes/ui/FormItem.js +56 -0
- data/apps/core/components/public/js/tinymce/classes/ui/FormatControls.js +535 -0
- data/apps/core/components/public/js/tinymce/classes/ui/GridLayout.js +233 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Iframe.js +85 -0
- data/apps/core/components/public/js/tinymce/classes/ui/InfoBox.js +93 -0
- data/apps/core/components/public/js/tinymce/classes/ui/KeyboardNavigation.js +406 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Label.js +144 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Layout.js +120 -0
- data/apps/core/components/public/js/tinymce/classes/ui/ListBox.js +152 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Menu.js +195 -0
- data/apps/core/components/public/js/tinymce/classes/ui/MenuBar.js +33 -0
- data/apps/core/components/public/js/tinymce/classes/ui/MenuButton.js +268 -0
- data/apps/core/components/public/js/tinymce/classes/ui/MenuItem.js +336 -0
- data/apps/core/components/public/js/tinymce/classes/ui/MessageBox.js +202 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Movable.js +200 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Notification.js +154 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Panel.js +67 -0
- data/apps/core/components/public/js/tinymce/classes/ui/PanelButton.js +114 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Path.js +127 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Progress.js +81 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Radio.js +29 -0
- data/apps/core/components/public/js/tinymce/classes/ui/ReflowQueue.js +79 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Resizable.js +68 -0
- data/apps/core/components/public/js/tinymce/classes/ui/ResizeHandle.js +86 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Scrollable.js +141 -0
- data/apps/core/components/public/js/tinymce/classes/ui/SelectBox.js +106 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Selector.js +369 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Slider.js +161 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Spacer.js +39 -0
- data/apps/core/components/public/js/tinymce/classes/ui/SplitButton.js +146 -0
- data/apps/core/components/public/js/tinymce/classes/ui/StackLayout.js +34 -0
- data/apps/core/components/public/js/tinymce/classes/ui/TabPanel.js +178 -0
- data/apps/core/components/public/js/tinymce/classes/ui/TextBox.js +208 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Throbber.js +88 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Toolbar.js +56 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Tooltip.js +73 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Widget.js +151 -0
- data/apps/core/components/public/js/tinymce/classes/ui/Window.js +474 -0
- data/apps/core/components/public/js/tinymce/classes/util/Arr.js +153 -0
- data/apps/core/components/public/js/tinymce/classes/util/Class.js +167 -0
- data/apps/core/components/public/js/tinymce/classes/util/Color.js +235 -0
- data/apps/core/components/public/js/tinymce/classes/util/Delay.js +191 -0
- data/apps/core/components/public/js/tinymce/classes/util/EventDispatcher.js +294 -0
- data/apps/core/components/public/js/tinymce/classes/util/Fun.js +87 -0
- data/apps/core/components/public/js/tinymce/classes/util/I18n.js +116 -0
- data/apps/core/components/public/js/tinymce/classes/util/JSON.js +109 -0
- data/apps/core/components/public/js/tinymce/classes/util/JSONP.js +38 -0
- data/apps/core/components/public/js/tinymce/classes/util/JSONRequest.js +110 -0
- data/apps/core/components/public/js/tinymce/classes/util/LocalStorage.js +213 -0
- data/apps/core/components/public/js/tinymce/classes/util/Observable.js +129 -0
- data/apps/core/components/public/js/tinymce/classes/util/Promise.js +200 -0
- data/apps/core/components/public/js/tinymce/classes/util/Quirks.js +1701 -0
- data/apps/core/components/public/js/tinymce/classes/util/Tools.js +442 -0
- data/apps/core/components/public/js/tinymce/classes/util/URI.js +411 -0
- data/apps/core/components/public/js/tinymce/classes/util/VK.js +37 -0
- data/apps/core/components/public/js/tinymce/classes/util/XHR.js +110 -0
- data/apps/core/components/public/js/tinymce/jquery.tinymce.min.js +1 -0
- data/apps/core/components/public/js/tinymce/langs/it.js +219 -0
- data/apps/core/components/public/js/tinymce/langs/readme.md +3 -0
- data/apps/core/components/public/js/tinymce/license.txt +504 -0
- data/apps/core/components/public/js/tinymce/plugins/advlist/plugin.js +97 -0
- data/apps/core/components/public/js/tinymce/plugins/advlist/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/anchor/plugin.js +55 -0
- data/apps/core/components/public/js/tinymce/plugins/anchor/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/autolink/plugin.js +204 -0
- data/apps/core/components/public/js/tinymce/plugins/autolink/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/autoresize/plugin.js +162 -0
- data/apps/core/components/public/js/tinymce/plugins/autoresize/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/autosave/plugin.js +165 -0
- data/apps/core/components/public/js/tinymce/plugins/autosave/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/bbcode/plugin.js +123 -0
- data/apps/core/components/public/js/tinymce/plugins/bbcode/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/charmap/plugin.js +450 -0
- data/apps/core/components/public/js/tinymce/plugins/charmap/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/code/plugin.js +60 -0
- data/apps/core/components/public/js/tinymce/plugins/code/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/codesample/classes/Dialog.js +121 -0
- data/apps/core/components/public/js/tinymce/plugins/codesample/classes/Plugin.js +95 -0
- data/apps/core/components/public/js/tinymce/plugins/codesample/classes/Prism.js +937 -0
- data/apps/core/components/public/js/tinymce/plugins/codesample/classes/Utils.js +33 -0
- data/apps/core/components/public/js/tinymce/plugins/codesample/css/prism.css +138 -0
- data/apps/core/components/public/js/tinymce/plugins/codesample/plugin.dev.js +141 -0
- data/apps/core/components/public/js/tinymce/plugins/codesample/plugin.js +1299 -0
- data/apps/core/components/public/js/tinymce/plugins/codesample/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/colorpicker/plugin.js +112 -0
- data/apps/core/components/public/js/tinymce/plugins/colorpicker/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/compat3x/css/dialog.css +118 -0
- data/apps/core/components/public/js/tinymce/plugins/compat3x/img/buttons.png +0 -0
- data/apps/core/components/public/js/tinymce/plugins/compat3x/img/icons.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/compat3x/img/items.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/compat3x/img/menu_arrow.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/compat3x/img/menu_check.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/compat3x/img/progress.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/compat3x/img/tabs.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/compat3x/plugin.js +297 -0
- data/apps/core/components/public/js/tinymce/plugins/compat3x/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/compat3x/tiny_mce_popup.js +542 -0
- data/apps/core/components/public/js/tinymce/plugins/compat3x/utils/editable_selects.js +70 -0
- data/apps/core/components/public/js/tinymce/plugins/compat3x/utils/form_utils.js +210 -0
- data/apps/core/components/public/js/tinymce/plugins/compat3x/utils/mctabs.js +164 -0
- data/apps/core/components/public/js/tinymce/plugins/compat3x/utils/validate.js +252 -0
- data/apps/core/components/public/js/tinymce/plugins/contextmenu/plugin.js +88 -0
- data/apps/core/components/public/js/tinymce/plugins/contextmenu/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/directionality/plugin.js +64 -0
- data/apps/core/components/public/js/tinymce/plugins/directionality/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/img/smiley-cool.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/img/smiley-cry.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/img/smiley-embarassed.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/img/smiley-foot-in-mouth.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/img/smiley-frown.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/img/smiley-innocent.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/img/smiley-kiss.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/img/smiley-laughing.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/img/smiley-money-mouth.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/img/smiley-sealed.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/img/smiley-smile.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/img/smiley-surprised.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/img/smiley-tongue-out.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/img/smiley-undecided.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/img/smiley-wink.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/img/smiley-yell.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/plugin.js +65 -0
- data/apps/core/components/public/js/tinymce/plugins/emoticons/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/example/dialog.html +8 -0
- data/apps/core/components/public/js/tinymce/plugins/example/plugin.js +68 -0
- data/apps/core/components/public/js/tinymce/plugins/example/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/example_dependency/plugin.js +22 -0
- data/apps/core/components/public/js/tinymce/plugins/example_dependency/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/fullpage/plugin.js +490 -0
- data/apps/core/components/public/js/tinymce/plugins/fullpage/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/fullscreen/plugin.js +154 -0
- data/apps/core/components/public/js/tinymce/plugins/fullscreen/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/hr/plugin.js +30 -0
- data/apps/core/components/public/js/tinymce/plugins/hr/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/image/plugin.js +630 -0
- data/apps/core/components/public/js/tinymce/plugins/image/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/imagetools/config/bolt/atomic.js +6 -0
- data/apps/core/components/public/js/tinymce/plugins/imagetools/config/bolt/browser.js +6 -0
- data/apps/core/components/public/js/tinymce/plugins/imagetools/config/bolt/demo.js +8 -0
- data/apps/core/components/public/js/tinymce/plugins/imagetools/config/bolt/prod.js +6 -0
- data/apps/core/components/public/js/tinymce/plugins/imagetools/plugin.js +2668 -0
- data/apps/core/components/public/js/tinymce/plugins/imagetools/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/imagetools/src/demo/html/demo.html +16 -0
- data/apps/core/components/public/js/tinymce/plugins/imagetools/src/demo/js/Demo.js +92 -0
- data/apps/core/components/public/js/tinymce/plugins/imagetools/src/main/js/CropRect.js +214 -0
- data/apps/core/components/public/js/tinymce/plugins/imagetools/src/main/js/Dialog.js +485 -0
- data/apps/core/components/public/js/tinymce/plugins/imagetools/src/main/js/ImagePanel.js +218 -0
- data/apps/core/components/public/js/tinymce/plugins/imagetools/src/main/js/Plugin.js +411 -0
- data/apps/core/components/public/js/tinymce/plugins/imagetools/src/main/js/UndoStack.js +57 -0
- data/apps/core/components/public/js/tinymce/plugins/importcss/plugin.js +227 -0
- data/apps/core/components/public/js/tinymce/plugins/importcss/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/insertdatetime/plugin.js +121 -0
- data/apps/core/components/public/js/tinymce/plugins/insertdatetime/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/layer/plugin.js +225 -0
- data/apps/core/components/public/js/tinymce/plugins/layer/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/legacyoutput/plugin.js +211 -0
- data/apps/core/components/public/js/tinymce/plugins/legacyoutput/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/link/plugin.js +403 -0
- data/apps/core/components/public/js/tinymce/plugins/link/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/lists/plugin.js +885 -0
- data/apps/core/components/public/js/tinymce/plugins/lists/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/media/moxieplayer.swf +0 -0
- data/apps/core/components/public/js/tinymce/plugins/media/plugin.js +878 -0
- data/apps/core/components/public/js/tinymce/plugins/media/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/nonbreaking/plugin.js +53 -0
- data/apps/core/components/public/js/tinymce/plugins/nonbreaking/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/noneditable/plugin.js +101 -0
- data/apps/core/components/public/js/tinymce/plugins/noneditable/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/pagebreak/plugin.js +88 -0
- data/apps/core/components/public/js/tinymce/plugins/pagebreak/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/paste/classes/Clipboard.js +672 -0
- data/apps/core/components/public/js/tinymce/plugins/paste/classes/Plugin.js +121 -0
- data/apps/core/components/public/js/tinymce/plugins/paste/classes/Quirks.js +159 -0
- data/apps/core/components/public/js/tinymce/plugins/paste/classes/Utils.js +140 -0
- data/apps/core/components/public/js/tinymce/plugins/paste/classes/WordFilter.js +500 -0
- data/apps/core/components/public/js/tinymce/plugins/paste/plugin.dev.js +142 -0
- data/apps/core/components/public/js/tinymce/plugins/paste/plugin.js +1708 -0
- data/apps/core/components/public/js/tinymce/plugins/paste/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/preview/plugin.js +88 -0
- data/apps/core/components/public/js/tinymce/plugins/preview/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/print/plugin.js +32 -0
- data/apps/core/components/public/js/tinymce/plugins/print/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/save/plugin.js +98 -0
- data/apps/core/components/public/js/tinymce/plugins/save/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/searchreplace/plugin.js +609 -0
- data/apps/core/components/public/js/tinymce/plugins/searchreplace/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/spellchecker/classes/DomTextMatcher.js +480 -0
- data/apps/core/components/public/js/tinymce/plugins/spellchecker/classes/Plugin.js +439 -0
- data/apps/core/components/public/js/tinymce/plugins/spellchecker/plugin.dev.js +139 -0
- data/apps/core/components/public/js/tinymce/plugins/spellchecker/plugin.js +1026 -0
- data/apps/core/components/public/js/tinymce/plugins/spellchecker/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/tabfocus/plugin.js +120 -0
- data/apps/core/components/public/js/tinymce/plugins/tabfocus/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/table/classes/CellSelection.js +202 -0
- data/apps/core/components/public/js/tinymce/plugins/table/classes/Dialogs.js +824 -0
- data/apps/core/components/public/js/tinymce/plugins/table/classes/Plugin.js +599 -0
- data/apps/core/components/public/js/tinymce/plugins/table/classes/Quirks.js +400 -0
- data/apps/core/components/public/js/tinymce/plugins/table/classes/ResizeBars.js +984 -0
- data/apps/core/components/public/js/tinymce/plugins/table/classes/TableGrid.js +941 -0
- data/apps/core/components/public/js/tinymce/plugins/table/classes/Utils.js +36 -0
- data/apps/core/components/public/js/tinymce/plugins/table/plugin.dev.js +142 -0
- data/apps/core/components/public/js/tinymce/plugins/table/plugin.js +4106 -0
- data/apps/core/components/public/js/tinymce/plugins/table/plugin.min.js +2 -0
- data/apps/core/components/public/js/tinymce/plugins/template/plugin.js +270 -0
- data/apps/core/components/public/js/tinymce/plugins/template/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/textcolor/plugin.js +282 -0
- data/apps/core/components/public/js/tinymce/plugins/textcolor/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/textpattern/plugin.js +268 -0
- data/apps/core/components/public/js/tinymce/plugins/textpattern/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/css/visualblocks.css +135 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/address.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/article.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/aside.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/blockquote.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/div.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/dl.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/figure.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/h1.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/h2.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/h3.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/h4.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/h5.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/h6.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/hgroup.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/ol.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/p.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/pre.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/section.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/img/ul.gif +0 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/plugin.js +86 -0
- data/apps/core/components/public/js/tinymce/plugins/visualblocks/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/visualchars/plugin.js +123 -0
- data/apps/core/components/public/js/tinymce/plugins/visualchars/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/plugins/wordcount/plugin.js +69 -0
- data/apps/core/components/public/js/tinymce/plugins/wordcount/plugin.min.js +1 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/AbsoluteLayout.less +17 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Animations.less +10 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Button.less +172 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/ButtonGroup.less +71 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Checkbox.less +49 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/ColorBox.less +6 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/ColorButton.less +72 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/ColorPicker.less +80 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/ComboBox.less +39 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Container.less +9 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Content.Inline.less +4 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Content.Objects.less +166 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Content.less +27 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/CropRect.less +54 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/FieldSet.less +15 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/FitLayout.less +9 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/FloatPanel.less +69 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/FlowLayout.less +36 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Icons.Ie7.less +136 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Icons.less +180 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Iframe.less +6 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/ImagePanel.less +20 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/InfoBox.less +71 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Label.less +38 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/ListBox.less +26 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Menu.less +34 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/MenuBar.less +32 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/MenuButton.less +34 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/MenuItem.less +142 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Mixins.less +54 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Notification.less +144 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Panel.less +7 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Path.less +45 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Progress.less +34 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Radio.less +1 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Reset.less +32 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/ResizeHandle.less +18 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Scrollable.less +44 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/SelectBox.less +6 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Slider.less +29 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Spacer.less +5 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/SplitButton.less +49 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/StackLayout.less +5 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/TabPanel.less +44 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/TextBox.less +41 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Throbber.less +19 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/TinyMCE.less +159 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/ToolTip.less +129 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Variables.less +214 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/Window.less +127 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/content.inline.min.css +1 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/content.min.css +1 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/fonts/readme.md +1 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/fonts/tinymce-small.eot +0 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/fonts/tinymce-small.json +1277 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/fonts/tinymce-small.svg +63 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/fonts/tinymce-small.ttf +0 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/fonts/tinymce-small.woff +0 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/fonts/tinymce.eot +0 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/fonts/tinymce.json +3381 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/fonts/tinymce.svg +129 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/fonts/tinymce.ttf +0 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/fonts/tinymce.woff +0 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/img/anchor.gif +0 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/img/loader.gif +0 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/img/object.gif +0 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/img/trans.gif +0 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/skin.dev.less +46 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/skin.ie7.dev.less +46 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/skin.ie7.less +2542 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/skin.ie7.min.css +1 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/skin.less +2586 -0
- data/apps/core/components/public/js/tinymce/skins/lightgray/skin.min.css +1 -0
- data/apps/core/components/public/js/tinymce/themes/modern/theme.js +878 -0
- data/apps/core/components/public/js/tinymce/themes/modern/theme.min.js +1 -0
- data/apps/core/components/public/js/tinymce/tinymce.dev.js +286 -0
- data/apps/core/components/public/js/tinymce/tinymce.js +45811 -0
- data/apps/core/components/public/js/tinymce/tinymce.min.js +13 -0
- data/apps/core/forms/widgets/form/form.rb +3 -1
- data/apps/core/forms/widgets/form/form.shtml +1 -0
- data/apps/core/forms/widgets/inputs/search_select/search_select.rb +1 -1
- data/apps/core/forms/widgets/inputs/select/select.rb +1 -1
- data/apps/core/forms/widgets/inputs/select/select.shtml +0 -1
- data/apps/messenger/backends/sms/skebby.rb +1 -1
- data/apps/messenger/controllers/mixins/messenger_helper.rb +23 -5
- data/lib/spiderfw/config/options/spider.rb +1 -1
- data/lib/spiderfw/controller/mixins/visual.rb +2 -0
- data/lib/spiderfw/http/adapters/rack.rb +10 -5
- data/lib/spiderfw/http/http.rb +4 -2
- data/lib/spiderfw/model/base_model.rb +4 -4
- data/lib/spiderfw/model/mappers/db_mapper.rb +4 -2
- data/lib/spiderfw/model/storage/db/adapters/mysql.rb +2 -1
- data/lib/spiderfw/model/storage/db/db_storage.rb +4 -0
- data/lib/spiderfw/spider.rb +6 -0
- data/lib/spiderfw/templates/layout.rb +1 -1
- data/lib/spiderfw/utils/monkey/object.rb +3 -0
- data/spider.gemspec +6 -2
- metadata +539 -42
- data/blueprints/.DS_Store +0 -0
@@ -0,0 +1,204 @@
|
|
1
|
+
/**
|
2
|
+
* EditorObservable.js
|
3
|
+
*
|
4
|
+
* Released under LGPL License.
|
5
|
+
* Copyright (c) 1999-2015 Ephox Corp. All rights reserved
|
6
|
+
*
|
7
|
+
* License: http://www.tinymce.com/license
|
8
|
+
* Contributing: http://www.tinymce.com/contributing
|
9
|
+
*/
|
10
|
+
|
11
|
+
/**
|
12
|
+
* This mixin contains the event logic for the tinymce.Editor class.
|
13
|
+
*
|
14
|
+
* @mixin tinymce.EditorObservable
|
15
|
+
* @extends tinymce.util.Observable
|
16
|
+
*/
|
17
|
+
define("tinymce/EditorObservable", [
|
18
|
+
"tinymce/util/Observable",
|
19
|
+
"tinymce/dom/DOMUtils",
|
20
|
+
"tinymce/util/Tools"
|
21
|
+
], function(Observable, DOMUtils, Tools) {
|
22
|
+
var DOM = DOMUtils.DOM, customEventRootDelegates;
|
23
|
+
|
24
|
+
/**
|
25
|
+
* Returns the event target so for the specified event. Some events fire
|
26
|
+
* only on document, some fire on documentElement etc. This also handles the
|
27
|
+
* custom event root setting where it returns that element instead of the body.
|
28
|
+
*
|
29
|
+
* @private
|
30
|
+
* @param {tinymce.Editor} editor Editor instance to get event target from.
|
31
|
+
* @param {String} eventName Name of the event for example "click".
|
32
|
+
* @return {Element/Document} HTML Element or document target to bind on.
|
33
|
+
*/
|
34
|
+
function getEventTarget(editor, eventName) {
|
35
|
+
if (eventName == 'selectionchange') {
|
36
|
+
return editor.getDoc();
|
37
|
+
}
|
38
|
+
|
39
|
+
// Need to bind mousedown/mouseup etc to document not body in iframe mode
|
40
|
+
// Since the user might click on the HTML element not the BODY
|
41
|
+
if (!editor.inline && /^mouse|click|contextmenu|drop|dragover|dragend/.test(eventName)) {
|
42
|
+
return editor.getDoc().documentElement;
|
43
|
+
}
|
44
|
+
|
45
|
+
// Bind to event root instead of body if it's defined
|
46
|
+
if (editor.settings.event_root) {
|
47
|
+
if (!editor.eventRoot) {
|
48
|
+
editor.eventRoot = DOM.select(editor.settings.event_root)[0];
|
49
|
+
}
|
50
|
+
|
51
|
+
return editor.eventRoot;
|
52
|
+
}
|
53
|
+
|
54
|
+
return editor.getBody();
|
55
|
+
}
|
56
|
+
|
57
|
+
/**
|
58
|
+
* Binds a event delegate for the specified name this delegate will fire
|
59
|
+
* the event to the editor dispatcher.
|
60
|
+
*
|
61
|
+
* @private
|
62
|
+
* @param {tinymce.Editor} editor Editor instance to get event target from.
|
63
|
+
* @param {String} eventName Name of the event for example "click".
|
64
|
+
*/
|
65
|
+
function bindEventDelegate(editor, eventName) {
|
66
|
+
var eventRootElm = getEventTarget(editor, eventName), delegate;
|
67
|
+
|
68
|
+
function isListening(editor) {
|
69
|
+
return !editor.hidden && !editor.readonly;
|
70
|
+
}
|
71
|
+
|
72
|
+
if (!editor.delegates) {
|
73
|
+
editor.delegates = {};
|
74
|
+
}
|
75
|
+
|
76
|
+
if (editor.delegates[eventName]) {
|
77
|
+
return;
|
78
|
+
}
|
79
|
+
|
80
|
+
if (editor.settings.event_root) {
|
81
|
+
if (!customEventRootDelegates) {
|
82
|
+
customEventRootDelegates = {};
|
83
|
+
editor.editorManager.on('removeEditor', function() {
|
84
|
+
var name;
|
85
|
+
|
86
|
+
if (!editor.editorManager.activeEditor) {
|
87
|
+
if (customEventRootDelegates) {
|
88
|
+
for (name in customEventRootDelegates) {
|
89
|
+
editor.dom.unbind(getEventTarget(editor, name));
|
90
|
+
}
|
91
|
+
|
92
|
+
customEventRootDelegates = null;
|
93
|
+
}
|
94
|
+
}
|
95
|
+
});
|
96
|
+
}
|
97
|
+
|
98
|
+
if (customEventRootDelegates[eventName]) {
|
99
|
+
return;
|
100
|
+
}
|
101
|
+
|
102
|
+
delegate = function(e) {
|
103
|
+
var target = e.target, editors = editor.editorManager.editors, i = editors.length;
|
104
|
+
|
105
|
+
while (i--) {
|
106
|
+
var body = editors[i].getBody();
|
107
|
+
|
108
|
+
if (body === target || DOM.isChildOf(target, body)) {
|
109
|
+
if (isListening(editors[i])) {
|
110
|
+
editors[i].fire(eventName, e);
|
111
|
+
}
|
112
|
+
}
|
113
|
+
}
|
114
|
+
};
|
115
|
+
|
116
|
+
customEventRootDelegates[eventName] = delegate;
|
117
|
+
DOM.bind(eventRootElm, eventName, delegate);
|
118
|
+
} else {
|
119
|
+
delegate = function(e) {
|
120
|
+
if (isListening(editor)) {
|
121
|
+
editor.fire(eventName, e);
|
122
|
+
}
|
123
|
+
};
|
124
|
+
|
125
|
+
DOM.bind(eventRootElm, eventName, delegate);
|
126
|
+
editor.delegates[eventName] = delegate;
|
127
|
+
}
|
128
|
+
}
|
129
|
+
|
130
|
+
var EditorObservable = {
|
131
|
+
/**
|
132
|
+
* Bind any pending event delegates. This gets executed after the target body/document is created.
|
133
|
+
*
|
134
|
+
* @private
|
135
|
+
*/
|
136
|
+
bindPendingEventDelegates: function() {
|
137
|
+
var self = this;
|
138
|
+
|
139
|
+
Tools.each(self._pendingNativeEvents, function(name) {
|
140
|
+
bindEventDelegate(self, name);
|
141
|
+
});
|
142
|
+
},
|
143
|
+
|
144
|
+
/**
|
145
|
+
* Toggles a native event on/off this is called by the EventDispatcher when
|
146
|
+
* the first native event handler is added and when the last native event handler is removed.
|
147
|
+
*
|
148
|
+
* @private
|
149
|
+
*/
|
150
|
+
toggleNativeEvent: function(name, state) {
|
151
|
+
var self = this;
|
152
|
+
|
153
|
+
// Never bind focus/blur since the FocusManager fakes those
|
154
|
+
if (name == "focus" || name == "blur") {
|
155
|
+
return;
|
156
|
+
}
|
157
|
+
|
158
|
+
if (state) {
|
159
|
+
if (self.initialized) {
|
160
|
+
bindEventDelegate(self, name);
|
161
|
+
} else {
|
162
|
+
if (!self._pendingNativeEvents) {
|
163
|
+
self._pendingNativeEvents = [name];
|
164
|
+
} else {
|
165
|
+
self._pendingNativeEvents.push(name);
|
166
|
+
}
|
167
|
+
}
|
168
|
+
} else if (self.initialized) {
|
169
|
+
self.dom.unbind(getEventTarget(self, name), name, self.delegates[name]);
|
170
|
+
delete self.delegates[name];
|
171
|
+
}
|
172
|
+
},
|
173
|
+
|
174
|
+
/**
|
175
|
+
* Unbinds all native event handlers that means delegates, custom events bound using the Events API etc.
|
176
|
+
*
|
177
|
+
* @private
|
178
|
+
*/
|
179
|
+
unbindAllNativeEvents: function() {
|
180
|
+
var self = this, name;
|
181
|
+
|
182
|
+
if (self.delegates) {
|
183
|
+
for (name in self.delegates) {
|
184
|
+
self.dom.unbind(getEventTarget(self, name), name, self.delegates[name]);
|
185
|
+
}
|
186
|
+
|
187
|
+
delete self.delegates;
|
188
|
+
}
|
189
|
+
|
190
|
+
if (!self.inline) {
|
191
|
+
self.getBody().onload = null;
|
192
|
+
self.dom.unbind(self.getWin());
|
193
|
+
self.dom.unbind(self.getDoc());
|
194
|
+
}
|
195
|
+
|
196
|
+
self.dom.unbind(self.getBody());
|
197
|
+
self.dom.unbind(self.getContainer());
|
198
|
+
}
|
199
|
+
};
|
200
|
+
|
201
|
+
EditorObservable = Tools.extend({}, Observable, EditorObservable);
|
202
|
+
|
203
|
+
return EditorObservable;
|
204
|
+
});
|
@@ -0,0 +1,191 @@
|
|
1
|
+
/**
|
2
|
+
* EditorUpload.js
|
3
|
+
*
|
4
|
+
* Released under LGPL License.
|
5
|
+
* Copyright (c) 1999-2015 Ephox Corp. All rights reserved
|
6
|
+
*
|
7
|
+
* License: http://www.tinymce.com/license
|
8
|
+
* Contributing: http://www.tinymce.com/contributing
|
9
|
+
*/
|
10
|
+
|
11
|
+
/**
|
12
|
+
* Handles image uploads, updates undo stack and patches over various internal functions.
|
13
|
+
*
|
14
|
+
* @private
|
15
|
+
* @class tinymce.EditorUpload
|
16
|
+
*/
|
17
|
+
define("tinymce/EditorUpload", [
|
18
|
+
"tinymce/util/Arr",
|
19
|
+
"tinymce/file/Uploader",
|
20
|
+
"tinymce/file/ImageScanner",
|
21
|
+
"tinymce/file/BlobCache"
|
22
|
+
], function(Arr, Uploader, ImageScanner, BlobCache) {
|
23
|
+
return function(editor) {
|
24
|
+
var blobCache = new BlobCache(), uploader, imageScanner, settings = editor.settings;
|
25
|
+
|
26
|
+
function aliveGuard(callback) {
|
27
|
+
return function(result) {
|
28
|
+
if (editor.selection) {
|
29
|
+
return callback(result);
|
30
|
+
}
|
31
|
+
|
32
|
+
return [];
|
33
|
+
};
|
34
|
+
}
|
35
|
+
|
36
|
+
// Replaces strings without regexps to avoid FF regexp to big issue
|
37
|
+
function replaceString(content, search, replace) {
|
38
|
+
var index = 0;
|
39
|
+
|
40
|
+
do {
|
41
|
+
index = content.indexOf(search, index);
|
42
|
+
|
43
|
+
if (index !== -1) {
|
44
|
+
content = content.substring(0, index) + replace + content.substr(index + search.length);
|
45
|
+
index += replace.length - search.length + 1;
|
46
|
+
}
|
47
|
+
} while (index !== -1);
|
48
|
+
|
49
|
+
return content;
|
50
|
+
}
|
51
|
+
|
52
|
+
function replaceImageUrl(content, targetUrl, replacementUrl) {
|
53
|
+
content = replaceString(content, 'src="' + targetUrl + '"', 'src="' + replacementUrl + '"');
|
54
|
+
content = replaceString(content, 'data-mce-src="' + targetUrl + '"', 'data-mce-src="' + replacementUrl + '"');
|
55
|
+
|
56
|
+
return content;
|
57
|
+
}
|
58
|
+
|
59
|
+
function replaceUrlInUndoStack(targetUrl, replacementUrl) {
|
60
|
+
Arr.each(editor.undoManager.data, function(level) {
|
61
|
+
level.content = replaceImageUrl(level.content, targetUrl, replacementUrl);
|
62
|
+
});
|
63
|
+
}
|
64
|
+
|
65
|
+
function openNotification() {
|
66
|
+
return editor.notificationManager.open({
|
67
|
+
text: editor.translate('Image uploading...'),
|
68
|
+
type: 'info',
|
69
|
+
timeout: -1,
|
70
|
+
progressBar: true
|
71
|
+
});
|
72
|
+
}
|
73
|
+
|
74
|
+
function uploadImages(callback) {
|
75
|
+
if (!uploader) {
|
76
|
+
uploader = new Uploader({
|
77
|
+
url: settings.images_upload_url,
|
78
|
+
basePath: settings.images_upload_base_path,
|
79
|
+
credentials: settings.images_upload_credentials,
|
80
|
+
handler: settings.images_upload_handler
|
81
|
+
});
|
82
|
+
}
|
83
|
+
|
84
|
+
return scanForImages().then(aliveGuard(function(imageInfos) {
|
85
|
+
var blobInfos;
|
86
|
+
|
87
|
+
blobInfos = Arr.map(imageInfos, function(imageInfo) {
|
88
|
+
return imageInfo.blobInfo;
|
89
|
+
});
|
90
|
+
|
91
|
+
return uploader.upload(blobInfos, openNotification).then(aliveGuard(function(result) {
|
92
|
+
result = Arr.map(result, function(uploadInfo, index) {
|
93
|
+
var image = imageInfos[index].image;
|
94
|
+
|
95
|
+
if (uploadInfo.status) {
|
96
|
+
replaceUrlInUndoStack(image.src, uploadInfo.url);
|
97
|
+
|
98
|
+
editor.$(image).attr({
|
99
|
+
src: uploadInfo.url,
|
100
|
+
'data-mce-src': editor.convertURL(uploadInfo.url, 'src')
|
101
|
+
});
|
102
|
+
}
|
103
|
+
|
104
|
+
return {
|
105
|
+
element: image,
|
106
|
+
status: uploadInfo.status
|
107
|
+
};
|
108
|
+
});
|
109
|
+
|
110
|
+
if (callback) {
|
111
|
+
callback(result);
|
112
|
+
}
|
113
|
+
|
114
|
+
return result;
|
115
|
+
}));
|
116
|
+
}));
|
117
|
+
}
|
118
|
+
|
119
|
+
function uploadImagesAuto(callback) {
|
120
|
+
if (settings.automatic_uploads !== false) {
|
121
|
+
return uploadImages(callback);
|
122
|
+
}
|
123
|
+
}
|
124
|
+
|
125
|
+
function scanForImages() {
|
126
|
+
if (!imageScanner) {
|
127
|
+
imageScanner = new ImageScanner(blobCache);
|
128
|
+
}
|
129
|
+
|
130
|
+
return imageScanner.findAll(editor.getBody(), settings.images_dataimg_filter).then(aliveGuard(function(result) {
|
131
|
+
Arr.each(result, function(resultItem) {
|
132
|
+
replaceUrlInUndoStack(resultItem.image.src, resultItem.blobInfo.blobUri());
|
133
|
+
resultItem.image.src = resultItem.blobInfo.blobUri();
|
134
|
+
});
|
135
|
+
|
136
|
+
return result;
|
137
|
+
}));
|
138
|
+
}
|
139
|
+
|
140
|
+
function destroy() {
|
141
|
+
blobCache.destroy();
|
142
|
+
imageScanner = uploader = null;
|
143
|
+
}
|
144
|
+
|
145
|
+
function replaceBlobWithBase64(content) {
|
146
|
+
return content.replace(/src="(blob:[^"]+)"/g, function(match, blobUri) {
|
147
|
+
var blobInfo = blobCache.getByUri(blobUri);
|
148
|
+
|
149
|
+
if (!blobInfo) {
|
150
|
+
blobInfo = Arr.reduce(editor.editorManager.editors, function(result, editor) {
|
151
|
+
return result || editor.editorUpload.blobCache.getByUri(blobUri);
|
152
|
+
}, null);
|
153
|
+
}
|
154
|
+
|
155
|
+
if (blobInfo) {
|
156
|
+
return 'src="data:' + blobInfo.blob().type + ';base64,' + blobInfo.base64() + '"';
|
157
|
+
}
|
158
|
+
|
159
|
+
return match;
|
160
|
+
});
|
161
|
+
}
|
162
|
+
|
163
|
+
editor.on('setContent', function() {
|
164
|
+
if (editor.settings.automatic_uploads !== false) {
|
165
|
+
uploadImagesAuto();
|
166
|
+
} else {
|
167
|
+
scanForImages();
|
168
|
+
}
|
169
|
+
});
|
170
|
+
|
171
|
+
editor.on('RawSaveContent', function(e) {
|
172
|
+
e.content = replaceBlobWithBase64(e.content);
|
173
|
+
});
|
174
|
+
|
175
|
+
editor.on('getContent', function(e) {
|
176
|
+
if (e.source_view || e.format == 'raw') {
|
177
|
+
return;
|
178
|
+
}
|
179
|
+
|
180
|
+
e.content = replaceBlobWithBase64(e.content);
|
181
|
+
});
|
182
|
+
|
183
|
+
return {
|
184
|
+
blobCache: blobCache,
|
185
|
+
uploadImages: uploadImages,
|
186
|
+
uploadImagesAuto: uploadImagesAuto,
|
187
|
+
scanForImages: scanForImages,
|
188
|
+
destroy: destroy
|
189
|
+
};
|
190
|
+
};
|
191
|
+
});
|
@@ -0,0 +1,676 @@
|
|
1
|
+
/**
|
2
|
+
* EnterKey.js
|
3
|
+
*
|
4
|
+
* Released under LGPL License.
|
5
|
+
* Copyright (c) 1999-2015 Ephox Corp. All rights reserved
|
6
|
+
*
|
7
|
+
* License: http://www.tinymce.com/license
|
8
|
+
* Contributing: http://www.tinymce.com/contributing
|
9
|
+
*/
|
10
|
+
|
11
|
+
/**
|
12
|
+
* Contains logic for handling the enter key to split/generate block elements.
|
13
|
+
*
|
14
|
+
* @private
|
15
|
+
* @class tinymce.EnterKey
|
16
|
+
*/
|
17
|
+
define("tinymce/EnterKey", [
|
18
|
+
"tinymce/dom/TreeWalker",
|
19
|
+
"tinymce/dom/RangeUtils",
|
20
|
+
"tinymce/Env"
|
21
|
+
], function(TreeWalker, RangeUtils, Env) {
|
22
|
+
var isIE = Env.ie && Env.ie < 11;
|
23
|
+
|
24
|
+
return function(editor) {
|
25
|
+
var dom = editor.dom, selection = editor.selection, settings = editor.settings;
|
26
|
+
var undoManager = editor.undoManager, schema = editor.schema, nonEmptyElementsMap = schema.getNonEmptyElements(),
|
27
|
+
moveCaretBeforeOnEnterElementsMap = schema.getMoveCaretBeforeOnEnterElements();
|
28
|
+
|
29
|
+
function handleEnterKey(evt) {
|
30
|
+
var rng, tmpRng, editableRoot, container, offset, parentBlock, documentMode, shiftKey,
|
31
|
+
newBlock, fragment, containerBlock, parentBlockName, containerBlockName, newBlockName, isAfterLastNodeInContainer;
|
32
|
+
|
33
|
+
// Returns true if the block can be split into two blocks or not
|
34
|
+
function canSplitBlock(node) {
|
35
|
+
return node &&
|
36
|
+
dom.isBlock(node) &&
|
37
|
+
!/^(TD|TH|CAPTION|FORM)$/.test(node.nodeName) &&
|
38
|
+
!/^(fixed|absolute)/i.test(node.style.position) &&
|
39
|
+
dom.getContentEditable(node) !== "true";
|
40
|
+
}
|
41
|
+
|
42
|
+
function isTableCell(node) {
|
43
|
+
return node && /^(TD|TH|CAPTION)$/.test(node.nodeName);
|
44
|
+
}
|
45
|
+
|
46
|
+
// Renders empty block on IE
|
47
|
+
function renderBlockOnIE(block) {
|
48
|
+
var oldRng;
|
49
|
+
|
50
|
+
if (dom.isBlock(block)) {
|
51
|
+
oldRng = selection.getRng();
|
52
|
+
block.appendChild(dom.create('span', null, '\u00a0'));
|
53
|
+
selection.select(block);
|
54
|
+
block.lastChild.outerHTML = '';
|
55
|
+
selection.setRng(oldRng);
|
56
|
+
}
|
57
|
+
}
|
58
|
+
|
59
|
+
// Remove the first empty inline element of the block so this: <p><b><em></em></b>x</p> becomes this: <p>x</p>
|
60
|
+
function trimInlineElementsOnLeftSideOfBlock(block) {
|
61
|
+
var node = block, firstChilds = [], i;
|
62
|
+
|
63
|
+
if (!node) {
|
64
|
+
return;
|
65
|
+
}
|
66
|
+
|
67
|
+
// Find inner most first child ex: <p><i><b>*</b></i></p>
|
68
|
+
while ((node = node.firstChild)) {
|
69
|
+
if (dom.isBlock(node)) {
|
70
|
+
return;
|
71
|
+
}
|
72
|
+
|
73
|
+
if (node.nodeType == 1 && !nonEmptyElementsMap[node.nodeName.toLowerCase()]) {
|
74
|
+
firstChilds.push(node);
|
75
|
+
}
|
76
|
+
}
|
77
|
+
|
78
|
+
i = firstChilds.length;
|
79
|
+
while (i--) {
|
80
|
+
node = firstChilds[i];
|
81
|
+
if (!node.hasChildNodes() || (node.firstChild == node.lastChild && node.firstChild.nodeValue === '')) {
|
82
|
+
dom.remove(node);
|
83
|
+
} else {
|
84
|
+
// Remove <a> </a> see #5381
|
85
|
+
if (node.nodeName == "A" && (node.innerText || node.textContent) === ' ') {
|
86
|
+
dom.remove(node);
|
87
|
+
}
|
88
|
+
}
|
89
|
+
}
|
90
|
+
}
|
91
|
+
|
92
|
+
// Moves the caret to a suitable position within the root for example in the first non
|
93
|
+
// pure whitespace text node or before an image
|
94
|
+
function moveToCaretPosition(root) {
|
95
|
+
var walker, node, rng, lastNode = root, tempElm;
|
96
|
+
function firstNonWhiteSpaceNodeSibling(node) {
|
97
|
+
while (node) {
|
98
|
+
if (node.nodeType == 1 || (node.nodeType == 3 && node.data && /[\r\n\s]/.test(node.data))) {
|
99
|
+
return node;
|
100
|
+
}
|
101
|
+
|
102
|
+
node = node.nextSibling;
|
103
|
+
}
|
104
|
+
}
|
105
|
+
|
106
|
+
if (!root) {
|
107
|
+
return;
|
108
|
+
}
|
109
|
+
|
110
|
+
// Old IE versions doesn't properly render blocks with br elements in them
|
111
|
+
// For example <p><br></p> wont be rendered correctly in a contentEditable area
|
112
|
+
// until you remove the br producing <p></p>
|
113
|
+
if (Env.ie && Env.ie < 9 && parentBlock && parentBlock.firstChild) {
|
114
|
+
if (parentBlock.firstChild == parentBlock.lastChild && parentBlock.firstChild.tagName == 'BR') {
|
115
|
+
dom.remove(parentBlock.firstChild);
|
116
|
+
}
|
117
|
+
}
|
118
|
+
|
119
|
+
if (/^(LI|DT|DD)$/.test(root.nodeName)) {
|
120
|
+
var firstChild = firstNonWhiteSpaceNodeSibling(root.firstChild);
|
121
|
+
|
122
|
+
if (firstChild && /^(UL|OL|DL)$/.test(firstChild.nodeName)) {
|
123
|
+
root.insertBefore(dom.doc.createTextNode('\u00a0'), root.firstChild);
|
124
|
+
}
|
125
|
+
}
|
126
|
+
|
127
|
+
rng = dom.createRng();
|
128
|
+
|
129
|
+
// Normalize whitespace to remove empty text nodes. Fix for: #6904
|
130
|
+
// Gecko will be able to place the caret in empty text nodes but it won't render propery
|
131
|
+
// Older IE versions will sometimes crash so for now ignore all IE versions
|
132
|
+
if (!Env.ie) {
|
133
|
+
root.normalize();
|
134
|
+
}
|
135
|
+
|
136
|
+
if (root.hasChildNodes()) {
|
137
|
+
walker = new TreeWalker(root, root);
|
138
|
+
|
139
|
+
while ((node = walker.current())) {
|
140
|
+
if (node.nodeType == 3) {
|
141
|
+
rng.setStart(node, 0);
|
142
|
+
rng.setEnd(node, 0);
|
143
|
+
break;
|
144
|
+
}
|
145
|
+
|
146
|
+
if (moveCaretBeforeOnEnterElementsMap[node.nodeName.toLowerCase()]) {
|
147
|
+
rng.setStartBefore(node);
|
148
|
+
rng.setEndBefore(node);
|
149
|
+
break;
|
150
|
+
}
|
151
|
+
|
152
|
+
lastNode = node;
|
153
|
+
node = walker.next();
|
154
|
+
}
|
155
|
+
|
156
|
+
if (!node) {
|
157
|
+
rng.setStart(lastNode, 0);
|
158
|
+
rng.setEnd(lastNode, 0);
|
159
|
+
}
|
160
|
+
} else {
|
161
|
+
if (root.nodeName == 'BR') {
|
162
|
+
if (root.nextSibling && dom.isBlock(root.nextSibling)) {
|
163
|
+
// Trick on older IE versions to render the caret before the BR between two lists
|
164
|
+
if (!documentMode || documentMode < 9) {
|
165
|
+
tempElm = dom.create('br');
|
166
|
+
root.parentNode.insertBefore(tempElm, root);
|
167
|
+
}
|
168
|
+
|
169
|
+
rng.setStartBefore(root);
|
170
|
+
rng.setEndBefore(root);
|
171
|
+
} else {
|
172
|
+
rng.setStartAfter(root);
|
173
|
+
rng.setEndAfter(root);
|
174
|
+
}
|
175
|
+
} else {
|
176
|
+
rng.setStart(root, 0);
|
177
|
+
rng.setEnd(root, 0);
|
178
|
+
}
|
179
|
+
}
|
180
|
+
|
181
|
+
selection.setRng(rng);
|
182
|
+
|
183
|
+
// Remove tempElm created for old IE:s
|
184
|
+
dom.remove(tempElm);
|
185
|
+
selection.scrollIntoView(root);
|
186
|
+
}
|
187
|
+
|
188
|
+
function setForcedBlockAttrs(node) {
|
189
|
+
var forcedRootBlockName = settings.forced_root_block;
|
190
|
+
|
191
|
+
if (forcedRootBlockName && forcedRootBlockName.toLowerCase() === node.tagName.toLowerCase()) {
|
192
|
+
dom.setAttribs(node, settings.forced_root_block_attrs);
|
193
|
+
}
|
194
|
+
}
|
195
|
+
|
196
|
+
function emptyBlock(elm) {
|
197
|
+
// BR is needed in empty blocks on non IE browsers
|
198
|
+
elm.innerHTML = !isIE ? '<br data-mce-bogus="1">' : '';
|
199
|
+
}
|
200
|
+
|
201
|
+
// Creates a new block element by cloning the current one or creating a new one if the name is specified
|
202
|
+
// This function will also copy any text formatting from the parent block and add it to the new one
|
203
|
+
function createNewBlock(name) {
|
204
|
+
var node = container, block, clonedNode, caretNode, textInlineElements = schema.getTextInlineElements();
|
205
|
+
|
206
|
+
if (name || parentBlockName == "TABLE") {
|
207
|
+
block = dom.create(name || newBlockName);
|
208
|
+
setForcedBlockAttrs(block);
|
209
|
+
} else {
|
210
|
+
block = parentBlock.cloneNode(false);
|
211
|
+
}
|
212
|
+
|
213
|
+
caretNode = block;
|
214
|
+
|
215
|
+
// Clone any parent styles
|
216
|
+
if (settings.keep_styles !== false) {
|
217
|
+
do {
|
218
|
+
if (textInlineElements[node.nodeName]) {
|
219
|
+
// Never clone a caret containers
|
220
|
+
if (node.id == '_mce_caret') {
|
221
|
+
continue;
|
222
|
+
}
|
223
|
+
|
224
|
+
clonedNode = node.cloneNode(false);
|
225
|
+
dom.setAttrib(clonedNode, 'id', ''); // Remove ID since it needs to be document unique
|
226
|
+
|
227
|
+
if (block.hasChildNodes()) {
|
228
|
+
clonedNode.appendChild(block.firstChild);
|
229
|
+
block.appendChild(clonedNode);
|
230
|
+
} else {
|
231
|
+
caretNode = clonedNode;
|
232
|
+
block.appendChild(clonedNode);
|
233
|
+
}
|
234
|
+
}
|
235
|
+
} while ((node = node.parentNode));
|
236
|
+
}
|
237
|
+
|
238
|
+
// BR is needed in empty blocks on non IE browsers
|
239
|
+
if (!isIE) {
|
240
|
+
caretNode.innerHTML = '<br data-mce-bogus="1">';
|
241
|
+
}
|
242
|
+
|
243
|
+
return block;
|
244
|
+
}
|
245
|
+
|
246
|
+
// Returns true/false if the caret is at the start/end of the parent block element
|
247
|
+
function isCaretAtStartOrEndOfBlock(start) {
|
248
|
+
var walker, node, name;
|
249
|
+
|
250
|
+
// Caret is in the middle of a text node like "a|b"
|
251
|
+
if (container.nodeType == 3 && (start ? offset > 0 : offset < container.nodeValue.length)) {
|
252
|
+
return false;
|
253
|
+
}
|
254
|
+
|
255
|
+
// If after the last element in block node edge case for #5091
|
256
|
+
if (container.parentNode == parentBlock && isAfterLastNodeInContainer && !start) {
|
257
|
+
return true;
|
258
|
+
}
|
259
|
+
|
260
|
+
// If the caret if before the first element in parentBlock
|
261
|
+
if (start && container.nodeType == 1 && container == parentBlock.firstChild) {
|
262
|
+
return true;
|
263
|
+
}
|
264
|
+
|
265
|
+
// Caret can be before/after a table
|
266
|
+
if (container.nodeName === "TABLE" || (container.previousSibling && container.previousSibling.nodeName == "TABLE")) {
|
267
|
+
return (isAfterLastNodeInContainer && !start) || (!isAfterLastNodeInContainer && start);
|
268
|
+
}
|
269
|
+
|
270
|
+
// Walk the DOM and look for text nodes or non empty elements
|
271
|
+
walker = new TreeWalker(container, parentBlock);
|
272
|
+
|
273
|
+
// If caret is in beginning or end of a text block then jump to the next/previous node
|
274
|
+
if (container.nodeType == 3) {
|
275
|
+
if (start && offset === 0) {
|
276
|
+
walker.prev();
|
277
|
+
} else if (!start && offset == container.nodeValue.length) {
|
278
|
+
walker.next();
|
279
|
+
}
|
280
|
+
}
|
281
|
+
|
282
|
+
while ((node = walker.current())) {
|
283
|
+
if (node.nodeType === 1) {
|
284
|
+
// Ignore bogus elements
|
285
|
+
if (!node.getAttribute('data-mce-bogus')) {
|
286
|
+
// Keep empty elements like <img /> <input /> but not trailing br:s like <p>text|<br></p>
|
287
|
+
name = node.nodeName.toLowerCase();
|
288
|
+
if (nonEmptyElementsMap[name] && name !== 'br') {
|
289
|
+
return false;
|
290
|
+
}
|
291
|
+
}
|
292
|
+
} else if (node.nodeType === 3 && !/^[ \t\r\n]*$/.test(node.nodeValue)) {
|
293
|
+
return false;
|
294
|
+
}
|
295
|
+
|
296
|
+
if (start) {
|
297
|
+
walker.prev();
|
298
|
+
} else {
|
299
|
+
walker.next();
|
300
|
+
}
|
301
|
+
}
|
302
|
+
|
303
|
+
return true;
|
304
|
+
}
|
305
|
+
|
306
|
+
// Wraps any text nodes or inline elements in the specified forced root block name
|
307
|
+
function wrapSelfAndSiblingsInDefaultBlock(container, offset) {
|
308
|
+
var newBlock, parentBlock, startNode, node, next, rootBlockName, blockName = newBlockName || 'P';
|
309
|
+
|
310
|
+
// Not in a block element or in a table cell or caption
|
311
|
+
parentBlock = dom.getParent(container, dom.isBlock);
|
312
|
+
if (!parentBlock || !canSplitBlock(parentBlock)) {
|
313
|
+
parentBlock = parentBlock || editableRoot;
|
314
|
+
|
315
|
+
if (parentBlock == editor.getBody() || isTableCell(parentBlock)) {
|
316
|
+
rootBlockName = parentBlock.nodeName.toLowerCase();
|
317
|
+
} else {
|
318
|
+
rootBlockName = parentBlock.parentNode.nodeName.toLowerCase();
|
319
|
+
}
|
320
|
+
|
321
|
+
if (!parentBlock.hasChildNodes()) {
|
322
|
+
newBlock = dom.create(blockName);
|
323
|
+
setForcedBlockAttrs(newBlock);
|
324
|
+
parentBlock.appendChild(newBlock);
|
325
|
+
rng.setStart(newBlock, 0);
|
326
|
+
rng.setEnd(newBlock, 0);
|
327
|
+
return newBlock;
|
328
|
+
}
|
329
|
+
|
330
|
+
// Find parent that is the first child of parentBlock
|
331
|
+
node = container;
|
332
|
+
while (node.parentNode != parentBlock) {
|
333
|
+
node = node.parentNode;
|
334
|
+
}
|
335
|
+
|
336
|
+
// Loop left to find start node start wrapping at
|
337
|
+
while (node && !dom.isBlock(node)) {
|
338
|
+
startNode = node;
|
339
|
+
node = node.previousSibling;
|
340
|
+
}
|
341
|
+
|
342
|
+
if (startNode && schema.isValidChild(rootBlockName, blockName.toLowerCase())) {
|
343
|
+
newBlock = dom.create(blockName);
|
344
|
+
setForcedBlockAttrs(newBlock);
|
345
|
+
startNode.parentNode.insertBefore(newBlock, startNode);
|
346
|
+
|
347
|
+
// Start wrapping until we hit a block
|
348
|
+
node = startNode;
|
349
|
+
while (node && !dom.isBlock(node)) {
|
350
|
+
next = node.nextSibling;
|
351
|
+
newBlock.appendChild(node);
|
352
|
+
node = next;
|
353
|
+
}
|
354
|
+
|
355
|
+
// Restore range to it's past location
|
356
|
+
rng.setStart(container, offset);
|
357
|
+
rng.setEnd(container, offset);
|
358
|
+
}
|
359
|
+
}
|
360
|
+
|
361
|
+
return container;
|
362
|
+
}
|
363
|
+
|
364
|
+
// Inserts a block or br before/after or in the middle of a split list of the LI is empty
|
365
|
+
function handleEmptyListItem() {
|
366
|
+
function isFirstOrLastLi(first) {
|
367
|
+
var node = containerBlock[first ? 'firstChild' : 'lastChild'];
|
368
|
+
|
369
|
+
// Find first/last element since there might be whitespace there
|
370
|
+
while (node) {
|
371
|
+
if (node.nodeType == 1) {
|
372
|
+
break;
|
373
|
+
}
|
374
|
+
|
375
|
+
node = node[first ? 'nextSibling' : 'previousSibling'];
|
376
|
+
}
|
377
|
+
|
378
|
+
return node === parentBlock;
|
379
|
+
}
|
380
|
+
|
381
|
+
function getContainerBlock() {
|
382
|
+
var containerBlockParent = containerBlock.parentNode;
|
383
|
+
|
384
|
+
if (/^(LI|DT|DD)$/.test(containerBlockParent.nodeName)) {
|
385
|
+
return containerBlockParent;
|
386
|
+
}
|
387
|
+
|
388
|
+
return containerBlock;
|
389
|
+
}
|
390
|
+
|
391
|
+
if (containerBlock == editor.getBody()) {
|
392
|
+
return;
|
393
|
+
}
|
394
|
+
|
395
|
+
// Check if we are in an nested list
|
396
|
+
var containerBlockParentName = containerBlock.parentNode.nodeName;
|
397
|
+
if (/^(OL|UL|LI)$/.test(containerBlockParentName)) {
|
398
|
+
newBlockName = 'LI';
|
399
|
+
}
|
400
|
+
|
401
|
+
newBlock = newBlockName ? createNewBlock(newBlockName) : dom.create('BR');
|
402
|
+
|
403
|
+
if (isFirstOrLastLi(true) && isFirstOrLastLi()) {
|
404
|
+
if (containerBlockParentName == 'LI') {
|
405
|
+
// Nested list is inside a LI
|
406
|
+
dom.insertAfter(newBlock, getContainerBlock());
|
407
|
+
} else {
|
408
|
+
// Is first and last list item then replace the OL/UL with a text block
|
409
|
+
dom.replace(newBlock, containerBlock);
|
410
|
+
}
|
411
|
+
} else if (isFirstOrLastLi(true)) {
|
412
|
+
if (containerBlockParentName == 'LI') {
|
413
|
+
// List nested in an LI then move the list to a new sibling LI
|
414
|
+
dom.insertAfter(newBlock, getContainerBlock());
|
415
|
+
newBlock.appendChild(dom.doc.createTextNode(' ')); // Needed for IE so the caret can be placed
|
416
|
+
newBlock.appendChild(containerBlock);
|
417
|
+
} else {
|
418
|
+
// First LI in list then remove LI and add text block before list
|
419
|
+
containerBlock.parentNode.insertBefore(newBlock, containerBlock);
|
420
|
+
}
|
421
|
+
} else if (isFirstOrLastLi()) {
|
422
|
+
// Last LI in list then remove LI and add text block after list
|
423
|
+
dom.insertAfter(newBlock, getContainerBlock());
|
424
|
+
renderBlockOnIE(newBlock);
|
425
|
+
} else {
|
426
|
+
// Middle LI in list the split the list and insert a text block in the middle
|
427
|
+
// Extract after fragment and insert it after the current block
|
428
|
+
containerBlock = getContainerBlock();
|
429
|
+
tmpRng = rng.cloneRange();
|
430
|
+
tmpRng.setStartAfter(parentBlock);
|
431
|
+
tmpRng.setEndAfter(containerBlock);
|
432
|
+
fragment = tmpRng.extractContents();
|
433
|
+
|
434
|
+
if (newBlockName == 'LI' && fragment.firstChild.nodeName == 'LI') {
|
435
|
+
newBlock = fragment.firstChild;
|
436
|
+
dom.insertAfter(fragment, containerBlock);
|
437
|
+
} else {
|
438
|
+
dom.insertAfter(fragment, containerBlock);
|
439
|
+
dom.insertAfter(newBlock, containerBlock);
|
440
|
+
}
|
441
|
+
}
|
442
|
+
|
443
|
+
dom.remove(parentBlock);
|
444
|
+
moveToCaretPosition(newBlock);
|
445
|
+
undoManager.add();
|
446
|
+
}
|
447
|
+
|
448
|
+
// Inserts a BR element if the forced_root_block option is set to false or empty string
|
449
|
+
function insertBr() {
|
450
|
+
editor.execCommand("InsertLineBreak", false, evt);
|
451
|
+
}
|
452
|
+
|
453
|
+
// Trims any linebreaks at the beginning of node user for example when pressing enter in a PRE element
|
454
|
+
function trimLeadingLineBreaks(node) {
|
455
|
+
do {
|
456
|
+
if (node.nodeType === 3) {
|
457
|
+
node.nodeValue = node.nodeValue.replace(/^[\r\n]+/, '');
|
458
|
+
}
|
459
|
+
|
460
|
+
node = node.firstChild;
|
461
|
+
} while (node);
|
462
|
+
}
|
463
|
+
|
464
|
+
function getEditableRoot(node) {
|
465
|
+
var root = dom.getRoot(), parent, editableRoot;
|
466
|
+
|
467
|
+
// Get all parents until we hit a non editable parent or the root
|
468
|
+
parent = node;
|
469
|
+
while (parent !== root && dom.getContentEditable(parent) !== "false") {
|
470
|
+
if (dom.getContentEditable(parent) === "true") {
|
471
|
+
editableRoot = parent;
|
472
|
+
}
|
473
|
+
|
474
|
+
parent = parent.parentNode;
|
475
|
+
}
|
476
|
+
|
477
|
+
return parent !== root ? editableRoot : root;
|
478
|
+
}
|
479
|
+
|
480
|
+
// Adds a BR at the end of blocks that only contains an IMG or INPUT since
|
481
|
+
// these might be floated and then they won't expand the block
|
482
|
+
function addBrToBlockIfNeeded(block) {
|
483
|
+
var lastChild;
|
484
|
+
|
485
|
+
// IE will render the blocks correctly other browsers needs a BR
|
486
|
+
if (!isIE) {
|
487
|
+
block.normalize(); // Remove empty text nodes that got left behind by the extract
|
488
|
+
|
489
|
+
// Check if the block is empty or contains a floated last child
|
490
|
+
lastChild = block.lastChild;
|
491
|
+
if (!lastChild || (/^(left|right)$/gi.test(dom.getStyle(lastChild, 'float', true)))) {
|
492
|
+
dom.add(block, 'br');
|
493
|
+
}
|
494
|
+
}
|
495
|
+
}
|
496
|
+
|
497
|
+
function insertNewBlockAfter() {
|
498
|
+
// If the caret is at the end of a header we produce a P tag after it similar to Word unless we are in a hgroup
|
499
|
+
if (/^(H[1-6]|PRE|FIGURE)$/.test(parentBlockName) && containerBlockName != 'HGROUP') {
|
500
|
+
newBlock = createNewBlock(newBlockName);
|
501
|
+
} else {
|
502
|
+
newBlock = createNewBlock();
|
503
|
+
}
|
504
|
+
|
505
|
+
// Split the current container block element if enter is pressed inside an empty inner block element
|
506
|
+
if (settings.end_container_on_empty_block && canSplitBlock(containerBlock) && dom.isEmpty(parentBlock)) {
|
507
|
+
// Split container block for example a BLOCKQUOTE at the current blockParent location for example a P
|
508
|
+
newBlock = dom.split(containerBlock, parentBlock);
|
509
|
+
} else {
|
510
|
+
dom.insertAfter(newBlock, parentBlock);
|
511
|
+
}
|
512
|
+
|
513
|
+
moveToCaretPosition(newBlock);
|
514
|
+
}
|
515
|
+
|
516
|
+
rng = selection.getRng(true);
|
517
|
+
|
518
|
+
// Event is blocked by some other handler for example the lists plugin
|
519
|
+
if (evt.isDefaultPrevented()) {
|
520
|
+
return;
|
521
|
+
}
|
522
|
+
|
523
|
+
// Delete any selected contents
|
524
|
+
if (!rng.collapsed) {
|
525
|
+
editor.execCommand('Delete');
|
526
|
+
return;
|
527
|
+
}
|
528
|
+
|
529
|
+
// Setup range items and newBlockName
|
530
|
+
new RangeUtils(dom).normalize(rng);
|
531
|
+
container = rng.startContainer;
|
532
|
+
offset = rng.startOffset;
|
533
|
+
newBlockName = (settings.force_p_newlines ? 'p' : '') || settings.forced_root_block;
|
534
|
+
newBlockName = newBlockName ? newBlockName.toUpperCase() : '';
|
535
|
+
documentMode = dom.doc.documentMode;
|
536
|
+
shiftKey = evt.shiftKey;
|
537
|
+
|
538
|
+
// Resolve node index
|
539
|
+
if (container.nodeType == 1 && container.hasChildNodes()) {
|
540
|
+
isAfterLastNodeInContainer = offset > container.childNodes.length - 1;
|
541
|
+
|
542
|
+
container = container.childNodes[Math.min(offset, container.childNodes.length - 1)] || container;
|
543
|
+
if (isAfterLastNodeInContainer && container.nodeType == 3) {
|
544
|
+
offset = container.nodeValue.length;
|
545
|
+
} else {
|
546
|
+
offset = 0;
|
547
|
+
}
|
548
|
+
}
|
549
|
+
|
550
|
+
// Get editable root node, normally the body element but sometimes a div or span
|
551
|
+
editableRoot = getEditableRoot(container);
|
552
|
+
|
553
|
+
// If there is no editable root then enter is done inside a contentEditable false element
|
554
|
+
if (!editableRoot) {
|
555
|
+
return;
|
556
|
+
}
|
557
|
+
|
558
|
+
undoManager.beforeChange();
|
559
|
+
|
560
|
+
// If editable root isn't block nor the root of the editor
|
561
|
+
if (!dom.isBlock(editableRoot) && editableRoot != dom.getRoot()) {
|
562
|
+
if (!newBlockName || shiftKey) {
|
563
|
+
insertBr();
|
564
|
+
}
|
565
|
+
|
566
|
+
return;
|
567
|
+
}
|
568
|
+
|
569
|
+
// Wrap the current node and it's sibling in a default block if it's needed.
|
570
|
+
// for example this <td>text|<b>text2</b></td> will become this <td><p>text|<b>text2</p></b></td>
|
571
|
+
// This won't happen if root blocks are disabled or the shiftKey is pressed
|
572
|
+
if ((newBlockName && !shiftKey) || (!newBlockName && shiftKey)) {
|
573
|
+
container = wrapSelfAndSiblingsInDefaultBlock(container, offset);
|
574
|
+
}
|
575
|
+
|
576
|
+
// Find parent block and setup empty block paddings
|
577
|
+
parentBlock = dom.getParent(container, dom.isBlock);
|
578
|
+
containerBlock = parentBlock ? dom.getParent(parentBlock.parentNode, dom.isBlock) : null;
|
579
|
+
|
580
|
+
// Setup block names
|
581
|
+
parentBlockName = parentBlock ? parentBlock.nodeName.toUpperCase() : ''; // IE < 9 & HTML5
|
582
|
+
containerBlockName = containerBlock ? containerBlock.nodeName.toUpperCase() : ''; // IE < 9 & HTML5
|
583
|
+
|
584
|
+
// Enter inside block contained within a LI then split or insert before/after LI
|
585
|
+
if (containerBlockName == 'LI' && !evt.ctrlKey) {
|
586
|
+
parentBlock = containerBlock;
|
587
|
+
parentBlockName = containerBlockName;
|
588
|
+
}
|
589
|
+
|
590
|
+
// Handle enter in list item
|
591
|
+
if (/^(LI|DT|DD)$/.test(parentBlockName)) {
|
592
|
+
if (!newBlockName && shiftKey) {
|
593
|
+
insertBr();
|
594
|
+
return;
|
595
|
+
}
|
596
|
+
|
597
|
+
// Handle enter inside an empty list item
|
598
|
+
if (dom.isEmpty(parentBlock)) {
|
599
|
+
handleEmptyListItem();
|
600
|
+
return;
|
601
|
+
}
|
602
|
+
}
|
603
|
+
|
604
|
+
// Don't split PRE tags but insert a BR instead easier when writing code samples etc
|
605
|
+
if (parentBlockName == 'PRE' && settings.br_in_pre !== false) {
|
606
|
+
if (!shiftKey) {
|
607
|
+
insertBr();
|
608
|
+
return;
|
609
|
+
}
|
610
|
+
} else {
|
611
|
+
// If no root block is configured then insert a BR by default or if the shiftKey is pressed
|
612
|
+
if ((!newBlockName && !shiftKey && parentBlockName != 'LI') || (newBlockName && shiftKey)) {
|
613
|
+
insertBr();
|
614
|
+
return;
|
615
|
+
}
|
616
|
+
}
|
617
|
+
|
618
|
+
// If parent block is root then never insert new blocks
|
619
|
+
if (newBlockName && parentBlock === editor.getBody()) {
|
620
|
+
return;
|
621
|
+
}
|
622
|
+
|
623
|
+
// Default block name if it's not configured
|
624
|
+
newBlockName = newBlockName || 'P';
|
625
|
+
|
626
|
+
// Insert new block before/after the parent block depending on caret location
|
627
|
+
if (isCaretAtStartOrEndOfBlock()) {
|
628
|
+
insertNewBlockAfter();
|
629
|
+
} else if (isCaretAtStartOrEndOfBlock(true)) {
|
630
|
+
// Insert new block before
|
631
|
+
newBlock = parentBlock.parentNode.insertBefore(createNewBlock(), parentBlock);
|
632
|
+
renderBlockOnIE(newBlock);
|
633
|
+
moveToCaretPosition(parentBlock);
|
634
|
+
} else {
|
635
|
+
// Extract after fragment and insert it after the current block
|
636
|
+
tmpRng = rng.cloneRange();
|
637
|
+
tmpRng.setEndAfter(parentBlock);
|
638
|
+
fragment = tmpRng.extractContents();
|
639
|
+
trimLeadingLineBreaks(fragment);
|
640
|
+
newBlock = fragment.firstChild;
|
641
|
+
dom.insertAfter(fragment, parentBlock);
|
642
|
+
trimInlineElementsOnLeftSideOfBlock(newBlock);
|
643
|
+
addBrToBlockIfNeeded(parentBlock);
|
644
|
+
|
645
|
+
if (dom.isEmpty(parentBlock)) {
|
646
|
+
emptyBlock(parentBlock);
|
647
|
+
}
|
648
|
+
|
649
|
+
newBlock.normalize();
|
650
|
+
|
651
|
+
// New block might become empty if it's <p><b>a |</b></p>
|
652
|
+
if (dom.isEmpty(newBlock)) {
|
653
|
+
dom.remove(newBlock);
|
654
|
+
insertNewBlockAfter();
|
655
|
+
} else {
|
656
|
+
moveToCaretPosition(newBlock);
|
657
|
+
}
|
658
|
+
}
|
659
|
+
|
660
|
+
dom.setAttrib(newBlock, 'id', ''); // Remove ID since it needs to be document unique
|
661
|
+
|
662
|
+
// Allow custom handling of new blocks
|
663
|
+
editor.fire('NewBlock', {newBlock: newBlock});
|
664
|
+
|
665
|
+
undoManager.add();
|
666
|
+
}
|
667
|
+
|
668
|
+
editor.on('keydown', function(evt) {
|
669
|
+
if (evt.keyCode == 13) {
|
670
|
+
if (handleEnterKey(evt) !== false) {
|
671
|
+
evt.preventDefault();
|
672
|
+
}
|
673
|
+
}
|
674
|
+
});
|
675
|
+
};
|
676
|
+
});
|