Extension pattern
This commit is contained in:
parent
e41f9919b4
commit
c6244d3190
@ -454,10 +454,58 @@ div.dropdown-menu i {
|
||||
max-width: 206px;
|
||||
}
|
||||
|
||||
.tooltip-inner {
|
||||
#modal-settings .accordion-group {
|
||||
border: 0;
|
||||
border-bottom: 1px solid #eee;
|
||||
-webkit-border-radius: inherit;
|
||||
-moz-border-radius: inherit;
|
||||
border-radius: inherit;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
#modal-settings .accordion-heading .checkbox {
|
||||
padding: 8px 15px;
|
||||
margin-bottom: 0px;
|
||||
}
|
||||
|
||||
#modal-settings .accordion-inner {
|
||||
border: 0;
|
||||
padding: 10px 40px;
|
||||
}
|
||||
|
||||
#modal-settings .accordion-inner .form-horizontal .control-group {
|
||||
color: #999;
|
||||
}
|
||||
|
||||
#modal-settings .accordion-inner .form-horizontal .control-label {
|
||||
text-align: left;
|
||||
}
|
||||
|
||||
.accordion-toggle {
|
||||
cursor: help;
|
||||
}
|
||||
|
||||
.nav-tabs > .active > a, .nav-tabs > .active > a:hover, .nav-tabs > .active > a:focus {
|
||||
color: #fff;
|
||||
background-color: #777;
|
||||
border-color: #777;
|
||||
border-bottom-color: transparent;
|
||||
}
|
||||
|
||||
.nav-tabs {
|
||||
border-bottom-color: #eee;
|
||||
}
|
||||
|
||||
.nav > li > a:hover,
|
||||
.nav > li > a:focus {
|
||||
background-color: #eee;
|
||||
}
|
||||
|
||||
.nav-tabs > li > a:hover,
|
||||
.nav-tabs > li > a:focus {
|
||||
border-color: #eee;
|
||||
}
|
||||
|
||||
table {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
35
index.html
35
index.html
@ -542,6 +542,8 @@
|
||||
href="#tabpane-settings-editor" data-toggle="tab">Editor</a></li>
|
||||
<li><a class="action-load-settings"
|
||||
href="#tabpane-settings-publish" data-toggle="tab">Publish</a></li>
|
||||
<li><a class="action-load-settings"
|
||||
href="#tabpane-settings-extensions" data-toggle="tab">Extensions</a></li>
|
||||
<li><a class="action-load-settings"
|
||||
href="#tabpane-settings-utils" data-toggle="tab">Utils</a></li>
|
||||
</ul>
|
||||
@ -570,24 +572,6 @@
|
||||
your own theme...</a></span>
|
||||
</div>
|
||||
</div>
|
||||
<div class="control-group">
|
||||
<label class="control-label" for="input-settings-converter-type">Converter</label>
|
||||
<div class="controls">
|
||||
<select id="input-settings-converter-type">
|
||||
<option value="markdown">Markdown</option>
|
||||
<option value="markdown-extra">Markdown Extra</option>
|
||||
<option value="markdown-extra-prettify">Markdown Extra
|
||||
+ Prettify</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
<div class="control-group">
|
||||
<label class="control-label" for="input-settings-enable-mathjax">MathJax
|
||||
support </label>
|
||||
<div class="controls">
|
||||
<input type="checkbox" id="input-settings-enable-mathjax" />
|
||||
</div>
|
||||
</div>
|
||||
<div class="control-group">
|
||||
<label class="control-label" for="input-settings-lazy-rendering">Lazy
|
||||
rendering <a href="#" class="tooltip-lazy-rendering">(?)</a>
|
||||
@ -596,14 +580,6 @@
|
||||
<input type="checkbox" id="input-settings-lazy-rendering" />
|
||||
</div>
|
||||
</div>
|
||||
<div class="control-group">
|
||||
<label class="control-label" for="input-settings-scroll-link">Scroll
|
||||
Link <a href="#" class="tooltip-scroll-link">(?)</a>
|
||||
</label>
|
||||
<div class="controls">
|
||||
<input type="checkbox" id="input-settings-scroll-link" />
|
||||
</div>
|
||||
</div>
|
||||
<div class="control-group">
|
||||
<label class="control-label"
|
||||
for="input-settings-editor-font-size">Editor font size</label>
|
||||
@ -650,6 +626,13 @@
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="tab-pane" id="tabpane-settings-extensions">
|
||||
<div class="accordion" id="accordion-extensions">
|
||||
</div>
|
||||
<span class="help-block pull-right"><a target="_blank"
|
||||
href="https://github.com/benweet/stackedit/blob/master/doc/theming.md#stackedit-theming-guide">Create
|
||||
your own extension...</a></span>
|
||||
</div>
|
||||
<div class="tab-pane" id="tabpane-settings-utils">
|
||||
<div style="width: 200px; margin: 10px auto;">
|
||||
<a href="#" class="btn btn-block btn-primary action-welcome-file"
|
||||
|
@ -1,4 +1,4 @@
|
||||
define(["jquery", "core", "google-helper"], function($, core, googleHelper) {
|
||||
define(["utils", "google-helper"], function(utils, googleHelper) {
|
||||
|
||||
var PROVIDER_BLOGGER = "blogger";
|
||||
|
||||
@ -31,17 +31,17 @@ define(["jquery", "core", "google-helper"], function($, core, googleHelper) {
|
||||
|
||||
bloggerProvider.newPublishAttributes = function(event) {
|
||||
var publishAttributes = {};
|
||||
var blogUrl = core.getInputValue($("#input-publish-blogger-url"), event);
|
||||
var blogUrl = utils.getInputTextValue("#input-publish-blogger-url", event);
|
||||
if(blogUrl !== undefined) {
|
||||
publishAttributes.blogUrl = core.checkUrl(blogUrl);
|
||||
publishAttributes.blogUrl = utils.checkUrl(blogUrl);
|
||||
}
|
||||
publishAttributes.postId = $("#input-publish-postid").val() || undefined;
|
||||
publishAttributes.postId = utils.getInputTextValue("#input-publish-postid");
|
||||
publishAttributes.labelList = [];
|
||||
var labels = $("#input-publish-labels").val() || undefined;
|
||||
var labels = utils.getInputTextValue("#input-publish-labels");
|
||||
if(labels !== undefined) {
|
||||
publishAttributes.labelList = _.chain(labels.split(","))
|
||||
.map(function(label) {
|
||||
return core.trim(label);
|
||||
return utils.trim(label);
|
||||
}).compact().value();
|
||||
}
|
||||
if(event.isPropagationStopped()) {
|
||||
|
282
js/core.js
282
js/core.js
@ -1,7 +1,7 @@
|
||||
define(
|
||||
[ "jquery", "extension-manager", "bootstrap", "layout", "Markdown.Editor", "storage", "config",
|
||||
[ "jquery", "utils", "extension-manager", "bootstrap", "layout", "Markdown.Editor", "storage", "config",
|
||||
"underscore", "FileSaver", "css_browser_selector" ],
|
||||
function($, extensionManager) {
|
||||
function($, utils, extensionManager) {
|
||||
|
||||
var core = {};
|
||||
|
||||
@ -46,7 +46,7 @@ define(
|
||||
return;
|
||||
}
|
||||
if(windowId === undefined) {
|
||||
windowId = core.randomString();
|
||||
windowId = utils.randomString();
|
||||
localStorage["frontWindowId"] = windowId;
|
||||
}
|
||||
var frontWindowId = localStorage["frontWindowId"];
|
||||
@ -62,61 +62,6 @@ define(
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
// Useful function for input control
|
||||
function inputError(element, event) {
|
||||
if(event !== undefined) {
|
||||
element.stop(true, true).addClass("error").delay(1000).switchClass("error");
|
||||
event.stopPropagation();
|
||||
}
|
||||
}
|
||||
core.getInputValue = function(element, event, validationRegex) {
|
||||
var value = element.val();
|
||||
if (value === undefined) {
|
||||
inputError(element, event);
|
||||
return undefined;
|
||||
}
|
||||
// trim
|
||||
value = core.trim(value);
|
||||
if((value.length === 0)
|
||||
|| (validationRegex !== undefined && !value.match(validationRegex))) {
|
||||
inputError(element, event);
|
||||
return undefined;
|
||||
}
|
||||
return value;
|
||||
};
|
||||
core.getInputIntValue = function(element, event, min, max) {
|
||||
var value = core.getInputValue(element, event);
|
||||
if(value === undefined) {
|
||||
return undefined;
|
||||
}
|
||||
value = parseInt(value);
|
||||
if((value === NaN)
|
||||
|| (min !== undefined && value < min)
|
||||
|| (max !== undefined && value > max)) {
|
||||
inputError(element, event);
|
||||
return undefined;
|
||||
}
|
||||
return value;
|
||||
};
|
||||
core.resetModalInputs = function() {
|
||||
$(".modal input[type=text]:not([disabled]), .modal input[type=password]").val("");
|
||||
};
|
||||
core.trim = function(str) {
|
||||
return str.replace(/^\s+|\s+$/g, '');
|
||||
};
|
||||
core.checkUrl = function(url, addSlash) {
|
||||
if(!url) {
|
||||
return url;
|
||||
}
|
||||
if(url.indexOf("http") !== 0) {
|
||||
url = "http://" + url;
|
||||
}
|
||||
if(addSlash && url.indexOf("/", url.length - 1) === -1) {
|
||||
url += "/";
|
||||
}
|
||||
return url;
|
||||
};
|
||||
|
||||
// Export data on disk
|
||||
core.saveFile = function(content, filename) {
|
||||
@ -126,7 +71,7 @@ define(
|
||||
}
|
||||
else {
|
||||
var uriContent = "data:application/octet-stream;base64,"
|
||||
+ core.encodeBase64(content);
|
||||
+ utils.encodeBase64(content);
|
||||
window.open(uriContent, 'file');
|
||||
}
|
||||
};
|
||||
@ -202,11 +147,8 @@ define(
|
||||
|
||||
// Setting management
|
||||
core.settings = {
|
||||
converterType : "markdown-extra-prettify",
|
||||
enableMathJax : true,
|
||||
lazyRendering : true,
|
||||
layoutOrientation : "horizontal",
|
||||
scrollLink : true,
|
||||
lazyRendering : true,
|
||||
editorFontSize : 14,
|
||||
defaultContent: "\n\n\n> Written with [StackEdit](http://benweet.github.io/stackedit/).",
|
||||
commitMsg : "Published by http://benweet.github.io/stackedit",
|
||||
@ -217,66 +159,58 @@ define(
|
||||
'</head>\n',
|
||||
'<body><%= documentHTML %></body>\n',
|
||||
'</html>'].join(""),
|
||||
sshProxy : SSH_PROXY_URL,
|
||||
sshConnectionList : []
|
||||
sshProxy : SSH_PROXY_URL
|
||||
};
|
||||
|
||||
core.loadSettings = function() {
|
||||
if (localStorage.settings) {
|
||||
$.extend(core.settings, JSON.parse(localStorage.settings));
|
||||
}
|
||||
if (_.has(localStorage, "settings")) {
|
||||
_.extend(core.settings, JSON.parse(localStorage.settings));
|
||||
}
|
||||
|
||||
core.loadSettings = function() {
|
||||
|
||||
// Layout orientation
|
||||
$("input:radio[name=radio-layout-orientation][value="
|
||||
+ core.settings.layoutOrientation + "]").prop("checked", true);
|
||||
// Scroll Link
|
||||
$("#input-settings-scroll-link").prop("checked", core.settings.scrollLink);
|
||||
utils.setInputRadio("radio-layout-orientation", core.settings.layoutOrientation);
|
||||
// Theme
|
||||
$("#input-settings-theme").val(localStorage.theme);
|
||||
// Converter type
|
||||
$("#input-settings-converter-type").val(core.settings.converterType);
|
||||
// MathJax
|
||||
$("#input-settings-enable-mathjax").prop("checked", core.settings.enableMathJax);
|
||||
utils.setInputValue("#input-settings-theme", localStorage.theme);
|
||||
// Lazy rendering
|
||||
$("#input-settings-lazy-rendering").prop("checked", core.settings.lazyRendering);
|
||||
utils.setInputChecked("#input-settings-lazy-rendering", core.settings.lazyRendering);
|
||||
// Editor font size
|
||||
$("#input-settings-editor-font-size").val(core.settings.editorFontSize);
|
||||
utils.setInputValue("#input-settings-editor-font-size", core.settings.editorFontSize);
|
||||
// Default content
|
||||
$("#textarea-settings-default-content").val(core.settings.defaultContent);
|
||||
utils.setInputValue("#textarea-settings-default-content", core.settings.defaultContent);
|
||||
// Commit message
|
||||
$("#input-settings-publish-commit-msg").val(core.settings.commitMsg);
|
||||
utils.setInputValue("#input-settings-publish-commit-msg", core.settings.commitMsg);
|
||||
// Template
|
||||
$("#textarea-settings-publish-template").val(core.settings.template);
|
||||
utils.setInputValue("#textarea-settings-publish-template", core.settings.template);
|
||||
// SSH proxy
|
||||
$("#input-settings-ssh-proxy").val(core.settings.sshProxy);
|
||||
utils.setInputValue("#input-settings-ssh-proxy", core.settings.sshProxy);
|
||||
|
||||
// Load extension settings
|
||||
extensionManager.onLoadSettings();
|
||||
};
|
||||
|
||||
core.saveSettings = function(event) {
|
||||
var newSettings = {};
|
||||
|
||||
// Layout orientation
|
||||
newSettings.layoutOrientation = $(
|
||||
"input:radio[name=radio-layout-orientation]:checked").prop("value");
|
||||
newSettings.layoutOrientation = utils.getInputRadio("radio-layout-orientation");
|
||||
// Theme
|
||||
var theme = $("#input-settings-theme").val();
|
||||
// Converter type
|
||||
newSettings.converterType = $("#input-settings-converter-type").val();
|
||||
// MathJax
|
||||
newSettings.enableMathJax = $("#input-settings-enable-mathjax").prop("checked");
|
||||
// Scroll Link
|
||||
newSettings.scrollLink = $("#input-settings-scroll-link").prop("checked");
|
||||
var theme = utils.getInputValue("#input-settings-theme");
|
||||
// Lazy Rendering
|
||||
newSettings.lazyRendering = $("#input-settings-lazy-rendering").prop("checked");
|
||||
newSettings.lazyRendering = utils.getInputChecked("#input-settings-lazy-rendering");
|
||||
// Editor font size
|
||||
newSettings.editorFontSize = core.getInputIntValue($("#input-settings-editor-font-size"), event, 1, 99);
|
||||
newSettings.editorFontSize = utils.getInputIntValue("#input-settings-editor-font-size", event, 1, 99);
|
||||
// Default content
|
||||
newSettings.defaultContent = $("#textarea-settings-default-content").val();
|
||||
newSettings.defaultContent = utils.getInputValue("#textarea-settings-default-content");
|
||||
// Commit message
|
||||
newSettings.commitMsg = core.getInputValue($("#input-settings-publish-commit-msg"), event);
|
||||
newSettings.commitMsg = utils.getInputTextValue("#input-settings-publish-commit-msg", event);
|
||||
// Template
|
||||
newSettings.template = core.getInputValue($("#textarea-settings-publish-template"), event);
|
||||
newSettings.template = utils.getInputTextValue("#textarea-settings-publish-template", event);
|
||||
// SSH proxy
|
||||
newSettings.sshProxy = core.checkUrl(core.getInputValue($("#input-settings-ssh-proxy"), event), true);
|
||||
newSettings.sshProxy = utils.checkUrl(utils.getInputTextValue("#input-settings-ssh-proxy", event), true);
|
||||
|
||||
// Save extension settings
|
||||
newSettings.extensionSettings = {};
|
||||
extensionManager.onSaveSettings(newSettings.extensionSettings, event);
|
||||
|
||||
if(!event.isPropagationStopped()) {
|
||||
$.extend(core.settings, newSettings);
|
||||
@ -428,142 +362,6 @@ define(
|
||||
$("#wmd-undo-button").append($("<i>").addClass("icon-undo"));
|
||||
$("#wmd-redo-button").append($("<i>").addClass("icon-share-alt"));
|
||||
};
|
||||
|
||||
// Base64 conversion
|
||||
core.encodeBase64 = function(str) {
|
||||
if (str.length === 0) {
|
||||
return "";
|
||||
}
|
||||
|
||||
// UTF-8 to byte array
|
||||
var bytes = [], offset = 0, length, char;
|
||||
|
||||
str = encodeURI(str);
|
||||
length = str.length;
|
||||
|
||||
while (offset < length) {
|
||||
char = str[offset];
|
||||
offset += 1;
|
||||
|
||||
if ('%' !== char) {
|
||||
bytes.push(char.charCodeAt(0));
|
||||
} else {
|
||||
char = str[offset] + str[offset + 1];
|
||||
bytes.push(parseInt(char, 16));
|
||||
offset += 2;
|
||||
}
|
||||
}
|
||||
|
||||
// byte array to base64
|
||||
var padchar = '=';
|
||||
var alpha = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/';
|
||||
|
||||
var i, b10;
|
||||
var x = [];
|
||||
|
||||
var imax = bytes.length - bytes.length % 3;
|
||||
|
||||
for (i = 0; i < imax; i += 3) {
|
||||
b10 = (bytes[i] << 16) | (bytes[i+1] << 8) | bytes[i+2];
|
||||
x.push(alpha.charAt(b10 >> 18));
|
||||
x.push(alpha.charAt((b10 >> 12) & 0x3F));
|
||||
x.push(alpha.charAt((b10 >> 6) & 0x3f));
|
||||
x.push(alpha.charAt(b10 & 0x3f));
|
||||
}
|
||||
switch (bytes.length - imax) {
|
||||
case 1:
|
||||
b10 = bytes[i] << 16;
|
||||
x.push(alpha.charAt(b10 >> 18) + alpha.charAt((b10 >> 12) & 0x3F) +
|
||||
padchar + padchar);
|
||||
break;
|
||||
case 2:
|
||||
b10 = (bytes[i] << 16) | (bytes[i+1] << 8);
|
||||
x.push(alpha.charAt(b10 >> 18) + alpha.charAt((b10 >> 12) & 0x3F) +
|
||||
alpha.charAt((b10 >> 6) & 0x3f) + padchar);
|
||||
break;
|
||||
}
|
||||
return x.join('');
|
||||
};
|
||||
|
||||
// CRC32 algorithm
|
||||
var mHash = [ 0, 1996959894, 3993919788, 2567524794, 124634137,
|
||||
1886057615, 3915621685, 2657392035, 249268274, 2044508324,
|
||||
3772115230, 2547177864, 162941995, 2125561021, 3887607047,
|
||||
2428444049, 498536548, 1789927666, 4089016648, 2227061214,
|
||||
450548861, 1843258603, 4107580753, 2211677639, 325883990,
|
||||
1684777152, 4251122042, 2321926636, 335633487, 1661365465,
|
||||
4195302755, 2366115317, 997073096, 1281953886, 3579855332,
|
||||
2724688242, 1006888145, 1258607687, 3524101629, 2768942443,
|
||||
901097722, 1119000684, 3686517206, 2898065728, 853044451,
|
||||
1172266101, 3705015759, 2882616665, 651767980, 1373503546,
|
||||
3369554304, 3218104598, 565507253, 1454621731, 3485111705,
|
||||
3099436303, 671266974, 1594198024, 3322730930, 2970347812,
|
||||
795835527, 1483230225, 3244367275, 3060149565, 1994146192,
|
||||
31158534, 2563907772, 4023717930, 1907459465, 112637215,
|
||||
2680153253, 3904427059, 2013776290, 251722036, 2517215374,
|
||||
3775830040, 2137656763, 141376813, 2439277719, 3865271297,
|
||||
1802195444, 476864866, 2238001368, 4066508878, 1812370925,
|
||||
453092731, 2181625025, 4111451223, 1706088902, 314042704,
|
||||
2344532202, 4240017532, 1658658271, 366619977, 2362670323,
|
||||
4224994405, 1303535960, 984961486, 2747007092, 3569037538,
|
||||
1256170817, 1037604311, 2765210733, 3554079995, 1131014506,
|
||||
879679996, 2909243462, 3663771856, 1141124467, 855842277,
|
||||
2852801631, 3708648649, 1342533948, 654459306, 3188396048,
|
||||
3373015174, 1466479909, 544179635, 3110523913, 3462522015,
|
||||
1591671054, 702138776, 2966460450, 3352799412, 1504918807,
|
||||
783551873, 3082640443, 3233442989, 3988292384, 2596254646,
|
||||
62317068, 1957810842, 3939845945, 2647816111, 81470997, 1943803523,
|
||||
3814918930, 2489596804, 225274430, 2053790376, 3826175755,
|
||||
2466906013, 167816743, 2097651377, 4027552580, 2265490386,
|
||||
503444072, 1762050814, 4150417245, 2154129355, 426522225,
|
||||
1852507879, 4275313526, 2312317920, 282753626, 1742555852,
|
||||
4189708143, 2394877945, 397917763, 1622183637, 3604390888,
|
||||
2714866558, 953729732, 1340076626, 3518719985, 2797360999,
|
||||
1068828381, 1219638859, 3624741850, 2936675148, 906185462,
|
||||
1090812512, 3747672003, 2825379669, 829329135, 1181335161,
|
||||
3412177804, 3160834842, 628085408, 1382605366, 3423369109,
|
||||
3138078467, 570562233, 1426400815, 3317316542, 2998733608,
|
||||
733239954, 1555261956, 3268935591, 3050360625, 752459403,
|
||||
1541320221, 2607071920, 3965973030, 1969922972, 40735498,
|
||||
2617837225, 3943577151, 1913087877, 83908371, 2512341634,
|
||||
3803740692, 2075208622, 213261112, 2463272603, 3855990285,
|
||||
2094854071, 198958881, 2262029012, 4057260610, 1759359992,
|
||||
534414190, 2176718541, 4139329115, 1873836001, 414664567,
|
||||
2282248934, 4279200368, 1711684554, 285281116, 2405801727,
|
||||
4167216745, 1634467795, 376229701, 2685067896, 3608007406,
|
||||
1308918612, 956543938, 2808555105, 3495958263, 1231636301,
|
||||
1047427035, 2932959818, 3654703836, 1088359270, 936918000,
|
||||
2847714899, 3736837829, 1202900863, 817233897, 3183342108,
|
||||
3401237130, 1404277552, 615818150, 3134207493, 3453421203,
|
||||
1423857449, 601450431, 3009837614, 3294710456, 1567103746,
|
||||
711928724, 3020668471, 3272380065, 1510334235, 755167117 ];
|
||||
core.crc32 = function(str) {
|
||||
var n = 0, crc = -1;
|
||||
for ( var i = 0; i < str.length; i++) {
|
||||
n = (crc ^ str.charCodeAt(i)) & 0xFF;
|
||||
crc = (crc >>> 8) ^ mHash[n];
|
||||
}
|
||||
crc = crc ^ (-1);
|
||||
if (crc < 0) {
|
||||
crc = 0xFFFFFFFF + crc + 1;
|
||||
}
|
||||
return crc.toString(16);
|
||||
};
|
||||
|
||||
// Generates a random string
|
||||
core.randomString = function() {
|
||||
return _.random(4294967296).toString(36);
|
||||
};
|
||||
|
||||
// Access a URL parameter
|
||||
core.getURLParameter = function(name) {
|
||||
var regex = new RegExp(name + "=(.+?)(&|$)");
|
||||
try {
|
||||
return decodeURIComponent(regex.exec(location.search)[1]);
|
||||
} catch (e) {
|
||||
return undefined;
|
||||
}
|
||||
};
|
||||
|
||||
// Create an centered popup window
|
||||
core.popupWindow = function(url, title, w, h) {
|
||||
@ -610,9 +408,8 @@ define(
|
||||
});
|
||||
|
||||
core.onReady(function() {
|
||||
extensionManager.init(core.settings.extensionConfig);
|
||||
extensionManager.init(core.settings.extensionSettings);
|
||||
});
|
||||
core.onReady(extensionManager.onReady);
|
||||
core.onReady(function() {
|
||||
|
||||
// Load theme list
|
||||
@ -637,13 +434,13 @@ define(
|
||||
|
||||
// Click events on "insert link" and "insert image" dialog buttons
|
||||
$(".action-insert-link").click(function(e) {
|
||||
var value = core.getInputValue($("#input-insert-link"), e);
|
||||
var value = utils.getInputTextValue($("#input-insert-link"), e);
|
||||
if(value !== undefined) {
|
||||
insertLinkCallback(value);
|
||||
}
|
||||
});
|
||||
$(".action-insert-image").click(function(e) {
|
||||
var value = core.getInputValue($("#input-insert-image"), e);
|
||||
var value = utils.getInputTextValue($("#input-insert-image"), e);
|
||||
if(value !== undefined) {
|
||||
insertLinkCallback(value);
|
||||
}
|
||||
@ -653,11 +450,9 @@ define(
|
||||
});
|
||||
|
||||
// Settings loading/saving
|
||||
core.loadSettings();
|
||||
$(".action-load-settings").click(function() {
|
||||
core.loadSettings();
|
||||
});
|
||||
|
||||
$(".action-apply-settings").click(function(e) {
|
||||
core.saveSettings(e);
|
||||
if(!e.isPropagationStopped()) {
|
||||
@ -667,6 +462,7 @@ define(
|
||||
|
||||
$(".action-default-settings").click(function() {
|
||||
localStorage.removeItem("settings");
|
||||
localStorage.removeItem("theme");
|
||||
window.location.reload();
|
||||
});
|
||||
|
||||
@ -723,7 +519,7 @@ define(
|
||||
html: true,
|
||||
container: '#modal-settings',
|
||||
placement: 'right',
|
||||
title: 'Thanks for supporting StackEdit by adding a backlink in your documents!'
|
||||
title: 'Thank you for supporting StackEdit by adding a backlink in your documents!'
|
||||
});
|
||||
$(".tooltip-template").tooltip({
|
||||
html: true,
|
||||
|
@ -1,4 +1,4 @@
|
||||
define(["jquery", "core", "dropbox-helper"], function($, core, dropboxHelper) {
|
||||
define(["core", "utils", "dropbox-helper"], function(core, utils, dropboxHelper) {
|
||||
|
||||
var PROVIDER_DROPBOX = "dropbox";
|
||||
|
||||
@ -28,7 +28,7 @@ define(["jquery", "core", "dropbox-helper"], function($, core, dropboxHelper) {
|
||||
syncAttributes.provider = PROVIDER_DROPBOX;
|
||||
syncAttributes.path = path;
|
||||
syncAttributes.version = versionTag;
|
||||
syncAttributes.contentCRC = core.crc32(content);
|
||||
syncAttributes.contentCRC = utils.crc32(content);
|
||||
return syncAttributes;
|
||||
}
|
||||
|
||||
@ -107,12 +107,12 @@ define(["jquery", "core", "dropbox-helper"], function($, core, dropboxHelper) {
|
||||
}
|
||||
|
||||
dropboxProvider.exportFile = function(event, title, content, callback) {
|
||||
var path = core.getInputValue($("#input-sync-export-dropbox-path"), event);
|
||||
var path = utils.getInputTextValue("#input-sync-export-dropbox-path", event);
|
||||
exportFileToPath(path, title, content, callback);
|
||||
};
|
||||
|
||||
dropboxProvider.exportManual = function(event, title, content, callback) {
|
||||
var path = core.getInputValue($("#input-sync-manual-dropbox-path"), event);
|
||||
var path = utils.getInputTextValue("#input-sync-manual-dropbox-path", event);
|
||||
exportFileToPath(path, title, content, callback);
|
||||
};
|
||||
|
||||
@ -191,9 +191,9 @@ define(["jquery", "core", "dropbox-helper"], function($, core, dropboxHelper) {
|
||||
}
|
||||
var syncAttributes = change.syncAttributes;
|
||||
var localContent = localStorage[fileIndex + ".content"];
|
||||
var localContentChanged = syncAttributes.contentCRC != core.crc32(localContent);
|
||||
var localContentChanged = syncAttributes.contentCRC != utils.crc32(localContent);
|
||||
var file = change.stat;
|
||||
var remoteContentCRC = core.crc32(file.content);
|
||||
var remoteContentCRC = utils.crc32(file.content);
|
||||
var remoteContentChanged = syncAttributes.contentCRC != remoteContentCRC;
|
||||
var fileContentChanged = localContent != file.content;
|
||||
// Conflict detection
|
||||
@ -236,7 +236,7 @@ define(["jquery", "core", "dropbox-helper"], function($, core, dropboxHelper) {
|
||||
|
||||
dropboxProvider.newPublishAttributes = function(event) {
|
||||
var publishAttributes = {};
|
||||
publishAttributes.path = core.getInputValue($("#input-publish-dropbox-path"), event);
|
||||
publishAttributes.path = utils.getInputTextValue("#input-publish-dropbox-path", event);
|
||||
if(event.isPropagationStopped()) {
|
||||
return undefined;
|
||||
}
|
||||
|
@ -1,24 +1,27 @@
|
||||
define( [
|
||||
"jquery",
|
||||
"utils",
|
||||
"underscore",
|
||||
"bootstrap",
|
||||
"extensions/notifications",
|
||||
"extensions/markdown-extra",
|
||||
"extensions/math-jax",
|
||||
"extensions/scroll-link"
|
||||
], function() {
|
||||
], function($, utils) {
|
||||
|
||||
var extensionManager = {};
|
||||
|
||||
// Create a map with providerId: providerObject
|
||||
var extensionList = _.chain(arguments)
|
||||
.map(function(argument) {
|
||||
return argument && argument.extensionId && argument;
|
||||
return _.isObject(argument) && argument.extensionId && argument;
|
||||
}).compact().value();
|
||||
|
||||
// Return every named callbacks implemented in extensions
|
||||
function getExtensionCallbackList(callbackName) {
|
||||
return _.chain(extensionList)
|
||||
.map(function(extension) {
|
||||
return extension[callbackName];
|
||||
return extension.config.enabled && extension[callbackName];
|
||||
}).compact().value();
|
||||
}
|
||||
|
||||
@ -38,39 +41,89 @@ define( [
|
||||
extensionManager[callbackName] = createCallback(callbackName);
|
||||
}
|
||||
|
||||
extensionManager.init = function(extensionConfigMap) {
|
||||
// Set the extension configuration
|
||||
extensionConfigMap = extensionConfigMap || {};
|
||||
_.each(extensionList, function(extension) {
|
||||
extension.config = _.extend({}, extension.defaultConfig, extensionConfigMap[extension.extensionId]);
|
||||
});
|
||||
};
|
||||
|
||||
addCallback("onReady");
|
||||
addCallback("onMessage");
|
||||
addCallback("onError");
|
||||
addCallback("onOfflineChanged");
|
||||
addCallback("onLayoutConfigure");
|
||||
addCallback("onLayoutCreated");
|
||||
addCallback("onEditorConfigure");
|
||||
var accordionTmpl = [
|
||||
'<div class="accordion-group">',
|
||||
'<div class="accordion-heading">',
|
||||
'<label class="checkbox pull-right">',
|
||||
'<input id="input-enable-extension-<%= extensionId %>" type="checkbox" <% if(!optional) { %> disabled <% } %>> enabled',
|
||||
'</label>',
|
||||
'<a id="accordion-toggle-test" data-toggle="collapse" data-parent="#accordion-extensions" class="accordion-toggle" href="#collapse-<%= extensionId %>">',
|
||||
'<%= extensionName %>',
|
||||
'</a>',
|
||||
'</div>',
|
||||
'<div id="collapse-<%= extensionId %>" class="accordion-body collapse">',
|
||||
'<div class="accordion-inner"><%= settingsBloc %></div>',
|
||||
'</div>',
|
||||
'</div>'].join("");
|
||||
|
||||
function createSettings(extension) {
|
||||
$("#accordion-extensions").append($(_.template(accordionTmpl, {
|
||||
extensionId: extension.extensionId,
|
||||
extensionName: extension.extensionName,
|
||||
optional: extension.optional,
|
||||
settingsBloc: extension.settingsBloc
|
||||
})));
|
||||
}
|
||||
|
||||
var onPreviewFinished = createCallback("onPreviewFinished");
|
||||
var onAsyncPreviewCallbackList = getExtensionCallbackList("onAsyncPreview");
|
||||
extensionManager["onAsyncPreview"] = function() {
|
||||
// Call onPreviewFinished callbacks when all async preview are finished
|
||||
var counter = 0;
|
||||
function tryFinished() {
|
||||
if(counter === onAsyncPreviewCallbackList.length) {
|
||||
onPreviewFinished();
|
||||
}
|
||||
}
|
||||
_.each(onAsyncPreviewCallbackList, function(asyncPreviewCallback) {
|
||||
asyncPreviewCallback(function() {
|
||||
counter++;
|
||||
tryFinished();
|
||||
});
|
||||
extensionManager.init = function(extensionSettings) {
|
||||
|
||||
// Set extension config
|
||||
extensionSettings = extensionSettings || {};
|
||||
_.each(extensionList, function(extension) {
|
||||
extension.config = _.extend({}, extension.defaultConfig, extensionSettings[extension.extensionId]);
|
||||
extension.config.enabled = !extension.optional || extension.config.enabled;
|
||||
});
|
||||
tryFinished();
|
||||
|
||||
// Create accordion in settings dialog
|
||||
_.each(extensionList, createSettings);
|
||||
|
||||
// Load/Save extension config from/to settings
|
||||
addCallback("onLoadSettings");
|
||||
extensionManager["onLoadSettings"] = function() {
|
||||
_.each(extensionList, function(extension) {
|
||||
utils.setInputChecked("#input-enable-extension-" + extension.extensionId, extension.config.enabled);
|
||||
var onLoadSettingsCallback = extension.onLoadSettings;
|
||||
onLoadSettingsCallback && onLoadSettingsCallback();
|
||||
});
|
||||
};
|
||||
extensionManager["onSaveSettings"] = function(newExtensionSettings, event) {
|
||||
_.each(extensionList, function(extension) {
|
||||
var newExtensionConfig = extension.defaultConfig || {};
|
||||
newExtensionConfig.enabled = utils.getInputChecked("#input-enable-extension-" + extension.extensionId);
|
||||
var onSaveSettingsCallback = extension.onSaveSettings;
|
||||
onSaveSettingsCallback && onSaveSettingsCallback(newExtensionConfig, event);
|
||||
newExtensionSettings[extension.extensionId] = newExtensionConfig;
|
||||
});
|
||||
};
|
||||
|
||||
addCallback("onMessage");
|
||||
addCallback("onError");
|
||||
addCallback("onOfflineChanged");
|
||||
addCallback("onLayoutConfigure");
|
||||
addCallback("onLayoutCreated");
|
||||
addCallback("onEditorConfigure");
|
||||
|
||||
var onPreviewFinished = createCallback("onPreviewFinished");
|
||||
var onAsyncPreviewCallbackList = getExtensionCallbackList("onAsyncPreview");
|
||||
extensionManager["onAsyncPreview"] = function() {
|
||||
// Call onPreviewFinished callbacks when all async preview are finished
|
||||
var counter = 0;
|
||||
function tryFinished() {
|
||||
if(counter === onAsyncPreviewCallbackList.length) {
|
||||
onPreviewFinished();
|
||||
}
|
||||
}
|
||||
_.each(onAsyncPreviewCallbackList, function(asyncPreviewCallback) {
|
||||
asyncPreviewCallback(function() {
|
||||
counter++;
|
||||
tryFinished();
|
||||
});
|
||||
});
|
||||
tryFinished();
|
||||
};
|
||||
|
||||
// Call onReady callbacks
|
||||
createCallback("onReady")();
|
||||
};
|
||||
|
||||
return extensionManager;
|
||||
|
@ -1,11 +1,31 @@
|
||||
define( [ "Markdown.Extra" ], function() {
|
||||
define( [ "utils", "Markdown.Extra" ], function(utils) {
|
||||
|
||||
var markdownExtra = {
|
||||
extensionId: "markdownExtra",
|
||||
extensionName: "Markdown Extra",
|
||||
optional: true,
|
||||
defaultConfig: {
|
||||
prettify: true
|
||||
}
|
||||
},
|
||||
settingsBloc: [
|
||||
'<p>Adds extra features to the original Markdown syntax.</p>',
|
||||
'<div class="form-horizontal">',
|
||||
'<div class="control-group">',
|
||||
'<label class="control-label" for="input-markdownextra-prettify">Prettify syntax highlighting</label>',
|
||||
'<div class="controls">',
|
||||
'<input type="checkbox" id="input-markdownextra-prettify">',
|
||||
'</div>',
|
||||
'</div>',
|
||||
'</div>'
|
||||
].join("")
|
||||
};
|
||||
|
||||
markdownExtra.onLoadSettings = function() {
|
||||
utils.setInputChecked("#input-markdownextra-prettify", markdownExtra.config.prettify);
|
||||
};
|
||||
|
||||
markdownExtra.onSaveSettings = function(newConfig, event) {
|
||||
newConfig.prettify = utils.getInputChecked("#input-markdownextra-prettify");
|
||||
};
|
||||
|
||||
markdownExtra.onEditorConfigure = function(editor) {
|
||||
|
@ -2,15 +2,19 @@ define( [ "MathJax" ], function($) {
|
||||
|
||||
var mathJax = {
|
||||
extensionId: "mathJax",
|
||||
extensionName: "MathJax"
|
||||
extensionName: "MathJax",
|
||||
optional: true,
|
||||
settingsBloc: '<p>Allows StackEdit to interpret LaTex mathematical expressions.</p>'
|
||||
};
|
||||
|
||||
MathJax.Hub.Config({"HTML-CSS": {preferredFont: "TeX",availableFonts: ["STIX", "TeX"],linebreaks: {automatic: true},EqnChunk: (MathJax.Hub.Browser.isMobile ? 10 : 50), imageFont: null},
|
||||
tex2jax: {inlineMath: [["$", "$"], ["\\\\(", "\\\\)"]],displayMath: [["$$", "$$"], ["\\[", "\\]"]],processEscapes: true,ignoreClass: "tex2jax_ignore|dno"},
|
||||
TeX: {noUndefined: {attributes: {mathcolor: "red",mathbackground: "#FFEEEE",mathsize: "90%"}},
|
||||
Safe: {allow: {URLs: "safe",classes: "safe",cssIDs: "safe",styles: "safe",fontsize: "all"}}},
|
||||
messageStyle: "none"
|
||||
});
|
||||
mathJax.onReady = function() {
|
||||
MathJax.Hub.Config({"HTML-CSS": {preferredFont: "TeX",availableFonts: ["STIX", "TeX"],linebreaks: {automatic: true},EqnChunk: (MathJax.Hub.Browser.isMobile ? 10 : 50), imageFont: null},
|
||||
tex2jax: {inlineMath: [["$", "$"], ["\\\\(", "\\\\)"]],displayMath: [["$$", "$$"], ["\\[", "\\]"]],processEscapes: true,ignoreClass: "tex2jax_ignore|dno"},
|
||||
TeX: {noUndefined: {attributes: {mathcolor: "red",mathbackground: "#FFEEEE",mathsize: "90%"}},
|
||||
Safe: {allow: {URLs: "safe",classes: "safe",cssIDs: "safe",styles: "safe",fontsize: "all"}}},
|
||||
messageStyle: "none"
|
||||
});
|
||||
};
|
||||
|
||||
var ready = false; // true after initial typeset is complete
|
||||
var pending = false; // true when MathJax has been requested
|
||||
|
@ -5,7 +5,8 @@ define( [ "jquery", "jgrowl", "underscore" ], function($) {
|
||||
extensionName: "Notifications",
|
||||
defaultConfig: {
|
||||
showingTime: 5000
|
||||
}
|
||||
},
|
||||
settingsBloc: "<p>Shows notification messages in the bottom-right corner of the screen.</p>"
|
||||
};
|
||||
|
||||
notifications.onReady = function() {
|
||||
|
@ -2,7 +2,15 @@ define( [ "jquery", "underscore" ], function($) {
|
||||
|
||||
var scrollLink = {
|
||||
extensionId: "scrollLink",
|
||||
extensionName: "Scroll Link"
|
||||
extensionName: "Scroll Link",
|
||||
optional: true,
|
||||
settingsBloc: [
|
||||
'<p>Binds together editor and preview scrollbars.</p>',
|
||||
'<blockquote class="muted"><b>NOTE:</b> ',
|
||||
'The mapping between Markdown and HTML is based on the position of the title elements (h1, h2, ...) in the page. ',
|
||||
'Therefore, if your document does not contain any title, the mapping will be linear and consequently less efficient.',
|
||||
'</bloquote>'
|
||||
].join("")
|
||||
};
|
||||
|
||||
var mdSectionList = [];
|
||||
|
@ -1,5 +1,5 @@
|
||||
define(["jquery", "core", "synchronizer", "publisher", "sharing", "text!../WELCOME.md", "underscore"],
|
||||
function($, core, synchronizer, publisher, sharing, welcomeContent) {
|
||||
define(["jquery", "core", "utils", "synchronizer", "publisher", "sharing", "text!../WELCOME.md", "underscore"],
|
||||
function($, core, utils, synchronizer, publisher, sharing, welcomeContent) {
|
||||
|
||||
var TEMPORARY_FILE_INDEX = "file.tempIndex";
|
||||
|
||||
@ -75,7 +75,7 @@ define(["jquery", "core", "synchronizer", "publisher", "sharing", "text!../WELCO
|
||||
var fileIndex = TEMPORARY_FILE_INDEX;
|
||||
if(!isTemporary) {
|
||||
do {
|
||||
fileIndex = "file." + core.randomString();
|
||||
fileIndex = "file." + utils.randomString();
|
||||
} while(_.has(localStorage, fileIndex + ".title"));
|
||||
}
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
define(["jquery", "core", "google-helper", "underscore"], function($, core, googleHelper) {
|
||||
define(["core", "utils", "google-helper", "underscore"], function(core, utils, googleHelper) {
|
||||
|
||||
var PROVIDER_GDRIVE = "gdrive";
|
||||
|
||||
@ -15,8 +15,8 @@ define(["jquery", "core", "google-helper", "underscore"], function($, core, goog
|
||||
syncAttributes.provider = PROVIDER_GDRIVE;
|
||||
syncAttributes.id = id;
|
||||
syncAttributes.etag = etag;
|
||||
syncAttributes.contentCRC = core.crc32(content);
|
||||
syncAttributes.titleCRC = core.crc32(title);
|
||||
syncAttributes.contentCRC = utils.crc32(content);
|
||||
syncAttributes.titleCRC = utils.crc32(title);
|
||||
return syncAttributes;
|
||||
}
|
||||
|
||||
@ -71,7 +71,7 @@ define(["jquery", "core", "google-helper", "underscore"], function($, core, goog
|
||||
};
|
||||
|
||||
gdriveProvider.exportFile = function(event, title, content, callback) {
|
||||
var parentId = core.getInputValue($("#input-sync-export-gdrive-parentid"));
|
||||
var parentId = utils.getInputTextValue("#input-sync-export-gdrive-parentid");
|
||||
googleHelper.upload(undefined, parentId, title, content, undefined, function(error, result) {
|
||||
if (error) {
|
||||
callback(error);
|
||||
@ -85,7 +85,7 @@ define(["jquery", "core", "google-helper", "underscore"], function($, core, goog
|
||||
};
|
||||
|
||||
gdriveProvider.exportManual = function(event, title, content, callback) {
|
||||
var id = core.getInputValue($("#input-sync-manual-gdrive-id"), event);
|
||||
var id = utils.getInputTextValue("#input-sync-manual-gdrive-id", event);
|
||||
if(!id) {
|
||||
return;
|
||||
}
|
||||
@ -186,14 +186,14 @@ define(["jquery", "core", "google-helper", "underscore"], function($, core, goog
|
||||
return;
|
||||
}
|
||||
var syncAttributes = change.syncAttributes;
|
||||
var localTitleChanged = syncAttributes.titleCRC != core.crc32(localTitle);
|
||||
var localTitleChanged = syncAttributes.titleCRC != utils.crc32(localTitle);
|
||||
var localContent = localStorage[fileIndex + ".content"];
|
||||
var localContentChanged = syncAttributes.contentCRC != core.crc32(localContent);
|
||||
var localContentChanged = syncAttributes.contentCRC != utils.crc32(localContent);
|
||||
var file = change.file;
|
||||
var remoteTitleCRC = core.crc32(file.title);
|
||||
var remoteTitleCRC = utils.crc32(file.title);
|
||||
var remoteTitleChanged = syncAttributes.titleCRC != remoteTitleCRC;
|
||||
var fileTitleChanged = localTitle != file.title;
|
||||
var remoteContentCRC = core.crc32(file.content);
|
||||
var remoteContentCRC = utils.crc32(file.content);
|
||||
var remoteContentChanged = syncAttributes.contentCRC != remoteContentCRC;
|
||||
var fileContentChanged = localContent != file.content;
|
||||
// Conflict detection
|
||||
@ -253,8 +253,8 @@ define(["jquery", "core", "google-helper", "underscore"], function($, core, goog
|
||||
|
||||
gdriveProvider.newPublishAttributes = function(event) {
|
||||
var publishAttributes = {};
|
||||
publishAttributes.id = $("#input-publish-gdrive-fileid").val() || undefined;
|
||||
publishAttributes.fileName = $("#input-publish-gdrive-filename").val() || undefined;
|
||||
publishAttributes.id = utils.getInputTextValue("#input-publish-gdrive-fileid");
|
||||
publishAttributes.fileName = utils.getInputTextValue("#input-publish-gdrive-filename");
|
||||
if(event.isPropagationStopped()) {
|
||||
return undefined;
|
||||
}
|
||||
|
@ -1,4 +1,4 @@
|
||||
define(["jquery", "core", "github-helper"], function($, core, githubHelper) {
|
||||
define(["utils", "github-helper"], function(utils, githubHelper) {
|
||||
|
||||
var PROVIDER_GIST = "gist";
|
||||
|
||||
@ -23,9 +23,9 @@ define(["jquery", "core", "github-helper"], function($, core, githubHelper) {
|
||||
|
||||
gistProvider.newPublishAttributes = function(event) {
|
||||
var publishAttributes = {};
|
||||
publishAttributes.gistId = $("#input-publish-gist-id").val() || undefined;
|
||||
publishAttributes.filename = core.getInputValue($("#input-publish-filename"), event);
|
||||
publishAttributes.isPublic = $("#input-publish-gist-public").is(":checked");
|
||||
publishAttributes.gistId = utils.getInputTextValue("#input-publish-gist-id");
|
||||
publishAttributes.filename = utils.getInputTextValue("#input-publish-filename", event);
|
||||
publishAttributes.isPublic = utils.getInputChecked("#input-publish-gist-public");
|
||||
if(event.isPropagationStopped()) {
|
||||
return undefined;
|
||||
}
|
||||
|
@ -1,4 +1,4 @@
|
||||
define(["jquery", "core", "github-helper"], function($, core, githubHelper) {
|
||||
define(["core", "utils", "github-helper"], function(core, utils, githubHelper) {
|
||||
|
||||
var PROVIDER_GITHUB = "github";
|
||||
|
||||
@ -16,9 +16,9 @@ define(["jquery", "core", "github-helper"], function($, core, githubHelper) {
|
||||
|
||||
githubProvider.newPublishAttributes = function(event) {
|
||||
var publishAttributes = {};
|
||||
publishAttributes.repository = core.getInputValue($("#input-publish-github-reponame"), event);
|
||||
publishAttributes.branch = core.getInputValue($("#input-publish-github-branch"), event);
|
||||
publishAttributes.path = core.getInputValue($("#input-publish-file-path"), event);
|
||||
publishAttributes.repository = utils.getInputTextValue("#input-publish-github-reponame", event);
|
||||
publishAttributes.branch = utils.getInputTextValue("#input-publish-github-branch", event);
|
||||
publishAttributes.path = utils.getInputTextValue("#input-publish-file-path", event);
|
||||
if(event.isPropagationStopped()) {
|
||||
return undefined;
|
||||
}
|
||||
|
@ -104,7 +104,7 @@ define(["jquery", "core", "async-runner"], function($, core, asyncRunner) {
|
||||
//headers["If-Match"] = etag;
|
||||
}
|
||||
|
||||
var base64Data = core.encodeBase64(content);
|
||||
var base64Data = utils.encodeBase64(content);
|
||||
var multipartRequestBody = delimiter
|
||||
+ 'Content-Type: application/json\r\n\r\n'
|
||||
+ JSON.stringify(metadata) + delimiter + 'Content-Type: '
|
||||
|
@ -1,256 +0,0 @@
|
||||
define([ "MathJax" ], function() {
|
||||
|
||||
MathJax.Hub.Config({"HTML-CSS": {preferredFont: "TeX",availableFonts: ["STIX", "TeX"],linebreaks: {automatic: true},EqnChunk: (MathJax.Hub.Browser.isMobile ? 10 : 50), imageFont: null},
|
||||
tex2jax: {inlineMath: [["$", "$"], ["\\\\(", "\\\\)"]],displayMath: [["$$", "$$"], ["\\[", "\\]"]],processEscapes: true,ignoreClass: "tex2jax_ignore|dno"},
|
||||
TeX: {noUndefined: {attributes: {mathcolor: "red",mathbackground: "#FFEEEE",mathsize: "90%"}},
|
||||
Safe: {allow: {URLs: "safe",classes: "safe",cssIDs: "safe",styles: "safe",fontsize: "all"}}},
|
||||
messageStyle: "none"
|
||||
});
|
||||
|
||||
var ready = false; // true after initial typeset is complete
|
||||
var pending = false; // true when MathJax has been requested
|
||||
var preview = null; // the preview container
|
||||
var inline = "$"; // the inline math delimiter
|
||||
|
||||
var blocks, start, end, last, braces; // used in searching for math
|
||||
var math; // stores math until markdone is done
|
||||
|
||||
var HUB = MathJax.Hub;
|
||||
|
||||
//
|
||||
// Runs after initial typeset
|
||||
//
|
||||
HUB.Queue(function() {
|
||||
ready = true;
|
||||
HUB.processUpdateTime = 50; // reduce update time so that we can cancel
|
||||
// easier
|
||||
HUB.Config({ "HTML-CSS" : { EqnChunk : 10, EqnChunkFactor : 1 }, // reduce
|
||||
// chunk
|
||||
// for
|
||||
// more
|
||||
// frequent
|
||||
// updates
|
||||
SVG : { EqnChunk : 10, EqnChunkFactor : 1 } });
|
||||
});
|
||||
|
||||
//
|
||||
// The pattern for math delimiters and special symbols
|
||||
// needed for searching for math in the page.
|
||||
//
|
||||
var SPLIT = /(\$\$?|\\(?:begin|end)\{[a-z]*\*?\}|\\[\\{}$]|[{}]|(?:\n\s*)+|@@\d+@@)/i;
|
||||
|
||||
//
|
||||
// The math is in blocks i through j, so
|
||||
// collect it into one block and clear the others.
|
||||
// Replace &, <, and > by named entities.
|
||||
// For IE, put <br> at the ends of comments since IE removes \n.
|
||||
// Clear the current math positions and store the index of the
|
||||
// math, then push the math string onto the storage array.
|
||||
//
|
||||
function processMath(i, j) {
|
||||
var block = blocks.slice(i, j + 1).join("").replace(/&/g, "&") // use
|
||||
// HTML
|
||||
// entity
|
||||
// for
|
||||
// &
|
||||
.replace(/</g, "<") // use HTML entity for <
|
||||
.replace(/>/g, ">") // use HTML entity for >
|
||||
;
|
||||
if (HUB.Browser.isMSIE) {
|
||||
block = block.replace(/(%[^\n]*)\n/g, "$1<br/>\n")
|
||||
}
|
||||
while (j > i) {
|
||||
blocks[j] = "";
|
||||
j--
|
||||
}
|
||||
blocks[i] = "@@" + math.length + "@@";
|
||||
math.push(block);
|
||||
start = end = last = null;
|
||||
}
|
||||
|
||||
//
|
||||
// Break up the text into its component parts and search
|
||||
// through them for math delimiters, braces, linebreaks, etc.
|
||||
// Math delimiters must match and braces must balance.
|
||||
// Don't allow math to pass through a double linebreak
|
||||
// (which will be a paragraph).
|
||||
//
|
||||
function removeMath(text) {
|
||||
start = end = last = null; // for tracking math delimiters
|
||||
math = []; // stores math strings for latter
|
||||
|
||||
blocks = text.replace(/\r\n?/g, "\n").split(SPLIT);
|
||||
for ( var i = 1, m = blocks.length; i < m; i += 2) {
|
||||
var block = blocks[i];
|
||||
if (block.charAt(0) === "@") {
|
||||
//
|
||||
// Things that look like our math markers will get
|
||||
// stored and then retrieved along with the math.
|
||||
//
|
||||
blocks[i] = "@@" + math.length + "@@";
|
||||
math.push(block);
|
||||
} else if (start) {
|
||||
//
|
||||
// If we are in math, look for the end delimiter,
|
||||
// but don't go past double line breaks, and
|
||||
// and balance braces within the math.
|
||||
//
|
||||
if (block === end) {
|
||||
if (braces) {
|
||||
last = i
|
||||
} else {
|
||||
processMath(start, i)
|
||||
}
|
||||
} else if (block.match(/\n.*\n/)) {
|
||||
if (last) {
|
||||
i = last;
|
||||
processMath(start, i)
|
||||
}
|
||||
start = end = last = null;
|
||||
braces = 0;
|
||||
} else if (block === "{") {
|
||||
braces++
|
||||
} else if (block === "}" && braces) {
|
||||
braces--
|
||||
}
|
||||
} else {
|
||||
//
|
||||
// Look for math start delimiters and when
|
||||
// found, set up the end delimiter.
|
||||
//
|
||||
if (block === inline || block === "$$") {
|
||||
start = i;
|
||||
end = block;
|
||||
braces = 0;
|
||||
} else if (block.substr(1, 5) === "begin") {
|
||||
start = i;
|
||||
end = "\\end" + block.substr(6);
|
||||
braces = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (last) {
|
||||
processMath(start, last)
|
||||
}
|
||||
return blocks.join("");
|
||||
}
|
||||
|
||||
//
|
||||
// Put back the math strings that were saved,
|
||||
// and clear the math array (no need to keep it around).
|
||||
//
|
||||
function replaceMath(text) {
|
||||
text = text.replace(/@@(\d+)@@/g, function(match, n) {
|
||||
return math[n]
|
||||
});
|
||||
math = null;
|
||||
return text;
|
||||
}
|
||||
|
||||
//
|
||||
// This is run to restart MathJax after it has finished
|
||||
// the previous run (that may have been canceled)
|
||||
//
|
||||
var beforeRefreshCallback = undefined;
|
||||
var afterRefreshCallback = undefined;
|
||||
function RestartMJ() {
|
||||
pending = false;
|
||||
HUB.cancelTypeset = false; // won't need to do this in the future
|
||||
HUB.Queue(beforeRefreshCallback);
|
||||
HUB.Queue([ "Typeset", HUB, preview ]);
|
||||
HUB.Queue(afterRefreshCallback);
|
||||
}
|
||||
|
||||
//
|
||||
// When the preview changes, cancel MathJax and restart,
|
||||
// if we haven't done that already.
|
||||
//
|
||||
function UpdateMJ() {
|
||||
if (!pending && ready) {
|
||||
pending = true;
|
||||
HUB.Cancel();
|
||||
HUB.Queue(RestartMJ);
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Save the preview ID and the inline math delimiter.
|
||||
// Create a converter for the editor and register a preConversion hook
|
||||
// to handle escaping the math.
|
||||
// Create a preview refresh hook to handle starting MathJax.
|
||||
//
|
||||
function prepareWmdForMathJax(editorObject, delimiters, beforeRefresh, afterRefresh) {
|
||||
beforeRefreshCallback = beforeRefresh;
|
||||
afterRefreshCallback = afterRefresh;
|
||||
preview = document.getElementById("wmd-preview");
|
||||
inline = delimiters[0][0];
|
||||
|
||||
var converterObject = editorObject.getConverter();
|
||||
converterObject.hooks.chain("preConversion", removeMath);
|
||||
converterObject.hooks.chain("postConversion", replaceMath);
|
||||
editorObject.hooks.chain("onPreviewRefresh", UpdateMJ);
|
||||
}
|
||||
|
||||
//
|
||||
// Set up MathJax to allow canceling of typesetting, if it
|
||||
// doesn't already have that.
|
||||
//
|
||||
if (!HUB.Cancel) {
|
||||
|
||||
HUB.cancelTypeset = false;
|
||||
var CANCELMESSAGE = "MathJax Canceled";
|
||||
|
||||
HUB.Register
|
||||
.StartupHook(
|
||||
"HTML-CSS Jax Config",
|
||||
function() {
|
||||
var HTMLCSS = MathJax.OutputJax["HTML-CSS"], TRANSLATE = HTMLCSS.Translate;
|
||||
HTMLCSS.Augment({ Translate : function(script, state) {
|
||||
if (HUB.cancelTypeset || state.cancelled) {
|
||||
throw Error(CANCELMESSAGE)
|
||||
}
|
||||
return TRANSLATE.call(HTMLCSS, script, state);
|
||||
} });
|
||||
});
|
||||
|
||||
HUB.Register.StartupHook("SVG Jax Config", function() {
|
||||
var SVG = MathJax.OutputJax["SVG"], TRANSLATE = SVG.Translate;
|
||||
SVG.Augment({ Translate : function(script, state) {
|
||||
if (HUB.cancelTypeset || state.cancelled) {
|
||||
throw Error(CANCELMESSAGE)
|
||||
}
|
||||
return TRANSLATE.call(SVG, script, state);
|
||||
} });
|
||||
});
|
||||
|
||||
HUB.Register.StartupHook("TeX Jax Config", function() {
|
||||
var TEX = MathJax.InputJax.TeX, TRANSLATE = TEX.Translate;
|
||||
TEX.Augment({ Translate : function(script, state) {
|
||||
if (HUB.cancelTypeset || state.cancelled) {
|
||||
throw Error(CANCELMESSAGE)
|
||||
}
|
||||
return TRANSLATE.call(TEX, script, state);
|
||||
} });
|
||||
});
|
||||
|
||||
var PROCESSERROR = HUB.processError;
|
||||
HUB.processError = function(error, state, type) {
|
||||
if (error.message !== CANCELMESSAGE) {
|
||||
return PROCESSERROR.call(HUB, error, state, type)
|
||||
}
|
||||
MathJax.Message.Clear(0, 0);
|
||||
state.jaxIDs = [];
|
||||
state.jax = {};
|
||||
state.scripts = [];
|
||||
state.i = state.j = 0;
|
||||
state.cancelled = true;
|
||||
return null;
|
||||
};
|
||||
|
||||
HUB.Cancel = function() {
|
||||
this.cancelTypeset = true
|
||||
};
|
||||
}
|
||||
|
||||
return { prepareWmdForMathJax : prepareWmdForMathJax };
|
||||
});
|
@ -1,5 +1,5 @@
|
||||
define(["jquery", "core", "sharing", "blogger-provider", "dropbox-provider", "gist-provider", "github-provider", "gdrive-provider", "ssh-provider", "tumblr-provider", "wordpress-provider", "underscore"],
|
||||
function($, core, sharing) {
|
||||
define(["jquery", "core", "utils", "sharing", "blogger-provider", "dropbox-provider", "gist-provider", "github-provider", "gdrive-provider", "ssh-provider", "tumblr-provider", "wordpress-provider", "underscore"],
|
||||
function($, core, sharing, utils) {
|
||||
|
||||
var publisher = {};
|
||||
|
||||
@ -131,7 +131,7 @@ define(["jquery", "core", "sharing", "blogger-provider", "dropbox-provider", "gi
|
||||
function createPublishIndex(fileIndex, publishAttributes) {
|
||||
var publishIndex = undefined;
|
||||
do {
|
||||
publishIndex = "publish." + core.randomString();
|
||||
publishIndex = "publish." + utils.randomString();
|
||||
} while(_.has(localStorage, publishIndex));
|
||||
localStorage[publishIndex] = JSON.stringify(publishAttributes);
|
||||
localStorage[fileIndex + ".publish"] += publishIndex + ";";
|
||||
@ -156,9 +156,9 @@ define(["jquery", "core", "sharing", "blogger-provider", "dropbox-provider", "gi
|
||||
if(serializedPreferences) {
|
||||
var publishPreferences = JSON.parse(serializedPreferences);
|
||||
_.each(provider.publishPreferencesInputIds, function(inputId) {
|
||||
$("#input-publish-" + inputId).val(publishPreferences[inputId]);
|
||||
utils.setInputValue("#input-publish-" + inputId, publishPreferences[inputId]);
|
||||
});
|
||||
$("input:radio[name=radio-publish-format][value=" + publishPreferences.format + "]").prop("checked", true);
|
||||
utils.setInputRadio("radio-publish-format", publishPreferences.format);
|
||||
}
|
||||
|
||||
// Open dialog box
|
||||
|
@ -1,4 +1,4 @@
|
||||
define(["jquery", "core", "async-runner", "download-provider", "gist-provider", "underscore"], function($, core, asyncRunner) {
|
||||
define(["jquery", "core", "utils", "async-runner", "download-provider", "gist-provider", "underscore"], function($, core, utils, asyncRunner) {
|
||||
var sharing = {};
|
||||
|
||||
// Create a map with providerId: providerObject
|
||||
@ -113,7 +113,7 @@ define(["jquery", "core", "async-runner", "download-provider", "gist-provider",
|
||||
return;
|
||||
}
|
||||
// Check parameters to see if we have to download a shared document
|
||||
var providerId = core.getURLParameter("provider");
|
||||
var providerId = utils.getURLParameter("provider");
|
||||
if(providerId === undefined) {
|
||||
providerId = "download";
|
||||
}
|
||||
@ -123,7 +123,7 @@ define(["jquery", "core", "async-runner", "download-provider", "gist-provider",
|
||||
}
|
||||
var importParameters = {};
|
||||
_.each(provider.sharingAttributes, function(attributeName) {
|
||||
var parameter = core.getURLParameter(attributeName);
|
||||
var parameter = utils.getURLParameter(attributeName);
|
||||
if(!parameter) {
|
||||
importParameters = undefined;
|
||||
return;
|
||||
|
@ -1,4 +1,4 @@
|
||||
define([ "jquery", "core", "ssh-helper" ], function($, core, sshHelper) {
|
||||
define([ "utils", "ssh-helper" ], function(utils, sshHelper) {
|
||||
|
||||
var PROVIDER_SSH = "ssh";
|
||||
|
||||
@ -22,19 +22,19 @@ define([ "jquery", "core", "ssh-helper" ], function($, core, sshHelper) {
|
||||
|
||||
sshProvider.newPublishAttributes = function(event) {
|
||||
var publishAttributes = {};
|
||||
publishAttributes.host = core
|
||||
.getInputValue(
|
||||
$("#input-publish-ssh-host"),
|
||||
publishAttributes.host = utils
|
||||
.getInputTextValue(
|
||||
"#input-publish-ssh-host",
|
||||
event,
|
||||
/^(([a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9\-]*[a-zA-Z0-9])\.)*([A-Za-z0-9]|[A-Za-z0-9][A-Za-z0-9\-]*[A-Za-z0-9])$/);
|
||||
publishAttributes.port = core.getInputIntValue(
|
||||
$("#input-publish-ssh-port"), undefined, 0);
|
||||
publishAttributes.username = core.getInputValue(
|
||||
$("#input-publish-ssh-username"), event);
|
||||
publishAttributes.password = core.getInputValue(
|
||||
$("#input-publish-ssh-password"), event);
|
||||
publishAttributes.path = core.getInputValue(
|
||||
$("#input-publish-file-path"), event);
|
||||
publishAttributes.port = utils.getInputIntValue(
|
||||
"#input-publish-ssh-port", undefined, 0);
|
||||
publishAttributes.username = utils.getInputTextValue(
|
||||
"#input-publish-ssh-username", event);
|
||||
publishAttributes.password = utils.getInputTextValue(
|
||||
"#input-publish-ssh-password", event);
|
||||
publishAttributes.path = utils.getInputTextValue(
|
||||
"#input-publish-file-path", event);
|
||||
if (event.isPropagationStopped()) {
|
||||
return undefined;
|
||||
}
|
||||
|
@ -1,4 +1,4 @@
|
||||
define(["jquery", "core", "dropbox-provider", "gdrive-provider", "underscore"], function($, core) {
|
||||
define(["jquery", "core", "utils", "dropbox-provider", "gdrive-provider", "underscore"], function($, core, utils) {
|
||||
var synchronizer = {};
|
||||
|
||||
// Create a map with providerId: providerObject
|
||||
@ -101,9 +101,9 @@ define(["jquery", "core", "dropbox-provider", "gdrive-provider", "underscore"],
|
||||
|
||||
// Get document title/content
|
||||
uploadContent = localStorage[fileIndex + ".content"];
|
||||
uploadContentCRC = core.crc32(uploadContent);
|
||||
uploadContentCRC = utils.crc32(uploadContent);
|
||||
uploadTitle = localStorage[fileIndex + ".title"];
|
||||
uploadTitleCRC = core.crc32(uploadTitle);
|
||||
uploadTitleCRC = utils.crc32(uploadTitle);
|
||||
|
||||
// Parse the list of synchronized locations associated to the document
|
||||
uploadFileSyncIndexList = _.compact(fileSyncIndexes.split(";"));
|
||||
@ -247,7 +247,7 @@ define(["jquery", "core", "dropbox-provider", "gdrive-provider", "underscore"],
|
||||
if(serializedPreferences) {
|
||||
var exportPreferences = JSON.parse(serializedPreferences);
|
||||
_.each(provider.exportPreferencesInputIds, function(inputId) {
|
||||
$("#input-sync-export-" + inputId).val(exportPreferences[inputId]);
|
||||
utils.setInputValue("#input-sync-export-" + inputId, exportPreferences[inputId]);
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
define(["jquery", "core", "tumblr-helper"], function($, core, tumblrHelper) {
|
||||
define(["utils", "tumblr-helper"], function(utils, tumblrHelper) {
|
||||
|
||||
var PROVIDER_TUMBLR = "tumblr";
|
||||
|
||||
@ -29,13 +29,13 @@ define(["jquery", "core", "tumblr-helper"], function($, core, tumblrHelper) {
|
||||
|
||||
tumblrProvider.newPublishAttributes = function(event) {
|
||||
var publishAttributes = {};
|
||||
publishAttributes.blogHostname = core
|
||||
.getInputValue(
|
||||
$("#input-publish-tumblr-hostname"),
|
||||
publishAttributes.blogHostname = utils
|
||||
.getInputTextValue(
|
||||
"#input-publish-tumblr-hostname",
|
||||
event,
|
||||
/^(([a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9\-]*[a-zA-Z0-9])\.)*([A-Za-z0-9]|[A-Za-z0-9][A-Za-z0-9\-]*[A-Za-z0-9])$/);
|
||||
publishAttributes.postId = $("#input-publish-postid").val() || undefined;
|
||||
publishAttributes.tags = $("#input-publish-tags").val() || undefined;
|
||||
publishAttributes.postId = utils.getInputTextValue("#input-publish-postid");
|
||||
publishAttributes.tags = utils.getInputTextValue("#input-publish-tags");
|
||||
if(event.isPropagationStopped()) {
|
||||
return undefined;
|
||||
}
|
||||
|
252
js/utils.js
Normal file
252
js/utils.js
Normal file
@ -0,0 +1,252 @@
|
||||
define([ "jquery", "underscore" ], function($) {
|
||||
|
||||
var utils = {};
|
||||
|
||||
// Return a parameter from the URL
|
||||
utils.getURLParameter = function(name) {
|
||||
var regex = new RegExp(name + "=(.+?)(&|$)");
|
||||
try {
|
||||
return decodeURIComponent(regex.exec(location.search)[1]);
|
||||
} catch (e) {
|
||||
return undefined;
|
||||
}
|
||||
};
|
||||
|
||||
// Transform a selector into a jQuery object
|
||||
function jqElt(element) {
|
||||
if(_.isString(element)) {
|
||||
return $(element);
|
||||
}
|
||||
return element;
|
||||
}
|
||||
|
||||
// For input control
|
||||
function inputError(element, event) {
|
||||
if(event !== undefined) {
|
||||
element.stop(true, true).addClass("error").delay(1000).switchClass("error");
|
||||
event.stopPropagation();
|
||||
}
|
||||
}
|
||||
|
||||
// Return input value
|
||||
utils.getInputValue = function(element) {
|
||||
element = jqElt(element);
|
||||
return element.val();
|
||||
};
|
||||
|
||||
// Set input value
|
||||
utils.setInputValue = function(element, value) {
|
||||
element = jqElt(element);
|
||||
element.val(value);
|
||||
};
|
||||
|
||||
// Return input text value
|
||||
utils.getInputTextValue = function(element, event, validationRegex) {
|
||||
element = jqElt(element);
|
||||
var value = element.val();
|
||||
if (value === undefined) {
|
||||
inputError(element, event);
|
||||
return undefined;
|
||||
}
|
||||
// trim
|
||||
value = utils.trim(value);
|
||||
if((value.length === 0)
|
||||
|| (validationRegex !== undefined && !value.match(validationRegex))) {
|
||||
inputError(element, event);
|
||||
return undefined;
|
||||
}
|
||||
return value;
|
||||
};
|
||||
|
||||
// Return input integer value
|
||||
utils.getInputIntValue = function(element, event, min, max) {
|
||||
element = jqElt(element);
|
||||
var value = utils.getInputTextValue(element, event);
|
||||
if(value === undefined) {
|
||||
return undefined;
|
||||
}
|
||||
value = parseInt(value);
|
||||
if((value === NaN)
|
||||
|| (min !== undefined && value < min)
|
||||
|| (max !== undefined && value > max)) {
|
||||
inputError(element, event);
|
||||
return undefined;
|
||||
}
|
||||
return value;
|
||||
};
|
||||
|
||||
// Return checkbox boolean value
|
||||
utils.getInputChecked = function(element) {
|
||||
element = jqElt(element);
|
||||
return element.prop("checked");
|
||||
};
|
||||
|
||||
// Set checkbox state
|
||||
utils.setInputChecked = function(element, checked) {
|
||||
element = jqElt(element);
|
||||
element.prop("checked", checked);
|
||||
};
|
||||
|
||||
// Get radio button value
|
||||
utils.getInputRadio = function(name) {
|
||||
return $("input:radio[name=" + name + "]:checked").prop("value");
|
||||
};
|
||||
|
||||
// Set radio button value
|
||||
utils.setInputRadio = function(name, value) {
|
||||
$("input:radio[name=" + name + "][value=" + value + "]").prop("checked", true);
|
||||
};
|
||||
|
||||
// Reset input control in all modals
|
||||
utils.resetModalInputs = function() {
|
||||
$(".modal input[type=text]:not([disabled]), .modal input[type=password]").val("");
|
||||
};
|
||||
|
||||
// Basic trim function
|
||||
utils.trim = function(str) {
|
||||
return str.replace(/^\s+|\s+$/g, '');
|
||||
};
|
||||
|
||||
// Check an URL
|
||||
utils.checkUrl = function(url, addSlash) {
|
||||
if(!url) {
|
||||
return url;
|
||||
}
|
||||
if(url.indexOf("http") !== 0) {
|
||||
url = "http://" + url;
|
||||
}
|
||||
if(addSlash && url.indexOf("/", url.length - 1) === -1) {
|
||||
url += "/";
|
||||
}
|
||||
return url;
|
||||
};
|
||||
|
||||
// Base64 conversion
|
||||
utils.encodeBase64 = function(str) {
|
||||
if (str.length === 0) {
|
||||
return "";
|
||||
}
|
||||
|
||||
// UTF-8 to byte array
|
||||
var bytes = [], offset = 0, length, char;
|
||||
|
||||
str = encodeURI(str);
|
||||
length = str.length;
|
||||
|
||||
while (offset < length) {
|
||||
char = str[offset];
|
||||
offset += 1;
|
||||
|
||||
if ('%' !== char) {
|
||||
bytes.push(char.charCodeAt(0));
|
||||
} else {
|
||||
char = str[offset] + str[offset + 1];
|
||||
bytes.push(parseInt(char, 16));
|
||||
offset += 2;
|
||||
}
|
||||
}
|
||||
|
||||
// byte array to base64
|
||||
var padchar = '=';
|
||||
var alpha = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/';
|
||||
|
||||
var i, b10;
|
||||
var x = [];
|
||||
|
||||
var imax = bytes.length - bytes.length % 3;
|
||||
|
||||
for (i = 0; i < imax; i += 3) {
|
||||
b10 = (bytes[i] << 16) | (bytes[i+1] << 8) | bytes[i+2];
|
||||
x.push(alpha.charAt(b10 >> 18));
|
||||
x.push(alpha.charAt((b10 >> 12) & 0x3F));
|
||||
x.push(alpha.charAt((b10 >> 6) & 0x3f));
|
||||
x.push(alpha.charAt(b10 & 0x3f));
|
||||
}
|
||||
switch (bytes.length - imax) {
|
||||
case 1:
|
||||
b10 = bytes[i] << 16;
|
||||
x.push(alpha.charAt(b10 >> 18) + alpha.charAt((b10 >> 12) & 0x3F) +
|
||||
padchar + padchar);
|
||||
break;
|
||||
case 2:
|
||||
b10 = (bytes[i] << 16) | (bytes[i+1] << 8);
|
||||
x.push(alpha.charAt(b10 >> 18) + alpha.charAt((b10 >> 12) & 0x3F) +
|
||||
alpha.charAt((b10 >> 6) & 0x3f) + padchar);
|
||||
break;
|
||||
}
|
||||
return x.join('');
|
||||
};
|
||||
|
||||
// CRC32 algorithm
|
||||
var mHash = [ 0, 1996959894, 3993919788, 2567524794, 124634137,
|
||||
1886057615, 3915621685, 2657392035, 249268274, 2044508324,
|
||||
3772115230, 2547177864, 162941995, 2125561021, 3887607047,
|
||||
2428444049, 498536548, 1789927666, 4089016648, 2227061214,
|
||||
450548861, 1843258603, 4107580753, 2211677639, 325883990,
|
||||
1684777152, 4251122042, 2321926636, 335633487, 1661365465,
|
||||
4195302755, 2366115317, 997073096, 1281953886, 3579855332,
|
||||
2724688242, 1006888145, 1258607687, 3524101629, 2768942443,
|
||||
901097722, 1119000684, 3686517206, 2898065728, 853044451,
|
||||
1172266101, 3705015759, 2882616665, 651767980, 1373503546,
|
||||
3369554304, 3218104598, 565507253, 1454621731, 3485111705,
|
||||
3099436303, 671266974, 1594198024, 3322730930, 2970347812,
|
||||
795835527, 1483230225, 3244367275, 3060149565, 1994146192,
|
||||
31158534, 2563907772, 4023717930, 1907459465, 112637215,
|
||||
2680153253, 3904427059, 2013776290, 251722036, 2517215374,
|
||||
3775830040, 2137656763, 141376813, 2439277719, 3865271297,
|
||||
1802195444, 476864866, 2238001368, 4066508878, 1812370925,
|
||||
453092731, 2181625025, 4111451223, 1706088902, 314042704,
|
||||
2344532202, 4240017532, 1658658271, 366619977, 2362670323,
|
||||
4224994405, 1303535960, 984961486, 2747007092, 3569037538,
|
||||
1256170817, 1037604311, 2765210733, 3554079995, 1131014506,
|
||||
879679996, 2909243462, 3663771856, 1141124467, 855842277,
|
||||
2852801631, 3708648649, 1342533948, 654459306, 3188396048,
|
||||
3373015174, 1466479909, 544179635, 3110523913, 3462522015,
|
||||
1591671054, 702138776, 2966460450, 3352799412, 1504918807,
|
||||
783551873, 3082640443, 3233442989, 3988292384, 2596254646,
|
||||
62317068, 1957810842, 3939845945, 2647816111, 81470997, 1943803523,
|
||||
3814918930, 2489596804, 225274430, 2053790376, 3826175755,
|
||||
2466906013, 167816743, 2097651377, 4027552580, 2265490386,
|
||||
503444072, 1762050814, 4150417245, 2154129355, 426522225,
|
||||
1852507879, 4275313526, 2312317920, 282753626, 1742555852,
|
||||
4189708143, 2394877945, 397917763, 1622183637, 3604390888,
|
||||
2714866558, 953729732, 1340076626, 3518719985, 2797360999,
|
||||
1068828381, 1219638859, 3624741850, 2936675148, 906185462,
|
||||
1090812512, 3747672003, 2825379669, 829329135, 1181335161,
|
||||
3412177804, 3160834842, 628085408, 1382605366, 3423369109,
|
||||
3138078467, 570562233, 1426400815, 3317316542, 2998733608,
|
||||
733239954, 1555261956, 3268935591, 3050360625, 752459403,
|
||||
1541320221, 2607071920, 3965973030, 1969922972, 40735498,
|
||||
2617837225, 3943577151, 1913087877, 83908371, 2512341634,
|
||||
3803740692, 2075208622, 213261112, 2463272603, 3855990285,
|
||||
2094854071, 198958881, 2262029012, 4057260610, 1759359992,
|
||||
534414190, 2176718541, 4139329115, 1873836001, 414664567,
|
||||
2282248934, 4279200368, 1711684554, 285281116, 2405801727,
|
||||
4167216745, 1634467795, 376229701, 2685067896, 3608007406,
|
||||
1308918612, 956543938, 2808555105, 3495958263, 1231636301,
|
||||
1047427035, 2932959818, 3654703836, 1088359270, 936918000,
|
||||
2847714899, 3736837829, 1202900863, 817233897, 3183342108,
|
||||
3401237130, 1404277552, 615818150, 3134207493, 3453421203,
|
||||
1423857449, 601450431, 3009837614, 3294710456, 1567103746,
|
||||
711928724, 3020668471, 3272380065, 1510334235, 755167117 ];
|
||||
utils.crc32 = function(str) {
|
||||
var n = 0, crc = -1;
|
||||
for ( var i = 0; i < str.length; i++) {
|
||||
n = (crc ^ str.charCodeAt(i)) & 0xFF;
|
||||
crc = (crc >>> 8) ^ mHash[n];
|
||||
}
|
||||
crc = crc ^ (-1);
|
||||
if (crc < 0) {
|
||||
crc = 0xFFFFFFFF + crc + 1;
|
||||
}
|
||||
return crc.toString(16);
|
||||
};
|
||||
|
||||
// Generates a random string
|
||||
utils.randomString = function() {
|
||||
return _.random(4294967296).toString(36);
|
||||
};
|
||||
|
||||
return utils;
|
||||
|
||||
});
|
@ -1,4 +1,4 @@
|
||||
define(["jquery", "core", "wordpress-helper"], function($, core, wordpressHelper) {
|
||||
define(["utils", "wordpress-helper"], function(utils, wordpressHelper) {
|
||||
|
||||
var PROVIDER_WORDPRESS = "wordpress";
|
||||
|
||||
@ -29,13 +29,13 @@ define(["jquery", "core", "wordpress-helper"], function($, core, wordpressHelper
|
||||
|
||||
wordpressProvider.newPublishAttributes = function(event) {
|
||||
var publishAttributes = {};
|
||||
publishAttributes.site = core
|
||||
.getInputValue(
|
||||
$("#input-publish-wordpress-site"),
|
||||
publishAttributes.site = utils
|
||||
.getInputTextValue(
|
||||
"#input-publish-wordpress-site",
|
||||
event,
|
||||
/^(([a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9\-]*[a-zA-Z0-9])\.)*([A-Za-z0-9]|[A-Za-z0-9][A-Za-z0-9\-]*[A-Za-z0-9])$/);
|
||||
publishAttributes.postId = $("#input-publish-postid").val() || undefined;
|
||||
publishAttributes.tags = $("#input-publish-tags").val() || undefined;
|
||||
publishAttributes.postId = utils.getInputTextValue("#input-publish-postid");
|
||||
publishAttributes.tags = utils.getInputTextValue("#input-publish-tags");
|
||||
if(event.isPropagationStopped()) {
|
||||
return undefined;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user