/*
Redactor v7.2.0
Updated 20.11.2011
In English http://imperavi.com/
In Russian http://imperavi.ru/
Copyright (c) 2009-2012, Imperavi Ltd.
Dual licensed under the MIT or GPL Version 2 licenses.
Usage: $('#content').redactor();
*/
var isCtrl = false;
var redactorActive = false;
var $table = false;
var $tbody = false;
var $thead = false;
var $current_tr = false;
var $current_td = false;
var deviceAndroid = "android";
var uagent = navigator.userAgent.toLowerCase();
// detect iOS and Android
function isiOS() {
return ((navigator.platform.indexOf("iPhone") != -1) || (navigator.platform.indexOf("iPod") != -1) || (navigator.platform.indexOf("iPad") != -1));
}
function detectAndroid() {
return uagent.search(deviceAndroid) > -1
}
function detectAndroidWebKit() {
if (detectAndroid()) {
return uagent.search('webkit') > -1
}
return false;
}
// redactor
(function($){
// Initialization
$.fn.redactor = function(options) {
if (isiOS() || detectAndroid() || detectAndroidWebKit()) return false;
var obj = new Construct(this, options);
obj.init();
return obj;
};
// Options and variables
function Construct(el, options) {
this.opts = $.extend({
air : false,
autosave : false, // false or url
interval : 20, // seconds
resize : true,
visual : true,
focus : false,
autoclear : true,
removeClasses : false,
removeStyles : true,
convertLinks : true,
autoformat : true,
clearOnInit : false,
overlay : true, // modal overlay
fileUploadCallback : false, // callback function
imageUploadCallback : false, // callback function
// Paths to various handlers
paths : {
// Editor css
stylesheets : ['/assets/imperavi-rails/imperavi/wym.css'],
// Toolbar
toolbar : '/imperavi/toolbar.js',
// Interface translations
language : '/imperavi/language.js',
// Typograf
typograf : '/imperavi/typograf',
// Dialogs
// TODO Add dialogs sizes
dialogs : {
file : '/imperavi/file?r',
fileEdit : '/imperavi/file_edit',
image : '/imperavi/image?r',
imageEdit : '/imperavi/image_edit',
link : '/imperavi/link',
table : '/imperavi/table',
video : '/imperavi/video'
},
// Images
images : {
upload : '/imperavi/images',
download : '/imperavi/images/777',
list : '/imperavi/images.json'
},
// Files
files : {
upload : '/imperavi/files',
download : '/imperavi/files/777', // /tests/file_download.php?file=
remove : '/imperavi/files/777' // /tests/file_delete.php?delete=
}
}
}, options);
this.$el = $(el);
};
// Functionality
Construct.prototype = {
init: function() {
if (this.opts.air) this.opts.toolbar = 'air';
// include lang and toolbar
this.include();
// sizes and id
this.frameID = this.$el.attr('id');
this.width = this.$el.css('width');
this.height = this.$el.css('height');
// modal overlay
if ($('#redactor_imp_modal_overlay').size() == 0) {
this.overlay = $('
');
$('body').prepend(this.overlay);
}
// create container
this.box = $('');
// air box
if (this.opts.air) {
this.air = $('');
}
// create iframe
this.frame = $('');
this.$el.hide();
// append box and frame
$(this.box).insertAfter(this.$el).append(this.frame).append(this.$el);
// toolbar
if (this.opts.toolbar !== false) this.buildToolbar();
// resizer
if (this.opts.resize) {
this.resizer = $('');
$(this.box).append(this.resizer);
$(this.resizer).mousedown(function(e) { this.initResize(e) }.bind2(this));
}
// enable
this.enable(this.$el.val());
$(this.doc).click(function() { this.hideAllDropDown() }.bind2(this));
if (this.opts.autoclear) {
$(this.doc).bind('paste', function(e) {
setTimeout(function () { this.clean(); }.bind2(this), 200);
}.bind2(this));
}
// air enable
this.enableAir();
// doc events
$(this.doc).keydown(function(e) {
if (e.ctrlKey || e.metaKey) isCtrl = true;
if (e.keyCode == 9) { this.execCommand('indent', false); return false; }
if (e.keyCode == 66 && isCtrl) { this.execCommand('bold', 'bold'); return false; }
if (e.keyCode == 73 && isCtrl) { this.execCommand('italic', 'italic'); return false; }
}.bind2(this)).keyup(function(e) {
isCtrl = false;
if (e.keyCode == 13) {
$(this.doc).linkify();
return true;
}
this.syncCode();
}.bind2(this));
// autosave
if (this.opts.autosave) {
setInterval(function() {
var html = this.getHtml();
$.post(this.opts.autosave, { data: html });
}.bind2(this), this.opts.interval*1000);
}
this.formSets();
// focus
if (this.opts.focus) this.focus();
},
/*
API
*/
setHtml: function(html) {
this.doc.body.innerHTML = html;
this.docObserve();
},
getHtml: function() {
return this.doc.body.innerHTML;
},
getCode: function(clear) {
return this.$el.val();
},
focus: function() {
if ($.browser.msie) $(this.frame).load(function() { $(this).get(0).contentWindow.focus(); });
else this.frame.get(0).contentWindow.focus();
},
typo: function() {
var html = this.getHtml();
$.ajax({
url : this.opts.paths.typograf,
type : 'post',
data : 'redactor=' + escape(encodeURIComponent(html)),
success: function(data) {
this.setHtml(data);
}.bind2(this)
});
},
syncCode: function() {
var html = this.getHtml();
html = this.tidyUp(html);
html = html.replace(/\%7B/gi, '{');
html = html.replace(/\%7D/gi, '}');
html = html.replace(/
/gi, '');
html = html.replace(/
/gi, '');
this.$el.val(html);
},
destroy: function() {
var html = this.getCode();
$(this.box).after(this.$el)
this.box.remove();
this.$el.val(html).show();
},
// Include
include: function() {
// lang
$('head').append(
$('')
);
// toolbar
// @tanraya
if (this.opts.toolbar !== false) {
$('head').append($(''));
}
},
// Enable
enable: function(html) {
this.doc = this.contentDocumentFrame(this.frame);
// flash replace
html = html.replace(/\","