unescape - Decodificar UTF-8 con Javascript
javascript html entities to utf 8 (9)
// Cadena a Utf8 ByteBuffer
function strToUTF8(str){
return Uint8Array.from(encodeURIComponent(str).replace(/%(..)/g,(m,v)=>{return String.fromCodePoint(parseInt(v,16))}), c=>c.codePointAt(0))
}
// Utf8 ByteArray a cadena
function UTF8toStr(ba){
return decodeURIComponent(ba.reduce((p,c)=>{return p+''%''+c.toString(16),''''}))
}
Tengo Javascript en una página web XHTML que está pasando cadenas codificadas en UTF-8. Necesita continuar aprobando la versión UTF-8, así como también decodificarla. ¿Cómo es posible decodificar una cadena UTF-8 para mostrar?
<script type="text/javascript">
// <![CDATA[
function updateUser(usernameSent){
var usernameReceived = usernameSent; // Current value: Größe
var usernameDecoded = usernameReceived; // Decode to: Größe
var html2id = '''';
html2id += ''Encoded: '' + usernameReceived + ''<br />Decoded: '' + usernameDecoded;
document.getElementById(''userId'').innerHTML = html2id;
}
// ]]>
</script>
Actualiza la condición de suma de respuesta de @ Albert para emoji.
function Utf8ArrayToStr(array) {
var out, i, len, c;
var char2, char3, char4;
out = "";
len = array.length;
i = 0;
while(i < len) {
c = array[i++];
switch(c >> 4)
{
case 0: case 1: case 2: case 3: case 4: case 5: case 6: case 7:
// 0xxxxxxx
out += String.fromCharCode(c);
break;
case 12: case 13:
// 110x xxxx 10xx xxxx
char2 = array[i++];
out += String.fromCharCode(((c & 0x1F) << 6) | (char2 & 0x3F));
break;
case 14:
// 1110 xxxx 10xx xxxx 10xx xxxx
char2 = array[i++];
char3 = array[i++];
out += String.fromCharCode(((c & 0x0F) << 12) |
((char2 & 0x3F) << 6) |
((char3 & 0x3F) << 0));
break;
case 15:
// 1111 0xxx 10xx xxxx 10xx xxxx 10xx xxxx
char2 = array[i++];
char3 = array[i++];
char4 = array[i++];
out += String.fromCodePoint(((c & 0x07) << 18) | ((char2 & 0x3F) << 12) | ((char3 & 0x3F) << 6) | (char4 & 0x3F));
break;
}
return out;
}
Aquí hay una solución que maneja todos los puntos de código Unicode que incluyen valores superiores (4 bytes) y es compatible con todos los navegadores modernos (IE y otros> 5.5). Utiliza decodeURIComponent (), pero NO las funciones de escape / unescape obsoletas:
function utf8_to_str(a) {
for(var i=0, s=''''; i<a.length; i++) {
var h = a[i].toString(16)
if(h.length < 2) h = ''0'' + h
s += ''%'' + h
}
return decodeURIComponent(s)
}
Probado y disponible en GitHub
Para crear UTF-8 a partir de una cadena:
function utf8_from_str(s) {
for(var i=0, enc = encodeURIComponent(s), a = []; i < enc.length;) {
if(enc[i] === ''%'') {
a.push(parseInt(enc.substr(i+1, 2), 16))
i += 3
} else {
a.push(enc.charCodeAt(i++))
}
}
return a
}
Probado y disponible en GitHub
Busqué una solución simple y esto funciona bien para mí:
//input data
view = new Uint8Array(data);
//output string
serialString = ua2text(view);
//convert UTF8 to string
function ua2text(ua) {
s = "";
for (var i = 0; i < ua.length; i++) {
s += String.fromCharCode(ua[i]);
}
return s;
}
El único problema que tengo es que a veces tengo un personaje a la vez. Esto podría ser por diseño con mi fuente del arraybuffer. Estoy usando https://github.com/xseignard/cordovarduino para leer datos en serie en un dispositivo Android.
Creo que la manera más fácil sería usar las funciones js incorporadas decodeURI () / encodeURI ().
function (usernameSent) {
var usernameEncoded = usernameSent; // Current value: utf8
var usernameDecoded = decodeURI(usernameReceived); // Decoded
// do stuff
}
Esto debería funcionar:
// http://www.onicos.com/staff/iz/amuse/javascript/expert/utf.txt
/* utf.js - UTF-8 <=> UTF-16 convertion
*
* Copyright (C) 1999 Masanao Izumo <[email protected]>
* Version: 1.0
* LastModified: Dec 25 1999
* This library is free. You can redistribute it and/or modify it.
*/
function Utf8ArrayToStr(array) {
var out, i, len, c;
var char2, char3;
out = "";
len = array.length;
i = 0;
while(i < len) {
c = array[i++];
switch(c >> 4)
{
case 0: case 1: case 2: case 3: case 4: case 5: case 6: case 7:
// 0xxxxxxx
out += String.fromCharCode(c);
break;
case 12: case 13:
// 110x xxxx 10xx xxxx
char2 = array[i++];
out += String.fromCharCode(((c & 0x1F) << 6) | (char2 & 0x3F));
break;
case 14:
// 1110 xxxx 10xx xxxx 10xx xxxx
char2 = array[i++];
char3 = array[i++];
out += String.fromCharCode(((c & 0x0F) << 12) |
((char2 & 0x3F) << 6) |
((char3 & 0x3F) << 0));
break;
}
}
return out;
}
Mira la demostración de JSFiddle .
La solución de @albert fue lo más parecido que creo, pero solo puede analizar hasta 3 bytes de caracteres utf-8.
function utf8ArrayToStr(array) {
var out, i, len, c;
var char2, char3;
out = "";
len = array.length;
i = 0;
// XXX: Invalid bytes are ignored
while(i < len) {
c = array[i++];
if (c >> 7 == 0) {
// 0xxx xxxx
out += String.fromCharCode(c);
continue;
}
// Invalid starting byte
if (c >> 6 == 0x02) {
continue;
}
// #### MULTIBYTE ####
// How many bytes left for thus character?
var extraLength = null;
if (c >> 5 == 0x06) {
extraLength = 1;
} else if (c >> 4 == 0x0e) {
extraLength = 2;
} else if (c >> 3 == 0x1e) {
extraLength = 3;
} else if (c >> 2 == 0x3e) {
extraLength = 4;
} else if (c >> 1 == 0x7e) {
extraLength = 5;
} else {
continue;
}
// Do we have enough bytes in our data?
if (i+extraLength > len) {
var leftovers = array.slice(i-1);
// If there is an invalid byte in the leftovers we might want to
// continue from there.
for (; i < len; i++) if (array[i] >> 6 != 0x02) break;
if (i != len) continue;
// All leftover bytes are valid.
return {result: out, leftovers: leftovers};
}
// Remove the UTF-8 prefix from the char (res)
var mask = (1 << (8 - extraLength - 1)) - 1,
res = c & mask, nextChar, count;
for (count = 0; count < extraLength; count++) {
nextChar = array[i++];
// Is the char valid multibyte part?
if (nextChar >> 6 != 0x02) {break;};
res = (res << 6) | (nextChar & 0x3f);
}
if (count != extraLength) {
i--;
continue;
}
if (res <= 0xffff) {
out += String.fromCharCode(res);
continue;
}
res -= 0x10000;
var high = ((res >> 10) & 0x3ff) + 0xd800,
low = (res & 0x3ff) + 0xdc00;
out += String.fromCharCode(high, low);
}
return {result: out, leftovers: []};
}
Esto devuelve {result: "parsed string", leftovers: [list of invalid bytes at the end]}
en caso de que esté analizando la cadena en fragmentos.
EDIT: solucionó el problema que encontró @unhammer.
Para responder la pregunta original: así es como decodifica utf-8 en javascript:
http://ecmanaut.blogspot.ca/2006/07/encoding-decoding-utf8-in-javascript.html
Específicamente,
function encode_utf8(s) {
return unescape(encodeURIComponent(s));
}
function decode_utf8(s) {
return decodeURIComponent(escape(s));
}
Acabo de usar esto en mi código, y funciona perfectamente.
Tal vez usar el textDecoder sea ​​suficiente.
Sin embargo, no es compatible con todos los navegadores. Pero podría ser suficiente si utiliza el cruce de peatones o cualquier otro caso de uso donde sepa qué navegador se utiliza.
var decoder = new TextDecoder(''utf-8''),
decodedMessage;
decodedMessage = decoder.decode(message.data);