Show a sensible error message when Lumina fails to init

This commit is contained in:
goaaats 2025-11-28 18:11:31 +01:00
parent 4c3ba35f07
commit d7915c7020

View file

@ -41,7 +41,7 @@ internal sealed class DataManager : IInternalDisposableService, IDataManager
try try
{ {
Log.Verbose("Starting data load..."); Log.Verbose("Starting data load...");
using (Timings.Start("Lumina Init")) using (Timings.Start("Lumina Init"))
{ {
var luminaOptions = new LuminaOptions var luminaOptions = new LuminaOptions
@ -53,12 +53,25 @@ internal sealed class DataManager : IInternalDisposableService, IDataManager
DefaultExcelLanguage = this.Language.ToLumina(), DefaultExcelLanguage = this.Language.ToLumina(),
}; };
this.GameData = new( try
Path.Combine(Path.GetDirectoryName(Environment.ProcessPath)!, "sqpack"),
luminaOptions)
{ {
StreamPool = new(), this.GameData = new(
}; Path.Combine(Path.GetDirectoryName(Environment.ProcessPath)!, "sqpack"),
luminaOptions)
{
StreamPool = new(),
};
}
catch (Exception ex)
{
Log.Error(ex, "Lumina GameData init failed");
Util.Fatal(
"Dalamud could not read required game data files. This likely means your game installation is corrupted or incomplete.\n\n" +
"Please repair your installation by right-clicking the login button in XIVLauncher and choosing \"Repair game files\".",
"Dalamud");
return;
}
Log.Information("Lumina is ready: {0}", this.GameData.DataPath); Log.Information("Lumina is ready: {0}", this.GameData.DataPath);
@ -71,7 +84,7 @@ internal sealed class DataManager : IInternalDisposableService, IDataManager
dalamud.StartInfo.TroubleshootingPackData); dalamud.StartInfo.TroubleshootingPackData);
this.HasModifiedGameDataFiles = this.HasModifiedGameDataFiles =
tsInfo?.IndexIntegrity is LauncherTroubleshootingInfo.IndexIntegrityResult.Failed or LauncherTroubleshootingInfo.IndexIntegrityResult.Exception; tsInfo?.IndexIntegrity is LauncherTroubleshootingInfo.IndexIntegrityResult.Failed or LauncherTroubleshootingInfo.IndexIntegrityResult.Exception;
if (this.HasModifiedGameDataFiles) if (this.HasModifiedGameDataFiles)
Log.Verbose("Game data integrity check failed!\n{TsData}", dalamud.StartInfo.TroubleshootingPackData); Log.Verbose("Game data integrity check failed!\n{TsData}", dalamud.StartInfo.TroubleshootingPackData);
} }
@ -130,7 +143,7 @@ internal sealed class DataManager : IInternalDisposableService, IDataManager
#region Lumina Wrappers #region Lumina Wrappers
/// <inheritdoc/> /// <inheritdoc/>
public ExcelSheet<T> GetExcelSheet<T>(ClientLanguage? language = null, string? name = null) where T : struct, IExcelRow<T> public ExcelSheet<T> GetExcelSheet<T>(ClientLanguage? language = null, string? name = null) where T : struct, IExcelRow<T>
=> this.Excel.GetSheet<T>(language?.ToLumina(), name); => this.Excel.GetSheet<T>(language?.ToLumina(), name);
/// <inheritdoc/> /// <inheritdoc/>
@ -138,7 +151,7 @@ internal sealed class DataManager : IInternalDisposableService, IDataManager
=> this.Excel.GetSubrowSheet<T>(language?.ToLumina(), name); => this.Excel.GetSubrowSheet<T>(language?.ToLumina(), name);
/// <inheritdoc/> /// <inheritdoc/>
public FileResource? GetFile(string path) public FileResource? GetFile(string path)
=> this.GetFile<FileResource>(path); => this.GetFile<FileResource>(path);
/// <inheritdoc/> /// <inheritdoc/>
@ -161,7 +174,7 @@ internal sealed class DataManager : IInternalDisposableService, IDataManager
: Task.FromException<T>(new FileNotFoundException("The file could not be found.")); : Task.FromException<T>(new FileNotFoundException("The file could not be found."));
/// <inheritdoc/> /// <inheritdoc/>
public bool FileExists(string path) public bool FileExists(string path)
=> this.GameData.FileExists(path); => this.GameData.FileExists(path);
#endregion #endregion