var base64Encode = function(data) {
var map = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/';
var out = '';
for (var i = 0, len = data.length; i < len; i += 3) {
var binStr = '',
newStr = '',
threeChar = data.slice(i, i+3);
for (var j = 0; j < 3; j++) {
var t = threeChar.charCodeAt(j).toString(2);
while (t.length < 8) t = '0' + t;
binStr += t;
}
for (var k = 0; k < 24; k += 6) {
newStr += map[parseInt(binStr.slice(k, k+6), 2)];
}
if (i+3-len == 1) newStr = newStr.slice(0, 3) + '=';
if (i+3-len == 2) newStr = newStr.slice(0, 2) + '==';
out += newStr;
}
return out;
};
var base64Decode = function(code) {
var map = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/';
var ascii = ' !"#$%&\'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ' +
'[\\]^_`abcdefghijklmnopqrstuvwxyz{|}~';
var out = '';
for (var i = 0, len = code.length; i < len; i += 4) {
var fourChar = code.slice(i, i+4),
binStr = '',
newStr = '';
for (var j = 0; j < 4; j++) {
var t = map.indexOf(fourChar.charAt(j)).toString(2);
while (t.length < 6) t = '0' + t;
binStr += t;
}
for (var k = 0; k < 24; k += 8) {
var char = ascii[parseInt(binStr.slice(k, k+8), 2) - 32];
if (char !== undefined) newStr += char;
}
out += newStr;
}
return out;
};
function utf8_to_b64( str ) {
return window.btoa(unescape(encodeURIComponent(str)));
}
function b64_to_utf8( str ) {
return decodeURIComponent(escape(window.atob(str)));
}