@markw65/monkeyc-optimizer 1.0.41 → 1.0.43

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/build/api.cjs CHANGED
@@ -1,8 +1,8 @@
1
- 0 && (module.exports = {checkCompilerVersion,collectNamespaces,findUsingForNode,formatAst,getApiFunctionInfo,getApiMapping,hasProperty,isLookupCandidate,isStateNode,markInvokeClassMethod,parseSdkVersion,sameLookupResult,traverseAst,variableDeclarationName,visitReferences,visitorNode});
1
+ 0 && (module.exports = {checkCompilerVersion,collectNamespaces,findUsingForNode,formatAst,getApiFunctionInfo,getApiMapping,hasProperty,isLookupCandidate,isStateNode,markInvokeClassMethod,parseSdkVersion,sameLookupResult,traverseAst,variableDeclarationName,visitReferences,visit_resources,visitorNode});
2
2
  /******/ (() => { // webpackBootstrap
3
3
  /******/ var __webpack_modules__ = ({
4
4
 
5
- /***/ 789:
5
+ /***/ 2789:
6
6
  /***/ ((module) => {
7
7
 
8
8
  /**
@@ -273,6 +273,7 @@ __webpack_require__.d(__webpack_exports__, {
273
273
  "traverseAst": () => (/* reexport */ ast_traverseAst),
274
274
  "variableDeclarationName": () => (/* binding */ api_variableDeclarationName),
275
275
  "visitReferences": () => (/* reexport */ visitor_visitReferences),
276
+ "visit_resources": () => (/* reexport */ visit_resources),
276
277
  "visitorNode": () => (/* reexport */ visitorNode)
277
278
  });
278
279
 
@@ -465,7 +466,13 @@ function ast_withLoc(node, start, end) {
465
466
  node.end = start.end;
466
467
  node.loc = { ...(node.loc || start.loc), start: start.loc.start };
467
468
  }
468
- if (end && end.loc) {
469
+ if (end === false) {
470
+ if (node.loc) {
471
+ node.loc.end = node.loc.start;
472
+ node.end = node.start;
473
+ }
474
+ }
475
+ else if (end && end.loc) {
469
476
  node.end = end.end;
470
477
  node.loc = { ...(node.loc || end.loc), end: end.loc.end };
471
478
  }
@@ -828,6 +835,12 @@ function getArgSafety(state, func, args, requireAll) {
828
835
  let allSafe = true;
829
836
  if (!args.every((arg, i) => {
830
837
  switch (arg.type) {
838
+ case "UnaryExpression":
839
+ if (arg.operator === ":") {
840
+ safeArgs.push(true);
841
+ return true;
842
+ }
843
+ break;
831
844
  case "Literal":
832
845
  safeArgs.push(true);
833
846
  return true;
@@ -1407,7 +1420,16 @@ function inlineWithArgs(state, func, call, context) {
1407
1420
  withLocDeep(body, context, context, true);
1408
1421
  return body;
1409
1422
  }
1410
- function inliner_inlineFunction(state, func, call, context) {
1423
+ function isTypecheckArg(node, arg) {
1424
+ return (node.type === "CallExpression" &&
1425
+ node.callee.type === "Identifier" &&
1426
+ node.callee.name === ":typecheck" &&
1427
+ (arg === null ||
1428
+ (node.arguments.length === 1 &&
1429
+ node.arguments[0].type === "Literal" &&
1430
+ node.arguments[0].value === arg)));
1431
+ }
1432
+ function inlineFunctionHelper(state, func, call, context) {
1411
1433
  if (context) {
1412
1434
  return inlineWithArgs(state, func, call, context);
1413
1435
  }
@@ -1418,6 +1440,33 @@ function inliner_inlineFunction(state, func, call, context) {
1418
1440
  state.localsStack[state.localsStack.length - 1].map = map;
1419
1441
  return ret && withLocDeep(ret, call, call, true);
1420
1442
  }
1443
+ function inliner_inlineFunction(state, func, call, context) {
1444
+ const ret = inlineFunctionHelper(state, func, call, context);
1445
+ if (!ret)
1446
+ return ret;
1447
+ const typecheckFalse = func.node.attrs?.attributes?.elements.find((attr) => isTypecheckArg(attr, false));
1448
+ if (!typecheckFalse) {
1449
+ return ret;
1450
+ }
1451
+ const callerSn = state.stack.find((sn) => sn.type === "FunctionDeclaration");
1452
+ if (!callerSn) {
1453
+ return ret;
1454
+ }
1455
+ const caller = callerSn.node;
1456
+ if (!caller.attrs) {
1457
+ caller.attrs = withLoc({
1458
+ type: "AttributeList",
1459
+ }, caller, false);
1460
+ }
1461
+ if (!caller.attrs.attributes) {
1462
+ caller.attrs.attributes = withLoc({ type: "Attributes", elements: [] }, caller.attrs, false);
1463
+ }
1464
+ if (caller.attrs.attributes.elements.find((attr) => isTypecheckArg(attr, null))) {
1465
+ return ret;
1466
+ }
1467
+ caller.attrs.attributes.elements.unshift(withLocDeep({ ...typecheckFalse }, caller.attrs, false));
1468
+ return ret;
1469
+ }
1421
1470
  function applyTypeIfNeeded(node) {
1422
1471
  if ("enumType" in node && node.enumType) {
1423
1472
  node = {
@@ -2158,7 +2207,7 @@ function getPreOrder(head) {
2158
2207
  }
2159
2208
 
2160
2209
  // EXTERNAL MODULE: ./node_modules/priorityqueuejs/index.js
2161
- var priorityqueuejs = __webpack_require__(789);
2210
+ var priorityqueuejs = __webpack_require__(2789);
2162
2211
  ;// CONCATENATED MODULE: ./src/pre.ts
2163
2212
 
2164
2213
 
@@ -3338,7 +3387,7 @@ function getFileASTs(fnMap) {
3338
3387
  return ok;
3339
3388
  }, true));
3340
3389
  }
3341
- async function analyze(fnMap, resourcesMap, config) {
3390
+ async function analyze(fnMap, resourcesMap, manifestXML, config) {
3342
3391
  let hasTests = false;
3343
3392
  let markApi = true;
3344
3393
  const preState = {
@@ -3401,7 +3450,7 @@ async function analyze(fnMap, resourcesMap, config) {
3401
3450
  return null;
3402
3451
  },
3403
3452
  };
3404
- await getApiMapping(preState, resourcesMap);
3453
+ await getApiMapping(preState, resourcesMap, manifestXML);
3405
3454
  markApi = false;
3406
3455
  const state = preState;
3407
3456
  await getFileASTs(fnMap);
@@ -3431,13 +3480,12 @@ function reportMissingSymbols(state, config) {
3431
3480
  if (diagnosticType &&
3432
3481
  !config?.compilerOptions?.includes("--Eno-invalid-symbol")) {
3433
3482
  const checkTypes = config?.typeCheckLevel && config.typeCheckLevel !== "Off";
3434
- Object.entries(state.fnMap).forEach(([, v]) => {
3435
- visitReferences(state, v.ast, null, false, (node, results, error) => {
3483
+ const report = (ast) => {
3484
+ visitReferences(state, ast, null, false, (node, results, error) => {
3436
3485
  if (node.type === "BinaryExpression" && node.operator === "has") {
3437
3486
  // Its not an error to check whether a property exists...
3438
3487
  return undefined;
3439
3488
  }
3440
- const nodeStr = formatAst(node);
3441
3489
  if (!error) {
3442
3490
  if (state.sdkVersion === 4001006 &&
3443
3491
  compiler2DiagnosticType &&
@@ -3460,19 +3508,22 @@ function reportMissingSymbols(state, config) {
3460
3508
  return false;
3461
3509
  });
3462
3510
  })) {
3463
- diagnostic(state, node.loc, `The expression ${nodeStr} will fail at runtime using sdk-4.1.6`, compiler2DiagnosticType);
3511
+ diagnostic(state, node.loc, `The expression ${formatAst(node)} will fail at runtime using sdk-4.1.6`, compiler2DiagnosticType);
3464
3512
  }
3465
3513
  return undefined;
3466
3514
  }
3515
+ let nodeStr;
3467
3516
  if (state.inType) {
3468
- if (!checkTypes || nodeStr.match(/^Void|Null$/)) {
3517
+ if (!checkTypes || (nodeStr = formatAst(node)).match(/^Void|Null$/)) {
3469
3518
  return undefined;
3470
3519
  }
3471
3520
  }
3472
- diagnostic(state, node.loc, `Undefined symbol ${nodeStr}`, diagnosticType);
3521
+ diagnostic(state, node.loc, `Undefined symbol ${nodeStr || formatAst(node)}`, diagnosticType);
3473
3522
  return false;
3474
3523
  });
3475
- });
3524
+ };
3525
+ Object.values(state.fnMap).forEach((v) => v.ast && report(v.ast));
3526
+ state.rezAst && report(state.rezAst);
3476
3527
  }
3477
3528
  }
3478
3529
  function compareLiteralLike(a, b) {
@@ -3769,8 +3820,8 @@ function markFunctionCalled(state, func) {
3769
3820
  }
3770
3821
  pushUnique(state.calledFunctions[func.id.name], func);
3771
3822
  }
3772
- async function optimizeMonkeyC(fnMap, resourcesMap, config) {
3773
- const state = (await analyze(fnMap, resourcesMap, config));
3823
+ async function optimizeMonkeyC(fnMap, resourcesMap, manifestXML, config) {
3824
+ const state = (await analyze(fnMap, resourcesMap, manifestXML, config));
3774
3825
  state.localsStack = [{}];
3775
3826
  state.calledFunctions = {};
3776
3827
  state.usedByName = {};
@@ -4560,198 +4611,399 @@ const external_sdk_util_cjs_namespaceObject = require("./sdk-util.cjs");
4560
4611
  * This is unavoidably ad-hoc. Garmin has arbitrary rules for how
4561
4612
  * resources can be nested, which we need to mimic here.
4562
4613
  */
4563
- function visit_resources(elements, parent, visitor, error) {
4614
+ function visit_resources(elements, parent, v) {
4615
+ const visitor = typeof v === "function"
4616
+ ? {
4617
+ visit: v,
4618
+ }
4619
+ : v;
4620
+ const pname = parent ? parent.name : null;
4621
+ const error = (e) => visitor.error && visitor.error(e, pname);
4622
+ const visit = (e, module) => visitor.visit && visitor.visit(e, module, parent);
4564
4623
  elements.forEach((e) => {
4565
- switch (e.name) {
4566
- // <resources> can contain any of the resource lists (except
4567
- // another resources), and any of their contents
4568
- case "resources":
4569
- if (parent) {
4570
- error(e, parent);
4571
- return;
4572
- }
4573
- visit_resources(external_sdk_util_cjs_namespaceObject.xmlUtil.elementKids(e), "resources", visitor, error);
4574
- return;
4575
- // Each of these is a list that can contain certain kinds of resource.
4576
- // They can only occur at the top level, or under a <resources> list.
4577
- case "strings":
4578
- case "fonts":
4579
- case "animations":
4580
- case "bitmaps":
4581
- case "layouts":
4582
- case "menus":
4583
- case "drawables":
4584
- case "properties":
4585
- case "settings":
4586
- case "fitContributions":
4587
- case "jsonDataResources":
4588
- case "complications":
4589
- if (parent && parent !== "resources") {
4590
- error(e, parent);
4591
- return;
4592
- }
4593
- visit_resources(external_sdk_util_cjs_namespaceObject.xmlUtil.elementKids(e), e.name, visitor, error);
4594
- return;
4595
- // These are the resources themselves. Some can occur at top level; most
4596
- // are restricted to <resources> or one or more of the specific lists above
4597
- case "string":
4598
- if (parent !== "strings" && parent !== "resources") {
4599
- error(e, parent);
4600
- return;
4601
- }
4602
- visitor(e, "Strings");
4603
- return;
4604
- case "font":
4605
- if (parent !== "fonts" && parent !== "resources") {
4606
- error(e, parent);
4607
- return;
4608
- }
4609
- visitor(e, "Fonts");
4610
- return;
4611
- case "animation":
4612
- if (parent !== "animations" && parent !== "resources") {
4613
- error(e, parent);
4614
- return;
4615
- }
4616
- visitor(e, "Drawables");
4617
- return;
4618
- case "menu":
4619
- case "menu2":
4620
- case "checkbox-menu":
4621
- case "action-menu":
4622
- if (parent && parent !== "menus" && parent !== "resources") {
4623
- error(e, parent);
4624
- return;
4625
- }
4626
- visitor(e, "Menus");
4627
- return;
4628
- case "bitmap":
4629
- if (parent !== "bitmaps" &&
4630
- parent !== "drawables" &&
4631
- parent !== "resources") {
4632
- error(e, parent);
4633
- return;
4634
- }
4635
- visitor(e, "Drawables");
4636
- return;
4637
- case "layout":
4638
- if (parent && parent !== "layouts" && parent !== "resources") {
4639
- error(e, parent);
4640
- return;
4641
- }
4642
- visitor(e, "Layouts");
4643
- return;
4644
- case "drawable-list":
4645
- if (parent && parent !== "drawables" && parent !== "resources") {
4646
- error(e, parent);
4647
- return;
4648
- }
4649
- visitor(e, "Drawables");
4650
- return;
4651
- case "property":
4652
- if (parent !== "properties" && parent !== "resources") {
4653
- error(e, parent);
4654
- return;
4655
- }
4656
- visitor(e, "Properties");
4657
- return;
4658
- case "setting":
4659
- if (parent !== "settings" && parent !== "resources") {
4660
- error(e, parent);
4661
- return;
4662
- }
4663
- visitor(e, null);
4664
- return;
4665
- case "group":
4666
- if (parent !== "settings" /* && parent !== "resources" */) {
4667
- error(e, parent);
4668
- return;
4669
- }
4670
- visitor(e, null);
4671
- return;
4672
- case "fitField":
4673
- if (parent !== "fitContributions" && parent !== "resources") {
4674
- error(e, parent);
4675
- return;
4676
- }
4677
- visitor(e, null);
4678
- return;
4679
- case "jsonData":
4680
- if (parent && parent != "jsonDataResources" && parent !== "resources") {
4681
- error(e, parent);
4682
- return;
4683
- }
4684
- visitor(e, "JsonData");
4685
- return;
4686
- case "build":
4687
- if (parent && parent !== "resources") {
4688
- error(e, parent);
4689
- return;
4690
- }
4691
- visitor(e, null);
4692
- return;
4624
+ if (visitor.pre ? visitor.pre(e) === false : e.type !== "element") {
4625
+ return;
4626
+ }
4627
+ if (e.type == "element") {
4628
+ switch (e.name) {
4629
+ // <resources> can contain any of the resource lists (except
4630
+ // another resources), and any of their contents
4631
+ case "resources":
4632
+ if (parent) {
4633
+ error(e);
4634
+ break;
4635
+ }
4636
+ e.children && visit_resources(e.children, e, visitor);
4637
+ break;
4638
+ // Each of these is a list that can contain certain kinds of resource.
4639
+ // They can only occur at the top level, or under a <resources> list.
4640
+ case "strings":
4641
+ case "fonts":
4642
+ case "animations":
4643
+ case "bitmaps":
4644
+ case "layouts":
4645
+ case "menus":
4646
+ case "drawables":
4647
+ case "properties":
4648
+ case "settings":
4649
+ case "fitContributions":
4650
+ case "jsonDataResources":
4651
+ case "complications":
4652
+ if (pname && pname !== "resources") {
4653
+ error(e);
4654
+ break;
4655
+ }
4656
+ visit_resources(external_sdk_util_cjs_namespaceObject.xmlUtil.elementKids(e), e, visitor);
4657
+ break;
4658
+ // These are the resources themselves. Some can occur at top level; most
4659
+ // are restricted to <resources> or one or more of the specific lists above
4660
+ case "string":
4661
+ if (pname !== "strings" && pname !== "resources") {
4662
+ error(e);
4663
+ break;
4664
+ }
4665
+ visit(e, "Strings");
4666
+ break;
4667
+ case "font":
4668
+ if (pname !== "fonts" && pname !== "resources") {
4669
+ error(e);
4670
+ break;
4671
+ }
4672
+ visit(e, "Fonts");
4673
+ break;
4674
+ case "animation":
4675
+ if (pname !== "animations" && pname !== "resources") {
4676
+ error(e);
4677
+ break;
4678
+ }
4679
+ visit(e, "Drawables");
4680
+ break;
4681
+ case "menu":
4682
+ case "menu2":
4683
+ case "checkbox-menu":
4684
+ case "action-menu":
4685
+ if (pname && pname !== "menus" && pname !== "resources") {
4686
+ error(e);
4687
+ break;
4688
+ }
4689
+ visit(e, "Menus");
4690
+ break;
4691
+ case "bitmap":
4692
+ if (pname !== "bitmaps" &&
4693
+ pname !== "drawables" &&
4694
+ pname !== "resources") {
4695
+ error(e);
4696
+ break;
4697
+ }
4698
+ visit(e, "Drawables");
4699
+ break;
4700
+ case "layout":
4701
+ if (pname && pname !== "layouts" && pname !== "resources") {
4702
+ error(e);
4703
+ break;
4704
+ }
4705
+ visit(e, "Layouts");
4706
+ break;
4707
+ case "drawable-list":
4708
+ if (pname && pname !== "drawables" && pname !== "resources") {
4709
+ error(e);
4710
+ break;
4711
+ }
4712
+ visit(e, "Drawables");
4713
+ break;
4714
+ case "property":
4715
+ if (pname !== "properties" && pname !== "resources") {
4716
+ error(e);
4717
+ break;
4718
+ }
4719
+ visit(e, "Properties");
4720
+ break;
4721
+ case "setting":
4722
+ if (pname !== "settings" && pname !== "resources") {
4723
+ error(e);
4724
+ break;
4725
+ }
4726
+ visit(e, "Settings");
4727
+ break;
4728
+ case "group":
4729
+ if (pname !== "settings" /* && pname !== "resources" */) {
4730
+ error(e);
4731
+ break;
4732
+ }
4733
+ visit(e, "Settings");
4734
+ break;
4735
+ case "fitField":
4736
+ if (pname !== "fitContributions" && pname !== "resources") {
4737
+ error(e);
4738
+ break;
4739
+ }
4740
+ visit(e, "FitFields");
4741
+ break;
4742
+ case "jsonData":
4743
+ if (pname && pname != "jsonDataResources" && pname !== "resources") {
4744
+ error(e);
4745
+ break;
4746
+ }
4747
+ visit(e, "JsonData");
4748
+ break;
4749
+ case "build":
4750
+ if (pname && pname !== "resources") {
4751
+ error(e);
4752
+ break;
4753
+ }
4754
+ visit(e, null);
4755
+ break;
4756
+ }
4693
4757
  }
4758
+ if (visitor.post)
4759
+ visitor.post(e);
4694
4760
  });
4695
4761
  }
4696
- function add_resources_to_ast(ast, resources) {
4762
+ function add_resources_to_ast(ast, resources, manifestXML) {
4763
+ const modules = {
4764
+ Drawables: true,
4765
+ Fonts: true,
4766
+ JsonData: true,
4767
+ Layouts: true,
4768
+ Menus: true,
4769
+ Strings: true,
4770
+ Properties: false,
4771
+ Settings: false,
4772
+ FitFields: false,
4773
+ };
4774
+ const outerLoc = ast.loc && { ...ast.loc };
4775
+ const makeModule = (m) => ({
4776
+ type: "ModuleDeclaration",
4777
+ id: { type: "Identifier", name: m },
4778
+ body: { type: "BlockStatement", body: [] },
4779
+ loc: outerLoc,
4780
+ });
4781
+ const makeImport = (type, module, as) => {
4782
+ const id = makeScopedName(module);
4783
+ return type === "Using" && as
4784
+ ? { type, id, as: makeIdentifier(as) }
4785
+ : { type, id };
4786
+ };
4787
+ ast.body.push(makeImport("ImportModule", "Toybox.Lang"), makeImport("Using", "Toybox.WatchUi"), makeImport("Using", "Toybox.WatchUi", "Ui"), makeImport("Using", "Toybox.Graphics"), makeImport("Using", "Toybox.Graphics", "Gfx"));
4697
4788
  Object.entries(resources).forEach(([barrel, resourceMap]) => {
4698
- const rezModules = {
4699
- Drawables: [],
4700
- Fonts: [],
4701
- JsonData: [],
4702
- Layouts: [],
4703
- Menus: [],
4704
- Properties: [],
4705
- Strings: [],
4706
- };
4789
+ let body = ast.body;
4790
+ if (barrel !== "") {
4791
+ const module = makeModule(barrel);
4792
+ body.push(module);
4793
+ body = module.body.body;
4794
+ }
4795
+ const rez = makeModule("Rez");
4796
+ body.push(rez);
4797
+ const hiddenRez = makeModule("*Rez*");
4798
+ rez.body.body.push(hiddenRez);
4799
+ if (barrel === "" &&
4800
+ manifestXML &&
4801
+ manifestXML.body instanceof external_sdk_util_cjs_namespaceObject.xmlUtil.Nodes) {
4802
+ manifestXML.body
4803
+ .children("iq:application")
4804
+ .elements.forEach((e) => add_one_resource(rez, e));
4805
+ }
4806
+ const rezModules = Object.fromEntries(Object.entries(modules).map(([moduleName, isPublic]) => {
4807
+ const module = makeModule(moduleName);
4808
+ (isPublic ? rez : hiddenRez).body.body.push(module);
4809
+ return [moduleName, module];
4810
+ }));
4707
4811
  Object.values(resourceMap).forEach((rez) => {
4708
- if (!rez || !(rez instanceof external_sdk_util_cjs_namespaceObject.xmlUtil.Document))
4812
+ if (!rez || rez.body instanceof Error)
4709
4813
  return;
4710
4814
  visit_resources(rez.body.elements, null, (e, s) => {
4711
4815
  if (!s)
4712
4816
  return;
4713
4817
  if (!ast_hasProperty(rezModules, s))
4714
4818
  return;
4715
- rezModules[s].push(e);
4716
- }, (_e, _s) => {
4717
- return;
4819
+ const module = rezModules[s];
4820
+ add_one_resource(module, e);
4718
4821
  });
4719
4822
  });
4720
- const outerLoc = ast.loc && { ...ast.loc };
4721
- const makeModule = (m) => ({
4722
- type: "ModuleDeclaration",
4723
- id: { type: "Identifier", name: m },
4724
- body: { type: "BlockStatement", body: [] },
4725
- loc: outerLoc,
4726
- });
4727
- let body = ast.body;
4728
- if (barrel !== "") {
4729
- const module = makeModule(barrel);
4730
- body.push(module);
4731
- body = module.body.body;
4823
+ });
4824
+ }
4825
+ function makeIdentifier(name, loc) {
4826
+ return wrap({ type: "Identifier", name }, loc);
4827
+ }
4828
+ function makeMemberExpression(object, property) {
4829
+ return wrap({
4830
+ type: "MemberExpression",
4831
+ object,
4832
+ property,
4833
+ computed: false,
4834
+ }, object.loc && locRange(object.loc, property.loc));
4835
+ }
4836
+ function makeScopedName(dotted, l) {
4837
+ const loc = l && adjustLoc(l, 0, l.start.offset - l.end.offset);
4838
+ return dotted.split(".").reduce(({ cur, offset }, next) => {
4839
+ const id = makeIdentifier(next, loc && adjustLoc(loc, offset, offset + next.length));
4840
+ if (!cur) {
4841
+ cur = id;
4732
4842
  }
4733
- const rez = makeModule("Rez");
4734
- body.push(rez);
4735
- body = rez.body.body;
4736
- Object.entries(rezModules).forEach(([m, elements]) => {
4737
- const module = makeModule(m);
4738
- body.push(module);
4739
- elements.forEach((e) => e.attr.id &&
4740
- module.body.body.push({
4741
- type: "VariableDeclaration",
4742
- declarations: [
4743
- {
4744
- type: "VariableDeclarator",
4745
- kind: "var",
4746
- id: { type: "Identifier", name: e.attr.id, loc: e.loc },
4747
- loc: e.loc,
4748
- },
4749
- ],
4750
- kind: "var",
4751
- loc: e.loc,
4752
- }));
4753
- });
4843
+ else {
4844
+ cur = makeMemberExpression(cur, id);
4845
+ }
4846
+ offset += next.length + 1;
4847
+ return { cur, offset };
4848
+ }, { cur: null, offset: 0 }).cur;
4849
+ }
4850
+ function visit_resource_refs(e) {
4851
+ const result = [];
4852
+ const stringToScopedName = (element, id, dotted, l) => {
4853
+ const match = dotted.match(/^(@)?([\w_$]+\s*\.\s*)*[\w_$]+$/);
4854
+ if (!match)
4855
+ return;
4856
+ let offset = 0;
4857
+ if (match[1]) {
4858
+ offset = 1;
4859
+ }
4860
+ else if ((element === "drawable" && id === "class") ||
4861
+ (element === "iq:application" && id === "entry")) {
4862
+ // nothing to do
4863
+ }
4864
+ else {
4865
+ return;
4866
+ }
4867
+ const dn = makeScopedName(dotted.substring(offset), adjustLoc(l, offset, 0));
4868
+ if (dn)
4869
+ result.push(dn);
4870
+ };
4871
+ visit_resources([e], null, {
4872
+ pre(node) {
4873
+ if (node.type === "element") {
4874
+ Object.values(node.attr).forEach((attr) => {
4875
+ if (!attr || !attr.value.loc)
4876
+ return;
4877
+ const loc = adjustLoc(attr.value.loc);
4878
+ attr &&
4879
+ stringToScopedName(node.name, attr.name.value, attr.value.value, loc);
4880
+ });
4881
+ if (node.children &&
4882
+ node.children.length === 1 &&
4883
+ node.children[0].type === "chardata") {
4884
+ stringToScopedName(node.name, null, node.children[0].value, node.children[0].loc);
4885
+ }
4886
+ return;
4887
+ }
4888
+ },
4754
4889
  });
4890
+ return result;
4891
+ }
4892
+ function wrap(node, loc) {
4893
+ if (loc) {
4894
+ node.loc = loc;
4895
+ node.start = loc.start.offset;
4896
+ node.end = loc.end.offset;
4897
+ }
4898
+ return node;
4899
+ }
4900
+ function locRange(start, end) {
4901
+ return {
4902
+ source: start.source || end.source,
4903
+ start: start.start,
4904
+ end: end.end,
4905
+ };
4906
+ }
4907
+ function adjustLoc(loc, start = 1, end = -1) {
4908
+ /* Attributes are quoted, so skip the quotes */
4909
+ return {
4910
+ source: loc.source,
4911
+ start: {
4912
+ offset: loc.start.offset + start,
4913
+ line: loc.start.line,
4914
+ column: loc.start.column + start,
4915
+ },
4916
+ end: {
4917
+ offset: loc.end.offset + end,
4918
+ line: loc.end.line,
4919
+ column: loc.end.column + end,
4920
+ },
4921
+ };
4922
+ }
4923
+ function add_one_resource(module, e) {
4924
+ let id;
4925
+ let func;
4926
+ const varDecl = () => {
4927
+ const loc = id && adjustLoc(id.value.loc);
4928
+ return wrap({
4929
+ type: "VariableDeclaration",
4930
+ declarations: [
4931
+ wrap({
4932
+ type: "VariableDeclarator",
4933
+ kind: "var",
4934
+ id: makeIdentifier(id ? id.value.value : "*invalid*", loc),
4935
+ init,
4936
+ }, loc),
4937
+ ],
4938
+ kind: "var",
4939
+ }, loc);
4940
+ };
4941
+ const classDecl = (parent) => {
4942
+ if (!id)
4943
+ return null;
4944
+ const loc = id.value.loc;
4945
+ const items = init
4946
+ ? [{ type: "ClassElement", item: varDecl(), loc }]
4947
+ : [];
4948
+ return {
4949
+ type: "ClassDeclaration",
4950
+ body: { type: "ClassBody", body: items, loc },
4951
+ id: makeIdentifier(id.value.value, loc),
4952
+ superClass: makeScopedName(parent),
4953
+ loc,
4954
+ };
4955
+ };
4956
+ switch (e.name) {
4957
+ case "font":
4958
+ case "string":
4959
+ case "jsonData":
4960
+ case "animation":
4961
+ case "bitmap":
4962
+ case "layout":
4963
+ case "drawable-list":
4964
+ case "property":
4965
+ case "fitField":
4966
+ id = e.attr.id;
4967
+ func = varDecl;
4968
+ break;
4969
+ case "menu":
4970
+ id = e.attr.id;
4971
+ func = () => classDecl("Ui.Menu");
4972
+ break;
4973
+ case "menu2":
4974
+ id = e.attr.id;
4975
+ func = () => classDecl("Ui.Menu2");
4976
+ break;
4977
+ case "checkbox-menu":
4978
+ id = e.attr.id;
4979
+ func = () => classDecl("Ui.CheckboxMenu");
4980
+ break;
4981
+ case "action-menu":
4982
+ id = e.attr.id;
4983
+ func = () => classDecl("Ui.Menu2");
4984
+ break;
4985
+ case "setting":
4986
+ case "group":
4987
+ func = varDecl;
4988
+ break;
4989
+ case "iq:application":
4990
+ func = varDecl;
4991
+ break;
4992
+ }
4993
+ if (!func)
4994
+ return;
4995
+ const elements = visit_resource_refs(e);
4996
+ const init = elements.length
4997
+ ? { type: "ArrayExpression", elements }
4998
+ : undefined;
4999
+ if (!id) {
5000
+ if (!init)
5001
+ return;
5002
+ }
5003
+ const item = func();
5004
+ if (item) {
5005
+ module.body.body.push(item);
5006
+ }
4755
5007
  }
4756
5008
 
4757
5009
  ;// CONCATENATED MODULE: ./src/visitor.ts
@@ -4761,7 +5013,10 @@ function visitorNode(node) {
4761
5013
  return node;
4762
5014
  }
4763
5015
  if (node.type === "MemberExpression") {
4764
- return node.property;
5016
+ return node.property.type === "UnaryExpression" &&
5017
+ node.property.operator === ":"
5018
+ ? node.property.argument
5019
+ : node.property;
4765
5020
  }
4766
5021
  if (node.type === "BinaryExpression" &&
4767
5022
  node.operator === "has" &&
@@ -4771,7 +5026,7 @@ function visitorNode(node) {
4771
5026
  }
4772
5027
  return node;
4773
5028
  }
4774
- function visitor_visitReferences(state, ast, name, defn, callback, includeDefs = false) {
5029
+ function visitor_visitReferences(state, ast, name, defn, callback, includeDefs = false, filter = null) {
4775
5030
  const checkResults = ([name, results], node) => {
4776
5031
  if (name && results) {
4777
5032
  if (!defn || (0,external_api_cjs_namespaceObject.sameLookupResult)(results, defn)) {
@@ -4788,6 +5043,8 @@ function visitor_visitReferences(state, ast, name, defn, callback, includeDefs =
4788
5043
  return null;
4789
5044
  };
4790
5045
  state.pre = (node) => {
5046
+ if (filter && !filter(node))
5047
+ return [];
4791
5048
  switch (node.type) {
4792
5049
  case "AttributeList":
4793
5050
  return [];
@@ -4948,7 +5205,7 @@ function api_checkCompilerVersion(version, sdkVer) {
4948
5205
  return sdkVer <= v2;
4949
5206
  }
4950
5207
  // Extract all enum values from api.mir
4951
- async function api_getApiMapping(state, resourcesMap) {
5208
+ async function api_getApiMapping(state, resourcesMap, manifestXML) {
4952
5209
  // get the path to the currently active sdk
4953
5210
  const parser = (prettier_plugin_monkeyc_default()).parsers.monkeyc;
4954
5211
  const sdk = await (0,external_sdk_util_cjs_namespaceObject.getSdkPath)();
@@ -4962,17 +5219,25 @@ async function api_getApiMapping(state, resourcesMap) {
4962
5219
  const api = (await promises_namespaceObject.readFile(`${sdk}bin/api.mir`))
4963
5220
  .toString()
4964
5221
  .replace(/\r\n/g, "\n")
4965
- .replace(/^\s*\[.*?\]\s*$/gm, "")
4966
- //.replace(/(COLOR_TRANSPARENT|LAYOUT_[HV]ALIGN_\w+) = (\d+)/gm, "$1 = -$2")
4967
5222
  .replace(/^(\s*type)\s/gm, "$1def ");
4968
5223
  try {
4969
5224
  const ast = parser.parse(api, null, {
4970
5225
  filepath: "api.mir",
4971
5226
  });
4972
5227
  if (resourcesMap) {
4973
- add_resources_to_ast(ast, resourcesMap);
5228
+ const rezAst = state
5229
+ ? state.rezAst || { type: "Program", body: [] }
5230
+ : ast;
5231
+ add_resources_to_ast(rezAst, resourcesMap, manifestXML);
5232
+ if (state) {
5233
+ state.rezAst = rezAst;
5234
+ state.manifestXML = manifestXML;
5235
+ }
4974
5236
  }
4975
5237
  const result = api_collectNamespaces(ast, state);
5238
+ if (state && state.rezAst) {
5239
+ api_collectNamespaces(state.rezAst, state);
5240
+ }
4976
5241
  negativeFixups.forEach((fixup) => {
4977
5242
  const vs = fixup.split(".").reduce((state, part) => {
4978
5243
  const decls = api_isStateNode(state) && state.decls?.[part];
@@ -5597,6 +5862,9 @@ function api_collectNamespaces(ast, stateIn) {
5597
5862
  throw new Error("Unexpected enum initializer");
5598
5863
  }
5599
5864
  if (init != m.init) {
5865
+ if (m.init.enumType) {
5866
+ init.enumType = m.init.enumType;
5867
+ }
5600
5868
  m.init = init;
5601
5869
  }
5602
5870
  if (init.type == "Literal" &&