/**
* EditorUpload.js
*
* 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
*/
/**
* Handles image uploads, updates undo stack and patches over various internal functions.
*
* @private
* @class tinymce.EditorUpload
*/
define("tinymce/EditorUpload", [
"tinymce/util/Arr",
"tinymce/file/Uploader",
"tinymce/file/ImageScanner",
"tinymce/file/BlobCache"
], function(Arr, Uploader, ImageScanner, BlobCache) {
return function(editor) {
var blobCache = new BlobCache(), uploader, imageScanner;
function aliveGuard(callback) {
return function(result) {
if (editor.selection) {
return callback(result);
}
return [];
};
}
// Replaces strings without regexps to avoid FF regexp to big issue
function replaceString(content, search, replace) {
var index = 0;
do {
index = content.indexOf(search, index);
if (index !== -1) {
content = content.substring(0, index) + replace + content.substr(index + search.length);
index += replace.length - search.length + 1;
}
} while (index !== -1);
return content;
}
function replaceImageUrl(content, targetUrl, replacementUrl) {
content = replaceString(content, 'src="' + targetUrl + '"', 'src="' + replacementUrl + '"');
content = replaceString(content, 'data-mce-src="' + targetUrl + '"', 'data-mce-src="' + replacementUrl + '"');
return content;
}
function replaceUrlInUndoStack(targetUrl, replacementUrl) {
Arr.each(editor.undoManager.data, function(level) {
level.content = replaceImageUrl(level.content, targetUrl, replacementUrl);
});
}
function uploadImages(callback) {
if (!uploader) {
uploader = new Uploader({
url: editor.settings.images_upload_url,
basePath: editor.settings.images_upload_base_path,
credentials: editor.settings.images_upload_credentials,
handler: editor.settings.images_upload_handler
});
}
return scanForImages().then(aliveGuard(function(imageInfos) {
var blobInfos;
blobInfos = Arr.map(imageInfos, function(imageInfo) {
return imageInfo.blobInfo;
});
return uploader.upload(blobInfos).then(aliveGuard(function(result) {
result = Arr.map(result, function(uploadInfo, index) {
var image = imageInfos[index].image;
replaceUrlInUndoStack(image.src, uploadInfo.url);
editor.$(image).attr({
src: uploadInfo.url,
'data-mce-src': editor.convertURL(uploadInfo.url, 'src')
});
return {
element: image,
status: uploadInfo.status
};
});
if (callback) {
callback(result);
}
return result;
}));
}));
}
function uploadImagesAuto(callback) {
if (editor.settings.automatic_uploads !== false) {
return uploadImages(callback);
}
}
function scanForImages() {
if (!imageScanner) {
imageScanner = new ImageScanner(blobCache);
}
return imageScanner.findAll(editor.getBody()).then(aliveGuard(function(result) {
Arr.each(result, function(resultItem) {
replaceUrlInUndoStack(resultItem.image.src, resultItem.blobInfo.blobUri());
resultItem.image.src = resultItem.blobInfo.blobUri();
});
return result;
}));
}
function destroy() {
blobCache.destroy();
imageScanner = uploader = null;
}
function replaceBlobWithBase64(content) {
return content.replace(/src="(blob:[^"]+)"/g, function(match, blobUri) {
var blobInfo = blobCache.getByUri(blobUri);
if (!blobInfo) {
blobInfo = Arr.reduce(editor.editorManager.editors, function(result, editor) {
return result || editor.editorUpload.blobCache.getByUri(blobUri);
}, null);
}
if (blobInfo) {
return 'src="data:' + blobInfo.blob().type + ';base64,' + blobInfo.base64() + '"';
}
return match;
});
}
editor.on('setContent', function() {
if (editor.settings.automatic_uploads !== false) {
uploadImagesAuto();
} else {
scanForImages();
}
});
editor.on('RawSaveContent', function(e) {
e.content = replaceBlobWithBase64(e.content);
});
editor.on('getContent', function(e) {
if (e.source_view || e.format == 'raw') {
return;
}
e.content = replaceBlobWithBase64(e.content);
});
return {
blobCache: blobCache,
uploadImages: uploadImages,
uploadImagesAuto: uploadImagesAuto,
scanForImages: scanForImages,
destroy: destroy
};
};
});
|