Научный консалтинг
Главная
Контакты
Номер телефона
Как мы работаем
Гарантии
Условия
Цены

Последнее обновление:

Как в javascript преобразовать специальные символы в HTML-сущности?

За исключением кириллицы, латинских букв и служебных символов

Т.е. поставим задачу:

если символ в строке JS не является ни цифрой, ни латинской, ни кириллической (русской) буквой, ни служебным символом (типа * ! . , > и т.д.), то преобразовываем его в HTML-сущность.

Ниже приведен универсальный JS-скрипт, пригодный для преобразования даже составных символов юникода, т.е. так называемых суррогатных пар.

HTML-сущности бывают двух видов, различающиеся синтаксисом

Например, для знака умножения × можно использовать следующие синтаксисы:

  1. ×  (в виде мнемоники)
  2. × (в виде десятичного html-кода)

Первый вариант предпочтительнее, так как его легче запомнить (поэтому такой синтаксис и называется мнемоническим). Однако, мнемоники существуют не для всех символов: например, для символа ‡ ( - двойной крестик) мненомика отсутствует. Поэтому, конечно, второй вариант – более универсальный.

Для чего это может быть нужно?

Например, для отображения на вебстранице специальных символов, если эта страница закодирована при помощи какой-нибудь национальной кодировки, не UTF-8 (последняя, видимо, станет скоро стандартной кодировкой по умолчанию). Например, в Windows-1251 (cp1251 – синоним).

На всякий случай:

  1. Термин «UTF» означает: «Unix transformation formats». Т.е. в UNIX/LINUX эта кодировка является стандартной. Ее предшественником является кодировка EUC (Extended Unix Code).
  2. Сам javascript хранит данные в кодировке UTF-16.

А не UTF-8! Несмотря на то, что отправка данных на сервер при помощи JS осуществляется все-таки в кодировке UTF-8. Кроме того, кодировка UTF-16 используется еще, например, в Java.

  1. Кодировка UTF-16 представляет собой расширенную версию двухбайтовой кодировки UCS-2, куда дополнен так называемый механизм суррогатных пар, при помощи которого отображаются символы юникода высоких номеров, например, разного рода смайлики.

Скрипт JS для преобразования остальных символов в HTML-сущности:

Основа скрипта взята отсюда и еще отсюда. Но, при этом он несколько доработан. Данный скрипт преобразовывает ПОЧТИ все остальные символы (за исключением перечисленных выше) в HTML-сущности, по возможности, в первую очередь используя мнемоники:

< ?php

header('Content-Type: text/html; charset=utf-8');

?>

<div>div>

<br>

<div id="qwer" style="width: 400px">div>


