Skip to content

Commit 1d74a8c

Browse files
committed
0.2
1 parent bed3865 commit 1d74a8c

File tree

3 files changed

+76
-76
lines changed

3 files changed

+76
-76
lines changed

README.md

+2-9
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,6 @@
11
Sometimes you just want to transform the page's contents into a data URL - this userscript will do it.
22

3-
Works for all HTML pages and *most* other data types:
4-
5-
- SVGs refuse to work for some reason
6-
- Some images will not work if the HTTP headers are too restrictive.
3+
Works for all HTML pages and *most* other data types (SVGs will sometimes refuse to load)
74

85
# Usage
9-
Click on Tampermonkey's icon and select "get data URL" when viewing the page/media you wish to URLise.
10-
11-
# Erm, Chrome dev tools?
12-
Yes, Chrome's dev tools do allow you to get a data URL of an image, but they don't work for other media, e.g. sound;
13-
plus, sometimes it's more convenient to use the monkey icon :smirk:
6+
Click on Tampermonkey's icon and select "get data URL" when viewing the page/media you wish to URLise. Alternatively, click "Search for images" and get data URLs for every image on the page!

data-url.meta.js

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
// ==UserScript==
2-
// @version 0.1.1
2+
// @version 0.2
33
// @name Data URL generator
44
// @namespace https://github.com/AlorelUserscripts/data-url-generator
55
// ==/UserScript==

data-url.user.js

+73-66
Original file line numberDiff line numberDiff line change
@@ -12,16 +12,13 @@
1212
// @grant GM_notification
1313
// @grant GM_openInTab
1414
// @grant GM_xmlhttpRequest
15-
// @grant GM_setValue
16-
// @grant GM_getValue
1715
// @connect *
1816
// @noframes
1917
// @require https://cdn.rawgit.com/coolaj86/TextEncoderLite/v1.0.0/index.js
2018
// @require https://cdn.rawgit.com/beatgammit/base64-js/v1.1.2/base64js.min.js
2119
// @downloadURL https://raw.githubusercontent.com/AlorelUserscripts/data-url-generator/master/data-url.user.js
2220
// @updateURL https://raw.githubusercontent.com/AlorelUserscripts/data-url-generator/master/data-url.meta.js
23-
24-
// @icon https://cdn.rawgit.com/AlorelUserscripts/data-url-generator/develop/assets/ico.png
21+
// @icon https://cdn.rawgit.com/AlorelUserscripts/data-url-generator/0.2/assets/ico.png
2522
// @license LGPL-2.1
2623
// ==/UserScript==
2724

