diff --git a/BSIPA-ModList/BSIPA-ModList.csproj b/BSIPA-ModList/BSIPA-ModList.csproj
index 126b0af5..f69147ae 100644
--- a/BSIPA-ModList/BSIPA-ModList.csproj
+++ b/BSIPA-ModList/BSIPA-ModList.csproj
@@ -72,6 +72,7 @@
+
diff --git a/BSIPA-ModList/UI/ViewControllers/ModCells.cs b/BSIPA-ModList/UI/ViewControllers/ModCells.cs
new file mode 100644
index 00000000..247b4eee
--- /dev/null
+++ b/BSIPA-ModList/UI/ViewControllers/ModCells.cs
@@ -0,0 +1,228 @@
+using CustomUI.BeatSaber;
+using CustomUI.Utilities;
+using IPA.Loader;
+using IPA.Loader.Features;
+using IPA.Old;
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+using UnityEngine;
+
+namespace BSIPA_ModList.UI.ViewControllers
+{
+ internal interface IClickableCell
+ {
+ void OnSelect(ModListController cntrl);
+ }
+
+ internal class BSIPAModCell : CustomCellInfo, IClickableCell
+ {
+ private static Sprite _defaultIcon;
+ public static Sprite DefaultIcon
+ {
+ get
+ {
+ if (_defaultIcon == null)
+ _defaultIcon = UIUtilities.LoadSpriteFromResources("BSIPA_ModList.Icons.mod_bsipa.png");
+ return _defaultIcon;
+ }
+ }
+
+ internal PluginLoader.PluginInfo Plugin;
+ private ModListController list;
+
+ public BSIPAModCell(ModListController list, PluginLoader.PluginInfo plugin)
+ : base($"{plugin.Metadata.Name} v{plugin.Metadata.Version}", plugin.Metadata.Manifest.Author, null)
+ {
+ Plugin = plugin;
+ this.list = list;
+
+ if (string.IsNullOrWhiteSpace(subtext))
+ subtext = "Unspecified Author";
+
+ if (plugin.Metadata.Manifest.IconPath != null)
+ {
+ try
+ {
+ icon = UIUtilities.LoadSpriteRaw(UIUtilities.GetResource(plugin.Metadata.Assembly, plugin.Metadata.Manifest.IconPath));
+ }
+ catch (Exception e)
+ {
+ Logger.log.Error($"Error loading icon for {plugin.Metadata.Name}");
+ Logger.log.Error(e);
+ }
+ }
+
+ if (icon == null)
+ icon = DefaultIcon;
+
+ Logger.log.Debug($"BSIPAModCell {plugin.Metadata.Name} {plugin.Metadata.Version}");
+ }
+
+ private ModInfoViewController infoView;
+
+ public void OnSelect(ModListController cntrl)
+ {
+ Logger.log.Debug($"Selected BSIPAModCell {Plugin.Metadata.Name} {Plugin.Metadata.Version}");
+
+ if (infoView == null)
+ {
+ var desc = Plugin.Metadata.Manifest.Description;
+ if (string.IsNullOrWhiteSpace(desc))
+ desc = "No description";
+
+ infoView = BeatSaberUI.CreateViewController();
+ infoView.Init(icon, Plugin.Metadata.Name, "v" + Plugin.Metadata.Version.ToString(), subtext,
+ desc, Plugin.Metadata.Features.FirstOrDefault(f => f is NoUpdateFeature) != null ? Plugin.Metadata : null,
+ Plugin.Metadata.Manifest.Links);
+ }
+
+ list.flow.SetSelected(infoView, immediate: list.flow.HasSelected);
+ }
+ }
+
+ internal class BSIPAIgnoredModCell : CustomCellInfo, IClickableCell
+ {
+ internal PluginLoader.PluginMetadata Plugin;
+ private ModListController list;
+
+ private const string authorFormat = "{0} - Not loaded";
+
+ private string authorText;
+
+ public BSIPAIgnoredModCell(ModListController list, PluginLoader.PluginMetadata plugin)
+ : base($"{plugin.Name} v{plugin.Version}", "", BSIPAModCell.DefaultIcon)
+ {
+ Plugin = plugin;
+ this.list = list;
+
+ if (string.IsNullOrWhiteSpace(plugin.Manifest.Author))
+ authorText = "Unspecified Author";
+ else
+ authorText = plugin.Manifest.Author;
+ subtext = string.Format(authorFormat, authorText);
+
+ Logger.log.Debug($"BSIPAIgnoredModCell {plugin.Name} {plugin.Version}");
+ }
+
+ private ModInfoViewController infoView;
+
+ public void OnSelect(ModListController cntrl)
+ {
+ Logger.log.Debug($"Selected BSIPAIgnoredModCell {Plugin.Name} {Plugin.Version}");
+
+ if (infoView == null)
+ {
+ var desc = Plugin.Manifest.Description;
+ if (string.IsNullOrWhiteSpace(desc))
+ desc = "No description";
+
+ infoView = BeatSaberUI.CreateViewController();
+ infoView.Init(icon, Plugin.Name, "v" + Plugin.Version.ToString(), authorText,
+ desc, Plugin.Features.FirstOrDefault(f => f is NoUpdateFeature) != null ? Plugin : null,
+ Plugin.Manifest.Links);
+ }
+
+ list.flow.SetSelected(infoView, immediate: list.flow.HasSelected);
+ }
+ }
+ internal class LibraryModCell : CustomCellInfo, IClickableCell
+ {
+ private static Sprite _defaultIcon;
+ public static Sprite DefaultIcon
+ {
+ get
+ {
+ if (_defaultIcon == null)
+ _defaultIcon = UIUtilities.LoadSpriteFromResources("BSIPA_ModList.Icons.library.png");
+ return _defaultIcon;
+ }
+ }
+
+ internal PluginLoader.PluginInfo Plugin;
+ private ModListController list;
+
+ public LibraryModCell(ModListController list, PluginLoader.PluginInfo plugin)
+ : base($"{plugin.Metadata.Name} v{plugin.Metadata.Version}", plugin.Metadata.Manifest.Author, null)
+ {
+ Plugin = plugin;
+ this.list = list;
+
+ if (string.IsNullOrWhiteSpace(subtext))
+ subtext = "Unspecified Author";
+
+ icon = DefaultIcon;
+
+ Logger.log.Debug($"LibraryModCell {plugin.Metadata.Name} {plugin.Metadata.Version}");
+ }
+
+ private ModInfoViewController infoView;
+
+ public void OnSelect(ModListController cntrl)
+ {
+ Logger.log.Debug($"Selected LibraryModCell {Plugin.Metadata.Name} {Plugin.Metadata.Version}");
+
+ if (infoView == null)
+ {
+ var desc = Plugin.Metadata.Manifest.Description;
+ if (string.IsNullOrWhiteSpace(desc))
+ desc = "No description";
+
+ infoView = BeatSaberUI.CreateViewController();
+ infoView.Init(icon, Plugin.Metadata.Name, "v" + Plugin.Metadata.Version.ToString(), subtext,
+ desc, Plugin.Metadata.Features.FirstOrDefault(f => f is NoUpdateFeature) != null ? Plugin.Metadata : null,
+ Plugin.Metadata.Manifest.Links);
+ }
+
+ list.flow.SetSelected(infoView, immediate: list.flow.HasSelected);
+ }
+ }
+
+#pragma warning disable CS0618
+ internal class IPAModCell : CustomCellInfo, IClickableCell
+ {
+ private static Sprite _defaultIcon;
+ public static Sprite DefaultIcon
+ {
+ get
+ {
+ if (_defaultIcon == null)
+ _defaultIcon = UIUtilities.LoadSpriteFromResources("BSIPA_ModList.Icons.mod_ipa.png");
+ return _defaultIcon;
+ }
+ }
+
+ internal IPlugin Plugin;
+ private ModListController list;
+
+ public IPAModCell(ModListController list, IPlugin plugin)
+ : base($"{plugin.Name} {plugin.Version}", "Legacy", DefaultIcon)
+ {
+ Plugin = plugin;
+ this.list = list;
+
+ Logger.log.Debug($"IPAModCell {plugin.Name} {plugin.Version}");
+ }
+
+ private ModInfoViewController infoView;
+
+ public void OnSelect(ModListController cntrl)
+ {
+ Logger.log.Debug($"Selected IPAModCell {Plugin.Name} {Plugin.Version}");
+
+ if (infoView == null)
+ {
+ infoView = BeatSaberUI.CreateViewController();
+ infoView.Init(icon, Plugin.Name, "v" + Plugin.Version.ToString(), "Unknown Author",
+ "This mod was written for IPA Reloaded. No metadata is avaliable for this mod. " +
+ "Please contact the mod author and ask them to port it to BSIPA to provide more information.", null);
+ }
+
+ list.flow.SetSelected(infoView, immediate: list.flow.HasSelected);
+ }
+ }
+#pragma warning restore
+
+}
diff --git a/BSIPA-ModList/UI/ViewControllers/ModListController.cs b/BSIPA-ModList/UI/ViewControllers/ModListController.cs
index 26af6e76..33dcf369 100644
--- a/BSIPA-ModList/UI/ViewControllers/ModListController.cs
+++ b/BSIPA-ModList/UI/ViewControllers/ModListController.cs
@@ -10,224 +10,12 @@ using UnityEngine;
using VRUI;
using IPA.Loader.Features;
using TMPro;
+using BSIPA_ModList.UI.ViewControllers;
namespace BSIPA_ModList.UI
{
internal class ModListController : CustomListViewController
{
- private interface IClickableCell
- {
- void OnSelect(ModListController cntrl);
- }
-
- private class BSIPAModCell : CustomCellInfo, IClickableCell
- {
- private static Sprite _defaultIcon;
- public static Sprite DefaultIcon
- {
- get
- {
- if (_defaultIcon == null)
- _defaultIcon = UIUtilities.LoadSpriteFromResources("BSIPA_ModList.Icons.mod_bsipa.png");
- return _defaultIcon;
- }
- }
-
- internal PluginLoader.PluginInfo Plugin;
- private ModListController list;
-
- public BSIPAModCell(ModListController list, PluginLoader.PluginInfo plugin)
- : base($"{plugin.Metadata.Name} v{plugin.Metadata.Version}", plugin.Metadata.Manifest.Author, null)
- {
- Plugin = plugin;
- this.list = list;
-
- if (string.IsNullOrWhiteSpace(subtext))
- subtext = "Unspecified Author";
-
- if (plugin.Metadata.Manifest.IconPath != null)
- {
- try
- {
- icon = UIUtilities.LoadSpriteRaw(UIUtilities.GetResource(plugin.Metadata.Assembly, plugin.Metadata.Manifest.IconPath));
- }
- catch (Exception e)
- {
- Logger.log.Error($"Error loading icon for {plugin.Metadata.Name}");
- Logger.log.Error(e);
- }
- }
-
- if (icon == null)
- icon = DefaultIcon;
-
- Logger.log.Debug($"BSIPAModCell {plugin.Metadata.Name} {plugin.Metadata.Version}");
- }
-
- private ModInfoViewController infoView;
-
- public void OnSelect(ModListController cntrl)
- {
- Logger.log.Debug($"Selected BSIPAModCell {Plugin.Metadata.Name} {Plugin.Metadata.Version}");
-
- if (infoView == null)
- {
- var desc = Plugin.Metadata.Manifest.Description;
- if (string.IsNullOrWhiteSpace(desc))
- desc = "No description";
-
- infoView = BeatSaberUI.CreateViewController();
- infoView.Init(icon, Plugin.Metadata.Name, "v" + Plugin.Metadata.Version.ToString(), subtext,
- desc, Plugin.Metadata.Features.FirstOrDefault(f => f is NoUpdateFeature) != null ? Plugin.Metadata : null,
- Plugin.Metadata.Manifest.Links);
- }
-
- list.flow.SetSelected(infoView, immediate: list.flow.HasSelected);
- }
- }
-
- private class BSIPAIgnoredModCell : CustomCellInfo, IClickableCell
- {
- internal PluginLoader.PluginMetadata Plugin;
- private ModListController list;
-
- private const string authorFormat = "{0} - Not loaded";
-
- private string authorText;
-
- public BSIPAIgnoredModCell(ModListController list, PluginLoader.PluginMetadata plugin)
- : base($"{plugin.Name} v{plugin.Version}", "", BSIPAModCell.DefaultIcon)
- {
- Plugin = plugin;
- this.list = list;
-
- if (string.IsNullOrWhiteSpace(plugin.Manifest.Author))
- authorText = "Unspecified Author";
- else
- authorText = plugin.Manifest.Author;
- subtext = string.Format(authorFormat, authorText);
-
- Logger.log.Debug($"BSIPAIgnoredModCell {plugin.Name} {plugin.Version}");
- }
-
- private ModInfoViewController infoView;
-
- public void OnSelect(ModListController cntrl)
- {
- Logger.log.Debug($"Selected BSIPAIgnoredModCell {Plugin.Name} {Plugin.Version}");
-
- if (infoView == null)
- {
- var desc = Plugin.Manifest.Description;
- if (string.IsNullOrWhiteSpace(desc))
- desc = "No description";
-
- infoView = BeatSaberUI.CreateViewController();
- infoView.Init(icon, Plugin.Name, "v" + Plugin.Version.ToString(), authorText,
- desc, Plugin.Features.FirstOrDefault(f => f is NoUpdateFeature) != null ? Plugin : null,
- Plugin.Manifest.Links);
- }
-
- list.flow.SetSelected(infoView, immediate: list.flow.HasSelected);
- }
- }
- private class LibraryModCell : CustomCellInfo, IClickableCell
- {
- private static Sprite _defaultIcon;
- public static Sprite DefaultIcon
- {
- get
- {
- if (_defaultIcon == null)
- _defaultIcon = UIUtilities.LoadSpriteFromResources("BSIPA_ModList.Icons.library.png");
- return _defaultIcon;
- }
- }
-
- internal PluginLoader.PluginInfo Plugin;
- private ModListController list;
-
- public LibraryModCell(ModListController list, PluginLoader.PluginInfo plugin)
- : base($"{plugin.Metadata.Name} v{plugin.Metadata.Version}", plugin.Metadata.Manifest.Author, null)
- {
- Plugin = plugin;
- this.list = list;
-
- if (string.IsNullOrWhiteSpace(subtext))
- subtext = "Unspecified Author";
-
- icon = DefaultIcon;
-
- Logger.log.Debug($"LibraryModCell {plugin.Metadata.Name} {plugin.Metadata.Version}");
- }
-
- private ModInfoViewController infoView;
-
- public void OnSelect(ModListController cntrl)
- {
- Logger.log.Debug($"Selected LibraryModCell {Plugin.Metadata.Name} {Plugin.Metadata.Version}");
-
- if (infoView == null)
- {
- var desc = Plugin.Metadata.Manifest.Description;
- if (string.IsNullOrWhiteSpace(desc))
- desc = "No description";
-
- infoView = BeatSaberUI.CreateViewController();
- infoView.Init(icon, Plugin.Metadata.Name, "v" + Plugin.Metadata.Version.ToString(), subtext,
- desc, Plugin.Metadata.Features.FirstOrDefault(f => f is NoUpdateFeature) != null ? Plugin.Metadata : null,
- Plugin.Metadata.Manifest.Links);
- }
-
- list.flow.SetSelected(infoView, immediate: list.flow.HasSelected);
- }
- }
-
-#pragma warning disable CS0618
- private class IPAModCell : CustomCellInfo, IClickableCell
- {
- private static Sprite _defaultIcon;
- public static Sprite DefaultIcon
- {
- get
- {
- if (_defaultIcon == null)
- _defaultIcon = UIUtilities.LoadSpriteFromResources("BSIPA_ModList.Icons.mod_ipa.png");
- return _defaultIcon;
- }
- }
-
- internal IPlugin Plugin;
- private ModListController list;
-
- public IPAModCell(ModListController list, IPlugin plugin)
- : base($"{plugin.Name} {plugin.Version}", "Legacy", DefaultIcon)
- {
- Plugin = plugin;
- this.list = list;
-
- Logger.log.Debug($"IPAModCell {plugin.Name} {plugin.Version}");
- }
-
- private ModInfoViewController infoView;
-
- public void OnSelect(ModListController cntrl)
- {
- Logger.log.Debug($"Selected IPAModCell {Plugin.Name} {Plugin.Version}");
-
- if (infoView == null)
- {
- infoView = BeatSaberUI.CreateViewController();
- infoView.Init(icon, Plugin.Name, "v" + Plugin.Version.ToString(), "Unknown Author",
- "This mod was written for IPA Reloaded. No metadata is avaliable for this mod. " +
- "Please contact the mod author and ask them to port it to BSIPA to provide more information.", null);
- }
-
- list.flow.SetSelected(infoView, immediate: list.flow.HasSelected);
- }
- }
-#pragma warning restore
-
public override TableCell CellForIdx(int idx)
{
var cell = base.CellForIdx(idx) as LevelListTableCell;
@@ -236,7 +24,7 @@ namespace BSIPA_ModList.UI
return cell;
}
- private ModListFlowCoordinator flow;
+ internal ModListFlowCoordinator flow;
#pragma warning disable CS0618
public void Init(ModListFlowCoordinator flow, IEnumerable bsipaPlugins, IEnumerable ignoredPlugins, IEnumerable ipaPlugins)
diff --git a/IPA.Injector/Updates.cs b/IPA.Injector/Updates.cs
index 663095c5..7d870fc5 100644
--- a/IPA.Injector/Updates.cs
+++ b/IPA.Injector/Updates.cs
@@ -110,7 +110,15 @@ namespace IPA.Injector
updater.Error(e);
}
- Directory.Delete(pendingDir, true);
+ try
+ {
+ Directory.Delete(pendingDir, true);
+ }
+ catch (Exception e)
+ {
+ updater.Error("Something went wrong performing an operation that should never fail!");
+ updater.Error(e);
+ }
}
}
}
diff --git a/IPA.Loader/Updating/BeatMods/Updater.cs b/IPA.Loader/Updating/BeatMods/Updater.cs
index a44b5071..1d4bbcd1 100644
--- a/IPA.Loader/Updating/BeatMods/Updater.cs
+++ b/IPA.Loader/Updating/BeatMods/Updater.cs
@@ -431,7 +431,7 @@ namespace IPA.Updating.BeatMods
using (var request = UnityWebRequest.Get(url))
using (var taskTokenSource = new CancellationTokenSource())
{
- var dlh = new StreamDownloadHandler(stream, (int i1, int i2, double d) => progress(item, i1, i2, d));
+ var dlh = new StreamDownloadHandler(stream, (int i1, int i2, double d) => progress?.Invoke(item, i1, i2, d));
request.downloadHandler = dlh;
downloadStart?.Invoke(item);