<script >

   function escapeHtmlEntities(text) { // Превращаем в HTML-сущности почти всё, за исключением цифр, латинских и русских букв, служебных символов

// Будут отображаться даже символы - суррогатные пары (типа смайликов), вставленные на страницу в режиме редактирования

       return [text.replace(/[\uD800-\uDBFF][\uDC00-\uDFFF] | [\u00A0-\u0400\u0402-\u040F\u0450\u0452-\u2115\u2117-\uFFFF]/g, function(c) {

           var charValue;

           if (c.length == 2) {

// Если символ представляет собой суррогатные пару юникода

               var  high = c.charCodeAt(0) - 0xD800;

               var  low  = c.charCodeAt(1) - 0xDC00;

               charValue = (high * 0x400) + low + 0x10000;

           }

           else {

               // Если это обычный символ юникода, НЕ являющийся суррогатной парой

               charValue = c.charCodeAt(0);

           }


           return '&' + (escapeHtmlEntities.entityTable[c.charCodeAt(0)] || '#'+charValue) + ';';}) ];

   }


   // Все HTML4 сущности определены здесь: http://www.w3.org/TR/html4/sgml/entities.html

   escapeHtmlEntities.entityTable = {

      34 : 'quot', 38 : 'amp', 39 : 'apos', 60 : 'lt', 62 : 'gt', 160 : 'nbsp', 161 : 'iexcl', 162 : 'cent', 163 : 'pound', 164 : 'curren', 165 : 'yen', 166 : 'brvbar', 167 : 'sect', 168 : 'uml', 169 : 'copy', 170 : 'ordf', 171 : 'laquo', 172 : 'not', 173 : 'shy', 174 : 'reg', 175 : 'macr', 176 : 'deg', 177 : 'plusmn', 178 : 'sup2', 179 : 'sup3', 180 : 'acute', 181 : 'micro', 182 : 'para', 183 : 'middot', 184 : 'cedil', 185 : 'sup1', 186 : 'ordm', 187 : 'raquo', 188 : 'frac14', 189 : 'frac12', 190 : 'frac34', 191 : 'iquest', 192 : 'Agrave', 193 : 'Aacute', 194 : 'Acirc', 195 : 'Atilde', 196 : 'Auml', 197 : 'Aring', 198 : 'AElig', 199 : 'Ccedil', 200 : 'Egrave', 201 : 'Eacute', 202 : 'Ecirc', 203 : 'Euml', 204 : 'Igrave', 205 : 'Iacute', 206 : 'Icirc', 207 : 'Iuml', 208 : 'ETH', 209 : 'Ntilde', 210 : 'Ograve', 211 : 'Oacute', 212 : 'Ocirc', 213 : 'Otilde', 214 : 'Ouml', 215 : 'times', 216 : 'Oslash', 217 : 'Ugrave', 218 : 'Uacute', 219 : 'Ucirc', 220 : 'Uuml', 221 : 'Yacute', 222 : 'THORN', 223 : 'szlig', 224 : 'agrave', 225 : 'aacute', 226 : 'acirc', 227 : 'atilde', 228 : 'auml', 229 : 'aring', 230 : 'aelig', 231 : 'ccedil', 232 : 'egrave', 233 : 'eacute', 234 : 'ecirc', 235 : 'euml', 236 : 'igrave', 237 : 'iacute', 238 : 'icirc', 239 : 'iuml', 240 : 'eth', 241 : 'ntilde', 242 : 'ograve', 243 : 'oacute', 244 : 'ocirc', 245 : 'otilde', 246 : 'ouml', 247 : 'divide', 248 : 'oslash', 249 : 'ugrave', 250 : 'uacute', 251 : 'ucirc', 252 : 'uuml', 253 : 'yacute', 254 : 'thorn', 255 : 'yuml', 402 : 'fnof', 913 : 'Alpha', 914 : 'Beta', 915 : 'Gamma', 916 : 'Delta', 917 : 'Epsilon', 918 : 'Zeta', 919 : 'Eta', 920 : 'Theta', 921 : 'Iota', 922 : 'Kappa', 923 : 'Lambda', 924 : 'Mu', 925 : 'Nu', 926 : 'Xi', 927 : 'Omicron', 928 : 'Pi', 929 : 'Rho', 931 : 'Sigma', 932 : 'Tau', 933 : 'Upsilon', 934 : 'Phi', 935 : 'Chi', 936 : 'Psi', 937 : 'Omega', 945 : 'alpha', 946 : 'beta', 947 : 'gamma', 948 : 'delta', 949 : 'epsilon', 950 : 'zeta', 951 : 'eta', 952 : 'theta', 953 : 'iota', 954 : 'kappa', 955 : 'lambda', 956 : 'mu', 957 : 'nu', 958 : 'xi', 959 : 'omicron', 960 : 'pi', 961 : 'rho', 962 : 'sigmaf', 963 : 'sigma', 964 : 'tau', 965 : 'upsilon', 966 : 'phi', 967 : 'chi', 968 : 'psi', 969 : 'omega', 977 : 'thetasym', 978 : 'upsih', 982 : 'piv', 8226 : 'bull', 8230 : 'hellip', 8242 : 'prime', 8243 : 'Prime', 8254 : 'oline', 8260 : 'frasl', 8472 : 'weierp', 8465 : 'image', 8476 : 'real', 8482 : 'trade', 8501 : 'alefsym', 8592 : 'larr', 8593 : 'uarr', 8594 : 'rarr', 8595 : 'darr', 8596 : 'harr', 8629 : 'crarr', 8656 : 'lArr', 8657 : 'uArr', 8658 : 'rArr', 8659 : 'dArr', 8660 : 'hArr', 8704 : 'forall', 8706 : 'part', 8707 : 'exist', 8709 : 'empty', 8711 : 'nabla', 8712 : 'isin', 8713 : 'notin', 8715 : 'ni', 8719 : 'prod', 8721 : 'sum', 8722 : 'minus', 8727 : 'lowast', 8730 : 'radic', 8733 : 'prop', 8734 : 'infin', 8736 : 'ang', 8743 : 'and', 8744 : 'or', 8745 : 'cap', 8746 : 'cup', 8747 : 'int', 8756 : 'there4', 8764 : 'sim', 8773 : 'cong', 8776 : 'asymp', 8800 : 'ne', 8801 : 'equiv', 8804 : 'le', 8805 : 'ge', 8834 : 'sub', 8835 : 'sup', 8836 : 'nsub', 8838 : 'sube', 8839 : 'supe', 8853 : 'oplus', 8855 : 'otimes', 8869 : 'perp', 8901 : 'sdot', 8968 : 'lceil', 8969 : 'rceil', 8970 : 'lfloor', 8971 : 'rfloor', 9001 : 'lang', 9002 : 'rang', 9674 : 'loz', 9824 : 'spades', 9827 : 'clubs', 9829 : 'hearts', 9830 : 'diams', 338 : 'OElig', 339 : 'oelig', 352 : 'Scaron', 353 : 'scaron', 376 : 'Yuml', 710 : 'circ', 732 : 'tilde', 8194 : 'ensp', 8195 : 'emsp', 8201 : 'thinsp', 8204 : 'zwnj', 8205 : 'zwj', 8206 : 'lrm', 8207 : 'rlm', 8211 : 'ndash', 8212 : 'mdash', 8216 : 'lsquo', 8217 : 'rsquo', 8218 : 'sbquo', 8220 : 'ldquo', 8221 : 'rdquo', 8222 : 'bdquo', 8224 : 'dagger', 8225 : 'Dagger', 8240 : 'permil', 8249 : 'lsaquo', 8250 : 'rsaquo', 8364 : 'euro' };


   var text = "Übergroße Äpfel mit Würmern ×  Ё!\"№ ;%:?*()_+ \n ё1234567890-=\n ~`@#$%^&*()_+ \n ЙЦУКЕНГШЩЗХЪФЫВАПРОЛДЖЭЯЧСМИТЬБЮ./ \n йцукенгшщзхъфывапролджэячсмитьбю.\\" + '\n'+        "qwertyuiop[]asdfghjkl;<>?'zxcvbnm,./ \n QWERTYUIOP{}ASDFGHJKL:\"ZXCVBNM,./|"+

       '\n'+ '♞ ♟  뀀 退 ﻼ  𐒅';


var arr = escapeHtmlEntities(text);

   alert( arr[0]);

document.getElementById('qwer').innerHTML = arr[0];

script>


Этот файл должен быть сохранен в кодировке UTF-8.

Примечание. Для наиболее полного отображения символов юникода, состоящих их суррогатных пар, целесообразно использовать, например, редактор Notepad++ - он отлично отображает всё. Тогда как, скажем, в PHPStorm символы юникода, имеющие номер выше 65535, могут отображаться квадратиками (при этом они, конечно, будут присутствовать в тексте).

Результат

Вот что получается при запуске этого файла в браузере (вполне сойдет и Firefox, скажем, 10-летней давности):

Результат работы скрипта
Результат работы скрипта

Как видно в окне функции alert, все символы русского и латинского алфавитов, а также цифры и служебные символы остались без изменений. А вот остальные символы преобразовались либо и символьные HTML-сущности (по возможности), либо в числовые HTML-сущности.

На всякий случай: символьной HTML-сущностью называется конструкция, имеющая синтаксис вида &Uuml; , &times; и т.д. Числовая HTML-сущность – это, к примеру, &#9823; &#65532; и др.

Числовая сущность существует для любого символа юникода, даже состоящего из двух суррогатных пар. Тогда как символьная – только для наиболее распространенных символов.

