@routevn/creator-model 1.1.5 → 1.1.6

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@routevn/creator-model",
3
- "version": "1.1.5",
3
+ "version": "1.1.6",
4
4
  "private": false,
5
5
  "type": "module",
6
6
  "license": "MIT",
package/src/model.js CHANGED
@@ -116,6 +116,7 @@ const LAYOUT_TYPE_KEYS = [
116
116
  "dialogue",
117
117
  "nvl",
118
118
  "choice",
119
+ "history",
119
120
  ];
120
121
  const LAYOUT_ELEMENT_TEXT_STYLE_ALIGN_KEYS = ["left", "center", "right"];
121
122
  const LAYOUT_TEXT_REVEAL_EFFECT_KEYS = ["typewriter", "softWipe", "none"];
@@ -133,11 +134,14 @@ const LAYOUT_ELEMENT_BASE_TYPES = [
133
134
  "text-ref-save-load-slot-date",
134
135
  "text-ref-dialogue-line-character-name",
135
136
  "text-ref-dialogue-line-content",
137
+ "text-ref-history-line-character-name",
138
+ "text-ref-history-line-content",
136
139
  "sprite-ref-save-load-slot-image",
137
140
  "fragment-ref",
138
141
  "container-ref-choice-item",
139
142
  "container-ref-save-load-slot",
140
143
  "container-ref-dialogue-line",
144
+ "container-ref-history-line",
141
145
  "container-ref-confirm-dialog-ok",
142
146
  "container-ref-confirm-dialog-cancel",
143
147
  ];
@@ -148,6 +152,7 @@ const LAYOUT_CONTAINER_ELEMENT_TYPES = [
148
152
  "container-ref-choice-item",
149
153
  "container-ref-save-load-slot",
150
154
  "container-ref-dialogue-line",
155
+ "container-ref-history-line",
151
156
  "container-ref-confirm-dialog-ok",
152
157
  "container-ref-confirm-dialog-cancel",
153
158
  ];
@@ -3043,6 +3048,7 @@ const validateLayoutItems = ({ items, path, errorFactory }) => {
3043
3048
  "description",
3044
3049
  "layoutType",
3045
3050
  "isFragment",
3051
+ "thumbnailFileId",
3046
3052
  "elements",
3047
3053
  ],
3048
3054
  path: itemPath,
@@ -3081,11 +3087,21 @@ const validateLayoutItems = ({ items, path, errorFactory }) => {
3081
3087
  );
3082
3088
  }
3083
3089
 
3090
+ if (
3091
+ item.thumbnailFileId !== undefined &&
3092
+ !isNonEmptyString(item.thumbnailFileId)
3093
+ ) {
3094
+ return invalidFromErrorFactory(
3095
+ errorFactory,
3096
+ `${itemPath}.thumbnailFileId must be a non-empty string when provided`,
3097
+ );
3098
+ }
3099
+
3084
3100
  if (item.type === "layout") {
3085
3101
  if (!LAYOUT_TYPE_KEYS.includes(item.layoutType)) {
3086
3102
  return invalidFromErrorFactory(
3087
3103
  errorFactory,
3088
- `${itemPath}.layoutType must be 'normal', 'save-load', 'confirmDialog', 'dialogue', 'nvl', or 'choice'`,
3104
+ `${itemPath}.layoutType must be 'normal', 'save-load', 'confirmDialog', 'dialogue', 'nvl', 'choice', or 'history'`,
3089
3105
  );
3090
3106
  }
3091
3107
 
@@ -3132,7 +3148,7 @@ const validateControlItems = ({ items, path, errorFactory }) => {
3132
3148
  allowedKeys:
3133
3149
  item.type === "folder"
3134
3150
  ? ["id", "type", "name"]
3135
- : ["id", "type", "name", "elements", "keyboard"],
3151
+ : ["id", "type", "name", "thumbnailFileId", "elements", "keyboard"],
3136
3152
  path: itemPath,
3137
3153
  errorFactory,
3138
3154
  });
@@ -3162,6 +3178,16 @@ const validateControlItems = ({ items, path, errorFactory }) => {
3162
3178
  );
3163
3179
  }
3164
3180
 
