@neocompose/cli 0.71.2 → 0.71.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.
package/dist/neo.mjs CHANGED
@@ -597,6 +597,13 @@ function isGeneratedCSharpReservedKeyword(value) {
597
597
  function generatedCSharpMemberNameForSchemaKey(schemaKey) {
598
598
  return isGeneratedCSharpReservedKeyword(schemaKey) ? `${schemaKey}Value` : schemaKey;
599
599
  }
600
+ function generatedCSharpTypeName(value, fallback) {
601
+ const parts = value.match(/[A-Za-z0-9]+/g) ?? [];
602
+ const joined = parts.map((part) => `${part[0]?.toUpperCase() ?? ""}${part.slice(1)}`).join("");
603
+ const candidate = joined.length > 0 ? joined : fallback;
604
+ const safe = /^[0-9]/.test(candidate) ? `_${candidate}` : candidate;
605
+ return isGeneratedCSharpReservedKeyword(safe) ? `${safe}Type` : safe;
606
+ }
600
607
  var GENERATED_CSHARP_RESERVED_KEYWORDS, GENERATED_CSHARP_IDENTIFIER_REGEX;
601
608
  var init_generated_csharp_identifiers = __esm({
602
609
  "../packages/neoscript-language/src/generated-csharp-identifiers.ts"() {
@@ -4022,16 +4029,16 @@ function isLiteralValueContent(value) {
4022
4029
  return false;
4023
4030
  }
4024
4031
  }
4025
- const constructorArgs = getField(value, "constructorArgs");
4026
- if (constructorArgs === void 0) return true;
4027
- if (constructorArgs === null) return false;
4032
+ const constructorArgs2 = getField(value, "constructorArgs");
4033
+ if (constructorArgs2 === void 0) return true;
4034
+ if (constructorArgs2 === null) return false;
4028
4035
  if (typeof classIdField !== "string") return false;
4029
4036
  const literalValue = getField(value, "value");
4030
4037
  if (typeof literalValue !== "object" || literalValue === null) return false;
4031
4038
  if (Array.isArray(literalValue)) return false;
4032
- if (typeof constructorArgs !== "object") return false;
4033
- if (Array.isArray(constructorArgs)) return false;
4034
- return Object.keys(constructorArgs).every((key) => key.length > 0);
4039
+ if (typeof constructorArgs2 !== "object") return false;
4040
+ if (Array.isArray(constructorArgs2)) return false;
4041
+ return Object.keys(constructorArgs2).every((key) => key.length > 0);
4035
4042
  }
4036
4043
  function isInitValueContent(value) {
4037
4044
  if (!hasField(value, "init")) return false;
@@ -8199,16 +8206,16 @@ function encodeStoredValueRowFields(row) {
8199
8206
  };
8200
8207
  }
8201
8208
  function canonicalInstanceProvenanceViolation(value) {
8202
- const constructorArgs = "constructorArgs" in value ? value.constructorArgs : void 0;
8209
+ const constructorArgs2 = "constructorArgs" in value ? value.constructorArgs : void 0;
8203
8210
  const constructorId = "instanceConstructorId" in value ? value.instanceConstructorId : void 0;
8204
8211
  const variantId = "instanceVariantId" in value ? value.instanceVariantId : void 0;
8205
- if (constructorArgs !== void 0 && constructorId === void 0 && typeof variantId !== "string") {
8212
+ if (constructorArgs2 !== void 0 && constructorId === void 0 && typeof variantId !== "string") {
8206
8213
  return "constructor-args-without-stamp";
8207
8214
  }
8208
- if (typeof constructorId === "string" && constructorArgs === void 0) {
8215
+ if (typeof constructorId === "string" && constructorArgs2 === void 0) {
8209
8216
  return "named-constructor-without-args";
8210
8217
  }
8211
- if (constructorId === null && constructorArgs !== void 0 && typeof constructorArgs === "object" && constructorArgs !== null && !Array.isArray(constructorArgs) && Object.keys(constructorArgs).length > 0) {
8218
+ if (constructorId === null && constructorArgs2 !== void 0 && typeof constructorArgs2 === "object" && constructorArgs2 !== null && !Array.isArray(constructorArgs2) && Object.keys(constructorArgs2).length > 0) {
8212
8219
  return "implicit-constructor-with-args";
8213
8220
  }
8214
8221
  if ("instanceVariantRowValueId" in value && typeof value.instanceVariantRowValueId === "string" && typeof variantId !== "string") {
@@ -9089,14 +9096,14 @@ function decodePackedValueRow(row) {
9089
9096
  constructionRootId: isCollapseStampedInstanceRoot(row) ? row.id : null
9090
9097
  };
9091
9098
  const value = decodeContentField(row.value, "value", scope, children);
9092
- const constructorArgs = decodeContentField(
9099
+ const constructorArgs2 = decodeContentField(
9093
9100
  isLiteralValueContent(row) ? row.constructorArgs : void 0,
9094
9101
  "constructorArgs",
9095
9102
  scope,
9096
9103
  children
9097
9104
  );
9098
9105
  return {
9099
- row: withDecodedContent(row, value, constructorArgs),
9106
+ row: withDecodedContent(row, value, constructorArgs2),
9100
9107
  children,
9101
9108
  packedChildIdsByParentId: state.edges
9102
9109
  };
@@ -9158,13 +9165,13 @@ function encodePackedValueRow(args) {
9158
9165
  const pending = pendingPackedChildIds(scope);
9159
9166
  if (pending === null) return args.parent;
9160
9167
  const value = encodeContentField(args.parent.value, pending, scope);
9161
- const constructorArgs = encodeContentField(
9168
+ const constructorArgs2 = encodeContentField(
9162
9169
  isLiteralValueContent(args.parent) ? args.parent.constructorArgs : void 0,
9163
9170
  pending,
9164
9171
  scope
9165
9172
  );
9166
9173
  assertEveryChildPlaced(pending, scope);
9167
- return withDecodedContent(args.parent, value, constructorArgs);
9174
+ return withDecodedContent(args.parent, value, constructorArgs2);
9168
9175
  }
9169
9176
  function canonicalPackedChildId(args) {
9170
9177
  if (args.constructionRootId === null) return null;
@@ -9229,7 +9236,7 @@ function logicalChildRow(entry, id2, scope, children) {
9229
9236
  };
9230
9237
  if (isInitValueContent(entry)) return { ...rowFields, init: entry.init };
9231
9238
  const value = decodeContentField(entry.value, "value", scope, children);
9232
- const constructorArgs = decodeContentField(
9239
+ const constructorArgs2 = decodeContentField(
9233
9240
  entry.constructorArgs,
9234
9241
  "constructorArgs",
9235
9242
  scope,
@@ -9237,7 +9244,7 @@ function logicalChildRow(entry, id2, scope, children) {
9237
9244
  );
9238
9245
  return {
9239
9246
  ...rowFields,
9240
- ...literalContent(entry, value, constructorArgs)
9247
+ ...literalContent(entry, value, constructorArgs2)
9241
9248
  };
9242
9249
  }
9243
9250
  function packedEntryLogicalId(entry, label, constructionRootId) {
@@ -9391,7 +9398,7 @@ function encodeEnvelope(childId, position, pending, scope) {
9391
9398
  [PACKED_VALUE_ENTRY_KEY]: packedEntry(child2, null, null, storedId)
9392
9399
  };
9393
9400
  const value = encodeContentField(child2.value, childPending, childScope);
9394
- const constructorArgs = encodeContentField(
9401
+ const constructorArgs2 = encodeContentField(
9395
9402
  isLiteralValueContent(child2) ? child2.constructorArgs : void 0,
9396
9403
  childPending,
9397
9404
  childScope
@@ -9401,12 +9408,12 @@ function encodeEnvelope(childId, position, pending, scope) {
9401
9408
  [PACKED_VALUE_ENTRY_KEY]: packedEntry(
9402
9409
  child2,
9403
9410
  value,
9404
- constructorArgs,
9411
+ constructorArgs2,
9405
9412
  storedId
9406
9413
  )
9407
9414
  };
9408
9415
  }
9409
- function packedEntry(child2, value, constructorArgs, storedId) {
9416
+ function packedEntry(child2, value, constructorArgs2, storedId) {
9410
9417
  const identity2 = storedId === void 0 ? {} : { id: storedId };
9411
9418
  const trailer = {
9412
9419
  ...child2.genericBindings === void 0 ? {} : { genericBindings: child2.genericBindings },
@@ -9419,11 +9426,11 @@ function packedEntry(child2, value, constructorArgs, storedId) {
9419
9426
  }
9420
9427
  return {
9421
9428
  ...identity2,
9422
- ...literalContent(child2, value, constructorArgs),
9429
+ ...literalContent(child2, value, constructorArgs2),
9423
9430
  ...trailer
9424
9431
  };
9425
9432
  }
9426
- function literalContent(content, value, constructorArgs) {
9433
+ function literalContent(content, value, constructorArgs2) {
9427
9434
  if (!isLiteralValueContent(content)) {
9428
9435
  throw new PackedValueEncodingError(
9429
9436
  `Value container has no literal "value" to encode.`
@@ -9434,12 +9441,12 @@ function literalContent(content, value, constructorArgs) {
9434
9441
  value: value === null ? content.value : value.content,
9435
9442
  ...Object.hasOwn(content, "classId") ? { classId: content.classId } : {},
9436
9443
  ...provenance,
9437
- ...constructorArgs === null ? {} : { constructorArgs: asConstructorArgs(constructorArgs.content) }
9444
+ ...constructorArgs2 === null ? {} : { constructorArgs: asConstructorArgs(constructorArgs2.content) }
9438
9445
  };
9439
9446
  }
9440
- function withDecodedContent(row, value, constructorArgs) {
9441
- if (value === null && constructorArgs === null) return row;
9442
- return { ...row, ...literalContent(row, value, constructorArgs) };
9447
+ function withDecodedContent(row, value, constructorArgs2) {
9448
+ if (value === null && constructorArgs2 === null) return row;
9449
+ return { ...row, ...literalContent(row, value, constructorArgs2) };
9443
9450
  }
9444
9451
  function asConstructorArgs(content) {
9445
9452
  if (content === null) return null;
@@ -22581,6 +22588,197 @@ var init_project_source_ignore = __esm({
22581
22588
  }
22582
22589
  });
22583
22590
 
22591
+ // ../packages/neoscript-language/src/dialogue-group-paths.ts
22592
+ var DialogueGroupPaths, EMPTY_OPTIONS, EMPTY_GROUPS;
22593
+ var init_dialogue_group_paths = __esm({
22594
+ "../packages/neoscript-language/src/dialogue-group-paths.ts"() {
22595
+ "use strict";
22596
+ init_generated_csharp_identifiers();
22597
+ DialogueGroupPaths = class {
22598
+ constructor(groups, priorities, defaultPriorityId) {
22599
+ this.defaultPriorityId = defaultPriorityId;
22600
+ for (const group of groups) {
22601
+ this.byId.set(group.id, group);
22602
+ this.bySymbol.set(group.symbol, group);
22603
+ const children = this.children.get(group.parentId) ?? /* @__PURE__ */ new Map();
22604
+ const name = generatedCSharpTypeName(group.name, "DialogueGroup");
22605
+ children.set(name, children.has(name) ? null : group);
22606
+ this.children.set(group.parentId, children);
22607
+ }
22608
+ for (const [id2, options] of priorities)
22609
+ this.priorities.set(
22610
+ id2,
22611
+ new Map(options.map((option) => [option.name, option]))
22612
+ );
22613
+ }
22614
+ defaultPriorityId;
22615
+ byId = /* @__PURE__ */ new Map();
22616
+ bySymbol = /* @__PURE__ */ new Map();
22617
+ children = /* @__PURE__ */ new Map();
22618
+ priorities = /* @__PURE__ */ new Map();
22619
+ group(path) {
22620
+ const first = path[0];
22621
+ if (!first) return void 0;
22622
+ let group = this.bySymbol.get(first) ?? this.children.get(null)?.get(first) ?? void 0;
22623
+ for (let i2 = 1; group && i2 < path.length; i2++)
22624
+ group = this.children.get(group.id)?.get(path[i2]) ?? void 0;
22625
+ return group;
22626
+ }
22627
+ priorityOptions(group) {
22628
+ return this.priorities.get(
22629
+ group.priorityGroupId ?? this.defaultPriorityId ?? ""
22630
+ ) ?? EMPTY_OPTIONS;
22631
+ }
22632
+ childGroups(group) {
22633
+ return this.children.get(group.id) ?? EMPTY_GROUPS;
22634
+ }
22635
+ failure(path) {
22636
+ if (!this.group(path.slice(0, 1)))
22637
+ return `Unknown dialogue group ${path[0] ?? ""}.`;
22638
+ const parentPath = path.slice(0, -1);
22639
+ const parent = this.group(parentPath);
22640
+ if (!parent) return `Unknown dialogue group ${parentPath.join(".")}.`;
22641
+ if (this.group(path) && this.priorityOptions(parent).has(path.at(-1)))
22642
+ return `Ambiguous dialogue group and priority option ${path.join(".")}. Use the group's local symbol or explicit references.`;
22643
+ return `Unknown priority option ${path.join(".")}.`;
22644
+ }
22645
+ resolve(path) {
22646
+ const group = this.group(path);
22647
+ const parent = path.length > 1 ? this.group(path.slice(0, -1)) : void 0;
22648
+ const option = parent && this.priorityOptions(parent).get(path.at(-1));
22649
+ if (group && option) return void 0;
22650
+ if (group) return { group, option: null };
22651
+ return parent && option ? { group: parent, option } : void 0;
22652
+ }
22653
+ };
22654
+ EMPTY_OPTIONS = /* @__PURE__ */ new Map();
22655
+ EMPTY_GROUPS = /* @__PURE__ */ new Map();
22656
+ }
22657
+ });
22658
+
22659
+ // ../packages/neoscript-language/src/project-source-dialogue-groups.ts
22660
+ function sourceDialogueGroups(source) {
22661
+ const cached = catalogs.get(source.documents);
22662
+ if (cached) return cached;
22663
+ const symbols = /* @__PURE__ */ new Map();
22664
+ const globals = /* @__PURE__ */ new Map();
22665
+ const options = /* @__PURE__ */ new Map();
22666
+ for (const symbol of source.symbols) {
22667
+ if (symbol.kind !== "global") continue;
22668
+ if (symbol.detail !== "DialogueGroup" && symbol.detail !== "PriorityGroup")
22669
+ continue;
22670
+ const id2 = symbol.id ?? `${symbol.location.uri}#${symbol.name}`;
22671
+ globals.set(symbol.name, id2);
22672
+ symbols.set(id2, symbol);
22673
+ }
22674
+ for (const symbol of source.symbols) {
22675
+ if (symbol.kind !== "graphChild" || symbol.detail !== "PriorityOption")
22676
+ continue;
22677
+ const owner = globals.get(symbol.ownerName ?? "");
22678
+ if (!owner) continue;
22679
+ const id2 = symbol.id ?? `${owner}.${symbol.name}`;
22680
+ symbols.set(id2, symbol);
22681
+ const entries = options.get(owner) ?? [];
22682
+ entries.push({ id: id2, name: symbol.name });
22683
+ options.set(owner, entries);
22684
+ }
22685
+ const groups = [];
22686
+ let defaultPriorityId = null;
22687
+ for (const document of source.documents.values()) {
22688
+ for (const declaration of document.declarations) {
22689
+ if (declaration.kind !== "global") continue;
22690
+ const type = declaration.type.name;
22691
+ if (type !== "DialogueGroup" && type !== "Project") continue;
22692
+ const args = constructorArgs(
22693
+ declaration.dialogueGroup?.constructor.text ?? declaration.initializer.text
22694
+ );
22695
+ if (type === "Project") {
22696
+ defaultPriorityId = referenceId(
22697
+ args.get("defaultPriorityGroup"),
22698
+ globals
22699
+ );
22700
+ continue;
22701
+ }
22702
+ const id2 = globals.get(declaration.name);
22703
+ if (!id2) continue;
22704
+ const name = args.get("name");
22705
+ groups.push({
22706
+ id: id2,
22707
+ symbol: declaration.name,
22708
+ name: name?.kind === "litString" ? name.value : declaration.name,
22709
+ parentId: referenceId(args.get("parent"), globals),
22710
+ priorityGroupId: referenceId(args.get("priorityGroup"), globals)
22711
+ });
22712
+ }
22713
+ }
22714
+ const result = {
22715
+ paths: new DialogueGroupPaths(groups, options, defaultPriorityId),
22716
+ symbols
22717
+ };
22718
+ catalogs.set(source.documents, result);
22719
+ return result;
22720
+ }
22721
+ function constructorArgs(text) {
22722
+ try {
22723
+ const expression = parseExpression(text);
22724
+ if (expression.kind !== "new") return /* @__PURE__ */ new Map();
22725
+ const args = /* @__PURE__ */ new Map();
22726
+ expression.args.forEach((arg, index) => {
22727
+ const name = expression.argumentNames?.[index];
22728
+ if (name) args.set(name, arg);
22729
+ });
22730
+ return args;
22731
+ } catch {
22732
+ return /* @__PURE__ */ new Map();
22733
+ }
22734
+ }
22735
+ function referenceId(expression, symbols) {
22736
+ if (expression?.kind === "ident") return symbols.get(expression.name) ?? null;
22737
+ if (expression?.kind === "call" && expression.callee.kind === "ident" && expression.callee.name === "Reference") {
22738
+ const id2 = expression.args[0];
22739
+ if (id2?.kind === "litString") return id2.value;
22740
+ }
22741
+ return null;
22742
+ }
22743
+ function validateDialogueGroupPaths(source) {
22744
+ const diagnostics = [];
22745
+ let catalog;
22746
+ for (const [uri, document] of source.documents) {
22747
+ for (const declaration of document.declarations) {
22748
+ if (declaration.kind !== "class") continue;
22749
+ for (const member of declaration.members) {
22750
+ if (member.kind !== "field" || member.type.name !== "Trigger") continue;
22751
+ const arg = member.flowInitializer?.arguments.find(
22752
+ (argument2) => argument2.name === "group"
22753
+ );
22754
+ if (!arg) continue;
22755
+ const path = arg.text.trim().split(/\s*\.\s*/u);
22756
+ if (path.length < 2 || path.some((segment) => !/^[A-Za-z_][A-Za-z0-9_]*$/u.test(segment)))
22757
+ continue;
22758
+ catalog ??= sourceDialogueGroups(source);
22759
+ if (catalog.paths.resolve(path)) continue;
22760
+ diagnostics.push({
22761
+ uri,
22762
+ severity: "error",
22763
+ code: "neoflow-lowering",
22764
+ message: catalog.paths.failure(path),
22765
+ range: arg.valueRange ?? arg.range
22766
+ });
22767
+ }
22768
+ }
22769
+ }
22770
+ return diagnostics;
22771
+ }
22772
+ var catalogs;
22773
+ var init_project_source_dialogue_groups = __esm({
22774
+ "../packages/neoscript-language/src/project-source-dialogue-groups.ts"() {
22775
+ "use strict";
22776
+ init_dialogue_group_paths();
22777
+ init_executable_parser();
22778
+ catalogs = /* @__PURE__ */ new WeakMap();
22779
+ }
22780
+ });
22781
+
22584
22782
  // ../packages/neoscript-language/src/project-source-tokens.ts
22585
22783
  function rangeContains(range2, position) {
22586
22784
  return positionCompare(range2.start, position) <= 0 && positionCompare(position, range2.end) <= 0;
@@ -44298,6 +44496,7 @@ function analyzeNeoProjectSources(inputs, parsedDocuments = /* @__PURE__ */ new
44298
44496
  }
44299
44497
  }
44300
44498
  validateSymbolUniqueness(symbols, diagnostics);
44499
+ diagnostics.push(...validateDialogueGroupPaths({ documents, symbols }));
44301
44500
  diagnostics.push(...validateLocalValueInitializers(documents));
44302
44501
  diagnostics.push(...validateVariantDeclarations(documents));
44303
44502
  validateSystemAnnotationAuthoring(documents, diagnostics);
@@ -44919,6 +45118,7 @@ var BUILTIN_TYPE_NAMES, SYSTEM_RECORD_ID_PREFIX2, RFC_4122_UUID, QUARANTINED_LEG
44919
45118
  var init_project_source_analysis = __esm({
44920
45119
  "../packages/neoscript-language/src/project-source-analysis.ts"() {
44921
45120
  "use strict";
45121
+ init_project_source_dialogue_groups();
44922
45122
  init_project_local_values();
44923
45123
  init_language_spec();
44924
45124
  init_pending_id();
@@ -45998,7 +46198,7 @@ var init_registry = __esm({
45998
46198
  "../packages/manifest/schema-contract/registry.mjs"() {
45999
46199
  "use strict";
46000
46200
  PROJECT_SCHEMA_CONTRACT = Object.freeze({
46001
- cliVersion: "0.71.2",
46201
+ cliVersion: "0.71.4",
46002
46202
  projectFileUploadBatchSize: 32,
46003
46203
  documentRecords: {
46004
46204
  member: {
@@ -47420,6 +47620,127 @@ var init_registry = __esm({
47420
47620
  }
47421
47621
  });
47422
47622
 
47623
+ // ../packages/manifest/src/value-comparison.ts
47624
+ function isObjectRecord2(value) {
47625
+ return typeof value === "object" && value !== null && !Array.isArray(value);
47626
+ }
47627
+ function splitRecordFields(data, serverOwnedFields) {
47628
+ const fileFields = {};
47629
+ const volatileValues = {};
47630
+ for (const [key, value] of Object.entries(data)) {
47631
+ if (value === void 0) continue;
47632
+ if (serverOwnedFields.includes(key)) {
47633
+ volatileValues[key] = value;
47634
+ } else {
47635
+ fileFields[key] = value;
47636
+ }
47637
+ }
47638
+ return { fileFields, volatileValues };
47639
+ }
47640
+ function canonicallyEqual(left, right) {
47641
+ return canonicalStringify(left) === canonicalStringify(right);
47642
+ }
47643
+ function canonicalStringify(value) {
47644
+ return JSON.stringify(toCanonical(value));
47645
+ }
47646
+ function toCanonical(value) {
47647
+ if (value === null || value === void 0) return value ?? null;
47648
+ if (Array.isArray(value)) return value.map((item) => toCanonical(item));
47649
+ if (typeof value === "object") {
47650
+ const entries = Object.entries(value).filter(([, entryValue]) => entryValue !== void 0).sort(([left], [right]) => left < right ? -1 : left > right ? 1 : 0);
47651
+ const result = {};
47652
+ for (const [key, entryValue] of entries) {
47653
+ result[key] = toCanonical(entryValue);
47654
+ }
47655
+ return result;
47656
+ }
47657
+ return value;
47658
+ }
47659
+ function isUuidV4Id(id2) {
47660
+ return /^[0-9a-f]{8}-[0-9a-f]{4}-4[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$/u.test(
47661
+ id2
47662
+ );
47663
+ }
47664
+ var init_value_comparison = __esm({
47665
+ "../packages/manifest/src/value-comparison.ts"() {
47666
+ "use strict";
47667
+ }
47668
+ });
47669
+
47670
+ // src/project-source/dialogue-group-symbols.ts
47671
+ function authoredDialogueGroupSymbols(analysis) {
47672
+ return new Map(
47673
+ analysis?.dialogueGroups.globals.filter((global) => global.type.name === "DialogueGroup").map((global) => [
47674
+ global.id ?? `__pending__:dialogue-group:${encodeURIComponent(global.source.uri)}:${global.source.range.start.line}:${global.source.range.start.character}:${encodeURIComponent(global.name)}`,
47675
+ global.name
47676
+ ])
47677
+ );
47678
+ }
47679
+ function emittedDialogueGroupSymbols(records2, local = /* @__PURE__ */ new Map(), reservedNames = []) {
47680
+ const result = /* @__PURE__ */ new Map();
47681
+ const used = /* @__PURE__ */ new Set([
47682
+ "project",
47683
+ "localization",
47684
+ "images",
47685
+ "audioclips",
47686
+ "root",
47687
+ "projectrelations"
47688
+ ]);
47689
+ for (const name of reservedNames) used.add(name.toLowerCase());
47690
+ const groups = [];
47691
+ const nextSuffix = /* @__PURE__ */ new Map();
47692
+ for (const record7 of records2.values()) {
47693
+ if (record7.deleted || !isObjectRecord2(record7.data)) continue;
47694
+ if (record7.recordKind === "dialogue-group") {
47695
+ groups.push(record7);
47696
+ continue;
47697
+ }
47698
+ const name = record7.recordKind === "dialogue" ? record7.data.sourceName : record7.data.name;
47699
+ if (GLOBAL_RECORD_KINDS.has(record7.recordKind) && typeof name === "string")
47700
+ used.add(name.toLowerCase());
47701
+ }
47702
+ for (const record7 of groups) {
47703
+ const symbol = local.get(record7.recordId);
47704
+ if (symbol && isValidNeoProjectIdentifier(symbol)) {
47705
+ if (used.has(symbol.toLowerCase()))
47706
+ throw new Error(`Duplicate local dialogue group symbol ${symbol}.`);
47707
+ result.set(record7.recordId, symbol);
47708
+ used.add(symbol.toLowerCase());
47709
+ }
47710
+ }
47711
+ for (const group of groups) {
47712
+ if (result.has(group.recordId) || !isObjectRecord2(group.data)) continue;
47713
+ const name = typeof group.data.name === "string" ? group.data.name : "DialogueGroup";
47714
+ const candidate = isValidNeoProjectIdentifier(name) ? name : generatedCSharpTypeName(name, "DialogueGroup");
47715
+ let symbol = candidate;
47716
+ let suffix = nextSuffix.get(candidate.toLowerCase()) ?? 2;
47717
+ while (used.has(symbol.toLowerCase()) || !isValidNeoProjectIdentifier(symbol))
47718
+ symbol = `${candidate}${suffix++}`;
47719
+ nextSuffix.set(candidate.toLowerCase(), suffix);
47720
+ used.add(symbol.toLowerCase());
47721
+ result.set(group.recordId, symbol);
47722
+ }
47723
+ return result;
47724
+ }
47725
+ var GLOBAL_RECORD_KINDS;
47726
+ var init_dialogue_group_symbols = __esm({
47727
+ "src/project-source/dialogue-group-symbols.ts"() {
47728
+ "use strict";
47729
+ init_value_comparison();
47730
+ init_project_source_identifiers();
47731
+ init_generated_csharp_identifiers();
47732
+ GLOBAL_RECORD_KINDS = /* @__PURE__ */ new Set([
47733
+ "class",
47734
+ "interface",
47735
+ "enum",
47736
+ "priority-group",
47737
+ "unity-texture-template",
47738
+ "unity-audio-clip-template",
47739
+ "dialogue"
47740
+ ]);
47741
+ }
47742
+ });
47743
+
47423
47744
  // src/project-sync/source-diagnostics.ts
47424
47745
  function isPullRecoveryDiagnosticCode(code) {
47425
47746
  return code !== void 0 && PULL_RECOVERY_DIAGNOSTIC_CODES.has(code);
@@ -47593,53 +47914,6 @@ var init_names = __esm({
47593
47914
  }
47594
47915
  });
47595
47916
 
47596
- // ../packages/manifest/src/value-comparison.ts
47597
- function isObjectRecord2(value) {
47598
- return typeof value === "object" && value !== null && !Array.isArray(value);
47599
- }
47600
- function splitRecordFields(data, serverOwnedFields) {
47601
- const fileFields = {};
47602
- const volatileValues = {};
47603
- for (const [key, value] of Object.entries(data)) {
47604
- if (value === void 0) continue;
47605
- if (serverOwnedFields.includes(key)) {
47606
- volatileValues[key] = value;
47607
- } else {
47608
- fileFields[key] = value;
47609
- }
47610
- }
47611
- return { fileFields, volatileValues };
47612
- }
47613
- function canonicallyEqual(left, right) {
47614
- return canonicalStringify(left) === canonicalStringify(right);
47615
- }
47616
- function canonicalStringify(value) {
47617
- return JSON.stringify(toCanonical(value));
47618
- }
47619
- function toCanonical(value) {
47620
- if (value === null || value === void 0) return value ?? null;
47621
- if (Array.isArray(value)) return value.map((item) => toCanonical(item));
47622
- if (typeof value === "object") {
47623
- const entries = Object.entries(value).filter(([, entryValue]) => entryValue !== void 0).sort(([left], [right]) => left < right ? -1 : left > right ? 1 : 0);
47624
- const result = {};
47625
- for (const [key, entryValue] of entries) {
47626
- result[key] = toCanonical(entryValue);
47627
- }
47628
- return result;
47629
- }
47630
- return value;
47631
- }
47632
- function isUuidV4Id(id2) {
47633
- return /^[0-9a-f]{8}-[0-9a-f]{4}-4[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$/u.test(
47634
- id2
47635
- );
47636
- }
47637
- var init_value_comparison = __esm({
47638
- "../packages/manifest/src/value-comparison.ts"() {
47639
- "use strict";
47640
- }
47641
- });
47642
-
47643
47917
  // src/project-sync/migration-files.ts
47644
47918
  function migrationFileName(order, name) {
47645
47919
  const slug = sanitizeCsIdentifier(name).replace(/_/g, "-").toLowerCase();
@@ -61773,7 +62047,7 @@ function resolveQualifiedMemberId(context, expression) {
61773
62047
  const match = /^([A-Za-z_][A-Za-z0-9_]*)\.([A-Za-z_][A-Za-z0-9_]*)$/.exec(
61774
62048
  expression.trim()
61775
62049
  );
61776
- if (!match) return referenceId(expression);
62050
+ if (!match) return referenceId2(expression);
61777
62051
  const classId = context.classIdsByName.get(match[1]);
61778
62052
  if (!classId) return null;
61779
62053
  return effectiveMemberIdByName(context, classId, match[2]);
@@ -61904,7 +62178,7 @@ function templateSymbolArgument(context, settings, ownerClass, declaration) {
61904
62178
  }
61905
62179
  return templateId;
61906
62180
  }
61907
- function referenceId(raw) {
62181
+ function referenceId2(raw) {
61908
62182
  const parsed = parseReferenceArgument(raw);
61909
62183
  if (parsed === null || parsed.kind === "none") return null;
61910
62184
  return parsed.kind === "id" ? parsed.value : `${PENDING_ID_PREFIX}root-path:${parsed.value}`;
@@ -62068,7 +62342,7 @@ function lowerVariantDefault(context, expression, expected, path) {
62068
62342
  };
62069
62343
  }
62070
62344
  function lowerVariantBindingReference(context, expression, path) {
62071
- const id2 = referenceId(expressionSource(expression));
62345
+ const id2 = referenceId2(expressionSource(expression));
62072
62346
  if (id2 === null) {
62073
62347
  throw new Error(
62074
62348
  `${path}.Bind requires Reference(id: ...) or Reference(root....).`
@@ -62939,7 +63213,7 @@ function emitSupplementalProjectSourcesV4(records2, binaryPaths, options = {}) {
62939
63213
  const textureNames = namesById(live, "unity-texture-template");
62940
63214
  const audioNames = namesById(live, "unity-audio-clip-template");
62941
63215
  const priorityNames = namesById(live, "priority-group");
62942
- const dialogueNames = namesById(live, "dialogue-group");
63216
+ const dialogueNames = options.dialogueGroupSymbols ?? emittedDialogueGroupSymbols(records2);
62943
63217
  const uiLogicResolver = supplementalUILogicResolver(live);
62944
63218
  const files = [];
62945
63219
  const memberContext = {
@@ -62981,7 +63255,7 @@ function emitSupplementalProjectSourcesV4(records2, binaryPaths, options = {}) {
62981
63255
  (candidate) => candidate.recordKind === "dialogue-group"
62982
63256
  )) {
62983
63257
  const data = recordData(record7);
62984
- const name = requiredName2(data, record7);
63258
+ const name = dialogueNames.get(record7.recordId);
62985
63259
  files.push({
62986
63260
  path: defaultDeclarationPathV4("DialogueGroups", name, record7.recordId),
62987
63261
  content: emitDialogueGroup(
@@ -63125,6 +63399,8 @@ function emitDialogueGroup(data, recordId, name, priorityNames, dialogueNames, u
63125
63399
  assertProjectIdentifier2(name, "dialogue group");
63126
63400
  const kind = data.type === 1 ? "Lookup" : data.type === 2 ? "Folder" : "Standard";
63127
63401
  const args = [["kind", `.${kind}`]];
63402
+ if (data.name !== name && typeof data.name === "string")
63403
+ args.push(["name", quote2(data.name)]);
63128
63404
  const priority = reference(
63129
63405
  data.priorityGroupIdOverride,
63130
63406
  priorityNames,
@@ -63351,6 +63627,13 @@ function dialogueGroupType(name, args) {
63351
63627
  throw new Error(`Unknown dialogue group kind .${kind.name}.`);
63352
63628
  return type;
63353
63629
  }
63630
+ function dialogueGroupDisplayName(expression, symbol) {
63631
+ if (expression?.kind !== "litString" || expression.value.trim().length === 0)
63632
+ throw new Error(
63633
+ `DialogueGroup ${symbol} name must be a non-empty string literal.`
63634
+ );
63635
+ return expression.value;
63636
+ }
63354
63637
  function lowerDialogueGroup(baseValue, global, priorityIds, dialogueIds, uiLogicResolver, memberContext) {
63355
63638
  const base = optionalBase(baseValue);
63356
63639
  const baseWithoutLookup = { ...base };
@@ -63377,7 +63660,7 @@ function lowerDialogueGroup(baseValue, global, priorityIds, dialogueIds, uiLogic
63377
63660
  collectionMemberId = resolveOptionalReference(collection, /* @__PURE__ */ new Map());
63378
63661
  }
63379
63662
  const collectionValue = args.get("collectionValue");
63380
- const collectionValueId = collectionValue === void 0 || collectionValue.kind === "litNull" ? null : referenceId(collectionValue);
63663
+ const collectionValueId = collectionValue === void 0 || collectionValue.kind === "litNull" ? null : referenceId2(collectionValue);
63381
63664
  if (collectionValue !== void 0 && collectionValue.kind !== "litNull" && collectionValueId === null) {
63382
63665
  throw new Error(
63383
63666
  `Lookup dialogue group ${global.name} requires collectionValue: Reference(root.Assets.Member), Reference(id: ...), or null.`
@@ -63386,7 +63669,7 @@ function lowerDialogueGroup(baseValue, global, priorityIds, dialogueIds, uiLogic
63386
63669
  return {
63387
63670
  ...baseWithoutLookup,
63388
63671
  id: globalId(global, "dialogue-group"),
63389
- name: global.name,
63672
+ name: args.has("name") ? dialogueGroupDisplayName(args.get("name"), global.name) : global.name,
63390
63673
  type,
63391
63674
  parentDialogueGroupId: resolveOptionalReference(
63392
63675
  args.get("parent"),
@@ -63960,6 +64243,7 @@ var PRIORITY_OPTION_PATTERN;
63960
64243
  var init_supplemental_records = __esm({
63961
64244
  "src/project-source/supplemental-records.ts"() {
63962
64245
  "use strict";
64246
+ init_dialogue_group_symbols();
63963
64247
  init_source_diagnostics();
63964
64248
  init_project_source_identifiers();
63965
64249
  init_lexer();
@@ -63994,6 +64278,18 @@ function sourceNameTokens(value) {
63994
64278
  const ascii = value.normalize("NFKD").replace(new RegExp("\\p{Mark}", "gu"), "").replace(/[\u0027\u2019]/gu, "");
63995
64279
  return (ascii.match(/[A-Za-z0-9]+/gu) ?? []).map((token) => `${token[0]?.toUpperCase() ?? ""}${token.slice(1)}`).join("");
63996
64280
  }
64281
+ function isDefaultDialogueSourceName(value) {
64282
+ return /^(?:Dialogue|Node|Option|Outcome|Value)_[0-9a-f_]{8,}$/iu.test(value) || /^NeoFunction_[0-9a-f]{16,}$/iu.test(value) || /^(?:Actions?|Conditions?|Dialogue|Node|Option|Outcome|Text|TextValue|Value)[0-9]+(?:_[0-9]+)?$/iu.test(
64283
+ value
64284
+ );
64285
+ }
64286
+ function inferredDialogueDisplayName(sourceName, kind) {
64287
+ if (!isDefaultDialogueSourceName(sourceName)) return sourceName;
64288
+ const family = /^[A-Za-z]+/u.exec(sourceName)?.[0]?.toLowerCase();
64289
+ if (family === kind.toLowerCase()) return null;
64290
+ const bodyNode = kind === "Text" || kind === "Actions" || kind === "Conditions";
64291
+ return bodyNode && family === "node" ? null : sourceName;
64292
+ }
63997
64293
  var DialogueSourceNameAllocator;
63998
64294
  var init_dialogue_source_names = __esm({
63999
64295
  "../src/models/dialogue/dialogue-source-names.ts"() {
@@ -64253,11 +64549,6 @@ function keptSourceName(value) {
64253
64549
  if (!isDialogueSourceIdentifier(value)) return null;
64254
64550
  return isDefaultDialogueSourceName(value) ? null : value;
64255
64551
  }
64256
- function isDefaultDialogueSourceName(value) {
64257
- return /^(?:Dialogue|Node|Option|Outcome|Value)_[0-9a-f_]{8,}$/iu.test(value) || /^NeoFunction_[0-9a-f]{16,}$/iu.test(value) || /^(?:Actions?|Conditions?|Dialogue|Node|Option|Outcome|Text|TextValue|Value)[0-9]+(?:_[0-9]+)?$/iu.test(
64258
- value
64259
- );
64260
- }
64261
64552
  function linkedValueRecords(rawLinks, owner) {
64262
64553
  if (!Array.isArray(rawLinks)) return [];
64263
64554
  return rawLinks.map((rawLink, index) => {
@@ -64488,7 +64779,7 @@ function optionalMeaningfulString(value) {
64488
64779
  function recordKey(record7) {
64489
64780
  return `${record7.recordKind}:${record7.recordId}`;
64490
64781
  }
64491
- function emitDialogueProjectSourcesV4(records2) {
64782
+ function emitDialogueProjectSourcesV4(records2, groupSymbols) {
64492
64783
  const live = [...records2.values()].filter((record7) => !record7.deleted);
64493
64784
  const dialogues = live.filter((record7) => record7.recordKind === "dialogue");
64494
64785
  if (dialogues.length === 0) return [];
@@ -64505,10 +64796,22 @@ function emitDialogueProjectSourcesV4(records2) {
64505
64796
  );
64506
64797
  const mainLocale = localization ? optionalString2(recordData2(localization).mainLocale) ?? "en-US" : "en-US";
64507
64798
  const values = new ValuePlacementIndex(live);
64508
- const dialogueGroupNames = namesById2(live, "dialogue-group");
64799
+ const dialogueGroupNames = groupSymbols ?? emittedDialogueGroupSymbols(records2);
64509
64800
  const memberNames = validNamesById(live, "member");
64510
64801
  const staticMemberExpressions = staticMemberExpressionsById(live);
64511
64802
  const enumOptionNames2 = enumOptionNamesById(live);
64803
+ const groupChildNames = /* @__PURE__ */ new Map();
64804
+ for (const record7 of live) {
64805
+ if (record7.recordKind !== "dialogue-group") continue;
64806
+ const data = recordData2(record7);
64807
+ const parentId = optionalString2(data.parentDialogueGroupId);
64808
+ if (!parentId) continue;
64809
+ const names = groupChildNames.get(parentId) ?? /* @__PURE__ */ new Set();
64810
+ names.add(
64811
+ generatedCSharpTypeName(stringField(data, "name"), "DialogueGroup")
64812
+ );
64813
+ groupChildNames.set(parentId, names);
64814
+ }
64512
64815
  const priorityOptionNames = /* @__PURE__ */ new Map();
64513
64816
  for (const record7 of live.filter(
64514
64817
  (candidate) => candidate.recordKind === "priority-group"
@@ -64539,6 +64842,7 @@ function emitDialogueProjectSourcesV4(records2) {
64539
64842
  localizedTexts,
64540
64843
  mainLocale,
64541
64844
  dialogueGroupNames,
64845
+ groupChildNames,
64542
64846
  priorityOptionNames,
64543
64847
  memberNames,
64544
64848
  staticMemberExpressions,
@@ -64593,6 +64897,7 @@ function emitDialogueProjectSourcesV4(records2) {
64593
64897
  localizedTexts,
64594
64898
  mainLocale,
64595
64899
  dialogueGroupNames,
64900
+ groupChildNames,
64596
64901
  priorityOptionNames,
64597
64902
  memberNames,
64598
64903
  staticMemberExpressions,
@@ -64637,6 +64942,7 @@ function emitDialogue(args) {
64637
64942
  localizedTexts: args.localizedTexts,
64638
64943
  mainLocale: args.mainLocale,
64639
64944
  dialogueGroupNames: args.dialogueGroupNames,
64945
+ groupChildNames: args.groupChildNames,
64640
64946
  priorityOptionNames: args.priorityOptionNames,
64641
64947
  memberNames: args.memberNames,
64642
64948
  staticMemberExpressions: args.staticMemberExpressions,
@@ -64645,7 +64951,7 @@ function emitDialogue(args) {
64645
64951
  const localizedTextIds = /* @__PURE__ */ new Set();
64646
64952
  const settings = [];
64647
64953
  const displayName = optionalString2(args.dialogue.name);
64648
- if (displayName !== null) settings.push(["name", quote3(displayName)]);
64954
+ emitDisplayName(settings, displayName, args.className, "Dialogue");
64649
64955
  const descriptionId = optionalString2(args.dialogue.description);
64650
64956
  if (descriptionId) {
64651
64957
  settings.push([
@@ -64716,7 +65022,7 @@ function emitTrigger(context, node) {
64716
65022
  const optionId = optionalString2(priority.priorityOptionId);
64717
65023
  const groupName = groupId ? context.dialogueGroupNames.get(groupId) : void 0;
64718
65024
  const optionName = optionId ? context.priorityOptionNames.get(optionId) : void 0;
64719
- if (groupName && optionName)
65025
+ if (groupName && optionName && !context.groupChildNames.get(groupId)?.has(optionName))
64720
65026
  args.push(["group", `${groupName}.${optionName}`]);
64721
65027
  else if (groupId) {
64722
65028
  args.push(["group", `Reference<DialogueGroup>(id: ${quote3(groupId)})`]);
@@ -64754,8 +65060,7 @@ function emitTextNode(context, node) {
64754
65060
  const id2 = stringField(node, "id");
64755
65061
  const symbol = requiredMap(context.nodeNames, id2, "dialogue node");
64756
65062
  const args = [];
64757
- const name = optionalString2(node.name);
64758
- if (name) args.push(["name", quote3(name)]);
65063
+ emitDisplayName(args, optionalString2(node.name), symbol, "Text");
64759
65064
  const textId = optionalString2(node.text);
64760
65065
  const nodeBindings = allocateBindings(node.linkedValues, context.values);
64761
65066
  assertNoBindingShadow(context.bindings, nodeBindings);
@@ -64818,8 +65123,7 @@ ${lines.map((line) => indentNeoSource(line, 2)).join("\n\n")}
64818
65123
  function emitOption(context, option, symbol, nodeBindings, prosePrimaryAlias) {
64819
65124
  const id2 = stringField(option, "id");
64820
65125
  const args = [];
64821
- const name = optionalString2(option.name);
64822
- if (name) args.push(["name", quote3(name)]);
65126
+ emitDisplayName(args, optionalString2(option.name), symbol, "Option");
64823
65127
  const settings = isObjectRecord2(option.settings) ? option.settings : null;
64824
65128
  const visible = conditionUses(context, settings?.conditions);
64825
65129
  const selectable = conditionUses(context, settings?.selectableConditions);
@@ -64854,8 +65158,7 @@ function emitActionsNode(context, node) {
64854
65158
  const id2 = stringField(node, "id");
64855
65159
  const symbol = requiredMap(context.nodeNames, id2, "dialogue node");
64856
65160
  const args = [];
64857
- const name = optionalString2(node.name);
64858
- if (name) args.push(["name", quote3(name)]);
65161
+ emitDisplayName(args, optionalString2(node.name), symbol, "Actions");
64859
65162
  const actions = Array.isArray(node.actions) ? node.actions : [];
64860
65163
  const lines = [];
64861
65164
  const nodeBindings = allocateBindings(node.linkedValues, context.values);
@@ -64932,8 +65235,7 @@ function emitConditionsNode(context, node) {
64932
65235
  const id2 = stringField(node, "id");
64933
65236
  const symbol = requiredMap(context.nodeNames, id2, "dialogue node");
64934
65237
  const args = [];
64935
- const name = optionalString2(node.name);
64936
- if (name) args.push(["name", quote3(name)]);
65238
+ emitDisplayName(args, optionalString2(node.name), symbol, "Conditions");
64937
65239
  const lines = emitNodeBindings(context, node);
64938
65240
  const outcomes = Array.isArray(node.outcomes) ? node.outcomes : [];
64939
65241
  const names = new UniqueNames();
@@ -64943,10 +65245,12 @@ function emitConditionsNode(context, node) {
64943
65245
  const outcomeName = names.claim(sourceIdentifier(raw, "sourceName"));
64944
65246
  const uses = conditionUses(context, raw.conditions);
64945
65247
  const outcomeArgs = uses.length > 0 ? [["when", emitUseList(uses)]] : [];
64946
- const outcomeDisplayName = optionalString2(raw.name);
64947
- if (outcomeDisplayName !== null && outcomeDisplayName !== outcomeName) {
64948
- outcomeArgs.unshift(["name", quote3(outcomeDisplayName)]);
64949
- }
65248
+ emitDisplayName(
65249
+ outcomeArgs,
65250
+ optionalString2(raw.name),
65251
+ outcomeName,
65252
+ "Outcome"
65253
+ );
64950
65254
  const destination = destinationName(
64951
65255
  context,
64952
65256
  raw.toNodeId,
@@ -65281,14 +65585,6 @@ function allocateBindings(rawLinks, placements) {
65281
65585
  });
65282
65586
  return result;
65283
65587
  }
65284
- function namesById2(records2, kind) {
65285
- return new Map(
65286
- records2.filter((record7) => record7.recordKind === kind).map((record7) => [
65287
- record7.recordId,
65288
- sourceIdentifier(recordData2(record7), "name")
65289
- ])
65290
- );
65291
- }
65292
65588
  function validNamesById(records2, kind) {
65293
65589
  return new Map(
65294
65590
  records2.flatMap((record7) => {
@@ -65414,10 +65710,19 @@ function requiredMap(map, id2, label) {
65414
65710
  function quote3(value) {
65415
65711
  return quoteNeoString(value);
65416
65712
  }
65713
+ function emitDisplayName(args, name, symbol, kind) {
65714
+ const empty2 = kind === "Dialogue" || kind === "Outcome" ? "" : null;
65715
+ const stored = name ?? empty2;
65716
+ const inferred = inferredDialogueDisplayName(symbol, kind) ?? empty2;
65717
+ if (stored !== inferred)
65718
+ args.unshift(["name", stored === null ? "null" : quote3(stored)]);
65719
+ }
65417
65720
  var PERSISTED_VARIABLE_PATH, DIALOGUE_SYSTEM_TYPE_NAMES, ValuePlacementIndex, UniqueNames;
65418
65721
  var init_dialogue_sources = __esm({
65419
65722
  "src/project-source/dialogue-sources.ts"() {
65420
65723
  "use strict";
65724
+ init_generated_csharp_identifiers();
65725
+ init_dialogue_group_symbols();
65421
65726
  init_language_spec();
65422
65727
  init_dialogue_source_names();
65423
65728
  init_dialogue_source_identifiers();
@@ -65992,9 +66297,9 @@ function collectDelegateClosureSite(container, sites, authored) {
65992
66297
  sites.push({ container: delegate, key: "action", authored });
65993
66298
  }
65994
66299
  function collectInlineDelegateArgumentSites(record7, sites) {
65995
- const constructorArgs = asRecord2(record7.constructorArgs);
65996
- if (constructorArgs === null) return;
65997
- for (const argument2 of Object.values(constructorArgs)) {
66300
+ const constructorArgs2 = asRecord2(record7.constructorArgs);
66301
+ if (constructorArgs2 === null) return;
66302
+ for (const argument2 of Object.values(constructorArgs2)) {
65998
66303
  const closure = asRecord2(argument2);
65999
66304
  if (closure === null) continue;
66000
66305
  if (typeof closure.code !== "string") continue;
@@ -66208,8 +66513,8 @@ function buildStoredValuePlacementIndexV4(records2, logicalValues) {
66208
66513
  }
66209
66514
  }
66210
66515
  const constructorId = value.instanceConstructorId;
66211
- const constructorArgs = value.constructorArgs;
66212
- if (classId === null || typeof constructorId !== "string" || !isObjectRecord2(constructorArgs)) {
66516
+ const constructorArgs2 = value.constructorArgs;
66517
+ if (classId === null || typeof constructorId !== "string" || !isObjectRecord2(constructorArgs2)) {
66213
66518
  continue;
66214
66519
  }
66215
66520
  const constructor2 = constructors.get(constructorId);
@@ -66227,7 +66532,7 @@ function buildStoredValuePlacementIndexV4(records2, logicalValues) {
66227
66532
  continue;
66228
66533
  }
66229
66534
  const parameterId = constructorActionParameterId(constructor2, index);
66230
- const childValueId2 = constructorArgs[parameterId];
66535
+ const childValueId2 = constructorArgs2[parameterId];
66231
66536
  if (typeof childValueId2 !== "string" || !values.has(childValueId2) || !memberStoresAggregate(
66232
66537
  memberDataById.get(settled.memberId),
66233
66538
  value,
@@ -71442,7 +71747,7 @@ var init_constructor_argument_ownership = __esm({
71442
71747
  }
71443
71748
  }
71444
71749
  const parameterTypes = this.constructorParameterTypes(row);
71445
- const constructorArgs = row.constructorArgs === void 0 || row.constructorArgs === null ? row.constructorArgs : Object.fromEntries(
71750
+ const constructorArgs2 = row.constructorArgs === void 0 || row.constructorArgs === null ? row.constructorArgs : Object.fromEntries(
71446
71751
  Object.entries(row.constructorArgs).map(
71447
71752
  ([parameterId, argument2]) => {
71448
71753
  const typeInfo = parameterTypes.get(parameterId);
@@ -71459,7 +71764,7 @@ var init_constructor_argument_ownership = __esm({
71459
71764
  value,
71460
71765
  ...typeof row.containerId !== "string" ? {} : { containerId: rewriteId(row.containerId) },
71461
71766
  ...row.sourceValueId === void 0 ? {} : { sourceValueId: rewriteId(row.sourceValueId) },
71462
- ...constructorArgs === void 0 ? {} : { constructorArgs }
71767
+ ...constructorArgs2 === void 0 ? {} : { constructorArgs: constructorArgs2 }
71463
71768
  };
71464
71769
  }
71465
71770
  collectSoftOwnedRows(ownerValueId, preservedValueIds) {
@@ -83086,9 +83391,9 @@ function evaluateInitializerInContext(init, member, ctx, createdValues, argument
83086
83391
  }
83087
83392
  deleteRuntimeSessionValue(ctx, rootRow.id);
83088
83393
  ctx.__executionState?.constructorGroups.delete(rootRow.id);
83089
- const constructorArgs = typeof result.value === "object" && result.value !== null ? ctx.__constructedArgumentsByValue.get(result.value) ?? rootRow.constructorArgs ?? void 0 : void 0;
83394
+ const constructorArgs2 = typeof result.value === "object" && result.value !== null ? ctx.__constructedArgumentsByValue.get(result.value) ?? rootRow.constructorArgs ?? void 0 : void 0;
83090
83395
  const provenance = pickInstanceProvenance({
83091
- constructorArgs,
83396
+ constructorArgs: constructorArgs2,
83092
83397
  instanceConstructorId: rootRow.instanceConstructorId,
83093
83398
  instanceVariantId: rootRow.instanceVariantId,
83094
83399
  instanceVariantRowValueId: rootRow.instanceVariantRowValueId
@@ -85182,12 +85487,12 @@ function cloneClassValueGraph(receiver, expectedClassId, ctx) {
85182
85487
  }
85183
85488
  }
85184
85489
  if (isLiteralValueContent(sourceRow) && sourceRow.constructorArgs !== void 0 && sourceRow.constructorArgs !== null) {
85185
- const constructorArgs = { ...sourceRow.constructorArgs };
85490
+ const constructorArgs2 = { ...sourceRow.constructorArgs };
85186
85491
  for (const argument2 of ownedConstructorArgumentValues(sourceRow, ctx)) {
85187
85492
  if (argument2.parameterId === void 0) continue;
85188
85493
  const alreadyCloned = clonedBySourceId.get(argument2.id);
85189
85494
  if (alreadyCloned !== void 0) {
85190
- constructorArgs[argument2.parameterId] = alreadyCloned.id;
85495
+ constructorArgs2[argument2.parameterId] = alreadyCloned.id;
85191
85496
  continue;
85192
85497
  }
85193
85498
  const argumentRow = evalValueById(
@@ -85201,14 +85506,14 @@ function cloneClassValueGraph(receiver, expectedClassId, ctx) {
85201
85506
  continue;
85202
85507
  }
85203
85508
  if (constructorArgumentReferenceCount(argument2.id) !== 1) continue;
85204
- constructorArgs[argument2.parameterId] = cloneRow2(
85509
+ constructorArgs2[argument2.parameterId] = cloneRow2(
85205
85510
  argumentRow,
85206
85511
  null,
85207
85512
  void 0,
85208
85513
  argument2.typeInfo
85209
85514
  ).id;
85210
85515
  }
85211
- clone.constructorArgs = constructorArgs;
85516
+ clone.constructorArgs = constructorArgs2;
85212
85517
  }
85213
85518
  if (typeof clone.value === "object" && clone.value !== null && clone.value !== sourceRow.value) {
85214
85519
  const sourceRowValue = sourceRow.value;
@@ -86251,13 +86556,13 @@ function evaluateMemberInitializer(args) {
86251
86556
  args.createdValues.push(row);
86252
86557
  }
86253
86558
  if (rootRow === null) return { value: result.value, classId: null };
86254
- const constructorArgs = (typeof result.value === "object" && result.value !== null ? ctx.__constructedArgumentsByValue?.get(result.value) : void 0) ?? // An implicit `new()` records its empty args on the row rather than in
86559
+ const constructorArgs2 = (typeof result.value === "object" && result.value !== null ? ctx.__constructedArgumentsByValue?.get(result.value) : void 0) ?? // An implicit `new()` records its empty args on the row rather than in
86255
86560
  // the declared-constructor argument map; the pair must survive either
86256
86561
  // origin or the recipe reads as an unrecorded overload.
86257
86562
  rootRow.constructorArgs ?? void 0;
86258
86563
  const pinnedRootSchemaKeys = typeof result.value === "object" && result.value !== null ? ctx.__constructedFieldSchemaKeysByValue?.get(result.value) : void 0;
86259
86564
  const provenance = pickInstanceProvenance({
86260
- constructorArgs,
86565
+ constructorArgs: constructorArgs2,
86261
86566
  instanceConstructorId: rootRow.instanceConstructorId,
86262
86567
  instanceVariantId: rootRow.instanceVariantId,
86263
86568
  instanceVariantRowValueId: rootRow.instanceVariantRowValueId
@@ -91140,9 +91445,9 @@ function createTypedValueNormalizer(reader, document, childrenByContainerId, par
91140
91445
  };
91141
91446
  function carriesSemanticConstructorArguments(row) {
91142
91447
  if (!isLiteralValueContent(row)) return false;
91143
- const constructorArgs = row.constructorArgs;
91144
- if (constructorArgs === void 0 || constructorArgs === null) return false;
91145
- return typeof row.instanceConstructorId === "string" || Object.keys(constructorArgs).length > 0;
91448
+ const constructorArgs2 = row.constructorArgs;
91449
+ if (constructorArgs2 === void 0 || constructorArgs2 === null) return false;
91450
+ return typeof row.instanceConstructorId === "string" || Object.keys(constructorArgs2).length > 0;
91146
91451
  }
91147
91452
  const normalizeClassValue = (row, typeInfo, env) => {
91148
91453
  if (!isStringRecord6(row.value)) return normalizeLiteral(row.value);
@@ -91198,10 +91503,10 @@ function createTypedValueNormalizer(reader, document, childrenByContainerId, par
91198
91503
  }
91199
91504
  return result;
91200
91505
  };
91201
- function normalizeConstructorArgs(constructorArgs, root) {
91506
+ function normalizeConstructorArgs(constructorArgs2, root) {
91202
91507
  const parameterTypes = parameterTypesForRow(root);
91203
91508
  const result = /* @__PURE__ */ Object.create(null);
91204
- for (const [parameterId, value] of Object.entries(constructorArgs)) {
91509
+ for (const [parameterId, value] of Object.entries(constructorArgs2)) {
91205
91510
  const typeInfo = parameterTypes.get(parameterId);
91206
91511
  if (typeInfo === void 0) {
91207
91512
  result[parameterId] = normalizeLiteral(value);
@@ -95709,9 +96014,9 @@ function constructorOwners(document) {
95709
96014
  (document.constructors ?? []).map((record7) => record7.id)
95710
96015
  );
95711
96016
  for (const schemaClass2 of document.classes) {
95712
- for (const referenceId3 of collectCompilerReferenceIds(schemaClass2)) {
95713
- if (constructorIds.has(referenceId3)) {
95714
- owners.set(referenceId3, schemaClass2.id);
96017
+ for (const referenceId4 of collectCompilerReferenceIds(schemaClass2)) {
96018
+ if (constructorIds.has(referenceId4)) {
96019
+ owners.set(referenceId4, schemaClass2.id);
95715
96020
  }
95716
96021
  }
95717
96022
  }
@@ -99739,10 +100044,10 @@ function extractProjectSnapshotDerivedEdges(source) {
99739
100044
  })
99740
100045
  });
99741
100046
  }
99742
- const constructorArgs = record7 === null ? null : asRecord3(record7.constructorArgs);
100047
+ const constructorArgs2 = record7 === null ? null : asRecord3(record7.constructorArgs);
99743
100048
  return {
99744
100049
  edges: [...edges.values()].sort(compareEdges),
99745
- complete: constructorArgs === null || Object.keys(constructorArgs).length === 0 || source.constructorAggregateEdges !== void 0
100050
+ complete: constructorArgs2 === null || Object.keys(constructorArgs2).length === 0 || source.constructorAggregateEdges !== void 0
99746
100051
  };
99747
100052
  }
99748
100053
  function addStampBindingEdges(genericBindings, add) {
@@ -107029,10 +107334,10 @@ function attachPreparedConstructorAggregateEdges(prepared, document) {
107029
107334
  );
107030
107335
  if (valueChanges.length === 0) return;
107031
107336
  const needsGraph = valueChanges.some((change) => {
107032
- const constructorArgs = asRecord4(
107337
+ const constructorArgs2 = asRecord4(
107033
107338
  asRecord4(change.nextData)?.constructorArgs
107034
107339
  );
107035
- return constructorArgs !== null && Object.keys(constructorArgs).length > 0;
107340
+ return constructorArgs2 !== null && Object.keys(constructorArgs2).length > 0;
107036
107341
  });
107037
107342
  const changedValueRows = /* @__PURE__ */ new Map();
107038
107343
  if (needsGraph) {
@@ -109570,16 +109875,16 @@ function collectDelegateSweepRows(args) {
109570
109875
  }
109571
109876
  function inlineDelegateSweepRow(value) {
109572
109877
  if (!isMemberValue(value) || !isLiteralValueContent(value)) return null;
109573
- const constructorArgs = asRecord4(
109878
+ const constructorArgs2 = asRecord4(
109574
109879
  value.constructorArgs
109575
109880
  );
109576
- if (constructorArgs === null) return null;
109881
+ if (constructorArgs2 === null) return null;
109577
109882
  let sourceArgs = null;
109578
- for (const [key, argument2] of Object.entries(constructorArgs)) {
109883
+ for (const [key, argument2] of Object.entries(constructorArgs2)) {
109579
109884
  const closure = asRecord4(argument2);
109580
109885
  if (typeof closure?.code !== "string") continue;
109581
109886
  if (!("action" in closure)) continue;
109582
- sourceArgs ??= { ...constructorArgs };
109887
+ sourceArgs ??= { ...constructorArgs2 };
109583
109888
  sourceArgs[key] = { code: closure.code };
109584
109889
  }
109585
109890
  return sourceArgs === null ? null : { ...value, constructorArgs: sourceArgs };
@@ -109593,11 +109898,11 @@ function delegateValueRow(value) {
109593
109898
  }
109594
109899
  function inlineDelegateArgumentRow(value) {
109595
109900
  if (!isMemberValue(value) || !isLiteralValueContent(value)) return null;
109596
- const constructorArgs = asRecord4(
109901
+ const constructorArgs2 = asRecord4(
109597
109902
  value.constructorArgs
109598
109903
  );
109599
- if (constructorArgs === null) return null;
109600
- for (const argument2 of Object.values(constructorArgs)) {
109904
+ if (constructorArgs2 === null) return null;
109905
+ for (const argument2 of Object.values(constructorArgs2)) {
109601
109906
  if (isUncompiledInlineDelegateArgument(argument2)) {
109602
109907
  return value;
109603
109908
  }
@@ -109612,8 +109917,8 @@ function isUncompiledInlineDelegateArgument(argument2) {
109612
109917
  }
109613
109918
  function compileInlineDelegateConstructorArguments(args) {
109614
109919
  const { document, row, ownerMember, rootOwner } = args;
109615
- const constructorArgs = asRecord4(row.constructorArgs);
109616
- if (constructorArgs === null) {
109920
+ const constructorArgs2 = asRecord4(row.constructorArgs);
109921
+ if (constructorArgs2 === null) {
109617
109922
  throw new Error(
109618
109923
  `Value "${row.id}" was collected for inline delegate compilation without constructor arguments.`
109619
109924
  );
@@ -109656,8 +109961,8 @@ function compileInlineDelegateConstructorArguments(args) {
109656
109961
  document.classes
109657
109962
  );
109658
109963
  const thisClass = findSchemaPlacement(rootOwner?.id ?? "", document.classes)?.ownerClass ?? null;
109659
- const compiled = { ...constructorArgs };
109660
- for (const [argumentKey, argument2] of Object.entries(constructorArgs)) {
109964
+ const compiled = { ...constructorArgs2 };
109965
+ for (const [argumentKey, argument2] of Object.entries(constructorArgs2)) {
109661
109966
  if (!isUncompiledInlineDelegateArgument(argument2)) continue;
109662
109967
  const match = /^__arg_(\d+)__$/.exec(argumentKey);
109663
109968
  if (match === null) {
@@ -115553,12 +115858,7 @@ function schemaKeyToMemberName(schemaKey) {
115553
115858
  return generatedCSharpMemberNameForSchemaKey(schemaKey);
115554
115859
  }
115555
115860
  function toCSharpTypeName(value, fallback) {
115556
- const parts = value.match(/[A-Za-z0-9]+/g) ?? [];
115557
- const joined = parts.map((part) => `${part[0]?.toUpperCase() ?? ""}${part.slice(1)}`).join("");
115558
- const candidate = joined.length > 0 ? joined : fallback;
115559
- const safe = /^[0-9]/.test(candidate) ? `_${candidate}` : candidate;
115560
- if (isCSharpReservedKeyword(safe)) return `${safe}Type`;
115561
- return safe;
115861
+ return generatedCSharpTypeName(value, fallback);
115562
115862
  }
115563
115863
  var init_csharp_identifiers = __esm({
115564
115864
  "../src/models/exports/unity-codegen/csharp-identifiers.ts"() {
@@ -118485,7 +118785,7 @@ function collectProjectDocumentTileGridReferenceBlockers(args) {
118485
118785
  ownerValue: gridValue,
118486
118786
  keyCandidates: root.keyCandidates
118487
118787
  });
118488
- for (const referenceId3 of referenceIds) {
118788
+ for (const referenceId4 of referenceIds) {
118489
118789
  pushWorldReferenceDeleteBlockers({
118490
118790
  graph: args.graph,
118491
118791
  deletedClassIds: args.deletedClassIds,
@@ -118494,7 +118794,7 @@ function collectProjectDocumentTileGridReferenceBlockers(args) {
118494
118794
  gridValueId: gridValue.id,
118495
118795
  location: `${root.locationLabel} on grid "${gridValue.id}"`,
118496
118796
  referenceKind: root.referenceKind,
118497
- referencedValueId: referenceId3
118797
+ referencedValueId: referenceId4
118498
118798
  });
118499
118799
  }
118500
118800
  }
@@ -123177,7 +123477,7 @@ function lowerReferenceValue(expression) {
123177
123477
  if (target?.kind === "litString") return target.value;
123178
123478
  const path = target === void 0 ? null : dottedPath(target);
123179
123479
  if (path === null || !path.startsWith("root.")) return null;
123180
- return referenceId(`Reference(${path})`);
123480
+ return referenceId2(`Reference(${path})`);
123181
123481
  }
123182
123482
  function dottedPath(expression) {
123183
123483
  const parts = [];
@@ -123662,6 +123962,28 @@ function lowerDialogueProjectSourcesV4(state, analysis, options = {}) {
123662
123962
  ).map((global) => dialogueGroupIds.get(global.name))
123663
123963
  );
123664
123964
  const priorityGroupsById = recordsById(state, "priority-group");
123965
+ const groupPaths = new DialogueGroupPaths(
123966
+ dialogueGroups.map((global) => {
123967
+ const id2 = dialogueGroupIds.get(global.name);
123968
+ const data = baseData2(state, "dialogue-group", id2);
123969
+ return {
123970
+ id: id2,
123971
+ symbol: global.name,
123972
+ name: typeof data.name === "string" ? data.name : global.name,
123973
+ parentId: nullableString4(data.parentDialogueGroupId),
123974
+ priorityGroupId: nullableString4(data.priorityGroupIdOverride)
123975
+ };
123976
+ }),
123977
+ [...priorityGroupsById].map(
123978
+ ([id2, data]) => [
123979
+ id2,
123980
+ (Array.isArray(data.options) ? data.options : []).flatMap(
123981
+ (option) => isObjectRecord2(option) && typeof option.id === "string" && typeof option.name === "string" ? [{ id: option.id, name: option.name }] : []
123982
+ )
123983
+ ]
123984
+ ),
123985
+ defaultPriorityGroupId(state)
123986
+ );
123665
123987
  const sourceSchema = new SourceSchemaIndex(analysis);
123666
123988
  const valueSymbols = indexValueSymbols(state, analysis);
123667
123989
  const nodesByDialogueId = dialogueNodesByDialogueId(state);
@@ -123687,6 +124009,7 @@ function lowerDialogueProjectSourcesV4(state, analysis, options = {}) {
123687
124009
  dialogue.functions.map((fn) => [fn.name, fn])
123688
124010
  );
123689
124011
  const context = {
124012
+ groupPaths,
123690
124013
  sourceCapture,
123691
124014
  referenceTypes,
123692
124015
  state,
@@ -123742,7 +124065,11 @@ function lowerDialogueProjectSourcesV4(state, analysis, options = {}) {
123742
124065
  ...baseDialogue,
123743
124066
  id: dialogueId,
123744
124067
  sourceName: dialogue.name,
123745
- name: literalString(settings.get("name")) ?? stringOr(baseDialogue.name, dialogue.name),
124068
+ name: authoredDisplayName(
124069
+ settings.get("name"),
124070
+ dialogue.name,
124071
+ "Dialogue"
124072
+ ) ?? "",
123746
124073
  description,
123747
124074
  settings: {
123748
124075
  ...isObjectRecord2(baseDialogue.settings) ? baseDialogue.settings : {},
@@ -123793,6 +124120,9 @@ function dialogueSourceError(error, source) {
123793
124120
  );
123794
124121
  }
123795
124122
  function lowerGraphMember(context, member, index) {
124123
+ const graphType = member.graphType;
124124
+ if (graphType !== "Trigger" && graphType !== "Text" && graphType !== "Actions" && graphType !== "Conditions")
124125
+ throw new Error(`Unsupported NeoFlow graph type ${graphType}.`);
123796
124126
  const id2 = sourceId2(member, "dialogue-node", member.name);
123797
124127
  const base = context.nodesById.get(id2) ?? {};
123798
124128
  const linkedValues = lowerNodeBindings(
@@ -123804,7 +124134,7 @@ function lowerGraphMember(context, member, index) {
123804
124134
  linkedValues,
123805
124135
  deriveLogicLinks(context, member)
123806
124136
  );
123807
- if (member.graphType === "Trigger") {
124137
+ if (graphType === "Trigger") {
123808
124138
  effectiveLinkedValues = effectiveLinkedValues.map((link) => {
123809
124139
  const inherited = context.dialogueLinks.find(
123810
124140
  (candidate) => candidate.valueId === link.valueId
@@ -123818,7 +124148,11 @@ function lowerGraphMember(context, member, index) {
123818
124148
  id: id2,
123819
124149
  dialogueId: context.dialogueId,
123820
124150
  sourceName: member.name,
123821
- name: constructorString(member.arguments, "name") ?? nullableString4(base.name),
124151
+ name: graphType === "Trigger" ? nullableString4(base.name) : authoredDisplayName(
124152
+ constructorExpression(member.arguments, "name") ?? void 0,
124153
+ member.name,
124154
+ graphType
124155
+ ),
123822
124156
  layout: isObjectRecord2(base.layout) ? base.layout : { x: 0, y: index * 200, width: 320, height: 160, isOpen: true },
123823
124157
  linkedValues: effectiveLinkedValues,
123824
124158
  primaryLinkedValueId: primaryValueId(member.content?.bindings ?? [], effectiveLinkedValues) ?? nullableString4(base.primaryLinkedValueId)
@@ -123828,7 +124162,7 @@ function lowerGraphMember(context, member, index) {
123828
124162
  member.destination,
123829
124163
  nullableString4(base.toNodeId)
123830
124164
  );
123831
- if (member.graphType === "Trigger") {
124165
+ if (graphType === "Trigger") {
123832
124166
  return [
123833
124167
  reconstructed2(
123834
124168
  "dialogue-node",
@@ -123853,10 +124187,10 @@ function lowerGraphMember(context, member, index) {
123853
124187
  )
123854
124188
  ];
123855
124189
  }
123856
- if (member.graphType === "Text") {
124190
+ if (graphType === "Text") {
123857
124191
  return lowerTextNode(context, member, id2, base, common, destination);
123858
124192
  }
123859
- if (member.graphType === "Actions") {
124193
+ if (graphType === "Actions") {
123860
124194
  return [
123861
124195
  reconstructed2(
123862
124196
  "dialogue-node",
@@ -123877,22 +124211,19 @@ function lowerGraphMember(context, member, index) {
123877
124211
  )
123878
124212
  ];
123879
124213
  }
123880
- if (member.graphType === "Conditions") {
123881
- return [
123882
- reconstructed2(
123883
- "dialogue-node",
123884
- id2,
123885
- {
123886
- ...common,
123887
- type: 3,
123888
- outcomes: lowerOutcomes(context, member.content, id2, base.outcomes),
123889
- toNodeId: void 0
123890
- },
123891
- member
123892
- )
123893
- ];
123894
- }
123895
- throw new Error(`Unsupported NeoFlow graph type ${member.graphType}.`);
124214
+ return [
124215
+ reconstructed2(
124216
+ "dialogue-node",
124217
+ id2,
124218
+ {
124219
+ ...common,
124220
+ type: 3,
124221
+ outcomes: lowerOutcomes(context, member.content, id2, base.outcomes),
124222
+ toNodeId: void 0
124223
+ },
124224
+ member
124225
+ )
124226
+ ];
123896
124227
  }
123897
124228
  function lowerTextNode(context, member, id2, base, common, destination) {
123898
124229
  const prose = requireProse(member.content, `Text ${member.name}`);
@@ -123952,7 +124283,11 @@ function lowerTextNode(context, member, id2, base, common, destination) {
123952
124283
  ...optionBase,
123953
124284
  id: optionId,
123954
124285
  sourceName: child2.name,
123955
- name: constructorString(child2.arguments, "name") ?? nullableString4(optionBase.name),
124286
+ name: authoredDisplayName(
124287
+ constructorExpression(child2.arguments, "name") ?? void 0,
124288
+ child2.name,
124289
+ "Option"
124290
+ ),
123956
124291
  text: optionText.textId,
123957
124292
  variables: optionText.variables,
123958
124293
  toNodeId: requiredDestination(
@@ -124103,7 +124438,11 @@ function lowerOutcomes(context, content, nodeId, rawBaseOutcomes) {
124103
124438
  ...base,
124104
124439
  id: id2,
124105
124440
  sourceName: child2.name,
124106
- name: constructorString(child2.arguments, "name") ?? child2.name,
124441
+ name: authoredDisplayName(
124442
+ constructorExpression(child2.arguments, "name") ?? void 0,
124443
+ child2.name,
124444
+ "Outcome"
124445
+ ) ?? "",
124107
124446
  conditions: lowerConditionUses(
124108
124447
  context,
124109
124448
  constructorExpression(child2.arguments, "when"),
@@ -124966,30 +125305,30 @@ function lowerDialogueGroupSettings(context, member, base) {
124966
125305
  const expression = constructorExpression(member.arguments, "group");
124967
125306
  if (expression === null) return null;
124968
125307
  const old = isObjectRecord2(base.dialogueGroupSettings) ? base.dialogueGroupSettings : {};
124969
- const referencedGroupId = referenceId2(expression, "DialogueGroup");
125308
+ const referencedGroupId = referenceId3(expression, "DialogueGroup");
124970
125309
  if (referencedGroupId !== null) {
124971
- if (![...context.dialogueGroupIds.values()].includes(referencedGroupId)) {
125310
+ if (!context.groupPaths.byId.has(referencedGroupId)) {
124972
125311
  throw dialogueSourceError(
124973
125312
  `Unknown dialogue group ${referencedGroupId}.`,
124974
125313
  groupSource
124975
125314
  );
124976
125315
  }
124977
- const group2 = baseData2(context.state, "dialogue-group", referencedGroupId);
124978
- const priorityGroupId2 = nullableString4(group2.priorityGroupIdOverride) ?? defaultPriorityGroupId(context.state);
124979
- const priority2 = priorityGroupId2 ? context.priorityGroupsById.get(priorityGroupId2) : void 0;
124980
- const options2 = Array.isArray(priority2?.options) ? priority2.options : [];
125316
+ const group = baseData2(context.state, "dialogue-group", referencedGroupId);
125317
+ const priorityGroupId = nullableString4(group.priorityGroupIdOverride) ?? defaultPriorityGroupId(context.state);
125318
+ const priority = priorityGroupId ? context.priorityGroupsById.get(priorityGroupId) : void 0;
125319
+ const options = Array.isArray(priority?.options) ? priority.options : [];
124981
125320
  const priorityExpression = constructorExpression(
124982
125321
  member.arguments,
124983
125322
  "priority"
124984
125323
  );
124985
- const priorityOptionId = priorityExpression === null ? null : referenceId2(priorityExpression, "PriorityOption");
125324
+ const priorityOptionId = priorityExpression === null ? null : referenceId3(priorityExpression, "PriorityOption");
124986
125325
  if (priorityExpression !== null && priorityOptionId === null) {
124987
125326
  throw dialogueSourceError(
124988
125327
  'Trigger priority must be authored as Reference<PriorityOption>(id: "...").',
124989
125328
  prioritySource
124990
125329
  );
124991
125330
  }
124992
- if (priorityOptionId !== null && !options2.some(
125331
+ if (priorityOptionId !== null && !options.some(
124993
125332
  (candidate) => isObjectRecord2(candidate) && candidate.id === priorityOptionId
124994
125333
  )) {
124995
125334
  throw dialogueSourceError(
@@ -125008,39 +125347,22 @@ function lowerDialogueGroupSettings(context, member, base) {
125008
125347
  }
125009
125348
  };
125010
125349
  }
125011
- const [groupName, optionName] = expression.split(".");
125012
- if (!groupName || !optionName) {
125350
+ const groupPath = expression.split(/\s*\.\s*/u);
125351
+ const resolved = context.groupPaths.resolve(groupPath);
125352
+ if (!resolved)
125013
125353
  throw dialogueSourceError(
125014
- `Trigger group must be authored as DialogueGroup.PriorityOption.`,
125354
+ context.groupPaths.failure(groupPath),
125015
125355
  groupSource
125016
125356
  );
125017
- }
125018
- const groupId = context.dialogueGroupIds.get(groupName);
125019
- if (!groupId)
125020
- throw dialogueSourceError(
125021
- `Unknown dialogue group ${groupName}.`,
125022
- groupSource
125023
- );
125024
- const group = baseData2(context.state, "dialogue-group", groupId);
125025
- const priorityGroupId = nullableString4(group.priorityGroupIdOverride) ?? defaultPriorityGroupId(context.state);
125026
- const priority = priorityGroupId ? context.priorityGroupsById.get(priorityGroupId) : void 0;
125027
- const options = Array.isArray(priority?.options) ? priority.options : [];
125028
- const option = options.find(
125029
- (candidate) => isObjectRecord2(candidate) && candidate.name === optionName
125030
- );
125031
- if (!isObjectRecord2(option) || typeof option.id !== "string") {
125032
- throw dialogueSourceError(
125033
- `Unknown priority option ${expression}.`,
125034
- groupSource
125035
- );
125036
- }
125357
+ const groupId = resolved.group.id;
125358
+ const option = resolved.option;
125037
125359
  return {
125038
125360
  ...old,
125039
125361
  ...lookupValueSettings(context, groupId, old),
125040
125362
  dialogueGroupId: groupId,
125041
125363
  priority: {
125042
125364
  ...isObjectRecord2(old.priority) ? old.priority : {},
125043
- priorityOptionId: option.id,
125365
+ priorityOptionId: option?.id ?? null,
125044
125366
  relativeOrder: constructorNumber(member.arguments, "order")
125045
125367
  }
125046
125368
  };
@@ -125071,7 +125393,7 @@ function lookupValueSettings(context, groupId, old) {
125071
125393
  }
125072
125394
  return old.lookupValueId == null ? {} : { lookupValueId: null };
125073
125395
  }
125074
- function referenceId2(expression, typeName) {
125396
+ function referenceId3(expression, typeName) {
125075
125397
  const pattern = new RegExp(
125076
125398
  `^Reference<${typeName}>\\(id:\\s*("(?:[^"\\\\]|\\\\.)*")\\)$`,
125077
125399
  "u"
@@ -125269,8 +125591,8 @@ function splitTopLevel(value) {
125269
125591
  function constructorExpression(args, name) {
125270
125592
  return args.find((argument2) => argument2.name === name)?.expression ?? null;
125271
125593
  }
125272
- function constructorString(args, name) {
125273
- return literalString(constructorExpression(args, name) ?? void 0);
125594
+ function authoredDisplayName(expression, symbol, kind) {
125595
+ return expression === void 0 ? inferredDialogueDisplayName(symbol, kind) : literalString(expression);
125274
125596
  }
125275
125597
  function constructorBoolean(args, name) {
125276
125598
  return literalBoolean(constructorExpression(args, name) ?? void 0);
@@ -125594,6 +125916,8 @@ var SourceSchemaIndex;
125594
125916
  var init_dialogue_lower = __esm({
125595
125917
  "src/project-source/dialogue-lower.ts"() {
125596
125918
  "use strict";
125919
+ init_dialogue_source_names();
125920
+ init_dialogue_group_paths();
125597
125921
  init_local_values();
125598
125922
  init_key_reference_spelling();
125599
125923
  init_reference_target_types();
@@ -126648,9 +126972,9 @@ function storedConstructionEmitters(state, manifest) {
126648
126972
  if (record7.recordKind !== "value") continue;
126649
126973
  if (!isObjectRecord2(record7.data)) continue;
126650
126974
  if (!isObjectRecord2(record7.data.value)) continue;
126651
- const constructorArgs = record7.data.constructorArgs;
126975
+ const constructorArgs2 = record7.data.constructorArgs;
126652
126976
  const hasInstanceProvenance = isVirtualInstanceRootShape(record7.data);
126653
- if (constructorArgs !== void 0 && constructorArgs !== null && !hasInstanceProvenance) {
126977
+ if (constructorArgs2 !== void 0 && constructorArgs2 !== null && !hasInstanceProvenance) {
126654
126978
  continue;
126655
126979
  }
126656
126980
  candidateRoots.add(record7.recordId);
@@ -134031,12 +134355,12 @@ function staticValueSeedRow(value, loweredMemberId) {
134031
134355
  };
134032
134356
  }
134033
134357
  function seedRowInstanceProvenance(value) {
134034
- const { constructorArgs, ...stamps } = pickInstanceProvenance(
134358
+ const { constructorArgs: constructorArgs2, ...stamps } = pickInstanceProvenance(
134035
134359
  readInstanceProvenance(value)
134036
134360
  );
134037
134361
  return {
134038
134362
  ...stamps,
134039
- ...constructorArgs === void 0 || constructorArgs === null ? {} : { constructorArgs }
134363
+ ...constructorArgs2 === void 0 || constructorArgs2 === null ? {} : { constructorArgs: constructorArgs2 }
134040
134364
  };
134041
134365
  }
134042
134366
  function readInstanceProvenance(value) {
@@ -134045,10 +134369,10 @@ function readInstanceProvenance(value) {
134045
134369
  if (field === null) return null;
134046
134370
  return typeof field === "string" ? field : void 0;
134047
134371
  };
134048
- const constructorArgs = value.constructorArgs;
134372
+ const constructorArgs2 = value.constructorArgs;
134049
134373
  return {
134050
- ...constructorArgs === void 0 ? {} : {
134051
- constructorArgs: isObjectRecord2(constructorArgs) ? constructorArgs : null
134374
+ ...constructorArgs2 === void 0 ? {} : {
134375
+ constructorArgs: isObjectRecord2(constructorArgs2) ? constructorArgs2 : null
134052
134376
  },
134053
134377
  instanceConstructorId: nullableString5(value.instanceConstructorId),
134054
134378
  instanceVariantId: nullableString5(value.instanceVariantId),
@@ -134192,7 +134516,7 @@ function lowerSeedRow(context, member, sourceExpression, source, valueId, path,
134192
134516
  let value;
134193
134517
  let classId = null;
134194
134518
  let genericBindings;
134195
- let constructorArgs;
134519
+ let constructorArgs2;
134196
134520
  let instanceConstructorId;
134197
134521
  if (expression.kind === "litNull") {
134198
134522
  if (resolvedMember.required) {
@@ -134360,7 +134684,7 @@ function lowerSeedRow(context, member, sourceExpression, source, valueId, path,
134360
134684
  }
134361
134685
  if (!partial) {
134362
134686
  instanceConstructorId = effectiveClass.requiredConstructorId ?? null;
134363
- constructorArgs = recordedConstructorArgs;
134687
+ constructorArgs2 = recordedConstructorArgs;
134364
134688
  }
134365
134689
  value = body;
134366
134690
  } else if (resolvedMember.kind === "list") {
@@ -134477,7 +134801,7 @@ function lowerSeedRow(context, member, sourceExpression, source, valueId, path,
134477
134801
  classId,
134478
134802
  ...containerId === void 0 ? {} : { containerId },
134479
134803
  ...genericBindings === void 0 ? {} : { genericBindings },
134480
- ...constructorArgs === void 0 ? {} : { constructorArgs },
134804
+ ...constructorArgs2 === void 0 ? {} : { constructorArgs: constructorArgs2 },
134481
134805
  ...instanceConstructorId === void 0 ? {} : { instanceConstructorId }
134482
134806
  };
134483
134807
  registerSeedRow(context, rows, row, source, sourceExpression);
@@ -134605,7 +134929,7 @@ function lowerStructuralConstructionRow(context, member, expression, source, val
134605
134929
  const settledBy = structuralMemberByParameterName(context, effectiveClass);
134606
134930
  const slices = constructorArgumentValueSlices(authoredSlice);
134607
134931
  const value = {};
134608
- const constructorArgs = {};
134932
+ const constructorArgs2 = {};
134609
134933
  expression.args.forEach((argument2, index) => {
134610
134934
  const name = expression.argumentNames?.[index] ?? parameters[index] ?? null;
134611
134935
  if (name === null) {
@@ -134643,7 +134967,7 @@ function lowerStructuralConstructionRow(context, member, expression, source, val
134643
134967
  slices[index]
134644
134968
  );
134645
134969
  if (structuralArgumentIsAggregate(context, childMember, environment)) {
134646
- constructorArgs[`__arg_${parameterIndex}__`] = childId;
134970
+ constructorArgs2[`__arg_${parameterIndex}__`] = childId;
134647
134971
  } else {
134648
134972
  const leaf = rows.get(childId);
134649
134973
  if (leaf?.nodeType !== "literal") {
@@ -134658,7 +134982,7 @@ function lowerStructuralConstructionRow(context, member, expression, source, val
134658
134982
  leaf,
134659
134983
  localizedTexts
134660
134984
  });
134661
- constructorArgs[`__arg_${parameterIndex}__`] = inline;
134985
+ constructorArgs2[`__arg_${parameterIndex}__`] = inline;
134662
134986
  deleteSeedRow(context, rows, childId);
134663
134987
  }
134664
134988
  });
@@ -134699,7 +135023,7 @@ function lowerStructuralConstructionRow(context, member, expression, source, val
134699
135023
  memberId: member.id,
134700
135024
  value,
134701
135025
  classId: effectiveClass.id,
134702
- constructorArgs,
135026
+ constructorArgs: constructorArgs2,
134703
135027
  // Provenance is stamped explicitly on every construction this lowerer
134704
135028
  // writes. `constructorArgs` alone is already a complete recipe (see
134705
135029
  // `carriesCompleteConstructionRecipe`), so the stamp adds no meaning — it
@@ -138220,14 +138544,14 @@ function firstRequiredConstructorParameterKey(context, classId) {
138220
138544
  return null;
138221
138545
  }
138222
138546
  function storedConstructorCallSource(context, schemaClass2, value, className, environment, visited, targetTyped, cloneAggregateArguments = false) {
138223
- const constructorArgs = value.constructorArgs;
138224
- if (!isObjectRecord2(constructorArgs)) return null;
138547
+ const constructorArgs2 = value.constructorArgs;
138548
+ if (!isObjectRecord2(constructorArgs2)) return null;
138225
138549
  const manifestClass = context.manifestClasses.get(
138226
138550
  stringField3(schemaClass2, "id")
138227
138551
  );
138228
138552
  if (manifestClass === void 0) return null;
138229
138553
  if (value.instanceConstructorId === null) {
138230
- if (Object.keys(constructorArgs).length !== 0) {
138554
+ if (Object.keys(constructorArgs2).length !== 0) {
138231
138555
  throw new Error(
138232
138556
  `Stored implicit construction for ${className} carries constructor arguments.`
138233
138557
  );
@@ -138251,7 +138575,7 @@ function storedConstructorCallSource(context, schemaClass2, value, className, en
138251
138575
  );
138252
138576
  const argumentsValue = constructor2.arguments.flatMap((argument2, index) => {
138253
138577
  const key = `__arg_${index}__`;
138254
- if (!(key in constructorArgs)) {
138578
+ if (!(key in constructorArgs2)) {
138255
138579
  if (argument2.default !== null || argument2.type.nullable) return [];
138256
138580
  throw new Error(
138257
138581
  `Stored construction on value row "${stringOrNull2(value.id) ?? "<unknown>"}" of class "${stringOrNull2(schemaClass2.name) ?? "<unnamed>"}" (${stringOrNull2(schemaClass2.id) ?? "<no id>"}) is missing evaluated argument ${key} for required parameter "${argument2.name}".`
@@ -138261,14 +138585,14 @@ function storedConstructorCallSource(context, schemaClass2, value, className, en
138261
138585
  context,
138262
138586
  schemaClass2,
138263
138587
  value,
138264
- constructorArgs[key],
138588
+ constructorArgs2[key],
138265
138589
  argument2.name
138266
138590
  );
138267
138591
  return [
138268
138592
  `${argument2.name}: ${storedConstructorArgumentSource(
138269
138593
  context,
138270
138594
  argument2.type,
138271
- constructorArgs[key],
138595
+ constructorArgs2[key],
138272
138596
  environment,
138273
138597
  visited,
138274
138598
  cloneAggregateArguments,
@@ -138285,7 +138609,7 @@ function storedConstructorCallSource(context, schemaClass2, value, className, en
138285
138609
  constructorArgumentBodySchemaKey(
138286
138610
  context,
138287
138611
  value,
138288
- constructorArgs[key]
138612
+ constructorArgs2[key]
138289
138613
  ) !== void 0
138290
138614
  )}`
138291
138615
  ];
@@ -139988,13 +140312,19 @@ function emitProjectDocumentSourcesV4(records2, options = {}) {
139988
140312
  recordKeys: emitted.recordKeys
139989
140313
  };
139990
140314
  }).toArray();
140315
+ const dialogueGroupSymbols = emittedDialogueGroupSymbols(
140316
+ records2,
140317
+ options.dialogueGroupSymbols,
140318
+ options.localValues?.map((value) => value.name)
140319
+ );
139991
140320
  const supplementalFiles = emitSupplementalProjectSourcesV4(
139992
140321
  records2,
139993
140322
  options.binaryPaths,
139994
140323
  {
139995
140324
  manifest,
139996
140325
  collectionValuePaths: indexes3.rootPathsByValueId,
139997
- localValues: options.localValues
140326
+ localValues: options.localValues,
140327
+ dialogueGroupSymbols
139998
140328
  }
139999
140329
  );
140000
140330
  const materializedConstructors = new Map(
@@ -140019,7 +140349,10 @@ function emitProjectDocumentSourcesV4(records2, options = {}) {
140019
140349
  localValues,
140020
140350
  valueOptions
140021
140351
  );
140022
- const dialogueFiles = emitDialogueProjectSourcesV4(records2);
140352
+ const dialogueFiles = emitDialogueProjectSourcesV4(
140353
+ records2,
140354
+ dialogueGroupSymbols
140355
+ );
140023
140356
  const localFiles = localValues.files();
140024
140357
  const groupingPaths = new Map(options.recordFiles);
140025
140358
  for (const file of localFiles) {
@@ -140113,6 +140446,7 @@ var PROJECT_SOURCE_ANALYSIS_V4_CACHE_PATH, SCHEMA_RECORD_KINDS2;
140113
140446
  var init_project_documents = __esm({
140114
140447
  "src/project-source/project-documents.ts"() {
140115
140448
  "use strict";
140449
+ init_dialogue_group_symbols();
140116
140450
  init_local_values();
140117
140451
  init_project_source_manifest();
140118
140452
  init_language_spec();
@@ -145481,6 +145815,8 @@ function projectCompletions(analysis, document, position) {
145481
145815
  items: [...script.items, variantScopeInBody]
145482
145816
  };
145483
145817
  }
145818
+ const groupMembers = dialogueGroupCompletions(analysis, document, position);
145819
+ if (groupMembers) return { isIncomplete: false, items: groupMembers };
145484
145820
  const annotations = projectAnnotationCompletions(
145485
145821
  analysis,
145486
145822
  document,
@@ -147209,6 +147545,15 @@ function indexedProjectSymbolAt(analysis, document, position, index) {
147209
147545
  }
147210
147546
  const exact = symbolsDeclaredAt(index, document.uri, token.range);
147211
147547
  if (exact.length === 1) return { token, symbol: exact[0] };
147548
+ if (!body) {
147549
+ const path = dialoguePathTokens(sourceTokens, tokenIndex);
147550
+ if (path.length > 0 && isDialogueGroupArgument(sourceTokens, tokenIndex - 2 * (path.length - 1))) {
147551
+ const catalog = sourceDialogueGroups(analysis);
147552
+ const resolved = catalog.paths.resolve(path);
147553
+ const symbol = resolved && catalog.symbols.get(resolved.option?.id ?? resolved.group.id);
147554
+ if (symbol) return { token, symbol };
147555
+ }
147556
+ }
147212
147557
  const candidates = index.byName.get(token.text) ?? [];
147213
147558
  if (candidates.length === 0) return null;
147214
147559
  const source = analysis.documents.get(document.uri);
@@ -148036,10 +148381,61 @@ function projectFunctionsNamed(analysis, name) {
148036
148381
  }
148037
148382
  return byName.get(name) ?? [];
148038
148383
  }
148384
+ function dialoguePathTokens(tokens, end) {
148385
+ const path = [];
148386
+ for (let i2 = end; i2 >= 0 && isProjectNameToken(tokens[i2]); i2 -= 2) {
148387
+ path.push(tokens[i2].text);
148388
+ if (tokens[i2 - 1]?.text !== ".") break;
148389
+ }
148390
+ return path.reverse();
148391
+ }
148392
+ function dialogueGroupCompletions(analysis, document, position) {
148393
+ const tokens = projectTokens(document);
148394
+ let index = projectTokenIndexAt(document, position);
148395
+ const token = tokens[index];
148396
+ if (isProjectNameToken(token) && positionCompare(token.range.start, position) < 0)
148397
+ index--;
148398
+ if (tokens[index]?.text !== ".") index--;
148399
+ if (tokens[index]?.text !== ".") return null;
148400
+ const path = dialoguePathTokens(tokens, index - 1);
148401
+ if (!isDialogueGroupArgument(tokens, index - 2 * path.length + 1))
148402
+ return null;
148403
+ const catalog = sourceDialogueGroups(analysis);
148404
+ const group = catalog.paths.group(path);
148405
+ if (!group) return null;
148406
+ const items = [];
148407
+ const children = catalog.paths.childGroups(group);
148408
+ const priorities = catalog.paths.priorityOptions(group);
148409
+ for (const [name, child2] of children) {
148410
+ if (!child2 || priorities.has(name)) continue;
148411
+ items.push({
148412
+ label: name,
148413
+ kind: "variable",
148414
+ detail: "DialogueGroup",
148415
+ insertText: name,
148416
+ symbolId: child2.id
148417
+ });
148418
+ }
148419
+ for (const [name, option] of priorities) {
148420
+ if (children.get(name)) continue;
148421
+ items.push({
148422
+ label: name,
148423
+ kind: "enumMember",
148424
+ detail: "PriorityOption",
148425
+ insertText: name,
148426
+ symbolId: option.id
148427
+ });
148428
+ }
148429
+ return items;
148430
+ }
148431
+ function isDialogueGroupArgument(tokens, pathStart) {
148432
+ return tokens[pathStart - 1]?.text === ":" && tokens[pathStart - 2]?.text === "group";
148433
+ }
148039
148434
  var PROJECT_BODIES, PROJECT_BODY_INDEX_CACHE, PROJECT_BODY_SNAPSHOT_CACHE, SOURCE_TYPES, CONSTRUCTION_INDEX_CACHE, VARIANT_SCOPE_INDEX_CACHE, PROJECT_SYMBOL_INDEX_CACHE, INITIALIZER_ROOTS, CONSTRUCTION_SITE_CACHE, DECLARATION_FIELDS, PROJECT_TYPE_DECLARATIONS, PROJECT_FUNCTIONS;
148040
148435
  var init_project_source_language_features = __esm({
148041
148436
  "../packages/neoscript-language/src/project-source-language-features.ts"() {
148042
148437
  "use strict";
148438
+ init_project_source_dialogue_groups();
148043
148439
  init_project_listener_annotations();
148044
148440
  init_strict_resolver();
148045
148441
  init_type_substitution();
@@ -149917,7 +150313,7 @@ function workspaceForSourceLayoutV4(workspace, document) {
149917
150313
  }
149918
150314
  return { ...workspace, state: { ...workspace.state, records: records2 } };
149919
150315
  }
149920
- function readWorkspaceRecordFilesV4(workspace) {
150316
+ function readWorkspaceRecordFilesV4(workspace, dialogueGroupSymbols) {
149921
150317
  const paths = /* @__PURE__ */ new Map();
149922
150318
  const keysById = /* @__PURE__ */ new Map();
149923
150319
  for (const [key, record7] of Object.entries(workspace.state.records)) {
@@ -149930,6 +150326,20 @@ function readWorkspaceRecordFilesV4(workspace) {
149930
150326
  for (const absolute of listProjectSourceFilesV4(workspace.root)) {
149931
150327
  const path = relative4(workspace.root, absolute).split(sep4).join("/");
149932
150328
  const content = readFileSync10(absolute, "utf8");
150329
+ if (dialogueGroupSymbols && /\bDialogueGroup\b/u.test(content) && neoProjectSourceKind(path, content) === "definition") {
150330
+ const source = parseNeoProjectSource(content, "definition", path);
150331
+ for (const declaration of source.declarations) {
150332
+ if (declaration.kind !== "global" || declaration.type.name !== "DialogueGroup")
150333
+ continue;
150334
+ const annotation2 = declaration.annotations.find(
150335
+ (item) => item.name === "id"
150336
+ );
150337
+ const argument2 = annotation2?.arguments[0];
150338
+ const id2 = argument2 && lex(argument2.text).tokens[0]?.value;
150339
+ if (typeof id2 === "string")
150340
+ dialogueGroupSymbols.set(id2, declaration.name);
150341
+ }
150342
+ }
149933
150343
  const tokens = lex(content).roots.filter(
149934
150344
  (token) => token.kind !== "comment"
149935
150345
  );
@@ -155550,9 +155960,9 @@ function pruneUnreachableAnimationValues(args) {
155550
155960
  }
155551
155961
  function visitConstructionArgumentIds(value, visit) {
155552
155962
  if (!isLiteralValueContent(value)) return;
155553
- const constructorArgs = value.constructorArgs;
155554
- if (constructorArgs === void 0) return;
155555
- if (constructorArgs === null) return;
155963
+ const constructorArgs2 = value.constructorArgs;
155964
+ if (constructorArgs2 === void 0) return;
155965
+ if (constructorArgs2 === null) return;
155556
155966
  const scan = (payload) => {
155557
155967
  if (typeof payload === "string") {
155558
155968
  visit(payload);
@@ -155561,7 +155971,7 @@ function visitConstructionArgumentIds(value, visit) {
155561
155971
  if (payload === null || typeof payload !== "object") return;
155562
155972
  for (const entry of Object.values(payload)) scan(entry);
155563
155973
  };
155564
- scan(constructorArgs);
155974
+ scan(constructorArgs2);
155565
155975
  }
155566
155976
  function buildOptionalUnityRuntimeLocalizationExport(args) {
155567
155977
  if (args.config === void 0) return void 0;
@@ -170210,8 +170620,8 @@ function cloneWorkspaceStatus(status) {
170210
170620
  };
170211
170621
  }
170212
170622
  function rewrittenSeedProvenance(memberId, seed) {
170213
- const constructorArgs = seed.constructorArgs;
170214
- if (constructorArgs !== void 0 && !isObjectRecord2(constructorArgs)) {
170623
+ const constructorArgs2 = seed.constructorArgs;
170624
+ if (constructorArgs2 !== void 0 && !isObjectRecord2(constructorArgs2)) {
170215
170625
  throw new Error(
170216
170626
  `Static value seed ${JSON.stringify(memberId)} rewrote constructorArgs to a non-object.`
170217
170627
  );
@@ -170229,7 +170639,7 @@ function rewrittenSeedProvenance(memberId, seed) {
170229
170639
  }
170230
170640
  }
170231
170641
  return {
170232
- ...constructorArgs === void 0 ? {} : { constructorArgs },
170642
+ ...constructorArgs2 === void 0 ? {} : { constructorArgs: constructorArgs2 },
170233
170643
  ...seed.instanceConstructorId === void 0 ? {} : {
170234
170644
  instanceConstructorId: seed.instanceConstructorId
170235
170645
  },
@@ -170378,6 +170788,9 @@ function createPendingProjectSourceIdentityV4(workspace, status, authoredValueSe
170378
170788
  }
170379
170789
  materializePendingSourceLocalization(records2, status);
170380
170790
  const emission = emitProjectDocumentFilesV4(records2, {
170791
+ dialogueGroupSymbols: authoredDialogueGroupSymbols(
170792
+ status.sourceSnapshot?.analysis
170793
+ ),
170381
170794
  storedValueBase: storedValueRowsByIdV4(
170382
170795
  Object.values(workspace.state.records)
170383
170796
  ),
@@ -171961,6 +172374,7 @@ var compileNSVoidBody2, compileNSFunction2, compileNSGetter2, compileNSSetter2,
171961
172374
  var init_push = __esm({
171962
172375
  "src/commands/push.ts"() {
171963
172376
  "use strict";
172377
+ init_dialogue_group_symbols();
171964
172378
  init_dialogue_source_diagnostic();
171965
172379
  init_lower_constructors();
171966
172380
  init_neoscript_source_catalog();
@@ -172356,8 +172770,9 @@ async function fetchProjectDocumentDelta(workspace, cursor) {
172356
172770
  const changedKeys = /* @__PURE__ */ new Set();
172357
172771
  for (const record7 of result.records) {
172358
172772
  const key = `${record7.recordKind}:${record7.recordId}`;
172359
- changedKeys.add(key);
172360
172773
  if (record7.deleted) {
172774
+ if (!records2.has(key)) continue;
172775
+ changedKeys.add(key);
172361
172776
  records2.delete(key);
172362
172777
  heads.set(key, {
172363
172778
  recordKind: record7.recordKind,
@@ -172372,6 +172787,8 @@ async function fetchProjectDocumentDelta(workspace, cursor) {
172372
172787
  `Project document delta record "${key}" is live but has no content hash.`
172373
172788
  );
172374
172789
  }
172790
+ if (records2.get(key)?.contentHash === record7.contentHash) continue;
172791
+ changedKeys.add(key);
172375
172792
  records2.set(key, {
172376
172793
  recordKind: record7.recordKind,
172377
172794
  recordId: record7.recordId,
@@ -172752,10 +173169,18 @@ function prepareWorkspaceResetV4(workspace, document, options = {}) {
172752
173169
  const layoutWorkspace = workspaceForSourceLayoutV4(workspace, document);
172753
173170
  const status = listProjectSourceFilesV4(workspace.root).length === 0 ? null : readWorkspaceLayoutStatusV4(layoutWorkspace, document);
172754
173171
  const localValues = status?.localValues ?? workspace.state.localValues;
173172
+ const dialogueGroupSymbols = new Map(
173173
+ authoredDialogueGroupSymbols(status?.sourceSnapshot?.analysis)
173174
+ );
173175
+ const recordFiles = readWorkspaceRecordFilesV4(
173176
+ layoutWorkspace,
173177
+ dialogueGroupSymbols
173178
+ );
172755
173179
  const emitted = emitProjectDocumentFilesV4(emissionRecords, {
172756
173180
  localValues,
173181
+ dialogueGroupSymbols,
172757
173182
  binaryPaths: workspaceBinaryPathsV4(workspace, status?.binaryFiles),
172758
- recordFiles: readWorkspaceRecordFilesV4(layoutWorkspace)
173183
+ recordFiles
172759
173184
  });
172760
173185
  assertUniqueEmittedPaths2(emitted.files);
172761
173186
  const resolveSourcePath = createWorkspaceSourcePathResolver(workspace.root);
@@ -172852,6 +173277,7 @@ var LEGACY_ROOT_FILES, LEGACY_PRIVATE_PATHS;
172852
173277
  var init_reset = __esm({
172853
173278
  "src/project-source/reset.ts"() {
172854
173279
  "use strict";
173280
+ init_dialogue_group_symbols();
172855
173281
  init_language_spec();
172856
173282
  init_source_layout();
172857
173283
  init_workspace_status();
@@ -173332,7 +173758,13 @@ async function finishFormat4Pull(args) {
173332
173758
  )
173333
173759
  );
173334
173760
  const layoutWorkspace = workspaceForSourceLayoutV4(workspace, document);
173335
- const recordFiles = readWorkspaceRecordFilesV4(layoutWorkspace);
173761
+ const dialogueGroupSymbols = new Map(
173762
+ authoredDialogueGroupSymbols(localStatus?.sourceSnapshot?.analysis)
173763
+ );
173764
+ const recordFiles = readWorkspaceRecordFilesV4(
173765
+ layoutWorkspace,
173766
+ dialogueGroupSymbols
173767
+ );
173336
173768
  for (const [key, record7] of localStatus?.reconstructed ?? []) {
173337
173769
  if (record7.file != null) recordFiles.set(key, record7.file);
173338
173770
  }
@@ -173351,7 +173783,8 @@ async function finishFormat4Pull(args) {
173351
173783
  {
173352
173784
  localValues,
173353
173785
  binaryPaths,
173354
- recordFiles
173786
+ recordFiles,
173787
+ dialogueGroupSymbols
173355
173788
  }
173356
173789
  );
173357
173790
  for (const recovery of localResult.staticMemberOwnershipRecoveries ?? []) {
@@ -173359,7 +173792,7 @@ async function finishFormat4Pull(args) {
173359
173792
  }
173360
173793
  const serverResult = conflictCount === 0 ? null : emitProjectDocumentFilesV4(
173361
173794
  buildEmitRecordSet(document, plans, "server"),
173362
- { recordFiles, localValues, binaryPaths }
173795
+ { recordFiles, localValues, binaryPaths, dialogueGroupSymbols }
173363
173796
  );
173364
173797
  const resolveSourcePath = createWorkspaceSourcePathResolver(workspace.root);
173365
173798
  if (!destructive && Object.keys(workspace.state.records).length === 0) {
@@ -173842,6 +174275,7 @@ function composeProspectivePullRecord(recordKind, recordId, data, serverRecord)
173842
174275
  var init_pull = __esm({
173843
174276
  "src/commands/pull.ts"() {
173844
174277
  "use strict";
174278
+ init_dialogue_group_symbols();
173845
174279
  init_project_file_source_preservation();
173846
174280
  init_push();
173847
174281
  init_source_layout();
@@ -185833,7 +186267,7 @@ There is no --keep-current: preserving current semantic state defines flatten.
185833
186267
  async function main() {
185834
186268
  const args = parseArgs(process.argv.slice(2));
185835
186269
  if (args.command === "--version") {
185836
- console.log("0.71.2");
186270
+ console.log("0.71.4");
185837
186271
  return;
185838
186272
  }
185839
186273
  if (args.command === null || args.command === "help" || args.command === "--help" || args.command === "-h") {