weml-monaco 0.4.0 → 0.4.3
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/CHANGELOG.md +37 -0
- package/dist/index.cjs +449 -61
- package/dist/index.cjs.map +1 -1
- package/dist/index.global.js +61 -61
- package/dist/index.mjs +449 -61
- package/dist/index.mjs.map +1 -1
- package/package.json +1 -1
package/dist/index.mjs
CHANGED
|
@@ -6111,21 +6111,47 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6111
6111
|
"a",
|
|
6112
6112
|
"w-anchor",
|
|
6113
6113
|
"w-sent",
|
|
6114
|
-
"w-page"
|
|
6114
|
+
"w-page",
|
|
6115
|
+
"w-color"
|
|
6115
6116
|
]);
|
|
6116
|
-
var VOID_HTML_ELEMENTS = /* @__PURE__ */ new Set([
|
|
6117
|
-
|
|
6118
|
-
|
|
6117
|
+
var VOID_HTML_ELEMENTS = /* @__PURE__ */ new Set([
|
|
6118
|
+
"area",
|
|
6119
|
+
"base",
|
|
6120
|
+
"br",
|
|
6121
|
+
"col",
|
|
6122
|
+
"embed",
|
|
6123
|
+
"hr",
|
|
6124
|
+
"img",
|
|
6125
|
+
"input",
|
|
6126
|
+
"link",
|
|
6127
|
+
"meta",
|
|
6128
|
+
"source",
|
|
6129
|
+
"track",
|
|
6130
|
+
"wbr",
|
|
6131
|
+
"param"
|
|
6132
|
+
]);
|
|
6133
|
+
var EMPTY_TEXT_WRAPPERS = /* @__PURE__ */ new Set([
|
|
6134
|
+
"w-format",
|
|
6135
|
+
"w-lang",
|
|
6136
|
+
"w-color",
|
|
6137
|
+
"w-non-egw",
|
|
6138
|
+
"w-sent"
|
|
6139
|
+
]);
|
|
6140
|
+
var ENTITY_RE2 = /&(#[xX][0-9a-fA-F]+|#[0-9]+|[a-zA-Z][a-zA-Z0-9]*);?/g;
|
|
6119
6141
|
var PH_OPEN = "\uE000";
|
|
6120
6142
|
var PH_CLOSE = "\uE001";
|
|
6121
|
-
var
|
|
6122
|
-
var
|
|
6143
|
+
var VOID_ELEMENTS = VOID_HTML_ELEMENTS;
|
|
6144
|
+
var SPACE_SEPARATED_ATTRIBUTES = /* @__PURE__ */ new Set(["class", "headers", "rel", "rev"]);
|
|
6123
6145
|
var WHITE_SPACE = /* @__PURE__ */ new Set([
|
|
6124
6146
|
9,
|
|
6125
6147
|
10,
|
|
6126
6148
|
11,
|
|
6127
6149
|
12,
|
|
6128
6150
|
13,
|
|
6151
|
+
28,
|
|
6152
|
+
29,
|
|
6153
|
+
30,
|
|
6154
|
+
31,
|
|
6129
6155
|
32,
|
|
6130
6156
|
133,
|
|
6131
6157
|
160,
|
|
@@ -6145,40 +6171,193 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6145
6171
|
8233,
|
|
6146
6172
|
8239,
|
|
6147
6173
|
8287,
|
|
6148
|
-
12288
|
|
6174
|
+
12288,
|
|
6175
|
+
65279
|
|
6149
6176
|
]);
|
|
6150
6177
|
function formatWeml(input) {
|
|
6151
|
-
const { html, entities: entities2 } = protectEntities(input);
|
|
6178
|
+
const { html, entities: entities2, marker } = protectEntities(input);
|
|
6152
6179
|
const doc = parse2(normalizeVoidTagSyntax(html));
|
|
6180
|
+
removeEmptyWrappers(doc);
|
|
6181
|
+
const title = doc.querySelector("head title");
|
|
6182
|
+
if (title) processInlineContent(title, true);
|
|
6153
6183
|
const body = doc.querySelector("body");
|
|
6154
6184
|
if (body) processBlockElement(body);
|
|
6155
|
-
return restoreEntities(serializeDocument(doc), entities2);
|
|
6185
|
+
return restoreEntities(serializeDocument(doc, entities2, marker), entities2, marker);
|
|
6156
6186
|
}
|
|
6157
6187
|
function protectEntities(input) {
|
|
6188
|
+
let markerLength = 1;
|
|
6189
|
+
let marker = PH_OPEN.repeat(markerLength) + PH_CLOSE;
|
|
6190
|
+
while (input.includes(marker)) {
|
|
6191
|
+
markerLength += 1;
|
|
6192
|
+
marker = PH_OPEN.repeat(markerLength) + PH_CLOSE;
|
|
6193
|
+
}
|
|
6158
6194
|
const entities2 = [];
|
|
6159
6195
|
const html = input.replace(ENTITY_RE2, (match) => {
|
|
6160
6196
|
const index = entities2.length;
|
|
6161
6197
|
entities2.push(match);
|
|
6162
|
-
return `${
|
|
6198
|
+
return `${marker}${index}${marker}`;
|
|
6163
6199
|
});
|
|
6164
|
-
return { html, entities: entities2 };
|
|
6165
|
-
}
|
|
6166
|
-
function restoreEntities(text, entities2) {
|
|
6167
|
-
|
|
6200
|
+
return { html, entities: entities2, marker };
|
|
6201
|
+
}
|
|
6202
|
+
function restoreEntities(text, entities2, marker) {
|
|
6203
|
+
const result = [];
|
|
6204
|
+
let position = 0;
|
|
6205
|
+
while (position < text.length) {
|
|
6206
|
+
const open = text.indexOf(marker, position);
|
|
6207
|
+
if (open < 0) {
|
|
6208
|
+
result.push(text.slice(position));
|
|
6209
|
+
break;
|
|
6210
|
+
}
|
|
6211
|
+
result.push(text.slice(position, open));
|
|
6212
|
+
const indexStart = open + marker.length;
|
|
6213
|
+
const close = text.indexOf(marker, indexStart);
|
|
6214
|
+
const indexText = close >= 0 ? text.slice(indexStart, close) : "";
|
|
6215
|
+
const entityIndex = Number(indexText);
|
|
6216
|
+
if (close < 0 || !/^[0-9]+$/.test(indexText) || !Number.isSafeInteger(entityIndex) || entityIndex >= entities2.length) {
|
|
6217
|
+
throw new Error("Invalid internal entity placeholder.");
|
|
6218
|
+
}
|
|
6219
|
+
result.push(entities2[entityIndex]);
|
|
6220
|
+
position = close + marker.length;
|
|
6221
|
+
}
|
|
6222
|
+
return result.join("");
|
|
6168
6223
|
}
|
|
6169
6224
|
function normalizeVoidTagSyntax(input) {
|
|
6170
|
-
|
|
6225
|
+
function slashBelongsToUnquotedValue(attrs) {
|
|
6226
|
+
let index2 = 0;
|
|
6227
|
+
const whitespace = /* @__PURE__ */ new Set([" ", " ", "\n", "\f", "\r", "\v"]);
|
|
6228
|
+
while (index2 < attrs.length) {
|
|
6229
|
+
while (index2 < attrs.length && whitespace.has(attrs[index2])) index2 += 1;
|
|
6230
|
+
if (index2 >= attrs.length || attrs[index2] === "/") return false;
|
|
6231
|
+
while (index2 < attrs.length && !whitespace.has(attrs[index2]) && !["=", "/"].includes(attrs[index2])) index2 += 1;
|
|
6232
|
+
while (index2 < attrs.length && whitespace.has(attrs[index2])) index2 += 1;
|
|
6233
|
+
if (index2 >= attrs.length || attrs[index2] !== "=") continue;
|
|
6234
|
+
index2 += 1;
|
|
6235
|
+
while (index2 < attrs.length && whitespace.has(attrs[index2])) index2 += 1;
|
|
6236
|
+
if (index2 >= attrs.length) return false;
|
|
6237
|
+
if (attrs[index2] === '"' || attrs[index2] === "'") {
|
|
6238
|
+
const quote = attrs[index2];
|
|
6239
|
+
index2 += 1;
|
|
6240
|
+
while (index2 < attrs.length && attrs[index2] !== quote) index2 += 1;
|
|
6241
|
+
if (index2 < attrs.length) index2 += 1;
|
|
6242
|
+
continue;
|
|
6243
|
+
}
|
|
6244
|
+
const valueStart = index2;
|
|
6245
|
+
while (index2 < attrs.length && !whitespace.has(attrs[index2])) index2 += 1;
|
|
6246
|
+
if (index2 === attrs.length) {
|
|
6247
|
+
return valueStart < attrs.length && attrs.endsWith("/");
|
|
6248
|
+
}
|
|
6249
|
+
}
|
|
6250
|
+
return false;
|
|
6251
|
+
}
|
|
6252
|
+
const result = [];
|
|
6253
|
+
let index = 0;
|
|
6254
|
+
while (index < input.length) {
|
|
6255
|
+
if (input[index] !== "<") {
|
|
6256
|
+
result.push(input[index++]);
|
|
6257
|
+
continue;
|
|
6258
|
+
}
|
|
6259
|
+
const start = index;
|
|
6260
|
+
if (input.startsWith("<!--", index) || input.startsWith("<?", index)) {
|
|
6261
|
+
const delimiter = input.startsWith("<!--", index) ? "-->" : "?>";
|
|
6262
|
+
let end2 = input.indexOf(delimiter, index + 2);
|
|
6263
|
+
end2 = end2 < 0 ? input.length : end2 + delimiter.length;
|
|
6264
|
+
result.push(input.slice(start, end2));
|
|
6265
|
+
index = end2;
|
|
6266
|
+
continue;
|
|
6267
|
+
}
|
|
6268
|
+
const { end } = findTagEnd(input, index + 1);
|
|
6269
|
+
if (end < 0) {
|
|
6270
|
+
result.push(input.slice(index));
|
|
6271
|
+
break;
|
|
6272
|
+
}
|
|
6273
|
+
let cursor = index + 1;
|
|
6274
|
+
if (input[cursor] === "!") {
|
|
6275
|
+
result.push(input.slice(start, end + 1));
|
|
6276
|
+
index = end + 1;
|
|
6277
|
+
continue;
|
|
6278
|
+
}
|
|
6279
|
+
const closing = input[cursor] === "/";
|
|
6280
|
+
if (closing) cursor++;
|
|
6281
|
+
if (cursor >= end || !isNameStart(input[cursor])) {
|
|
6282
|
+
result.push(input[index++]);
|
|
6283
|
+
continue;
|
|
6284
|
+
}
|
|
6285
|
+
const nameStart = cursor++;
|
|
6286
|
+
while (cursor < end && isNameChar(input[cursor])) cursor++;
|
|
6287
|
+
const name = input.slice(nameStart, cursor);
|
|
6288
|
+
const attributes = [];
|
|
6289
|
+
let quote = null;
|
|
6290
|
+
let inSpace = false;
|
|
6291
|
+
for (let offset = cursor; offset < end; offset++) {
|
|
6292
|
+
const character = input[offset];
|
|
6293
|
+
if (quote !== null) {
|
|
6294
|
+
attributes.push(character);
|
|
6295
|
+
if (character === quote) quote = null;
|
|
6296
|
+
continue;
|
|
6297
|
+
}
|
|
6298
|
+
if (isSourceSpace(character)) {
|
|
6299
|
+
if (!inSpace) attributes.push(" ");
|
|
6300
|
+
inSpace = true;
|
|
6301
|
+
} else {
|
|
6302
|
+
inSpace = false;
|
|
6303
|
+
attributes.push(character);
|
|
6304
|
+
if (character === '"' || character === "'") quote = character;
|
|
6305
|
+
}
|
|
6306
|
+
}
|
|
6307
|
+
let attrs = attributes.join("").replace(/ +$/, "");
|
|
6308
|
+
if (!closing && VOID_HTML_ELEMENTS.has(name.toLowerCase())) {
|
|
6309
|
+
if (attrs.endsWith("/") && !slashBelongsToUnquotedValue(attrs)) {
|
|
6310
|
+
attrs = attrs.slice(0, -1).replace(/ +$/, "");
|
|
6311
|
+
}
|
|
6312
|
+
result.push(`<${name.toLowerCase()}${attrs} />`);
|
|
6313
|
+
} else {
|
|
6314
|
+
result.push(input.slice(start, cursor), attrs, ">");
|
|
6315
|
+
}
|
|
6316
|
+
index = end + 1;
|
|
6317
|
+
}
|
|
6318
|
+
return result.join("");
|
|
6171
6319
|
}
|
|
6172
|
-
function
|
|
6320
|
+
function removeEmptyWrappers(node) {
|
|
6321
|
+
for (const child of [...node.childNodes]) {
|
|
6322
|
+
if (child.nodeType === 8) {
|
|
6323
|
+
node.removeChild(child);
|
|
6324
|
+
continue;
|
|
6325
|
+
}
|
|
6326
|
+
if (child.nodeType !== 1) continue;
|
|
6327
|
+
removeEmptyWrappers(child);
|
|
6328
|
+
const hasId = Object.keys(child.rawAttributes).some((name) => name.toLowerCase() === "id");
|
|
6329
|
+
if (EMPTY_TEXT_WRAPPERS.has(child.rawTagName.toLowerCase()) && !hasId && child.childNodes.every((item) => item.nodeType === 3 && isWhitespaceOnly(item.rawText))) {
|
|
6330
|
+
const replacement = new TextNode(child.childNodes.some((item) => item.rawText.length > 0) ? " " : "", node);
|
|
6331
|
+
node.exchangeChild(child, replacement);
|
|
6332
|
+
}
|
|
6333
|
+
}
|
|
6334
|
+
let previous = null;
|
|
6173
6335
|
for (const child of [...node.childNodes]) {
|
|
6174
|
-
if (child.nodeType === 3
|
|
6336
|
+
if (child.nodeType === 3) {
|
|
6337
|
+
if (previous !== null) {
|
|
6338
|
+
previous.rawText += child.rawText;
|
|
6339
|
+
node.removeChild(child);
|
|
6340
|
+
} else previous = child;
|
|
6341
|
+
} else previous = null;
|
|
6175
6342
|
}
|
|
6343
|
+
}
|
|
6344
|
+
function processBlockElement(node) {
|
|
6345
|
+
node.childNodes = node.childNodes.filter((child) => {
|
|
6346
|
+
if (child.nodeType !== 3) return true;
|
|
6347
|
+
const normalized = trimWhitespace(child.rawText);
|
|
6348
|
+
if (normalized) {
|
|
6349
|
+
child.rawText = normalized;
|
|
6350
|
+
return true;
|
|
6351
|
+
}
|
|
6352
|
+
child.parentNode = null;
|
|
6353
|
+
return false;
|
|
6354
|
+
});
|
|
6176
6355
|
for (const child of [...node.childNodes]) {
|
|
6177
6356
|
if (child.nodeType !== 1) continue;
|
|
6178
6357
|
const name = child.rawTagName.toLowerCase();
|
|
6179
6358
|
if (INLINE_CONTAINERS.has(name)) processInlineContainer(child);
|
|
6180
6359
|
else if (BLOCK_ELEMENTS.has(name)) processBlockElement(child);
|
|
6181
|
-
else if (
|
|
6360
|
+
else if (isInlineTextElement(child)) processInlineContent(child, true);
|
|
6182
6361
|
}
|
|
6183
6362
|
}
|
|
6184
6363
|
function processInlineContainer(node) {
|
|
@@ -6189,7 +6368,7 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6189
6368
|
for (const child of [...node.childNodes]) {
|
|
6190
6369
|
if (child.nodeType !== 1) continue;
|
|
6191
6370
|
const name = child.rawTagName.toLowerCase();
|
|
6192
|
-
if (
|
|
6371
|
+
if (isInlineTextElement(child)) {
|
|
6193
6372
|
if (hasDirectSentChildren(child)) processSentContainer(child);
|
|
6194
6373
|
else processInlineContent(child, false);
|
|
6195
6374
|
} else if (BLOCK_ELEMENTS.has(name)) {
|
|
@@ -6199,19 +6378,19 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6199
6378
|
}
|
|
6200
6379
|
}
|
|
6201
6380
|
for (const child of [...node.childNodes]) {
|
|
6202
|
-
if (child.nodeType === 1 &&
|
|
6381
|
+
if (child.nodeType === 1 && isInlineTextElement(child)) {
|
|
6203
6382
|
bleedEdgeSpaces(child);
|
|
6204
6383
|
}
|
|
6205
6384
|
}
|
|
6206
6385
|
for (const child of [...node.childNodes]) {
|
|
6207
|
-
if (child.nodeType === 3) child.rawText = child.rawText
|
|
6386
|
+
if (child.nodeType === 3) child.rawText = collapseWhitespace(child.rawText);
|
|
6208
6387
|
}
|
|
6209
6388
|
for (const child of [...node.childNodes]) {
|
|
6210
6389
|
if (child.nodeType === 1 && child.rawTagName.toLowerCase() === "br") {
|
|
6211
6390
|
const prev = child.previousSibling;
|
|
6212
|
-
if (prev && prev.nodeType === 3) prev.rawText = prev.rawText
|
|
6391
|
+
if (prev && prev.nodeType === 3) prev.rawText = trimEndWhitespace(prev.rawText);
|
|
6213
6392
|
const next = child.nextSibling;
|
|
6214
|
-
if (next && next.nodeType === 3) next.rawText = next.rawText
|
|
6393
|
+
if (next && next.nodeType === 3) next.rawText = trimStartWhitespace(next.rawText);
|
|
6215
6394
|
}
|
|
6216
6395
|
}
|
|
6217
6396
|
trimContainerEdges(node);
|
|
@@ -6225,17 +6404,17 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6225
6404
|
const first = children[0];
|
|
6226
6405
|
const last = children[children.length - 1];
|
|
6227
6406
|
if (children.length === 1) {
|
|
6228
|
-
if (first.nodeType === 3) first.rawText = first.rawText
|
|
6407
|
+
if (first.nodeType === 3) first.rawText = trimWhitespace(first.rawText);
|
|
6229
6408
|
} else {
|
|
6230
|
-
if (first.nodeType === 3) first.rawText = first.rawText
|
|
6231
|
-
if (last.nodeType === 3) last.rawText = last.rawText
|
|
6409
|
+
if (first.nodeType === 3) first.rawText = trimStartWhitespace(first.rawText);
|
|
6410
|
+
if (last.nodeType === 3) last.rawText = trimEndWhitespace(last.rawText);
|
|
6232
6411
|
}
|
|
6233
6412
|
}
|
|
6234
6413
|
function processInlineContent(node, trimEdges) {
|
|
6235
6414
|
for (const child of [...node.childNodes]) {
|
|
6236
6415
|
if (child.nodeType !== 1) continue;
|
|
6237
6416
|
const name = child.rawTagName.toLowerCase();
|
|
6238
|
-
if (
|
|
6417
|
+
if (isInlineTextElement(child)) {
|
|
6239
6418
|
if (hasDirectSentChildren(child)) processSentContainer(child);
|
|
6240
6419
|
else processInlineContent(child, false);
|
|
6241
6420
|
} else if (BLOCK_ELEMENTS.has(name)) {
|
|
@@ -6245,19 +6424,19 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6245
6424
|
}
|
|
6246
6425
|
}
|
|
6247
6426
|
for (const child of [...node.childNodes]) {
|
|
6248
|
-
if (child.nodeType === 1 &&
|
|
6427
|
+
if (child.nodeType === 1 && isInlineTextElement(child)) {
|
|
6249
6428
|
bleedEdgeSpaces(child);
|
|
6250
6429
|
}
|
|
6251
6430
|
}
|
|
6252
6431
|
for (const child of [...node.childNodes]) {
|
|
6253
|
-
if (child.nodeType === 3) child.rawText = child.rawText
|
|
6432
|
+
if (child.nodeType === 3) child.rawText = collapseWhitespace(child.rawText);
|
|
6254
6433
|
}
|
|
6255
6434
|
for (const child of [...node.childNodes]) {
|
|
6256
6435
|
if (child.nodeType === 1 && child.rawTagName.toLowerCase() === "br") {
|
|
6257
6436
|
const prev = child.previousSibling;
|
|
6258
|
-
if (prev && prev.nodeType === 3) prev.rawText = prev.rawText
|
|
6437
|
+
if (prev && prev.nodeType === 3) prev.rawText = trimEndWhitespace(prev.rawText);
|
|
6259
6438
|
const next = child.nextSibling;
|
|
6260
|
-
if (next && next.nodeType === 3) next.rawText = next.rawText
|
|
6439
|
+
if (next && next.nodeType === 3) next.rawText = trimStartWhitespace(next.rawText);
|
|
6261
6440
|
}
|
|
6262
6441
|
}
|
|
6263
6442
|
if (trimEdges) trimEdgeTextNodes(node);
|
|
@@ -6295,7 +6474,7 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6295
6474
|
const first = getFirstTextNode(node);
|
|
6296
6475
|
if (!first) return "";
|
|
6297
6476
|
const raw = first.rawText;
|
|
6298
|
-
const trimmed = raw
|
|
6477
|
+
const trimmed = trimStartWhitespace(raw);
|
|
6299
6478
|
if (trimmed === raw) return "";
|
|
6300
6479
|
first.rawText = trimmed;
|
|
6301
6480
|
return " ";
|
|
@@ -6304,7 +6483,7 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6304
6483
|
const last = getLastTextNode(node);
|
|
6305
6484
|
if (!last) return "";
|
|
6306
6485
|
const raw = last.rawText;
|
|
6307
|
-
const trimmed = raw
|
|
6486
|
+
const trimmed = trimEndWhitespace(raw);
|
|
6308
6487
|
if (trimmed === raw) return "";
|
|
6309
6488
|
last.rawText = trimmed;
|
|
6310
6489
|
return " ";
|
|
@@ -6341,10 +6520,10 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6341
6520
|
const first = children[0];
|
|
6342
6521
|
const last = children[children.length - 1];
|
|
6343
6522
|
if (first === last) {
|
|
6344
|
-
if (first.nodeType === 3) first.rawText = first.rawText
|
|
6523
|
+
if (first.nodeType === 3) first.rawText = trimWhitespace(first.rawText);
|
|
6345
6524
|
} else {
|
|
6346
|
-
if (first.nodeType === 3) first.rawText = first.rawText
|
|
6347
|
-
if (last.nodeType === 3) last.rawText = last.rawText
|
|
6525
|
+
if (first.nodeType === 3) first.rawText = trimStartWhitespace(first.rawText);
|
|
6526
|
+
if (last.nodeType === 3) last.rawText = trimEndWhitespace(last.rawText);
|
|
6348
6527
|
}
|
|
6349
6528
|
}
|
|
6350
6529
|
function hasDirectSentChildren(node) {
|
|
@@ -6352,17 +6531,22 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6352
6531
|
(child) => child.nodeType === 1 && child.rawTagName.toLowerCase() === "w-sent"
|
|
6353
6532
|
);
|
|
6354
6533
|
}
|
|
6355
|
-
function
|
|
6534
|
+
function isInlineTextElement(node) {
|
|
6535
|
+
if (node.nodeType !== 1) return false;
|
|
6536
|
+
const name = node.rawTagName.toLowerCase();
|
|
6537
|
+
return INLINE_ELEMENTS.has(name) || !BLOCK_ELEMENTS.has(name) && !INLINE_CONTAINERS.has(name) && !VOID_HTML_ELEMENTS.has(name);
|
|
6538
|
+
}
|
|
6539
|
+
function serializeDocument(doc, entities2, marker) {
|
|
6356
6540
|
const parts = ["<!DOCTYPE html>\n"];
|
|
6357
6541
|
const htmlNode = doc.querySelector("html");
|
|
6358
|
-
parts.push(`<html${serializeAttrs(htmlNode ? htmlNode.
|
|
6542
|
+
parts.push(`<html${serializeAttrs(htmlNode ? htmlNode.rawAttrs : "", entities2, marker)}>
|
|
6359
6543
|
|
|
6360
6544
|
`);
|
|
6361
6545
|
const head = doc.querySelector("head");
|
|
6362
6546
|
parts.push("<head>\n");
|
|
6363
6547
|
if (head) {
|
|
6364
6548
|
for (const child of head.childNodes) {
|
|
6365
|
-
if (child.nodeType === 1) parts.push(serializeNode(child), "\n");
|
|
6549
|
+
if (child.nodeType === 1) parts.push(serializeNode(child, entities2, marker), "\n");
|
|
6366
6550
|
}
|
|
6367
6551
|
}
|
|
6368
6552
|
parts.push("</head>\n\n");
|
|
@@ -6370,28 +6554,81 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6370
6554
|
parts.push("<body>\n");
|
|
6371
6555
|
if (body) {
|
|
6372
6556
|
for (const child of body.childNodes) {
|
|
6373
|
-
if (child.nodeType === 1) parts.push(serializeNode(child), "\n");
|
|
6557
|
+
if (child.nodeType === 1) parts.push(serializeNode(child, entities2, marker), "\n");
|
|
6374
6558
|
}
|
|
6375
6559
|
}
|
|
6376
6560
|
parts.push("</body>\n</html>");
|
|
6377
6561
|
return parts.join("");
|
|
6378
6562
|
}
|
|
6379
|
-
function serializeNode(node) {
|
|
6563
|
+
function serializeNode(node, entities2, marker) {
|
|
6380
6564
|
if (node.nodeType === 3) return node.rawText;
|
|
6381
6565
|
if (node.nodeType === 8 || node.nodeType !== 1) return "";
|
|
6382
6566
|
const name = node.rawTagName.toLowerCase();
|
|
6383
|
-
const attrs = serializeAttrs(node.
|
|
6567
|
+
const attrs = serializeAttrs(node.rawAttrs, entities2, marker);
|
|
6384
6568
|
if (VOID_HTML_ELEMENTS.has(name)) return `<${name}${attrs} />`;
|
|
6385
6569
|
const isBlock = BLOCK_ELEMENTS.has(name);
|
|
6386
6570
|
const inner = [];
|
|
6387
6571
|
for (const child of node.childNodes) {
|
|
6388
|
-
if (isBlock && child.nodeType === 3 && child.rawText
|
|
6389
|
-
inner.push(serializeNode(child));
|
|
6572
|
+
if (isBlock && child.nodeType === 3 && isWhitespaceOnly(child.rawText)) continue;
|
|
6573
|
+
inner.push(serializeNode(child, entities2, marker));
|
|
6390
6574
|
}
|
|
6391
6575
|
return `<${name}${attrs}>${inner.join("")}</${name}>`;
|
|
6392
6576
|
}
|
|
6393
|
-
function serializeAttrs(
|
|
6394
|
-
|
|
6577
|
+
function serializeAttrs(rawAttrs, entities2, marker) {
|
|
6578
|
+
const canonical = /* @__PURE__ */ new Map();
|
|
6579
|
+
let index = 0;
|
|
6580
|
+
while (index < rawAttrs.length) {
|
|
6581
|
+
while (index < rawAttrs.length && isNormalizableWhitespace(rawAttrs[index])) index++;
|
|
6582
|
+
if (index >= rawAttrs.length || rawAttrs[index] === "/") break;
|
|
6583
|
+
const nameStart = index;
|
|
6584
|
+
while (index < rawAttrs.length && !isNormalizableWhitespace(rawAttrs[index]) && !"=/>".includes(rawAttrs[index])) index++;
|
|
6585
|
+
if (index === nameStart) {
|
|
6586
|
+
index++;
|
|
6587
|
+
continue;
|
|
6588
|
+
}
|
|
6589
|
+
const name = rawAttrs.slice(nameStart, index).toLowerCase();
|
|
6590
|
+
while (index < rawAttrs.length && isNormalizableWhitespace(rawAttrs[index])) index++;
|
|
6591
|
+
let value = "";
|
|
6592
|
+
if (rawAttrs[index] === "=") {
|
|
6593
|
+
index++;
|
|
6594
|
+
while (index < rawAttrs.length && isNormalizableWhitespace(rawAttrs[index])) index++;
|
|
6595
|
+
if (rawAttrs[index] === '"' || rawAttrs[index] === "'") {
|
|
6596
|
+
const quote = rawAttrs[index++];
|
|
6597
|
+
const valueStart = index;
|
|
6598
|
+
while (index < rawAttrs.length && rawAttrs[index] !== quote) index++;
|
|
6599
|
+
value = rawAttrs.slice(valueStart, index);
|
|
6600
|
+
if (index < rawAttrs.length) index++;
|
|
6601
|
+
} else {
|
|
6602
|
+
const valueStart = index;
|
|
6603
|
+
while (index < rawAttrs.length && !isNormalizableWhitespace(rawAttrs[index])) index++;
|
|
6604
|
+
value = rawAttrs.slice(valueStart, index);
|
|
6605
|
+
}
|
|
6606
|
+
}
|
|
6607
|
+
canonical.set(
|
|
6608
|
+
name,
|
|
6609
|
+
SPACE_SEPARATED_ATTRIBUTES.has(name) ? normalizeTokenList(value, entities2, marker) : trimWhitespace(value)
|
|
6610
|
+
);
|
|
6611
|
+
}
|
|
6612
|
+
return [...canonical.entries()].sort(([left], [right]) => left < right ? -1 : left > right ? 1 : 0).map(([name, value]) => ` ${name}="${encodeAttr(String(value))}"`).join("");
|
|
6613
|
+
}
|
|
6614
|
+
function normalizeTokenList(value, entities2, marker) {
|
|
6615
|
+
const normalized = trimWhitespace(value);
|
|
6616
|
+
if (!normalized) return normalized;
|
|
6617
|
+
return normalized.split(" ").sort((left, right) => compareUnicodeScalars(
|
|
6618
|
+
restoreEntities(left, entities2, marker),
|
|
6619
|
+
restoreEntities(right, entities2, marker)
|
|
6620
|
+
)).join(" ");
|
|
6621
|
+
}
|
|
6622
|
+
function compareUnicodeScalars(left, right) {
|
|
6623
|
+
const leftScalars = Array.from(left, (character) => character.codePointAt(0));
|
|
6624
|
+
const rightScalars = Array.from(right, (character) => character.codePointAt(0));
|
|
6625
|
+
const limit = Math.min(leftScalars.length, rightScalars.length);
|
|
6626
|
+
for (let index = 0; index < limit; index++) {
|
|
6627
|
+
if (leftScalars[index] !== rightScalars[index]) {
|
|
6628
|
+
return leftScalars[index] - rightScalars[index];
|
|
6629
|
+
}
|
|
6630
|
+
}
|
|
6631
|
+
return leftScalars.length - rightScalars.length;
|
|
6395
6632
|
}
|
|
6396
6633
|
function encodeAttr(value) {
|
|
6397
6634
|
return value.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").replace(/"/g, """);
|
|
@@ -6429,6 +6666,7 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6429
6666
|
}
|
|
6430
6667
|
};
|
|
6431
6668
|
function wemlContentNormalize2(input, isWemlValid = false) {
|
|
6669
|
+
if (input.startsWith("\uFEFF")) input = input.slice(1);
|
|
6432
6670
|
const inputText = withoutWhiteSpace(analyze(input, !isWemlValid).text);
|
|
6433
6671
|
const result = formatWeml(input);
|
|
6434
6672
|
const outputText = withoutWhiteSpace(analyze(result, true).text);
|
|
@@ -6443,6 +6681,9 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6443
6681
|
if (source[index2] === "\n") lineStarts.push(index2 + 1);
|
|
6444
6682
|
}
|
|
6445
6683
|
const stack = [];
|
|
6684
|
+
const rootTagCounts = /* @__PURE__ */ new Map([["html", 0], ["head", 0], ["body", 0]]);
|
|
6685
|
+
let seenHead = false;
|
|
6686
|
+
let seenBody = false;
|
|
6446
6687
|
const textParts = [];
|
|
6447
6688
|
let textStart = 0;
|
|
6448
6689
|
let index = 0;
|
|
@@ -6526,6 +6767,26 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6526
6767
|
if (expected !== name) fail("MISMATCHED_CLOSING_TAG", index, expected, name);
|
|
6527
6768
|
stack.pop();
|
|
6528
6769
|
} else {
|
|
6770
|
+
if (rootTagCounts.has(name)) {
|
|
6771
|
+
if (rootTagCounts.get(name) > 0) {
|
|
6772
|
+
fail("DUPLICATE_ROOT_TAG", index, null, name);
|
|
6773
|
+
}
|
|
6774
|
+
const parent = stack.length > 0 ? stack.at(-1).name : null;
|
|
6775
|
+
if (name === "html") {
|
|
6776
|
+
if (parent !== null) fail("INVALID_ROOT_TAG_PARENT", index, null, name);
|
|
6777
|
+
} else if (parent !== "html") {
|
|
6778
|
+
fail("INVALID_ROOT_TAG_PARENT", index, "html", name);
|
|
6779
|
+
}
|
|
6780
|
+
if (name === "body" && !seenHead) {
|
|
6781
|
+
fail("BODY_BEFORE_HEAD", index, "head", "body");
|
|
6782
|
+
}
|
|
6783
|
+
if (name === "head" && seenBody) {
|
|
6784
|
+
fail("HEAD_AFTER_BODY", index, "body", "head");
|
|
6785
|
+
}
|
|
6786
|
+
rootTagCounts.set(name, rootTagCounts.get(name) + 1);
|
|
6787
|
+
seenHead || (seenHead = name === "head");
|
|
6788
|
+
seenBody || (seenBody = name === "body");
|
|
6789
|
+
}
|
|
6529
6790
|
let last = found.end - 1;
|
|
6530
6791
|
while (last >= cursor && isSourceSpace(source[last])) last--;
|
|
6531
6792
|
const selfClosing = last >= cursor && source[last] === "/";
|
|
@@ -6547,6 +6808,11 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6547
6808
|
null
|
|
6548
6809
|
);
|
|
6549
6810
|
}
|
|
6811
|
+
if (validateStructure) {
|
|
6812
|
+
for (const name of ["html", "head", "body"]) {
|
|
6813
|
+
if (rootTagCounts.get(name) === 0) fail("MISSING_ROOT_TAG", 0, name, null);
|
|
6814
|
+
}
|
|
6815
|
+
}
|
|
6550
6816
|
return { text: textParts.join("") };
|
|
6551
6817
|
}
|
|
6552
6818
|
function findTagEnd(source, start) {
|
|
@@ -6570,11 +6836,40 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6570
6836
|
return isNameStart(character) || character >= "0" && character <= "9" || character === "-" || character === "_" || character === ":" || character === ".";
|
|
6571
6837
|
}
|
|
6572
6838
|
function isSourceSpace(character) {
|
|
6573
|
-
return character
|
|
6839
|
+
return isNormalizableWhitespace(character);
|
|
6574
6840
|
}
|
|
6575
6841
|
function withoutWhiteSpace(text) {
|
|
6576
6842
|
return Array.from(text, (character) => WHITE_SPACE.has(character.codePointAt(0)) ? "" : character).join("");
|
|
6577
6843
|
}
|
|
6844
|
+
function isNormalizableWhitespace(character) {
|
|
6845
|
+
return character !== void 0 && WHITE_SPACE.has(character.codePointAt(0));
|
|
6846
|
+
}
|
|
6847
|
+
function collapseWhitespace(text) {
|
|
6848
|
+
const result = [];
|
|
6849
|
+
let inWhitespace = false;
|
|
6850
|
+
for (const character of text) {
|
|
6851
|
+
if (isNormalizableWhitespace(character)) {
|
|
6852
|
+
if (!inWhitespace) result.push(" ");
|
|
6853
|
+
inWhitespace = true;
|
|
6854
|
+
} else {
|
|
6855
|
+
result.push(character);
|
|
6856
|
+
inWhitespace = false;
|
|
6857
|
+
}
|
|
6858
|
+
}
|
|
6859
|
+
return result.join("");
|
|
6860
|
+
}
|
|
6861
|
+
function trimStartWhitespace(text) {
|
|
6862
|
+
return collapseWhitespace(text).replace(/^ +/, "");
|
|
6863
|
+
}
|
|
6864
|
+
function trimEndWhitespace(text) {
|
|
6865
|
+
return collapseWhitespace(text).replace(/ +$/, "");
|
|
6866
|
+
}
|
|
6867
|
+
function trimWhitespace(text) {
|
|
6868
|
+
return collapseWhitespace(text).replace(/^ +| +$/g, "");
|
|
6869
|
+
}
|
|
6870
|
+
function isWhitespaceOnly(text) {
|
|
6871
|
+
return Array.from(text).every(isNormalizableWhitespace);
|
|
6872
|
+
}
|
|
6578
6873
|
function sha256(text) {
|
|
6579
6874
|
const crypto = __require("crypto");
|
|
6580
6875
|
return crypto.createHash("sha256").update(text, "utf8").digest("hex");
|
|
@@ -6594,6 +6889,16 @@ var require_wemlContentNormalizeV2 = __commonJS({
|
|
|
6594
6889
|
detail = `unexpected closing tag </${actualTag}>.`;
|
|
6595
6890
|
} else if (code === "UNCLOSED_TAG") {
|
|
6596
6891
|
detail = `tag <${expectedTag}> is not closed.`;
|
|
6892
|
+
} else if (code === "DUPLICATE_ROOT_TAG") {
|
|
6893
|
+
detail = `document contains more than one <${actualTag}> tag.`;
|
|
6894
|
+
} else if (code === "INVALID_ROOT_TAG_PARENT") {
|
|
6895
|
+
detail = expectedTag ? `tag <${actualTag}> must be a direct child of <${expectedTag}>.` : `root tag <${actualTag}> must not be nested.`;
|
|
6896
|
+
} else if (code === "BODY_BEFORE_HEAD") {
|
|
6897
|
+
detail = "tag <body> appears before <head>.";
|
|
6898
|
+
} else if (code === "HEAD_AFTER_BODY") {
|
|
6899
|
+
detail = "tag <head> appears after <body>.";
|
|
6900
|
+
} else if (code === "MISSING_ROOT_TAG") {
|
|
6901
|
+
detail = `required root tag <${expectedTag}> is missing.`;
|
|
6597
6902
|
} else if (code === "UNTERMINATED_COMMENT") {
|
|
6598
6903
|
detail = "comment is not terminated.";
|
|
6599
6904
|
} else if (code === "UNTERMINATED_DECLARATION") {
|
|
@@ -29245,6 +29550,13 @@ var TAGS = {
|
|
|
29245
29550
|
"default": "paragraph",
|
|
29246
29551
|
"description": "Type of the paragraph. See corresponding page for values",
|
|
29247
29552
|
"enumRef": "paragraph-type"
|
|
29553
|
+
},
|
|
29554
|
+
{
|
|
29555
|
+
"name": "align",
|
|
29556
|
+
"required": false,
|
|
29557
|
+
"default": "`left` for LTR, `right` for RTL",
|
|
29558
|
+
"description": "Horizontal alignment. See corresponding page for allowed values",
|
|
29559
|
+
"enumRef": "horizontal-alignment"
|
|
29248
29560
|
}
|
|
29249
29561
|
],
|
|
29250
29562
|
"notes": "",
|
|
@@ -29257,6 +29569,24 @@ var TAGS = {
|
|
|
29257
29569
|
"notes": "Current line is broken and the next line is started. Next line has the same alignment\nas the current line, and the same indentation level as any line other than the first.",
|
|
29258
29570
|
"source": "inlines/br.md"
|
|
29259
29571
|
},
|
|
29572
|
+
"w-color": {
|
|
29573
|
+
"tag": "w-color",
|
|
29574
|
+
"description": "Represents an inline span with a foreground color, a background color, or both.",
|
|
29575
|
+
"attributes": [
|
|
29576
|
+
{
|
|
29577
|
+
"name": "background",
|
|
29578
|
+
"required": false,
|
|
29579
|
+
"description": "Background color. See Colors."
|
|
29580
|
+
},
|
|
29581
|
+
{
|
|
29582
|
+
"name": "foreground",
|
|
29583
|
+
"required": false,
|
|
29584
|
+
"description": "Foreground color. See Colors."
|
|
29585
|
+
}
|
|
29586
|
+
],
|
|
29587
|
+
"notes": "Any inline elements.",
|
|
29588
|
+
"source": "inlines/w-color.md"
|
|
29589
|
+
},
|
|
29260
29590
|
"w-entity": {
|
|
29261
29591
|
"tag": "w-entity",
|
|
29262
29592
|
"description": "An entity is a reference to a person, place, or thing. Entities are used to",
|
|
@@ -29389,6 +29719,16 @@ var TAGS = {
|
|
|
29389
29719
|
"name": "override-chapter-number",
|
|
29390
29720
|
"required": false,
|
|
29391
29721
|
"description": "Chapter number for manual set"
|
|
29722
|
+
},
|
|
29723
|
+
{
|
|
29724
|
+
"name": "background",
|
|
29725
|
+
"required": false,
|
|
29726
|
+
"description": "Background color. See Colors"
|
|
29727
|
+
},
|
|
29728
|
+
{
|
|
29729
|
+
"name": "foreground",
|
|
29730
|
+
"required": false,
|
|
29731
|
+
"description": "Foreground color. See Colors"
|
|
29392
29732
|
}
|
|
29393
29733
|
],
|
|
29394
29734
|
"notes": "Must contain a single text block element.",
|
|
@@ -29419,6 +29759,16 @@ var TAGS = {
|
|
|
29419
29759
|
"required": false,
|
|
29420
29760
|
"description": "Horizontal alignment. See corresponding page for allowed values. Defaults to `left` for left-to-right languages and `right` to right-to-left",
|
|
29421
29761
|
"enumRef": "horizontal-alignment"
|
|
29762
|
+
},
|
|
29763
|
+
{
|
|
29764
|
+
"name": "background",
|
|
29765
|
+
"required": false,
|
|
29766
|
+
"description": "Background color. See Colors"
|
|
29767
|
+
},
|
|
29768
|
+
{
|
|
29769
|
+
"name": "foreground",
|
|
29770
|
+
"required": false,
|
|
29771
|
+
"description": "Foreground color. See Colors"
|
|
29422
29772
|
}
|
|
29423
29773
|
],
|
|
29424
29774
|
"notes": "Must contain a single block element.",
|
|
@@ -29775,8 +30125,12 @@ var META_FIELDS = [
|
|
|
29775
30125
|
"description": "Publication description."
|
|
29776
30126
|
},
|
|
29777
30127
|
{
|
|
29778
|
-
"name": "
|
|
29779
|
-
"description": "
|
|
30128
|
+
"name": "purchase-link",
|
|
30129
|
+
"description": "Purchase link."
|
|
30130
|
+
},
|
|
30131
|
+
{
|
|
30132
|
+
"name": "version-id",
|
|
30133
|
+
"description": "Publication version GUID."
|
|
29780
30134
|
}
|
|
29781
30135
|
];
|
|
29782
30136
|
|
|
@@ -30033,7 +30387,7 @@ Unicode: \`U+${resolved.codePoint.toString(16).toUpperCase().padStart(4, "0")}\`
|
|
|
30033
30387
|
// src/schema/structureRules.ts
|
|
30034
30388
|
var CONTAINER_TAGS = ["w-para", "w-heading", "w-para-group", "w-toc"];
|
|
30035
30389
|
var BLOCK_TAGS = ["w-text-block", "figure", "w-list", "table", "hr"];
|
|
30036
|
-
var INLINE_TAGS = ["a", "br", "w-entity", "w-format", "w-lang", "w-non-egw", "w-note", "w-page", "w-sent"];
|
|
30390
|
+
var INLINE_TAGS = ["a", "br", "w-color", "w-entity", "w-format", "w-lang", "w-non-egw", "w-note", "w-page", "w-sent"];
|
|
30037
30391
|
var STRUCTURE_RULES = {
|
|
30038
30392
|
html: {
|
|
30039
30393
|
children: [
|
|
@@ -30180,6 +30534,13 @@ var STRUCTURE_RULES = {
|
|
|
30180
30534
|
allowText: true,
|
|
30181
30535
|
description: "With href: a link that may contain inline content. With id: a named anchor that must be empty. Exactly one of href/id is required, not both."
|
|
30182
30536
|
},
|
|
30537
|
+
"w-color": {
|
|
30538
|
+
children: [
|
|
30539
|
+
{ tags: [...INLINE_TAGS], min: 0, max: null, description: "inline elements" }
|
|
30540
|
+
],
|
|
30541
|
+
allowText: true,
|
|
30542
|
+
description: "May contain inline elements and text; requires a foreground or background color."
|
|
30543
|
+
},
|
|
30183
30544
|
"w-entity": {
|
|
30184
30545
|
children: [
|
|
30185
30546
|
{ tags: [...INLINE_TAGS], min: 0, max: null, description: "inline elements" }
|
|
@@ -30253,11 +30614,18 @@ var STRUCTURE_RULES = {
|
|
|
30253
30614
|
}
|
|
30254
30615
|
};
|
|
30255
30616
|
var ARABIC_OR_ROMAN = /^(?:\d+|[ivxlcdm]+)$/i;
|
|
30617
|
+
var COLOR_VALUE = /^#(?:[0-9a-f]{3}|[0-9a-f]{4}|[0-9a-f]{6}|[0-9a-f]{8})$/i;
|
|
30256
30618
|
var ATTRIBUTE_CONSTRAINTS = [
|
|
30257
30619
|
{ tag: "w-heading", attribute: "level", kind: "integer-range", min: 1, max: 6, message: "`level` must be an integer between 1 and 6." },
|
|
30258
30620
|
{ tag: "w-heading", attribute: "override-chapter-number", kind: "integer-min", min: 0, message: "`override-chapter-number` must be a non-negative integer." },
|
|
30621
|
+
{ tag: "w-heading", attribute: "background", kind: "pattern", pattern: COLOR_VALUE, allowEmpty: false, message: "`background` must be a color in #RGB, #RGBA, #RRGGBB or #RRGGBBAA format." },
|
|
30622
|
+
{ tag: "w-heading", attribute: "foreground", kind: "pattern", pattern: COLOR_VALUE, allowEmpty: false, message: "`foreground` must be a color in #RGB, #RGBA, #RRGGBB or #RRGGBBAA format." },
|
|
30259
30623
|
{ tag: "w-page", attribute: "number", kind: "pattern", pattern: ARABIC_OR_ROMAN, message: "`number` must be an arabic or roman number." },
|
|
30260
30624
|
{ tag: "w-para", attribute: "indent", kind: "integer-min", min: -4, message: "`indent` must be an integer >= -4." },
|
|
30625
|
+
{ tag: "w-para", attribute: "background", kind: "pattern", pattern: COLOR_VALUE, allowEmpty: false, message: "`background` must be a color in #RGB, #RGBA, #RRGGBB or #RRGGBBAA format." },
|
|
30626
|
+
{ tag: "w-para", attribute: "foreground", kind: "pattern", pattern: COLOR_VALUE, allowEmpty: false, message: "`foreground` must be a color in #RGB, #RGBA, #RRGGBB or #RRGGBBAA format." },
|
|
30627
|
+
{ tag: "w-color", attribute: "background", kind: "pattern", pattern: COLOR_VALUE, allowEmpty: false, message: "`background` must be a color in #RGB, #RGBA, #RRGGBB or #RRGGBBAA format." },
|
|
30628
|
+
{ tag: "w-color", attribute: "foreground", kind: "pattern", pattern: COLOR_VALUE, allowEmpty: false, message: "`foreground` must be a color in #RGB, #RGBA, #RRGGBB or #RRGGBBAA format." },
|
|
30261
30629
|
{ tag: "w-note-para", attribute: "indent", kind: "integer-min", min: 0, message: "`indent` must be an integer >= 0." },
|
|
30262
30630
|
{ tag: "td", attribute: "indent", kind: "integer-min", min: -4, message: "`indent` must be an integer >= -4." },
|
|
30263
30631
|
{ tag: "th", attribute: "indent", kind: "integer-min", min: -4, message: "`indent` must be an integer >= -4." },
|
|
@@ -30398,6 +30766,9 @@ function indent(text) {
|
|
|
30398
30766
|
function buildElement(tag, counter, depth) {
|
|
30399
30767
|
const schema = TAGS[tag];
|
|
30400
30768
|
let attrs = "";
|
|
30769
|
+
if (tag === "w-color") {
|
|
30770
|
+
attrs = ` foreground="${placeholder(counter)}"`;
|
|
30771
|
+
}
|
|
30401
30772
|
for (const attr of schema?.attributes ?? []) {
|
|
30402
30773
|
if (attr.required) {
|
|
30403
30774
|
attrs += ` ${attr.name}="${placeholder(counter)}"`;
|
|
@@ -30433,6 +30804,9 @@ function buildElementSnippet(tag) {
|
|
|
30433
30804
|
function buildOpeningTag(tag) {
|
|
30434
30805
|
const counter = { n: 1 };
|
|
30435
30806
|
let attrs = "";
|
|
30807
|
+
if (tag === "w-color") {
|
|
30808
|
+
attrs = ` foreground="${placeholder(counter)}"`;
|
|
30809
|
+
}
|
|
30436
30810
|
for (const attr of TAGS[tag]?.attributes ?? []) {
|
|
30437
30811
|
if (attr.required) {
|
|
30438
30812
|
attrs += ` ${attr.name}="${placeholder(counter)}"`;
|
|
@@ -30540,24 +30914,22 @@ function getCompletionContext(text, offset, nodeStart) {
|
|
|
30540
30914
|
switch (token) {
|
|
30541
30915
|
case TokenType.StartTagOpen:
|
|
30542
30916
|
if (scanner.getTokenEnd() === offset) {
|
|
30543
|
-
|
|
30544
|
-
return { kind: "tag", start: offset - 1, end, includesBracket: true };
|
|
30917
|
+
return { kind: "tag", start: offset - 1, end: offset, includesBracket: true };
|
|
30545
30918
|
}
|
|
30546
30919
|
break;
|
|
30547
30920
|
case TokenType.EndTagOpen:
|
|
30548
30921
|
if (scanner.getTokenEnd() === offset) {
|
|
30549
|
-
|
|
30550
|
-
return { kind: "end-tag", start: offset, end };
|
|
30922
|
+
return { kind: "end-tag", start: offset, end: offset };
|
|
30551
30923
|
}
|
|
30552
30924
|
break;
|
|
30553
30925
|
case TokenType.EndTag:
|
|
30554
30926
|
if (scanner.getTokenOffset() <= offset && offset <= scanner.getTokenEnd()) {
|
|
30555
|
-
return { kind: "end-tag", start: scanner.getTokenOffset(), end:
|
|
30927
|
+
return { kind: "end-tag", start: scanner.getTokenOffset(), end: offset };
|
|
30556
30928
|
}
|
|
30557
30929
|
break;
|
|
30558
30930
|
case TokenType.StartTag:
|
|
30559
30931
|
if (scanner.getTokenOffset() <= offset && offset <= scanner.getTokenEnd()) {
|
|
30560
|
-
return { kind: "tag", start: scanner.getTokenOffset(), end:
|
|
30932
|
+
return { kind: "tag", start: scanner.getTokenOffset(), end: offset, includesBracket: false };
|
|
30561
30933
|
}
|
|
30562
30934
|
currentTag = scanner.getTokenText();
|
|
30563
30935
|
break;
|
|
@@ -30595,8 +30967,7 @@ function getCompletionContext(text, offset, nodeStart) {
|
|
|
30595
30967
|
switch (scanner.getScannerState()) {
|
|
30596
30968
|
case ScannerState.AfterOpeningStartTag: {
|
|
30597
30969
|
const start = scanner.getTokenOffset();
|
|
30598
|
-
|
|
30599
|
-
return { kind: "tag", start, end, includesBracket: false };
|
|
30970
|
+
return { kind: "tag", start, end: offset, includesBracket: false };
|
|
30600
30971
|
}
|
|
30601
30972
|
case ScannerState.WithinTag:
|
|
30602
30973
|
case ScannerState.AfterAttributeName:
|
|
@@ -30636,6 +31007,7 @@ function dedupe(items) {
|
|
|
30636
31007
|
function hasValueSuggestions(tag, attribute, enumRef) {
|
|
30637
31008
|
if (enumRef && ENUMS[enumRef]) return true;
|
|
30638
31009
|
if (tag === "w-heading" && attribute === "level") return true;
|
|
31010
|
+
if (tag === "meta" && attribute === "name") return true;
|
|
30639
31011
|
if (tag === "meta" && attribute === "content") return true;
|
|
30640
31012
|
if (tag === "a" && attribute === "href") return true;
|
|
30641
31013
|
return false;
|
|
@@ -30805,6 +31177,18 @@ var WemlCompletionProvider = class {
|
|
|
30805
31177
|
});
|
|
30806
31178
|
}
|
|
30807
31179
|
}
|
|
31180
|
+
if (ctx.tag === "meta" && ctx.attribute === "name") {
|
|
31181
|
+
for (const field of META_FIELDS) {
|
|
31182
|
+
items.push({
|
|
31183
|
+
label: field.name,
|
|
31184
|
+
kind: this.m.languages.CompletionItemKind.Property,
|
|
31185
|
+
detail: "WEML metadata field",
|
|
31186
|
+
documentation: metaFieldMarkdown(field.name),
|
|
31187
|
+
insertText: wrap(field.name),
|
|
31188
|
+
range
|
|
31189
|
+
});
|
|
31190
|
+
}
|
|
31191
|
+
}
|
|
30808
31192
|
if (ctx.tag === "meta" && ctx.attribute === "content" && stripQuotes2(node.attributes?.["name"]) === "type") {
|
|
30809
31193
|
const codeEnum = ENUMS["publication-type"];
|
|
30810
31194
|
if (codeEnum) {
|
|
@@ -30962,6 +31346,9 @@ function validateWemlModel(m, model) {
|
|
|
30962
31346
|
push(href.valueRange, `Unrecognized href format "${href.value}". Expected formats like: ${types}.`, "warning");
|
|
30963
31347
|
}
|
|
30964
31348
|
}
|
|
31349
|
+
if (tag === "w-color" && !attrs.has("background") && !attrs.has("foreground")) {
|
|
31350
|
+
push(tagRange, '<w-color> must have either "background" or "foreground".', "error");
|
|
31351
|
+
}
|
|
30965
31352
|
if (tag === "div") {
|
|
30966
31353
|
const id = stripQuotes2(node.attributes?.["id"]);
|
|
30967
31354
|
const range = attrs.get("id")?.valueRange ?? tagRange;
|
|
@@ -30975,7 +31362,8 @@ function validateWemlModel(m, model) {
|
|
|
30975
31362
|
function validateConstraint(constraint, info) {
|
|
30976
31363
|
if (info.value === void 0 || !info.valueRange) return;
|
|
30977
31364
|
if (constraint.kind === "pattern") {
|
|
30978
|
-
|
|
31365
|
+
const emptyIsInvalid = constraint.allowEmpty === false && info.value === "";
|
|
31366
|
+
if (emptyIsInvalid || info.value !== "" && constraint.pattern && !constraint.pattern.test(info.value)) {
|
|
30979
31367
|
push(info.valueRange, constraint.message, "error");
|
|
30980
31368
|
}
|
|
30981
31369
|
return;
|
|
@@ -31354,7 +31742,7 @@ function escapeSnippet(text) {
|
|
|
31354
31742
|
return text.replace(/\\/g, "\\\\").replace(/\$/g, "\\$").replace(/}/g, "\\}");
|
|
31355
31743
|
}
|
|
31356
31744
|
function buildWrapSnippet(tag, type, selection) {
|
|
31357
|
-
const attrs = type ? ` type="${type}"` : tag === "a" ? ' href="$1"' : (TAGS[tag]?.attributes ?? []).filter((a) => a.required).map((a) => ` ${a.name}="$1"`).join("");
|
|
31745
|
+
const attrs = type ? ` type="${type}"` : tag === "a" ? ' href="$1"' : tag === "w-color" ? ' foreground="$1"' : (TAGS[tag]?.attributes ?? []).filter((a) => a.required).map((a) => ` ${a.name}="$1"`).join("");
|
|
31358
31746
|
const inner = selection.length > 0 ? escapeSnippet(selection) : attrs.includes("$1") ? "$2" : "$1";
|
|
31359
31747
|
return `<${tag}${attrs}>${inner}</${tag}>`;
|
|
31360
31748
|
}
|
|
@@ -31507,7 +31895,7 @@ var WRAP_OPTIONS = [
|
|
|
31507
31895
|
tag: "w-format",
|
|
31508
31896
|
type: v.value
|
|
31509
31897
|
})),
|
|
31510
|
-
...["w-lang", "w-non-egw", "w-entity", "a"].map((t2) => ({ value: t2, label: t2, tag: t2 }))
|
|
31898
|
+
...["w-color", "w-lang", "w-non-egw", "w-entity", "a"].map((t2) => ({ value: t2, label: t2, tag: t2 }))
|
|
31511
31899
|
];
|
|
31512
31900
|
var SNIPPET_BUTTONS = [
|
|
31513
31901
|
{ label: "w-para", id: "w-para" },
|