3181
+ if (
3182
+ item.thumbnailFileId !== undefined &&
3183
+ !isNonEmptyString(item.thumbnailFileId)
3184
+ ) {
3185
+ return invalidFromErrorFactory(
3186
+ errorFactory,
3187
+ `${itemPath}.thumbnailFileId must be a non-empty string when provided`,
3188
+ );
3189
+ }
3190
+
3165
3191
  if (item.type === "control") {
3166
3192
  {
3167
3193
  const result = validateNestedCollection({
@@ -4231,6 +4257,40 @@ export const assertInvariants = ({ state }) => {
4231
4257
  }
4232
4258
  }
4233
4259
 
4260
+ for (const [layoutId, layout] of Object.entries(state.layouts.items)) {
4261
+ if (layout.type !== "layout" || layout.thumbnailFileId === undefined) {
4262
+ continue;
4263
+ }
4264
+
4265
+ const result = validateFileReference({
4266
+ state,
4267
+ fileId: layout.thumbnailFileId,
4268
+ path: "layout.thumbnailFileId",
4269
+ details: { layoutId, thumbnailFileId: layout.thumbnailFileId },
4270
+ errorFactory: createInvariantValidationError,
4271
+ });
4272
+ if (!result.valid) {
4273
+ return result;
4274
+ }
4275
+ }
4276
+
4277
+ for (const [controlId, control] of Object.entries(state.controls.items)) {
4278
+ if (control.type !== "control" || control.thumbnailFileId === undefined) {
4279
+ continue;
4280
+ }
4281
+
4282
+ const result = validateFileReference({
4283
+ state,
4284
+ fileId: control.thumbnailFileId,
4285
+ path: "control.thumbnailFileId",
4286
+ details: { controlId, thumbnailFileId: control.thumbnailFileId },
4287
+ errorFactory: createInvariantValidationError,
4288
+ });
4289
+ if (!result.valid) {
4290
+ return result;
4291
+ }
4292
+ }
4293
+
4234
4294
  const assertImageReference = ({
4235
4295
  ownerIdField,
4236
4296
  ownerId,
@@ -6603,6 +6663,7 @@ const validateLayoutCreateData = ({ data, errorFactory }) => {
6603
6663
  "description",
6604
6664
  "layoutType",
6605
6665
  "isFragment",
6666
+ "thumbnailFileId",
6606
6667
  "elements",
6607
6668
  ],
6608
6669
  path: "payload.data",
@@ -6627,11 +6688,21 @@ const validateLayoutCreateData = ({ data, errorFactory }) => {
6627
6688
  );
6628
6689
  }
6629
6690
 
6691
+ if (
6692
+ data.thumbnailFileId !== undefined &&
6693
+ !isNonEmptyString(data.thumbnailFileId)
6694
+ ) {
6695
+ return invalidFromErrorFactory(
6696
+ errorFactory,
6697
+ "payload.data.thumbnailFileId must be a non-empty string when provided",
6698
+ );
6699
+ }
6700
+
6630
6701
  if (data.type === "layout") {
6631
6702
  if (!LAYOUT_TYPE_KEYS.includes(data.layoutType)) {
6632
6703
  return invalidFromErrorFactory(
6633
6704
  errorFactory,
6634
- "payload.data.layoutType must be 'normal', 'save-load', 'confirmDialog', 'dialogue', 'nvl', or 'choice'",
6705
+ "payload.data.layoutType must be 'normal', 'save-load', 'confirmDialog', 'dialogue', 'nvl', 'choice', or 'history'",
6635
6706
  );
6636
6707
  }
6637
6708
 
@@ -6661,7 +6732,13 @@ const validateLayoutUpdateData = ({ data, errorFactory }) => {
6661
6732
  {
6662
6733
  const result = validateAllowedKeys({
6663
6734
  value: data,
6664
- allowedKeys: ["name", "description", "layoutType", "isFragment"],
6735
+ allowedKeys: [
6736
+ "name",
6737
+ "description",
6738
+ "layoutType",
6739
+ "isFragment",
6740
+ "thumbnailFileId",
6741
+ ],
6665
6742
  path: "payload.data",
6666
6743
  errorFactory,
6667
6744
  });
@@ -6691,13 +6768,23 @@ const validateLayoutUpdateData = ({ data, errorFactory }) => {
6691
6768
  );
6692
6769
  }
6693
6770
 
6771
+ if (
6772
+ data.thumbnailFileId !== undefined &&
6773
+ !isNonEmptyString(data.thumbnailFileId)
6774
+ ) {
6775
+ return invalidFromErrorFactory(
6776
+ errorFactory,
6777
+ "payload.data.thumbnailFileId must be a non-empty string when provided",
6778
+ );
6779
+ }
6780
+
6694
6781
  if (
6695
6782
  data.layoutType !== undefined &&
6696
6783
  !LAYOUT_TYPE_KEYS.includes(data.layoutType)
6697
6784
  ) {
6698
6785
  return invalidFromErrorFactory(
6699
6786
  errorFactory,
6700
- "payload.data.layoutType must be 'normal', 'save-load', 'confirmDialog', 'dialogue', 'nvl', or 'choice' when provided",
6787
+ "payload.data.layoutType must be 'normal', 'save-load', 'confirmDialog', 'dialogue', 'nvl', 'choice', or 'history' when provided",
6701
6788
  );
6702
6789
  }
6703
6790
 
@@ -6730,7 +6817,7 @@ const validateControlCreateData = ({ data, errorFactory }) => {
6730
6817
  allowedKeys:
6731
6818
  data.type === "folder"
6732
6819
  ? ["type", "name"]
6733
- : ["type", "name", "elements", "keyboard"],
6820
+ : ["type", "name", "thumbnailFileId", "elements", "keyboard"],
6734
6821
  path: "payload.data",
6735
6822
  errorFactory,
6736
6823
  });
@@ -6746,6 +6833,16 @@ const validateControlCreateData = ({ data, errorFactory }) => {
6746
6833
  );
6747
6834
  }
6748
6835
 
6836
+ if (
6837
+ data.thumbnailFileId !== undefined &&
6838
+ !isNonEmptyString(data.thumbnailFileId)
6839
+ ) {
6840
+ return invalidFromErrorFactory(
6841
+ errorFactory,
6842
+ "payload.data.thumbnailFileId must be a non-empty string when provided",
6843
+ );
6844
+ }
6845
+
6749
6846
  if (data.type === "control") {
6750
6847
  {
6751
6848
  const result = validateNestedCollection({
@@ -6777,7 +6874,7 @@ const validateControlUpdateData = ({ data, errorFactory }) => {
6777
6874
  {
6778
6875
  const result = validateAllowedKeys({
6779
6876
  value: data,
6780
- allowedKeys: ["name", "keyboard"],
6877
+ allowedKeys: ["name", "keyboard", "thumbnailFileId"],
6781
6878
  path: "payload.data",
6782
6879
  errorFactory,
6783
6880
  });
@@ -6800,6 +6897,16 @@ const validateControlUpdateData = ({ data, errorFactory }) => {
6800
6897
  );
6801
6898
  }
6802
6899
 
6900
+ if (
6901
+ data.thumbnailFileId !== undefined &&
6902
+ !isNonEmptyString(data.thumbnailFileId)
6903
+ ) {
6904
+ return invalidFromErrorFactory(
6905
+ errorFactory,
6906
+ "payload.data.thumbnailFileId must be a non-empty string when provided",
6907
+ );
6908
+ }
6909
+
6803
6910
  {
6804
6911
  const result = validateKeyboardMap({
6805
6912
  value: data.keyboard,
@@ -11779,11 +11886,30 @@ const COMMAND_DEFINITIONS = [
11779
11886
  description: payload.data.description,
11780
11887
  layoutType: payload.data.layoutType,
11781
11888
  isFragment: payload.data.isFragment,
11889
+ ...(payload.data.thumbnailFileId !== undefined
11890
+ ? {
11891
+ thumbnailFileId: payload.data.thumbnailFileId,
11892
+ }
11893
+ : {}),
11782
11894
  elements: structuredClone(payload.data.elements),
11783
11895
  }
11784
11896
  : {}),
11785
11897
  }),
11786
- validateUpdateState: ({ payload, currentItem }) => {
11898
+ validateCreateState: ({ state, payload }) => {
11899
+ if (payload.data.type !== "layout") {
11900
+ return;
11901
+ }
11902
+
11903
+ return validateReferencedFilesInData({
11904
+ state,
11905
+ data: payload.data,
11906
+ fields: ["thumbnailFileId"],
11907
+ details: {
11908
+ layoutId: payload.layoutId,
11909
+ },
11910
+ });
11911
+ },
11912
+ validateUpdateState: ({ state, payload, currentItem }) => {
11787
11913
  if (
11788
11914
  currentItem.type === "folder" &&
11789
11915
  Object.keys(payload.data).some((key) => key !== "name")
@@ -11792,6 +11918,17 @@ const COMMAND_DEFINITIONS = [
11792
11918
  "folder layout items cannot update layout fields",
11793
11919
  );
11794
11920
  }
11921
+
11922
+ if (currentItem.type === "layout") {
11923
+ return validateReferencedFilesInData({
11924
+ state,
11925
+ data: payload.data,
11926
+ fields: ["thumbnailFileId"],
11927
+ details: {
11928
+ layoutId: payload.layoutId,
11929
+ },
11930
+ });
11931
+ }
11795
11932
  },
11796
11933
  }),
11797
11934
  ...createFolderedCollectionCommandDefinitions({
@@ -11807,6 +11944,11 @@ const COMMAND_DEFINITIONS = [
11807
11944
  name: payload.data.name,
11808
11945
  ...(payload.data.type === "control"
11809
11946
  ? {
11947
+ ...(payload.data.thumbnailFileId !== undefined
11948
+ ? {
11949
+ thumbnailFileId: payload.data.thumbnailFileId,
11950
+ }
11951
+ : {}),
11810
11952
  elements: structuredClone(payload.data.elements),
11811
11953
  ...(payload.data.keyboard !== undefined
11812
11954
  ? {
@@ -11816,7 +11958,21 @@ const COMMAND_DEFINITIONS = [
11816
11958
  }
11817
11959
  : {}),
11818
11960
  }),
11819
- validateUpdateState: ({ payload, currentItem }) => {
11961
+ validateCreateState: ({ state, payload }) => {
11962
+ if (payload.data.type !== "control") {
11963
+ return;
11964
+ }
11965
+
11966
+ return validateReferencedFilesInData({
11967
+ state,
11968
+ data: payload.data,
11969
+ fields: ["thumbnailFileId"],
11970
+ details: {
11971
+ controlId: payload.controlId,
11972
+ },
11973
+ });
11974
+ },
11975
+ validateUpdateState: ({ state, payload, currentItem }) => {
11820
11976
  if (
11821
11977
  currentItem.type === "folder" &&
11822
11978
  Object.keys(payload.data).some((key) => key !== "name")
@@ -11825,6 +11981,17 @@ const COMMAND_DEFINITIONS = [
11825
11981
  "folder control items cannot update control fields",
11826
11982
  );
11827
11983
  }
11984
+
11985
+ if (currentItem.type === "control") {
11986
+ return validateReferencedFilesInData({
11987
+ state,
11988
+ data: payload.data,
11989
+ fields: ["thumbnailFileId"],
11990
+ details: {
11991
+ controlId: payload.controlId,
11992
+ },
11993
+ });
11994
+ }
11828
11995
  },
11829
11996
  }),
11830
11997
  {
@@ -24,12 +24,30 @@ export const SYSTEM_VARIABLE_GROUPS = Object.freeze([
24
24
  {
25
25
  id: "_currentSaveLoadPagination",
26
26
  name: "Current Save/Load Pagination",
27
- scope: "runtime-screen",
27
+ scope: "context",
28
28
  type: "number",
29
29
  default: 0,
30
30
  description:
31
31
  "The current save/load pagination index. Resolves to 0, 1, 2, 3, and so on for the active save/load page.",
32
32
  },
33
+ {
34
+ id: "_currentMenuPage",
35
+ name: "Current Menu Page",
36
+ scope: "context",
37
+ type: "string",
38
+ default: "",
39
+ description:
40
+ "The current menu page id for the active UI flow. Typical values include options, save, load, and history.",
41
+ },
42
+ {
43
+ id: "_menuEntryPoint",
44
+ name: "Menu Entry Point",
45
+ scope: "context",
46
+ type: "string",
47
+ default: "",
48
+ description:
49
+ "Indicates how the current menu flow was opened. Typical values include title and read.",
50
+ },
33
51
  ]),
34
52
  },
35
53
  ]);