@vue/compiler-vapor 3.6.0-alpha.2 → 3.6.0-alpha.4

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.
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @vue/compiler-vapor v3.6.0-alpha.2
2
+ * @vue/compiler-vapor v3.6.0-alpha.4
3
3
  * (c) 2018-present Yuxi (Evan) You and Vue contributors
4
4
  * @license MIT
5
5
  **/
@@ -11,7 +11,6 @@ var compilerDom = require('@vue/compiler-dom');
11
11
  var shared = require('@vue/shared');
12
12
  var sourceMapJs = require('source-map-js');
13
13
  var parser = require('@babel/parser');
14
- var types = require('@babel/types');
15
14
  var estreeWalker = require('estree-walker');
16
15
 
17
16
  const newDynamic = () => ({
@@ -25,7 +24,8 @@ const newBlock = (node) => ({
25
24
  effect: [],
26
25
  operation: [],
27
26
  returns: [],
28
- tempId: 0
27
+ tempId: 0,
28
+ hasDeferredVShow: false
29
29
  });
30
30
  function wrapTemplate(node, dirs) {
31
31
  if (node.tagType === 3) {
@@ -65,31 +65,85 @@ function isStaticExpression(node, bindings) {
65
65
  if (node.ast) {
66
66
  return compilerDom.isConstantNode(node.ast, bindings);
67
67
  } else if (node.ast === null) {
68
+ if (!node.isStatic && (node.content === "true" || node.content === "false")) {
69
+ return true;
70
+ }
68
71
  const type = bindings[node.content];
69
72
  return type === "literal-const";
70
73
  }
71
74
  return false;
72
75
  }
73
- function resolveExpression(exp) {
76
+ function resolveExpression(exp, isComponent) {
74
77
  if (!exp.isStatic) {
75
- const value = getLiteralExpressionValue(exp);
78
+ const value = getLiteralExpressionValue(exp, isComponent);
76
79
  if (value !== null) {
77
- return compilerDom.createSimpleExpression("" + value, true, exp.loc);
80
+ return compilerDom.createSimpleExpression(value, true, exp.loc);
78
81
  }
79
82
  }
80
83
  return exp;
81
84
  }
82
- function getLiteralExpressionValue(exp) {
85
+ function getLiteralExpressionValue(exp, excludeNumber) {
83
86
  if (exp.ast) {
84
87
  if (exp.ast.type === "StringLiteral") {
85
88
  return exp.ast.value;
86
- } else if (exp.ast.type === "TemplateLiteral" && exp.ast.expressions.length === 0) {
87
- return exp.ast.quasis[0].value.cooked;
89
+ } else if (!excludeNumber && (exp.ast.type === "NumericLiteral" || exp.ast.type === "BigIntLiteral")) {
90
+ return String(exp.ast.value);
91
+ } else if (exp.ast.type === "TemplateLiteral") {
92
+ let result = "";
93
+ for (const [index, quasi] of exp.ast.quasis.entries()) {
94
+ result += quasi.value.cooked;
95
+ if (exp.ast.expressions[index]) {
96
+ let expressionValue = getLiteralExpressionValue({
97
+ ast: exp.ast.expressions[index]
98
+ });
99
+ if (expressionValue == null) {
100
+ return null;
101
+ } else {
102
+ result += expressionValue;
103
+ }
104
+ }
105
+ }
106
+ return result;
88
107
  }
89
108
  }
90
109
  return exp.isStatic ? exp.content : null;
91
110
  }
111
+ function isInTransition(context) {
112
+ const parentNode = context.parent && context.parent.node;
113
+ return !!(parentNode && isTransitionNode(parentNode));
114
+ }
115
+ function isTransitionNode(node) {
116
+ return node.type === 1 && isTransitionTag(node.tag);
117
+ }
118
+ function isTransitionTag(tag) {
119
+ tag = tag.toLowerCase();
120
+ return tag === "transition" || tag === "vaportransition";
121
+ }
122
+ function isTransitionGroupTag(tag) {
123
+ tag = tag.toLowerCase().replace(/-/g, "");
124
+ return tag === "transitiongroup" || tag === "vaportransitiongroup";
125
+ }
126
+ function isKeepAliveTag(tag) {
127
+ tag = tag.toLowerCase();
128
+ return tag === "keepalive" || tag === "vaporkeepalive";
129
+ }
130
+ function isTeleportTag(tag) {
131
+ tag = tag.toLowerCase();
132
+ return tag === "teleport" || tag === "vaporteleport";
133
+ }
134
+ function isBuiltInComponent(tag) {
135
+ if (isTeleportTag(tag)) {
136
+ return "VaporTeleport";
137
+ } else if (isKeepAliveTag(tag)) {
138
+ return "VaporKeepAlive";
139
+ } else if (isTransitionTag(tag)) {
140
+ return "VaporTransition";
141
+ } else if (isTransitionGroupTag(tag)) {
142
+ return "VaporTransitionGroup";
143
+ }
144
+ }
92
145
 
146
+ const generatedVarRE = /^[nxr](\d+)$/;
93
147
  class TransformContext {
94
148
  constructor(ir, node, options = {}) {
95
149
  this.ir = ir;
@@ -101,6 +155,7 @@ class TransformContext {
101
155
  this.template = "";
102
156
  this.childrenTemplate = [];
103
157
  this.dynamic = this.ir.block.dynamic;
158
+ this.imports = [];
104
159
  this.inVOnce = false;
105
160
  this.inVFor = 0;
106
161
  this.comment = [];
@@ -108,10 +163,16 @@ class TransformContext {
108
163
  this.directive = this.ir.directive;
109
164
  this.slots = [];
110
165
  this.globalId = 0;
111
- this.increaseId = () => this.globalId++;
166
+ this.nextIdMap = null;
167
+ this.increaseId = () => {
168
+ const id = getNextId(this.nextIdMap, this.globalId);
169
+ this.globalId = getNextId(this.nextIdMap, id + 1);
170
+ return id;
171
+ };
112
172
  this.options = shared.extend({}, defaultOptions, options);
113
173
  this.root = this;
114
174
  if (options.filename) this.selfName = compilerDom.getSelfName(options.filename);
175
+ this.initNextIdMap();
115
176
  }
116
177
  enterBlock(ir, isVFor = false) {
117
178
  const { block, template, dynamic, childrenTemplate, slots } = this;
@@ -131,18 +192,33 @@ class TransformContext {
131
192
  isVFor && this.inVFor--;
132
193
  };
133
194
  }
195
+ initNextIdMap() {
196
+ const binding = this.root.options.bindingMetadata;
197
+ if (!binding) return;
198
+ const keys = Object.keys(binding);
199
+ if (keys.length === 0) return;
200
+ const numbers = /* @__PURE__ */ new Set();
201
+ for (const name of keys) {
202
+ const m = generatedVarRE.exec(name);
203
+ if (m) numbers.add(Number(m[1]));
204
+ }
205
+ if (numbers.size === 0) return;
206
+ this.globalId = getNextId(this.nextIdMap = buildNextIdMap(numbers), 0);
207
+ }
134
208
  reference() {
135
209
  if (this.dynamic.id !== void 0) return this.dynamic.id;
136
210
  this.dynamic.flags |= 1;
137
211
  return this.dynamic.id = this.increaseId();
138
212
  }
139
213
  pushTemplate(content) {
140
- const existing = this.ir.template.findIndex(
141
- (template) => template === content
142
- );
143
- if (existing !== -1) return existing;
144
- this.ir.template.push(content);
145
- return this.ir.template.length - 1;
214
+ const existingIndex = this.ir.templateIndexMap.get(content);
215
+ if (existingIndex !== void 0) {
216
+ return existingIndex;
217
+ }
218
+ const newIndex = this.ir.template.size;
219
+ this.ir.template.set(content, this.node.ns);
220
+ this.ir.templateIndexMap.set(content, newIndex);
221
+ return newIndex;
146
222
  }
147
223
  registerTemplate() {
148
224
  if (!this.template) return -1;
@@ -204,7 +280,8 @@ function transform(node, options = {}) {
204
280
  type: 0,
205
281
  node,
206
282
  source: node.source,
207
- template: [],
283
+ template: /* @__PURE__ */ new Map(),
284
+ templateIndexMap: /* @__PURE__ */ new Map(),
208
285
  component: /* @__PURE__ */ new Set(),
209
286
  directive: /* @__PURE__ */ new Set(),
210
287
  block: newBlock(node),
@@ -212,6 +289,7 @@ function transform(node, options = {}) {
212
289
  };
213
290
  const context = new TransformContext(ir, node, options);
214
291
  transformNode(context);
292
+ ir.node.imports = context.imports;
215
293
  return ir;
216
294
  }
217
295
  function transformNode(context) {
@@ -265,7 +343,32 @@ function createStructuralDirectiveTransform(name, fn) {
265
343
  }
266
344
  };
267
345
  }
346
+ function buildNextIdMap(nums) {
347
+ const map = /* @__PURE__ */ new Map();
348
+ const arr = Array.from(new Set(nums)).sort((a, b) => a - b);
349
+ if (arr.length === 0) return map;
350
+ for (let i = 0; i < arr.length; i++) {
351
+ let start = arr[i];
352
+ let end = start;
353
+ while (i + 1 < arr.length && arr[i + 1] === end + 1) {
354
+ i++;
355
+ end = arr[i];
356
+ }
357
+ for (let v = start; v <= end; v++) map.set(v, end + 1);
358
+ }
359
+ return map;
360
+ }
361
+ function getNextId(map, n) {
362
+ if (map && map.has(n)) return map.get(n);
363
+ return n;
364
+ }
268
365
 
366
+ const IMPORT_EXP_START = "__IMPORT_EXP_START__";
367
+ const IMPORT_EXP_END = "__IMPORT_EXP_END__";
368
+ const IMPORT_EXPR_RE = new RegExp(
369
+ `${IMPORT_EXP_START}(.*?)${IMPORT_EXP_END}`,
370
+ "g"
371
+ );
269
372
  const NEWLINE = Symbol(`newline` );
270
373
  const LF = Symbol(`line feed` );
271
374
  const INDENT_START = Symbol(`indent start` );
@@ -301,13 +404,13 @@ const DELIMITERS_ARRAY = ["[", "]", ", "];
301
404
  const DELIMITERS_ARRAY_NEWLINE = [
302
405
  ["[", INDENT_START, NEWLINE],
303
406
  [INDENT_END, NEWLINE, "]"],
304
- [", ", NEWLINE]
407
+ [",", NEWLINE]
305
408
  ];
306
409
  const DELIMITERS_OBJECT = ["{ ", " }", ", "];
307
410
  const DELIMITERS_OBJECT_NEWLINE = [
308
411
  ["{", INDENT_START, NEWLINE],
309
412
  [INDENT_END, NEWLINE, "}"],
310
- [", ", NEWLINE]
413
+ [",", NEWLINE]
311
414
  ];
312
415
  function genCall(name, ...frags) {
313
416
  const hasPlaceholder = shared.isArray(name);
@@ -508,15 +611,12 @@ function genExpression(node, context, assignment) {
508
611
  let hasMemberExpression = false;
509
612
  if (ids.length) {
510
613
  const [frag, push] = buildCodeFragment();
511
- const isTSNode = ast && compilerDom.TS_NODE_TYPES.includes(ast.type);
512
614
  ids.sort((a, b) => a.start - b.start).forEach((id, i) => {
513
615
  const start = id.start - 1;
514
616
  const end = id.end - 1;
515
617
  const last = ids[i - 1];
516
- if (!(isTSNode && i === 0)) {
517
- const leadingText = content.slice(last ? last.end - 1 : 0, start);
518
- if (leadingText.length) push([leadingText, -3]);
519
- }
618
+ const leadingText = content.slice(last ? last.end - 1 : 0, start);
619
+ if (leadingText.length) push([leadingText, -3]);
520
620
  const source = content.slice(start, end);
521
621
  const parentStack2 = parentStackMap.get(id);
522
622
  const parent = parentStack2[parentStack2.length - 1];
@@ -536,7 +636,7 @@ function genExpression(node, context, assignment) {
536
636
  parentStack2
537
637
  )
538
638
  );
539
- if (i === ids.length - 1 && end < content.length && !isTSNode) {
639
+ if (i === ids.length - 1 && end < content.length) {
540
640
  push([content.slice(end), -3]);
541
641
  }
542
642
  });
@@ -918,7 +1018,11 @@ function genSetEvent(oper, context) {
918
1018
  const { helper } = context;
919
1019
  const { element, key, keyOverride, value, modifiers, delegate, effect } = oper;
920
1020
  const name = genName();
921
- const handler = genEventHandler(context, value, modifiers);
1021
+ const handler = [
1022
+ `${context.helper("createInvoker")}(`,
1023
+ ...genEventHandler(context, value, modifiers),
1024
+ `)`
1025
+ ];
922
1026
  const eventOptions = genEventOptions();
923
1027
  if (delegate) {
924
1028
  context.delegates.add(key.content);
@@ -979,7 +1083,14 @@ function genEventHandler(context, value, modifiers = { nonKeys: [], keys: [] },
979
1083
  if (compilerDom.isMemberExpression(value, context.options)) {
980
1084
  handlerExp = genExpression(value, context);
981
1085
  if (!isConstantBinding(value, context) && !extraWrap) {
982
- handlerExp = [`e => `, ...handlerExp, `(e)`];
1086
+ const isTSNode = value.ast && compilerDom.TS_NODE_TYPES.includes(value.ast.type);
1087
+ handlerExp = [
1088
+ `e => `,
1089
+ isTSNode ? "(" : "",
1090
+ ...handlerExp,
1091
+ isTSNode ? ")" : "",
1092
+ `(e)`
1093
+ ];
983
1094
  }
984
1095
  } else if (compilerDom.isFnExpression(value, context.options)) {
985
1096
  handlerExp = genExpression(value, context);
@@ -1265,12 +1376,12 @@ function matchPatterns(render, keyProp, idMap) {
1265
1376
  const keyOnlyBindingPatterns = [];
1266
1377
  render.effect = render.effect.filter((effect) => {
1267
1378
  if (keyProp !== void 0) {
1268
- const selector = matchSelectorPattern(effect, keyProp.ast, idMap);
1379
+ const selector = matchSelectorPattern(effect, keyProp.content, idMap);
1269
1380
  if (selector) {
1270
1381
  selectorPatterns.push(selector);
1271
1382
  return false;
1272
1383
  }
1273
- const keyOnly = matchKeyOnlyBindingPattern(effect, keyProp.ast);
1384
+ const keyOnly = matchKeyOnlyBindingPattern(effect, keyProp.content);
1274
1385
  if (keyOnly) {
1275
1386
  keyOnlyBindingPatterns.push(keyOnly);
1276
1387
  return false;
@@ -1283,19 +1394,19 @@ function matchPatterns(render, keyProp, idMap) {
1283
1394
  selectorPatterns
1284
1395
  };
1285
1396
  }
1286
- function matchKeyOnlyBindingPattern(effect, keyAst) {
1397
+ function matchKeyOnlyBindingPattern(effect, key) {
1287
1398
  if (effect.expressions.length === 1) {
1288
- const ast = effect.expressions[0].ast;
1399
+ const { ast, content } = effect.expressions[0];
1289
1400
  if (typeof ast === "object" && ast !== null) {
1290
- if (isKeyOnlyBinding(ast, keyAst)) {
1401
+ if (isKeyOnlyBinding(ast, key, content)) {
1291
1402
  return { effect };
1292
1403
  }
1293
1404
  }
1294
1405
  }
1295
1406
  }
1296
- function matchSelectorPattern(effect, keyAst, idMap) {
1407
+ function matchSelectorPattern(effect, key, idMap) {
1297
1408
  if (effect.expressions.length === 1) {
1298
- const ast = effect.expressions[0].ast;
1409
+ const { ast, content } = effect.expressions[0];
1299
1410
  if (typeof ast === "object" && ast) {
1300
1411
  const matcheds = [];
1301
1412
  estreeWalker.walk(ast, {
@@ -1306,10 +1417,10 @@ function matchSelectorPattern(effect, keyAst, idMap) {
1306
1417
  [left, right],
1307
1418
  [right, left]
1308
1419
  ]) {
1309
- const aIsKey = isKeyOnlyBinding(a, keyAst);
1310
- const bIsKey = isKeyOnlyBinding(b, keyAst);
1420
+ const aIsKey = isKeyOnlyBinding(a, key, content);
1421
+ const bIsKey = isKeyOnlyBinding(b, key, content);
1311
1422
  const bVars = analyzeVariableScopes(b, idMap);
1312
- if (aIsKey && !bIsKey && !bVars.locals.length) {
1423
+ if (aIsKey && !bIsKey && !bVars.length) {
1313
1424
  matcheds.push([a, b]);
1314
1425
  }
1315
1426
  }
@@ -1317,21 +1428,17 @@ function matchSelectorPattern(effect, keyAst, idMap) {
1317
1428
  }
1318
1429
  });
1319
1430
  if (matcheds.length === 1) {
1320
- const [key, selector] = matcheds[0];
1431
+ const [key2, selector] = matcheds[0];
1321
1432
  const content2 = effect.expressions[0].content;
1322
1433
  let hasExtraId = false;
1323
- const parentStackMap = /* @__PURE__ */ new Map();
1324
- const parentStack = [];
1325
1434
  compilerDom.walkIdentifiers(
1326
1435
  ast,
1327
1436
  (id) => {
1328
- if (id.start !== key.start && id.start !== selector.start) {
1437
+ if (id.start !== key2.start && id.start !== selector.start) {
1329
1438
  hasExtraId = true;
1330
1439
  }
1331
- parentStackMap.set(id, parentStack.slice());
1332
1440
  },
1333
- false,
1334
- parentStack
1441
+ false
1335
1442
  );
1336
1443
  if (!hasExtraId) {
1337
1444
  const name = content2.slice(selector.start - 1, selector.end - 1);
@@ -1351,47 +1458,17 @@ function matchSelectorPattern(effect, keyAst, idMap) {
1351
1458
  }
1352
1459
  }
1353
1460
  }
1354
- const content = effect.expressions[0].content;
1355
- if (typeof ast === "object" && ast && ast.type === "ConditionalExpression" && ast.test.type === "BinaryExpression" && ast.test.operator === "===" && ast.test.left.type !== "PrivateName" && compilerDom.isStaticNode(ast.consequent) && compilerDom.isStaticNode(ast.alternate)) {
1356
- const left = ast.test.left;
1357
- const right = ast.test.right;
1358
- for (const [a, b] of [
1359
- [left, right],
1360
- [right, left]
1361
- ]) {
1362
- const aIsKey = isKeyOnlyBinding(a, keyAst);
1363
- const bIsKey = isKeyOnlyBinding(b, keyAst);
1364
- const bVars = analyzeVariableScopes(b, idMap);
1365
- if (aIsKey && !bIsKey && !bVars.locals.length) {
1366
- return {
1367
- effect,
1368
- // @ts-expect-error
1369
- selector: {
1370
- content: content.slice(b.start - 1, b.end - 1),
1371
- ast: b,
1372
- loc: b.loc,
1373
- isStatic: false
1374
- }
1375
- };
1376
- }
1377
- }
1378
- }
1379
1461
  }
1380
1462
  }
1381
1463
  function analyzeVariableScopes(ast, idMap) {
1382
- let globals = [];
1383
1464
  let locals = [];
1384
1465
  const ids = [];
1385
- const parentStackMap = /* @__PURE__ */ new Map();
1386
- const parentStack = [];
1387
1466
  compilerDom.walkIdentifiers(
1388
1467
  ast,
1389
1468
  (id) => {
1390
1469
  ids.push(id);
1391
- parentStackMap.set(id, parentStack.slice());
1392
1470
  },
1393
- false,
1394
- parentStack
1471
+ false
1395
1472
  );
1396
1473
  for (const id of ids) {
1397
1474
  if (shared.isGloballyAllowed(id.name)) {
@@ -1399,17 +1476,15 @@ function analyzeVariableScopes(ast, idMap) {
1399
1476
  }
1400
1477
  if (idMap[id.name]) {
1401
1478
  locals.push(id.name);
1402
- } else {
1403
- globals.push(id.name);
1404
1479
  }
1405
1480
  }
1406
- return { globals, locals };
1481
+ return locals;
1407
1482
  }
1408
- function isKeyOnlyBinding(expr, keyAst) {
1483
+ function isKeyOnlyBinding(expr, key, source) {
1409
1484
  let only = true;
1410
1485
  estreeWalker.walk(expr, {
1411
1486
  enter(node) {
1412
- if (types.isNodesEquivalent(node, keyAst)) {
1487
+ if (source.slice(node.start - 1, node.end - 1) === key) {
1413
1488
  this.skip();
1414
1489
  return;
1415
1490
  }
@@ -1423,10 +1498,15 @@ function isKeyOnlyBinding(expr, keyAst) {
1423
1498
 
1424
1499
  function genSetHtml(oper, context) {
1425
1500
  const { helper } = context;
1426
- const { value, element } = oper;
1501
+ const { value, element, isComponent } = oper;
1427
1502
  return [
1428
1503
  NEWLINE,
1429
- ...genCall(helper("setHtml"), `n${element}`, genExpression(value, context))
1504
+ ...genCall(
1505
+ // use setBlockHtml for component
1506
+ isComponent ? helper("setBlockHtml") : helper("setHtml"),
1507
+ `n${element}`,
1508
+ genExpression(value, context)
1509
+ )
1430
1510
  ];
1431
1511
  }
1432
1512
 
@@ -1469,7 +1549,8 @@ const helpers = {
1469
1549
  setValue: { name: "setValue" },
1470
1550
  setAttr: { name: "setAttr", needKey: true },
1471
1551
  setProp: { name: "setProp", needKey: true },
1472
- setDOMProp: { name: "setDOMProp", needKey: true }};
1552
+ setDOMProp: { name: "setDOMProp", needKey: true }
1553
+ };
1473
1554
  function genSetProp(oper, context) {
1474
1555
  const { helper } = context;
1475
1556
  const {
@@ -1484,12 +1565,14 @@ function genSetProp(oper, context) {
1484
1565
  [helper(resolvedHelper.name), null],
1485
1566
  `n${oper.element}`,
1486
1567
  resolvedHelper.needKey ? genExpression(key, context) : false,
1487
- propValue
1568
+ propValue,
1569
+ resolvedHelper.isSVG && "true"
1488
1570
  )
1489
1571
  ];
1490
1572
  }
1491
1573
  function genDynamicProps$1(oper, context) {
1492
1574
  const { helper } = context;
1575
+ const isSVG = shared.isSVGTag(oper.tag);
1493
1576
  const values = oper.props.map(
1494
1577
  (props) => Array.isArray(props) ? genLiteralObjectProps(props, context) : props.kind === 1 ? genLiteralObjectProps([props], context) : genExpression(props.value, context)
1495
1578
  );
@@ -1499,7 +1582,8 @@ function genDynamicProps$1(oper, context) {
1499
1582
  helper("setDynamicProps"),
1500
1583
  `n${oper.element}`,
1501
1584
  genMulti(DELIMITERS_ARRAY, ...values),
1502
- oper.root && "true"
1585
+ oper.root && "true",
1586
+ isSVG && "true"
1503
1587
  )
1504
1588
  ];
1505
1589
  }
@@ -1515,7 +1599,7 @@ function genLiteralObjectProps(props, context) {
1515
1599
  }
1516
1600
  function genPropKey({ key: node, modifier, runtimeCamelize, handler, handlerModifiers }, context) {
1517
1601
  const { helper } = context;
1518
- const handlerModifierPostfix = handlerModifiers ? handlerModifiers.map(shared.capitalize).join("") : "";
1602
+ const handlerModifierPostfix = handlerModifiers && handlerModifiers.options ? handlerModifiers.options.map(shared.capitalize).join("") : "";
1519
1603
  if (node.isStatic) {
1520
1604
  const keyName = (handler ? shared.toHandlerKey(node.content) : node.content) + handlerModifierPostfix;
1521
1605
  return [
@@ -1552,6 +1636,10 @@ function genPropValue(values, context) {
1552
1636
  }
1553
1637
  function getRuntimeHelper(tag, key, modifier) {
1554
1638
  const tagName = tag.toUpperCase();
1639
+ const isSVG = shared.isSVGTag(tag);
1640
+ if (isSVG) {
1641
+ return shared.extend({ isSVG: true }, helpers.setAttr);
1642
+ }
1555
1643
  if (modifier) {
1556
1644
  if (modifier === ".") {
1557
1645
  return getSpecialHelper(key, tagName) || helpers.setDOMProp;
@@ -1566,9 +1654,6 @@ function getRuntimeHelper(tag, key, modifier) {
1566
1654
  if (/aria[A-Z]/.test(key)) {
1567
1655
  return helpers.setDOMProp;
1568
1656
  }
1569
- if (shared.isSVGTag(tag)) {
1570
- return helpers.setAttr;
1571
- }
1572
1657
  if (shared.shouldSetAsAttr(tagName, key) || key.includes("-")) {
1573
1658
  return helpers.setAttr;
1574
1659
  }
@@ -1590,6 +1675,7 @@ function getSpecialHelper(keyName, tagName) {
1590
1675
 
1591
1676
  const setTemplateRefIdent = `_setTemplateRef`;
1592
1677
  function genSetTemplateRef(oper, context) {
1678
+ const [refValue, refKey] = genRefValue(oper.value, context);
1593
1679
  return [
1594
1680
  NEWLINE,
1595
1681
  oper.effect && `r${oper.element} = `,
@@ -1597,9 +1683,10 @@ function genSetTemplateRef(oper, context) {
1597
1683
  setTemplateRefIdent,
1598
1684
  // will be generated in root scope
1599
1685
  `n${oper.element}`,
1600
- genRefValue(oper.value, context),
1686
+ refValue,
1601
1687
  oper.effect ? `r${oper.element}` : oper.refFor ? "void 0" : void 0,
1602
- oper.refFor && "true"
1688
+ oper.refFor && "true",
1689
+ refKey
1603
1690
  )
1604
1691
  ];
1605
1692
  }
@@ -1610,25 +1697,30 @@ function genRefValue(value, context) {
1610
1697
  if (value && context.options.inline) {
1611
1698
  const binding = context.options.bindingMetadata[value.content];
1612
1699
  if (binding === "setup-let" || binding === "setup-ref" || binding === "setup-maybe-ref") {
1613
- return [value.content];
1700
+ return [[value.content], JSON.stringify(value.content)];
1614
1701
  }
1615
1702
  }
1616
- return genExpression(value, context);
1703
+ return [genExpression(value, context)];
1617
1704
  }
1618
1705
 
1619
1706
  function genSetText(oper, context) {
1620
1707
  const { helper } = context;
1621
- const { element, values, generated, jsx } = oper;
1708
+ const { element, values, generated, jsx, isComponent } = oper;
1622
1709
  const texts = combineValues(values, context, jsx);
1623
1710
  return [
1624
1711
  NEWLINE,
1625
- ...genCall(helper("setText"), `${generated ? "x" : "n"}${element}`, texts)
1712
+ ...genCall(
1713
+ // use setBlockText for component
1714
+ isComponent ? helper("setBlockText") : helper("setText"),
1715
+ `${generated && !isComponent ? "x" : "n"}${element}`,
1716
+ texts
1717
+ )
1626
1718
  ];
1627
1719
  }
1628
1720
  function combineValues(values, context, jsx) {
1629
1721
  return values.flatMap((value, i) => {
1630
1722
  let exp = genExpression(value, context);
1631
- if (!jsx && getLiteralExpressionValue(value) == null) {
1723
+ if (!jsx && getLiteralExpressionValue(value, true) == null) {
1632
1724
  exp = genCall(context.helper("toDisplayString"), exp);
1633
1725
  }
1634
1726
  if (i > 0) {
@@ -1640,18 +1732,21 @@ function combineValues(values, context, jsx) {
1640
1732
  function genGetTextChild(oper, context) {
1641
1733
  return [
1642
1734
  NEWLINE,
1643
- `const x${oper.parent} = ${context.helper("child")}(n${oper.parent})`
1735
+ `const x${oper.parent} = ${context.helper("txt")}(n${oper.parent})`
1644
1736
  ];
1645
1737
  }
1646
1738
 
1647
1739
  function genVShow(oper, context) {
1740
+ const { deferred, element } = oper;
1648
1741
  return [
1649
1742
  NEWLINE,
1650
- ...genCall(context.helper("applyVShow"), `n${oper.element}`, [
1743
+ deferred ? `deferredApplyVShows.push(() => ` : void 0,
1744
+ ...genCall(context.helper("applyVShow"), `n${element}`, [
1651
1745
  `() => (`,
1652
1746
  ...genExpression(oper.dir.exp, context),
1653
1747
  `)`
1654
- ])
1748
+ ]),
1749
+ deferred ? `)` : void 0
1655
1750
  ];
1656
1751
  }
1657
1752
 
@@ -1768,7 +1863,7 @@ function genCreateComponent(operation, context) {
1768
1863
  ...inlineHandlers,
1769
1864
  `const n${operation.id} = `,
1770
1865
  ...genCall(
1771
- operation.dynamic && !operation.dynamic.isStatic ? helper("createDynamicComponent") : operation.asset ? helper("createComponentWithFallback") : helper("createComponent"),
1866
+ operation.dynamic && !operation.dynamic.isStatic ? helper("createDynamicComponent") : operation.isCustomElement ? helper("createPlainElement") : operation.asset ? helper("createComponentWithFallback") : helper("createComponent"),
1772
1867
  tag,
1773
1868
  rawProps,
1774
1869
  rawSlots,
@@ -1778,7 +1873,9 @@ function genCreateComponent(operation, context) {
1778
1873
  ...genDirectivesForElement(operation.id, context)
1779
1874
  ];
1780
1875
  function genTag() {
1781
- if (operation.dynamic) {
1876
+ if (operation.isCustomElement) {
1877
+ return JSON.stringify(operation.tag);
1878
+ } else if (operation.dynamic) {
1782
1879
  if (operation.dynamic.isStatic) {
1783
1880
  return genCall(
1784
1881
  helper("resolveDynamicComponent"),
@@ -1790,8 +1887,14 @@ function genCreateComponent(operation, context) {
1790
1887
  } else if (operation.asset) {
1791
1888
  return compilerDom.toValidAssetId(operation.tag, "component");
1792
1889
  } else {
1890
+ const { tag: tag2 } = operation;
1891
+ const builtInTag = isBuiltInComponent(tag2);
1892
+ if (builtInTag) {
1893
+ helper(builtInTag);
1894
+ return `_${builtInTag}`;
1895
+ }
1793
1896
  return genExpression(
1794
- shared.extend(compilerDom.createSimpleExpression(operation.tag, false), { ast: null }),
1897
+ shared.extend(compilerDom.createSimpleExpression(tag2, false), { ast: null }),
1795
1898
  context
1796
1899
  );
1797
1900
  }
@@ -1815,7 +1918,10 @@ function processInlineHandlers(props, context) {
1815
1918
  prop.values.forEach((value, i2) => {
1816
1919
  const isMemberExp = compilerDom.isMemberExpression(value, context.options);
1817
1920
  if (!isMemberExp) {
1818
- const name = getUniqueHandlerName(context, `_on_${prop.key.content}`);
1921
+ const name = getUniqueHandlerName(
1922
+ context,
1923
+ `_on_${prop.key.content.replace(/-/g, "_")}`
1924
+ );
1819
1925
  handlers.push({ name, value });
1820
1926
  ids[name] = null;
1821
1927
  prop.values[i2] = shared.extend({ ast: null }, compilerDom.createSimpleExpression(name));
@@ -1882,7 +1988,7 @@ function genProp(prop, context, isStatic) {
1882
1988
  ...prop.handler ? genEventHandler(
1883
1989
  context,
1884
1990
  prop.values[0],
1885
- void 0,
1991
+ prop.handlerModifiers,
1886
1992
  true
1887
1993
  ) : isStatic ? ["() => (", ...values, ")"] : values,
1888
1994
  ...prop.model ? [...genModelEvent(prop, context), ...genModelModifiers(prop, context)] : []
@@ -1896,7 +2002,7 @@ function genModelEvent(prop, context) {
1896
2002
  function genModelModifiers(prop, context) {
1897
2003
  const { key, modelModifiers } = prop;
1898
2004
  if (!modelModifiers || !modelModifiers.length) return [];
1899
- const modifiersKey = key.isStatic ? key.content === "modelValue" ? [`modelModifiers`] : [`${key.content}Modifiers`] : ["[", ...genExpression(key, context), ' + "Modifiers"]'];
2005
+ const modifiersKey = key.isStatic ? [shared.getModifierPropName(key.content)] : ["[", ...genExpression(key, context), ' + "Modifiers"]'];
1900
2006
  const modifiersVal = genDirectiveModifiers(modelModifiers);
1901
2007
  return [",", NEWLINE, ...modifiersKey, `: () => ({ ${modifiersVal} })`];
1902
2008
  }
@@ -2014,7 +2120,7 @@ function genSlotBlockWithProps(oper, context) {
2014
2120
  let propsName;
2015
2121
  let exitScope;
2016
2122
  let depth;
2017
- const { props } = oper;
2123
+ const { props, key, node } = oper;
2018
2124
  const idsOfProps = /* @__PURE__ */ new Set();
2019
2125
  if (props) {
2020
2126
  rawProps = props.content;
@@ -2036,17 +2142,36 @@ function genSlotBlockWithProps(oper, context) {
2036
2142
  idsOfProps.forEach(
2037
2143
  (id) => idMap[id] = isDestructureAssignment ? `${propsName}[${JSON.stringify(id)}]` : null
2038
2144
  );
2039
- const blockFn = context.withId(
2145
+ let blockFn = context.withId(
2040
2146
  () => genBlock(oper, context, [propsName]),
2041
2147
  idMap
2042
2148
  );
2043
2149
  exitScope && exitScope();
2150
+ if (key) {
2151
+ blockFn = [
2152
+ `() => {`,
2153
+ INDENT_START,
2154
+ NEWLINE,
2155
+ `return `,
2156
+ ...genCall(
2157
+ context.helper("createKeyedFragment"),
2158
+ [`() => `, ...genExpression(key, context)],
2159
+ blockFn
2160
+ ),
2161
+ INDENT_END,
2162
+ NEWLINE,
2163
+ `}`
2164
+ ];
2165
+ }
2166
+ if (node.type === 1) {
2167
+ blockFn = [`${context.helper("withVaporCtx")}(`, ...blockFn, `)`];
2168
+ }
2044
2169
  return blockFn;
2045
2170
  }
2046
2171
 
2047
2172
  function genSlotOutlet(oper, context) {
2048
2173
  const { helper } = context;
2049
- const { id, name, fallback } = oper;
2174
+ const { id, name, fallback, noSlotted } = oper;
2050
2175
  const [frag, push] = buildCodeFragment();
2051
2176
  const nameExpr = name.isStatic ? genExpression(name, context) : ["() => (", ...genExpression(name, context), ")"];
2052
2177
  let fallbackArg;
@@ -2060,7 +2185,9 @@ function genSlotOutlet(oper, context) {
2060
2185
  helper("createSlot"),
2061
2186
  nameExpr,
2062
2187
  genRawProps(oper.props, context) || "null",
2063
- fallbackArg
2188
+ fallbackArg,
2189
+ noSlotted && "true"
2190
+ // noSlotted
2064
2191
  )
2065
2192
  );
2066
2193
  return frag;
@@ -2176,34 +2303,53 @@ function genEffect({ operations }, context) {
2176
2303
  return frag;
2177
2304
  }
2178
2305
  function genInsertionState(operation, context) {
2306
+ const { parent, anchor, append, last } = operation;
2179
2307
  return [
2180
2308
  NEWLINE,
2181
2309
  ...genCall(
2182
2310
  context.helper("setInsertionState"),
2183
- `n${operation.parent}`,
2184
- operation.anchor == null ? void 0 : operation.anchor === -1 ? `0` : `n${operation.anchor}`
2311
+ `n${parent}`,
2312
+ anchor == null ? void 0 : anchor === -1 ? `0` : append ? (
2313
+ // null or anchor > 0 for append
2314
+ // anchor > 0 is the logical index of append node - used for locate node during hydration
2315
+ anchor === 0 ? "null" : `${anchor}`
2316
+ ) : `n${anchor}`,
2317
+ last && "true"
2185
2318
  )
2186
2319
  ];
2187
2320
  }
2188
2321
 
2189
- function genTemplates(templates, rootIndex, { helper }) {
2190
- return templates.map(
2191
- (template, i) => `const t${i} = ${helper("template")}(${JSON.stringify(
2192
- template
2193
- )}${i === rootIndex ? ", true" : ""})
2322
+ function genTemplates(templates, rootIndex, context) {
2323
+ const result = [];
2324
+ let i = 0;
2325
+ templates.forEach((ns, template) => {
2326
+ result.push(
2327
+ `const ${context.tName(i)} = ${context.helper("template")}(${JSON.stringify(
2328
+ template
2329
+ ).replace(
2330
+ // replace import expressions with string concatenation
2331
+ IMPORT_EXPR_RE,
2332
+ `" + $1 + "`
2333
+ )}${i === rootIndex ? ", true" : ns ? ", false" : ""}${ns ? `, ${ns}` : ""})
2194
2334
  `
2195
- ).join("");
2335
+ );
2336
+ i++;
2337
+ });
2338
+ return result.join("");
2196
2339
  }
2197
2340
  function genSelf(dynamic, context) {
2198
2341
  const [frag, push] = buildCodeFragment();
2199
- const { id, template, operation } = dynamic;
2342
+ const { id, template, operation, hasDynamicChild } = dynamic;
2200
2343
  if (id !== void 0 && template !== void 0) {
2201
- push(NEWLINE, `const n${id} = t${template}()`);
2344
+ push(NEWLINE, `const n${id} = ${context.tName(template)}()`);
2202
2345
  push(...genDirectivesForElement(id, context));
2203
2346
  }
2204
2347
  if (operation) {
2205
2348
  push(...genOperationWithInsertionState(operation, context));
2206
2349
  }
2350
+ if (hasDynamicChild) {
2351
+ push(...genChildren(dynamic, context, push, `n${id}`));
2352
+ }
2207
2353
  return frag;
2208
2354
  }
2209
2355
  function genChildren(dynamic, context, pushBlock, from = `n${dynamic.id}`) {
@@ -2212,51 +2358,65 @@ function genChildren(dynamic, context, pushBlock, from = `n${dynamic.id}`) {
2212
2358
  const { children } = dynamic;
2213
2359
  let offset = 0;
2214
2360
  let prev;
2215
- const childrenToGen = [];
2361
+ let ifBranchCount = 0;
2362
+ let prependCount = 0;
2216
2363
  for (const [index, child] of children.entries()) {
2364
+ if (child.operation && child.operation.anchor === -1) {
2365
+ prependCount++;
2366
+ }
2217
2367
  if (child.flags & 2) {
2218
2368
  offset--;
2369
+ } else if (child.ifBranch) {
2370
+ ifBranchCount++;
2219
2371
  }
2220
2372
  const id = child.flags & 1 ? child.flags & 4 ? child.anchor : child.id : void 0;
2221
2373
  if (id === void 0 && !child.hasDynamicChild) {
2222
2374
  push(...genSelf(child, context));
2223
2375
  continue;
2224
2376
  }
2225
- const elementIndex = Number(index) + offset;
2226
- const variable = id === void 0 ? `p${context.block.tempId++}` : `n${id}`;
2377
+ const elementIndex = index + offset;
2378
+ const logicalIndex = elementIndex - ifBranchCount + prependCount;
2379
+ const variable = id === void 0 ? context.pName(context.block.tempId++) : `n${id}`;
2227
2380
  pushBlock(NEWLINE, `const ${variable} = `);
2228
2381
  if (prev) {
2229
2382
  if (elementIndex - prev[1] === 1) {
2230
- pushBlock(...genCall(helper("next"), prev[0]));
2383
+ pushBlock(...genCall(helper("next"), prev[0], String(logicalIndex)));
2231
2384
  } else {
2232
- pushBlock(...genCall(helper("nthChild"), from, String(elementIndex)));
2385
+ pushBlock(
2386
+ ...genCall(
2387
+ helper("nthChild"),
2388
+ from,
2389
+ String(elementIndex),
2390
+ String(logicalIndex)
2391
+ )
2392
+ );
2233
2393
  }
2234
2394
  } else {
2235
2395
  if (elementIndex === 0) {
2236
- pushBlock(...genCall(helper("child"), from));
2396
+ pushBlock(...genCall(helper("child"), from, String(logicalIndex)));
2237
2397
  } else {
2238
2398
  let init = genCall(helper("child"), from);
2239
2399
  if (elementIndex === 1) {
2240
- init = genCall(helper("next"), init);
2400
+ init = genCall(helper("next"), init, String(logicalIndex));
2241
2401
  } else if (elementIndex > 1) {
2242
- init = genCall(helper("nthChild"), from, String(elementIndex));
2402
+ init = genCall(
2403
+ helper("nthChild"),
2404
+ from,
2405
+ String(elementIndex),
2406
+ String(logicalIndex)
2407
+ );
2243
2408
  }
2244
2409
  pushBlock(...init);
2245
2410
  }
2246
2411
  }
2247
- if (id === child.anchor) {
2412
+ if (id === child.anchor && !child.hasDynamicChild) {
2248
2413
  push(...genSelf(child, context));
2249
2414
  }
2250
2415
  if (id !== void 0) {
2251
2416
  push(...genDirectivesForElement(id, context));
2252
2417
  }
2253
2418
  prev = [variable, elementIndex];
2254
- childrenToGen.push([child, variable]);
2255
- }
2256
- if (childrenToGen.length) {
2257
- for (const [child, from2] of childrenToGen) {
2258
- push(...genChildren(child, context, pushBlock, from2));
2259
- }
2419
+ push(...genChildren(child, context, pushBlock, variable));
2260
2420
  }
2261
2421
  return frag;
2262
2422
  }
@@ -2275,8 +2435,11 @@ function genBlock(oper, context, args = [], root) {
2275
2435
  }
2276
2436
  function genBlockContent(block, context, root, genEffectsExtraFrag) {
2277
2437
  const [frag, push] = buildCodeFragment();
2278
- const { dynamic, effect, operation, returns } = block;
2438
+ const { dynamic, effect, operation, returns, key } = block;
2279
2439
  const resetBlock = context.enterBlock(block);
2440
+ if (block.hasDeferredVShow) {
2441
+ push(NEWLINE, `const deferredApplyVShows = []`);
2442
+ }
2280
2443
  if (root) {
2281
2444
  for (let name of context.ir.component) {
2282
2445
  const id = compilerDom.toValidAssetId(name, "component");
@@ -2299,10 +2462,21 @@ function genBlockContent(block, context, root, genEffectsExtraFrag) {
2299
2462
  push(...genSelf(child, context));
2300
2463
  }
2301
2464
  for (const child of dynamic.children) {
2302
- push(...genChildren(child, context, push, `n${child.id}`));
2465
+ if (!child.hasDynamicChild) {
2466
+ push(...genChildren(child, context, push, `n${child.id}`));
2467
+ }
2303
2468
  }
2304
2469
  push(...genOperations(operation, context));
2305
2470
  push(...genEffects(effect, context, genEffectsExtraFrag));
2471
+ if (block.hasDeferredVShow) {
2472
+ push(NEWLINE, `deferredApplyVShows.forEach(fn => fn())`);
2473
+ }
2474
+ if (dynamic.needsKey) {
2475
+ for (const child of dynamic.children) {
2476
+ const keyValue = key ? genExpression(key, context) : JSON.stringify(child.id);
2477
+ push(NEWLINE, `n${child.id}.$key = `, ...keyValue);
2478
+ }
2479
+ }
2306
2480
  push(NEWLINE, `return `);
2307
2481
  const returnNodes = returns.map((n) => `n${n}`);
2308
2482
  const returnsCode = returnNodes.length > 1 ? genMulti(DELIMITERS_ARRAY, ...returnNodes) : [returnNodes[0] || "null"];
@@ -2320,18 +2494,34 @@ function genBlockContent(block, context, root, genEffectsExtraFrag) {
2320
2494
  }
2321
2495
  }
2322
2496
 
2497
+ const idWithTrailingDigitsRE = /^([A-Za-z_$][\w$]*)(\d+)$/;
2323
2498
  class CodegenContext {
2324
2499
  constructor(ir, options) {
2325
2500
  this.ir = ir;
2326
- this.helpers = /* @__PURE__ */ new Set([]);
2501
+ this.bindingNames = /* @__PURE__ */ new Set();
2502
+ this.helpers = /* @__PURE__ */ new Map();
2327
2503
  this.helper = (name) => {
2328
- this.helpers.add(name);
2329
- return `_${name}`;
2504
+ if (this.helpers.has(name)) {
2505
+ return this.helpers.get(name);
2506
+ }
2507
+ const base = `_${name}`;
2508
+ if (this.bindingNames.size === 0 || !this.bindingNames.has(base)) {
2509
+ this.helpers.set(name, base);
2510
+ return base;
2511
+ }
2512
+ const map = this.nextIdMap.get(base);
2513
+ const alias = `${base}${getNextId(map, 1)}`;
2514
+ this.helpers.set(name, alias);
2515
+ return alias;
2330
2516
  };
2331
2517
  this.delegates = /* @__PURE__ */ new Set();
2332
2518
  this.identifiers = /* @__PURE__ */ Object.create(null);
2333
2519
  this.seenInlineHandlerNames = /* @__PURE__ */ Object.create(null);
2334
2520
  this.scopeLevel = 0;
2521
+ this.templateVars = /* @__PURE__ */ new Map();
2522
+ this.nextIdMap = /* @__PURE__ */ new Map();
2523
+ this.lastIdMap = /* @__PURE__ */ new Map();
2524
+ this.lastTIndex = -1;
2335
2525
  const defaultOptions = {
2336
2526
  mode: "module",
2337
2527
  prefixIdentifiers: true,
@@ -2350,6 +2540,10 @@ class CodegenContext {
2350
2540
  };
2351
2541
  this.options = shared.extend(defaultOptions, options);
2352
2542
  this.block = ir.block;
2543
+ this.bindingNames = new Set(
2544
+ this.options.bindingMetadata ? Object.keys(this.options.bindingMetadata) : []
2545
+ );
2546
+ this.initNextIdMap();
2353
2547
  }
2354
2548
  withId(fn, map) {
2355
2549
  const { identifiers } = this;
@@ -2370,11 +2564,47 @@ class CodegenContext {
2370
2564
  enterScope() {
2371
2565
  return [this.scopeLevel++, () => this.scopeLevel--];
2372
2566
  }
2567
+ initNextIdMap() {
2568
+ if (this.bindingNames.size === 0) return;
2569
+ const map = /* @__PURE__ */ new Map();
2570
+ for (const name of this.bindingNames) {
2571
+ const m = idWithTrailingDigitsRE.exec(name);
2572
+ if (!m) continue;
2573
+ const prefix = m[1];
2574
+ const num = Number(m[2]);
2575
+ let set = map.get(prefix);
2576
+ if (!set) map.set(prefix, set = /* @__PURE__ */ new Set());
2577
+ set.add(num);
2578
+ }
2579
+ for (const [prefix, nums] of map) {
2580
+ this.nextIdMap.set(prefix, buildNextIdMap(nums));
2581
+ }
2582
+ }
2583
+ tName(i) {
2584
+ let name = this.templateVars.get(i);
2585
+ if (name) return name;
2586
+ const map = this.nextIdMap.get("t");
2587
+ let lastId = this.lastIdMap.get("t") || -1;
2588
+ for (let j = this.lastTIndex + 1; j <= i; j++) {
2589
+ this.templateVars.set(
2590
+ j,
2591
+ name = `t${lastId = getNextId(map, Math.max(j, lastId + 1))}`
2592
+ );
2593
+ }
2594
+ this.lastIdMap.set("t", lastId);
2595
+ this.lastTIndex = i;
2596
+ return name;
2597
+ }
2598
+ pName(i) {
2599
+ const map = this.nextIdMap.get("p");
2600
+ let lastId = this.lastIdMap.get("p") || -1;
2601
+ this.lastIdMap.set("p", lastId = getNextId(map, Math.max(i, lastId + 1)));
2602
+ return `p${lastId}`;
2603
+ }
2373
2604
  }
2374
2605
  function generate(ir, options = {}) {
2375
2606
  const [frag, push] = buildCodeFragment();
2376
2607
  const context = new CodegenContext(ir, options);
2377
- const { helpers } = context;
2378
2608
  const { inline, bindingMetadata } = options;
2379
2609
  const functionName = "render";
2380
2610
  const args = ["_ctx"];
@@ -2401,7 +2631,7 @@ function generate(ir, options = {}) {
2401
2631
  }
2402
2632
  const delegates = genDelegates(context);
2403
2633
  const templates = genTemplates(ir.template, ir.rootTemplateIndex, context);
2404
- const imports = genHelperImports(context);
2634
+ const imports = genHelperImports(context) + genAssetImports(context);
2405
2635
  const preamble = imports + templates + delegates;
2406
2636
  const newlineCount = [...preamble].filter((c) => c === "\n").length;
2407
2637
  if (newlineCount && !inline) {
@@ -2416,7 +2646,7 @@ function generate(ir, options = {}) {
2416
2646
  ast: ir,
2417
2647
  preamble,
2418
2648
  map: map && map.toJSON(),
2419
- helpers
2649
+ helpers: new Set(Array.from(context.helpers.keys()))
2420
2650
  };
2421
2651
  }
2422
2652
  function genDelegates({ delegates, helper }) {
@@ -2425,10 +2655,21 @@ function genDelegates({ delegates, helper }) {
2425
2655
  ...Array.from(delegates).map((v) => `"${v}"`)
2426
2656
  ).join("") + "\n" : "";
2427
2657
  }
2428
- function genHelperImports({ helpers, helper, options }) {
2658
+ function genHelperImports({ helpers, options }) {
2429
2659
  let imports = "";
2430
2660
  if (helpers.size) {
2431
- imports += `import { ${[...helpers].map((h) => `${h} as _${h}`).join(", ")} } from '${options.runtimeModuleName}';
2661
+ imports += `import { ${Array.from(helpers).map(([h, alias]) => `${h} as ${alias}`).join(", ")} } from '${options.runtimeModuleName}';
2662
+ `;
2663
+ }
2664
+ return imports;
2665
+ }
2666
+ function genAssetImports({ ir }) {
2667
+ const assetImports = ir.node.imports;
2668
+ let imports = "";
2669
+ for (const assetImport of assetImports) {
2670
+ const exp = assetImport.exp;
2671
+ const name = exp.content;
2672
+ imports += `import ${name} from '${assetImport.path}';
2432
2673
  `;
2433
2674
  }
2434
2675
  return imports;
@@ -2461,15 +2702,17 @@ const transformChildren = (node, context) => {
2461
2702
  };
2462
2703
  function processDynamicChildren(context) {
2463
2704
  let prevDynamics = [];
2464
- let hasStaticTemplate = false;
2705
+ let staticCount = 0;
2706
+ let dynamicCount = 0;
2707
+ let lastInsertionChild;
2465
2708
  const children = context.dynamic.children;
2466
2709
  for (const [index, child] of children.entries()) {
2467
2710
  if (child.flags & 4) {
2468
- prevDynamics.push(child);
2711
+ prevDynamics.push(lastInsertionChild = child);
2469
2712
  }
2470
2713
  if (!(child.flags & 2)) {
2471
2714
  if (prevDynamics.length) {
2472
- if (hasStaticTemplate) {
2715
+ if (staticCount) {
2473
2716
  context.childrenTemplate[index - prevDynamics.length] = `<!>`;
2474
2717
  prevDynamics[0].flags -= 2;
2475
2718
  const anchor = prevDynamics[0].anchor = context.increaseId();
@@ -2482,27 +2725,38 @@ function processDynamicChildren(context) {
2482
2725
  /* prepend */
2483
2726
  );
2484
2727
  }
2728
+ dynamicCount += prevDynamics.length;
2485
2729
  prevDynamics = [];
2486
2730
  }
2487
- hasStaticTemplate = true;
2731
+ staticCount++;
2488
2732
  }
2489
2733
  }
2490
2734
  if (prevDynamics.length) {
2491
- registerInsertion(prevDynamics, context);
2735
+ registerInsertion(
2736
+ prevDynamics,
2737
+ context,
2738
+ // the logical index of append child
2739
+ dynamicCount + staticCount,
2740
+ true
2741
+ );
2742
+ }
2743
+ if (lastInsertionChild && lastInsertionChild.operation) {
2744
+ lastInsertionChild.operation.last = true;
2492
2745
  }
2493
2746
  }
2494
- function registerInsertion(dynamics, context, anchor) {
2747
+ function registerInsertion(dynamics, context, anchor, append) {
2495
2748
  for (const child of dynamics) {
2496
2749
  if (child.template != null) {
2497
2750
  context.registerOperation({
2498
2751
  type: 9,
2499
2752
  elements: dynamics.map((child2) => child2.id),
2500
2753
  parent: context.reference(),
2501
- anchor
2754
+ anchor: append ? void 0 : anchor
2502
2755
  });
2503
2756
  } else if (child.operation && isBlockOperation(child.operation)) {
2504
2757
  child.operation.parent = context.reference();
2505
2758
  child.operation.anchor = anchor;
2759
+ child.operation.append = append;
2506
2760
  }
2507
2761
  }
2508
2762
  }
@@ -2527,7 +2781,8 @@ const transformElement = (node, context) => {
2527
2781
  ({ node } = context);
2528
2782
  if (!(node.type === 1 && (node.tagType === 0 || node.tagType === 1)))
2529
2783
  return;
2530
- const isComponent = node.tagType === 1;
2784
+ const isCustomElement = !!context.options.isCustomElement(node.tag);
2785
+ const isComponent = node.tagType === 1 || isCustomElement;
2531
2786
  const isDynamicComponent = isComponentTag(node.tag);
2532
2787
  const propsResult = buildProps(
2533
2788
  node,
@@ -2540,14 +2795,15 @@ const transformElement = (node, context) => {
2540
2795
  while (parent && parent.parent && parent.node.type === 1 && parent.node.tagType === 3) {
2541
2796
  parent = parent.parent;
2542
2797
  }
2543
- const singleRoot = context.root === parent && parent.node.children.filter((child) => child.type !== 3).length === 1;
2798
+ const singleRoot = context.root === parent && parent.node.children.filter((child) => child.type !== 3).length === 1 || isCustomElement;
2544
2799
  if (isComponent) {
2545
2800
  transformComponentElement(
2546
2801
  node,
2547
2802
  propsResult,
2548
2803
  singleRoot,
2549
2804
  context,
2550
- isDynamicComponent
2805
+ isDynamicComponent,
2806
+ isCustomElement
2551
2807
  );
2552
2808
  } else {
2553
2809
  transformNativeElement(
@@ -2560,16 +2816,21 @@ const transformElement = (node, context) => {
2560
2816
  }
2561
2817
  };
2562
2818
  };
2563
- function transformComponentElement(node, propsResult, singleRoot, context, isDynamicComponent) {
2819
+ function transformComponentElement(node, propsResult, singleRoot, context, isDynamicComponent, isCustomElement) {
2564
2820
  const dynamicComponent = isDynamicComponent ? resolveDynamicComponent(node) : void 0;
2565
2821
  let { tag } = node;
2566
2822
  let asset = true;
2567
- if (!dynamicComponent) {
2823
+ if (!dynamicComponent && !isCustomElement) {
2568
2824
  const fromSetup = resolveSetupReference(tag, context);
2569
2825
  if (fromSetup) {
2570
2826
  tag = fromSetup;
2571
2827
  asset = false;
2572
2828
  }
2829
+ const builtInTag = isBuiltInComponent(tag);
2830
+ if (builtInTag) {
2831
+ tag = builtInTag;
2832
+ asset = false;
2833
+ }
2573
2834
  const dotIndex = tag.indexOf(".");
2574
2835
  if (dotIndex > 0) {
2575
2836
  const ns = resolveSetupReference(tag.slice(0, dotIndex), context);
@@ -2595,7 +2856,8 @@ function transformComponentElement(node, propsResult, singleRoot, context, isDyn
2595
2856
  root: singleRoot && !context.inVFor,
2596
2857
  slots: [...context.slots],
2597
2858
  once: context.inVOnce,
2598
- dynamic: dynamicComponent
2859
+ dynamic: dynamicComponent,
2860
+ isCustomElement
2599
2861
  };
2600
2862
  context.slots = [];
2601
2863
  }
@@ -2626,6 +2888,7 @@ function resolveSetupReference(name, context) {
2626
2888
  const PascalName = shared.capitalize(camelName);
2627
2889
  return bindings[name] ? name : bindings[camelName] ? camelName : bindings[PascalName] ? PascalName : void 0;
2628
2890
  }
2891
+ const dynamicKeys = ["indeterminate"];
2629
2892
  function transformNativeElement(node, propsResult, singleRoot, context, getEffectIndex) {
2630
2893
  const { tag } = node;
2631
2894
  const { scopeId } = context.options;
@@ -2641,16 +2904,22 @@ function transformNativeElement(node, propsResult, singleRoot, context, getEffec
2641
2904
  type: 3,
2642
2905
  element: context.reference(),
2643
2906
  props: dynamicArgs,
2644
- root: singleRoot
2907
+ root: singleRoot,
2908
+ tag
2645
2909
  },
2646
2910
  getEffectIndex
2647
2911
  );
2648
2912
  } else {
2649
2913
  for (const prop of propsResult[1]) {
2650
2914
  const { key, values } = prop;
2651
- if (key.isStatic && values.length === 1 && values[0].isStatic) {
2915
+ if (context.imports.some(
2916
+ (imported) => values[0].content.includes(imported.exp.content)
2917
+ )) {
2918
+ template += ` ${key.content}="${IMPORT_EXP_START}${values[0].content}${IMPORT_EXP_END}"`;
2919
+ } else if (key.isStatic && values.length === 1 && (values[0].isStatic || values[0].content === "''") && !dynamicKeys.includes(key.content)) {
2652
2920
  template += ` ${key.content}`;
2653
- if (values[0].content) template += `="${values[0].content}"`;
2921
+ if (values[0].content)
2922
+ template += `="${values[0].content === "''" ? "" : values[0].content}"`;
2654
2923
  } else {
2655
2924
  dynamicProps.push(key.content);
2656
2925
  context.registerEffect(
@@ -2672,7 +2941,7 @@ function transformNativeElement(node, propsResult, singleRoot, context, getEffec
2672
2941
  template += `</${tag}>`;
2673
2942
  }
2674
2943
  if (singleRoot) {
2675
- context.ir.rootTemplateIndex = context.ir.template.length;
2944
+ context.ir.rootTemplateIndex = context.ir.template.size;
2676
2945
  }
2677
2946
  if (context.parent && context.parent.node.type === 1 && !compilerDom.isValidHTMLNesting(context.parent.node.tag, tag)) {
2678
2947
  context.reference();
@@ -2804,7 +3073,7 @@ function dedupeProperties(results) {
2804
3073
  }
2805
3074
  const name = prop.key.content;
2806
3075
  const existing = knownProps.get(name);
2807
- if (existing) {
3076
+ if (existing && existing.handler === prop.handler) {
2808
3077
  if (name === "style" || name === "class") {
2809
3078
  mergePropValues(existing, prop);
2810
3079
  }
@@ -2846,11 +3115,11 @@ const transformVHtml = (dir, node, context) => {
2846
3115
  context.registerEffect([exp], {
2847
3116
  type: 7,
2848
3117
  element: context.reference(),
2849
- value: exp
3118
+ value: exp,
3119
+ isComponent: node.tagType === 1
2850
3120
  });
2851
3121
  };
2852
3122
 
2853
- /*! #__NO_SIDE_EFFECTS__ */
2854
3123
  // @__NO_SIDE_EFFECTS__
2855
3124
  function makeMap(str) {
2856
3125
  const map = /* @__PURE__ */ Object.create(null);
@@ -2883,15 +3152,19 @@ const transformVText = (dir, node, context) => {
2883
3152
  context.childrenTemplate = [String(literal)];
2884
3153
  } else {
2885
3154
  context.childrenTemplate = [" "];
2886
- context.registerOperation({
2887
- type: 17,
2888
- parent: context.reference()
2889
- });
3155
+ const isComponent = node.tagType === 1;
3156
+ if (!isComponent) {
3157
+ context.registerOperation({
3158
+ type: 17,
3159
+ parent: context.reference()
3160
+ });
3161
+ }
2890
3162
  context.registerEffect([exp], {
2891
3163
  type: 4,
2892
3164
  element: context.reference(),
2893
3165
  values: [exp],
2894
- generated: true
3166
+ generated: true,
3167
+ isComponent
2895
3168
  });
2896
3169
  }
2897
3170
  };
@@ -2923,7 +3196,8 @@ const transformVBind = (dir, node, context) => {
2923
3196
  );
2924
3197
  exp = compilerDom.createSimpleExpression("", true, loc);
2925
3198
  }
2926
- exp = resolveExpression(exp);
3199
+ const isComponent = node.tagType === 1;
3200
+ exp = resolveExpression(exp, isComponent);
2927
3201
  arg = resolveExpression(arg);
2928
3202
  if (arg.isStatic && isReservedProp(arg.content)) return;
2929
3203
  let camel = false;
@@ -2984,7 +3258,11 @@ const transformVOn = (dir, node, context) => {
2984
3258
  key: arg,
2985
3259
  value: handler,
2986
3260
  handler: true,
2987
- handlerModifiers: eventOptionModifiers
3261
+ handlerModifiers: {
3262
+ keys: keyModifiers,
3263
+ nonKeys: nonKeyModifiers,
3264
+ options: eventOptionModifiers
3265
+ }
2988
3266
  };
2989
3267
  }
2990
3268
  const delegate = arg.isStatic && !eventOptionModifiers.length && delegatedEvents(arg.content);
@@ -3022,12 +3300,21 @@ const transformVShow = (dir, node, context) => {
3022
3300
  );
3023
3301
  return;
3024
3302
  }
3303
+ let shouldDeferred = false;
3304
+ const parentNode = context.parent && context.parent.node;
3305
+ if (parentNode && parentNode.type === 1) {
3306
+ shouldDeferred = !!(isTransitionTag(parentNode.tag) && findProp(parentNode, "appear", false, true));
3307
+ if (shouldDeferred) {
3308
+ context.parent.parent.block.hasDeferredVShow = true;
3309
+ }
3310
+ }
3025
3311
  context.registerOperation({
3026
3312
  type: 13,
3027
3313
  element: context.reference(),
3028
3314
  dir,
3029
3315
  name: "show",
3030
- builtin: true
3316
+ builtin: true,
3317
+ deferred: shouldDeferred
3031
3318
  });
3032
3319
  };
3033
3320
 
@@ -3097,7 +3384,7 @@ const transformText = (node, context) => {
3097
3384
  } else if (node.type === 5) {
3098
3385
  processInterpolation(context);
3099
3386
  } else if (node.type === 2) {
3100
- context.template += node.content;
3387
+ context.template += shared.escapeHtml(node.content);
3101
3388
  }
3102
3389
  };
3103
3390
  function processInterpolation(context) {
@@ -3116,32 +3403,20 @@ function processInterpolation(context) {
3116
3403
  }
3117
3404
  context.template += " ";
3118
3405
  const id = context.reference();
3119
- if (values.length === 0) {
3406
+ if (values.length === 0 || values.every((v) => getLiteralExpressionValue(v) != null) && parentNode.type !== 0) {
3120
3407
  return;
3121
3408
  }
3122
- const nonConstantExps = values.filter((v) => !isConstantExpression(v));
3123
- const isStatic = !nonConstantExps.length || nonConstantExps.every(
3124
- (e) => isStaticExpression(e, context.options.bindingMetadata)
3125
- ) || context.inVOnce;
3126
- if (isStatic) {
3127
- context.registerOperation({
3128
- type: 4,
3129
- element: id,
3130
- values
3131
- });
3132
- } else {
3133
- context.registerEffect(values, {
3134
- type: 4,
3135
- element: id,
3136
- values
3137
- });
3138
- }
3409
+ context.registerEffect(values, {
3410
+ type: 4,
3411
+ element: id,
3412
+ values
3413
+ });
3139
3414
  }
3140
3415
  function processTextContainer(children, context) {
3141
3416
  const values = processTextLikeChildren(children, context);
3142
- const literals = values.map(getLiteralExpressionValue);
3417
+ const literals = values.map((value) => getLiteralExpressionValue(value));
3143
3418
  if (literals.every((l) => l != null)) {
3144
- context.childrenTemplate = literals.map((l) => String(l));
3419
+ context.childrenTemplate = literals.map((l) => shared.escapeHtml(String(l)));
3145
3420
  } else {
3146
3421
  context.childrenTemplate = [" "];
3147
3422
  context.registerOperation({
@@ -3292,7 +3567,7 @@ const transformComment = (node, context) => {
3292
3567
  context.comment.push(node);
3293
3568
  context.dynamic.flags |= 2;
3294
3569
  } else {
3295
- context.template += `<!--${node.content}-->`;
3570
+ context.template += `<!--${shared.escapeHtml(node.content)}-->`;
3296
3571
  }
3297
3572
  };
3298
3573
  function getSiblingIf(context, reverse) {
@@ -3346,6 +3621,7 @@ function processIf(node, dir, context) {
3346
3621
  };
3347
3622
  } else {
3348
3623
  const siblingIf = getSiblingIf(context, true);
3624
+ context.dynamic.ifBranch = true;
3349
3625
  const siblings = context.parent && context.parent.dynamic.children;
3350
3626
  let lastIfNode;
3351
3627
  if (siblings) {
@@ -3391,7 +3667,7 @@ function processIf(node, dir, context) {
3391
3667
  id: -1,
3392
3668
  condition: dir.exp,
3393
3669
  positive: branch,
3394
- once: context.inVOnce
3670
+ once: context.inVOnce || isStaticExpression(dir.exp, context.options.bindingMetadata)
3395
3671
  };
3396
3672
  }
3397
3673
  return () => onExit();
@@ -3402,6 +3678,7 @@ function createIfBranch(node, context) {
3402
3678
  const branch = newBlock(node);
3403
3679
  const exitBlock = context.enterBlock(branch);
3404
3680
  context.reference();
3681
+ branch.dynamic.needsKey = isInTransition(context);
3405
3682
  return [branch, exitBlock];
3406
3683
  }
3407
3684
 
@@ -3426,7 +3703,8 @@ function processFor(node, dir, context) {
3426
3703
  const { source, value, key, index } = parseResult;
3427
3704
  const keyProp = findProp(node, "key");
3428
3705
  const keyProperty = keyProp && propToExpression(keyProp);
3429
- const isComponent = node.tagType === 1;
3706
+ const isComponent = node.tagType === 1 || // template v-for with a single component child
3707
+ isTemplateWithSingleComponent(node);
3430
3708
  context.node = node = wrapTemplate(node, ["for"]);
3431
3709
  context.dynamic.flags |= 2 | 4;
3432
3710
  const id = context.reference();
@@ -3455,6 +3733,13 @@ function processFor(node, dir, context) {
3455
3733
  };
3456
3734
  };
3457
3735
  }
3736
+ function isTemplateWithSingleComponent(node) {
3737
+ if (node.tag !== "template") return false;
3738
+ const nonCommentChildren = node.children.filter(
3739
+ (c) => c.type !== 3
3740
+ );
3741
+ return nonCommentChildren.length === 1 && nonCommentChildren[0].type === 1 && nonCommentChildren[0].tagType === 1;
3742
+ }
3458
3743
 
3459
3744
  const transformSlotOutlet = (node, context) => {
3460
3745
  if (node.type !== 1 || node.tag !== "slot") {
@@ -3528,7 +3813,8 @@ const transformSlotOutlet = (node, context) => {
3528
3813
  id,
3529
3814
  name: slotName,
3530
3815
  props: irProps,
3531
- fallback
3816
+ fallback,
3817
+ noSlotted: !!(context.options.scopeId && !context.options.slotted)
3532
3818
  };
3533
3819
  };
3534
3820
  };
@@ -3590,7 +3876,22 @@ function transformComponentSlot(node, dir, context) {
3590
3876
  markNonTemplate(n, context);
3591
3877
  });
3592
3878
  }
3593
- const [block, onExit] = createSlotBlock(node, dir, context);
3879
+ let slotKey;
3880
+ if (isTransitionNode(node) && nonSlotTemplateChildren.length) {
3881
+ const nonCommentChild = nonSlotTemplateChildren.find(
3882
+ (n) => n.type !== 3
3883
+ );
3884
+ if (nonCommentChild) {
3885
+ const keyProp = findProp(
3886
+ nonCommentChild,
3887
+ "key"
3888
+ );
3889
+ if (keyProp) {
3890
+ slotKey = keyProp.exp;
3891
+ }
3892
+ }
3893
+ }
3894
+ const [block, onExit] = createSlotBlock(node, dir, context, slotKey);
3594
3895
  const { slots } = context;
3595
3896
  return () => {
3596
3897
  onExit();
@@ -3724,9 +4025,13 @@ function hasStaticSlot(slots, name) {
3724
4025
  if (slot.slotType === 0) return !!slot.slots[name];
3725
4026
  });
3726
4027
  }
3727
- function createSlotBlock(slotNode, dir, context) {
4028
+ function createSlotBlock(slotNode, dir, context, key = void 0) {
3728
4029
  const block = newBlock(slotNode);
3729
4030
  block.props = dir && dir.exp;
4031
+ if (key) {
4032
+ block.key = key;
4033
+ block.dynamic.needsKey = true;
4034
+ }
3730
4035
  const exitBlock = context.enterBlock(block);
3731
4036
  return [block, exitBlock];
3732
4037
  }
@@ -3735,6 +4040,37 @@ function isNonWhitespaceContent(node) {
3735
4040
  return !!node.content.trim();
3736
4041
  }
3737
4042
 
4043
+ const transformTransition = (node, context) => {
4044
+ if (node.type === 1 && node.tagType === 1) {
4045
+ if (isTransitionTag(node.tag)) {
4046
+ return compilerDom.postTransformTransition(
4047
+ node,
4048
+ context.options.onError,
4049
+ hasMultipleChildren
4050
+ );
4051
+ }
4052
+ }
4053
+ };
4054
+ function hasMultipleChildren(node) {
4055
+ const children = node.children = node.children.filter(
4056
+ (c) => c.type !== 3 && !(c.type === 2 && !c.content.trim())
4057
+ );
4058
+ const first = children[0];
4059
+ if (children.length === 1 && first.type === 1 && (findDir(first, "for") || compilerDom.isTemplateNode(first))) {
4060
+ return true;
4061
+ }
4062
+ const hasElse = (node2) => findDir(node2, "else-if") || findDir(node2, "else", true);
4063
+ if (children.every(
4064
+ (c, index) => c.type === 1 && // not template
4065
+ !compilerDom.isTemplateNode(c) && // not has v-for
4066
+ !findDir(c, "for") && // if the first child has v-if, the rest should also have v-else-if/v-else
4067
+ (index === 0 ? findDir(c, "if") : hasElse(c)) && !hasMultipleChildren(c)
4068
+ )) {
4069
+ return false;
4070
+ }
4071
+ return children.length > 1;
4072
+ }
4073
+
3738
4074
  function compile(source, options = {}) {
3739
4075
  const resolvedOptions = shared.extend({}, options);
3740
4076
  const ast = shared.isString(source) ? compilerDom.parse(source, resolvedOptions) : source;
@@ -3753,6 +4089,7 @@ function compile(source, options = {}) {
3753
4089
  shared.extend({}, resolvedOptions, {
3754
4090
  nodeTransforms: [
3755
4091
  ...nodeTransforms,
4092
+ ...[transformTransition] ,
3756
4093
  ...options.nodeTransforms || []
3757
4094
  // user transforms
3758
4095
  ],