Temporarily revert "Take messaging between iframes out of the qr code, get ready for ajaxing with
images.4chan.org" This reverts commit dea285d389cdb33b30a92d6057434120ee4b0928.
This commit is contained in:
parent
227ad8fefb
commit
53405d085f
371
4chan_x.user.js
371
4chan_x.user.js
@ -71,7 +71,7 @@
|
||||
*/
|
||||
|
||||
(function() {
|
||||
var $, $$, DAY, Favicon, HOUR, MINUTE, Main, NAMESPACE, SECOND, Time, VERSION, anonymize, conf, config, d, engine, expandComment, expandThread, filter, flatten, g, getTitle, imgExpand, imgGif, imgHover, key, keybinds, log, message, nav, options, qr, quoteBacklink, quoteDR, quoteInline, quoteOP, quotePreview, redirect, replyHiding, reportButton, revealSpoilers, sauce, strikethroughQuotes, threadHiding, threadStats, threading, titlePost, ui, unread, updater, val, watcher, _base,
|
||||
var $, $$, DAY, Favicon, HOUR, MINUTE, Main, NAMESPACE, SECOND, Time, VERSION, anonymize, conf, config, d, engine, expandComment, expandThread, filter, flatten, g, getTitle, imgExpand, imgGif, imgHover, key, keybinds, log, nav, options, qr, quoteBacklink, quoteDR, quoteInline, quoteOP, quotePreview, redirect, replyHiding, reportButton, revealSpoilers, sauce, strikethroughQuotes, threadHiding, threadStats, threading, titlePost, ui, unread, updater, val, watcher, _base,
|
||||
__slice = Array.prototype.slice;
|
||||
|
||||
config = {
|
||||
@ -1191,7 +1191,7 @@
|
||||
|
||||
qr = {
|
||||
init: function() {
|
||||
var form, link;
|
||||
var form, iframe, link, loadChecking;
|
||||
if (!$.id('recaptcha_challenge_field_holder')) return;
|
||||
if (conf['Hide Original Post Form']) {
|
||||
link = $.el('h1', {
|
||||
@ -1205,6 +1205,26 @@
|
||||
$.before(form, link);
|
||||
}
|
||||
g.callbacks.push(this.node);
|
||||
iframe = $.el('iframe', {
|
||||
id: 'iframe',
|
||||
hidden: true,
|
||||
src: 'http://sys.4chan.org/robots.txt'
|
||||
});
|
||||
$.on(iframe, 'error', function() {
|
||||
return this.src = this.src;
|
||||
});
|
||||
loadChecking = function(iframe) {
|
||||
if (!qr.status.ready) {
|
||||
iframe.src = 'about:blank';
|
||||
return setTimeout((function() {
|
||||
return iframe.src = 'http://sys.4chan.org/robots.txt';
|
||||
}), 250);
|
||||
}
|
||||
};
|
||||
$.on(iframe, 'load', function() {
|
||||
if (this.src !== 'about:blank') return setTimeout(loadChecking, 500, this);
|
||||
});
|
||||
$.add(d.body, iframe);
|
||||
if (conf['Persistent QR']) {
|
||||
qr.dialog();
|
||||
if (conf['Auto Hide QR']) qr.hide();
|
||||
@ -1229,9 +1249,9 @@
|
||||
close: function() {
|
||||
var i, spoiler, _i, _len, _ref;
|
||||
qr.el.hidden = true;
|
||||
message.send({
|
||||
qr.message.send({
|
||||
req: 'abort'
|
||||
}, 'sys');
|
||||
});
|
||||
d.activeElement.blur();
|
||||
$.removeClass(qr.el, 'dump');
|
||||
_ref = qr.replies;
|
||||
@ -1701,6 +1721,7 @@
|
||||
qr.status();
|
||||
qr.cooldown.init();
|
||||
qr.captcha.init();
|
||||
qr.message.init();
|
||||
$.add(d.body, qr.el);
|
||||
e = d.createEvent('CustomEvent');
|
||||
e.initEvent('QRDialogCreation', true, false);
|
||||
@ -1714,9 +1735,9 @@
|
||||
qr.status();
|
||||
return;
|
||||
}
|
||||
message.send({
|
||||
qr.message.send({
|
||||
req: 'abort'
|
||||
}, 'sys');
|
||||
});
|
||||
reply = qr.replies[0];
|
||||
if (!(reply.com || reply.file)) {
|
||||
err = 'No file selected.';
|
||||
@ -1774,12 +1795,12 @@
|
||||
file.name = reply.file.name;
|
||||
file.type = reply.file.type;
|
||||
post.upfile = file;
|
||||
return message.send(post, 'sys');
|
||||
return qr.message.send(post);
|
||||
};
|
||||
reader.readAsBinaryString(reply.file);
|
||||
return;
|
||||
}
|
||||
return message.send(post, 'sys');
|
||||
return qr.message.send(post);
|
||||
},
|
||||
response: function(html) {
|
||||
var b, err, node, persona, postNumber, reply, thread, _, _ref;
|
||||
@ -1831,93 +1852,150 @@
|
||||
qr.status();
|
||||
return qr.resetFileInput();
|
||||
},
|
||||
post: function(data) {
|
||||
var boundary, callbacks, form, i, name, opts, parts, toBin, url, val;
|
||||
url = "http://sys.4chan.org/" + data.board + "/post";
|
||||
delete data.board;
|
||||
if (engine === 'gecko' && data.upfile) {
|
||||
if (!data.binary) {
|
||||
toBin = function(data, name, val) {
|
||||
var bb, r;
|
||||
bb = new MozBlobBuilder();
|
||||
bb.append(val);
|
||||
r = new FileReader();
|
||||
r.onload = function() {
|
||||
data[name] = r.result;
|
||||
if (!--i) return qr.post(data);
|
||||
message: {
|
||||
init: function() {
|
||||
var code, ready, script;
|
||||
code = function(e) {
|
||||
var data, host;
|
||||
data = e.data;
|
||||
if (!data.changeContext) return;
|
||||
delete data.changeContext;
|
||||
host = location.hostname;
|
||||
if (host === 'boards.4chan.org') {
|
||||
return document.getElementById('iframe').contentWindow.postMessage(data, '*');
|
||||
} else if (host === 'sys.4chan.org') {
|
||||
return parent.postMessage(data, '*');
|
||||
}
|
||||
};
|
||||
script = $.el('script', {
|
||||
textContent: "window.addEventListener('message'," + code + ",false)"
|
||||
});
|
||||
ready = function() {
|
||||
$.add(d.documentElement, script);
|
||||
if (location.hostname === 'sys.4chan.org') {
|
||||
qr.message.send({
|
||||
req: 'status',
|
||||
ready: true
|
||||
});
|
||||
}
|
||||
return $.rm(script);
|
||||
};
|
||||
if (d.documentElement) {
|
||||
return ready();
|
||||
} else {
|
||||
return $.ready(ready);
|
||||
}
|
||||
},
|
||||
send: function(data) {
|
||||
data.changeContext = true;
|
||||
data.qr = true;
|
||||
return postMessage(data, '*');
|
||||
},
|
||||
receive: function(data) {
|
||||
var _ref;
|
||||
switch (data.req) {
|
||||
case 'abort':
|
||||
if ((_ref = qr.ajax) != null) _ref.abort();
|
||||
return qr.message.send({
|
||||
req: 'status'
|
||||
});
|
||||
case 'response':
|
||||
return qr.response(data.html);
|
||||
case 'status':
|
||||
return qr.status(data);
|
||||
default:
|
||||
return qr.message.post(data);
|
||||
}
|
||||
},
|
||||
post: function(data) {
|
||||
var boundary, callbacks, form, i, name, opts, parts, toBin, url, val;
|
||||
url = "http://sys.4chan.org/" + data.board + "/post";
|
||||
delete data.board;
|
||||
delete data.qr;
|
||||
if (engine === 'gecko' && data.upfile) {
|
||||
if (!data.binary) {
|
||||
toBin = function(data, name, val) {
|
||||
var bb, r;
|
||||
bb = new MozBlobBuilder();
|
||||
bb.append(val);
|
||||
r = new FileReader();
|
||||
r.onload = function() {
|
||||
data[name] = r.result;
|
||||
if (!--i) return qr.message.post(data);
|
||||
};
|
||||
return r.readAsBinaryString(bb.getBlob('text/plain'));
|
||||
};
|
||||
return r.readAsBinaryString(bb.getBlob('text/plain'));
|
||||
};
|
||||
i = Object.keys(data).length;
|
||||
i = Object.keys(data).length;
|
||||
for (name in data) {
|
||||
val = data[name];
|
||||
if (typeof val === 'object') {
|
||||
toBin(data.upfile, 'name', data.upfile.name);
|
||||
} else if (typeof val === 'boolean') {
|
||||
if (val) {
|
||||
toBin(data, name, String(val));
|
||||
} else {
|
||||
i--;
|
||||
}
|
||||
} else {
|
||||
toBin(data, name, val);
|
||||
}
|
||||
}
|
||||
data.board = url.split('/')[3];
|
||||
data.binary = true;
|
||||
return;
|
||||
}
|
||||
delete data.binary;
|
||||
boundary = '-------------SMCD' + Date.now();
|
||||
parts = [];
|
||||
parts.push('Content-Disposition: form-data; name="upfile"; filename="' + data.upfile.name + '"\r\n' + 'Content-Type: ' + data.upfile.type + '\r\n\r\n' + data.upfile.buffer + '\r\n');
|
||||
delete data.upfile;
|
||||
for (name in data) {
|
||||
val = data[name];
|
||||
if (typeof val === 'object') {
|
||||
toBin(data.upfile, 'name', data.upfile.name);
|
||||
} else if (typeof val === 'boolean') {
|
||||
if (val) {
|
||||
toBin(data, name, String(val));
|
||||
} else {
|
||||
i--;
|
||||
}
|
||||
} else {
|
||||
toBin(data, name, val);
|
||||
if (val) {
|
||||
parts.push('Content-Disposition: form-data; name="' + name + '"\r\n\r\n' + val + '\r\n');
|
||||
}
|
||||
}
|
||||
data.board = url.split('/')[3];
|
||||
data.binary = true;
|
||||
return;
|
||||
}
|
||||
delete data.binary;
|
||||
boundary = '-------------SMCD' + Date.now();
|
||||
parts = [];
|
||||
parts.push('Content-Disposition: form-data; name="upfile"; filename="' + data.upfile.name + '"\r\n' + 'Content-Type: ' + data.upfile.type + '\r\n\r\n' + data.upfile.buffer + '\r\n');
|
||||
delete data.upfile;
|
||||
for (name in data) {
|
||||
val = data[name];
|
||||
if (val) {
|
||||
parts.push('Content-Disposition: form-data; name="' + name + '"\r\n\r\n' + val + '\r\n');
|
||||
form = '--' + boundary + '\r\n' + parts.join('--' + boundary + '\r\n') + '--' + boundary + '--\r\n';
|
||||
} else {
|
||||
form = new FormData();
|
||||
for (name in data) {
|
||||
val = data[name];
|
||||
if (val) form.append(name, val);
|
||||
}
|
||||
}
|
||||
form = '--' + boundary + '\r\n' + parts.join('--' + boundary + '\r\n') + '--' + boundary + '--\r\n';
|
||||
} else {
|
||||
form = new FormData();
|
||||
for (name in data) {
|
||||
val = data[name];
|
||||
if (val) form.append(name, val);
|
||||
}
|
||||
}
|
||||
callbacks = {
|
||||
onload: function() {
|
||||
return message.send({
|
||||
req: 'response',
|
||||
html: this.response
|
||||
});
|
||||
}
|
||||
};
|
||||
opts = {
|
||||
form: form,
|
||||
type: 'post',
|
||||
upCallbacks: {
|
||||
callbacks = {
|
||||
onload: function() {
|
||||
return message.send({
|
||||
req: 'status',
|
||||
progress: '...'
|
||||
});
|
||||
},
|
||||
onprogress: function(e) {
|
||||
return message.send({
|
||||
req: 'status',
|
||||
progress: "" + (Math.round(e.loaded / e.total * 100)) + "%"
|
||||
return qr.message.send({
|
||||
req: 'response',
|
||||
html: this.response
|
||||
});
|
||||
}
|
||||
}
|
||||
};
|
||||
if (boundary) {
|
||||
opts.headers = {
|
||||
'Content-Type': 'multipart/form-data;boundary=' + boundary
|
||||
};
|
||||
opts = {
|
||||
form: form,
|
||||
type: 'post',
|
||||
upCallbacks: {
|
||||
onload: function() {
|
||||
return qr.message.send({
|
||||
req: 'status',
|
||||
progress: '...'
|
||||
});
|
||||
},
|
||||
onprogress: function(e) {
|
||||
return qr.message.send({
|
||||
req: 'status',
|
||||
progress: "" + (Math.round(e.loaded / e.total * 100)) + "%"
|
||||
});
|
||||
}
|
||||
}
|
||||
};
|
||||
if (boundary) {
|
||||
opts.headers = {
|
||||
'Content-Type': 'multipart/form-data;boundary=' + boundary
|
||||
};
|
||||
}
|
||||
return qr.ajax = $.ajax(url, callbacks, opts);
|
||||
}
|
||||
return qr.ajax = $.ajax(url, callbacks, opts);
|
||||
}
|
||||
};
|
||||
|
||||
@ -2352,9 +2430,9 @@
|
||||
d.title = d.title.match(/^.+-/)[0] + ' 404';
|
||||
}
|
||||
unread.update(true);
|
||||
message.send({
|
||||
qr.message.send({
|
||||
req: 'abort'
|
||||
}, 'sys');
|
||||
});
|
||||
qr.status();
|
||||
Favicon.update();
|
||||
return;
|
||||
@ -3410,113 +3488,6 @@
|
||||
}
|
||||
};
|
||||
|
||||
message = {
|
||||
init: function() {
|
||||
var code, script;
|
||||
$.on(window, 'message', message.receive);
|
||||
$.ready(function() {
|
||||
var domain, domains, iframe, _i, _len, _results;
|
||||
if (location.hostname !== 'boards.4chan.org') return;
|
||||
domains = [];
|
||||
if (conf['Quick Reply']) domains.push('sys');
|
||||
if (conf['Image Expansion'] || conf['Sauce']) domains.push('images');
|
||||
_results = [];
|
||||
for (_i = 0, _len = domains.length; _i < _len; _i++) {
|
||||
domain = domains[_i];
|
||||
iframe = $.el('iframe', {
|
||||
id: domain,
|
||||
hidden: true,
|
||||
src: "http://" + domain + ".4chan.org/robots.txt"
|
||||
});
|
||||
$.on(iframe, 'error', message.loadControl);
|
||||
$.on(iframe, 'load', message.loadControl);
|
||||
_results.push($.add(d.body, iframe));
|
||||
}
|
||||
return _results;
|
||||
});
|
||||
code = function(e) {
|
||||
var data;
|
||||
data = e.data;
|
||||
if (!data.changeContext) return;
|
||||
delete data.changeContext;
|
||||
if (location.hostname === 'boards.4chan.org') {
|
||||
return document.getElementById(data.iframe).contentWindow.postMessage(data, '*');
|
||||
} else {
|
||||
return parent.postMessage(data, '*');
|
||||
}
|
||||
};
|
||||
script = $.el('script', {
|
||||
textContent: "window.addEventListener('message'," + code + ",false)"
|
||||
});
|
||||
return $.ready(function() {
|
||||
var host;
|
||||
$.add(d.documentElement, script);
|
||||
host = location.hostname;
|
||||
if (host === 'sys.4chan.org') {
|
||||
message.send({
|
||||
req: 'status',
|
||||
ready: true
|
||||
});
|
||||
}
|
||||
if (host !== 'boards.4chan.org') {
|
||||
message.send({
|
||||
req: 'iframeLoad',
|
||||
id: location.hostname.split('.')[0]
|
||||
});
|
||||
}
|
||||
return $.rm(script);
|
||||
});
|
||||
},
|
||||
loadControl: function() {
|
||||
var _this = this;
|
||||
return setTimeout((function() {
|
||||
if (_this.src === 'about:blank' || message[_this.id] === 'ready') return;
|
||||
_this.src = 'about:blank';
|
||||
return setTimeout((function() {
|
||||
return _this.src = "http://" + _this.id + ".4chan.org/robots.txt";
|
||||
}), 250);
|
||||
}), 1000);
|
||||
},
|
||||
receive: function(e) {
|
||||
var data, version;
|
||||
data = e.data;
|
||||
if (data.iframe) {
|
||||
if (!data.changeContext) message.handle(data);
|
||||
return;
|
||||
}
|
||||
version = data.version;
|
||||
if (version && version !== VERSION && confirm('An updated version of 4chan X is available, would you like to install it now?')) {
|
||||
return window.location = "https://raw.github.com/mayhemydg/4chan-x/" + version + "/4chan_x.user.js";
|
||||
}
|
||||
},
|
||||
send: function(data, iframe) {
|
||||
data.changeContext = true;
|
||||
data.iframe = iframe || 'boards';
|
||||
return postMessage(data, '*');
|
||||
},
|
||||
handle: function(data) {
|
||||
var req, _ref;
|
||||
req = data.req;
|
||||
delete data.req;
|
||||
delete data.iframe;
|
||||
switch (req) {
|
||||
case 'iframeLoad':
|
||||
return message[data.id] = 'ready';
|
||||
case 'abort':
|
||||
if ((_ref = qr.ajax) != null) _ref.abort();
|
||||
return message.send({
|
||||
req: 'status'
|
||||
});
|
||||
case 'response':
|
||||
return qr.response(data.html);
|
||||
case 'status':
|
||||
return qr.status(data);
|
||||
default:
|
||||
return qr.post(data);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
Main = {
|
||||
init: function() {
|
||||
var cutoff, hiddenThreads, id, now, pathname, temp, timestamp, _ref;
|
||||
@ -3528,9 +3499,11 @@
|
||||
} else {
|
||||
g.PAGENUM = parseInt(temp) || 0;
|
||||
}
|
||||
message.init();
|
||||
$.on(window, 'message', Main.message);
|
||||
if (location.hostname === 'sys.4chan.org') {
|
||||
if (/report/.test(location.search)) {
|
||||
if (location.pathname === '/robots.txt') {
|
||||
qr.message.init();
|
||||
} else if (/report/.test(location.search)) {
|
||||
$.ready(function() {
|
||||
return $.on($('#recaptcha_response_field'), 'keydown', function(e) {
|
||||
if (e.keyCode === 8 && !e.target.value) {
|
||||
@ -3646,6 +3619,16 @@
|
||||
return $.on(d, 'DOMNodeInserted', Main.addStyle);
|
||||
}
|
||||
},
|
||||
message: function(e) {
|
||||
var data, version;
|
||||
data = e.data;
|
||||
version = data.version;
|
||||
if (data.qr && !data.changeContext) {
|
||||
return qr.message.receive(data);
|
||||
} else if (version && version !== VERSION && confirm('An updated version of 4chan X is available, would you like to install it now?')) {
|
||||
return window.location = "https://raw.github.com/mayhemydg/4chan-x/" + version + "/4chan_x.user.js";
|
||||
}
|
||||
},
|
||||
node: function(e) {
|
||||
var callback, target, _i, _len, _ref, _results;
|
||||
target = e.target;
|
||||
|
||||
297
script.coffee
297
script.coffee
@ -880,6 +880,19 @@ qr =
|
||||
$.before form, link
|
||||
g.callbacks.push @node
|
||||
|
||||
iframe = $.el 'iframe',
|
||||
id: 'iframe'
|
||||
hidden: true
|
||||
src: 'http://sys.4chan.org/robots.txt'
|
||||
$.on iframe, 'error', -> @src = @src
|
||||
# Greasemonkey ghetto fix
|
||||
loadChecking = (iframe) ->
|
||||
unless qr.status.ready
|
||||
iframe.src = 'about:blank'
|
||||
setTimeout (-> iframe.src = 'http://sys.4chan.org/robots.txt'), 250
|
||||
$.on iframe, 'load', -> unless @src is 'about:blank' then setTimeout loadChecking, 500, @
|
||||
$.add d.body, iframe
|
||||
|
||||
if conf['Persistent QR']
|
||||
qr.dialog()
|
||||
qr.hide() if conf['Auto Hide QR']
|
||||
@ -901,7 +914,7 @@ qr =
|
||||
qr.dialog()
|
||||
close: ->
|
||||
qr.el.hidden = true
|
||||
message.send req: 'abort', 'sys'
|
||||
qr.message.send req: 'abort'
|
||||
d.activeElement.blur()
|
||||
$.removeClass qr.el, 'dump'
|
||||
for i in qr.replies
|
||||
@ -1274,6 +1287,7 @@ qr =
|
||||
qr.status()
|
||||
qr.cooldown.init()
|
||||
qr.captcha.init()
|
||||
qr.message.init()
|
||||
$.add d.body, qr.el
|
||||
|
||||
# Create a custom event when the QR dialog is first initialized.
|
||||
@ -1288,7 +1302,7 @@ qr =
|
||||
qr.cooldown.auto = !qr.cooldown.auto
|
||||
qr.status()
|
||||
return
|
||||
message.send req: 'abort', 'sys'
|
||||
qr.message.send req: 'abort'
|
||||
reply = qr.replies[0]
|
||||
|
||||
# prevent errors
|
||||
@ -1357,11 +1371,11 @@ qr =
|
||||
file.name = reply.file.name
|
||||
file.type = reply.file.type
|
||||
post.upfile = file
|
||||
message.send post, 'sys'
|
||||
qr.message.send post
|
||||
reader.readAsBinaryString reply.file
|
||||
return
|
||||
|
||||
message.send post, 'sys'
|
||||
qr.message.send post
|
||||
|
||||
response: (html) ->
|
||||
unless b = $ 'td b', $.el('a', innerHTML: html)
|
||||
@ -1413,78 +1427,121 @@ qr =
|
||||
qr.status()
|
||||
qr.resetFileInput()
|
||||
|
||||
post: (data) ->
|
||||
message:
|
||||
init: ->
|
||||
# http://code.google.com/p/chromium/issues/detail?id=20773
|
||||
# Let content scripts see other frames (instead of them being undefined)
|
||||
# To access the parent, we have to break out of the sandbox and evaluate
|
||||
# in the global context.
|
||||
code = (e) ->
|
||||
{data} = e
|
||||
return unless data.changeContext
|
||||
delete data.changeContext
|
||||
host = location.hostname
|
||||
if host is 'boards.4chan.org'
|
||||
document.getElementById('iframe').contentWindow.postMessage data, '*'
|
||||
else if host is 'sys.4chan.org'
|
||||
parent.postMessage data, '*'
|
||||
script = $.el 'script', textContent: "window.addEventListener('message',#{code},false)"
|
||||
ready = ->
|
||||
$.add d.documentElement, script
|
||||
if location.hostname is 'sys.4chan.org'
|
||||
qr.message.send req: 'status', ready: true
|
||||
$.rm script
|
||||
# Chrome can access the documentElement on document-start
|
||||
if d.documentElement
|
||||
ready()
|
||||
# other browsers will have to wait
|
||||
else $.ready ready
|
||||
send: (data) ->
|
||||
data.changeContext = true
|
||||
data.qr = true
|
||||
postMessage data, '*'
|
||||
receive: (data) ->
|
||||
switch data.req
|
||||
when 'abort'
|
||||
qr.ajax?.abort()
|
||||
qr.message.send req: 'status'
|
||||
when 'response' # xhr response
|
||||
qr.response data.html
|
||||
when 'status'
|
||||
qr.status data
|
||||
else
|
||||
qr.message.post data # Reply object: we're posting
|
||||
|
||||
url = "http://sys.4chan.org/#{data.board}/post"
|
||||
# Do not append that value to the form.
|
||||
delete data.board
|
||||
post: (data) ->
|
||||
|
||||
# File with filename upload fix from desuwa
|
||||
if engine is 'gecko' and data.upfile
|
||||
# All of this is fucking retarded.
|
||||
unless data.binary
|
||||
toBin = (data, name, val) ->
|
||||
bb = new MozBlobBuilder()
|
||||
bb.append val
|
||||
r = new FileReader()
|
||||
r.onload = ->
|
||||
data[name] = r.result
|
||||
unless --i
|
||||
qr.post data
|
||||
r.readAsBinaryString bb.getBlob 'text/plain'
|
||||
i = Object.keys(data).length
|
||||
for name, val of data
|
||||
if typeof val is 'object' # File. toBin the filename.
|
||||
toBin data.upfile, 'name', data.upfile.name
|
||||
else if typeof val is 'boolean'
|
||||
if val
|
||||
toBin data, name, String val
|
||||
url = "http://sys.4chan.org/#{data.board}/post"
|
||||
# Do not append these values to the form.
|
||||
delete data.board
|
||||
delete data.qr
|
||||
|
||||
# File with filename upload fix from desuwa
|
||||
if engine is 'gecko' and data.upfile
|
||||
# All of this is fucking retarded.
|
||||
unless data.binary
|
||||
toBin = (data, name, val) ->
|
||||
bb = new MozBlobBuilder()
|
||||
bb.append val
|
||||
r = new FileReader()
|
||||
r.onload = ->
|
||||
data[name] = r.result
|
||||
unless --i
|
||||
qr.message.post data
|
||||
r.readAsBinaryString bb.getBlob 'text/plain'
|
||||
i = Object.keys(data).length
|
||||
for name, val of data
|
||||
if typeof val is 'object' # File. toBin the filename.
|
||||
toBin data.upfile, 'name', data.upfile.name
|
||||
else if typeof val is 'boolean'
|
||||
if val
|
||||
toBin data, name, String val
|
||||
else
|
||||
i--
|
||||
else
|
||||
i--
|
||||
else
|
||||
toBin data, name, val
|
||||
data.board = url.split('/')[3]
|
||||
data.binary = true
|
||||
return
|
||||
toBin data, name, val
|
||||
data.board = url.split('/')[3]
|
||||
data.binary = true
|
||||
return
|
||||
|
||||
delete data.binary
|
||||
delete data.binary
|
||||
|
||||
boundary = '-------------SMCD' + Date.now();
|
||||
parts = []
|
||||
parts.push 'Content-Disposition: form-data; name="upfile"; filename="' + data.upfile.name + '"\r\n' + 'Content-Type: ' + data.upfile.type + '\r\n\r\n' + data.upfile.buffer + '\r\n'
|
||||
delete data.upfile
|
||||
boundary = '-------------SMCD' + Date.now();
|
||||
parts = []
|
||||
parts.push 'Content-Disposition: form-data; name="upfile"; filename="' + data.upfile.name + '"\r\n' + 'Content-Type: ' + data.upfile.type + '\r\n\r\n' + data.upfile.buffer + '\r\n'
|
||||
delete data.upfile
|
||||
|
||||
for name, val of data
|
||||
parts.push 'Content-Disposition: form-data; name="' + name + '"\r\n\r\n' + val + '\r\n' if val
|
||||
form = '--' + boundary + '\r\n' + parts.join('--' + boundary + '\r\n') + '--' + boundary + '--\r\n'
|
||||
for name, val of data
|
||||
parts.push 'Content-Disposition: form-data; name="' + name + '"\r\n\r\n' + val + '\r\n' if val
|
||||
form = '--' + boundary + '\r\n' + parts.join('--' + boundary + '\r\n') + '--' + boundary + '--\r\n'
|
||||
|
||||
else
|
||||
form = new FormData()
|
||||
for name, val of data
|
||||
form.append name, val if val
|
||||
else
|
||||
form = new FormData()
|
||||
for name, val of data
|
||||
form.append name, val if val
|
||||
|
||||
callbacks =
|
||||
onload: ->
|
||||
message.send
|
||||
req: 'response'
|
||||
html: @response
|
||||
opts =
|
||||
form: form
|
||||
type: 'post'
|
||||
upCallbacks:
|
||||
callbacks =
|
||||
onload: ->
|
||||
message.send
|
||||
req: 'status'
|
||||
progress: '...'
|
||||
onprogress: (e) ->
|
||||
message.send
|
||||
req: 'status'
|
||||
progress: "#{Math.round e.loaded / e.total * 100}%"
|
||||
if boundary
|
||||
opts.headers =
|
||||
'Content-Type': 'multipart/form-data;boundary=' + boundary
|
||||
qr.message.send
|
||||
req: 'response'
|
||||
html: @response
|
||||
opts =
|
||||
form: form
|
||||
type: 'post'
|
||||
upCallbacks:
|
||||
onload: ->
|
||||
qr.message.send
|
||||
req: 'status'
|
||||
progress: '...'
|
||||
onprogress: (e) ->
|
||||
qr.message.send
|
||||
req: 'status'
|
||||
progress: "#{Math.round e.loaded / e.total * 100}%"
|
||||
if boundary
|
||||
opts.headers =
|
||||
'Content-Type': 'multipart/form-data;boundary=' + boundary
|
||||
|
||||
qr.ajax = $.ajax url, callbacks, opts
|
||||
qr.ajax = $.ajax url, callbacks, opts
|
||||
|
||||
options =
|
||||
init: ->
|
||||
@ -1864,7 +1921,7 @@ updater =
|
||||
else
|
||||
d.title = d.title.match(/^.+-/)[0] + ' 404'
|
||||
unread.update true
|
||||
message.send req: 'abort', 'sys'
|
||||
qr.message.send req: 'abort'
|
||||
qr.status()
|
||||
Favicon.update()
|
||||
return
|
||||
@ -2656,98 +2713,6 @@ imgExpand =
|
||||
resize: ->
|
||||
imgExpand.style.innerHTML = ".fitheight img[md5] + img {max-height:#{d.body.clientHeight}px;}"
|
||||
|
||||
message =
|
||||
init: ->
|
||||
$.on window, 'message', message.receive
|
||||
|
||||
$.ready ->
|
||||
return if location.hostname isnt 'boards.4chan.org'
|
||||
domains = []
|
||||
if conf['Quick Reply']
|
||||
domains.push 'sys'
|
||||
if conf['Image Expansion'] or conf['Sauce']
|
||||
domains.push 'images'
|
||||
for domain in domains
|
||||
iframe = $.el 'iframe',
|
||||
id: domain
|
||||
hidden: true
|
||||
src: "http://#{domain}.4chan.org/robots.txt"
|
||||
$.on iframe, 'error', message.loadControl
|
||||
$.on iframe, 'load', message.loadControl
|
||||
$.add d.body, iframe
|
||||
|
||||
# http://code.google.com/p/chromium/issues/detail?id=20773
|
||||
# Let content scripts see other frames (instead of them being undefined)
|
||||
# To access the parent, we have to break out of the sandbox and evaluate
|
||||
# in the global context.
|
||||
code = (e) ->
|
||||
{data} = e
|
||||
return unless data.changeContext
|
||||
delete data.changeContext
|
||||
if location.hostname is 'boards.4chan.org'
|
||||
document.getElementById(data.iframe).contentWindow.postMessage data, '*'
|
||||
else
|
||||
parent.postMessage data, '*'
|
||||
|
||||
script = $.el 'script',
|
||||
textContent: "window.addEventListener('message',#{code},false)"
|
||||
|
||||
$.ready ->
|
||||
$.add d.documentElement, script
|
||||
host = location.hostname
|
||||
if host is 'sys.4chan.org'
|
||||
message.send req: 'status', ready: true
|
||||
if host isnt 'boards.4chan.org'
|
||||
message.send req: 'iframeLoad', id: location.hostname.split('.')[0]
|
||||
$.rm script
|
||||
|
||||
loadControl: ->
|
||||
# Make sure the iframe has loaded correctly.
|
||||
# This is necessary for Greasemonkey users.
|
||||
setTimeout (=>
|
||||
return if @src is 'about:blank' or message[@id] is 'ready'
|
||||
@src = 'about:blank'
|
||||
setTimeout (=>
|
||||
@src = "http://#{@id}.4chan.org/robots.txt"
|
||||
), 250
|
||||
), 1000
|
||||
|
||||
receive: (e) ->
|
||||
{data} = e
|
||||
if data.iframe
|
||||
unless data.changeContext
|
||||
message.handle data
|
||||
return
|
||||
|
||||
{version} = data
|
||||
if version and version isnt VERSION and confirm 'An updated version of 4chan X is available, would you like to install it now?'
|
||||
window.location = "https://raw.github.com/mayhemydg/4chan-x/#{version}/4chan_x.user.js"
|
||||
|
||||
send: (data, iframe) ->
|
||||
data.changeContext = true
|
||||
data.iframe = iframe or 'boards'
|
||||
postMessage data, '*'
|
||||
|
||||
handle: (data) ->
|
||||
{req} = data
|
||||
|
||||
delete data.req
|
||||
delete data.iframe
|
||||
|
||||
switch req
|
||||
when 'iframeLoad'
|
||||
message[data.id] = 'ready'
|
||||
when 'abort'
|
||||
qr.ajax?.abort()
|
||||
message.send req: 'status'
|
||||
when 'response' # xhr response
|
||||
qr.response data.html
|
||||
when 'status'
|
||||
qr.status data
|
||||
else
|
||||
# Reply object: we're posting
|
||||
qr.post data
|
||||
|
||||
Main =
|
||||
init: ->
|
||||
pathname = location.pathname[1..].split('/')
|
||||
@ -2758,10 +2723,12 @@ Main =
|
||||
else
|
||||
g.PAGENUM = parseInt(temp) or 0
|
||||
|
||||
message.init()
|
||||
$.on window, 'message', Main.message
|
||||
|
||||
if location.hostname is 'sys.4chan.org'
|
||||
if /report/.test location.search
|
||||
if location.pathname is '/robots.txt'
|
||||
qr.message.init()
|
||||
else if /report/.test location.search
|
||||
$.ready ->
|
||||
$.on $('#recaptcha_response_field'), 'keydown', (e) ->
|
||||
window.location = 'javascript:Recaptcha.reload()' if e.keyCode is 8 and not e.target.value
|
||||
@ -2920,6 +2887,14 @@ Main =
|
||||
else # XXX fox
|
||||
$.on d, 'DOMNodeInserted', Main.addStyle
|
||||
|
||||
message: (e) ->
|
||||
{data} = e
|
||||
{version} = data
|
||||
if data.qr and not data.changeContext
|
||||
qr.message.receive data
|
||||
else if version and version isnt VERSION and confirm 'An updated version of 4chan X is available, would you like to install it now?'
|
||||
window.location = "https://raw.github.com/mayhemydg/4chan-x/#{version}/4chan_x.user.js"
|
||||
|
||||
node: (e) ->
|
||||
{target} = e
|
||||
return unless target.nodeName is 'TABLE'
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user