X-Git-Url: https://scripts.mit.edu/gitweb/autoinstalls/wordpress.git/blobdiff_plain/af50974463450c98503e763a7836a50e260461a9..refs/tags/wordpress-4.5:/wp-includes/js/tinymce/plugins/image/plugin.js diff --git a/wp-includes/js/tinymce/plugins/image/plugin.js b/wp-includes/js/tinymce/plugins/image/plugin.js index a478da5c..a385f3d6 100644 --- a/wp-includes/js/tinymce/plugins/image/plugin.js +++ b/wp-includes/js/tinymce/plugins/image/plugin.js @@ -1,8 +1,8 @@ /** * plugin.js * - * Copyright, Moxiecode Systems AB * Released under LGPL License. + * Copyright (c) 1999-2015 Ephox Corp. All rights reserved * * License: http://www.tinymce.com/license * Contributing: http://www.tinymce.com/contributing @@ -23,7 +23,7 @@ tinymce.PluginManager.add('image', function(editor) { } img.onload = function() { - done(img.clientWidth, img.clientHeight); + done(Math.max(img.width, img.clientWidth), Math.max(img.height, img.clientHeight)); }; img.onerror = function() { @@ -67,14 +67,14 @@ tinymce.PluginManager.add('image', function(editor) { return function() { var imageList = editor.settings.image_list; - if (typeof(imageList) == "string") { + if (typeof imageList == "string") { tinymce.util.XHR.send({ url: imageList, success: function(text) { callback(tinymce.util.JSON.parse(text)); } }); - } else if (typeof(imageList) == "function") { + } else if (typeof imageList == "function") { imageList(callback); } else { callback(imageList); @@ -83,7 +83,7 @@ tinymce.PluginManager.add('image', function(editor) { } function showDialog(imageList) { - var win, data = {}, dom = editor.dom, imgElm = editor.selection.getNode(); + var win, data = {}, dom = editor.dom, imgElm, figureElm; var width, height, imageListCtrl, classListCtrl, imageDimensions = editor.settings.image_dimensions !== false; function recalcSize() { @@ -102,10 +102,16 @@ tinymce.PluginManager.add('image', function(editor) { if (win.find('#constrain')[0].checked() && width && height && newWidth && newHeight) { if (width != newWidth) { newHeight = Math.round((newWidth / width) * newHeight); - heightCtrl.value(newHeight); + + if (!isNaN(newHeight)) { + heightCtrl.value(newHeight); + } } else { newWidth = Math.round((newHeight / height) * newWidth); - widthCtrl.value(newWidth); + + if (!isNaN(newWidth)) { + widthCtrl.value(newWidth); + } } } @@ -114,6 +120,8 @@ tinymce.PluginManager.add('image', function(editor) { } function onSubmitForm() { + var figureElm, oldImg; + function waitLoad(imgElm) { function selectImage() { imgElm.onload = imgElm.onerror = null; @@ -144,12 +152,16 @@ tinymce.PluginManager.add('image', function(editor) { recalcSize(); data = tinymce.extend(data, win.toJSON()); - var caption = data.caption; // WP + var wpcaption = data.wpcaption; // WP if (!data.alt) { data.alt = ''; } + if (!data.title) { + data.title = ''; + } + if (data.width === '') { data.width = null; } @@ -163,18 +175,21 @@ tinymce.PluginManager.add('image', function(editor) { } // Setup new data excluding style properties + /*eslint dot-notation: 0*/ data = { src: data.src, alt: data.alt, + title: data.title, width: data.width, height: data.height, style: data.style, + caption: data.caption, "class": data["class"] }; editor.undoManager.transact(function() { // WP - var eventData = { node: imgElm, data: data, caption: caption }; + var eventData = { node: imgElm, data: data, wpcaption: wpcaption }; editor.fire( 'wpImageFormSubmit', { imgData: eventData } ); @@ -194,6 +209,10 @@ tinymce.PluginManager.add('image', function(editor) { return; } + if (data.title === "") { + data.title = null; + } + if (!imgElm) { data.id = '__mcenew'; editor.focus(); @@ -204,6 +223,42 @@ tinymce.PluginManager.add('image', function(editor) { dom.setAttribs(imgElm, data); } + editor.editorUpload.uploadImagesAuto(); + + if (data.caption === false) { + if (dom.is(imgElm.parentNode, 'figure.image')) { + figureElm = imgElm.parentNode; + dom.insertAfter(imgElm, figureElm); + dom.remove(figureElm); + } + } + + function isTextBlock(node) { + return editor.schema.getTextBlockElements()[node.nodeName]; + } + + if (data.caption === true) { + if (!dom.is(imgElm.parentNode, 'figure.image')) { + oldImg = imgElm; + imgElm = imgElm.cloneNode(true); + figureElm = dom.create('figure', {'class': 'image'}); + figureElm.appendChild(imgElm); + figureElm.appendChild(dom.create('figcaption', {contentEditable: true}, 'Caption')); + figureElm.contentEditable = false; + + var textBlock = dom.getParent(oldImg, isTextBlock); + if (textBlock) { + dom.split(textBlock, oldImg, figureElm); + } else { + dom.replace(figureElm, oldImg); + } + + editor.selection.select(figureElm); + } + + return; + } + waitLoad(imgElm); }); } @@ -217,7 +272,7 @@ tinymce.PluginManager.add('image', function(editor) { } function srcChange(e) { - var meta = e.meta || {}; + var srcURL, prependURL, absoluteURLPattern, meta = e.meta || {}; if (imageListCtrl) { imageListCtrl.value(editor.convertURL(this.value(), 'src')); @@ -228,16 +283,18 @@ tinymce.PluginManager.add('image', function(editor) { }); if (!meta.width && !meta.height) { - var srcURL = this.value(), - absoluteURLPattern = new RegExp('^(?:[a-z]+:)?//', 'i'), - baseURL = editor.settings.document_base_url; + srcURL = editor.convertURL(this.value(), 'src'); - //Pattern test the src url and make sure we haven't already prepended the url - if (baseURL && !absoluteURLPattern.test(srcURL) && srcURL.substring(0, baseURL.length) !== baseURL) { - this.value(baseURL + srcURL); + // Pattern test the src url and make sure we haven't already prepended the url + prependURL = editor.settings.image_prepend_url; + absoluteURLPattern = new RegExp('^(?:[a-z]+:)?//', 'i'); + if (prependURL && !absoluteURLPattern.test(srcURL) && srcURL.substring(0, prependURL.length) !== prependURL) { + srcURL = prependURL + srcURL; } - getImageSize(this.value(), function(data) { + this.value(srcURL); + + getImageSize(editor.documentBaseURI.toAbsolute(this.value()), function(data) { if (data.width && data.height && imageDimensions) { width = data.width; height = data.height; @@ -249,22 +306,32 @@ tinymce.PluginManager.add('image', function(editor) { } } - width = dom.getAttrib(imgElm, 'width'); - height = dom.getAttrib(imgElm, 'height'); + imgElm = editor.selection.getNode(); + figureElm = dom.getParent(imgElm, 'figure.image'); + if (figureElm) { + imgElm = dom.select('img', figureElm)[0]; + } + + if (imgElm && (imgElm.nodeName != 'IMG' || imgElm.getAttribute('data-mce-object') || imgElm.getAttribute('data-mce-placeholder'))) { + imgElm = null; + } + + if (imgElm) { + width = dom.getAttrib(imgElm, 'width'); + height = dom.getAttrib(imgElm, 'height'); - if (imgElm.nodeName == 'IMG' && !imgElm.getAttribute('data-mce-object') && !imgElm.getAttribute('data-mce-placeholder')) { data = { src: dom.getAttrib(imgElm, 'src'), alt: dom.getAttrib(imgElm, 'alt'), + title: dom.getAttrib(imgElm, 'title'), "class": dom.getAttrib(imgElm, 'class'), width: width, - height: height + height: height, + caption: !!figureElm }; // WP editor.fire( 'wpLoadImageData', { imgData: { data: data, node: imgElm } } ); - } else { - imgElm = null; } if (imageList) { @@ -289,6 +356,7 @@ tinymce.PluginManager.add('image', function(editor) { win.find('#src').value(e.control.value()).fire('change'); }, onPostRender: function() { + /*eslint consistent-this: 0*/ imageListCtrl = this; } }; @@ -329,6 +397,10 @@ tinymce.PluginManager.add('image', function(editor) { generalFormItems.push({name: 'alt', type: 'textbox', label: 'Image description'}); } + if (editor.settings.image_title) { + generalFormItems.push({name: 'title', type: 'textbox', label: 'Image Title'}); + } + if (imageDimensions) { generalFormItems.push({ type: 'container', @@ -348,9 +420,48 @@ tinymce.PluginManager.add('image', function(editor) { generalFormItems.push(classListCtrl); + if (editor.settings.image_caption && tinymce.Env.ceFalse) { + generalFormItems.push({name: 'caption', type: 'checkbox', label: 'Caption'}); + } + // WP editor.fire( 'wpLoadImageForm', { data: generalFormItems } ); + function mergeMargins(css) { + if (css.margin) { + + var splitMargin = css.margin.split(" "); + + switch (splitMargin.length) { + case 1: //margin: toprightbottomleft; + css['margin-top'] = css['margin-top'] || splitMargin[0]; + css['margin-right'] = css['margin-right'] || splitMargin[0]; + css['margin-bottom'] = css['margin-bottom'] || splitMargin[0]; + css['margin-left'] = css['margin-left'] || splitMargin[0]; + break; + case 2: //margin: topbottom rightleft; + css['margin-top'] = css['margin-top'] || splitMargin[0]; + css['margin-right'] = css['margin-right'] || splitMargin[1]; + css['margin-bottom'] = css['margin-bottom'] || splitMargin[0]; + css['margin-left'] = css['margin-left'] || splitMargin[1]; + break; + case 3: //margin: top rightleft bottom; + css['margin-top'] = css['margin-top'] || splitMargin[0]; + css['margin-right'] = css['margin-right'] || splitMargin[1]; + css['margin-bottom'] = css['margin-bottom'] || splitMargin[2]; + css['margin-left'] = css['margin-left'] || splitMargin[1]; + break; + case 4: //margin: top right bottom left; + css['margin-top'] = css['margin-top'] || splitMargin[0]; + css['margin-right'] = css['margin-right'] || splitMargin[1]; + css['margin-bottom'] = css['margin-bottom'] || splitMargin[2]; + css['margin-left'] = css['margin-left'] || splitMargin[3]; + } + delete css.margin; + } + return css; + } + function updateStyle() { function addPixelSuffix(value) { if (value.length > 0 && /^[0-9]+$/.test(value)) { @@ -364,23 +475,73 @@ tinymce.PluginManager.add('image', function(editor) { return; } - var data = win.toJSON(); - var css = dom.parseStyle(data.style); + var data = win.toJSON(), + css = dom.parseStyle(data.style); + + css = mergeMargins(css); + + if (data.vspace) { + css['margin-top'] = css['margin-bottom'] = addPixelSuffix(data.vspace); + } + if (data.hspace) { + css['margin-left'] = css['margin-right'] = addPixelSuffix(data.hspace); + } + if (data.border) { + css['border-width'] = addPixelSuffix(data.border); + } + + win.find('#style').value(dom.serializeStyle(dom.parseStyle(dom.serializeStyle(css)))); + } + + function updateVSpaceHSpaceBorder() { + if (!editor.settings.image_advtab) { + return; + } + + var data = win.toJSON(), + css = dom.parseStyle(data.style); + + win.find('#vspace').value(""); + win.find('#hspace').value(""); - delete css.margin; - css['margin-top'] = css['margin-bottom'] = addPixelSuffix(data.vspace); - css['margin-left'] = css['margin-right'] = addPixelSuffix(data.hspace); - css['border-width'] = addPixelSuffix(data.border); + css = mergeMargins(css); + + //Move opposite equal margins to vspace/hspace field + if ((css['margin-top'] && css['margin-bottom']) || (css['margin-right'] && css['margin-left'])) { + if (css['margin-top'] === css['margin-bottom']) { + win.find('#vspace').value(removePixelSuffix(css['margin-top'])); + } else { + win.find('#vspace').value(''); + } + if (css['margin-right'] === css['margin-left']) { + win.find('#hspace').value(removePixelSuffix(css['margin-right'])); + } else { + win.find('#hspace').value(''); + } + } + + //Move border-width + if (css['border-width']) { + win.find('#border').value(removePixelSuffix(css['border-width'])); + } win.find('#style').value(dom.serializeStyle(dom.parseStyle(dom.serializeStyle(css)))); + } if (editor.settings.image_advtab) { // Parse styles from img if (imgElm) { - data.hspace = removePixelSuffix(imgElm.style.marginLeft || imgElm.style.marginRight); - data.vspace = removePixelSuffix(imgElm.style.marginTop || imgElm.style.marginBottom); - data.border = removePixelSuffix(imgElm.style.borderWidth); + if (imgElm.style.marginLeft && imgElm.style.marginRight && imgElm.style.marginLeft === imgElm.style.marginRight) { + data.hspace = removePixelSuffix(imgElm.style.marginLeft); + } + if (imgElm.style.marginTop && imgElm.style.marginBottom && imgElm.style.marginTop === imgElm.style.marginBottom) { + data.vspace = removePixelSuffix(imgElm.style.marginTop); + } + if (imgElm.style.borderWidth) { + data.border = removePixelSuffix(imgElm.style.borderWidth); + } + data.style = editor.dom.serializeStyle(editor.dom.parseStyle(editor.dom.getAttrib(imgElm, 'style'))); } @@ -404,7 +565,8 @@ tinymce.PluginManager.add('image', function(editor) { { label: 'Style', name: 'style', - type: 'textbox' + type: 'textbox', + onchange: updateVSpaceHSpaceBorder }, { type: 'form', @@ -440,16 +602,45 @@ tinymce.PluginManager.add('image', function(editor) { } } + editor.on('preInit', function() { + function hasImageClass(node) { + var className = node.attr('class'); + return className && /\bimage\b/.test(className); + } + + function toggleContentEditableState(state) { + return function(nodes) { + var i = nodes.length, node; + + function toggleContentEditable(node) { + node.attr('contenteditable', state ? 'true' : null); + } + + while (i--) { + node = nodes[i]; + + if (hasImageClass(node)) { + node.attr('contenteditable', state ? 'false' : null); + tinymce.each(node.getAll('figcaption'), toggleContentEditable); + } + } + }; + } + + editor.parser.addNodeFilter('figure', toggleContentEditableState(true)); + editor.serializer.addNodeFilter('figure', toggleContentEditableState(false)); + }); + editor.addButton('image', { icon: 'image', tooltip: 'Insert/edit image', onclick: createImageList(showDialog), - stateSelector: 'img:not([data-mce-object],[data-mce-placeholder])' + stateSelector: 'img:not([data-mce-object],[data-mce-placeholder]),figure.image' }); editor.addMenuItem('image', { icon: 'image', - text: 'Insert image', + text: 'Insert/edit image', onclick: createImageList(showDialog), context: 'insert', prependToContext: true