Ticket #15085: overpass-turbo-lzw.js

File overpass-turbo-lzw.js, 7.3 KB (added by Don-vip, 7 years ago)
Line 
1/* ---
2 * Copied from https://github.com/tyrasd/overpass-turbo/blob/e12b7a07fbdf18db2fe70a7f8a064e6737daaa7e/js/misc.js
3 * ---
4 * Base64 encode / decode
5 * initial version fom http://www.webtoolkit.info/
6 * modified to support more url friendly variant "base64url".
7 * modified to include Base64 for decimal numbers.
8 * modified to support native (= much faster) base64 encoders
9 * ---
10 * lzw_* taken from jsolait library (http://jsolait.net/), LGPL
11 * slightly modified to support utf8 strings.
12 */
13var Base64 = {
14 // private property
15 _keyStr: "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=",
16
17 // public method for encoding
18 encode: function(input, not_base64url) {
19 var output = "";
20 input = unescape(encodeURIComponent(input));
21
22 /*if (typeof window.btoa == "function") {
23 output = window.btoa(input);
24 } else*/ {
25 var chr1, chr2, chr3, enc1, enc2, enc3, enc4;
26 var i = 0;
27
28 while (i < input.length) {
29 chr1 = input.charCodeAt(i++);
30 chr2 = input.charCodeAt(i++);
31 chr3 = input.charCodeAt(i++);
32
33 enc1 = chr1 >> 2;
34 enc2 = ((chr1 & 3) << 4) | (chr2 >> 4);
35 enc3 = ((chr2 & 15) << 2) | (chr3 >> 6);
36 enc4 = chr3 & 63;
37
38 if (isNaN(chr2)) {
39 enc3 = enc4 = 64;
40 } else if (isNaN(chr3)) {
41 enc4 = 64;
42 }
43
44 output =
45 output +
46 this._keyStr.charAt(enc1) +
47 this._keyStr.charAt(enc2) +
48 this._keyStr.charAt(enc3) +
49 this._keyStr.charAt(enc4);
50 }
51 }
52
53 if (!not_base64url) return this._convert_to_base64url(output);
54 else return output;
55 },
56
57 // public method for decoding
58 // this decodes base64url as well as standard base64 with or without padding)
59 decode: function(input, binary) {
60 var output = "";
61 input = this._convert_to_base64nopad(input);
62 input = input.replace(/[^A-Za-z0-9\+\/]/g, "");
63 //reappend the padding
64 input = input + "==".substring(0, (4 - input.length % 4) % 4);
65
66 /*if (typeof window.btoa == "function") {
67 output = window.atob(input);
68 } else*/ {
69 var chr1, chr2, chr3;
70 var enc1, enc2, enc3, enc4;
71 var i = 0;
72
73 while (i < input.length) {
74 enc1 = this._keyStr.indexOf(input.charAt(i++));
75 enc2 = this._keyStr.indexOf(input.charAt(i++));
76 enc3 = this._keyStr.indexOf(input.charAt(i++));
77 enc4 = this._keyStr.indexOf(input.charAt(i++));
78
79 chr1 = (enc1 << 2) | (enc2 >> 4);
80 chr2 = ((enc2 & 15) << 4) | (enc3 >> 2);
81 chr3 = ((enc3 & 3) << 6) | enc4;
82
83 output = output + String.fromCharCode(chr1);
84
85 if (enc3 != 64) {
86 output = output + String.fromCharCode(chr2);
87 }
88 if (enc4 != 64) {
89 output = output + String.fromCharCode(chr3);
90 }
91 }
92 }
93
94 function str2ab(str) {
95 var buf = new ArrayBuffer(str.length); // 1 byte for each char
96 var bufView = new Uint8Array(buf);
97 for (var i = 0, strLen = str.length; i < strLen; i++) {
98 bufView[i] = str.charCodeAt(i);
99 }
100 return buf;
101 }
102
103 if (!binary) {
104 // try to decode utf8 characters
105 try {
106 output = decodeURIComponent(escape(output));
107 } catch (e) {}
108 } else {
109 // convert binary string to typed (Uint8) array
110 output = str2ab(output);
111 }
112 return output;
113 },
114
115 encodeNum: function(num, not_base64url) {
116 var output = "";
117 if (num == 0) return this._keyStr.charAt(0);
118 var neg = false;
119 if (num < 0) {
120 neg = true;
121 num = Math.abs(num);
122 }
123 while (num > 0) {
124 output = this._keyStr.charAt(num % 64) + output;
125 num -= num % 64;
126 num /= 64;
127 }
128 if (neg) output = "~" + output;
129 if (!not_base64url) return this._convert_to_base64url(output);
130 else return output;
131 },
132
133 decodeNum: function(input) {
134 input = this._convert_to_base64nopad(input);
135 input = input.replace(/[^A-Za-z0-9\+\/.]/g, "");
136 var num = 0;
137 var neg = false;
138 if (input.charAt(0) == ".") {
139 neg = true;
140 input = input.substr(1);
141 }
142 for (var i = 0; i < input.length; i++) {
143 num +=
144 this._keyStr.indexOf(input.charAt(input.length - 1 - i)) *
145 Math.pow(64, i);
146 }
147 return (neg ? -1 : 1) * num;
148 },
149
150 _convert_to_base64url: function(input) {
151 return input.replace(/\+/g, "-").replace(/\//g, "_").replace(/=/g, "");
152 },
153 _convert_to_base64nopad: function(input) {
154 return input.replace(/\-/g, "+").replace(/_/g, "/");
155 },
156
157 // private method for UTF-8 encoding
158 _utf8_encode: function(string) {
159 string = string.replace(/\r\n/g, "\n");
160 var utftext = "";
161
162 for (var n = 0; n < string.length; n++) {
163 var c = string.charCodeAt(n);
164
165 if (c < 128) {
166 utftext += String.fromCharCode(c);
167 } else if (c > 127 && c < 2048) {
168 utftext += String.fromCharCode((c >> 6) | 192);
169 utftext += String.fromCharCode((c & 63) | 128);
170 } else {
171 utftext += String.fromCharCode((c >> 12) | 224);
172 utftext += String.fromCharCode(((c >> 6) & 63) | 128);
173 utftext += String.fromCharCode((c & 63) | 128);
174 }
175 }
176
177 return utftext;
178 },
179
180 // private method for UTF-8 decoding
181 _utf8_decode: function(utftext) {
182 var string = "";
183 var i = 0;
184 var c = (c1 = c2 = 0);
185
186 while (i < utftext.length) {
187 c = utftext.charCodeAt(i);
188
189 if (c < 128) {
190 string += String.fromCharCode(c);
191 i++;
192 } else if (c > 191 && c < 224) {
193 c2 = utftext.charCodeAt(i + 1);
194 string += String.fromCharCode(((c & 31) << 6) | (c2 & 63));
195 i += 2;
196 } else {
197 c2 = utftext.charCodeAt(i + 1);
198 c3 = utftext.charCodeAt(i + 2);
199 string += String.fromCharCode(
200 ((c & 15) << 12) | ((c2 & 63) << 6) | (c3 & 63)
201 );
202 i += 3;
203 }
204 }
205
206 return string;
207 }
208};
209
210// LZW-compress a string
211function lzw_encode(s) {
212 s = unescape(encodeURIComponent(s));
213 var dict = {};
214 var data = (s + "").split("");
215 var out = [];
216 var currChar;
217 var phrase = data[0];
218 var code = 256;
219 for (var i = 1; i < data.length; i++) {
220 currChar = data[i];
221 if (dict[phrase + currChar] != null) {
222 phrase += currChar;
223 } else {
224 out.push(phrase.length > 1 ? dict[phrase] : phrase.charCodeAt(0));
225 dict[phrase + currChar] = code;
226 code++;
227 phrase = currChar;
228 }
229 }
230 out.push(phrase.length > 1 ? dict[phrase] : phrase.charCodeAt(0));
231 for (var i = 0; i < out.length; i++) {
232 out[i] = String.fromCharCode(out[i]);
233 }
234 return out.join("");
235}
236
237// Decompress an LZW-encoded string
238function lzw_decode(s) {
239 var dict = {};
240 var data = (s + "").split("");
241 var currChar = data[0];
242 var oldPhrase = currChar;
243 var out = [currChar];
244 var code = 256;
245 var phrase;
246 for (var i = 1; i < data.length; i++) {
247 var currCode = data[i].charCodeAt(0);
248 if (currCode < 256) {
249 phrase = data[i];
250 } else {
251 phrase = dict[currCode] ? dict[currCode] : oldPhrase + currChar;
252 }
253 out.push(phrase);
254 currChar = phrase.charAt(0);
255 dict[code] = oldPhrase + currChar;
256 code++;
257 oldPhrase = phrase;
258 }
259 return decodeURIComponent(escape(out.join("")));
260}