如何使用JavaScript将特殊的UTF-8字符转换为与iso-8859-1等效的字符?

我正在做一个JavaScript应用程序,它使用jQuery检索.json文件,并将数据注入到embedded的网页中。

.json文件使用UTF-8编码,包含重音字符,如é,ö和å。

问题是,我不控制将要使用该应用程序的页面上的字符集。

有些将使用UTF-8,但其他将使用iso-8859-1字符集。 这当然会从.json文件中弄出特殊的字符。

如何使用JavaScript将特殊的UTF-8字符转换为与iso-8859-1等效的字符?

实际上,一切内容通常都是以某种Unicode的forms存储的,但是不要赘述。 我假设你正在使用ISO-8859作为你的字符编码来获得标志性的“åâûÔtypes的string。 有一个技巧,你可以做转换这些字符。 用于编码和解码查询string的escapeunescape函数是为ISO字符定义的,而更新的encodeURIComponentdecodeURIComponent则是为UTF8字符定义的。

escape编码扩展ISO-8859-1字符(UTF代码点U + 0080-U + 00ff)为%xx (两位hex),而它将UTF代码点U + 0100及以上编码为%uxxxx%u , )例如, escape("å") == "%E5"escape("あ") == "%u3042"

encodeURIComponent将扩展字符百分比编码为UTF8字节序列。 例如encodeURIComponent("å") == "%C3%A5"encodeURIComponent("あ") == "%E3%81%82"

所以你可以这样做:

 fixedstring = decodeURIComponent(escape(utfstring)); 

例如,错误编码的字符“å”变成“Ã¥”。 该命令确实escape("Ã¥") == "%C3%A5" ,这是两个不正确的ISO字符编码为单个字节。 然后decodeURIComponent("%C3%A5") == "å" ,其中两个编码百分比的字节被解释为一个UTF8序列。

如果出于某种原因需要做相反的操作,那也是可行的:

 utfstring = unescape(encodeURIComponent(originalstring)); 

有没有办法区分不好的UTF8string和ISOstring? 原来是有的。 如果给出格式不正确的编码序列,则上面使用的decodeURIComponent函数将引发错误。 我们可以用这个来检测我们的string是UTF8还是ISO。

 var fixedstring; try{ // If the string is UTF-8, this will work and not throw an error. fixedstring=decodeURIComponent(escape(badstring)); }catch(e){ // If it isn't, an error will be thrown, and we can asume that we have an ISO string. fixedstring=badstring; } 

问题是,一旦页面被提供,内容将在内容types元标记中描述的编码。 “错误”编码的内容已经乱码了。

您最好在服务器上完成此操作之前在服务器上执行此操作。 或者正如我所知道的那样: UTF-8端到端或者死亡

在内部,Javascriptstring都是Unicode(实际上是UCS-2,UTF-16的一个子集)。

如果您通过AJAX单独检索JSON文件,那么您只需确保JSON文件具有正确的Content-Type和charset: Content-Type: application/json; charset="utf-8" Content-Type: application/json; charset="utf-8" )。 如果你这样做,jQuery应该在你访问反序列化对象时已经正确解释了它们。

你能发表一个你用来检索JSON对象的代码的例子吗?

由于关于如何从ISO-8859-1转换为UTF-8的问题已经closures了,因为这个我要在这里发布我的解决scheme。

问题是当你试图通过使用XMLHttpRequest获取任何东西,如果XMLHttpRequest.responseType是“文本”或空的,XMLHttpRequest.response被转换为DOMString,这是事情分手。 之后,使用该string进行可靠的工作几乎是不可能的。

现在,如果来自服务器的内容是ISO-8859-1,则必须强制响应为“ Blob ”types,然后将其转换为DOMSTring。 例如:

 var ajax = new XMLHttpRequest(); ajax.open('GET', url, true); ajax.responseType = 'blob'; ajax.onreadystatechange = function(){ ... if(ajax.responseType === 'blob'){ // Convert the blob to a string var reader = new window.FileReader(); reader.addEventListener('loadend', function() { // For ISO-8859-1 there's no further conversion required Promise.resolve(reader.result); }); reader.readAsBinaryString(ajax.response); } } 

看起来像readAsBinaryString上发生的魔术,所以也许有人可以阐明为什么这个工程。

我正在寻找这个答案,但认为在许多代码的一行,可能是这样的:

  var converted = "<?php echo mb_convert_encoding($str_to_convert, 'UTF-8', 'ISO-8859-1'); ?>"; 

这对我有用,但是如果你把这个variables放到php中,像这样:

  document.write("<?php $str_to_convert = " + your_str + " ?>"); 

希望这也有助于任何人。

您应该在页面上方添加此行

 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />