typograf 6.14.1 → 6.15.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -0
- package/dist/typograf.all.js +25 -5
- package/dist/typograf.all.min.js +1 -1
- package/dist/typograf.es.js +3143 -0
- package/dist/typograf.js +21 -5
- package/dist/typograf.min.js +1 -1
- package/dist/typograf.titles.js +4 -0
- package/dist/typograf.titles.json +4 -0
- package/docs/RULES.en-US.md +45 -44
- package/docs/RULES.ru.md +45 -44
- package/docs/RULES_SORTED.en-US.md +68 -67
- package/docs/RULES_SORTED.ru.md +68 -67
- package/package.json +11 -6
|
@@ -0,0 +1,3143 @@
|
|
|
1
|
+
/*! typograf | © 2022 Denis Seleznev | MIT License | https://github.com/typograf/typograf */
|
|
2
|
+
function _typeof(obj) {
|
|
3
|
+
"@babel/helpers - typeof";
|
|
4
|
+
|
|
5
|
+
return _typeof = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function (obj) {
|
|
6
|
+
return typeof obj;
|
|
7
|
+
} : function (obj) {
|
|
8
|
+
return obj && "function" == typeof Symbol && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj;
|
|
9
|
+
}, _typeof(obj);
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
function _classCallCheck(instance, Constructor) {
|
|
13
|
+
if (!(instance instanceof Constructor)) {
|
|
14
|
+
throw new TypeError("Cannot call a class as a function");
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
function _defineProperties(target, props) {
|
|
19
|
+
for (var i = 0; i < props.length; i++) {
|
|
20
|
+
var descriptor = props[i];
|
|
21
|
+
descriptor.enumerable = descriptor.enumerable || false;
|
|
22
|
+
descriptor.configurable = true;
|
|
23
|
+
if ("value" in descriptor) descriptor.writable = true;
|
|
24
|
+
Object.defineProperty(target, descriptor.key, descriptor);
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
function _createClass(Constructor, protoProps, staticProps) {
|
|
29
|
+
if (protoProps) _defineProperties(Constructor.prototype, protoProps);
|
|
30
|
+
if (staticProps) _defineProperties(Constructor, staticProps);
|
|
31
|
+
Object.defineProperty(Constructor, "prototype", {
|
|
32
|
+
writable: false
|
|
33
|
+
});
|
|
34
|
+
return Constructor;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
function _slicedToArray(arr, i) {
|
|
38
|
+
return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest();
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
function _arrayWithHoles(arr) {
|
|
42
|
+
if (Array.isArray(arr)) return arr;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
function _iterableToArrayLimit(arr, i) {
|
|
46
|
+
var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"];
|
|
47
|
+
|
|
48
|
+
if (_i == null) return;
|
|
49
|
+
var _arr = [];
|
|
50
|
+
var _n = true;
|
|
51
|
+
var _d = false;
|
|
52
|
+
|
|
53
|
+
var _s, _e;
|
|
54
|
+
|
|
55
|
+
try {
|
|
56
|
+
for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) {
|
|
57
|
+
_arr.push(_s.value);
|
|
58
|
+
|
|
59
|
+
if (i && _arr.length === i) break;
|
|
60
|
+
}
|
|
61
|
+
} catch (err) {
|
|
62
|
+
_d = true;
|
|
63
|
+
_e = err;
|
|
64
|
+
} finally {
|
|
65
|
+
try {
|
|
66
|
+
if (!_n && _i["return"] != null) _i["return"]();
|
|
67
|
+
} finally {
|
|
68
|
+
if (_d) throw _e;
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
return _arr;
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
function _unsupportedIterableToArray(o, minLen) {
|
|
76
|
+
if (!o) return;
|
|
77
|
+
if (typeof o === "string") return _arrayLikeToArray(o, minLen);
|
|
78
|
+
var n = Object.prototype.toString.call(o).slice(8, -1);
|
|
79
|
+
if (n === "Object" && o.constructor) n = o.constructor.name;
|
|
80
|
+
if (n === "Map" || n === "Set") return Array.from(o);
|
|
81
|
+
if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen);
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
function _arrayLikeToArray(arr, len) {
|
|
85
|
+
if (len == null || len > arr.length) len = arr.length;
|
|
86
|
+
|
|
87
|
+
for (var i = 0, arr2 = new Array(len); i < len; i++) arr2[i] = arr[i];
|
|
88
|
+
|
|
89
|
+
return arr2;
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
function _nonIterableRest() {
|
|
93
|
+
throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.");
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
var groupIndexes = {
|
|
97
|
+
symbols: 110,
|
|
98
|
+
space: 210,
|
|
99
|
+
dash: 310,
|
|
100
|
+
punctuation: 410,
|
|
101
|
+
nbsp: 510,
|
|
102
|
+
'number': 610,
|
|
103
|
+
money: 710,
|
|
104
|
+
date: 810,
|
|
105
|
+
other: 910,
|
|
106
|
+
optalign: 1010,
|
|
107
|
+
typo: 1110,
|
|
108
|
+
html: 1210
|
|
109
|
+
};
|
|
110
|
+
|
|
111
|
+
// http://www.w3.org/TR/html4/sgml/entities
|
|
112
|
+
var visibleEntities = [['iexcl', 161], ['cent', 162], ['pound', 163], ['curren', 164], ['yen', 165], ['brvbar', 166], ['sect', 167], ['uml', 168], ['copy', 169], ['ordf', 170], ['laquo', 171], ['not', 172], ['reg', 174], ['macr', 175], ['deg', 176], ['plusmn', 177], ['sup2', 178], ['sup3', 179], ['acute', 180], ['micro', 181], ['para', 182], ['middot', 183], ['cedil', 184], ['sup1', 185], ['ordm', 186], ['raquo', 187], ['frac14', 188], ['frac12', 189], ['frac34', 190], ['iquest', 191], ['Agrave', 192], ['Aacute', 193], ['Acirc', 194], ['Atilde', 195], ['Auml', 196], ['Aring', 197], ['AElig', 198], ['Ccedil', 199], ['Egrave', 200], ['Eacute', 201], ['Ecirc', 202], ['Euml', 203], ['Igrave', 204], ['Iacute', 205], ['Icirc', 206], ['Iuml', 207], ['ETH', 208], ['Ntilde', 209], ['Ograve', 210], ['Oacute', 211], ['Ocirc', 212], ['Otilde', 213], ['Ouml', 214], ['times', 215], ['Oslash', 216], ['Ugrave', 217], ['Uacute', 218], ['Ucirc', 219], ['Uuml', 220], ['Yacute', 221], ['THORN', 222], ['szlig', 223], ['agrave', 224], ['aacute', 225], ['acirc', 226], ['atilde', 227], ['auml', 228], ['aring', 229], ['aelig', 230], ['ccedil', 231], ['egrave', 232], ['eacute', 233], ['ecirc', 234], ['euml', 235], ['igrave', 236], ['iacute', 237], ['icirc', 238], ['iuml', 239], ['eth', 240], ['ntilde', 241], ['ograve', 242], ['oacute', 243], ['ocirc', 244], ['otilde', 245], ['ouml', 246], ['divide', 247], ['oslash', 248], ['ugrave', 249], ['uacute', 250], ['ucirc', 251], ['uuml', 252], ['yacute', 253], ['thorn', 254], ['yuml', 255], ['fnof', 402], ['Alpha', 913], ['Beta', 914], ['Gamma', 915], ['Delta', 916], ['Epsilon', 917], ['Zeta', 918], ['Eta', 919], ['Theta', 920], ['Iota', 921], ['Kappa', 922], ['Lambda', 923], ['Mu', 924], ['Nu', 925], ['Xi', 926], ['Omicron', 927], ['Pi', 928], ['Rho', 929], ['Sigma', 931], ['Tau', 932], ['Upsilon', 933], ['Phi', 934], ['Chi', 935], ['Psi', 936], ['Omega', 937], ['alpha', 945], ['beta', 946], ['gamma', 947], ['delta', 948], ['epsilon', 949], ['zeta', 950], ['eta', 951], ['theta', 952], ['iota', 953], ['kappa', 954], ['lambda', 955], ['mu', 956], ['nu', 957], ['xi', 958], ['omicron', 959], ['pi', 960], ['rho', 961], ['sigmaf', 962], ['sigma', 963], ['tau', 964], ['upsilon', 965], ['phi', 966], ['chi', 967], ['psi', 968], ['omega', 969], ['thetasym', 977], ['upsih', 978], ['piv', 982], ['bull', 8226], ['hellip', 8230], ['prime', 8242], ['Prime', 8243], ['oline', 8254], ['frasl', 8260], ['weierp', 8472], ['image', 8465], ['real', 8476], ['trade', 8482], ['alefsym', 8501], ['larr', 8592], ['uarr', 8593], ['rarr', 8594], ['darr', 8595], ['harr', 8596], ['crarr', 8629], ['lArr', 8656], ['uArr', 8657], ['rArr', 8658], ['dArr', 8659], ['hArr', 8660], ['forall', 8704], ['part', 8706], ['exist', 8707], ['empty', 8709], ['nabla', 8711], ['isin', 8712], ['notin', 8713], ['ni', 8715], ['prod', 8719], ['sum', 8721], ['minus', 8722], ['lowast', 8727], ['radic', 8730], ['prop', 8733], ['infin', 8734], ['ang', 8736], ['and', 8743], ['or', 8744], ['cap', 8745], ['cup', 8746], ['int', 8747], ['there4', 8756], ['sim', 8764], ['cong', 8773], ['asymp', 8776], ['ne', 8800], ['equiv', 8801], ['le', 8804], ['ge', 8805], ['sub', 8834], ['sup', 8835], ['nsub', 8836], ['sube', 8838], ['supe', 8839], ['oplus', 8853], ['otimes', 8855], ['perp', 8869], ['sdot', 8901], ['lceil', 8968], ['rceil', 8969], ['lfloor', 8970], ['rfloor', 8971], ['lang', 9001], ['rang', 9002], ['spades', 9824], ['clubs', 9827], ['hearts', 9829], ['diams', 9830], ['loz', 9674], ['OElig', 338], ['oelig', 339], ['Scaron', 352], ['scaron', 353], ['Yuml', 376], ['circ', 710], ['tilde', 732], ['ndash', 8211], ['mdash', 8212], ['lsquo', 8216], ['rsquo', 8217], ['sbquo', 8218], ['ldquo', 8220], ['rdquo', 8221], ['bdquo', 8222], ['dagger', 8224], ['Dagger', 8225], ['permil', 8240], ['lsaquo', 8249], ['rsaquo', 8250], ['euro', 8364], ['NestedGreaterGreater', 8811], ['NestedLessLess', 8810]];
|
|
113
|
+
|
|
114
|
+
var invisibleEntities = [['nbsp', 160], ['thinsp', 8201], ['ensp', 8194], ['emsp', 8195], ['shy', 173], ['zwnj', 8204], ['zwj', 8205], ['lrm', 8206], ['rlm', 8207]];
|
|
115
|
+
|
|
116
|
+
var HtmlEntities = /*#__PURE__*/function () {
|
|
117
|
+
function HtmlEntities() {
|
|
118
|
+
_classCallCheck(this, HtmlEntities);
|
|
119
|
+
|
|
120
|
+
this._entities = this._prepareEntities([].concat(visibleEntities, invisibleEntities));
|
|
121
|
+
this._entitiesByName = {};
|
|
122
|
+
this._entitiesByNameEntity = {};
|
|
123
|
+
this._entitiesByDigitEntity = {};
|
|
124
|
+
this._entitiesByUtf = {};
|
|
125
|
+
|
|
126
|
+
this._entities.forEach(function (entity) {
|
|
127
|
+
this._entitiesByName[entity.name] = entity;
|
|
128
|
+
this._entitiesByNameEntity[entity.nameEntity] = entity;
|
|
129
|
+
this._entitiesByDigitEntity[entity.digitEntity] = entity;
|
|
130
|
+
this._entitiesByUtf[entity.utf] = entity;
|
|
131
|
+
}, this);
|
|
132
|
+
|
|
133
|
+
this._invisibleEntities = this._prepareEntities(invisibleEntities);
|
|
134
|
+
}
|
|
135
|
+
/**
|
|
136
|
+
* Entities as name or digit to UTF-8.
|
|
137
|
+
*
|
|
138
|
+
* @param {Object} context
|
|
139
|
+
*/
|
|
140
|
+
|
|
141
|
+
|
|
142
|
+
_createClass(HtmlEntities, [{
|
|
143
|
+
key: "toUtf",
|
|
144
|
+
value: function toUtf(context) {
|
|
145
|
+
var _this = this;
|
|
146
|
+
|
|
147
|
+
if (context.text.search(/&#/) !== -1) {
|
|
148
|
+
context.text = this.decHexToUtf(context.text);
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
if (context.text.search(/&[a-z]/i) !== -1) {
|
|
152
|
+
// 2 - min length of entity without & and ;. Example: ⅅ
|
|
153
|
+
// 31 - max length of entity without & and ;. Example: ∳
|
|
154
|
+
context.text = context.text.replace(/&[a-z\d]{2,31};/gi, function (key) {
|
|
155
|
+
var entity = _this._entitiesByNameEntity[key];
|
|
156
|
+
return entity ? entity.utf : key;
|
|
157
|
+
});
|
|
158
|
+
}
|
|
159
|
+
}
|
|
160
|
+
/**
|
|
161
|
+
* Entities in decimal or hexadecimal form to UTF-8.
|
|
162
|
+
*
|
|
163
|
+
* @param {string} text
|
|
164
|
+
* @returns {string}
|
|
165
|
+
*/
|
|
166
|
+
|
|
167
|
+
}, {
|
|
168
|
+
key: "decHexToUtf",
|
|
169
|
+
value: function decHexToUtf(text) {
|
|
170
|
+
return text.replace(/&#(\d{1,6});/gi, function ($0, $1) {
|
|
171
|
+
return String.fromCharCode(parseInt($1, 10));
|
|
172
|
+
}).replace(/&#x([\da-f]{1,6});/gi, function ($0, $1) {
|
|
173
|
+
return String.fromCharCode(parseInt($1, 16));
|
|
174
|
+
});
|
|
175
|
+
}
|
|
176
|
+
/**
|
|
177
|
+
* Restore HTML entities in text.
|
|
178
|
+
*
|
|
179
|
+
* @param {Object} context
|
|
180
|
+
*/
|
|
181
|
+
|
|
182
|
+
}, {
|
|
183
|
+
key: "restore",
|
|
184
|
+
value: function restore(context) {
|
|
185
|
+
var params = context.prefs.htmlEntity;
|
|
186
|
+
var type = params.type;
|
|
187
|
+
var entities = this._entities;
|
|
188
|
+
|
|
189
|
+
if (type === 'name' || type === 'digit') {
|
|
190
|
+
if (params.onlyInvisible || params.list) {
|
|
191
|
+
entities = [];
|
|
192
|
+
|
|
193
|
+
if (params.onlyInvisible) {
|
|
194
|
+
entities = entities.concat(this._invisibleEntities);
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
if (params.list) {
|
|
198
|
+
entities = entities.concat(this._prepareListParam(params.list));
|
|
199
|
+
}
|
|
200
|
+
}
|
|
201
|
+
|
|
202
|
+
context.text = this._restoreEntitiesByIndex(context.text, type + 'Entity', entities);
|
|
203
|
+
}
|
|
204
|
+
}
|
|
205
|
+
/**
|
|
206
|
+
* Get a entity by utf using the type.
|
|
207
|
+
*
|
|
208
|
+
* @param {string} symbol
|
|
209
|
+
* @param {string} [type]
|
|
210
|
+
* @returns {string}
|
|
211
|
+
*/
|
|
212
|
+
|
|
213
|
+
}, {
|
|
214
|
+
key: "getByUtf",
|
|
215
|
+
value: function getByUtf(symbol, type) {
|
|
216
|
+
var result = '';
|
|
217
|
+
|
|
218
|
+
switch (type) {
|
|
219
|
+
case 'digit':
|
|
220
|
+
result = this._entitiesByDigitEntity[symbol];
|
|
221
|
+
break;
|
|
222
|
+
|
|
223
|
+
case 'name':
|
|
224
|
+
result = this._entitiesByNameEntity[symbol];
|
|
225
|
+
break;
|
|
226
|
+
|
|
227
|
+
default:
|
|
228
|
+
result = symbol;
|
|
229
|
+
break;
|
|
230
|
+
}
|
|
231
|
+
|
|
232
|
+
return result;
|
|
233
|
+
}
|
|
234
|
+
}, {
|
|
235
|
+
key: "_prepareEntities",
|
|
236
|
+
value: function _prepareEntities(entities) {
|
|
237
|
+
var result = [];
|
|
238
|
+
entities.forEach(function (entity) {
|
|
239
|
+
var _entity = _slicedToArray(entity, 2),
|
|
240
|
+
name = _entity[0],
|
|
241
|
+
digit = _entity[1];
|
|
242
|
+
|
|
243
|
+
var utf = String.fromCharCode(digit);
|
|
244
|
+
result.push({
|
|
245
|
+
name: name,
|
|
246
|
+
nameEntity: '&' + name + ';',
|
|
247
|
+
//
|
|
248
|
+
digitEntity: '&#' + digit + ';',
|
|
249
|
+
//  
|
|
250
|
+
utf: utf,
|
|
251
|
+
// \u00A0
|
|
252
|
+
reName: new RegExp('&' + name + ';', 'g'),
|
|
253
|
+
reUtf: new RegExp(utf, 'g')
|
|
254
|
+
});
|
|
255
|
+
}, this);
|
|
256
|
+
return result;
|
|
257
|
+
}
|
|
258
|
+
}, {
|
|
259
|
+
key: "_prepareListParam",
|
|
260
|
+
value: function _prepareListParam(list) {
|
|
261
|
+
var result = [];
|
|
262
|
+
list.forEach(function (name) {
|
|
263
|
+
var entity = this._entitiesByName[name];
|
|
264
|
+
|
|
265
|
+
if (entity) {
|
|
266
|
+
result.push(entity);
|
|
267
|
+
}
|
|
268
|
+
}, this);
|
|
269
|
+
return result;
|
|
270
|
+
}
|
|
271
|
+
}, {
|
|
272
|
+
key: "_restoreEntitiesByIndex",
|
|
273
|
+
value: function _restoreEntitiesByIndex(text, type, entities) {
|
|
274
|
+
entities.forEach(function (entity) {
|
|
275
|
+
text = text.replace(entity.reUtf, entity[type]);
|
|
276
|
+
});
|
|
277
|
+
return text;
|
|
278
|
+
}
|
|
279
|
+
}]);
|
|
280
|
+
|
|
281
|
+
return HtmlEntities;
|
|
282
|
+
}();
|
|
283
|
+
|
|
284
|
+
var HtmlEntities$1 = new HtmlEntities();
|
|
285
|
+
/**
|
|
286
|
+
* @typedef HtmlEntity
|
|
287
|
+
*
|
|
288
|
+
* @property {string} type - 'default' - UTF-8, 'digit' -  , 'name' -
|
|
289
|
+
* @property {boolean} [onlyInvisible]
|
|
290
|
+
* @property {string[]} [list]
|
|
291
|
+
*/
|
|
292
|
+
|
|
293
|
+
var locales = [];
|
|
294
|
+
/**
|
|
295
|
+
* Add a locale.
|
|
296
|
+
*
|
|
297
|
+
* @param {string} locale
|
|
298
|
+
*/
|
|
299
|
+
|
|
300
|
+
function addLocale(locale) {
|
|
301
|
+
var code = (locale || '').split('/')[0];
|
|
302
|
+
|
|
303
|
+
if (code && code !== 'common' && !hasLocale(code)) {
|
|
304
|
+
locales.push(code);
|
|
305
|
+
locales.sort();
|
|
306
|
+
}
|
|
307
|
+
}
|
|
308
|
+
/**
|
|
309
|
+
* Get locales.
|
|
310
|
+
*
|
|
311
|
+
* @returns {Array}
|
|
312
|
+
*/
|
|
313
|
+
|
|
314
|
+
function getLocales() {
|
|
315
|
+
return locales;
|
|
316
|
+
}
|
|
317
|
+
/**
|
|
318
|
+
* Has a locale.
|
|
319
|
+
*
|
|
320
|
+
* @param {string} locale
|
|
321
|
+
*
|
|
322
|
+
* @returns {boolean}
|
|
323
|
+
*/
|
|
324
|
+
|
|
325
|
+
function hasLocale(locale) {
|
|
326
|
+
return locale === 'common' || locales.indexOf(locale) !== -1;
|
|
327
|
+
}
|
|
328
|
+
function prepareLocale(locale1, locale2) {
|
|
329
|
+
var locale = locale1 || locale2;
|
|
330
|
+
var result = locale;
|
|
331
|
+
|
|
332
|
+
if (!Array.isArray(locale)) {
|
|
333
|
+
result = [locale];
|
|
334
|
+
}
|
|
335
|
+
|
|
336
|
+
return result;
|
|
337
|
+
}
|
|
338
|
+
|
|
339
|
+
var data = {};
|
|
340
|
+
/**
|
|
341
|
+
* Get data for use in rules.
|
|
342
|
+
*
|
|
343
|
+
* @param {string} key
|
|
344
|
+
*
|
|
345
|
+
* @returns {*}
|
|
346
|
+
*/
|
|
347
|
+
|
|
348
|
+
function getData(key) {
|
|
349
|
+
return data[key];
|
|
350
|
+
}
|
|
351
|
+
/**
|
|
352
|
+
* Set data for use in rules.
|
|
353
|
+
*
|
|
354
|
+
* @param {string|Object} key
|
|
355
|
+
* @param {*} [value]
|
|
356
|
+
*/
|
|
357
|
+
|
|
358
|
+
function setData(key, value) {
|
|
359
|
+
if (typeof key === 'string') {
|
|
360
|
+
addLocale(key);
|
|
361
|
+
data[key] = value;
|
|
362
|
+
} else if (_typeof(key) === 'object') {
|
|
363
|
+
Object.keys(key).forEach(function (k) {
|
|
364
|
+
addLocale(k);
|
|
365
|
+
data[k] = key[k];
|
|
366
|
+
});
|
|
367
|
+
}
|
|
368
|
+
}
|
|
369
|
+
|
|
370
|
+
var inlineElements = ['a', 'abbr', 'acronym', 'b', 'bdo', 'big', 'br', 'button', 'cite', 'code', 'dfn', 'em', 'i', 'img', 'input', 'kbd', 'label', 'map', 'object', 'q', 'samp', 'script', 'select', 'small', 'span', 'strong', 'sub', 'sup', 'textarea', 'time', 'tt', 'var'];
|
|
371
|
+
|
|
372
|
+
var regExpUrl = new RegExp('(https?|file|ftp)://([a-zA-Z0-9/+-=%&:_.~?]+[a-zA-Z0-9#+]*)', 'g');
|
|
373
|
+
var regExpNumber = '\\d+([.,]\\d+)?';
|
|
374
|
+
var regExpDigit = /\d/;
|
|
375
|
+
function isDigit(symbol) {
|
|
376
|
+
return symbol.search(regExpDigit) > -1;
|
|
377
|
+
}
|
|
378
|
+
|
|
379
|
+
var privateLabel = "\uF000";
|
|
380
|
+
var privateSeparateLabel = "\uF001";
|
|
381
|
+
|
|
382
|
+
var SafeTags = /*#__PURE__*/function () {
|
|
383
|
+
function SafeTags() {
|
|
384
|
+
_classCallCheck(this, SafeTags);
|
|
385
|
+
|
|
386
|
+
var html = [['<!--', '-->'], ['<!ENTITY', '>'], ['<!DOCTYPE', '>'], ['<\\?xml', '\\?>'], ['<!\\[CDATA\\[', '\\]\\]>']];
|
|
387
|
+
['code', 'kbd', 'object', 'pre', 'samp', 'script', 'style', 'var'].forEach(function (tag) {
|
|
388
|
+
html.push(['<' + tag + '(\\s[^>]*?)?>', '</' + tag + '>']);
|
|
389
|
+
}, this);
|
|
390
|
+
this._tags = {
|
|
391
|
+
own: [],
|
|
392
|
+
html: html.map(this._prepareRegExp),
|
|
393
|
+
url: [regExpUrl]
|
|
394
|
+
};
|
|
395
|
+
this._groups = ['own', 'html', 'url'];
|
|
396
|
+
}
|
|
397
|
+
/**
|
|
398
|
+
* Add own safe tag.
|
|
399
|
+
*
|
|
400
|
+
* @param {RegExp|string[]} tag
|
|
401
|
+
*/
|
|
402
|
+
|
|
403
|
+
|
|
404
|
+
_createClass(SafeTags, [{
|
|
405
|
+
key: "add",
|
|
406
|
+
value: function add(tag) {
|
|
407
|
+
this._tags.own.push(this._prepareRegExp(tag));
|
|
408
|
+
}
|
|
409
|
+
/**
|
|
410
|
+
* Show safe tags.
|
|
411
|
+
*
|
|
412
|
+
* @param {Object} context
|
|
413
|
+
* @param {string} group
|
|
414
|
+
*/
|
|
415
|
+
|
|
416
|
+
}, {
|
|
417
|
+
key: "show",
|
|
418
|
+
value: function show(context, group) {
|
|
419
|
+
var reReplace = new RegExp(privateLabel + 'tf\\d+' + privateLabel, 'g');
|
|
420
|
+
var reSearch = new RegExp(privateLabel + 'tf\\d');
|
|
421
|
+
|
|
422
|
+
var replaceLabel = function replaceLabel(match) {
|
|
423
|
+
return context.safeTags.hidden[group][match] || match;
|
|
424
|
+
};
|
|
425
|
+
|
|
426
|
+
for (var i = 0, len = this._tags[group].length; i < len; i++) {
|
|
427
|
+
context.text = context.text.replace(reReplace, replaceLabel);
|
|
428
|
+
|
|
429
|
+
if (context.text.search(reSearch) === -1) {
|
|
430
|
+
break;
|
|
431
|
+
}
|
|
432
|
+
}
|
|
433
|
+
}
|
|
434
|
+
/**
|
|
435
|
+
* Hide safe tags.
|
|
436
|
+
*
|
|
437
|
+
* @param {Object} context
|
|
438
|
+
* @param {string} group
|
|
439
|
+
*/
|
|
440
|
+
|
|
441
|
+
}, {
|
|
442
|
+
key: "hide",
|
|
443
|
+
value: function hide(context, group) {
|
|
444
|
+
context.safeTags = context.safeTags || {
|
|
445
|
+
hidden: {},
|
|
446
|
+
i: 0
|
|
447
|
+
};
|
|
448
|
+
context.safeTags.hidden[group] = {};
|
|
449
|
+
|
|
450
|
+
var pasteLabel = this._pasteLabel.bind(this, context, group);
|
|
451
|
+
|
|
452
|
+
this._tags[group].forEach(function (tag) {
|
|
453
|
+
context.text = context.text.replace(this._prepareRegExp(tag), pasteLabel);
|
|
454
|
+
}, this);
|
|
455
|
+
}
|
|
456
|
+
/**
|
|
457
|
+
* Hide HTML tags.
|
|
458
|
+
*
|
|
459
|
+
* @param {Object} context
|
|
460
|
+
*/
|
|
461
|
+
|
|
462
|
+
}, {
|
|
463
|
+
key: "hideHTMLTags",
|
|
464
|
+
value: function hideHTMLTags(context) {
|
|
465
|
+
if (context.isHTML) {
|
|
466
|
+
var pasteLabel = this._pasteLabel.bind(this, context, 'html');
|
|
467
|
+
|
|
468
|
+
context.text = context.text.replace(/<\/?[a-z][^]*?>/gi, pasteLabel) // Tags
|
|
469
|
+
.replace(/<\/?[a-z][^]*?>/gi, pasteLabel) // Escaping tags
|
|
470
|
+
.replace(/&[gl]t;/gi, pasteLabel);
|
|
471
|
+
}
|
|
472
|
+
}
|
|
473
|
+
/**
|
|
474
|
+
* Get previous label.
|
|
475
|
+
*
|
|
476
|
+
* @param {string} text
|
|
477
|
+
* @param {number} position
|
|
478
|
+
*
|
|
479
|
+
* @returns {string|false}
|
|
480
|
+
*/
|
|
481
|
+
|
|
482
|
+
}, {
|
|
483
|
+
key: "getPrevLabel",
|
|
484
|
+
value: function getPrevLabel(text, position) {
|
|
485
|
+
for (var i = position - 1; i >= 0; i--) {
|
|
486
|
+
if (text[i] === privateLabel) {
|
|
487
|
+
return text.slice(i, position + 1);
|
|
488
|
+
}
|
|
489
|
+
}
|
|
490
|
+
|
|
491
|
+
return false;
|
|
492
|
+
}
|
|
493
|
+
/**
|
|
494
|
+
* Get next label.
|
|
495
|
+
*
|
|
496
|
+
* @param {string} text
|
|
497
|
+
* @param {number} position
|
|
498
|
+
*
|
|
499
|
+
* @returns {string|false}
|
|
500
|
+
*/
|
|
501
|
+
|
|
502
|
+
}, {
|
|
503
|
+
key: "getNextLabel",
|
|
504
|
+
value: function getNextLabel(text, position) {
|
|
505
|
+
for (var i = position + 1; i < text.length; i++) {
|
|
506
|
+
if (text[i] === privateLabel) {
|
|
507
|
+
return text.slice(position, i + 1);
|
|
508
|
+
}
|
|
509
|
+
}
|
|
510
|
+
|
|
511
|
+
return false;
|
|
512
|
+
}
|
|
513
|
+
/**
|
|
514
|
+
* Get a tag by a label.
|
|
515
|
+
*
|
|
516
|
+
* @param {Object} context
|
|
517
|
+
* @param {string} label
|
|
518
|
+
*
|
|
519
|
+
* @returns {Object|boolean}
|
|
520
|
+
*/
|
|
521
|
+
|
|
522
|
+
}, {
|
|
523
|
+
key: "getTagByLabel",
|
|
524
|
+
value: function getTagByLabel(context, label) {
|
|
525
|
+
var result = false;
|
|
526
|
+
|
|
527
|
+
this._groups.some(function (group) {
|
|
528
|
+
var value = context.safeTags.hidden[group][label];
|
|
529
|
+
|
|
530
|
+
if (typeof value !== 'undefined') {
|
|
531
|
+
result = {
|
|
532
|
+
group: group,
|
|
533
|
+
value: value
|
|
534
|
+
};
|
|
535
|
+
}
|
|
536
|
+
|
|
537
|
+
return result;
|
|
538
|
+
});
|
|
539
|
+
|
|
540
|
+
return result;
|
|
541
|
+
}
|
|
542
|
+
/**
|
|
543
|
+
* Get info about a tag.
|
|
544
|
+
*
|
|
545
|
+
* @param {Object|undefined} tag
|
|
546
|
+
*
|
|
547
|
+
* @returns {Object|undefined}
|
|
548
|
+
*/
|
|
549
|
+
|
|
550
|
+
}, {
|
|
551
|
+
key: "getTagInfo",
|
|
552
|
+
value: function getTagInfo(tag) {
|
|
553
|
+
if (!tag) {
|
|
554
|
+
return;
|
|
555
|
+
}
|
|
556
|
+
|
|
557
|
+
var result = {
|
|
558
|
+
group: tag.group
|
|
559
|
+
};
|
|
560
|
+
|
|
561
|
+
switch (tag.group) {
|
|
562
|
+
case 'html':
|
|
563
|
+
result.name = tag.value.split(/[<\s>]/)[1];
|
|
564
|
+
result.isInline = inlineElements.indexOf(result.name) > -1;
|
|
565
|
+
result.isClosing = tag.value.search(/^<\//) > -1;
|
|
566
|
+
break;
|
|
567
|
+
|
|
568
|
+
case 'url':
|
|
569
|
+
result.isInline = true;
|
|
570
|
+
break;
|
|
571
|
+
|
|
572
|
+
case 'own':
|
|
573
|
+
result.isInline = false;
|
|
574
|
+
break;
|
|
575
|
+
}
|
|
576
|
+
|
|
577
|
+
return result;
|
|
578
|
+
}
|
|
579
|
+
}, {
|
|
580
|
+
key: "_pasteLabel",
|
|
581
|
+
value: function _pasteLabel(context, group, match) {
|
|
582
|
+
var safeTags = context.safeTags;
|
|
583
|
+
var key = privateLabel + 'tf' + safeTags.i + privateLabel;
|
|
584
|
+
safeTags.hidden[group][key] = match;
|
|
585
|
+
safeTags.i++;
|
|
586
|
+
return key;
|
|
587
|
+
}
|
|
588
|
+
}, {
|
|
589
|
+
key: "_prepareRegExp",
|
|
590
|
+
value: function _prepareRegExp(tag) {
|
|
591
|
+
var re;
|
|
592
|
+
|
|
593
|
+
if (tag instanceof RegExp) {
|
|
594
|
+
re = tag;
|
|
595
|
+
} else {
|
|
596
|
+
var _tag = _slicedToArray(tag, 3),
|
|
597
|
+
startTag = _tag[0],
|
|
598
|
+
endTag = _tag[1],
|
|
599
|
+
middle = _tag[2];
|
|
600
|
+
|
|
601
|
+
if (typeof middle === 'undefined') {
|
|
602
|
+
middle = '[^]*?';
|
|
603
|
+
}
|
|
604
|
+
|
|
605
|
+
re = new RegExp(startTag + middle + endTag, 'gi');
|
|
606
|
+
}
|
|
607
|
+
|
|
608
|
+
return re;
|
|
609
|
+
}
|
|
610
|
+
}]);
|
|
611
|
+
|
|
612
|
+
return SafeTags;
|
|
613
|
+
}();
|
|
614
|
+
|
|
615
|
+
function repeat(symbol, count) {
|
|
616
|
+
var result = '';
|
|
617
|
+
|
|
618
|
+
for (;;) {
|
|
619
|
+
if ((count & 1) === 1) {
|
|
620
|
+
result += symbol;
|
|
621
|
+
}
|
|
622
|
+
|
|
623
|
+
count >>>= 1;
|
|
624
|
+
|
|
625
|
+
if (count === 0) {
|
|
626
|
+
break;
|
|
627
|
+
}
|
|
628
|
+
|
|
629
|
+
symbol += symbol;
|
|
630
|
+
}
|
|
631
|
+
|
|
632
|
+
return result;
|
|
633
|
+
}
|
|
634
|
+
function replaceNbsp(text) {
|
|
635
|
+
return text.replace(/\u00A0/g, ' ');
|
|
636
|
+
}
|
|
637
|
+
function replace(text, re) {
|
|
638
|
+
for (var i = 0; i < re.length; i++) {
|
|
639
|
+
text = text.replace(re[i][0], re[i][1]);
|
|
640
|
+
}
|
|
641
|
+
|
|
642
|
+
return text;
|
|
643
|
+
}
|
|
644
|
+
function isHTML(text) {
|
|
645
|
+
return text.search(/(<\/?[a-z]|<!|&[lg]t;)/i) !== -1;
|
|
646
|
+
}
|
|
647
|
+
function removeCR(text) {
|
|
648
|
+
return text.replace(/\r\n?/g, '\n');
|
|
649
|
+
}
|
|
650
|
+
function fixLineEnding(text, type) {
|
|
651
|
+
if (type === 'CRLF') {
|
|
652
|
+
// Windows
|
|
653
|
+
return text.replace(/\n/g, '\r\n');
|
|
654
|
+
} else if (type === 'CR') {
|
|
655
|
+
// Mac
|
|
656
|
+
return text.replace(/\n/g, '\r');
|
|
657
|
+
}
|
|
658
|
+
|
|
659
|
+
return text;
|
|
660
|
+
}
|
|
661
|
+
|
|
662
|
+
/**
|
|
663
|
+
* Get a deep copy of a object.
|
|
664
|
+
*
|
|
665
|
+
* @param {*} obj
|
|
666
|
+
*
|
|
667
|
+
* @returns {*}
|
|
668
|
+
*/
|
|
669
|
+
function deepCopy(obj) {
|
|
670
|
+
return _typeof(obj) === 'object' ? JSON.parse(JSON.stringify(obj)) : obj;
|
|
671
|
+
}
|
|
672
|
+
|
|
673
|
+
/**
|
|
674
|
+
* @constructor
|
|
675
|
+
* @param {Object} [prefs]
|
|
676
|
+
* @param {string} [prefs.locale] Locale
|
|
677
|
+
* @param {string} [prefs.lineEnding] Line ending. 'LF' (Unix), 'CR' (Mac) or 'CRLF' (Windows). Default: 'LF'.
|
|
678
|
+
* @param {HtmlEntity} [prefs.htmlEntity]
|
|
679
|
+
* @param {boolean} [prefs.live] Live mode
|
|
680
|
+
* @param {string|string[]} [prefs.enableRule] Enable a rule
|
|
681
|
+
* @param {string|string[]} [prefs.disableRule] Disable a rule
|
|
682
|
+
*/
|
|
683
|
+
|
|
684
|
+
var Typograf = /*#__PURE__*/function () {
|
|
685
|
+
function Typograf(prefs) {
|
|
686
|
+
_classCallCheck(this, Typograf);
|
|
687
|
+
|
|
688
|
+
this._prefs = _typeof(prefs) === 'object' ? prefs : {};
|
|
689
|
+
this._prefs.locale = prepareLocale(this._prefs.locale);
|
|
690
|
+
this._prefs.live = this._prefs.live || false;
|
|
691
|
+
this._safeTags = new SafeTags();
|
|
692
|
+
this._settings = {};
|
|
693
|
+
this._enabledRules = {};
|
|
694
|
+
this._innerRulesByQueues = {};
|
|
695
|
+
this._innerRules = [].concat(this._innerRules);
|
|
696
|
+
|
|
697
|
+
this._innerRules.forEach(function (rule) {
|
|
698
|
+
var q = rule.queue || 'default';
|
|
699
|
+
this._innerRulesByQueues[q] = this._innerRulesByQueues[q] || [];
|
|
700
|
+
|
|
701
|
+
this._innerRulesByQueues[q].push(rule);
|
|
702
|
+
}, this);
|
|
703
|
+
|
|
704
|
+
this._rulesByQueues = {};
|
|
705
|
+
this._rules = [].concat(this._rules);
|
|
706
|
+
|
|
707
|
+
this._rules.forEach(function (rule) {
|
|
708
|
+
var q = rule.queue || 'default';
|
|
709
|
+
|
|
710
|
+
this._prepareRule(rule);
|
|
711
|
+
|
|
712
|
+
this._rulesByQueues[q] = this._rulesByQueues[q] || [];
|
|
713
|
+
|
|
714
|
+
this._rulesByQueues[q].push(rule);
|
|
715
|
+
}, this);
|
|
716
|
+
|
|
717
|
+
this._prefs.disableRule && this.disableRule(this._prefs.disableRule);
|
|
718
|
+
this._prefs.enableRule && this.enableRule(this._prefs.enableRule);
|
|
719
|
+
this._separatePartsTags = ['title', 'p', 'h[1-6]', 'select', 'legend'];
|
|
720
|
+
}
|
|
721
|
+
/**
|
|
722
|
+
* Add a rule.
|
|
723
|
+
*
|
|
724
|
+
* @static
|
|
725
|
+
* @param {TypografRule} rule
|
|
726
|
+
*
|
|
727
|
+
* @returns {Typograf} this
|
|
728
|
+
*/
|
|
729
|
+
|
|
730
|
+
|
|
731
|
+
_createClass(Typograf, [{
|
|
732
|
+
key: "execute",
|
|
733
|
+
value:
|
|
734
|
+
/**
|
|
735
|
+
* Execute typographical rules for text.
|
|
736
|
+
*
|
|
737
|
+
* @param {string} text
|
|
738
|
+
* @param {Object} [prefs]
|
|
739
|
+
* @param {string} [prefs.locale] Locale
|
|
740
|
+
* @param {HtmlEntity} [prefs.htmlEntity] Type of HTML entities
|
|
741
|
+
* @param {string} [prefs.lineEnding] Line ending. 'LF' (Unix), 'CR' (Mac) or 'CRLF' (Windows). Default: 'LF'.
|
|
742
|
+
*
|
|
743
|
+
* @returns {string}
|
|
744
|
+
*/
|
|
745
|
+
function execute(text, prefs) {
|
|
746
|
+
text = '' + text;
|
|
747
|
+
|
|
748
|
+
if (!text) {
|
|
749
|
+
return '';
|
|
750
|
+
}
|
|
751
|
+
|
|
752
|
+
var context = this._prepareContext(text);
|
|
753
|
+
|
|
754
|
+
this._preparePrefs(context, prefs);
|
|
755
|
+
|
|
756
|
+
return this._process(context);
|
|
757
|
+
}
|
|
758
|
+
}, {
|
|
759
|
+
key: "_prepareContext",
|
|
760
|
+
value: function _prepareContext(text) {
|
|
761
|
+
return {
|
|
762
|
+
text: text,
|
|
763
|
+
isHTML: isHTML(text),
|
|
764
|
+
prefs: deepCopy(this._prefs),
|
|
765
|
+
getData: function getData$$1(key) {
|
|
766
|
+
if (key === 'char') {
|
|
767
|
+
return this.prefs.locale.map(function (item) {
|
|
768
|
+
return getData(item + '/' + key);
|
|
769
|
+
}).join('');
|
|
770
|
+
} else {
|
|
771
|
+
return getData(this.prefs.locale[0] + '/' + key);
|
|
772
|
+
}
|
|
773
|
+
}
|
|
774
|
+
};
|
|
775
|
+
}
|
|
776
|
+
}, {
|
|
777
|
+
key: "_preparePrefs",
|
|
778
|
+
value: function _preparePrefs(context, prefs) {
|
|
779
|
+
prefs = prefs || {};
|
|
780
|
+
var contextPrefs = context.prefs;
|
|
781
|
+
|
|
782
|
+
for (var _i = 0, _arr = ['htmlEntity', 'lineEnding', 'processingSeparateParts', 'ruleFilter']; _i < _arr.length; _i++) {
|
|
783
|
+
var name = _arr[_i];
|
|
784
|
+
|
|
785
|
+
if (name in prefs) {
|
|
786
|
+
contextPrefs[name] = prefs[name];
|
|
787
|
+
} else if (name in this._prefs) {
|
|
788
|
+
contextPrefs[name] = this._prefs[name];
|
|
789
|
+
}
|
|
790
|
+
}
|
|
791
|
+
|
|
792
|
+
contextPrefs.htmlEntity = contextPrefs.htmlEntity || {};
|
|
793
|
+
contextPrefs.locale = prepareLocale(prefs.locale, this._prefs.locale);
|
|
794
|
+
var locale = contextPrefs.locale;
|
|
795
|
+
var locale0 = locale[0];
|
|
796
|
+
|
|
797
|
+
if (!locale.length || !locale0) {
|
|
798
|
+
throw Error('Not defined the property "locale".');
|
|
799
|
+
}
|
|
800
|
+
|
|
801
|
+
if (!hasLocale(locale0)) {
|
|
802
|
+
throw Error('"' + locale0 + '" is not supported locale.');
|
|
803
|
+
}
|
|
804
|
+
}
|
|
805
|
+
}, {
|
|
806
|
+
key: "_splitBySeparateParts",
|
|
807
|
+
value: function _splitBySeparateParts(context) {
|
|
808
|
+
if (!context.isHTML || context.prefs.processingSeparateParts === false) {
|
|
809
|
+
return [context.text];
|
|
810
|
+
}
|
|
811
|
+
|
|
812
|
+
var text = [],
|
|
813
|
+
reTags = new RegExp('<(' + this._separatePartsTags.join('|') + ')(\\s[^>]*?)?>[^]*?</\\1>', 'gi');
|
|
814
|
+
var position = 0;
|
|
815
|
+
context.text.replace(reTags, function ($0, $1, $2, itemPosition) {
|
|
816
|
+
if (position !== itemPosition) {
|
|
817
|
+
text.push((position ? privateSeparateLabel : '') + context.text.slice(position, itemPosition) + privateSeparateLabel);
|
|
818
|
+
}
|
|
819
|
+
|
|
820
|
+
text.push($0);
|
|
821
|
+
position = itemPosition + $0.length;
|
|
822
|
+
return $0;
|
|
823
|
+
});
|
|
824
|
+
text.push(position ? privateSeparateLabel + context.text.slice(position, context.text.length) : context.text);
|
|
825
|
+
return text;
|
|
826
|
+
}
|
|
827
|
+
}, {
|
|
828
|
+
key: "_process",
|
|
829
|
+
value: function _process(context) {
|
|
830
|
+
var _this = this;
|
|
831
|
+
|
|
832
|
+
context.text = removeCR(context.text);
|
|
833
|
+
|
|
834
|
+
this._executeRules(context, 'start');
|
|
835
|
+
|
|
836
|
+
this._safeTags.hide(context, 'own');
|
|
837
|
+
|
|
838
|
+
this._executeRules(context, 'hide-safe-tags-own');
|
|
839
|
+
|
|
840
|
+
this._safeTags.hide(context, 'html');
|
|
841
|
+
|
|
842
|
+
this._executeRules(context, 'hide-safe-tags-html');
|
|
843
|
+
|
|
844
|
+
var isRootHTML = context.isHTML,
|
|
845
|
+
re = new RegExp(privateSeparateLabel, 'g');
|
|
846
|
+
context.text = this._splitBySeparateParts(context).map(function (item) {
|
|
847
|
+
context.text = item;
|
|
848
|
+
context.isHTML = isHTML(item);
|
|
849
|
+
|
|
850
|
+
_this._safeTags.hideHTMLTags(context);
|
|
851
|
+
|
|
852
|
+
_this._safeTags.hide(context, 'url');
|
|
853
|
+
|
|
854
|
+
_this._executeRules(context, 'hide-safe-tags-url');
|
|
855
|
+
|
|
856
|
+
_this._executeRules(context, 'hide-safe-tags');
|
|
857
|
+
|
|
858
|
+
HtmlEntities$1.toUtf(context);
|
|
859
|
+
|
|
860
|
+
if (_this._prefs.live) {
|
|
861
|
+
context.text = replaceNbsp(context.text);
|
|
862
|
+
}
|
|
863
|
+
|
|
864
|
+
_this._executeRules(context, 'utf');
|
|
865
|
+
|
|
866
|
+
_this._executeRules(context);
|
|
867
|
+
|
|
868
|
+
HtmlEntities$1.restore(context);
|
|
869
|
+
|
|
870
|
+
_this._executeRules(context, 'html-entities');
|
|
871
|
+
|
|
872
|
+
_this._safeTags.show(context, 'url');
|
|
873
|
+
|
|
874
|
+
_this._executeRules(context, 'show-safe-tags-url');
|
|
875
|
+
|
|
876
|
+
return context.text.replace(re, '');
|
|
877
|
+
}).join('');
|
|
878
|
+
context.isHTML = isRootHTML;
|
|
879
|
+
|
|
880
|
+
this._safeTags.show(context, 'html');
|
|
881
|
+
|
|
882
|
+
this._executeRules(context, 'show-safe-tags-html');
|
|
883
|
+
|
|
884
|
+
this._safeTags.show(context, 'own');
|
|
885
|
+
|
|
886
|
+
this._executeRules(context, 'show-safe-tags-own');
|
|
887
|
+
|
|
888
|
+
this._executeRules(context, 'end');
|
|
889
|
+
|
|
890
|
+
return fixLineEnding(context.text, context.prefs.lineEnding);
|
|
891
|
+
}
|
|
892
|
+
/**
|
|
893
|
+
* Get a setting.
|
|
894
|
+
*
|
|
895
|
+
* @param {string} ruleName
|
|
896
|
+
* @param {string} setting
|
|
897
|
+
*
|
|
898
|
+
* @returns {*}
|
|
899
|
+
*/
|
|
900
|
+
|
|
901
|
+
}, {
|
|
902
|
+
key: "getSetting",
|
|
903
|
+
value: function getSetting(ruleName, setting) {
|
|
904
|
+
return this._settings[ruleName] && this._settings[ruleName][setting];
|
|
905
|
+
}
|
|
906
|
+
/**
|
|
907
|
+
* Set a setting.
|
|
908
|
+
*
|
|
909
|
+
* @param {string} ruleName
|
|
910
|
+
* @param {string} setting
|
|
911
|
+
* @param {*} [value]
|
|
912
|
+
*
|
|
913
|
+
* @returns {Typograf}
|
|
914
|
+
*/
|
|
915
|
+
|
|
916
|
+
}, {
|
|
917
|
+
key: "setSetting",
|
|
918
|
+
value: function setSetting(ruleName, setting, value) {
|
|
919
|
+
this._settings[ruleName] = this._settings[ruleName] || {};
|
|
920
|
+
this._settings[ruleName][setting] = value;
|
|
921
|
+
return this;
|
|
922
|
+
}
|
|
923
|
+
/**
|
|
924
|
+
* Is enabled a rule.
|
|
925
|
+
*
|
|
926
|
+
* @param {string} ruleName
|
|
927
|
+
*
|
|
928
|
+
* @returns {boolean}
|
|
929
|
+
*/
|
|
930
|
+
|
|
931
|
+
}, {
|
|
932
|
+
key: "isEnabledRule",
|
|
933
|
+
value: function isEnabledRule(ruleName) {
|
|
934
|
+
return this._enabledRules[ruleName];
|
|
935
|
+
}
|
|
936
|
+
/**
|
|
937
|
+
* Is disabled a rule.
|
|
938
|
+
*
|
|
939
|
+
* @param {string} ruleName
|
|
940
|
+
*
|
|
941
|
+
* @returns {boolean}
|
|
942
|
+
*/
|
|
943
|
+
|
|
944
|
+
}, {
|
|
945
|
+
key: "isDisabledRule",
|
|
946
|
+
value: function isDisabledRule(ruleName) {
|
|
947
|
+
return !this._enabledRules[ruleName];
|
|
948
|
+
}
|
|
949
|
+
/**
|
|
950
|
+
* Enable a rule.
|
|
951
|
+
*
|
|
952
|
+
* @param {string|string[]} ruleName
|
|
953
|
+
*
|
|
954
|
+
* @returns {Typograf} this
|
|
955
|
+
*/
|
|
956
|
+
|
|
957
|
+
}, {
|
|
958
|
+
key: "enableRule",
|
|
959
|
+
value: function enableRule(ruleName) {
|
|
960
|
+
return this._enable(ruleName, true);
|
|
961
|
+
}
|
|
962
|
+
/**
|
|
963
|
+
* Disable a rule.
|
|
964
|
+
*
|
|
965
|
+
* @param {string|string[]} ruleName
|
|
966
|
+
*
|
|
967
|
+
* @returns {Typograf} this
|
|
968
|
+
*/
|
|
969
|
+
|
|
970
|
+
}, {
|
|
971
|
+
key: "disableRule",
|
|
972
|
+
value: function disableRule(ruleName) {
|
|
973
|
+
return this._enable(ruleName, false);
|
|
974
|
+
}
|
|
975
|
+
/**
|
|
976
|
+
* Add safe tag.
|
|
977
|
+
*
|
|
978
|
+
* @example
|
|
979
|
+
* // var t = new Typograf({locale: 'ru'});
|
|
980
|
+
* // t.addSafeTag('<mytag>', '</mytag>');
|
|
981
|
+
* // t.addSafeTag('<mytag>', '</mytag>', '.*?');
|
|
982
|
+
* // t.addSafeTag(/<mytag>.*?</mytag>/gi);
|
|
983
|
+
*
|
|
984
|
+
* @param {string|RegExp} startTag
|
|
985
|
+
* @param {string} [endTag]
|
|
986
|
+
* @param {string} [middle]
|
|
987
|
+
*
|
|
988
|
+
* @returns {Typograf} this
|
|
989
|
+
*/
|
|
990
|
+
|
|
991
|
+
}, {
|
|
992
|
+
key: "addSafeTag",
|
|
993
|
+
value: function addSafeTag(startTag, endTag, middle) {
|
|
994
|
+
var tag = startTag instanceof RegExp ? startTag : [startTag, endTag, middle];
|
|
995
|
+
|
|
996
|
+
this._safeTags.add(tag);
|
|
997
|
+
|
|
998
|
+
return this;
|
|
999
|
+
}
|
|
1000
|
+
}, {
|
|
1001
|
+
key: "_executeRules",
|
|
1002
|
+
value: function _executeRules(context, queue) {
|
|
1003
|
+
queue = queue || 'default';
|
|
1004
|
+
var rules = this._rulesByQueues[queue];
|
|
1005
|
+
var innerRules = this._innerRulesByQueues[queue];
|
|
1006
|
+
innerRules && innerRules.forEach(function (rule) {
|
|
1007
|
+
this._ruleIterator(context, rule);
|
|
1008
|
+
}, this);
|
|
1009
|
+
rules && rules.forEach(function (rule) {
|
|
1010
|
+
this._ruleIterator(context, rule);
|
|
1011
|
+
}, this);
|
|
1012
|
+
}
|
|
1013
|
+
}, {
|
|
1014
|
+
key: "_ruleIterator",
|
|
1015
|
+
value: function _ruleIterator(context, rule) {
|
|
1016
|
+
var rlocale = rule._locale;
|
|
1017
|
+
var live = this._prefs.live;
|
|
1018
|
+
|
|
1019
|
+
if (live === true && rule.live === false || live === false && rule.live === true) {
|
|
1020
|
+
return;
|
|
1021
|
+
}
|
|
1022
|
+
|
|
1023
|
+
if ((rlocale === 'common' || rlocale === context.prefs.locale[0]) && this.isEnabledRule(rule.name)) {
|
|
1024
|
+
if (context.prefs.ruleFilter && !context.prefs.ruleFilter(rule)) {
|
|
1025
|
+
return;
|
|
1026
|
+
}
|
|
1027
|
+
|
|
1028
|
+
this._onBeforeRule && this._onBeforeRule(rule.name, context.text, context);
|
|
1029
|
+
context.text = rule.handler.call(this, context.text, this._settings[rule.name], context);
|
|
1030
|
+
this._onAfterRule && this._onAfterRule(rule.name, context.text, context);
|
|
1031
|
+
}
|
|
1032
|
+
}
|
|
1033
|
+
}, {
|
|
1034
|
+
key: "_prepareRule",
|
|
1035
|
+
value: function _prepareRule(rule) {
|
|
1036
|
+
var name = rule.name;
|
|
1037
|
+
|
|
1038
|
+
var t = _typeof(rule.settings);
|
|
1039
|
+
|
|
1040
|
+
var settings = {};
|
|
1041
|
+
|
|
1042
|
+
if (t === 'object') {
|
|
1043
|
+
settings = deepCopy(rule.settings);
|
|
1044
|
+
} else if (t === 'function') {
|
|
1045
|
+
settings = rule.settings(rule);
|
|
1046
|
+
}
|
|
1047
|
+
|
|
1048
|
+
this._settings[name] = settings;
|
|
1049
|
+
this._enabledRules[name] = rule._enabled;
|
|
1050
|
+
}
|
|
1051
|
+
}, {
|
|
1052
|
+
key: "_enable",
|
|
1053
|
+
value: function _enable(rule, enabled) {
|
|
1054
|
+
if (Array.isArray(rule)) {
|
|
1055
|
+
rule.forEach(function (el) {
|
|
1056
|
+
this._enableByMask(el, enabled);
|
|
1057
|
+
}, this);
|
|
1058
|
+
} else {
|
|
1059
|
+
this._enableByMask(rule, enabled);
|
|
1060
|
+
}
|
|
1061
|
+
|
|
1062
|
+
return this;
|
|
1063
|
+
}
|
|
1064
|
+
}, {
|
|
1065
|
+
key: "_enableByMask",
|
|
1066
|
+
value: function _enableByMask(rule, enabled) {
|
|
1067
|
+
if (!rule) {
|
|
1068
|
+
return;
|
|
1069
|
+
}
|
|
1070
|
+
|
|
1071
|
+
if (rule.search(/\*/) !== -1) {
|
|
1072
|
+
var re = new RegExp(rule.replace(/\//g, '\\/').replace(/\*/g, '.*'));
|
|
1073
|
+
|
|
1074
|
+
this._rules.forEach(function (el) {
|
|
1075
|
+
var name = el.name;
|
|
1076
|
+
|
|
1077
|
+
if (re.test(name)) {
|
|
1078
|
+
this._enabledRules[name] = enabled;
|
|
1079
|
+
}
|
|
1080
|
+
}, this);
|
|
1081
|
+
} else {
|
|
1082
|
+
this._enabledRules[rule] = enabled;
|
|
1083
|
+
}
|
|
1084
|
+
}
|
|
1085
|
+
}, {
|
|
1086
|
+
key: "_getRule",
|
|
1087
|
+
value: function _getRule(name) {
|
|
1088
|
+
var rule = null;
|
|
1089
|
+
|
|
1090
|
+
this._rules.some(function (item) {
|
|
1091
|
+
if (item.name === name) {
|
|
1092
|
+
rule = item;
|
|
1093
|
+
return true;
|
|
1094
|
+
}
|
|
1095
|
+
|
|
1096
|
+
return false;
|
|
1097
|
+
});
|
|
1098
|
+
|
|
1099
|
+
return rule;
|
|
1100
|
+
}
|
|
1101
|
+
}], [{
|
|
1102
|
+
key: "addRule",
|
|
1103
|
+
value: function addRule(rule) {
|
|
1104
|
+
var _rule$name$split = rule.name.split('/'),
|
|
1105
|
+
_rule$name$split2 = _slicedToArray(_rule$name$split, 3),
|
|
1106
|
+
locale = _rule$name$split2[0],
|
|
1107
|
+
group = _rule$name$split2[1],
|
|
1108
|
+
name = _rule$name$split2[2];
|
|
1109
|
+
|
|
1110
|
+
rule._enabled = rule.disabled === true ? false : true;
|
|
1111
|
+
rule._locale = locale;
|
|
1112
|
+
rule._group = group;
|
|
1113
|
+
rule._name = name;
|
|
1114
|
+
this.addLocale(rule._locale);
|
|
1115
|
+
|
|
1116
|
+
this._setIndex(rule);
|
|
1117
|
+
|
|
1118
|
+
this.prototype._rules.push(rule);
|
|
1119
|
+
|
|
1120
|
+
this._sortRules(this.prototype._rules);
|
|
1121
|
+
|
|
1122
|
+
return this;
|
|
1123
|
+
}
|
|
1124
|
+
/**
|
|
1125
|
+
* Add rules.
|
|
1126
|
+
*
|
|
1127
|
+
* @static
|
|
1128
|
+
* @param {TypografRule[]} rules
|
|
1129
|
+
*
|
|
1130
|
+
* @returns {Typograf} this
|
|
1131
|
+
*/
|
|
1132
|
+
|
|
1133
|
+
}, {
|
|
1134
|
+
key: "addRules",
|
|
1135
|
+
value: function addRules(rules) {
|
|
1136
|
+
var _this2 = this;
|
|
1137
|
+
|
|
1138
|
+
rules.forEach(function (item) {
|
|
1139
|
+
_this2.addRule(item);
|
|
1140
|
+
});
|
|
1141
|
+
return this;
|
|
1142
|
+
}
|
|
1143
|
+
/**
|
|
1144
|
+
* Add internal rule.
|
|
1145
|
+
* Internal rules are executed before main.
|
|
1146
|
+
*
|
|
1147
|
+
* @static
|
|
1148
|
+
* @param {TypografRule} rule
|
|
1149
|
+
*
|
|
1150
|
+
* @returns {Typograf} this
|
|
1151
|
+
*/
|
|
1152
|
+
|
|
1153
|
+
}, {
|
|
1154
|
+
key: "addInnerRule",
|
|
1155
|
+
value: function addInnerRule(rule) {
|
|
1156
|
+
this.prototype._innerRules.push(rule);
|
|
1157
|
+
|
|
1158
|
+
rule._locale = rule.name.split('/')[0];
|
|
1159
|
+
return this;
|
|
1160
|
+
}
|
|
1161
|
+
/**
|
|
1162
|
+
* Add internal rules.
|
|
1163
|
+
* Internal rules are executed before main.
|
|
1164
|
+
*
|
|
1165
|
+
* @static
|
|
1166
|
+
* @param {TypografRule[]} rules
|
|
1167
|
+
*
|
|
1168
|
+
* @returns {Typograf} this
|
|
1169
|
+
*/
|
|
1170
|
+
|
|
1171
|
+
}, {
|
|
1172
|
+
key: "addInnerRules",
|
|
1173
|
+
value: function addInnerRules(rules) {
|
|
1174
|
+
var _this3 = this;
|
|
1175
|
+
|
|
1176
|
+
rules.forEach(function (item) {
|
|
1177
|
+
_this3.addInnerRule(item);
|
|
1178
|
+
});
|
|
1179
|
+
return this;
|
|
1180
|
+
}
|
|
1181
|
+
}, {
|
|
1182
|
+
key: "_setIndex",
|
|
1183
|
+
value: function _setIndex(rule) {
|
|
1184
|
+
var index = rule.index;
|
|
1185
|
+
|
|
1186
|
+
var t = _typeof(index);
|
|
1187
|
+
|
|
1188
|
+
var groupIndex = groupIndexes[rule._group];
|
|
1189
|
+
|
|
1190
|
+
if (t === 'undefined') {
|
|
1191
|
+
index = groupIndex;
|
|
1192
|
+
} else if (t === 'string') {
|
|
1193
|
+
index = (groupIndex || 0) + parseInt(rule.index, 10);
|
|
1194
|
+
}
|
|
1195
|
+
|
|
1196
|
+
rule._index = index;
|
|
1197
|
+
}
|
|
1198
|
+
}, {
|
|
1199
|
+
key: "_sortRules",
|
|
1200
|
+
value: function _sortRules(rules) {
|
|
1201
|
+
rules.sort(function (a, b) {
|
|
1202
|
+
return a._index > b._index ? 1 : -1;
|
|
1203
|
+
});
|
|
1204
|
+
}
|
|
1205
|
+
}]);
|
|
1206
|
+
|
|
1207
|
+
return Typograf;
|
|
1208
|
+
}();
|
|
1209
|
+
Typograf.version = '6.15.0';
|
|
1210
|
+
Typograf.addLocale = addLocale;
|
|
1211
|
+
Typograf.getLocales = getLocales;
|
|
1212
|
+
Typograf.hasLocale = hasLocale;
|
|
1213
|
+
Typograf.setData = setData;
|
|
1214
|
+
Typograf.getData = getData; // @deprecated
|
|
1215
|
+
|
|
1216
|
+
Typograf.deepCopy = deepCopy;
|
|
1217
|
+
Typograf.prototype._rules = [];
|
|
1218
|
+
Typograf.prototype._innerRules = [];
|
|
1219
|
+
/**
|
|
1220
|
+
* @typedef TypografRule
|
|
1221
|
+
* @type {object}
|
|
1222
|
+
*
|
|
1223
|
+
* @property {string} name Name of rule
|
|
1224
|
+
* @property {Function} handler Processing function
|
|
1225
|
+
* @property {number} [index] Sorting index for rule
|
|
1226
|
+
* @property {boolean} [disabled] Rule is disabled by default
|
|
1227
|
+
* @property {boolean} [live] Live mode
|
|
1228
|
+
* @property {Object} [settings] Settings for rule
|
|
1229
|
+
*/
|
|
1230
|
+
|
|
1231
|
+
var common = {
|
|
1232
|
+
'common/char': 'a-z',
|
|
1233
|
+
'common/dash': '--?|‒|–|—',
|
|
1234
|
+
// --, ‒, &ndash, &mdash
|
|
1235
|
+
'common/quote': '«‹»›„“‟”"'
|
|
1236
|
+
};
|
|
1237
|
+
|
|
1238
|
+
var be = {
|
|
1239
|
+
'be/char': 'абвгдежзйклмнопрстуфхцчшыьэюяёіўґ',
|
|
1240
|
+
'be/quote': {
|
|
1241
|
+
left: '«“',
|
|
1242
|
+
right: '»”'
|
|
1243
|
+
}
|
|
1244
|
+
};
|
|
1245
|
+
|
|
1246
|
+
var bg = {
|
|
1247
|
+
'bg/char': 'абвгдежзийклмнопрстуфхцчшщъьюя',
|
|
1248
|
+
'bg/quote': {
|
|
1249
|
+
left: '„’',
|
|
1250
|
+
right: '“’'
|
|
1251
|
+
}
|
|
1252
|
+
};
|
|
1253
|
+
|
|
1254
|
+
var ca = {
|
|
1255
|
+
'ca/char': 'abcdefghijlmnopqrstuvxyzàçèéíïòóúü',
|
|
1256
|
+
'ca/quote': {
|
|
1257
|
+
left: '«“',
|
|
1258
|
+
right: '»”'
|
|
1259
|
+
}
|
|
1260
|
+
};
|
|
1261
|
+
|
|
1262
|
+
var da = {
|
|
1263
|
+
'da/char': 'a-zåæø',
|
|
1264
|
+
'da/quote': {
|
|
1265
|
+
left: '»›',
|
|
1266
|
+
right: '«‹'
|
|
1267
|
+
}
|
|
1268
|
+
};
|
|
1269
|
+
|
|
1270
|
+
var de = {
|
|
1271
|
+
'de/char': 'a-zßäöü',
|
|
1272
|
+
'de/quote': {
|
|
1273
|
+
left: '„‚',
|
|
1274
|
+
right: '“‘'
|
|
1275
|
+
}
|
|
1276
|
+
};
|
|
1277
|
+
|
|
1278
|
+
var el = {
|
|
1279
|
+
'el/char': 'ΐάέήίΰαβγδεζηθικλμνξοπρςστυφχψωϊϋόύώϲάέήίόύώ',
|
|
1280
|
+
'el/quote': {
|
|
1281
|
+
left: '«“',
|
|
1282
|
+
right: '»”'
|
|
1283
|
+
}
|
|
1284
|
+
};
|
|
1285
|
+
|
|
1286
|
+
var enGB = {
|
|
1287
|
+
'en-GB/char': 'a-z',
|
|
1288
|
+
'en-GB/quote': {
|
|
1289
|
+
left: '‘“',
|
|
1290
|
+
right: '’”'
|
|
1291
|
+
}
|
|
1292
|
+
};
|
|
1293
|
+
|
|
1294
|
+
var enUS = {
|
|
1295
|
+
'en-US/char': 'a-z',
|
|
1296
|
+
'en-US/quote': {
|
|
1297
|
+
left: '“‘',
|
|
1298
|
+
right: '”’'
|
|
1299
|
+
}
|
|
1300
|
+
};
|
|
1301
|
+
|
|
1302
|
+
var eo = {
|
|
1303
|
+
'eo/char': 'abcdefghijklmnoprstuvzĉĝĥĵŝŭ',
|
|
1304
|
+
'eo/quote': {
|
|
1305
|
+
left: '“‘',
|
|
1306
|
+
right: '”’'
|
|
1307
|
+
}
|
|
1308
|
+
};
|
|
1309
|
+
|
|
1310
|
+
var es = {
|
|
1311
|
+
'es/char': 'a-záéíñóúü',
|
|
1312
|
+
'es/quote': {
|
|
1313
|
+
left: '«“',
|
|
1314
|
+
right: '»”'
|
|
1315
|
+
}
|
|
1316
|
+
};
|
|
1317
|
+
|
|
1318
|
+
var et = {
|
|
1319
|
+
'et/char': 'abdefghijklmnoprstuvzäõöüšž',
|
|
1320
|
+
'et/quote': {
|
|
1321
|
+
left: '„«',
|
|
1322
|
+
right: '“»'
|
|
1323
|
+
}
|
|
1324
|
+
};
|
|
1325
|
+
|
|
1326
|
+
var fi = {
|
|
1327
|
+
'fi/char': 'abcdefghijklmnopqrstuvyöäå',
|
|
1328
|
+
'fi/quote': {
|
|
1329
|
+
left: '”’',
|
|
1330
|
+
right: '”’'
|
|
1331
|
+
}
|
|
1332
|
+
};
|
|
1333
|
+
|
|
1334
|
+
var fr = {
|
|
1335
|
+
'fr/char': 'a-zàâçèéêëîïôûüœæ',
|
|
1336
|
+
'fr/quote': {
|
|
1337
|
+
left: '«‹',
|
|
1338
|
+
right: '»›',
|
|
1339
|
+
spacing: true
|
|
1340
|
+
}
|
|
1341
|
+
};
|
|
1342
|
+
|
|
1343
|
+
var ga = {
|
|
1344
|
+
'ga/char': 'abcdefghilmnoprstuvwxyzáéíóú',
|
|
1345
|
+
'ga/quote': {
|
|
1346
|
+
left: '“‘',
|
|
1347
|
+
right: '”’'
|
|
1348
|
+
}
|
|
1349
|
+
};
|
|
1350
|
+
|
|
1351
|
+
var hu = {
|
|
1352
|
+
'hu/char': 'a-záäéíóöúüőű',
|
|
1353
|
+
'hu/quote': {
|
|
1354
|
+
left: '„»',
|
|
1355
|
+
right: '”«'
|
|
1356
|
+
}
|
|
1357
|
+
};
|
|
1358
|
+
|
|
1359
|
+
var it = {
|
|
1360
|
+
'it/char': 'a-zàéèìòù',
|
|
1361
|
+
'it/quote': {
|
|
1362
|
+
left: '«“',
|
|
1363
|
+
right: '»”'
|
|
1364
|
+
}
|
|
1365
|
+
};
|
|
1366
|
+
|
|
1367
|
+
var lv = {
|
|
1368
|
+
'lv/char': 'abcdefghijklmnopqrstuvxzæœ',
|
|
1369
|
+
'lv/quote': {
|
|
1370
|
+
left: '«„',
|
|
1371
|
+
right: '»“'
|
|
1372
|
+
}
|
|
1373
|
+
};
|
|
1374
|
+
|
|
1375
|
+
var nl = {
|
|
1376
|
+
'nl/char': 'a-zäçèéêëîïñöûü',
|
|
1377
|
+
'nl/quote': {
|
|
1378
|
+
left: '‘“',
|
|
1379
|
+
right: '’”'
|
|
1380
|
+
}
|
|
1381
|
+
};
|
|
1382
|
+
|
|
1383
|
+
var no = {
|
|
1384
|
+
'no/char': 'a-zåæèéêòóôø',
|
|
1385
|
+
'no/quote': {
|
|
1386
|
+
left: '«’',
|
|
1387
|
+
right: '»’'
|
|
1388
|
+
}
|
|
1389
|
+
};
|
|
1390
|
+
|
|
1391
|
+
var pl = {
|
|
1392
|
+
'pl/char': 'abcdefghijklmnoprstuvwxyzóąćęłńśźż',
|
|
1393
|
+
'pl/quote': {
|
|
1394
|
+
left: '„«',
|
|
1395
|
+
right: '”»'
|
|
1396
|
+
}
|
|
1397
|
+
};
|
|
1398
|
+
|
|
1399
|
+
var ro = {
|
|
1400
|
+
'ro/char': 'abcdefghijklmnoprstuvxzîășț',
|
|
1401
|
+
'ro/quote': {
|
|
1402
|
+
left: '„«',
|
|
1403
|
+
right: '”»'
|
|
1404
|
+
}
|
|
1405
|
+
};
|
|
1406
|
+
|
|
1407
|
+
var ru = {
|
|
1408
|
+
'ru/char': 'а-яё',
|
|
1409
|
+
'ru/dashBefore': '(^| |\\n)',
|
|
1410
|
+
'ru/dashAfter': "(?=[\xA0 ,.?:!]|$)",
|
|
1411
|
+
'ru/dashAfterDe': "(?=[,.?:!]|[\xA0 ][^\u0410-\u042F\u0401]|$)",
|
|
1412
|
+
'ru/l': 'а-яёa-z',
|
|
1413
|
+
'ru/L': 'А-ЯЁA-Z',
|
|
1414
|
+
'ru/month': 'январь|февраль|март|апрель|май|июнь|июль|август|сентябрь|октябрь|ноябрь|декабрь',
|
|
1415
|
+
'ru/monthGenCase': 'января|февраля|марта|апреля|мая|июня|июля|августа|сентября|октября|ноября|декабря',
|
|
1416
|
+
'ru/monthPreCase': 'январе|феврале|марте|апреле|мае|июне|июле|августе|сентябре|октябре|ноябре|декабре',
|
|
1417
|
+
'ru/quote': {
|
|
1418
|
+
left: '«„‚',
|
|
1419
|
+
right: '»“‘',
|
|
1420
|
+
removeDuplicateQuotes: true
|
|
1421
|
+
},
|
|
1422
|
+
'ru/shortMonth': 'янв|фев|мар|апр|ма[ейя]|июн|июл|авг|сен|окт|ноя|дек',
|
|
1423
|
+
'ru/weekday': 'понедельник|вторник|среда|четверг|пятница|суббота|воскресенье'
|
|
1424
|
+
};
|
|
1425
|
+
|
|
1426
|
+
var sk = {
|
|
1427
|
+
'sk/char': 'abcdefghijklmnoprstuvwxyzáäéíóôúýčďľňŕšťž',
|
|
1428
|
+
'sk/quote': {
|
|
1429
|
+
left: '„‚',
|
|
1430
|
+
right: '“‘'
|
|
1431
|
+
}
|
|
1432
|
+
};
|
|
1433
|
+
|
|
1434
|
+
var sl = {
|
|
1435
|
+
'sl/char': 'a-zčšž',
|
|
1436
|
+
'sl/quote': {
|
|
1437
|
+
left: '„‚',
|
|
1438
|
+
right: '“‘'
|
|
1439
|
+
}
|
|
1440
|
+
};
|
|
1441
|
+
|
|
1442
|
+
var sr = {
|
|
1443
|
+
'sr/char': 'abcdefghijklmnoprstuvzćčđšž',
|
|
1444
|
+
'sr/quote': {
|
|
1445
|
+
left: '„’',
|
|
1446
|
+
right: '”’'
|
|
1447
|
+
}
|
|
1448
|
+
};
|
|
1449
|
+
|
|
1450
|
+
var sv = {
|
|
1451
|
+
'sv/char': 'a-zäåéö',
|
|
1452
|
+
'sv/quote': {
|
|
1453
|
+
left: '”’',
|
|
1454
|
+
right: '”’'
|
|
1455
|
+
}
|
|
1456
|
+
};
|
|
1457
|
+
|
|
1458
|
+
var tr = {
|
|
1459
|
+
'tr/char': 'abcdefghijklmnoprstuvyzâçîöûüğış',
|
|
1460
|
+
'tr/quote': {
|
|
1461
|
+
left: '“‘',
|
|
1462
|
+
right: '”’'
|
|
1463
|
+
}
|
|
1464
|
+
};
|
|
1465
|
+
|
|
1466
|
+
var uk = {
|
|
1467
|
+
'uk/char': 'абвгдежзийклмнопрстуфхцчшщьюяєіїґ',
|
|
1468
|
+
'uk/quote': {
|
|
1469
|
+
left: '«„',
|
|
1470
|
+
right: '»“'
|
|
1471
|
+
}
|
|
1472
|
+
};
|
|
1473
|
+
|
|
1474
|
+
var data$1 = [common, be, bg, ca, da, de, el, enGB, enUS, eo, es, et, fi, fr, ga, hu, it, lv, nl, no, pl, ro, ru, sk, sl, sr, sv, tr, uk];
|
|
1475
|
+
data$1.forEach(function (item) {
|
|
1476
|
+
return setData(item);
|
|
1477
|
+
});
|
|
1478
|
+
|
|
1479
|
+
var eMail = {
|
|
1480
|
+
name: 'common/html/e-mail',
|
|
1481
|
+
queue: 'end',
|
|
1482
|
+
handler: function handler(text, settings, context) {
|
|
1483
|
+
return context.isHTML ? text : text.replace(/(^|[\s;(])([\w\-.]{2,64})@([\w\-.]{2,64})\.([a-z]{2,64})([)\s.,!?]|$)/gi, '$1<a href="mailto:$2@$3.$4">$2@$3.$4</a>$5');
|
|
1484
|
+
},
|
|
1485
|
+
disabled: true,
|
|
1486
|
+
htmlAttrs: false
|
|
1487
|
+
};
|
|
1488
|
+
|
|
1489
|
+
var escape = {
|
|
1490
|
+
name: 'common/html/escape',
|
|
1491
|
+
index: '+100',
|
|
1492
|
+
queue: 'end',
|
|
1493
|
+
handler: function handler(text) {
|
|
1494
|
+
var entityMap = {
|
|
1495
|
+
'&': '&',
|
|
1496
|
+
'<': '<',
|
|
1497
|
+
'>': '>',
|
|
1498
|
+
'"': '"',
|
|
1499
|
+
'\'': ''',
|
|
1500
|
+
'/': '/'
|
|
1501
|
+
};
|
|
1502
|
+
return text.replace(/[&<>"'/]/g, function (s) {
|
|
1503
|
+
return entityMap[s];
|
|
1504
|
+
});
|
|
1505
|
+
},
|
|
1506
|
+
disabled: true
|
|
1507
|
+
};
|
|
1508
|
+
|
|
1509
|
+
var nbr = {
|
|
1510
|
+
name: 'common/html/nbr',
|
|
1511
|
+
index: '+10',
|
|
1512
|
+
queue: 'end',
|
|
1513
|
+
handler: function handler(text) {
|
|
1514
|
+
return text.replace(/([^\n>])\n(?=[^\n])/g, '$1<br/>\n');
|
|
1515
|
+
},
|
|
1516
|
+
disabled: true,
|
|
1517
|
+
htmlAttrs: false
|
|
1518
|
+
};
|
|
1519
|
+
|
|
1520
|
+
var blockElements = ['address', 'article', 'aside', 'blockquote', 'canvas', 'dd', 'div', 'dl', 'fieldset', 'figcaption', 'figure', 'footer', 'form', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'header', 'hgroup', 'hr', 'li', 'main', 'nav', 'noscript', 'ol', 'output', 'p', 'pre', 'section', 'table', 'tfoot', 'ul', 'video'];
|
|
1521
|
+
|
|
1522
|
+
var p = {
|
|
1523
|
+
name: 'common/html/p',
|
|
1524
|
+
index: '+5',
|
|
1525
|
+
queue: 'end',
|
|
1526
|
+
handler: function handler(text) {
|
|
1527
|
+
var blockRe = new RegExp('<(' + blockElements.join('|') + ')[>\\s]');
|
|
1528
|
+
var separator = '\n\n';
|
|
1529
|
+
var buffer = text.split(separator);
|
|
1530
|
+
buffer.forEach(function (text, i, data) {
|
|
1531
|
+
if (!text.trim()) {
|
|
1532
|
+
return;
|
|
1533
|
+
}
|
|
1534
|
+
|
|
1535
|
+
if (!blockRe.test(text)) {
|
|
1536
|
+
data[i] = text.replace(/^(\s*)/, '$1<p>').replace(/(\s*)$/, '</p>$1');
|
|
1537
|
+
}
|
|
1538
|
+
});
|
|
1539
|
+
return buffer.join(separator);
|
|
1540
|
+
},
|
|
1541
|
+
disabled: true,
|
|
1542
|
+
htmlAttrs: false
|
|
1543
|
+
};
|
|
1544
|
+
|
|
1545
|
+
var processingAttrs = {
|
|
1546
|
+
name: 'common/html/processingAttrs',
|
|
1547
|
+
queue: 'hide-safe-tags-own',
|
|
1548
|
+
// After "hide-safe-tags-own", before "hide-safe-tags-html".
|
|
1549
|
+
handler: function handler(text, settings, context) {
|
|
1550
|
+
var that = this;
|
|
1551
|
+
var reAttrs = new RegExp('(^|\\s)(' + settings.attrs.join('|') + ')=("[^"]*?"|\'[^\']*?\')', 'gi');
|
|
1552
|
+
var prefs = deepCopy(context.prefs);
|
|
1553
|
+
|
|
1554
|
+
prefs.ruleFilter = function (rule) {
|
|
1555
|
+
return rule.htmlAttrs !== false;
|
|
1556
|
+
};
|
|
1557
|
+
|
|
1558
|
+
return text.replace(/(<[-\w]+\s)([^>]+?)(?=>)/g, function (match, tagName, attrs) {
|
|
1559
|
+
var resultAttrs = attrs.replace(reAttrs, function (submatch, space, attrName, attrValue) {
|
|
1560
|
+
var lquote = attrValue[0];
|
|
1561
|
+
var rquote = attrValue[attrValue.length - 1];
|
|
1562
|
+
var value = attrValue.slice(1, -1);
|
|
1563
|
+
return space + attrName + '=' + lquote + that.execute(value, prefs) + rquote;
|
|
1564
|
+
});
|
|
1565
|
+
return tagName + resultAttrs;
|
|
1566
|
+
});
|
|
1567
|
+
},
|
|
1568
|
+
settings: {
|
|
1569
|
+
attrs: ['title', 'placeholder']
|
|
1570
|
+
},
|
|
1571
|
+
disabled: true,
|
|
1572
|
+
htmlAttrs: false
|
|
1573
|
+
};
|
|
1574
|
+
|
|
1575
|
+
var quot = {
|
|
1576
|
+
name: 'common/html/quot',
|
|
1577
|
+
queue: 'hide-safe-tags',
|
|
1578
|
+
handler: function handler(text) {
|
|
1579
|
+
return text.replace(/"/g, '"');
|
|
1580
|
+
}
|
|
1581
|
+
};
|
|
1582
|
+
|
|
1583
|
+
var stripTags = {
|
|
1584
|
+
name: 'common/html/stripTags',
|
|
1585
|
+
index: '+99',
|
|
1586
|
+
queue: 'end',
|
|
1587
|
+
handler: function handler(text) {
|
|
1588
|
+
return text.replace(/<[^>]+>/g, '');
|
|
1589
|
+
},
|
|
1590
|
+
disabled: true
|
|
1591
|
+
};
|
|
1592
|
+
|
|
1593
|
+
var url = {
|
|
1594
|
+
name: 'common/html/url',
|
|
1595
|
+
queue: 'end',
|
|
1596
|
+
handler: function handler(text, settings, context) {
|
|
1597
|
+
return context.isHTML ? text : text.replace(regExpUrl, function ($0, protocol, path) {
|
|
1598
|
+
path = path.replace(/([^/]+\/?)(\?|#)$/, '$1') // Remove ending ? and #
|
|
1599
|
+
.replace(/^([^/]+)\/$/, '$1'); // Remove ending /
|
|
1600
|
+
|
|
1601
|
+
if (protocol === 'http') {
|
|
1602
|
+
path = path.replace(/^([^/]+)(:80)([^\d]|\/|$)/, '$1$3'); // Remove 80 port
|
|
1603
|
+
} else if (protocol === 'https') {
|
|
1604
|
+
path = path.replace(/^([^/]+)(:443)([^\d]|\/|$)/, '$1$3'); // Remove 443 port
|
|
1605
|
+
}
|
|
1606
|
+
|
|
1607
|
+
var url = path;
|
|
1608
|
+
var fullUrl = protocol + '://' + path;
|
|
1609
|
+
var firstPart = '<a href="' + fullUrl + '">';
|
|
1610
|
+
|
|
1611
|
+
if (protocol === 'http' || protocol === 'https') {
|
|
1612
|
+
url = url.replace(/^www\./, '');
|
|
1613
|
+
return firstPart + (protocol === 'http' ? url : protocol + '://' + url) + '</a>';
|
|
1614
|
+
}
|
|
1615
|
+
|
|
1616
|
+
return firstPart + fullUrl + '</a>';
|
|
1617
|
+
});
|
|
1618
|
+
},
|
|
1619
|
+
disabled: true,
|
|
1620
|
+
htmlAttrs: false
|
|
1621
|
+
};
|
|
1622
|
+
|
|
1623
|
+
Typograf.addRules([eMail, escape, nbr, p, processingAttrs, quot, stripTags, url]);
|
|
1624
|
+
|
|
1625
|
+
var afterNumber = {
|
|
1626
|
+
name: 'common/nbsp/afterNumber',
|
|
1627
|
+
handler: function handler(text, settings, context) {
|
|
1628
|
+
var re = '(^|\\s)(\\d{1,5}) ([' + context.getData('char') + ']+)';
|
|
1629
|
+
return text.replace(new RegExp(re, 'gi'), "$1$2\xA0$3");
|
|
1630
|
+
},
|
|
1631
|
+
disabled: true
|
|
1632
|
+
};
|
|
1633
|
+
|
|
1634
|
+
var afterParagraphMark = {
|
|
1635
|
+
name: 'common/nbsp/afterParagraphMark',
|
|
1636
|
+
handler: function handler(text) {
|
|
1637
|
+
return text.replace(/¶ ?(?=\d)/g, "\xB6\xA0");
|
|
1638
|
+
}
|
|
1639
|
+
};
|
|
1640
|
+
|
|
1641
|
+
var afterSectionMark = {
|
|
1642
|
+
name: 'common/nbsp/afterSectionMark',
|
|
1643
|
+
handler: function handler(text, settings, context) {
|
|
1644
|
+
// \u2009 - THIN SPACE
|
|
1645
|
+
// \u202F - NARROW NO-BREAK SPACE
|
|
1646
|
+
var locale = context.prefs.locale[0];
|
|
1647
|
+
return text.replace(/§[ \u00A0\u2009]?(?=\d|I|V|X)/g, locale === 'ru' ? "\xA7\u202F" : "\xA7\xA0");
|
|
1648
|
+
}
|
|
1649
|
+
};
|
|
1650
|
+
|
|
1651
|
+
var afterShortWord = {
|
|
1652
|
+
name: 'common/nbsp/afterShortWord',
|
|
1653
|
+
handler: function handler(text, settings, context) {
|
|
1654
|
+
var len = settings.lengthShortWord;
|
|
1655
|
+
var before = " \xA0(" + privateLabel + getData('common/quote');
|
|
1656
|
+
var subStr = '(^|[' + before + '])([' + context.getData('char') + ']{1,' + len + '}) ';
|
|
1657
|
+
var newSubStr = "$1$2\xA0";
|
|
1658
|
+
var re = new RegExp(subStr, 'gim');
|
|
1659
|
+
return text.replace(re, newSubStr).replace(re, newSubStr);
|
|
1660
|
+
},
|
|
1661
|
+
settings: {
|
|
1662
|
+
lengthShortWord: 2
|
|
1663
|
+
}
|
|
1664
|
+
};
|
|
1665
|
+
|
|
1666
|
+
var beforeShortLastNumber = {
|
|
1667
|
+
name: 'common/nbsp/beforeShortLastNumber',
|
|
1668
|
+
handler: function handler(text, settings, context) {
|
|
1669
|
+
var ch = context.getData('char');
|
|
1670
|
+
var CH = ch.toUpperCase();
|
|
1671
|
+
var re = new RegExp('([' + ch + CH + ']) (?=\\d{1,' + settings.lengthLastNumber + '}[-+−%\'"' + context.getData('quote').right + ')]?([.!?…]( [' + CH + ']|$)|$))', 'gm');
|
|
1672
|
+
return text.replace(re, "$1\xA0");
|
|
1673
|
+
},
|
|
1674
|
+
live: false,
|
|
1675
|
+
settings: {
|
|
1676
|
+
lengthLastNumber: 2
|
|
1677
|
+
}
|
|
1678
|
+
};
|
|
1679
|
+
|
|
1680
|
+
var beforeShortLastWord = {
|
|
1681
|
+
name: 'common/nbsp/beforeShortLastWord',
|
|
1682
|
+
handler: function handler(text, settings, context) {
|
|
1683
|
+
var ch = context.getData('char');
|
|
1684
|
+
var CH = ch.toUpperCase();
|
|
1685
|
+
var re = new RegExp('([' + ch + '\\d]) ([' + ch + CH + ']{1,' + settings.lengthLastWord + '}[.!?…])( [' + CH + ']|$)', 'g');
|
|
1686
|
+
return text.replace(re, "$1\xA0$2$3");
|
|
1687
|
+
},
|
|
1688
|
+
settings: {
|
|
1689
|
+
lengthLastWord: 3
|
|
1690
|
+
}
|
|
1691
|
+
};
|
|
1692
|
+
|
|
1693
|
+
var dpi = {
|
|
1694
|
+
name: 'common/nbsp/dpi',
|
|
1695
|
+
handler: function handler(text) {
|
|
1696
|
+
return text.replace(/(\d) ?(lpi|dpi)(?!\w)/, "$1\xA0$2");
|
|
1697
|
+
}
|
|
1698
|
+
};
|
|
1699
|
+
|
|
1700
|
+
function replaceNbsp$1($0, $1, $2, $3) {
|
|
1701
|
+
return $1 + $2.replace(/([^\u00A0])\u00A0([^\u00A0])/g, '$1 $2') + $3;
|
|
1702
|
+
}
|
|
1703
|
+
|
|
1704
|
+
var nowrap = {
|
|
1705
|
+
name: 'common/nbsp/nowrap',
|
|
1706
|
+
queue: 'end',
|
|
1707
|
+
handler: function handler(text) {
|
|
1708
|
+
return text.replace(/(<nowrap>)(.*?)(<\/nowrap>)/g, replaceNbsp$1).replace(/(<nobr>)(.*?)(<\/nobr>)/g, replaceNbsp$1);
|
|
1709
|
+
}
|
|
1710
|
+
};
|
|
1711
|
+
|
|
1712
|
+
var replaceNbsp$2 = {
|
|
1713
|
+
name: 'common/nbsp/replaceNbsp',
|
|
1714
|
+
queue: 'utf',
|
|
1715
|
+
live: false,
|
|
1716
|
+
handler: replaceNbsp,
|
|
1717
|
+
disabled: true
|
|
1718
|
+
};
|
|
1719
|
+
|
|
1720
|
+
Typograf.addRules([afterNumber, afterParagraphMark, afterSectionMark, afterShortWord, beforeShortLastNumber, beforeShortLastWord, dpi, nowrap, replaceNbsp$2]);
|
|
1721
|
+
|
|
1722
|
+
var digitGrouping = {
|
|
1723
|
+
name: 'common/number/digitGrouping',
|
|
1724
|
+
index: '310',
|
|
1725
|
+
disabled: true,
|
|
1726
|
+
handler: function handler(text, settings) {
|
|
1727
|
+
return text.replace(new RegExp("(^ ?|\\D |".concat(privateLabel, ")(\\d{1,3}([ \xA0\u202F\u2009]\\d{3})+)(?! ?[\\d-])"), 'gm'), function ($0, $1, $2) {
|
|
1728
|
+
return $1 + $2.replace(/\s/g, settings.space);
|
|
1729
|
+
}) // https://www.bipm.org/utils/common/pdf/si-brochure/SI-Brochure-9-EN.pdf #5.4.4
|
|
1730
|
+
.replace(/(\d{5,}([.,]\d+)?)/g, function ($0, $1) {
|
|
1731
|
+
var decimalMarker = $1.match(/[.,]/);
|
|
1732
|
+
|
|
1733
|
+
var _ref = decimalMarker ? $1.split(decimalMarker) : [$1],
|
|
1734
|
+
_ref2 = _slicedToArray(_ref, 2),
|
|
1735
|
+
integerPart = _ref2[0],
|
|
1736
|
+
fractionalPart = _ref2[1];
|
|
1737
|
+
|
|
1738
|
+
integerPart = integerPart.replace(/(\d)(?=(\d{3})+([^\d]|$))/g, '$1' + settings.space);
|
|
1739
|
+
return decimalMarker ? integerPart + decimalMarker + fractionalPart : integerPart;
|
|
1740
|
+
});
|
|
1741
|
+
},
|
|
1742
|
+
settings: {
|
|
1743
|
+
space: "\u202F"
|
|
1744
|
+
}
|
|
1745
|
+
};
|
|
1746
|
+
|
|
1747
|
+
var fraction = {
|
|
1748
|
+
name: 'common/number/fraction',
|
|
1749
|
+
handler: function handler(text) {
|
|
1750
|
+
return text.replace(/(^|\D)1\/2(\D|$)/g, '$1½$2').replace(/(^|\D)1\/4(\D|$)/g, '$1¼$2').replace(/(^|\D)3\/4(\D|$)/g, '$1¾$2');
|
|
1751
|
+
}
|
|
1752
|
+
};
|
|
1753
|
+
|
|
1754
|
+
var mathSigns = {
|
|
1755
|
+
name: 'common/number/mathSigns',
|
|
1756
|
+
handler: function handler(text) {
|
|
1757
|
+
return replace(text, [[/!=/g, '≠'], [/<=/g, '≤'], [/(^|[^=])>=/g, '$1≥'], [/<=>/g, '⇔'], [/<</g, '≪'], [/>>/g, '≫'], [/~=/g, '≅'], [/(^|[^+])\+-/g, '$1±']]);
|
|
1758
|
+
}
|
|
1759
|
+
};
|
|
1760
|
+
|
|
1761
|
+
var times = {
|
|
1762
|
+
name: 'common/number/times',
|
|
1763
|
+
handler: function handler(text) {
|
|
1764
|
+
return text.replace(/(\d)[ \u00A0]?[xх][ \u00A0]?(\d)/g, '$1×$2');
|
|
1765
|
+
}
|
|
1766
|
+
};
|
|
1767
|
+
|
|
1768
|
+
Typograf.addRules([digitGrouping, fraction, mathSigns, times]);
|
|
1769
|
+
|
|
1770
|
+
var delBOM = {
|
|
1771
|
+
name: 'common/other/delBOM',
|
|
1772
|
+
queue: 'start',
|
|
1773
|
+
index: -1,
|
|
1774
|
+
handler: function handler(text) {
|
|
1775
|
+
if (text.charCodeAt(0) === 0xFEFF) {
|
|
1776
|
+
return text.slice(1);
|
|
1777
|
+
}
|
|
1778
|
+
|
|
1779
|
+
return text;
|
|
1780
|
+
}
|
|
1781
|
+
};
|
|
1782
|
+
|
|
1783
|
+
var repeatWord = {
|
|
1784
|
+
name: 'common/other/repeatWord',
|
|
1785
|
+
handler: function handler(text, settings, context) {
|
|
1786
|
+
var punc = '[;:,.?! \n' + getData('common/quote') + ']';
|
|
1787
|
+
var re = new RegExp('(' + punc + '|^)' + '([' + context.getData('char') + ']{' + settings.min + ',}) ' + '\\2(' + punc + '|$)', 'gi');
|
|
1788
|
+
return text.replace(re, '$1$2$3');
|
|
1789
|
+
},
|
|
1790
|
+
settings: {
|
|
1791
|
+
min: 2
|
|
1792
|
+
},
|
|
1793
|
+
disabled: true
|
|
1794
|
+
};
|
|
1795
|
+
|
|
1796
|
+
Typograf.addRules([delBOM, repeatWord]);
|
|
1797
|
+
|
|
1798
|
+
var apostrophe = {
|
|
1799
|
+
name: 'common/punctuation/apostrophe',
|
|
1800
|
+
handler: function handler(text, settings, context) {
|
|
1801
|
+
var letters = '([' + context.getData('char') + '])';
|
|
1802
|
+
var re = new RegExp(letters + '\'' + letters, 'gi');
|
|
1803
|
+
return text.replace(re, '$1’$2');
|
|
1804
|
+
}
|
|
1805
|
+
};
|
|
1806
|
+
|
|
1807
|
+
var delDoublePunctuation = {
|
|
1808
|
+
name: 'common/punctuation/delDoublePunctuation',
|
|
1809
|
+
handler: function handler(text) {
|
|
1810
|
+
return text.replace(/(^|[^,]),,(?!,)/g, '$1,').replace(/(^|[^:])::(?!:)/g, '$1:').replace(/(^|[^!?.])\.\.(?!\.)/g, '$1.').replace(/(^|[^;]);;(?!;)/g, '$1;').replace(/(^|[^?])\?\?(?!\?)/g, '$1?');
|
|
1811
|
+
}
|
|
1812
|
+
};
|
|
1813
|
+
|
|
1814
|
+
var hellip = {
|
|
1815
|
+
name: 'common/punctuation/hellip',
|
|
1816
|
+
handler: function handler(text, settings, context) {
|
|
1817
|
+
return context.prefs.locale[0] === 'ru' ? text.replace(/(^|[^.])\.{3,4}(?=[^.]|$)/g, '$1…') : text.replace(/(^|[^.])\.{3}(\.?)(?=[^.]|$)/g, '$1…$2');
|
|
1818
|
+
}
|
|
1819
|
+
};
|
|
1820
|
+
|
|
1821
|
+
var MAX_LEVEL_WITH_ERRORS = 2;
|
|
1822
|
+
var Quote = {
|
|
1823
|
+
bufferQuotes: {
|
|
1824
|
+
left: "\uF005\uF006\uF007",
|
|
1825
|
+
right: "\uF008\uF009\uF0A0"
|
|
1826
|
+
},
|
|
1827
|
+
beforeLeft: " \n\t\xA0[(",
|
|
1828
|
+
afterRight: " \n\t\xA0!?.:;#*,\u2026)\\]",
|
|
1829
|
+
process: function process(params) {
|
|
1830
|
+
var text = params.context.text;
|
|
1831
|
+
var count = this.count(text);
|
|
1832
|
+
|
|
1833
|
+
if (!count.total) {
|
|
1834
|
+
return text;
|
|
1835
|
+
}
|
|
1836
|
+
|
|
1837
|
+
var originalSettings = params.settings;
|
|
1838
|
+
var isEqualQuotes = params.settings.left[0] === params.settings.right[0]; // For SW, FI
|
|
1839
|
+
|
|
1840
|
+
if (isEqualQuotes) {
|
|
1841
|
+
params.settings = deepCopy(params.settings);
|
|
1842
|
+
params.settings.left = this.bufferQuotes.left.slice(0, params.settings.left.length);
|
|
1843
|
+
params.settings.right = this.bufferQuotes.right.slice(0, params.settings.right.length);
|
|
1844
|
+
} // For FR
|
|
1845
|
+
|
|
1846
|
+
|
|
1847
|
+
if (params.settings.spacing) {
|
|
1848
|
+
text = this.removeSpacing(text, params.settings);
|
|
1849
|
+
}
|
|
1850
|
+
|
|
1851
|
+
text = this.set(text, params); // For FR
|
|
1852
|
+
|
|
1853
|
+
if (params.settings.spacing) {
|
|
1854
|
+
text = this.setSpacing(text, params.settings);
|
|
1855
|
+
} // For RU
|
|
1856
|
+
|
|
1857
|
+
|
|
1858
|
+
if (params.settings.removeDuplicateQuotes) {
|
|
1859
|
+
text = this.removeDuplicates(text, params.settings);
|
|
1860
|
+
} // For SW, FI
|
|
1861
|
+
|
|
1862
|
+
|
|
1863
|
+
if (isEqualQuotes) {
|
|
1864
|
+
text = this.returnOriginalQuotes(text, originalSettings, params.settings);
|
|
1865
|
+
params.settings = originalSettings;
|
|
1866
|
+
}
|
|
1867
|
+
|
|
1868
|
+
return text;
|
|
1869
|
+
},
|
|
1870
|
+
returnOriginalQuotes: function returnOriginalQuotes(text, originalSettings, bufferSettings) {
|
|
1871
|
+
var buffer = {};
|
|
1872
|
+
|
|
1873
|
+
for (var i = 0; i < bufferSettings.left.length; i++) {
|
|
1874
|
+
buffer[bufferSettings.left[i]] = originalSettings.left[i];
|
|
1875
|
+
buffer[bufferSettings.right[i]] = originalSettings.right[i];
|
|
1876
|
+
}
|
|
1877
|
+
|
|
1878
|
+
return text.replace(new RegExp('[' + bufferSettings.left + bufferSettings.right + ']', 'g'), function (quote) {
|
|
1879
|
+
return buffer[quote];
|
|
1880
|
+
});
|
|
1881
|
+
},
|
|
1882
|
+
count: function count(text) {
|
|
1883
|
+
var count = {
|
|
1884
|
+
total: 0
|
|
1885
|
+
};
|
|
1886
|
+
text.replace(new RegExp('[' + getData('common/quote') + ']', 'g'), function (quote) {
|
|
1887
|
+
if (!count[quote]) {
|
|
1888
|
+
count[quote] = 0;
|
|
1889
|
+
}
|
|
1890
|
+
|
|
1891
|
+
count[quote]++;
|
|
1892
|
+
count.total++;
|
|
1893
|
+
return quote;
|
|
1894
|
+
});
|
|
1895
|
+
return count;
|
|
1896
|
+
},
|
|
1897
|
+
removeDuplicates: function removeDuplicates(text, settings) {
|
|
1898
|
+
var lquote = settings.left[0];
|
|
1899
|
+
var lquote2 = settings.left[1] || lquote;
|
|
1900
|
+
var rquote = settings.right[0];
|
|
1901
|
+
|
|
1902
|
+
if (lquote !== lquote2) {
|
|
1903
|
+
return text;
|
|
1904
|
+
}
|
|
1905
|
+
|
|
1906
|
+
return text // ««word» word» -> «word» word»
|
|
1907
|
+
.replace(new RegExp(lquote + lquote, 'g'), lquote) // «word «word»» -> «word «word»
|
|
1908
|
+
.replace(new RegExp(rquote + rquote, 'g'), rquote);
|
|
1909
|
+
},
|
|
1910
|
+
removeSpacing: function removeSpacing(text, settings) {
|
|
1911
|
+
for (var i = 0, len = settings.left.length; i < len; i++) {
|
|
1912
|
+
var lquote = settings.left[i];
|
|
1913
|
+
var rquote = settings.right[i];
|
|
1914
|
+
text = text.replace(new RegExp(lquote + "([ \u202F\xA0])", 'g'), lquote).replace(new RegExp("([ \u202F\xA0])" + rquote, 'g'), rquote);
|
|
1915
|
+
}
|
|
1916
|
+
|
|
1917
|
+
return text;
|
|
1918
|
+
},
|
|
1919
|
+
setSpacing: function setSpacing(text, settings) {
|
|
1920
|
+
for (var i = 0, len = settings.left.length; i < len; i++) {
|
|
1921
|
+
var lquote = settings.left[i];
|
|
1922
|
+
var rquote = settings.right[i];
|
|
1923
|
+
text = text.replace(new RegExp(lquote + "([^\u202F])", 'g'), lquote + "\u202F$1").replace(new RegExp("([^\u202F])" + rquote, 'g'), "$1\u202F" + rquote);
|
|
1924
|
+
}
|
|
1925
|
+
|
|
1926
|
+
return text;
|
|
1927
|
+
},
|
|
1928
|
+
set: function set(text, params) {
|
|
1929
|
+
var quotes = getData('common/quote');
|
|
1930
|
+
var lquote = params.settings.left[0];
|
|
1931
|
+
var lquote2 = params.settings.left[1] || lquote;
|
|
1932
|
+
var rquote = params.settings.right[0];
|
|
1933
|
+
var reL = new RegExp('(^|[' + this.beforeLeft + '])([' + quotes + ']+)(?=[^\\s' + privateLabel + '])', 'gim');
|
|
1934
|
+
var reR = new RegExp('([^\\s' + privateLabel + '])([' + quotes + ']+)(?=[' + this.afterRight + ']|$)', 'gim');
|
|
1935
|
+
text = text.replace(reL, function ($0, $1, $2) {
|
|
1936
|
+
return $1 + repeat(lquote, $2.length);
|
|
1937
|
+
}).replace(reR, function ($0, $1, $2) {
|
|
1938
|
+
return $1 + repeat(rquote, $2.length);
|
|
1939
|
+
});
|
|
1940
|
+
text = this.setAboveTags(text, params);
|
|
1941
|
+
|
|
1942
|
+
if (lquote !== lquote2) {
|
|
1943
|
+
text = this.setInner(text, params.settings);
|
|
1944
|
+
}
|
|
1945
|
+
|
|
1946
|
+
return text;
|
|
1947
|
+
},
|
|
1948
|
+
setAboveTags: function setAboveTags(text, params) {
|
|
1949
|
+
var _this = this;
|
|
1950
|
+
|
|
1951
|
+
var quotes = getData('common/quote');
|
|
1952
|
+
var lquote = params.settings.left[0];
|
|
1953
|
+
var rquote = params.settings.right[0];
|
|
1954
|
+
return text.replace(new RegExp('(^|.)([' + quotes + '])(.|$)', 'gm'), function (original, prev, quote, next, pos) {
|
|
1955
|
+
if (prev !== privateLabel && next !== privateLabel) {
|
|
1956
|
+
return original;
|
|
1957
|
+
}
|
|
1958
|
+
|
|
1959
|
+
if (prev === privateLabel && next === privateLabel) {
|
|
1960
|
+
if (quote === '"') {
|
|
1961
|
+
return prev + _this.getAboveTwoTags(text, pos + 1, params) + next;
|
|
1962
|
+
}
|
|
1963
|
+
|
|
1964
|
+
return original;
|
|
1965
|
+
}
|
|
1966
|
+
|
|
1967
|
+
if (prev === privateLabel) {
|
|
1968
|
+
var hasRight = _this.afterRight.indexOf(next) > -1;
|
|
1969
|
+
|
|
1970
|
+
var prevInfo = _this.getPrevTagInfo(text, pos - 1, params);
|
|
1971
|
+
|
|
1972
|
+
if (hasRight && prevInfo && prevInfo.group === 'html') {
|
|
1973
|
+
return prev + (prevInfo.isClosing ? rquote : lquote) + next;
|
|
1974
|
+
}
|
|
1975
|
+
|
|
1976
|
+
return prev + (!next || hasRight ? rquote : lquote) + next;
|
|
1977
|
+
} else {
|
|
1978
|
+
var hasLeft = _this.beforeLeft.indexOf(prev) > -1;
|
|
1979
|
+
|
|
1980
|
+
var nextInfo = _this.getNextTagInfo(text, pos + 1, params);
|
|
1981
|
+
|
|
1982
|
+
if (hasLeft && nextInfo && nextInfo.group === 'html') {
|
|
1983
|
+
return prev + (nextInfo.isClosing ? rquote : lquote) + next;
|
|
1984
|
+
}
|
|
1985
|
+
|
|
1986
|
+
return prev + (!prev || hasLeft ? lquote : rquote) + next;
|
|
1987
|
+
}
|
|
1988
|
+
});
|
|
1989
|
+
},
|
|
1990
|
+
getAboveTwoTags: function getAboveTwoTags(text, pos, params) {
|
|
1991
|
+
var prevInfo = this.getPrevTagInfo(text, pos, params);
|
|
1992
|
+
var nextInfo = this.getNextTagInfo(text, pos, params);
|
|
1993
|
+
|
|
1994
|
+
if (prevInfo) {
|
|
1995
|
+
if (prevInfo.group === 'html') {
|
|
1996
|
+
if (!prevInfo.isClosing) {
|
|
1997
|
+
return params.settings.left[0];
|
|
1998
|
+
}
|
|
1999
|
+
|
|
2000
|
+
if (nextInfo && nextInfo.isClosing && prevInfo.isClosing) {
|
|
2001
|
+
return params.settings.right[0];
|
|
2002
|
+
}
|
|
2003
|
+
}
|
|
2004
|
+
}
|
|
2005
|
+
|
|
2006
|
+
return text[pos];
|
|
2007
|
+
},
|
|
2008
|
+
getPrevTagInfo: function getPrevTagInfo(text, pos, params) {
|
|
2009
|
+
var prevLabel = params.safeTags.getPrevLabel(text, pos - 1);
|
|
2010
|
+
|
|
2011
|
+
if (prevLabel) {
|
|
2012
|
+
var prevTag = params.safeTags.getTagByLabel(params.context, prevLabel);
|
|
2013
|
+
|
|
2014
|
+
if (prevTag) {
|
|
2015
|
+
return params.safeTags.getTagInfo(prevTag);
|
|
2016
|
+
}
|
|
2017
|
+
}
|
|
2018
|
+
|
|
2019
|
+
return null;
|
|
2020
|
+
},
|
|
2021
|
+
getNextTagInfo: function getNextTagInfo(text, pos, params) {
|
|
2022
|
+
var nextLabel = params.safeTags.getNextLabel(text, pos + 1);
|
|
2023
|
+
|
|
2024
|
+
if (nextLabel) {
|
|
2025
|
+
var nextTag = params.safeTags.getTagByLabel(params.context, nextLabel);
|
|
2026
|
+
|
|
2027
|
+
if (nextTag) {
|
|
2028
|
+
return params.safeTags.getTagInfo(nextTag);
|
|
2029
|
+
}
|
|
2030
|
+
}
|
|
2031
|
+
|
|
2032
|
+
return null;
|
|
2033
|
+
},
|
|
2034
|
+
setInner: function setInner(text, settings) {
|
|
2035
|
+
var lquote = settings.left[0];
|
|
2036
|
+
var rquote = settings.right[0];
|
|
2037
|
+
var minLevel = 0;
|
|
2038
|
+
var maxLevel = this.getMaxLevel(text, lquote, rquote, settings.left.length);
|
|
2039
|
+
var level = minLevel;
|
|
2040
|
+
var result = '';
|
|
2041
|
+
|
|
2042
|
+
for (var i = 0, len = text.length; i < len; i++) {
|
|
2043
|
+
var letter = text[i];
|
|
2044
|
+
|
|
2045
|
+
if (letter === lquote) {
|
|
2046
|
+
result += settings.left[level > maxLevel - 1 ? maxLevel - 1 : level];
|
|
2047
|
+
level++;
|
|
2048
|
+
|
|
2049
|
+
if (level > maxLevel) {
|
|
2050
|
+
level = maxLevel;
|
|
2051
|
+
}
|
|
2052
|
+
} else if (letter === rquote) {
|
|
2053
|
+
level--;
|
|
2054
|
+
|
|
2055
|
+
if (level < minLevel) {
|
|
2056
|
+
level = minLevel;
|
|
2057
|
+
}
|
|
2058
|
+
|
|
2059
|
+
result += settings.right[level];
|
|
2060
|
+
} else {
|
|
2061
|
+
if (letter === '"') {
|
|
2062
|
+
level = minLevel;
|
|
2063
|
+
}
|
|
2064
|
+
|
|
2065
|
+
result += letter;
|
|
2066
|
+
}
|
|
2067
|
+
}
|
|
2068
|
+
|
|
2069
|
+
return result;
|
|
2070
|
+
},
|
|
2071
|
+
getMaxLevel: function getMaxLevel(text, leftQuote, rightQuote, length) {
|
|
2072
|
+
var count = this.count(text);
|
|
2073
|
+
return count[leftQuote] === count[rightQuote] ? length : Math.min(length, MAX_LEVEL_WITH_ERRORS);
|
|
2074
|
+
}
|
|
2075
|
+
};
|
|
2076
|
+
var quote = {
|
|
2077
|
+
name: 'common/punctuation/quote',
|
|
2078
|
+
handler: function handler(text, commonSettings, context) {
|
|
2079
|
+
var locale = context.prefs.locale[0];
|
|
2080
|
+
var settings = commonSettings[locale];
|
|
2081
|
+
|
|
2082
|
+
if (!settings) {
|
|
2083
|
+
return text;
|
|
2084
|
+
}
|
|
2085
|
+
|
|
2086
|
+
return Quote.process({
|
|
2087
|
+
context: context,
|
|
2088
|
+
settings: settings,
|
|
2089
|
+
safeTags: this._safeTags
|
|
2090
|
+
});
|
|
2091
|
+
},
|
|
2092
|
+
settings: function settings() {
|
|
2093
|
+
var settings = {};
|
|
2094
|
+
getLocales().forEach(function (locale) {
|
|
2095
|
+
settings[locale] = deepCopy(getData(locale + '/quote'));
|
|
2096
|
+
});
|
|
2097
|
+
return settings;
|
|
2098
|
+
}
|
|
2099
|
+
};
|
|
2100
|
+
|
|
2101
|
+
var quoteLink = {
|
|
2102
|
+
name: 'common/punctuation/quoteLink',
|
|
2103
|
+
queue: 'show-safe-tags-html',
|
|
2104
|
+
index: '+5',
|
|
2105
|
+
handler: function handler(text, settings, context) {
|
|
2106
|
+
var quotes = this.getSetting('common/punctuation/quote', context.prefs.locale[0]);
|
|
2107
|
+
|
|
2108
|
+
if (!quotes) {
|
|
2109
|
+
return text;
|
|
2110
|
+
}
|
|
2111
|
+
|
|
2112
|
+
var lquote1 = HtmlEntities$1.getByUtf(quotes.left[0]);
|
|
2113
|
+
var rquote1 = HtmlEntities$1.getByUtf(quotes.right[0]);
|
|
2114
|
+
var lquote2 = HtmlEntities$1.getByUtf(quotes.left[1]);
|
|
2115
|
+
var rquote2 = HtmlEntities$1.getByUtf(quotes.right[1]);
|
|
2116
|
+
lquote2 = lquote2 ? '|' + lquote2 : '';
|
|
2117
|
+
rquote2 = rquote2 ? '|' + rquote2 : '';
|
|
2118
|
+
var re = new RegExp('(<[aA]\\s[^>]*?>)(' + lquote1 + lquote2 + ')([^]*?)(' + rquote1 + rquote2 + ')(</[aA]>)', 'g');
|
|
2119
|
+
return text.replace(re, '$2$1$3$5$4');
|
|
2120
|
+
}
|
|
2121
|
+
};
|
|
2122
|
+
|
|
2123
|
+
Typograf.addRules([apostrophe, delDoublePunctuation, hellip, quote, quoteLink]);
|
|
2124
|
+
|
|
2125
|
+
var beforeBracket = {
|
|
2126
|
+
name: 'common/space/beforeBracket',
|
|
2127
|
+
handler: function handler(text, settings, context) {
|
|
2128
|
+
var re = new RegExp('([' + context.getData('char') + '.!?,;…)])\\(', 'gi');
|
|
2129
|
+
return text.replace(re, '$1 (');
|
|
2130
|
+
}
|
|
2131
|
+
};
|
|
2132
|
+
|
|
2133
|
+
var bracket = {
|
|
2134
|
+
name: 'common/space/bracket',
|
|
2135
|
+
handler: function handler(text) {
|
|
2136
|
+
return text.replace(/(\() +/g, '(').replace(/ +\)/g, ')');
|
|
2137
|
+
}
|
|
2138
|
+
};
|
|
2139
|
+
|
|
2140
|
+
var delBeforePercent = {
|
|
2141
|
+
name: 'common/space/delBeforePercent',
|
|
2142
|
+
handler: function handler(text) {
|
|
2143
|
+
return text.replace(/(\d)( |\u00A0)(%|‰|‱)/g, '$1$3');
|
|
2144
|
+
}
|
|
2145
|
+
};
|
|
2146
|
+
|
|
2147
|
+
var delBeforePunctuation = {
|
|
2148
|
+
name: 'common/space/delBeforePunctuation',
|
|
2149
|
+
handler: function handler(text) {
|
|
2150
|
+
return text.replace(/(^|[^!?:;,.…]) ([!?:;,])(?!\))/g, '$1$2');
|
|
2151
|
+
}
|
|
2152
|
+
};
|
|
2153
|
+
|
|
2154
|
+
var delBetweenExclamationMarks = {
|
|
2155
|
+
name: 'common/space/delBetweenExclamationMarks',
|
|
2156
|
+
handler: function handler(text) {
|
|
2157
|
+
return text.replace(/([!?]) (?=[!?])/g, '$1');
|
|
2158
|
+
}
|
|
2159
|
+
};
|
|
2160
|
+
|
|
2161
|
+
var delBeforeDot = {
|
|
2162
|
+
name: 'common/space/delBeforeDot',
|
|
2163
|
+
handler: function handler(text) {
|
|
2164
|
+
return text.replace(/(^|[^!?:;,.…]) (\.|\.\.\.)(\s|$)/g, '$1$2$3');
|
|
2165
|
+
}
|
|
2166
|
+
};
|
|
2167
|
+
|
|
2168
|
+
var delLeadingBlanks = {
|
|
2169
|
+
name: 'common/space/delLeadingBlanks',
|
|
2170
|
+
handler: function handler(text) {
|
|
2171
|
+
return text.replace(/^[ \t]+/mg, '');
|
|
2172
|
+
},
|
|
2173
|
+
disabled: true
|
|
2174
|
+
};
|
|
2175
|
+
|
|
2176
|
+
var delRepeatN = {
|
|
2177
|
+
name: 'common/space/delRepeatN',
|
|
2178
|
+
index: '-1',
|
|
2179
|
+
handler: function handler(text, settings) {
|
|
2180
|
+
var maxConsecutiveLineBreaks = settings.maxConsecutiveLineBreaks;
|
|
2181
|
+
var consecutiveLineBreaksRegex = new RegExp("\n{".concat(maxConsecutiveLineBreaks + 1, ",}"), 'g');
|
|
2182
|
+
var replaceValue = repeat('\n', maxConsecutiveLineBreaks);
|
|
2183
|
+
return text.replace(consecutiveLineBreaksRegex, replaceValue);
|
|
2184
|
+
},
|
|
2185
|
+
settings: {
|
|
2186
|
+
maxConsecutiveLineBreaks: 2
|
|
2187
|
+
}
|
|
2188
|
+
};
|
|
2189
|
+
|
|
2190
|
+
var delRepeatSpace = {
|
|
2191
|
+
name: 'common/space/delRepeatSpace',
|
|
2192
|
+
index: '-1',
|
|
2193
|
+
handler: function handler(text) {
|
|
2194
|
+
return text.replace(/([^\n \t])[ \t]{2,}(?![\n \t])/g, '$1 ');
|
|
2195
|
+
}
|
|
2196
|
+
};
|
|
2197
|
+
|
|
2198
|
+
var delTrailingBlanks = {
|
|
2199
|
+
name: 'common/space/delTrailingBlanks',
|
|
2200
|
+
index: '-3',
|
|
2201
|
+
handler: function handler(text) {
|
|
2202
|
+
return text.replace(/[ \t]+\n/g, '\n');
|
|
2203
|
+
}
|
|
2204
|
+
};
|
|
2205
|
+
|
|
2206
|
+
var insertFinalNewline = {
|
|
2207
|
+
name: 'common/space/insertFinalNewline',
|
|
2208
|
+
live: false,
|
|
2209
|
+
disabled: true,
|
|
2210
|
+
queue: 'end',
|
|
2211
|
+
handler: function handler(text) {
|
|
2212
|
+
return text[text.length - 1] === '\n' ? text : text + '\n';
|
|
2213
|
+
}
|
|
2214
|
+
};
|
|
2215
|
+
|
|
2216
|
+
var replaceTab = {
|
|
2217
|
+
name: 'common/space/replaceTab',
|
|
2218
|
+
index: '-5',
|
|
2219
|
+
handler: function handler(text) {
|
|
2220
|
+
return text.replace(/\t/g, ' ');
|
|
2221
|
+
}
|
|
2222
|
+
};
|
|
2223
|
+
|
|
2224
|
+
var squareBracket = {
|
|
2225
|
+
name: 'common/space/squareBracket',
|
|
2226
|
+
handler: function handler(text) {
|
|
2227
|
+
return text.replace(/(\[) +/g, '[').replace(/ +\]/g, ']');
|
|
2228
|
+
}
|
|
2229
|
+
};
|
|
2230
|
+
|
|
2231
|
+
var trimLeft = {
|
|
2232
|
+
name: 'common/space/trimLeft',
|
|
2233
|
+
index: '-4',
|
|
2234
|
+
handler: String.prototype.trimLeft ? function (text) {
|
|
2235
|
+
return text.trimLeft();
|
|
2236
|
+
} :
|
|
2237
|
+
/* istanbul ignore next */
|
|
2238
|
+
function (text) {
|
|
2239
|
+
return text.replace(/^[\s\uFEFF\xA0]+/g, '');
|
|
2240
|
+
}
|
|
2241
|
+
};
|
|
2242
|
+
|
|
2243
|
+
var trimRight = {
|
|
2244
|
+
name: 'common/space/trimRight',
|
|
2245
|
+
index: '-3',
|
|
2246
|
+
live: false,
|
|
2247
|
+
handler: String.prototype.trimRight ? function (text) {
|
|
2248
|
+
return text.trimRight();
|
|
2249
|
+
} :
|
|
2250
|
+
/* istanbul ignore next */
|
|
2251
|
+
function (text) {
|
|
2252
|
+
return text.replace(/[\s\uFEFF\xA0]+$/g, '');
|
|
2253
|
+
}
|
|
2254
|
+
};
|
|
2255
|
+
|
|
2256
|
+
var reColon = new RegExp('(\\D):([^)",:.?\\s\\/\\\\' + privateLabel + '])', 'g');
|
|
2257
|
+
var afterColon = {
|
|
2258
|
+
name: 'common/space/afterColon',
|
|
2259
|
+
handler: function handler(text) {
|
|
2260
|
+
return text.replace(reColon, '$1: $2');
|
|
2261
|
+
}
|
|
2262
|
+
};
|
|
2263
|
+
|
|
2264
|
+
var reComma = new RegExp('(.),([^)",:.?\\s\\/\\\\' + privateLabel + '])', 'g');
|
|
2265
|
+
var afterComma = {
|
|
2266
|
+
name: 'common/space/afterComma',
|
|
2267
|
+
handler: function handler(text) {
|
|
2268
|
+
return text.replace(reComma, function ($0, $1, $2) {
|
|
2269
|
+
return isDigit($1) && isDigit($2) ? $0 : $1 + ', ' + $2;
|
|
2270
|
+
});
|
|
2271
|
+
}
|
|
2272
|
+
};
|
|
2273
|
+
|
|
2274
|
+
var reQuestionMark = new RegExp('\\?([^).…!;?\\s[\\])' + privateLabel + getData('common/quote') + '])', 'g');
|
|
2275
|
+
var afterQuestionMark = {
|
|
2276
|
+
name: 'common/space/afterQuestionMark',
|
|
2277
|
+
handler: function handler(text) {
|
|
2278
|
+
return text.replace(reQuestionMark, '? $1');
|
|
2279
|
+
}
|
|
2280
|
+
};
|
|
2281
|
+
|
|
2282
|
+
var reExclamationMark = new RegExp('!([^).…!;?\\s[\\])' + privateLabel + getData('common/quote') + '])', 'g');
|
|
2283
|
+
var afterExclamationMark = {
|
|
2284
|
+
name: 'common/space/afterExclamationMark',
|
|
2285
|
+
handler: function handler(text) {
|
|
2286
|
+
return text.replace(reExclamationMark, '! $1');
|
|
2287
|
+
}
|
|
2288
|
+
};
|
|
2289
|
+
|
|
2290
|
+
var reSemicolon = new RegExp(';([^).…!;?\\s[\\])' + privateLabel + getData('common/quote') + '])', 'g');
|
|
2291
|
+
var afterSemicolon = {
|
|
2292
|
+
name: 'common/space/afterSemicolon',
|
|
2293
|
+
handler: function handler(text) {
|
|
2294
|
+
return text.replace(reSemicolon, '; $1');
|
|
2295
|
+
}
|
|
2296
|
+
};
|
|
2297
|
+
|
|
2298
|
+
Typograf.addRules([afterColon, afterComma, afterQuestionMark, afterExclamationMark, afterSemicolon, beforeBracket, bracket, delBeforeDot, delBeforePercent, delBeforePunctuation, delBetweenExclamationMarks, delLeadingBlanks, delRepeatN, delRepeatSpace, delTrailingBlanks, insertFinalNewline, replaceTab, squareBracket, trimLeft, trimRight]);
|
|
2299
|
+
|
|
2300
|
+
var arrow = {
|
|
2301
|
+
name: 'common/symbols/arrow',
|
|
2302
|
+
handler: function handler(text) {
|
|
2303
|
+
return replace(text, [[/(^|[^-])->(?!>)/g, '$1→'], [/(^|[^<])<-(?!-)/g, '$1←']]);
|
|
2304
|
+
}
|
|
2305
|
+
};
|
|
2306
|
+
|
|
2307
|
+
var cf = {
|
|
2308
|
+
name: 'common/symbols/cf',
|
|
2309
|
+
handler: function handler(text) {
|
|
2310
|
+
var re = new RegExp("(^|[\\s(\\[+\u2248\xB1\u2212\u2014\u2013\\-])(\\d+(?:[.,]\\d+)?)[ \xA0\u2009]?(C|F)([\\W\\s.,:!?\")\\]]|$)", 'mg');
|
|
2311
|
+
return text.replace(re, "$1$2\u2009\xB0$3$4");
|
|
2312
|
+
}
|
|
2313
|
+
};
|
|
2314
|
+
|
|
2315
|
+
var copy = {
|
|
2316
|
+
name: 'common/symbols/copy',
|
|
2317
|
+
handler: function handler(text) {
|
|
2318
|
+
return replace(text, [[/\(r\)/gi, '®'], [/(copyright )?\((c|с)\)/gi, '©'], [/\(tm\)/gi, '™']]);
|
|
2319
|
+
}
|
|
2320
|
+
};
|
|
2321
|
+
|
|
2322
|
+
Typograf.addRules([arrow, cf, copy]);
|
|
2323
|
+
|
|
2324
|
+
var main = {
|
|
2325
|
+
name: 'en-US/dash/main',
|
|
2326
|
+
index: '-5',
|
|
2327
|
+
handler: function handler(text) {
|
|
2328
|
+
var dashes = getData('common/dash');
|
|
2329
|
+
var nonBreakingSpace = "\xA0";
|
|
2330
|
+
var emDash = "\u2014";
|
|
2331
|
+
var spaceBefore = "[ ".concat(nonBreakingSpace, "]"); // white space or a non-breaking space
|
|
2332
|
+
|
|
2333
|
+
var spaceAfter = "[ ".concat(nonBreakingSpace, "\n]"); // same as spaceBefore, but includes line break
|
|
2334
|
+
|
|
2335
|
+
var re = new RegExp("".concat(spaceBefore, "(").concat(dashes, ")(").concat(spaceAfter, ")"), 'g');
|
|
2336
|
+
return text.replace(re, "".concat(nonBreakingSpace).concat(emDash, "$2"));
|
|
2337
|
+
}
|
|
2338
|
+
};
|
|
2339
|
+
|
|
2340
|
+
Typograf.addRules([main]);
|
|
2341
|
+
|
|
2342
|
+
var centuries = {
|
|
2343
|
+
name: 'ru/dash/centuries',
|
|
2344
|
+
handler: function handler(text, settings) {
|
|
2345
|
+
var dashes = '(' + getData('common/dash') + ')';
|
|
2346
|
+
var re = new RegExp("(X|I|V)[ |\xA0]?" + dashes + "[ |\xA0]?(X|I|V)", 'g');
|
|
2347
|
+
return text.replace(re, '$1' + settings.dash + '$3');
|
|
2348
|
+
},
|
|
2349
|
+
settings: {
|
|
2350
|
+
dash: "\u2013" // –
|
|
2351
|
+
|
|
2352
|
+
}
|
|
2353
|
+
};
|
|
2354
|
+
|
|
2355
|
+
var daysMonth = {
|
|
2356
|
+
name: 'ru/dash/daysMonth',
|
|
2357
|
+
handler: function handler(text, settings) {
|
|
2358
|
+
var re = new RegExp('(^|\\s)([123]?\\d)' + '(' + getData('common/dash') + ')' + "([123]?\\d)[ \xA0]" + '(' + getData('ru/monthGenCase') + ')', 'g');
|
|
2359
|
+
return text.replace(re, '$1$2' + settings.dash + "$4\xA0$5");
|
|
2360
|
+
},
|
|
2361
|
+
settings: {
|
|
2362
|
+
dash: "\u2013" // –
|
|
2363
|
+
|
|
2364
|
+
}
|
|
2365
|
+
};
|
|
2366
|
+
|
|
2367
|
+
var de$1 = {
|
|
2368
|
+
name: 'ru/dash/de',
|
|
2369
|
+
handler: function handler(text) {
|
|
2370
|
+
var re = new RegExp('([a-яё]+) де' + getData('ru/dashAfterDe'), 'g');
|
|
2371
|
+
return text.replace(re, '$1-де');
|
|
2372
|
+
},
|
|
2373
|
+
disabled: true
|
|
2374
|
+
};
|
|
2375
|
+
|
|
2376
|
+
var decade = {
|
|
2377
|
+
name: 'ru/dash/decade',
|
|
2378
|
+
handler: function handler(text, settings) {
|
|
2379
|
+
var re = new RegExp('(^|\\s)(\\d{3}|\\d)0' + '(' + getData('common/dash') + ')' + "(\\d{3}|\\d)0(-\u0435[ \xA0])" + "(?=\u0433\\.?[ \xA0]?\u0433|\u0433\u043E\u0434)", 'g');
|
|
2380
|
+
return text.replace(re, '$1$20' + settings.dash + '$40$5');
|
|
2381
|
+
},
|
|
2382
|
+
settings: {
|
|
2383
|
+
dash: "\u2013" // –
|
|
2384
|
+
|
|
2385
|
+
}
|
|
2386
|
+
};
|
|
2387
|
+
|
|
2388
|
+
var directSpeech = {
|
|
2389
|
+
name: 'ru/dash/directSpeech',
|
|
2390
|
+
handler: function handler(text) {
|
|
2391
|
+
var dashes = getData('common/dash');
|
|
2392
|
+
var re1 = new RegExp("([\"\xBB\u2018\u201C,])[ |\xA0]?(".concat(dashes, ")[ |\xA0]"), 'g');
|
|
2393
|
+
var re2 = new RegExp("(^|".concat(privateLabel, ")(").concat(dashes, ")( |\xA0)"), 'gm');
|
|
2394
|
+
var re3 = new RegExp("([.\u2026?!])[ \xA0](".concat(dashes, ")[ \xA0]"), 'g');
|
|
2395
|
+
return text.replace(re1, "$1\xA0\u2014 ").replace(re2, "$1\u2014\xA0").replace(re3, "$1 \u2014\xA0");
|
|
2396
|
+
}
|
|
2397
|
+
};
|
|
2398
|
+
|
|
2399
|
+
var izpod = {
|
|
2400
|
+
name: 'ru/dash/izpod',
|
|
2401
|
+
handler: function handler(text) {
|
|
2402
|
+
var re = new RegExp(getData('ru/dashBefore') + '(И|и)з под' + getData('ru/dashAfter'), 'g');
|
|
2403
|
+
return text.replace(re, '$1$2з-под');
|
|
2404
|
+
}
|
|
2405
|
+
};
|
|
2406
|
+
|
|
2407
|
+
var izza = {
|
|
2408
|
+
name: 'ru/dash/izza',
|
|
2409
|
+
handler: function handler(text) {
|
|
2410
|
+
var re = new RegExp(getData('ru/dashBefore') + '(И|и)з за' + getData('ru/dashAfter'), 'g');
|
|
2411
|
+
return text.replace(re, '$1$2з-за');
|
|
2412
|
+
}
|
|
2413
|
+
};
|
|
2414
|
+
|
|
2415
|
+
var ka = {
|
|
2416
|
+
name: 'ru/dash/ka',
|
|
2417
|
+
handler: function handler(text) {
|
|
2418
|
+
var re = new RegExp('([a-яё]+) ка(сь)?' + getData('ru/dashAfter'), 'g');
|
|
2419
|
+
return text.replace(re, '$1-ка$2');
|
|
2420
|
+
}
|
|
2421
|
+
};
|
|
2422
|
+
|
|
2423
|
+
var koe = {
|
|
2424
|
+
name: 'ru/dash/koe',
|
|
2425
|
+
handler: function handler(text) {
|
|
2426
|
+
var re = new RegExp(getData('ru/dashBefore') + '([Кк]о[ей])\\s([а-яё]{3,})' + getData('ru/dashAfter'), 'g');
|
|
2427
|
+
return text.replace(re, '$1$2-$3');
|
|
2428
|
+
}
|
|
2429
|
+
};
|
|
2430
|
+
|
|
2431
|
+
var main$1 = {
|
|
2432
|
+
name: 'ru/dash/main',
|
|
2433
|
+
index: '-5',
|
|
2434
|
+
handler: function handler(text) {
|
|
2435
|
+
var dashes = getData('common/dash');
|
|
2436
|
+
var re = new RegExp("([ \xA0])(" + dashes + ")([ \xA0\\n])", 'g');
|
|
2437
|
+
return text.replace(re, "\xA0\u2014$3");
|
|
2438
|
+
}
|
|
2439
|
+
};
|
|
2440
|
+
|
|
2441
|
+
var month = {
|
|
2442
|
+
name: 'ru/dash/month',
|
|
2443
|
+
handler: function handler(text, settings) {
|
|
2444
|
+
var months = '(' + getData('ru/month') + ')';
|
|
2445
|
+
var monthsPre = '(' + getData('ru/monthPreCase') + ')';
|
|
2446
|
+
var dashes = getData('common/dash');
|
|
2447
|
+
var re = new RegExp(months + ' ?(' + dashes + ') ?' + months, 'gi');
|
|
2448
|
+
var rePre = new RegExp(monthsPre + ' ?(' + dashes + ') ?' + monthsPre, 'gi');
|
|
2449
|
+
var newSubStr = '$1' + settings.dash + '$3';
|
|
2450
|
+
return text.replace(re, newSubStr).replace(rePre, newSubStr);
|
|
2451
|
+
},
|
|
2452
|
+
settings: {
|
|
2453
|
+
dash: "\u2013" // –
|
|
2454
|
+
|
|
2455
|
+
}
|
|
2456
|
+
};
|
|
2457
|
+
|
|
2458
|
+
var surname = {
|
|
2459
|
+
name: 'ru/dash/surname',
|
|
2460
|
+
handler: function handler(text) {
|
|
2461
|
+
var re = new RegExp('([А-ЯЁ][а-яё]+)\\s-([а-яё]{1,3})(?![^а-яё]|$)', 'g');
|
|
2462
|
+
return text.replace(re, "$1\xA0\u2014$2");
|
|
2463
|
+
}
|
|
2464
|
+
};
|
|
2465
|
+
|
|
2466
|
+
var taki = {
|
|
2467
|
+
name: 'ru/dash/taki',
|
|
2468
|
+
handler: function handler(text) {
|
|
2469
|
+
var re = new RegExp('(верно|довольно|опять|прямо|так|вс[её]|действительно|неужели)\\s(таки)' + getData('ru/dashAfter'), 'g');
|
|
2470
|
+
return text.replace(re, '$1-$2');
|
|
2471
|
+
}
|
|
2472
|
+
};
|
|
2473
|
+
|
|
2474
|
+
var time = {
|
|
2475
|
+
name: 'ru/dash/time',
|
|
2476
|
+
handler: function handler(text, settings) {
|
|
2477
|
+
var re = new RegExp(getData('ru/dashBefore') + '(\\d?\\d:[0-5]\\d)' + getData('common/dash') + '(\\d?\\d:[0-5]\\d)' + getData('ru/dashAfter'), 'g');
|
|
2478
|
+
return text.replace(re, '$1$2' + settings.dash + '$3');
|
|
2479
|
+
},
|
|
2480
|
+
settings: {
|
|
2481
|
+
dash: "\u2013" // –
|
|
2482
|
+
|
|
2483
|
+
}
|
|
2484
|
+
};
|
|
2485
|
+
|
|
2486
|
+
var to = {
|
|
2487
|
+
name: 'ru/dash/to',
|
|
2488
|
+
handler: function handler(text) {
|
|
2489
|
+
var words = '[Оо]ткуда|[Кк]уда|[Гг]де|[Кк]огда|[Зз]ачем|[Пп]очему|[Кк]ак|[Кк]ако[ейм]|[Кк]акая|[Кк]аки[емх]|[Кк]акими|[Кк]акую|[Чч]то|[Чч]его|[Чч]е[йм]|[Чч]ьим?|[Кк]то|[Кк]ого|[Кк]ому|[Кк]ем';
|
|
2490
|
+
var re = new RegExp('(^|[^А-ЯЁа-яё\\w])(' + words + ')( | -|- )(то|либо|нибудь)' + getData('ru/dashAfter'), 'g');
|
|
2491
|
+
return text.replace(re, function ($0, $1, $2, $3, $4) {
|
|
2492
|
+
var kakto = $2 + $3 + $4; // Отдельно обрабатываем в ru/dash/kakto
|
|
2493
|
+
|
|
2494
|
+
if (kakto === 'как то' || kakto === 'Как то') {
|
|
2495
|
+
return $0;
|
|
2496
|
+
}
|
|
2497
|
+
|
|
2498
|
+
return $1 + $2 + '-' + $4;
|
|
2499
|
+
});
|
|
2500
|
+
}
|
|
2501
|
+
};
|
|
2502
|
+
|
|
2503
|
+
var kakto = {
|
|
2504
|
+
name: 'ru/dash/kakto',
|
|
2505
|
+
handler: function handler(text) {
|
|
2506
|
+
var re = new RegExp('(^|[^А-ЯЁа-яё\\w])([Кк]ак) то' + getData('ru/dashAfter'), 'g');
|
|
2507
|
+
return text.replace(re, '$1$2-то');
|
|
2508
|
+
}
|
|
2509
|
+
};
|
|
2510
|
+
|
|
2511
|
+
var weekday = {
|
|
2512
|
+
name: 'ru/dash/weekday',
|
|
2513
|
+
handler: function handler(text, settings) {
|
|
2514
|
+
var part = '(' + getData('ru/weekday') + ')';
|
|
2515
|
+
var re = new RegExp(part + ' ?(' + getData('common/dash') + ') ?' + part, 'gi');
|
|
2516
|
+
return text.replace(re, '$1' + settings.dash + '$3');
|
|
2517
|
+
},
|
|
2518
|
+
settings: {
|
|
2519
|
+
dash: "\u2013" // –
|
|
2520
|
+
|
|
2521
|
+
}
|
|
2522
|
+
};
|
|
2523
|
+
|
|
2524
|
+
var years = {
|
|
2525
|
+
name: 'ru/dash/years',
|
|
2526
|
+
handler: function handler(text, settings) {
|
|
2527
|
+
var dashes = getData('common/dash');
|
|
2528
|
+
var re = new RegExp("(\\D|^)(\\d{4})[ \xA0]?(" + dashes + ")[ \xA0]?(\\d{4})(?=[ \xA0]?\u0433)", 'g');
|
|
2529
|
+
return text.replace(re, function ($0, $1, $2, $3, $4) {
|
|
2530
|
+
if (parseInt($2, 10) < parseInt($4, 10)) {
|
|
2531
|
+
return $1 + $2 + settings.dash + $4;
|
|
2532
|
+
}
|
|
2533
|
+
|
|
2534
|
+
return $0;
|
|
2535
|
+
});
|
|
2536
|
+
},
|
|
2537
|
+
settings: {
|
|
2538
|
+
dash: "\u2013" // –
|
|
2539
|
+
|
|
2540
|
+
}
|
|
2541
|
+
};
|
|
2542
|
+
|
|
2543
|
+
Typograf.addRules([centuries, daysMonth, de$1, decade, directSpeech, izpod, izza, ka, koe, main$1, month, surname, taki, time, to, kakto, weekday, years]);
|
|
2544
|
+
|
|
2545
|
+
var fromISO = {
|
|
2546
|
+
name: 'ru/date/fromISO',
|
|
2547
|
+
handler: function handler(text) {
|
|
2548
|
+
var sp1 = '(-|\\.|\\/)';
|
|
2549
|
+
var sp2 = '(-|\\/)';
|
|
2550
|
+
var re1 = new RegExp('(^|\\D)(\\d{4})' + sp1 + '(\\d{2})' + sp1 + '(\\d{2})(\\D|$)', 'gi');
|
|
2551
|
+
var re2 = new RegExp('(^|\\D)(\\d{2})' + sp2 + '(\\d{2})' + sp2 + '(\\d{4})(\\D|$)', 'gi');
|
|
2552
|
+
return text.replace(re1, '$1$6.$4.$2$7').replace(re2, '$1$4.$2.$6$7');
|
|
2553
|
+
}
|
|
2554
|
+
};
|
|
2555
|
+
|
|
2556
|
+
var weekday$1 = {
|
|
2557
|
+
name: 'ru/date/weekday',
|
|
2558
|
+
handler: function handler(text) {
|
|
2559
|
+
var space = "( |\xA0)";
|
|
2560
|
+
var monthCase = getData('ru/monthGenCase');
|
|
2561
|
+
var weekday = getData('ru/weekday');
|
|
2562
|
+
var re = new RegExp('(\\d)' + space + '(' + monthCase + '),' + space + '(' + weekday + ')', 'gi');
|
|
2563
|
+
return text.replace(re, function () {
|
|
2564
|
+
var a = arguments;
|
|
2565
|
+
return a[1] + a[2] + a[3].toLowerCase() + ',' + a[4] + a[5].toLowerCase();
|
|
2566
|
+
});
|
|
2567
|
+
}
|
|
2568
|
+
};
|
|
2569
|
+
|
|
2570
|
+
Typograf.addRules([fromISO, weekday$1]);
|
|
2571
|
+
|
|
2572
|
+
var currency = {
|
|
2573
|
+
name: 'ru/money/currency',
|
|
2574
|
+
handler: function handler(text) {
|
|
2575
|
+
var currency = '([$€¥Ұ£₤₽])';
|
|
2576
|
+
var space = "[ \xA0\u2009\u202F]";
|
|
2577
|
+
var re1 = new RegExp('(^|[\\D]{2})' + currency + ' ?(' + regExpNumber + '(' + space + '\\d{3})*)(' + space + '?(тыс\\.|млн|млрд|трлн))?', 'gm');
|
|
2578
|
+
var re2 = new RegExp('(^|[\\D])(' + regExpNumber + ') ?' + currency, 'gm');
|
|
2579
|
+
return text.replace(re1, function ($0, $1, $2, $3, $4, $5, $6, $7) {
|
|
2580
|
+
return $1 + $3 + ($7 ? "\xA0" + $7 : '') + "\xA0" + $2;
|
|
2581
|
+
}).replace(re2, "$1$2\xA0$4");
|
|
2582
|
+
},
|
|
2583
|
+
disabled: true
|
|
2584
|
+
};
|
|
2585
|
+
|
|
2586
|
+
var ruble = {
|
|
2587
|
+
name: 'ru/money/ruble',
|
|
2588
|
+
handler: function handler(text) {
|
|
2589
|
+
var newSubstr = "$1\xA0\u20BD";
|
|
2590
|
+
var commonPart = "(\\d+)( |\xA0)?(\u0440|\u0440\u0443\u0431)\\.";
|
|
2591
|
+
var re1 = new RegExp('^' + commonPart + '$', 'g');
|
|
2592
|
+
var re2 = new RegExp(commonPart + '(?=[!?,:;])', 'g');
|
|
2593
|
+
var re3 = new RegExp(commonPart + '(?=\\s+[A-ЯЁ])', 'g');
|
|
2594
|
+
return text.replace(re1, newSubstr).replace(re2, newSubstr).replace(re3, newSubstr + '.');
|
|
2595
|
+
},
|
|
2596
|
+
disabled: true
|
|
2597
|
+
};
|
|
2598
|
+
|
|
2599
|
+
Typograf.addRules([currency, ruble]);
|
|
2600
|
+
|
|
2601
|
+
var abbr = {
|
|
2602
|
+
name: 'ru/nbsp/abbr',
|
|
2603
|
+
handler: function handler(text) {
|
|
2604
|
+
function abbr($0, $1, $2, $3) {
|
|
2605
|
+
// дд.мм.гггг
|
|
2606
|
+
if ($2 === 'дд' && $3 === 'мм') {
|
|
2607
|
+
return $0;
|
|
2608
|
+
} // Являются ли сокращения ссылкой
|
|
2609
|
+
|
|
2610
|
+
|
|
2611
|
+
if (['рф', 'ру', 'рус', 'орг', 'укр', 'бг', 'срб'].indexOf($3) > -1) {
|
|
2612
|
+
return $0;
|
|
2613
|
+
}
|
|
2614
|
+
|
|
2615
|
+
return $1 + $2 + '.' + "\xA0" + $3 + '.';
|
|
2616
|
+
}
|
|
2617
|
+
|
|
2618
|
+
var re = new RegExp("(^|\\s|".concat(privateLabel, ")([\u0430-\u044F\u0451]{1,3})\\. ?([\u0430-\u044F\u0451]{1,3})\\."), 'g');
|
|
2619
|
+
return text.replace(re, abbr) // Для тройных сокращений - а.е.м.
|
|
2620
|
+
.replace(re, abbr);
|
|
2621
|
+
}
|
|
2622
|
+
};
|
|
2623
|
+
|
|
2624
|
+
var addr = {
|
|
2625
|
+
name: 'ru/nbsp/addr',
|
|
2626
|
+
handler: function handler(text) {
|
|
2627
|
+
return text.replace(/(\s|^)(дом|д\.|кв\.|под\.|п-д) *(\d+)/gi, "$1$2\xA0$3").replace(/(\s|^)(мкр-н|мк-н|мкр\.|мкрн)\s/gi, "$1$2\xA0") // микрорайон
|
|
2628
|
+
.replace(/(\s|^)(эт\.) *(-?\d+)/gi, "$1$2\xA0$3").replace(/(\s|^)(\d+) +этаж([^а-яё]|$)/gi, "$1$2\xA0\u044D\u0442\u0430\u0436$3").replace(/(\s|^)литер\s([А-Я]|$)/gi, "$1\u043B\u0438\u0442\u0435\u0440\xA0$2")
|
|
2629
|
+
/*
|
|
2630
|
+
область, край, станция, поселок, село,
|
|
2631
|
+
деревня, улица, переулок, проезд, проспект,
|
|
2632
|
+
бульвар, площадь, набережная, шоссе,
|
|
2633
|
+
тупик, офис, комната, участок, владение, строение, корпус
|
|
2634
|
+
*/
|
|
2635
|
+
.replace(/(\s|^)(обл|кр|ст|пос|с|д|ул|пер|пр|пр-т|просп|пл|бул|б-р|наб|ш|туп|оф|комн?|уч|вл|влад|стр|кор)\. *([а-яёa-z\d]+)/gi, "$1$2.\xA0$3") // город
|
|
2636
|
+
.replace(/(\D[ \u00A0]|^)г\. ?([А-ЯЁ])/gm, "$1\u0433.\xA0$2");
|
|
2637
|
+
}
|
|
2638
|
+
};
|
|
2639
|
+
|
|
2640
|
+
var afterNumberSign = {
|
|
2641
|
+
name: 'ru/nbsp/afterNumberSign',
|
|
2642
|
+
handler: function handler(text) {
|
|
2643
|
+
// \u2009 - THIN SPACE
|
|
2644
|
+
// \u202F - NARROW NO-BREAK SPACE
|
|
2645
|
+
return text.replace(/№[ \u00A0\u2009]?(\d|п\/п)/g, "\u2116\u202F$1");
|
|
2646
|
+
}
|
|
2647
|
+
};
|
|
2648
|
+
|
|
2649
|
+
var beforeParticle = {
|
|
2650
|
+
name: 'ru/nbsp/beforeParticle',
|
|
2651
|
+
index: '+5',
|
|
2652
|
+
handler: function handler(text) {
|
|
2653
|
+
var particles = '(ли|ль|же|ж|бы|б)';
|
|
2654
|
+
var re1 = new RegExp('([А-ЯЁа-яё]) ' + particles + '(?=[,;:?!"‘“»])', 'g');
|
|
2655
|
+
var re2 = new RegExp("([\u0410-\u042F\u0401\u0430-\u044F\u0451])[ \xA0]" + particles + "[ \xA0]", 'g');
|
|
2656
|
+
return text.replace(re1, "$1\xA0$2").replace(re2, "$1\xA0$2 ");
|
|
2657
|
+
}
|
|
2658
|
+
};
|
|
2659
|
+
|
|
2660
|
+
var centuries$1 = {
|
|
2661
|
+
name: 'ru/nbsp/centuries',
|
|
2662
|
+
handler: function handler(text) {
|
|
2663
|
+
var dashes = getData('common/dash');
|
|
2664
|
+
var before = '(^|\\s)([VIX]+)';
|
|
2665
|
+
var after = '(?=[,;:?!"‘“»]|$)';
|
|
2666
|
+
var re1 = new RegExp(before + "[ \xA0]?\u0432\\.?" + after, 'gm');
|
|
2667
|
+
var re2 = new RegExp(before + '(' + dashes + ')' + "([VIX]+)[ \xA0]?\u0432\\.?([ \xA0]?\u0432\\.?)?" + after, 'gm');
|
|
2668
|
+
return text.replace(re1, "$1$2\xA0\u0432.").replace(re2, "$1$2$3$4\xA0\u0432\u0432.");
|
|
2669
|
+
}
|
|
2670
|
+
};
|
|
2671
|
+
|
|
2672
|
+
var dayMonth = {
|
|
2673
|
+
name: 'ru/nbsp/dayMonth',
|
|
2674
|
+
handler: function handler(text) {
|
|
2675
|
+
var re = new RegExp('(\\d{1,2}) (' + getData('ru/shortMonth') + ')', 'gi');
|
|
2676
|
+
return text.replace(re, "$1\xA0$2");
|
|
2677
|
+
}
|
|
2678
|
+
};
|
|
2679
|
+
|
|
2680
|
+
var initials = {
|
|
2681
|
+
name: 'ru/nbsp/initials',
|
|
2682
|
+
handler: function handler(text) {
|
|
2683
|
+
var spaces = "\xA0\u202F "; // nbsp, thinsp
|
|
2684
|
+
|
|
2685
|
+
var quote = getData('ru/quote');
|
|
2686
|
+
var re = new RegExp('(^|[' + spaces + quote.left + privateLabel + '"])([А-ЯЁ])\\.[' + spaces + ']?([А-ЯЁ])\\.[' + spaces + ']?([А-ЯЁ][а-яё]+)', 'gm');
|
|
2687
|
+
return text.replace(re, "$1$2.\xA0$3.\xA0$4");
|
|
2688
|
+
}
|
|
2689
|
+
};
|
|
2690
|
+
|
|
2691
|
+
var m = {
|
|
2692
|
+
name: 'ru/nbsp/m',
|
|
2693
|
+
index: '+5',
|
|
2694
|
+
handler: function handler(text) {
|
|
2695
|
+
var re = new RegExp('(^|[\\s,.\\(' + privateLabel + '])' + "(\\d+)[ \xA0]?(\u043C\u043C?|\u0441\u043C|\u043A\u043C|\u0434\u043C|\u0433\u043C|mm?|km|cm|dm)([23\xB2\xB3])?([\\s\\).!?,;" + privateLabel + ']|$)', 'gm');
|
|
2696
|
+
return text.replace(re, function ($0, $1, $2, $3, $4, $5) {
|
|
2697
|
+
var pow = {
|
|
2698
|
+
'2': '²',
|
|
2699
|
+
'²': '²',
|
|
2700
|
+
'3': '³',
|
|
2701
|
+
'³': '³',
|
|
2702
|
+
'': ''
|
|
2703
|
+
}[$4 || ''];
|
|
2704
|
+
return $1 + $2 + "\xA0" + $3 + pow + ($5 === "\xA0" ? ' ' : $5);
|
|
2705
|
+
});
|
|
2706
|
+
}
|
|
2707
|
+
};
|
|
2708
|
+
|
|
2709
|
+
var mln = {
|
|
2710
|
+
name: 'ru/nbsp/mln',
|
|
2711
|
+
handler: function handler(text) {
|
|
2712
|
+
return text.replace(/(\d) ?(тыс|млн|млрд|трлн)(\.|\s|$)/gi, "$1\xA0$2$3");
|
|
2713
|
+
}
|
|
2714
|
+
};
|
|
2715
|
+
|
|
2716
|
+
var ooo = {
|
|
2717
|
+
name: 'ru/nbsp/ooo',
|
|
2718
|
+
handler: function handler(text) {
|
|
2719
|
+
return text.replace(/(^|[^a-яёA-ЯЁ])(ООО|ОАО|ЗАО|НИИ|ПБОЮЛ) /g, "$1$2\xA0");
|
|
2720
|
+
}
|
|
2721
|
+
};
|
|
2722
|
+
|
|
2723
|
+
var page = {
|
|
2724
|
+
name: 'ru/nbsp/page',
|
|
2725
|
+
handler: function handler(text) {
|
|
2726
|
+
var re = new RegExp('(^|[)\\s' + privateLabel + '])' + '(стр|гл|рис|илл?|ст|п|c)\\. *(\\d+)([\\s.,?!;:]|$)', 'gim');
|
|
2727
|
+
return text.replace(re, "$1$2.\xA0$3$4");
|
|
2728
|
+
}
|
|
2729
|
+
};
|
|
2730
|
+
|
|
2731
|
+
var ps = {
|
|
2732
|
+
name: 'ru/nbsp/ps',
|
|
2733
|
+
handler: function handler(text) {
|
|
2734
|
+
var re = new RegExp("(^|\\s|".concat(privateLabel, ")[p\u0437]\\.[ \xA0]?([p\u0437]\\.[ \xA0]?)?[s\u044B]\\.:? "), 'gim');
|
|
2735
|
+
return text.replace(re, function ($0, $1, $2) {
|
|
2736
|
+
return $1 + ($2 ? "P.\xA0P.\xA0S. " : "P.\xA0S. ");
|
|
2737
|
+
});
|
|
2738
|
+
}
|
|
2739
|
+
};
|
|
2740
|
+
|
|
2741
|
+
var rubleKopek = {
|
|
2742
|
+
name: 'ru/nbsp/rubleKopek',
|
|
2743
|
+
handler: function handler(text) {
|
|
2744
|
+
return text.replace(/(\d) ?(?=(руб|коп)\.)/g, "$1\xA0");
|
|
2745
|
+
}
|
|
2746
|
+
};
|
|
2747
|
+
|
|
2748
|
+
var see = {
|
|
2749
|
+
name: 'ru/nbsp/see',
|
|
2750
|
+
handler: function handler(text) {
|
|
2751
|
+
var re = new RegExp("(^|\\s|".concat(privateLabel, "|\\()(\u0441\u043C|\u0438\u043C)\\.[ \xA0]?([\u0430-\u044F\u04510-9a-z]+)([\\s.,?!]|$)"), 'gi');
|
|
2752
|
+
return text.replace(re, function ($0, $1, $2, $3, $4) {
|
|
2753
|
+
return ($1 === "\xA0" ? ' ' : $1) + $2 + ".\xA0" + $3 + $4;
|
|
2754
|
+
});
|
|
2755
|
+
}
|
|
2756
|
+
};
|
|
2757
|
+
|
|
2758
|
+
var year = {
|
|
2759
|
+
name: 'ru/nbsp/year',
|
|
2760
|
+
handler: function handler(text) {
|
|
2761
|
+
return text.replace(/(^|\D)(\d{4}) ?г([ ,;.\n]|$)/g, "$1$2\xA0\u0433$3");
|
|
2762
|
+
}
|
|
2763
|
+
};
|
|
2764
|
+
|
|
2765
|
+
var years$1 = {
|
|
2766
|
+
name: 'ru/nbsp/years',
|
|
2767
|
+
index: '+5',
|
|
2768
|
+
handler: function handler(text) {
|
|
2769
|
+
var dashes = getData('common/dash');
|
|
2770
|
+
var re = new RegExp('(^|\\D)(\\d{4})(' + dashes + ")(\\d{4})[ \xA0]?\u0433\\.?([ \xA0]?\u0433\\.)?(?=[,;:?!\"\u2018\u201C\xBB\\s]|$)", 'gm');
|
|
2771
|
+
return text.replace(re, "$1$2$3$4\xA0\u0433\u0433.");
|
|
2772
|
+
}
|
|
2773
|
+
};
|
|
2774
|
+
|
|
2775
|
+
Typograf.addRules([abbr, addr, afterNumberSign, beforeParticle, centuries$1, dayMonth, initials, m, mln, ooo, page, ps, rubleKopek, see, year, years$1]);
|
|
2776
|
+
|
|
2777
|
+
var comma = {
|
|
2778
|
+
name: 'ru/number/comma',
|
|
2779
|
+
handler: function handler(text) {
|
|
2780
|
+
// \u00A0 - NO-BREAK SPACE
|
|
2781
|
+
// \u2009 - THIN SPACE
|
|
2782
|
+
// \u202F - NARROW NO-BREAK SPACE
|
|
2783
|
+
return text.replace(/(^|\s)(\d+)\.(\d+[\u00A0\u2009\u202F ]*?[%‰°×x])/gim, '$1$2,$3');
|
|
2784
|
+
}
|
|
2785
|
+
};
|
|
2786
|
+
|
|
2787
|
+
var ordinals = {
|
|
2788
|
+
name: 'ru/number/ordinals',
|
|
2789
|
+
handler: function handler(text, settings, context) {
|
|
2790
|
+
var re = new RegExp('(\\d[%‰]?)-(ый|ой|ая|ое|ые|ым|ом|ых|ого|ому|ыми)(?![' + context.getData('char') + '])', 'g');
|
|
2791
|
+
return text.replace(re, function ($0, $1, $2) {
|
|
2792
|
+
var parts = {
|
|
2793
|
+
'ой': 'й',
|
|
2794
|
+
'ый': 'й',
|
|
2795
|
+
'ая': 'я',
|
|
2796
|
+
'ое': 'е',
|
|
2797
|
+
'ые': 'е',
|
|
2798
|
+
'ым': 'м',
|
|
2799
|
+
'ом': 'м',
|
|
2800
|
+
'ых': 'х',
|
|
2801
|
+
'ого': 'го',
|
|
2802
|
+
'ому': 'му',
|
|
2803
|
+
'ыми': 'ми'
|
|
2804
|
+
};
|
|
2805
|
+
return $1 + '-' + parts[$2];
|
|
2806
|
+
});
|
|
2807
|
+
}
|
|
2808
|
+
};
|
|
2809
|
+
|
|
2810
|
+
Typograf.addRules([comma, ordinals]);
|
|
2811
|
+
|
|
2812
|
+
function removeOptAlignTags(text, classNames) {
|
|
2813
|
+
var re = new RegExp('<span class="(' + classNames.join('|') + ')">([^]*?)</span>', 'g');
|
|
2814
|
+
return text.replace(re, '$2');
|
|
2815
|
+
}
|
|
2816
|
+
function removeOptAlignTagsFromTitle(text, classNames) {
|
|
2817
|
+
return text.replace(/<title>[^]*?<\/title>/i, function (text) {
|
|
2818
|
+
return removeOptAlignTags(text, classNames);
|
|
2819
|
+
});
|
|
2820
|
+
}
|
|
2821
|
+
|
|
2822
|
+
var classNames = ['typograf-oa-lbracket', 'typograf-oa-n-lbracket', 'typograf-oa-sp-lbracket'];
|
|
2823
|
+
var name = 'ru/optalign/bracket';
|
|
2824
|
+
var bracket$1 = {
|
|
2825
|
+
name: name,
|
|
2826
|
+
handler: function handler(text) {
|
|
2827
|
+
return text.replace(/( |\u00A0)\(/g, '<span class="typograf-oa-sp-lbracket">$1</span><span class="typograf-oa-lbracket">(</span>').replace(/^\(/gm, '<span class="typograf-oa-n-lbracket">(</span>');
|
|
2828
|
+
},
|
|
2829
|
+
disabled: true,
|
|
2830
|
+
htmlAttrs: false
|
|
2831
|
+
};
|
|
2832
|
+
var innerStartBracket = {
|
|
2833
|
+
name: name,
|
|
2834
|
+
queue: 'start',
|
|
2835
|
+
handler: function handler(text) {
|
|
2836
|
+
return removeOptAlignTags(text, classNames);
|
|
2837
|
+
}
|
|
2838
|
+
};
|
|
2839
|
+
var innerEndBracket = {
|
|
2840
|
+
name: name,
|
|
2841
|
+
queue: 'end',
|
|
2842
|
+
handler: function handler(text) {
|
|
2843
|
+
return removeOptAlignTagsFromTitle(text, classNames);
|
|
2844
|
+
}
|
|
2845
|
+
};
|
|
2846
|
+
|
|
2847
|
+
var classNames$1 = ['typograf-oa-comma', 'typograf-oa-comma-sp'];
|
|
2848
|
+
var name$1 = 'ru/optalign/comma';
|
|
2849
|
+
var comma$1 = {
|
|
2850
|
+
name: name$1,
|
|
2851
|
+
handler: function handler(text, settings, context) {
|
|
2852
|
+
var re = new RegExp('([' + context.getData('char') + "\\d\u0301]+), ", 'gi');
|
|
2853
|
+
return text.replace(re, '$1<span class="typograf-oa-comma">,</span><span class="typograf-oa-comma-sp"> </span>');
|
|
2854
|
+
},
|
|
2855
|
+
disabled: true,
|
|
2856
|
+
htmlAttrs: false
|
|
2857
|
+
};
|
|
2858
|
+
var innerStartComma = {
|
|
2859
|
+
name: name$1,
|
|
2860
|
+
queue: 'start',
|
|
2861
|
+
handler: function handler(text) {
|
|
2862
|
+
return removeOptAlignTags(text, classNames$1);
|
|
2863
|
+
}
|
|
2864
|
+
};
|
|
2865
|
+
var innerEndComma = {
|
|
2866
|
+
name: name$1,
|
|
2867
|
+
queue: 'end',
|
|
2868
|
+
handler: function handler(text) {
|
|
2869
|
+
return removeOptAlignTagsFromTitle(text, classNames$1);
|
|
2870
|
+
}
|
|
2871
|
+
};
|
|
2872
|
+
|
|
2873
|
+
var classNames$2 = ['typograf-oa-lquote', 'typograf-oa-n-lquote', 'typograf-oa-sp-lquote'];
|
|
2874
|
+
var name$2 = 'ru/optalign/quote';
|
|
2875
|
+
var quote$1 = {
|
|
2876
|
+
name: name$2,
|
|
2877
|
+
handler: function handler(text) {
|
|
2878
|
+
var quote = this.getSetting('common/punctuation/quote', 'ru');
|
|
2879
|
+
var lquotes = '([' + quote.left[0] + (quote.left[1] || '') + '])';
|
|
2880
|
+
var reNewLine = new RegExp('(^|\n\n|' + privateLabel + ')(' + lquotes + ')', 'g');
|
|
2881
|
+
var reInside = new RegExp('([^\n' + privateLabel + "])([ \xA0\n])(" + lquotes + ')', 'gi');
|
|
2882
|
+
return text.replace(reNewLine, '$1<span class="typograf-oa-n-lquote">$2</span>').replace(reInside, '$1<span class="typograf-oa-sp-lquote">$2</span><span class="typograf-oa-lquote">$3</span>');
|
|
2883
|
+
},
|
|
2884
|
+
disabled: true,
|
|
2885
|
+
htmlAttrs: false
|
|
2886
|
+
};
|
|
2887
|
+
var innerStartQuote = {
|
|
2888
|
+
name: name$2,
|
|
2889
|
+
queue: 'start',
|
|
2890
|
+
handler: function handler(text) {
|
|
2891
|
+
return removeOptAlignTags(text, classNames$2);
|
|
2892
|
+
}
|
|
2893
|
+
};
|
|
2894
|
+
var innerEndQuote = {
|
|
2895
|
+
name: name$2,
|
|
2896
|
+
queue: 'end',
|
|
2897
|
+
handler: function handler(text) {
|
|
2898
|
+
return removeOptAlignTagsFromTitle(text, classNames$2);
|
|
2899
|
+
}
|
|
2900
|
+
};
|
|
2901
|
+
|
|
2902
|
+
Typograf.addRules([bracket$1, comma$1, quote$1]);
|
|
2903
|
+
Typograf.addInnerRules([innerStartBracket, innerEndBracket, innerStartComma, innerEndComma, innerStartQuote, innerEndQuote]);
|
|
2904
|
+
|
|
2905
|
+
var accent = {
|
|
2906
|
+
name: 'ru/other/accent',
|
|
2907
|
+
handler: function handler(text) {
|
|
2908
|
+
return text.replace(/([а-яё])([АЕЁИОУЫЭЮЯ])([^А-ЯЁ\w]|$)/g, function ($0, $1, $2, $3) {
|
|
2909
|
+
return $1 + $2.toLowerCase() + "\u0301" + $3;
|
|
2910
|
+
});
|
|
2911
|
+
},
|
|
2912
|
+
disabled: true
|
|
2913
|
+
};
|
|
2914
|
+
|
|
2915
|
+
var defaultCityCodeLength = 5;
|
|
2916
|
+
var countryCode = '7';
|
|
2917
|
+
var exceptions = [];
|
|
2918
|
+
var exceptionsMax = 8;
|
|
2919
|
+
var exceptionsMin = 2;
|
|
2920
|
+
[4162, 416332, 8512, 851111, 4722, 4725, 391379, 8442, 4732, 4152, 4154451, 4154459, 4154455, 41544513, 8142, 8332, 8612, 8622, 3525, 812, 8342, 8152, 3812, 4862, 3422, 342633, 8112, 9142, 8452, 3432, 3434, 3435, 4812, 8432, 8439, 3822, 4872, 3412, 3511, 3512, 3022, 4112, 4852, 4855, 3852, 3854, 8182, 818, 90, 3472, 4741, 4764, 4832, 4922, 8172, 8202, 8722, 4932, 493, 3952, 3951, 3953, 411533, 4842, 3842, 3843, 8212, 4942, '39131-39179', '39190-39199', 391, 4712, 4742, 8362, 495, 499, 4966, 4964, 4967, 498, 8312, 8313, 3832, 383612, 3532, 8412, 4232, 423370, 423630, 8632, 8642, 8482, 4242, 8672, 8652, 4752, 4822, 482502, 4826300, 3452, 8422, 4212, 3466, 3462, 8712, 8352, '901-934', '936-939', '950-953', 958, '960-969', '977-989', '991-997', 999].forEach(function (num) {
|
|
2921
|
+
if (typeof num === 'string') {
|
|
2922
|
+
var buf = num.split('-');
|
|
2923
|
+
|
|
2924
|
+
for (var i = +buf[0]; i <= +buf[1]; i++) {
|
|
2925
|
+
exceptions.push(i);
|
|
2926
|
+
}
|
|
2927
|
+
} else {
|
|
2928
|
+
exceptions.push(num);
|
|
2929
|
+
}
|
|
2930
|
+
});
|
|
2931
|
+
|
|
2932
|
+
function phone(num) {
|
|
2933
|
+
var firstSym = num[0];
|
|
2934
|
+
var cityCode = '';
|
|
2935
|
+
var hasPlusWithCode;
|
|
2936
|
+
var hasEight;
|
|
2937
|
+
|
|
2938
|
+
if (num.length < 8) {
|
|
2939
|
+
return phoneBlocks(num);
|
|
2940
|
+
} // 8 495 123-45-67, +7 495 123-45-67
|
|
2941
|
+
|
|
2942
|
+
|
|
2943
|
+
if (num.length > 10) {
|
|
2944
|
+
if (firstSym === '+') {
|
|
2945
|
+
if (num[1] === countryCode) {
|
|
2946
|
+
hasPlusWithCode = true;
|
|
2947
|
+
num = num.substr(2);
|
|
2948
|
+
} else {
|
|
2949
|
+
return num;
|
|
2950
|
+
}
|
|
2951
|
+
} else if (firstSym === '8') {
|
|
2952
|
+
hasEight = true;
|
|
2953
|
+
num = num.substr(1);
|
|
2954
|
+
}
|
|
2955
|
+
}
|
|
2956
|
+
|
|
2957
|
+
for (var cityCodeLen = exceptionsMax; cityCodeLen >= exceptionsMin; cityCodeLen--) {
|
|
2958
|
+
var code = +num.substr(0, cityCodeLen);
|
|
2959
|
+
|
|
2960
|
+
if (exceptions.indexOf(code) > -1) {
|
|
2961
|
+
cityCode = num.substr(0, cityCodeLen);
|
|
2962
|
+
num = num.substr(cityCodeLen);
|
|
2963
|
+
break;
|
|
2964
|
+
}
|
|
2965
|
+
}
|
|
2966
|
+
|
|
2967
|
+
if (!cityCode) {
|
|
2968
|
+
cityCode = num.substr(0, defaultCityCodeLength);
|
|
2969
|
+
num = num.substr(defaultCityCodeLength);
|
|
2970
|
+
}
|
|
2971
|
+
|
|
2972
|
+
return (hasPlusWithCode ? '+' + countryCode + "\xA0" : '') + (hasEight ? "8\xA0" : '') + prepareCode(cityCode) + "\xA0" + phoneBlocks(num);
|
|
2973
|
+
}
|
|
2974
|
+
|
|
2975
|
+
function prepareCode(code) {
|
|
2976
|
+
var numCode = +code;
|
|
2977
|
+
var len = code.length;
|
|
2978
|
+
var result = [code];
|
|
2979
|
+
var withoutBrackets = false;
|
|
2980
|
+
|
|
2981
|
+
if (len > 3) {
|
|
2982
|
+
switch (len) {
|
|
2983
|
+
case 4:
|
|
2984
|
+
result = [code.substr(0, 2), code.substr(2, 2)];
|
|
2985
|
+
break;
|
|
2986
|
+
|
|
2987
|
+
case 5:
|
|
2988
|
+
result = [code.substr(0, 3), code.substr(3, 3)];
|
|
2989
|
+
break;
|
|
2990
|
+
|
|
2991
|
+
case 6:
|
|
2992
|
+
result = [code.substr(0, 2), code.substr(2, 2), code.substr(4, 2)];
|
|
2993
|
+
break;
|
|
2994
|
+
}
|
|
2995
|
+
} else {
|
|
2996
|
+
// Мобильные и московские номера без скобок
|
|
2997
|
+
withoutBrackets = numCode > 900 && numCode <= 999 || numCode === 495 || numCode === 499;
|
|
2998
|
+
}
|
|
2999
|
+
|
|
3000
|
+
result = result.join('-');
|
|
3001
|
+
return withoutBrackets ? result : '(' + result + ')';
|
|
3002
|
+
}
|
|
3003
|
+
|
|
3004
|
+
function phoneBlocks(num) {
|
|
3005
|
+
var add = '';
|
|
3006
|
+
|
|
3007
|
+
if (num.length % 2) {
|
|
3008
|
+
add = num[0];
|
|
3009
|
+
add += num.length <= 5 ? '-' : '';
|
|
3010
|
+
num = num.substr(1, num.length - 1);
|
|
3011
|
+
}
|
|
3012
|
+
|
|
3013
|
+
return add + num.split(/(?=(?:\d\d)+$)/).join('-');
|
|
3014
|
+
}
|
|
3015
|
+
|
|
3016
|
+
function clearPhone(text) {
|
|
3017
|
+
return text.replace(/[^\d+]/g, '');
|
|
3018
|
+
}
|
|
3019
|
+
|
|
3020
|
+
var phoneNumber = {
|
|
3021
|
+
name: 'ru/other/phone-number',
|
|
3022
|
+
live: false,
|
|
3023
|
+
handler: function handler(text) {
|
|
3024
|
+
var re = new RegExp('(^|,| |' + privateLabel + ")(\\+7[\\d\\(\\) \xA0-]{10,18})(?=,|;|" + privateLabel + '|$)', 'gm');
|
|
3025
|
+
return text.replace(re, function ($0, $1, $2) {
|
|
3026
|
+
var buf = clearPhone($2);
|
|
3027
|
+
return buf.length === 12 ? $1 + phone(buf) : $0;
|
|
3028
|
+
}).replace( // eslint-disable-next-line no-misleading-character-class
|
|
3029
|
+
/(^|[^а-яё])([☎☏✆📠📞📱]|т\.|тел\.|ф\.|моб\.|факс|сотовый|мобильный|телефон)(:?\s*?)([+\d(][\d \u00A0\-()]{3,}\d)/gi, function ($0, $1, $2, $3, $4) {
|
|
3030
|
+
var buf = clearPhone($4);
|
|
3031
|
+
|
|
3032
|
+
if (buf.length >= 5) {
|
|
3033
|
+
return $1 + $2 + $3 + phone(buf);
|
|
3034
|
+
}
|
|
3035
|
+
|
|
3036
|
+
return $0;
|
|
3037
|
+
});
|
|
3038
|
+
}
|
|
3039
|
+
};
|
|
3040
|
+
|
|
3041
|
+
Typograf.addRules([accent, phoneNumber]);
|
|
3042
|
+
|
|
3043
|
+
var ano = {
|
|
3044
|
+
name: 'ru/punctuation/ano',
|
|
3045
|
+
handler: function handler(text) {
|
|
3046
|
+
var re = new RegExp('([^«„[(!?,:;\\-‒–—\\s' + privateLabel + "])(\\s+)(\u0430|\u043D\u043E)(?= |\xA0|\\n)", 'g');
|
|
3047
|
+
return text.replace(re, '$1,$2$3');
|
|
3048
|
+
}
|
|
3049
|
+
};
|
|
3050
|
+
|
|
3051
|
+
var exclamation = {
|
|
3052
|
+
name: 'ru/punctuation/exclamation',
|
|
3053
|
+
live: false,
|
|
3054
|
+
handler: function handler(text) {
|
|
3055
|
+
return text.replace(/(^|[^!])!{2}($|[^!])/gm, '$1!$2').replace(/(^|[^!])!{4}($|[^!])/gm, '$1!!!$2');
|
|
3056
|
+
}
|
|
3057
|
+
};
|
|
3058
|
+
|
|
3059
|
+
var exclamationQuestion = {
|
|
3060
|
+
name: 'ru/punctuation/exclamationQuestion',
|
|
3061
|
+
index: '+5',
|
|
3062
|
+
handler: function handler(text) {
|
|
3063
|
+
var re = new RegExp('(^|[^!])!\\?([^?]|$)', 'g');
|
|
3064
|
+
return text.replace(re, '$1?!$2');
|
|
3065
|
+
}
|
|
3066
|
+
};
|
|
3067
|
+
|
|
3068
|
+
var hellipQuestion = {
|
|
3069
|
+
name: 'ru/punctuation/hellipQuestion',
|
|
3070
|
+
handler: function handler(text) {
|
|
3071
|
+
return text.replace(/(^|[^.])(\.\.\.|…),/g, '$1…').replace(/(!|\?)(\.\.\.|…)(?=[^.]|$)/g, '$1..');
|
|
3072
|
+
}
|
|
3073
|
+
};
|
|
3074
|
+
|
|
3075
|
+
Typograf.addRules([ano, exclamation, exclamationQuestion, hellipQuestion]);
|
|
3076
|
+
|
|
3077
|
+
var afterHellip = {
|
|
3078
|
+
name: 'ru/space/afterHellip',
|
|
3079
|
+
handler: function handler(text) {
|
|
3080
|
+
return text.replace(/([а-яё])(\.\.\.|…)([А-ЯЁ])/g, '$1$2 $3').replace(/([?!]\.\.)([а-яёa-z])/gi, '$1 $2');
|
|
3081
|
+
}
|
|
3082
|
+
};
|
|
3083
|
+
|
|
3084
|
+
var year$1 = {
|
|
3085
|
+
name: 'ru/space/year',
|
|
3086
|
+
handler: function handler(text, settings, context) {
|
|
3087
|
+
var re = new RegExp("(^| |\xA0)(\\d{3,4})(\u0433\u043E\u0434([\u0430\u0443\u0435]|\u043E\u043C)?)([^" + context.getData('char') + ']|$)', 'g');
|
|
3088
|
+
return text.replace(re, '$1$2 $3$5');
|
|
3089
|
+
}
|
|
3090
|
+
};
|
|
3091
|
+
|
|
3092
|
+
Typograf.addRules([afterHellip, year$1]);
|
|
3093
|
+
|
|
3094
|
+
var nn = {
|
|
3095
|
+
name: 'ru/symbols/NN',
|
|
3096
|
+
handler: function handler(text) {
|
|
3097
|
+
return text.replace(/№№/g, '№');
|
|
3098
|
+
}
|
|
3099
|
+
};
|
|
3100
|
+
|
|
3101
|
+
Typograf.addRules([nn]);
|
|
3102
|
+
|
|
3103
|
+
var replacements = {
|
|
3104
|
+
A: 'А',
|
|
3105
|
+
// Latin: Russian
|
|
3106
|
+
a: 'а',
|
|
3107
|
+
B: 'В',
|
|
3108
|
+
E: 'Е',
|
|
3109
|
+
e: 'е',
|
|
3110
|
+
K: 'К',
|
|
3111
|
+
M: 'М',
|
|
3112
|
+
H: 'Н',
|
|
3113
|
+
O: 'О',
|
|
3114
|
+
o: 'о',
|
|
3115
|
+
P: 'Р',
|
|
3116
|
+
p: 'р',
|
|
3117
|
+
C: 'С',
|
|
3118
|
+
c: 'с',
|
|
3119
|
+
T: 'Т',
|
|
3120
|
+
y: 'у',
|
|
3121
|
+
X: 'Х',
|
|
3122
|
+
x: 'х'
|
|
3123
|
+
};
|
|
3124
|
+
var keys = Object.keys(replacements).join('');
|
|
3125
|
+
var switchingKeyboardLayout = {
|
|
3126
|
+
name: 'ru/typo/switchingKeyboardLayout',
|
|
3127
|
+
handler: function handler(text) {
|
|
3128
|
+
var re = new RegExp('([' + keys + ']{1,3})(?=[А-ЯЁа-яё]+?)', 'g');
|
|
3129
|
+
return text.replace(re, function (str, $1) {
|
|
3130
|
+
var result = '';
|
|
3131
|
+
|
|
3132
|
+
for (var i = 0; i < $1.length; i++) {
|
|
3133
|
+
result += replacements[$1[i]];
|
|
3134
|
+
}
|
|
3135
|
+
|
|
3136
|
+
return result;
|
|
3137
|
+
});
|
|
3138
|
+
}
|
|
3139
|
+
};
|
|
3140
|
+
|
|
3141
|
+
Typograf.addRules([switchingKeyboardLayout]);
|
|
3142
|
+
|
|
3143
|
+
export default Typograf;
|