В переменную text записана тестовая строка, содержащая все латинские и кириллические (русские) буквы, а также цифры и служебные символы. Кроме того, в начале тестовой строки приведена фраза на немецком языке, содержащая, в том числе, и специфично немецкие буквы.

Основная «рабочая часть» скрипта – это регулярное выражение из символов юникода, которое представляет собой шаблон для замены. Согласно этому шаблону, на HTML-сущности будут заменяться почти все символы в диапазоне кодов от U+00A0 до U+0400.

Т.е. все символы, начиная с пробела и вплоть до U+040F (&#9830;). Букве Ё соответствует код U+0401, букве ё - U+0451, а символу № - код U+2116. Поэтому эти символы исключены из диапазонов регулярного выражения.

Цифры, латинские буквы, пробел и разные служебные символы занимают диапазон U+0020 … U+007E. Кириллица (за исключением букв ё, Ё): U+0410 … U+044F. С учетом этого и было сформировано такое регулярное выражение.

Что же касается мнемоник, то их перечень может быть дополнен – в зависимости от потребностей.

Обратите внимание на последний символ, напоминающий латинскую букву h, оформленную курсивом (в alert он отобразился в виде числовой HTMLсущности &#66693;). Несмотря на то, что он представляет собой суррогатную пару (так как выходит за пределы U+FFFF), тем не менее, на открытой в браузере странице вполне хорошо виден.

В заключение

Этот скрипт может быть применен и на сайтах с национальной кодировкой, например, Windows-1251 (правда, тогда символы в переменной text придется задавать путем вставки из буфера обмена или т.п.). Все символы юникода, в том числе и состоящие из суррогатных пар, при отправке сообщений со страницы (например, посредством технологии AJAX) можно будет перед отправкой кодировать в виде HTML-сущностей и, таким образом, избавиться от необходимости использовать кодировку UTF-8 на сайте. Соответственно, и на сервере они будут храниться в виде HTML-сущностей, а не в виде символов юникода. Кстати, некоторые ресурсы, даже крупные до сих пор работают в национальных кодировках и хранят символы юникода именно в виде HTML-сущностей.

У начинающих может возникнуть вопрос: как же на сайтах, страницы которых закодированы НЕ при помощи юникода (UTF-8), тем не менее сможет работать этот скрипт? Всё просто: дело в том, что javascript хранит строки в любом случае в юникоде (точнее, в UTF-16). Поэтому нет особой разницы, в какой именно кодировке закодирован HTML-код страницы. Для проверки этого факта, можно перевести страницу в режим редактирования (путем соответствующего плагина или через JS, задав тегу body атрибут contenteditable: true).

Если же потребуется не подвергать кодированию символы иного алфавита – не русского, а, скажем, немецкого (если в операционной системе будет установлена немецкая локаль), при этом кириллицу, наоборот, необходимо будет кодировать - то регулярное выражение придется соответствующим образом изменить.


Комментарии:
Женя Пустозвонов09.04.2020 21:51РедактироватьУдалить
Добрый вечер
Всего комментариев: 1
Пожалуйста, не забудьте ознакомиться с правилами оставления комментариев.



Подписаться на комментарии на этой странице

Мы можем выполнить

Другие услуги
Интересная и полезная
информация