@@ -58,16 +55,11 @@
5855
contentTypeRegex = /content\-type:\s+([^\/]+\/[a-z0-9]+)/ig,
5956
failedEncodeRegex = /^data:;/g,
6057
bgImgRegex = /url\(['"]?([^'"\)]+)['"]?\)/g,
58+
dataUrlRegex = /^data:/,
6159
menuCallback,
6260
pseudos = [null, "before", "after"],
63-
BG_IMG_NONE = "none";
64-
65-
if (document.contentType === "text/html") {
66-
menuCallback = function () {
67-
saveDataURL("data:text/html;base64," + base64js.fromByteArray(encoder.encode(document.firstElementChild.outerHTML)));
68-
};
69-
} else {
70-
var blobToDataURL = function (blob, callback, fallbackContentType) {
61+
BG_IMG_NONE = "none",
62+
blobToDataURL = function (blob, callback, fallbackContentType) {
7163
if ("undefined" === typeof fallbackContentType) {
7264
fallbackContentType = false;
7365
}
@@ -80,7 +72,14 @@
8072
callback(res);
8173
};
8274
a.readAsDataURL(blob);
83-
}, readyStateListener = function () {
75+
};
76+
77+
if (document.contentType === "text/html") {
78+
menuCallback = function () {
79+
saveDataURL("data:text/html;base64," + base64js.fromByteArray(encoder.encode(document.firstElementChild.outerHTML)));
80+
};
81+
} else {
82+
var readyStateListener = function () {
8483
var fallbackContentType = null,
8584
headers = this.responseHeaders.split("\n"),
8685
i = 0;
@@ -105,29 +104,26 @@
105104

106105
GM_registerMenuCommand("Get data URL!", menuCallback, "d");
107106
GM_registerMenuCommand("Search for images", function () {
108-
var ret = [],
109-
pageElements = document.querySelectorAll("*"),
110-
i = 0,
111-
j, k,
112-
bgImg;
107+
toast({
108+
text: "Parsing the page for ya, chief!",
109+
timeout: 3000
110+
});
111+
/** @type {Set} */
112+
var ret = new Set();
113+
var pageElements = document.querySelectorAll("*"),
114+
i = 0, j, k, bgImg;
113115

114116
for (; i < pageElements.length; i++) {
115117
if (pageElements[i] instanceof HTMLImageElement) {
116-
ret.push({
117-
url: pageElements[i].src,
118-
element: pageElements[i]
119-
});
118+
ret.add(pageElements[i].src);
120119
} else {
121120
for (j = 0; j < pseudos.length; j++) {
122121
if (
123122
(bgImg = getComputedStyle(pageElements[i], pseudos[j]).backgroundImage) !== BG_IMG_NONE &&
124123
(bgImg = bgImg.match(bgImgRegex))
125124
) {
126125
for (k = 0; k < bgImg.length; k++) {
127-
ret.push({
128-
url: bgImg[k].replace(bgImgRegex, "$1"),
129-
element: pageElements[i]
130-
});
126+
ret.add(bgImg[k].replace(bgImgRegex, "$1"));
131127
}
132128
}
133129
}
@@ -136,50 +132,61 @@
136132

137133
//Begin generating our DOM
138134
var body = document.createElement("body"),
139-
table = document.createElement("table"),
140-
thead = document.createElement("thead"),
141-
tfoot = document.createElement("tfoot"),
142-
tbody = document.createElement("tbody"),
143-
tr, preview, selector;
144-
145-
table.style.width = "100%";
146-
table.style.borderCollapse = "collapse";
147-
thead.innerHTML = '<tr>\
148-
<th style="border:1px solid black">Preview</th>\
149-
<th style="border:1px solid black">Rough selector</th>\
150-
</tr>';
151-
tfoot.innerHTML = thead.innerHTML;
152-
153-
ret.forEach(function (r) {
154-
tr = document.createElement("tr");
155-
preview = document.createElement("td");
156-
selector = document.createElement("td");
135+
progress = document.createElement("progress"),
136+
ajaxPostListener = function (dataurl) {
137+
var a = document.createElement("a");
138+
a.setAttribute("style", "float:left;margin:5px;border:1px solid #000;text-decoration:none");
139+
a.href = dataurl;
140+
a.target = '_blank';
141+
a.innerHTML = '<img src="' + dataurl + '"/>';
142+
body.appendChild(a);
143+
progress.value = ++numProcessed;
144+
145+
if (numProcessed >= ret.size) {
146+
body.innerHTML += "<script>\
147+
document.getElementById('bgcolour').addEventListener('change',function(){\
148+
document.body.style.backgroundColor= this.value;\
149+
});\
150+
</script>";
151+
152+
GM_openInTab("data:text/html;base64," + base64js.fromByteArray(encoder.encode(body.outerHTML)));
153+
progress.parentNode.removeChild(progress);
154+
}
155+
},
156+
ajaxListener = function () {
157+
var fallbackContentType = null,
158+
headers = this.responseHeaders.split("\n"),
159+
i = 0;
160+
for (; i < headers.length; i++) {
161+
if (headers[i].match(contentTypeRegex)) {
162+
fallbackContentType = headers[i].replace(contentTypeRegex, "$1");
163+
break;
164+
}
165+
}
166+
blobToDataURL(this.response, ajaxPostListener, fallbackContentType);
167+
},
168+
numProcessed = 0;
157169

158-
selector.style.whiteSpace = "nowrap";
159-
tr.style.border = preview.style.border = selector.style.border = "1px solid black";
170+
progress.max = ret.size;
171+
progress.value = 0;
172+
progress.setAttribute("style", "position:fixed;top:0;right:0");
173+
document.body.appendChild(progress);
160174

161-
preview.innerHTML = '<img src="' + r.url + '" style="max-width:100%;height:auto"/>';
162-
selector.innerText = 'To be implemented';
175+
body.innerHTML = "<input id='bgcolour' type='color' value='#ffffff' style='position:fixed;bottom:0;right:0;text-align:center;'/>";
176+
body.style.backgroundColor = "#ffffff";
163177

164-
tr.appendChild(preview);
165-
tr.appendChild(selector);
166-
tbody.appendChild(tr);
178+
ret.forEach(function (url) {
179+
if (url.match(dataUrlRegex)) {
180+
ajaxPostListener(url);
181+
} else {
182+
GM_xmlhttpRequest({
183+
responseType: "blob",
184+
method: "GET",
185+
url: url,
186+
onload: ajaxListener
187+
});
188+
}
167189
});
168-
169-
table.appendChild(thead);
170-
table.appendChild(tbody);
171-
table.appendChild(tfoot);
172-
body.appendChild(table);
173-
174-
var a = document.createElement("a"),
175-
event = document.createEvent('HTMLEvents');
176-
event.initEvent('click', true, false);
177-
a.href = "data:text/html;base64," + base64js.fromByteArray(encoder.encode(body.outerHTML));
178-
a.target = "_blank";
179-
a.style.display = "none";
180-
document.body.appendChild(a);
181-
a.dispatchEvent(event);
182-
a.parentNode.removeChild(a);
183190
}, "s");
184191
}
185192
})(GM_notification);

0 commit comments

Comments
 (0)