Arma Reforger Explorer  1.1.0.42
Arma Reforger Code Explorer by Zeroy - Thanks to MisterOutofTime
SCR_DSSessionCallback.c
Go to the documentation of this file.
1 
6 class SCR_DSSessionCallback: DSSessionCallback
7 {
8  [Attribute(ESaveType.USER.ToString(), UIWidgets.ComboBox, "Save file type.", enums: ParamEnumArray.FromEnum(ESaveType))]
9  protected ESaveType m_eType;
10 
11  [Attribute(desc: "Unique extension added in front of .json extension.\nUsed for identifying save types without opening files.\n\nMust contain only letters!")]
12  protected string m_sExtension;
13 
14  [Attribute("-", desc: "Character added between mission name and custom name.\nWhen empty, custom name will not be used.")]
15  protected string m_sCustomNameDelimiter;
16 
17  [Attribute(desc: "When enabled, save file will never be saved in cloud.")]
18  protected bool m_bAlwaysLocal;
19 
20  [Attribute(desc: "When enabled, save of this type will also become the latest save for given mission.")]
21  protected bool m_bRegisterLatestSave;
22 
23  [Attribute()]
24  protected ref SCR_UIInfo m_Info;
25 
26  protected SCR_MissionStruct m_Struct;
27  protected bool m_bLoadPreview;
28  protected string m_sCurrentFileName;
29 
31  // Public
33 
37  ESaveType GetSaveType()
38  {
39  return m_eType;
40  }
41 
42  //----------------------------------------------------------------------------------------
46  SCR_UIInfo GetInfo()
47  {
48  return m_Info;
49  }
50 
51  //----------------------------------------------------------------------------------------
58  bool SaveSession(string missionFileName, string customName = string.Empty)
59  {
60  string fileName = GetFileName(missionFileName, customName);
61 
62  if (!IsCompatible(fileName))
63  return false;
64 
65  SessionStorage storage = GetGame().GetBackendApi().GetStorage();
66  storage.AssignFileIDCallback(fileName, this);
67 
68  if (!m_bAlwaysLocal && GetGame().GetSaveManager().CanSaveToCloud())
69  {
70  Print(string.Format("SCR_DSSessionCallback: RequestSave: %1", fileName), LogLevel.VERBOSE);
71  storage.RequestSave(fileName);
72  }
73  else
74  {
75  Print(string.Format("SCR_DSSessionCallback: LocalSave: %1", fileName), LogLevel.VERBOSE);
76  storage.LocalSave(fileName);
77  }
78  return true;
79  }
80 
81  //----------------------------------------------------------------------------------------
87  bool LoadSession(string fileName)
88  {
89  if (!IsCompatible(fileName))
90  return false;
91 
92  m_bLoadPreview = false;
93  SessionStorage storage = GetGame().GetBackendApi().GetStorage();
94  if (!storage.CheckFileID(fileName))
95  {
96  Print(string.Format("SCR_DSSessionCallback: Cannot load save file '%1', it does not exist!", fileName), LogLevel.WARNING);
97  return false;
98  }
99 
100  storage.AssignFileIDCallback(fileName, this);
101 
102  if (!m_bAlwaysLocal && GetGame().GetSaveManager().CanSaveToCloud())
103  {
104  Print(string.Format("SCR_DSSessionCallback: RequestLoad: %1", fileName), LogLevel.VERBOSE);
105  storage.RequestLoad(fileName);
106  }
107  else
108  {
109  Print(string.Format("SCR_DSSessionCallback: LocalLoad: %1", fileName), LogLevel.VERBOSE);
110  storage.LocalLoad(fileName);
111  }
112  return true;
113  }
114 
115  //----------------------------------------------------------------------------------------
122  bool Delete(string missionFileName, string customName)
123  {
124  string fileName = GetFileName(missionFileName, customName);
125  return IsCompatible(fileName) && Delete(fileName);
126  }
127 
128  //----------------------------------------------------------------------------------------
134  bool Delete(string fileName)
135  {
136  if (!GetGame().GetBackendApi().GetStorage().CheckFileID(fileName))
137  return false;
138 
139  GetGame().GetSaveManager().GetOnDeleted().Invoke(m_eType, fileName); //--- Call before the file is actually deleted
140  GetGame().GetBackendApi().GetStorage().LocalDelete(fileName);
141  Print(string.Format("SCR_DSSessionCallback: LocalDelete: '%1'", fileName), LogLevel.VERBOSE);
142  return true;
143  }
144 
145  //----------------------------------------------------------------------------------------
152  bool FileExists(string fileName, string customName = string.Empty)
153  {
154  return GetGame().GetBackendApi().GetStorage().CheckFileID(GetFileName(fileName, customName));
155  }
156 
157  //----------------------------------------------------------------------------------------
163  SCR_MetaStruct GetMeta(string fileName)
164  {
165  if (!IsCompatible(fileName))
166  return null;
167 
168  m_Struct.ClearCache();
169 
170  m_bLoadPreview = true;
171  SessionStorage storage = GetGame().GetBackendApi().GetStorage();
172  storage.AssignFileIDCallback(fileName, this);
173  storage.LocalLoad(fileName);
174 
175  return m_Struct.GetMeta();
176  }
177 
178  //----------------------------------------------------------------------------------------
183  void SetStruct(SCR_MissionStruct struct)
184  {
185  m_Struct = struct;
186  }
187 
188  //----------------------------------------------------------------------------------------
192  SCR_MissionStruct GetStruct()
193  {
194  return m_Struct;
195  }
196 
197  //----------------------------------------------------------------------------------------
201  void Log()
202  {
203  m_Struct.Log();
204  }
205 
206  //----------------------------------------------------------------------------------------
210  bool IsConfigured()
211  {
212  return m_Struct != null;
213  }
214 
215  //----------------------------------------------------------------------------------------
221  bool IsCompatible(string fileName)
222  {
223  if (!m_Struct)
224  return false;
225 
226  //--- Cannot just use EndsWith(), because downloaded files have a GUID added at the end, e.g., "MissionName-CustomName.save_5D82C234B9132BBC"
227  string ext;
228  FilePath.StripExtension(fileName, ext);
229  return ext.StartsWith(m_sExtension);
230  }
231 
232  //----------------------------------------------------------------------------------------
238  string GetMissionFileName(string fileName)
239  {
240  if (!m_sCustomNameDelimiter)
241  {
242  return FilePath.StripExtension(fileName);
243  }
244 
245  int delimiterIndex = fileName.IndexOf(m_sCustomNameDelimiter);
246  if (delimiterIndex >= 0)
247  return fileName.Substring(0, delimiterIndex);
248  else
249  return string.Empty;
250  }
251 
252  //----------------------------------------------------------------------------------------
259  string GetCustomName(string fileName)
260  {
261  if (!m_sCustomNameDelimiter)
262  return string.Empty;
263 
264  int delimiterIndex = fileName.IndexOf(m_sCustomNameDelimiter);
265  if (delimiterIndex < 0)
266  return string.Empty;
267 
268  delimiterIndex += m_sCustomNameDelimiter.Length();
269  int length = fileName.Length() - delimiterIndex;
270  fileName = fileName.Substring(delimiterIndex, length);
271 
272  string ext;
273  return FilePath.StripExtension(fileName, ext);
274  }
275 
276  //----------------------------------------------------------------------------------------
280  string GetCurrentCustomName()
281  {
282  return GetCustomName(m_sCurrentFileName);
283  }
284 
285  //----------------------------------------------------------------------------------------
291  string GetFileName(string missionFileName, string customName)
292  {
293  if (m_sCustomNameDelimiter)
294  {
295  customName = SCR_StringHelper.Filter(customName, SCR_StringHelper.LETTERS + SCR_StringHelper.DIGITS + "_");
296  missionFileName += m_sCustomNameDelimiter + customName;
297  }
298 
299  return FilePath.AppendExtension(missionFileName, m_sExtension);
300  }
301 
302  //----------------------------------------------------------------------------------------
303  void OnGameStart(string missionFileName)
304  {
305  }
306 
307  //----------------------------------------------------------------------------------------
308  void OnGameEnd(string missionFileName)
309  {
310  m_sCurrentFileName = string.Empty;
311  m_Struct = null;
312  }
313 
314  //----------------------------------------------------------------------------------------
315  protected void OnLatestSave(string fileName)
316  {
317  //--- Call invoker with a delay, because the storage is still blocked in this frame, and whatever listens may also need the storage
318  GetGame().GetSaveManager().GetOnLatestSave().Remove(OnLatestSave);
319  GetGame().GetCallqueue().CallLater(InvokeOnSaved);
320  }
321 
322  //----------------------------------------------------------------------------------------
323  protected void InvokeOnSaved()
324  {
325  GetGame().GetSaveManager().GetOnSaved().Invoke(m_eType, m_sCurrentFileName);
326  }
327 
329  // Override
331  override void OnSaving(string fileName)
332  {
333  if (m_Struct.Serialize())
334  GetGame().GetBackendApi().GetStorage().ProcessSave(m_Struct, fileName);
335  }
336 
337  //----------------------------------------------------------------------------------------
338  override void OnSaveSuccess(string fileName)
339  {
340  m_sCurrentFileName = fileName;
341 
342  if (m_bRegisterLatestSave)
343  {
344  //--- Set the save file as the latest save (with a delay; this callback is still used by storage)
345  GetGame().GetSaveManager().GetOnLatestSave().Insert(OnLatestSave);
346  GetGame().GetCallqueue().CallLater(GetGame().GetSaveManager().SetCurrentMissionLatestSave, 0, false, fileName);
347  }
348  else
349  {
350  InvokeOnSaved();
351  }
352 
353  Print(string.Format("SCR_DSSessionCallback: Saving save file of type %1 in '%2' succeeded!", typename.EnumToString(ESaveType, m_eType), fileName), LogLevel.VERBOSE);
354  }
355 
356  //----------------------------------------------------------------------------------------
357  override void OnSaveFailed(string fileName)
358  {
359  Print(string.Format("SCR_DSSessionCallback: Saving save file of type %1 in '%2' failed!", typename.EnumToString(ESaveType, m_eType), fileName), LogLevel.WARNING);
360  }
361 
362  //----------------------------------------------------------------------------------------
363  override void OnLoaded(string fileName)
364  {
365  m_Struct.ClearCache();
366  GetGame().GetBackendApi().GetStorage().ProcessLoad(m_Struct, fileName);
367 
368  if (m_bLoadPreview)
369  {
370  Print(string.Format("SCR_DSSessionCallback: Previewing save file of type %1 from '%2' succeeded!", typename.EnumToString(ESaveType, m_eType), fileName), LogLevel.VERBOSE);
371  }
372  else
373  {
374  m_Struct.Deserialize();
375 
376  m_sCurrentFileName = fileName;
377 
378  GetGame().GetSaveManager().GetOnLoaded().Invoke(m_eType, fileName);
379 
380  Print(string.Format("SCR_DSSessionCallback: Loading save file of type %1 from '%2' succeeded!", typename.EnumToString(ESaveType, m_eType), fileName), LogLevel.VERBOSE);
381  }
382  }
383 
384  //----------------------------------------------------------------------------------------
385  override void OnLoadFailed(string fileName)
386  {
387  Print(string.Format("SCR_DSSessionCallback: Loading save file of type %1 from '%2' failed!", typename.EnumToString(ESaveType, m_eType), fileName), LogLevel.WARNING);
388  }
389 
390  //----------------------------------------------------------------------------------------
391  override void OnDeleteSuccess( string fileName )
392  {
393  if (m_sCurrentFileName == fileName)
394  m_sCurrentFileName = string.Empty;
395 
396  Print(string.Format("SCR_DSSessionCallback: Deleting save file of type %1 at '%2' succeeded!", typename.EnumToString(ESaveType, m_eType), fileName), LogLevel.VERBOSE);
397  }
398 
399  //----------------------------------------------------------------------------------------
400  override void OnDeleteFailed( string fileName )
401  {
402  Print(string.Format("SCR_DSSessionCallback: Deleting save file of type %1 at '%2' failed!", typename.EnumToString(ESaveType, m_eType), fileName), LogLevel.WARNING);
403  }
404 
405  //----------------------------------------------------------------------------------------
406  void SCR_DSSessionCallback()
407  {
408  //--- Only letters allowed in the extension - other characters could confuse save type recognition
409  m_sExtension = SCR_StringHelper.Filter(m_sExtension, SCR_StringHelper.LETTERS);
410  }
411 };
412 
415 {
416  [Attribute("1", UIWidgets.Slider, "", params: "1 10 1")]
417  protected int m_iMaxSaves;
418 
419  //----------------------------------------------------------------------------------------
420  override protected string GetFileName(string missionFileName, string customName)
421  {
422  if (m_iMaxSaves > 1)
423  {
424  int saveId;
425 
426  string latestSaveName;
427  if (GetGame().GetSaveManager().FindCurrentMissionLatestSave(latestSaveName))
428  saveId = GetCustomName(latestSaveName).ToInt();
429 
430  saveId = (saveId % m_iMaxSaves) + 1;
431  customName = saveId.ToString();
432  }
433  else
434  {
435  customName = "1";
436  }
437  return super.GetFileName(missionFileName, customName);
438  }
439 };
440 
443 {
444  //----------------------------------------------------------------------------------------
445  protected void DeleteDelayed(string fileName)
446  {
447  Delete(fileName);
448  }
449  protected void DeleteIfNotToLoad(string missionFileName)
450  {
451  //--- Delete the file only when it's not marked for loading
452  string fileNameToLoad;
453  if (!GetGame().GetSaveManager().FindFileNameToLoad(fileNameToLoad) || !IsCompatible(fileNameToLoad))
454  Delete(missionFileName, string.Empty);
455  }
456 
457  //----------------------------------------------------------------------------------------
458  override void OnLoaded(string fileName)
459  {
460  super.OnLoaded(fileName);
461 
462  //--- Call with delay, won't delete the file when it's still locked after loading
463  GetGame().GetCallqueue().CallLater(DeleteDelayed, 1, false, fileName);
464  }
465  //----------------------------------------------------------------------------------------
466  override void OnGameStart(string missionFileName)
467  {
468  DeleteIfNotToLoad(missionFileName);
469  super.OnGameStart(missionFileName);
470  }
471 
472  //----------------------------------------------------------------------------------------
473  override void OnGameEnd(string missionFileName)
474  {
475  DeleteIfNotToLoad(missionFileName);
476  super.OnGameEnd(missionFileName);
477  }
478 };
SCR_BaseContainerCustomTitleEnum
class SCR_CampaignHintStorage SCR_BaseContainerCustomTitleEnum(EHint, "m_eHintId")
Definition: SCR_CampaignHintStorage.c:22
GetGame
ArmaReforgerScripted GetGame()
Definition: game.c:1424
SCR_StringHelper
Definition: SCR_StringHelper.c:1
desc
UI Textures DeployMenu Briefing conflict_HintBanner_1_UI desc
Definition: SCR_RespawnBriefingComponent.c:17
SCR_NumberedDSSessionCallback
Definition: SCR_DSSessionCallback.c:414
Delete
override bool Delete(bool changedByUser=false, bool updateNavmesh=true)
Definition: SCR_EditableCharacterComponent.c:195
SCR_MetaStruct
Definition: SCR_MetaStruct.c:2
ESaveType
ESaveType
Definition: ESaveType.c:1
Attribute
typedef Attribute
Post-process effect of scripted camera.
m_Info
protected ref SCR_HintUIInfo m_Info
Definition: SCR_BaseHintCondition.c:3
SCR_DisposableDSSessionCallback
Definition: SCR_DSSessionCallback.c:442
SCR_MissionStruct
Definition: SCR_MissionStruct.c:7
SCR_UIInfo
Definition: SCR_UIInfo.c:7
m_eType
protected SCR_ECampaignBaseType m_eType
Definition: SCR_CampaignMilitaryBaseComponent.c:59
params
Configs ServerBrowser KickDialogs params
Definition: SCR_NotificationSenderComponent.c:24
SCR_DSSessionCallback
Definition: SCR_DSSessionCallback.c:6
GetSaveManager
SCR_SaveManagerCore GetSaveManager()
Definition: game.c:211
BaseContainerProps
SCR_AIGoalReaction_Follow BaseContainerProps
Handles insects that are supposed to be spawned around selected prefabs defined in prefab names array...
Definition: SCR_AIGoalReaction.c:468