This commit is contained in:
2025-11-17 07:19:43 +01:00
parent 72a81e05ad
commit e584996043
29 changed files with 134 additions and 668 deletions

View File

@@ -63,7 +63,7 @@
<PackageReference Include="Pilz.Cryptography" Version="2.1.2" /> <PackageReference Include="Pilz.Cryptography" Version="2.1.2" />
<PackageReference Include="Pilz.IO" Version="2.1.0" /> <PackageReference Include="Pilz.IO" Version="2.1.0" />
<PackageReference Include="Pilz.UI" Version="3.1.4" /> <PackageReference Include="Pilz.UI" Version="3.1.4" />
<PackageReference Include="Pilz.UI.AvaloniaUI" Version="1.2.15" /> <PackageReference Include="Pilz.UI.AvaloniaUI" Version="1.2.17" />
<PackageReference Include="Avalonia" Version="11.3.8" /> <PackageReference Include="Avalonia" Version="11.3.8" />
<PackageReference Include="Avalonia.Desktop" Version="11.3.8" /> <PackageReference Include="Avalonia.Desktop" Version="11.3.8" />
<PackageReference Include="Avalonia.Svg" Version="11.3.0" /> <PackageReference Include="Avalonia.Svg" Version="11.3.0" />

View File

@@ -1,5 +1,6 @@
using Avalonia.Controls; using Avalonia.Controls;
using ModpackUpdater.Apps.Manager.Ui.Models; using ModpackUpdater.Apps.Manager.Ui.Models;
using ModpackUpdater.Apps.Manager.Ui.Models.MainWindow;
namespace ModpackUpdater.Apps.Manager.Api.Model; namespace ModpackUpdater.Apps.Manager.Api.Model;

View File

@@ -15,12 +15,12 @@ internal class CheckSingleActionHealthyFeature : PluginFunction, IPluginFeatureP
Icon = AppGlobals.Symbols.GetImage(AppSymbols.heart_with_pulse, SymbolSize.Small); Icon = AppGlobals.Symbols.GetImage(AppSymbols.heart_with_pulse, SymbolSize.Small);
} }
protected override object? ExecuteFunction(PluginFunctionParameter? @params) protected override async Task<object?> ExecuteFunctionAsync(PluginFunctionParameter? @params)
{ {
if (@params is not MainApiParameters p || p.Api.Model.SelectedGridRow is not { } row) if (@params is not MainApiParameters p || p.Api.Model.SelectedGridRow is not { } row)
return null; return null;
Task.Run(() => SharedFunctions.CheckActionHealthy(p.Api, row)).Wait(); await SharedFunctions.CheckActionHealthy(p.Api, row);
return null; return null;
} }

View File

@@ -1,8 +1,8 @@
using ModpackUpdater.Apps.Manager.Api; using ModpackUpdater.Apps.Manager.Api;
using ModpackUpdater.Apps.Manager.Api.Plugins.Params; using ModpackUpdater.Apps.Manager.Api.Plugins.Params;
using ModpackUpdater.Apps.Manager.LangRes; using ModpackUpdater.Apps.Manager.LangRes;
using ModpackUpdater.Apps.Manager.Ui;
using Pilz.Features; using Pilz.Features;
using Pilz.UI.Symbols;
namespace ModpackUpdater.Apps.Manager.Features.CM; namespace ModpackUpdater.Apps.Manager.Features.CM;
@@ -12,16 +12,13 @@ internal class ClearDirectLinkFeature : PluginFunction, IPluginFeatureProvider<C
public ClearDirectLinkFeature() : base(FeatureTypes.ActionsContextMenu, "origin.cleardirectlink", FeatureNamesLangRes.ClearDirectLinkFeature) public ClearDirectLinkFeature() : base(FeatureTypes.ActionsContextMenu, "origin.cleardirectlink", FeatureNamesLangRes.ClearDirectLinkFeature)
{ {
Icon = AppGlobals.Symbols.GetImage(AppSymbols.broom, Pilz.UI.Symbols.SymbolSize.Small); Icon = AppGlobals.Symbols.GetImage(AppSymbols.broom, SymbolSize.Small);
} }
protected override object? ExecuteFunction(PluginFunctionParameter? @params) protected override Task<object?> ExecuteFunctionAsync(PluginFunctionParameter? @params)
{ {
if (@params is not MainApiParameters p || p.Api.Model.SelectedGridRow is not { } row) if (@params is MainApiParameters p && p.Api.Model.SelectedGridRow is { } row)
return null;
SharedFunctions.ClearDirectLinks(row); SharedFunctions.ClearDirectLinks(row);
return Task.FromResult<object?>(null);
return null;
} }
} }

View File

@@ -14,12 +14,12 @@ internal class UpdateCollectorFeature : PluginFunction, IPluginFeatureProvider<U
Icon = AppGlobals.Symbols.GetImage(AppSymbols.search, SymbolSize.Small); Icon = AppGlobals.Symbols.GetImage(AppSymbols.search, SymbolSize.Small);
} }
protected override object? ExecuteFunction(PluginFunctionParameter? @params) protected override async Task<object?> ExecuteFunctionAsync(PluginFunctionParameter? @params)
{ {
if (@params is not MainApiParameters p || p.Api.Model.SelectedGridRow is not { } row) if (@params is not MainApiParameters p || p.Api.Model.SelectedGridRow is not { } row)
return null; return null;
Task.Run(() => SharedFunctions.CollectUpdates(p.Api, row.Action)).Wait(); await SharedFunctions.CollectUpdates(p.Api, row.Action);
return null; return null;
} }

View File

@@ -1,7 +1,7 @@
using ModpackUpdater.Apps.Manager.Api; using ModpackUpdater.Apps.Manager.Api;
using ModpackUpdater.Apps.Manager.Api.Plugins.Params; using ModpackUpdater.Apps.Manager.Api.Plugins.Params;
using ModpackUpdater.Apps.Manager.LangRes; using ModpackUpdater.Apps.Manager.LangRes;
using ModpackUpdater.Apps.Manager.Ui.Models; using ModpackUpdater.Apps.Manager.Ui.Models.MainWindow;
using Pilz.Features; using Pilz.Features;
using Pilz.UI.Symbols; using Pilz.UI.Symbols;
@@ -16,12 +16,12 @@ internal class UpdateDirectLinkFeature : PluginFunction, IPluginFeatureProvider<
Icon = AppGlobals.Symbols.GetImage(AppSymbols.renew, SymbolSize.Small); Icon = AppGlobals.Symbols.GetImage(AppSymbols.renew, SymbolSize.Small);
} }
protected override object? ExecuteFunction(PluginFunctionParameter? @params) protected override async Task<object?> ExecuteFunctionAsync(PluginFunctionParameter? @params)
{ {
if (@params is not MainApiParameters p || p.Api.Model.SelectedGridRow is not MainWindowGridRow row) if (@params is not MainApiParameters p || p.Api.Model.SelectedGridRow is not MainWindowGridRow row)
return null; return null;
Task.Run(() => SharedFunctions.FindNewDirectLinks(row)).Wait(); await SharedFunctions.FindNewDirectLinks(row);
return null; return null;
} }

View File

@@ -1,8 +1,11 @@
using System.Text; using System.Text;
using Avalonia.Controls;
using ModpackUpdater.Apps.Manager.Api.Model; using ModpackUpdater.Apps.Manager.Api.Model;
using ModpackUpdater.Apps.Manager.LangRes; using ModpackUpdater.Apps.Manager.LangRes;
using ModpackUpdater.Apps.Manager.Ui; using ModpackUpdater.Apps.Manager.Ui;
using ModpackUpdater.Apps.Manager.Ui.Models; using ModpackUpdater.Apps.Manager.Ui.Models;
using ModpackUpdater.Apps.Manager.Ui.Models.MainWindow;
using ModpackUpdater.Apps.Manager.Ui.Models.UpdatesCollectorViewMode;
using ModpackUpdater.Manager; using ModpackUpdater.Manager;
using MsBox.Avalonia; using MsBox.Avalonia;
using OfficeOpenXml; using OfficeOpenXml;
@@ -52,11 +55,11 @@ internal static class SharedFunctions
// Collect updates // Collect updates
var result = await AvaloniaFlyoutBase.Show(new UpdatesCollectorView(api.Model.CurrentWorkspace, actions), api.MainWindow); var result = await AvaloniaFlyoutBase.Show(new UpdatesCollectorView(api.Model.CurrentWorkspace, actions), api.MainWindow);
if (result.Result is null || result.CurrentUpdates is null) if (result.Result is not ModUpdates resultUpdates)
return false; return false;
// Collect versions with changes // Collect versions with changes
var updates = result.CurrentUpdates.List.Where(update => update.Origin.SourceTag != update.AvailableVersions[update.NewVersion].Key).ToList(); var updates = resultUpdates.List.Where(update => update.Origin.SourceTag != update.AvailableVersions[update.NewVersion].Key).ToList();
// Path install actions // Path install actions
foreach (var update in updates) foreach (var update in updates)

View File

@@ -15,12 +15,12 @@ internal class CheckAllActionsHealthyFeature : PluginFunction, IPluginFeaturePro
Icon = AppGlobals.Symbols.GetImage(AppSymbols.heart_with_pulse, SymbolSize.Small); Icon = AppGlobals.Symbols.GetImage(AppSymbols.heart_with_pulse, SymbolSize.Small);
} }
protected override object? ExecuteFunction(PluginFunctionParameter? @params) protected override async Task<object?> ExecuteFunctionAsync(PluginFunctionParameter? @params)
{ {
if (@params is not MainApiParameters p || p.Api.Model.CurrentGridRows is null) if (@params is not MainApiParameters p || p.Api.Model.CurrentGridRows is null)
return null; return null;
Task.Run(() => SharedFunctions.CheckActionHealthy(p.Api, [.. p.Api.Model.CurrentGridRows])).Wait(); await SharedFunctions.CheckActionHealthy(p.Api, [.. p.Api.Model.CurrentGridRows]);
return null; return null;
} }

View File

@@ -1,8 +1,8 @@
using ModpackUpdater.Apps.Manager.Api; using ModpackUpdater.Apps.Manager.Api;
using ModpackUpdater.Apps.Manager.Api.Plugins.Params; using ModpackUpdater.Apps.Manager.Api.Plugins.Params;
using ModpackUpdater.Apps.Manager.LangRes; using ModpackUpdater.Apps.Manager.LangRes;
using ModpackUpdater.Apps.Manager.Ui.Models;
using Pilz.Features; using Pilz.Features;
using Pilz.UI.Symbols;
namespace ModpackUpdater.Apps.Manager.Features.Tools; namespace ModpackUpdater.Apps.Manager.Features.Tools;
@@ -12,16 +12,13 @@ internal class ClearDirectLinksFeature : PluginFunction, IPluginFeatureProvider<
public ClearDirectLinksFeature() : base(FeatureTypes.Tools, "origin.cleardirectlinks", FeatureNamesLangRes.ClearDirectLinksFeature) public ClearDirectLinksFeature() : base(FeatureTypes.Tools, "origin.cleardirectlinks", FeatureNamesLangRes.ClearDirectLinksFeature)
{ {
Icon = AppGlobals.Symbols.GetImage(AppSymbols.broom, Pilz.UI.Symbols.SymbolSize.Small); Icon = AppGlobals.Symbols.GetImage(AppSymbols.broom, SymbolSize.Small);
} }
protected override object? ExecuteFunction(PluginFunctionParameter? @params) protected override Task<object?> ExecuteFunctionAsync(PluginFunctionParameter? @params)
{ {
if (@params is not MainApiParameters p || p.Api.Model.CurrentGridRows is null) if (@params is MainApiParameters p && p.Api.Model.CurrentGridRows is not null)
return null;
SharedFunctions.ClearDirectLinks([.. p.Api.Model.CurrentGridRows]); SharedFunctions.ClearDirectLinks([.. p.Api.Model.CurrentGridRows]);
return Task.FromResult<object?>(null);
return null;
} }
} }

View File

@@ -1,7 +1,7 @@
using ModpackUpdater.Apps.Manager.Api; using ModpackUpdater.Apps.Manager.Api;
using ModpackUpdater.Apps.Manager.Api.Plugins.Params; using ModpackUpdater.Apps.Manager.Api.Plugins.Params;
using ModpackUpdater.Apps.Manager.LangRes; using ModpackUpdater.Apps.Manager.LangRes;
using ModpackUpdater.Apps.Manager.Ui.Models; using ModpackUpdater.Apps.Manager.Ui.Models.MainWindow;
using MsBox.Avalonia; using MsBox.Avalonia;
using MsBox.Avalonia.Enums; using MsBox.Avalonia.Enums;
using Pilz.Features; using Pilz.Features;
@@ -18,7 +18,7 @@ internal class GenerateChangelogFeature : PluginFunction, IPluginFeatureProvider
Icon = AppGlobals.Symbols.GetImage(AppSymbols.time_machine, SymbolSize.Small); Icon = AppGlobals.Symbols.GetImage(AppSymbols.time_machine, SymbolSize.Small);
} }
protected override object? ExecuteFunction(PluginFunctionParameter? @params) protected override async Task<object?> ExecuteFunctionAsync(PluginFunctionParameter? @params)
{ {
if (@params is not MainApiParameters p if (@params is not MainApiParameters p
|| p.Api.Model.CurrentWorkspace?.InstallInfos is null || p.Api.Model.CurrentWorkspace?.InstallInfos is null
@@ -30,8 +30,8 @@ internal class GenerateChangelogFeature : PluginFunction, IPluginFeatureProvider
if (string.IsNullOrWhiteSpace(changelog)) if (string.IsNullOrWhiteSpace(changelog))
return null; return null;
p.Api.MainWindow.Clipboard?.SetTextAsync(changelog); await p.Api.MainWindow.Clipboard?.SetTextAsync(changelog);
MessageBoxManager.GetMessageBoxStandard(MsgBoxLangRes.ChangelogCopiedToClipboard_Title, MsgBoxLangRes.ChangelogCopiedToClipboard, ButtonEnum.Ok, MsBox.Avalonia.Enums.Icon.Info).ShowAsPopupAsync(p.Api.MainWindow); await MessageBoxManager.GetMessageBoxStandard(MsgBoxLangRes.ChangelogCopiedToClipboard_Title, MsgBoxLangRes.ChangelogCopiedToClipboard, ButtonEnum.Ok, MsBox.Avalonia.Enums.Icon.Info).ShowAsPopupAsync(p.Api.MainWindow);
return null; return null;
} }

View File

@@ -1,5 +1,4 @@
using Avalonia.Controls; using Avalonia.Controls;
using Avalonia.Platform.Storage;
using ModpackUpdater.Apps.Manager.Api; using ModpackUpdater.Apps.Manager.Api;
using ModpackUpdater.Apps.Manager.Api.Plugins.Params; using ModpackUpdater.Apps.Manager.Api.Plugins.Params;
using ModpackUpdater.Apps.Manager.LangRes; using ModpackUpdater.Apps.Manager.LangRes;
@@ -19,7 +18,7 @@ internal class GenerateModlistAsExcelFeature : PluginFunction, IPluginFeaturePro
Icon = AppGlobals.Symbols.GetImage(AppSymbols.list_view, SymbolSize.Small); Icon = AppGlobals.Symbols.GetImage(AppSymbols.list_view, SymbolSize.Small);
} }
protected override object? ExecuteFunction(PluginFunctionParameter? @params) protected override async Task<object?> ExecuteFunctionAsync(PluginFunctionParameter? @params)
{ {
if (@params is not MainApiParameters p || p.Api.Model.CurrentWorkspace?.InstallInfos is null) if (@params is not MainApiParameters p || p.Api.Model.CurrentWorkspace?.InstallInfos is null)
return null; return null;
@@ -28,16 +27,16 @@ internal class GenerateModlistAsExcelFeature : PluginFunction, IPluginFeaturePro
using var pkg = SharedFunctions.GenerateModlistAsExcel(p.Api.Model.CurrentWorkspace.InstallInfos); using var pkg = SharedFunctions.GenerateModlistAsExcel(p.Api.Model.CurrentWorkspace.InstallInfos);
// Ask for save // Ask for save
var file = Task.Run(() => TopLevel.GetTopLevel(p.Api.MainWindow)!.StorageProvider.SaveFilePickerAsync(new() var file = await TopLevel.GetTopLevel(p.Api.MainWindow)!.StorageProvider.SaveFilePickerAsync(new()
{ {
FileTypeChoices = [MyFilePickerFileTypes.Excel] FileTypeChoices = [MyFilePickerFileTypes.Excel]
})).Result; });
if (file is null) if (file is null)
return null; return null;
// Save file // Save file
pkg.SaveAs(file.Path.AbsolutePath); await pkg.SaveAsAsync(file.Path.AbsolutePath);
MessageBoxManager.GetMessageBoxStandard(MsgBoxLangRes.ModlistGenerated_Title, MsgBoxLangRes.ModlistGenerated, ButtonEnum.Ok, MsBox.Avalonia.Enums.Icon.Info).ShowAsPopupAsync(p.Api.MainWindow); await MessageBoxManager.GetMessageBoxStandard(MsgBoxLangRes.ModlistGenerated_Title, MsgBoxLangRes.ModlistGenerated, ButtonEnum.Ok, MsBox.Avalonia.Enums.Icon.Info).ShowAsPopupAsync(p.Api.MainWindow);
return null; return null;
} }

View File

@@ -17,14 +17,14 @@ internal class GenerateModlistAsMarkdownFeature : PluginFunction, IPluginFeature
Icon = AppGlobals.Symbols.GetImage(AppSymbols.list_view, SymbolSize.Small); Icon = AppGlobals.Symbols.GetImage(AppSymbols.list_view, SymbolSize.Small);
} }
protected override object? ExecuteFunction(PluginFunctionParameter? @params) protected override async Task<object?> ExecuteFunctionAsync(PluginFunctionParameter? @params)
{ {
if (@params is not MainApiParameters p || p.Api.Model.CurrentWorkspace?.InstallInfos is null) if (@params is not MainApiParameters p || p.Api.Model.CurrentWorkspace?.InstallInfos is null)
return null; return null;
p.Api.MainWindow.Clipboard?.SetTextAsync(SharedFunctions.GenerateModlistAsMarkdown(p.Api.Model.CurrentWorkspace.InstallInfos)); p.Api.MainWindow.Clipboard?.SetTextAsync(SharedFunctions.GenerateModlistAsMarkdown(p.Api.Model.CurrentWorkspace.InstallInfos));
MessageBoxManager.GetMessageBoxStandard(MsgBoxLangRes.ModlistCopiedToClipboard_Title, MsgBoxLangRes.ModlistCopiedToClipboard, ButtonEnum.Ok, MsBox.Avalonia.Enums.Icon.Info).ShowAsPopupAsync(p.Api.MainWindow); await MessageBoxManager.GetMessageBoxStandard(MsgBoxLangRes.ModlistCopiedToClipboard_Title, MsgBoxLangRes.ModlistCopiedToClipboard, ButtonEnum.Ok, MsBox.Avalonia.Enums.Icon.Info).ShowAsPopupAsync(p.Api.MainWindow);
return null; return null;
} }

View File

@@ -15,12 +15,12 @@ internal class UpdateDirectLinksFeature : PluginFunction, IPluginFeatureProvider
Icon = AppGlobals.Symbols.GetImage(AppSymbols.renew, SymbolSize.Small); Icon = AppGlobals.Symbols.GetImage(AppSymbols.renew, SymbolSize.Small);
} }
protected override object? ExecuteFunction(PluginFunctionParameter? @params) protected override async Task<object?> ExecuteFunctionAsync(PluginFunctionParameter? @params)
{ {
if (@params is not MainApiParameters p || p.Api.Model.CurrentGridRows is null) if (@params is not MainApiParameters p || p.Api.Model.CurrentGridRows is null)
return null; return null;
Task.Run(() => SharedFunctions.FindNewDirectLinks([.. p.Api.Model.CurrentGridRows])).Wait(); await SharedFunctions.FindNewDirectLinks([.. p.Api.Model.CurrentGridRows]);
return null; return null;
} }

View File

@@ -15,12 +15,12 @@ internal class UpdatesCollectorFeature : PluginFunction, IPluginFeatureProvider<
Icon = AppGlobals.Symbols.GetImage(AppSymbols.search, SymbolSize.Small); Icon = AppGlobals.Symbols.GetImage(AppSymbols.search, SymbolSize.Small);
} }
protected override object? ExecuteFunction(PluginFunctionParameter? @params) protected override async Task<object?> ExecuteFunctionAsync(PluginFunctionParameter? @params)
{ {
if (@params is not MainApiParameters p || p.Api.Model.CurrentWorkspace?.InstallInfos is null) if (@params is not MainApiParameters p || p.Api.Model.CurrentWorkspace?.InstallInfos is null)
return null; return null;
Task.Run(() => SharedFunctions.CollectUpdates(p.Api, [.. p.Api.Model.CurrentWorkspace.InstallInfos.Actions])).Wait(); await SharedFunctions.CollectUpdates(p.Api, [.. p.Api.Model.CurrentWorkspace.InstallInfos.Actions]);
return null; return null;
} }

View File

@@ -25,10 +25,10 @@
<PackageReference Include="Pilz" Version="2.6.1" /> <PackageReference Include="Pilz" Version="2.6.1" />
<PackageReference Include="Pilz.Configuration" Version="3.2.7" /> <PackageReference Include="Pilz.Configuration" Version="3.2.7" />
<PackageReference Include="Pilz.Cryptography" Version="2.1.2" /> <PackageReference Include="Pilz.Cryptography" Version="2.1.2" />
<PackageReference Include="Pilz.Features" Version="2.12.0" /> <PackageReference Include="Pilz.Features" Version="2.13.0" />
<PackageReference Include="Pilz.UI" Version="3.1.4" /> <PackageReference Include="Pilz.UI" Version="3.1.4" />
<PackageReference Include="Pilz.UI.AvaloniaUI" Version="1.2.15" /> <PackageReference Include="Pilz.UI.AvaloniaUI" Version="1.2.17" />
<PackageReference Include="Pilz.UI.AvaloniaUI.Features" Version="1.0.0" /> <PackageReference Include="Pilz.UI.AvaloniaUI.Features" Version="1.0.1" />
<PackageReference Include="Avalonia" Version="11.3.8" /> <PackageReference Include="Avalonia" Version="11.3.8" />
<PackageReference Include="Avalonia.Desktop" Version="11.3.8" /> <PackageReference Include="Avalonia.Desktop" Version="11.3.8" />
<PackageReference Include="Avalonia.Svg" Version="11.3.0" /> <PackageReference Include="Avalonia.Svg" Version="11.3.0" />

View File

@@ -1,547 +0,0 @@
// using ModpackUpdater.Apps.Manager.Api.Model;
// using ModpackUpdater.Apps.Manager.Api.Plugins.Features;
// using ModpackUpdater.Apps.Manager.Api.Plugins.Params;
// using ModpackUpdater.Apps.Manager.LangRes;
// using ModpackUpdater.Apps.Manager.Settings;
// using Pilz.Features;
// using Pilz.UI.Symbols;
// using Pilz.UI.WinForms.Extensions;
// using Pilz.UI.WinForms.Telerik.Features;
// using Telerik.WinControls;
// using Telerik.WinControls.UI;
//
// namespace ModpackUpdater.Apps.Manager.Ui;
//
// public partial class MainForm : RadForm, IMainApi
// {
// private record WorkspaceTag(IWorkspace Workspace, WorkspaceFeature Feature);
//
// private bool loadingMainView;
// private WorkspaceTag? wsInfo;
// private InstallAction? tempAction;
//
// Form IMainApi.MainWindow => this;
// IWorkspace? IMainApi.CurWorkspace => wsInfo?.Workspace;
//
// public IActionSetInfos? CurActionSet => radTreeView_Sets.SelectedNode?.Tag as IActionSetInfos;
//
// public MainForm()
// {
// InitializeComponent();
// }
//
// private RadTreeNode AddUpdateItem(IActionSetInfos infos)
// {
// return AddUpdateItem(infos, radTreeView_Sets.Nodes);
// }
//
// private RadTreeNode AddUpdateItem(IActionSetInfos infos, RadTreeNodeCollection parent)
// {
// var item = CreateUpdateItem(infos);
// parent.Add(item);
// return item;
// }
//
// private RadTreeNode InsertUpdateItem(IActionSetInfos infos)
// {
// var item = CreateUpdateItem(infos);
// var nodeUpdates = radTreeView_Sets.Nodes["updates"];
// nodeUpdates.Nodes.Insert(Math.Min(1, nodeUpdates.Nodes.Count), item);
// return item;
// }
//
// private RadTreeNode CreateUpdateItem(IActionSetInfos infos)
// {
// var item = new RadTreeNode();
// UpdateUpdateItem(item, infos);
// return item;
// }
//
// private void UpdateUpdateItem(RadTreeNode item)
// {
// if (item.Tag is IActionSetInfos infos)
// UpdateUpdateItem(item, infos);
// }
//
// private void SaveActionsSet()
// {
// if (loadingMainView || CurActionSet is not IActionSetInfos infos)
// return;
//
// if (!Version.TryParse(radTextBoxControl_Version.Text.Trim(), out Version? version))
// version = new Version("1.0.0.0");
//
// infos.Version = version;
// infos.IsPublic = radCheckBox_IsPublic.Checked;
//
// UpdateUpdateItem(radTreeView_Sets.SelectedNode);
// }
//
// private void UpdateUpdateItem(RadTreeNode item, IActionSetInfos infos)
// {
// if (item.Tag != infos)
// item.Tag = infos;
//
// if (infos is UpdateInfo)
// item.Text = string.Format(GeneralLangRes.Node_Update, infos.Version?.ToString() ?? "?");
// else if (infos is InstallInfos)
// item.Text = string.Format(GeneralLangRes.Node_Install, infos.Version?.ToString() ?? "?");
// else
// item.Text = infos.Version.ToString();
//
// item.SvgImage = AppGlobals.Symbols.GetSvgImage(infos.IsPublic ? AppSymbols.eye : AppSymbols.invisible, SymbolSize.Small);
// }
//
// public void UpdateItem(IActionSetInfos actionSetInfos)
// {
// RadTreeNode? item = null;
// var nodeUpdates = radTreeView_Sets.Nodes["updates"];
//
// foreach (var iitem in nodeUpdates.Nodes)
// {
// if (item == null && iitem.Value == actionSetInfos)
// item = iitem;
// }
//
// if (item == null)
// InsertUpdateItem(actionSetInfos);
// else if (wsInfo?.Workspace.UpdateInfos != null && !wsInfo.Workspace.UpdateInfos.Updates.Contains(actionSetInfos))
// item.Remove();
// else
// UpdateUpdateItem(item);
// }
//
// public void UpdateItem(InstallAction action)
// {
// foreach (var row in radGridView_Actions.Rows)
// {
// if (row.Tag == action)
// UpdateActionRow(row);
// }
// }
//
// private void LoadMainView()
// {
// loadingMainView = true;
//
// tableLayoutPanel_ActionSet.Visible = false;
// tableLayoutPanel_ActionSetInfo.Visible = false;
//
// if (CurActionSet is IActionSet set)
// {
// if (set is IActionSetInfos infos)
// {
// radTextBoxControl_Version.Text = infos.Version?.ToString();
// radCheckBox_IsPublic.Checked = infos.IsPublic;
// tableLayoutPanel_ActionSetInfo.Visible = true;
// }
// tableLayoutPanel_ActionSet.Visible = true;
// LoadActionSet(set);
// }
//
// loadingMainView = false;
// }
//
// private void LoadActionSet(IActionSet infos)
// {
// radGridView_Actions.BeginUpdate();
// radGridView_Actions.Rows.Clear();
// radGridView_Actions.Columns.Clear();
//
// // Add columns
// radGridView_Actions.Columns.AddRange([
// new GridViewTextBoxColumn
// {
// Name = "id",
// HeaderText = ActionsListLangRes.Col_Id,
// Width = 150,
// IsVisible = infos is not UpdateInfo,
// IsPinned = true,
// },
// new GridViewTextBoxColumn
// {
// Name = "name",
// HeaderText = ActionsListLangRes.Col_Name,
// Width = 150,
// IsVisible = infos is not UpdateInfo,
// },
// new GridViewTextBoxColumn
// {
// Name = "inherit",
// HeaderText = ActionsListLangRes.Col_InheritFrom,
// Width = 150,
// IsVisible = infos is UpdateInfo,
// IsPinned = true,
// },
// new GridViewComboBoxColumn
// {
// Name = "utype",
// HeaderText = ActionsListLangRes.Col_UpdateType,
// Width = 150,
// DataSource = Enum.GetValues<UpdateActionType>(),
// IsVisible = infos is UpdateInfo,
// },
// new GridViewComboBoxColumn
// {
// Name = "side",
// HeaderText = ActionsListLangRes.Col_Side,
// Width = 100,
// DataSource = Enum.GetValues<Side>(),
// },
// new GridViewCheckBoxColumn
// {
// Name = "isextra",
// HeaderText = ActionsListLangRes.Col_IsExtra,
// Width = 50,
// },
// new GridViewCheckBoxColumn
// {
// Name = "iszip",
// HeaderText = ActionsListLangRes.Col_IsZip,
// Width = 50,
// },
// new GridViewCheckBoxColumn
// {
// Name = "isdir",
// HeaderText = ActionsListLangRes.Col_IsDir,
// Width = 50,
// IsVisible = infos is UpdateInfo,
// },
// new GridViewTextBoxColumn
// {
// Name = "destpath",
// HeaderText = ActionsListLangRes.Col_DestPath,
// Width = 250,
// },
// new GridViewComboBoxColumn
// {
// Name = "srctype",
// HeaderText = ActionsListLangRes.Col_SrcType,
// Width = 150,
// DataSource = Enum.GetValues<SourceType>(),
// },
// new GridViewTextBoxColumn
// {
// Name = "srcowner",
// HeaderText = ActionsListLangRes.Col_SrcOwner,
// Width = 150,
// },
// new GridViewTextBoxColumn
// {
// Name = "srcname",
// HeaderText = ActionsListLangRes.Col_SrcName,
// Width = 150,
// },
// new GridViewTextBoxColumn
// {
// Name = "srcregex",
// HeaderText = ActionsListLangRes.Col_SrcRegEx,
// Width = 200,
// },
// new GridViewTextBoxColumn
// {
// Name = "srctag",
// HeaderText = ActionsListLangRes.Col_SrcTag,
// Width = 150,
// },
// new GridViewTextBoxColumn
// {
// Name = "srcurl",
// HeaderText = ActionsListLangRes.Col_SrcUrl,
// Width = 350,
// },
// new GridViewTextBoxColumn
// {
// Name = "zippath",
// HeaderText = ActionsListLangRes.Col_ZipPath,
// Width = 200,
// },
// new GridViewTextBoxColumn
// {
// Name = "srcpath",
// HeaderText = ActionsListLangRes.Col_SrcPath,
// Width = 250,
// IsVisible = infos is UpdateInfo,
// },
// new GridViewTextBoxColumn
// {
// Name = "website",
// HeaderText = ActionsListLangRes.Col_Website,
// Width = 350,
// },
// ]);
//
// // Add rows
// foreach (var action in infos.Actions)
// {
// var row = radGridView_Actions.Rows.AddNew();
// row.Tag = action;
// UpdateActionRow(row);
// }
//
// radGridView_Actions.EndUpdate();
// }
//
// private void UpdateActionRow(GridViewRowInfo row)
// {
// if (row.Tag is not InstallAction action)
// return;
//
// row.Cells["id"].Value = action.Id;
// row.Cells["name"].Value = action.Name;
// row.Cells["iszip"].Value = action.IsZip;
// row.Cells["zippath"].Value = action.ZipPath;
// row.Cells["destpath"].Value = action.DestPath;
// row.Cells["srcurl"].Value = action.SourceUrl;
// row.Cells["srctype"].Value = action.SourceType;
// row.Cells["srcowner"].Value = action.SourceOwner;
// row.Cells["srcname"].Value = action.SourceName;
// row.Cells["srcregex"].Value = action.SourceRegex;
// row.Cells["srctag"].Value = action.SourceTag;
// row.Cells["side"].Value = action.Side;
// row.Cells["isextra"].Value = action.IsExtra;
// row.Cells["website"].Value = action.Website;
//
// if (action is not UpdateAction uaction)
// return;
//
// row.Cells["inherit"].Value = uaction.InheritFrom; // TODO: Find inherit action and put it in here!
// row.Cells["utype"].Value = uaction.Type;
// row.Cells["srcpath"].Value = uaction.SrcPath;
// row.Cells["isdir"].Value = uaction.IsDirectory;
// }
//
// private void Form1_Load(object sender, EventArgs e)
// {
// LoadRecentWorkspaces();
// }
//
// private async void RadMenuItem_OpenNewWorkspace_Click(object? sender, EventArgs e)
// {
// if (sender is RadMenuItem item && item.Tag is WorkspaceFeature feature)
// {
// var ws = wsInfo?.Workspace;
// if (feature.Configure(ws))
// await LoadNewWorkspace(ws, feature);
// }
// }
//
// private async void RadMenuItem_OpenRecentWorkspace_Click(object? sender, EventArgs e)
// {
// if (sender is RadMenuItem item && item.Tag is RecentFilesItemTag tag && tag.Feature.CreateFromConfig(tag.Config) is IWorkspace workspace)
// await LoadNewWorkspace(workspace, tag.Feature);
// }
//
// private async void RadMenuItem_WorkspacePreferences_Click(object sender, EventArgs e)
// {
// if (wsInfo != null)
// {
// var ws = wsInfo.Workspace;
// if (wsInfo.Feature.Configure(ws))
// await LoadNewWorkspace(ws, wsInfo.Feature);
// }
// }
//
// private void RadMenuItem_SaveWorkspace_Click(object sender, EventArgs e)
// {
// wsInfo?.Workspace.Save();
// }
//
// private void RadMenuItem_ToolsItem_Click(object? sender, EventArgs e)
// {
// if (sender is RadMenuItem item && item.Tag is PluginFunction func)
// func.Execute(new MainApiParameters(this));
// }
//
// private void RadTreeView_Sets_SelectedNodeChanged(object sender, RadTreeViewEventArgs e)
// {
// LoadMainView();
// }
//
// private void RadGridView_Actions_CellFormatting(object sender, CellFormattingEventArgs e)
// {
// //var cellElement = e.CellElement;
// //var cellInfo = e.Row.Cells[e.Column.Name];
//
// //if (e.Column.Name == "srctype" && cellInfo?.Value is string sourceTypeStr && Enum.Parse<SourceType>(sourceTypeStr) is SourceType sourceType)
// //{
// // cellElement.SvgImage = sourceType switch
// // {
// // SourceType.DirectLink => AppGlobals.Symbols.GetSvgImage(AppSymbols.link, SymbolSize.Small),
// // SourceType.GitHub => AppGlobals.Symbols.GetSvgImage(AppSymbols.github, SymbolSize.Small),
// // _ => null,
// // };
// // cellElement.DrawImage = cellElement.SvgImage != null;
// // cellElement.TextImageRelation = TextImageRelation.ImageBeforeText;
// // cellElement.ImageAlignment = ContentAlignment.MiddleLeft;
// //}
// //else
// //{
// // cellElement.ResetValue(LightVisualElement.SvgImageProperty, ValueResetFlags.Local);
// // cellElement.ResetValue(LightVisualElement.DrawImageProperty, ValueResetFlags.Local);
// // cellElement.ResetValue(LightVisualElement.TextImageRelationProperty, ValueResetFlags.Local);
// // cellElement.ResetValue(LightVisualElement.ImageAlignmentProperty, ValueResetFlags.Local);
// //}
// }
//
// private void RadGridView_Actions_CellValueChanged(object sender, GridViewCellEventArgs e)
// {
// if (e.Row is null)
// return;
//
// if (e.Row.Tag is not InstallAction action)
// {
// if (CurActionSet is UpdateInfo)
// action = tempAction ??= new UpdateAction();
// else if (CurActionSet is InstallInfos)
// action = tempAction ??= new InstallAction();
// else
// return;
// }
//
// var uaction = action as UpdateAction;
// var newValue = e.Row.Cells[e.Column.Name].Value;
// var colName = e.Column.Name;
//
// if (newValue is bool valueBool)
// {
// switch (colName)
// {
// case "iszip":
// action.IsZip = valueBool;
// break;
// case "isextra":
// action.IsExtra = valueBool;
// break;
// case "isdir":
// if (uaction is not null)
// uaction.IsDirectory = valueBool;
// break;
// }
// }
// else
// {
// var valueStr = newValue as string ?? string.Empty;
// var valueNullStr = valueStr.Nullify();
//
// switch (colName)
// {
// case "id":
// action.Id = valueNullStr;
// break;
// case "name":
// action.Name = valueNullStr;
// break;
// case "zippath":
// action.ZipPath = valueNullStr;
// break;
// case "destpath":
// action.DestPath = valueNullStr;
// break;
// case "srcurl":
// action.SourceUrl = valueNullStr;
// break;
// case "srctype":
// action.SourceType = Enum.Parse<SourceType>(valueStr);
// break;
// case "srcowner":
// action.SourceOwner = valueNullStr;
// break;
// case "srcname":
// action.SourceName = valueNullStr;
// break;
// case "srcregex":
// action.SourceRegex = valueNullStr;
// break;
// case "srctag":
// action.SourceTag = valueNullStr;
// break;
// case "website":
// action.Website = valueNullStr;
// break;
// case "side":
// action.Side = Enum.Parse<Side>(valueStr);
// break;
// case "inherit":
// if (uaction is not null)
// uaction.InheritFrom = valueNullStr;
// break;
// case "utype":
// if (uaction is not null)
// uaction.Type = Enum.Parse<UpdateActionType>(valueStr);
// break;
// case "srcpath":
// if (uaction is not null)
// uaction.SrcPath = valueNullStr;
// break;
// }
// }
// }
//
// private void RadMenuItem_Updates_DropDownOpening(object sender, System.ComponentModel.CancelEventArgs e)
// {
// radMenuItem_RemoveUpdate.Enabled = radTreeView_Sets.SelectedNode?.Tag is UpdateInfo;
// }
//
// private void RadMenuItem_CreateUpdate_Click(object sender, EventArgs e)
// {
// if (wsInfo?.Workspace.UpdateInfos is null)
// return;
//
// var infos = new UpdateInfo
// {
// Version = wsInfo.Workspace.InstallInfos?.Version,
// };
// wsInfo.Workspace.UpdateInfos.Updates.Insert(0, infos);
// InsertUpdateItem(infos);
// }
//
// private void RadMenuItem_RemoveUpdate_Click(object sender, EventArgs e)
// {
// if (radTreeView_Sets.SelectedNode?.Tag is UpdateInfo infos && wsInfo?.Workspace.UpdateInfos is not null
// && RadMessageBox.Show(MsgBoxLangRes.RemoveUpdate, MsgBoxLangRes.RemoveUpdate_Title, MessageBoxButtons.YesNo, RadMessageIcon.Exclamation).IsYes())
// {
// wsInfo.Workspace.UpdateInfos.Updates.Remove(infos);
// radTreeView_Sets.SelectedNode.Remove();
// }
// }
//
// private void RadGridView_Actions_UserAddedRow(object sender, GridViewRowEventArgs e)
// {
// if (tempAction is UpdateAction uaction && CurActionSet is UpdateInfo uinfo)
// uinfo.Actions.Add(uaction);
// else if (tempAction is InstallAction iaction && CurActionSet is InstallInfos iinfo)
// iinfo.Actions.Add(iaction);
// tempAction = null;
// }
//
// private void RadGridView_Actions_UserDeletingRow(object sender, GridViewRowCancelEventArgs e)
// {
// foreach (var row in e.Rows)
// {
// if (row.Tag is UpdateAction uaction && CurActionSet is UpdateInfo uinfo)
// uinfo.Actions.Remove(uaction);
// else if (row.Tag is InstallAction iaction && CurActionSet is InstallInfos iinfo)
// iinfo.Actions.Remove(iaction);
// }
// }
//
// private void RadGridView_Actions_ContextMenuOpening(object sender, ContextMenuOpeningEventArgs e)
// {
// if (e.ContextMenuProvider is GridDataCellElement)
// {
// e.ContextMenu.Items.Add(new RadMenuSeparatorItem());
// PluginFeatureController.Instance.Functions.Get(FeatureTypes.ActionsContextMenu).InsertItemsTo(e.ContextMenu.Items, customClickHandler: RadMenuItem_ToolsItem_Click, insertPrioSplitters: true);
// }
// }
//
// private void RadTextBoxControl1_TextChanged(object sender, EventArgs e)
// {
// SaveActionsSet();
// }
//
// private void RadCheckBox1_ToggleStateChanged(object sender, StateChangedEventArgs args)
// {
// SaveActionsSet();
// }
// }

View File

@@ -7,9 +7,10 @@
xmlns:vm="clr-namespace:ModpackUpdater.Apps.Manager.Ui.Models" xmlns:vm="clr-namespace:ModpackUpdater.Apps.Manager.Ui.Models"
xmlns:pilz="https://git.pilzinsel64.de/pilz-framework/pilz" xmlns:pilz="https://git.pilzinsel64.de/pilz-framework/pilz"
xmlns:symbols="clr-namespace:Pilz.UI.Symbols;assembly=Pilz.UI" xmlns:symbols="clr-namespace:Pilz.UI.Symbols;assembly=Pilz.UI"
xmlns:mainWindow="clr-namespace:ModpackUpdater.Apps.Manager.Ui.Models.MainWindow"
mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450" mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450"
x:Class="ModpackUpdater.Apps.Manager.Ui.MainWindow" x:Class="ModpackUpdater.Apps.Manager.Ui.MainWindow"
x:DataType="vm:MainWindowViewModel" x:DataType="mainWindow:MainWindowViewModel"
Title="Minecraft Modpack Manager" Title="Minecraft Modpack Manager"
WindowState="Maximized" WindowState="Maximized"
Loaded="Window_OnLoaded"> Loaded="Window_OnLoaded">
@@ -106,7 +107,7 @@
<ContentControl.DataTemplates> <ContentControl.DataTemplates>
<DataTemplate <DataTemplate
DataType="vm:ActionSetTreeNode"> DataType="mainWindow:ActionSetTreeNode">
<StackPanel <StackPanel
Orientation="Horizontal"> Orientation="Horizontal">
@@ -142,7 +143,7 @@
</DataTemplate> </DataTemplate>
<DataTemplate <DataTemplate
DataType="vm:MainWindowTreeNode"/> DataType="mainWindow:MainWindowTreeNode"/>
</ContentControl.DataTemplates> </ContentControl.DataTemplates>
</ContentControl> </ContentControl>
@@ -220,7 +221,7 @@
<ComboBox <ComboBox
Grid.Row="2" Grid.Column="1" Grid.Row="2" Grid.Column="1"
x:Name="ComboBoxUpdateActionSourceType" x:Name="ComboBoxUpdateActionSourceType"
ItemsSource="{x:Static vm:MainWindowGridRow.UpdateActionTypes}" ItemsSource="{x:Static mainWindow:MainWindowGridRow.UpdateActionTypes}"
DisplayMemberBinding="{Binding Value}" DisplayMemberBinding="{Binding Value}"
SelectedValueBinding="{Binding Key}" SelectedValueBinding="{Binding Key}"
SelectedValue="{Binding UpdateType}"/> SelectedValue="{Binding UpdateType}"/>
@@ -277,7 +278,7 @@
<ComboBox <ComboBox
Grid.Row="3" Grid.Column="1" Grid.Row="3" Grid.Column="1"
x:Name="ComboBoxInstallActionSide" x:Name="ComboBoxInstallActionSide"
ItemsSource="{x:Static vm:MainWindowGridRow.Sides}" ItemsSource="{x:Static mainWindow:MainWindowGridRow.Sides}"
DisplayMemberBinding="{Binding Value}" DisplayMemberBinding="{Binding Value}"
SelectedValueBinding="{Binding Key}" SelectedValueBinding="{Binding Key}"
SelectedValue="{Binding Side}"/> SelectedValue="{Binding Side}"/>
@@ -341,7 +342,7 @@
<ComboBox <ComboBox
Grid.Row="1" Grid.Column="1" Grid.Row="1" Grid.Column="1"
x:Name="CheckBoxInstallActionSourceType" x:Name="CheckBoxInstallActionSourceType"
ItemsSource="{x:Static vm:MainWindowGridRow.SourceTypes}" ItemsSource="{x:Static mainWindow:MainWindowGridRow.SourceTypes}"
DisplayMemberBinding="{Binding Value}" DisplayMemberBinding="{Binding Value}"
SelectedValueBinding="{Binding Key}" SelectedValueBinding="{Binding Key}"
SelectedValue="{Binding SourceType}"/> SelectedValue="{Binding SourceType}"/>

View File

@@ -7,6 +7,7 @@ using ModpackUpdater.Apps.Manager.Api.Plugins.Features;
using ModpackUpdater.Apps.Manager.Api.Plugins.Params; using ModpackUpdater.Apps.Manager.Api.Plugins.Params;
using ModpackUpdater.Apps.Manager.Settings; using ModpackUpdater.Apps.Manager.Settings;
using ModpackUpdater.Apps.Manager.Ui.Models; using ModpackUpdater.Apps.Manager.Ui.Models;
using ModpackUpdater.Apps.Manager.Ui.Models.MainWindow;
using Pilz.Features; using Pilz.Features;
using Pilz.UI.AvaloniaUI.Features; using Pilz.UI.AvaloniaUI.Features;
using Pilz.UI.Symbols; using Pilz.UI.Symbols;
@@ -129,7 +130,7 @@ public partial class MainWindow : Window, IMainApi
private void MenuItemToolsItem_Click(object? sender, RoutedEventArgs e) private void MenuItemToolsItem_Click(object? sender, RoutedEventArgs e)
{ {
if (sender is MenuItem item && item.Tag is PluginFunction func) if (sender is MenuItem item && item.Tag is PluginFunction func)
func.Execute(new MainApiParameters(this)); func.ExecuteAsync(new MainApiParameters(this));
} }
private void MenuItemCreateUpdate_OnClick(object? sender, RoutedEventArgs e) private void MenuItemCreateUpdate_OnClick(object? sender, RoutedEventArgs e)

View File

@@ -2,7 +2,7 @@ using System.ComponentModel;
using ModpackUpdater.Apps.Manager.Utils; using ModpackUpdater.Apps.Manager.Utils;
using PropertyChanged; using PropertyChanged;
namespace ModpackUpdater.Apps.Manager.Ui.Models; namespace ModpackUpdater.Apps.Manager.Ui.Models.MainWindow;
public class MainWindowGridRow(InstallAction action, IActionSet baseActions) : INotifyPropertyChanged public class MainWindowGridRow(InstallAction action, IActionSet baseActions) : INotifyPropertyChanged
{ {

View File

@@ -1,6 +1,6 @@
using ModpackUpdater.Apps.Manager.Api.Model; using ModpackUpdater.Apps.Manager.Api.Model;
using ModpackUpdater.Apps.Manager.Api.Plugins.Features; using ModpackUpdater.Apps.Manager.Api.Plugins.Features;
namespace ModpackUpdater.Apps.Manager.Ui.Models; namespace ModpackUpdater.Apps.Manager.Ui.Models.MainWindow;
public record class MainWindowRecentFilesItem(WorkspaceConfig Config, WorkspaceFeature Feature); public record class MainWindowRecentFilesItem(WorkspaceConfig Config, WorkspaceFeature Feature);

View File

@@ -4,7 +4,7 @@ using System.Runtime.CompilerServices;
using Avalonia.Media; using Avalonia.Media;
using PropertyChanged; using PropertyChanged;
namespace ModpackUpdater.Apps.Manager.Ui.Models; namespace ModpackUpdater.Apps.Manager.Ui.Models.MainWindow;
public abstract class MainWindowTreeNode : INotifyPropertyChanged public abstract class MainWindowTreeNode : INotifyPropertyChanged
{ {

View File

@@ -1,11 +1,9 @@
using System.Collections.ObjectModel; using System.Collections.ObjectModel;
using System.ComponentModel; using System.ComponentModel;
using System.Runtime.CompilerServices;
using Avalonia.Controls;
using ModpackUpdater.Apps.Manager.Api.Model; using ModpackUpdater.Apps.Manager.Api.Model;
using PropertyChanged; using PropertyChanged;
namespace ModpackUpdater.Apps.Manager.Ui.Models; namespace ModpackUpdater.Apps.Manager.Ui.Models.MainWindow;
public class MainWindowViewModel : INotifyPropertyChanged public class MainWindowViewModel : INotifyPropertyChanged
{ {

View File

@@ -0,0 +1,13 @@
namespace ModpackUpdater.Apps.Manager.Ui.Models.UpdatesCollectorViewMode;
public record ModUpdateInfo(KeyValuePair<string, string>[] AvailableVersions, InstallAction Origin)
{
public int NewVersion { get; set; }
public bool Visible { get; set; }
public IEnumerable<string> DisplayVersions { get; } = AvailableVersions.Select(n =>
{
if (string.IsNullOrWhiteSpace(n.Value) || n.Value == n.Key)
return n.Key;
return $"{n.Value} ({n.Value})";
});
}

View File

@@ -0,0 +1,3 @@
namespace ModpackUpdater.Apps.Manager.Ui.Models.UpdatesCollectorViewMode;
public record ModUpdates(IList<ModUpdateInfo> List);

View File

@@ -0,0 +1,18 @@
using System.Collections.ObjectModel;
using System.ComponentModel;
using PropertyChanged;
namespace ModpackUpdater.Apps.Manager.Ui.Models.UpdatesCollectorViewMode;
public class UpdatesCollectorViewModel : INotifyPropertyChanged
{
public event PropertyChangedEventHandler? PropertyChanged;
public bool ProgressVisible { get; set; }
public double ProgressMaxValue { get; set; }
public double ProgressValue { get; set; }
[DependsOn(nameof(ProgressValue), nameof(ProgressMaxValue))]
public string? ProgressText => $"{Math.Round(ProgressValue / ProgressMaxValue * 100)}%";
public string? SearchText { get; set; }
public ObservableCollection<ModUpdateInfo> Updates { get; } = [];
}

View File

@@ -4,14 +4,14 @@
xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:dialogs="https://git.pilzinsel64.de/pilz-framework/pilz" xmlns:dialogs="https://git.pilzinsel64.de/pilz-framework/pilz"
xmlns:local="clr-namespace:ModpackUpdater.Apps.Manager.Ui" xmlns:updatesCollectorViewMode="clr-namespace:ModpackUpdater.Apps.Manager.Ui.Models.UpdatesCollectorViewMode"
mc:Ignorable="d" mc:Ignorable="d"
d:DesignWidth="600" d:DesignWidth="600"
d:DesignHeight="450" d:DesignHeight="450"
Width="1000" Width="800"
Height="800" Height="600"
x:Class="ModpackUpdater.Apps.Manager.Ui.UpdatesCollectorView" x:Class="ModpackUpdater.Apps.Manager.Ui.UpdatesCollectorView"
Title="UpdatesCollectorWindow" x:DataType="updatesCollectorViewMode:UpdatesCollectorViewModel"
Loaded="Me_OnLoaded"> Loaded="Me_OnLoaded">
<!-- Main --> <!-- Main -->
@@ -23,7 +23,6 @@
<!-- TextBox: Search --> <!-- TextBox: Search -->
<TextBox <TextBox
x:Name="TextBoxSearch"
Grid.Row="0" Grid.Row="0"
Watermark="Search" Watermark="Search"
TextChanged="TextBoxSearch_OnTextChanged"/> TextChanged="TextBoxSearch_OnTextChanged"/>
@@ -33,11 +32,10 @@
Grid.Row="1"> Grid.Row="1">
<ItemsControl <ItemsControl
x:Name="ItemsControlUpdates"> ItemsSource="{Binding Updates}">
<ItemsControl.ItemTemplate> <ItemsControl.ItemTemplate>
<DataTemplate <DataTemplate>
DataType="{x:Type local:UpdatesCollectorView+ModUpdateInfo}">
<Grid <Grid
ColumnDefinitions="20*,20*,20*,Auto" ColumnDefinitions="20*,20*,20*,Auto"
@@ -83,19 +81,21 @@
<dialogs:AvaloniaFlyoutBase.FooterContent> <dialogs:AvaloniaFlyoutBase.FooterContent>
<Panel <Panel
HorizontalAlignment="Stretch" HorizontalAlignment="Stretch"
VerticalAlignment="Stretch"> VerticalAlignment="Stretch"
IsVisible="{Binding ProgressVisible}">
<!-- ProgressBar: Status --> <!-- ProgressBar: Status -->
<ProgressBar <ProgressBar
x:Name="ProgressBarStatus"
HorizontalAlignment="Stretch" HorizontalAlignment="Stretch"
VerticalAlignment="Stretch"/> VerticalAlignment="Stretch"
Maximum="{Binding ProgressMaxValue}"
Value="{Binding ProgressValue}"/>
<!-- TextBox: Status --> <!-- TextBox: Status -->
<TextBlock <TextBlock
x:Name="TextBlockStatus" HorizontalAlignment="Center"
HorizontalAlignment="Stretch" VerticalAlignment="Center"
VerticalAlignment="Stretch"/> Text="{Binding ProgressText}"/>
</Panel> </Panel>
</dialogs:AvaloniaFlyoutBase.FooterContent> </dialogs:AvaloniaFlyoutBase.FooterContent>
</dialogs:AvaloniaFlyoutBase> </dialogs:AvaloniaFlyoutBase>

View File

@@ -1,8 +1,7 @@
using System.Collections.ObjectModel;
using System.ComponentModel;
using Avalonia.Controls; using Avalonia.Controls;
using Avalonia.Interactivity; using Avalonia.Interactivity;
using ModpackUpdater.Apps.Manager.Api.Model; using ModpackUpdater.Apps.Manager.Api.Model;
using ModpackUpdater.Apps.Manager.Ui.Models.UpdatesCollectorViewMode;
using ModpackUpdater.Manager; using ModpackUpdater.Manager;
using Pilz.UI.AvaloniaUI.Dialogs; using Pilz.UI.AvaloniaUI.Dialogs;
@@ -10,85 +9,65 @@ namespace ModpackUpdater.Apps.Manager.Ui;
public partial class UpdatesCollectorView : AvaloniaFlyoutBase public partial class UpdatesCollectorView : AvaloniaFlyoutBase
{ {
public record ModUpdateInfo(KeyValuePair<string, string>[] AvailableVersions, InstallAction Origin)
{
public int NewVersion { get; set; }
public IEnumerable<string> DisplayVersions { get; } = AvailableVersions.Select(n =>
{
if (string.IsNullOrWhiteSpace(n.Value) || n.Value == n.Key)
return n.Key;
return $"{n.Value} ({n.Value})";
});
}
public record ModUpdates(IList<ModUpdateInfo> List);
private readonly IWorkspace workspace; private readonly IWorkspace workspace;
private readonly ModpackFactory factory = new(); private readonly ModpackFactory factory = new();
private readonly InstallAction[] actions; private readonly InstallAction[] actions;
public ModUpdates? CurrentUpdates { get; private set; } public UpdatesCollectorViewModel Model { get; } = new();
public UpdatesCollectorView(IWorkspace workspace, params InstallAction[] actions) public UpdatesCollectorView(IWorkspace workspace, params InstallAction[] actions)
{ {
this.workspace = workspace; this.workspace = workspace;
this.actions = actions; this.actions = actions;
DataContext = Model;
InitializeComponent(); InitializeComponent();
} }
private async Task<ModUpdates> FindUpdates() private async Task FindUpdates()
{ {
var list = new ObservableCollection<ModUpdateInfo>(); Model.ProgressVisible = true;
Model.ProgressMaxValue = actions.Length;
ProgressBarStatus.Maximum = actions.Length;
foreach (var action in actions) foreach (var action in actions)
{ {
var updates = await factory.FindUpdates(action, workspace.ModpackConfig?.MinecraftVersion, workspace.ModpackConfig?.ModLoader ?? ModLoader.Any); var updates = await factory.FindUpdates(action, workspace.ModpackConfig?.MinecraftVersion, workspace.ModpackConfig?.ModLoader ?? ModLoader.Any);
ProgressBarStatus.Value += 1; Model.ProgressValue += 1;
TextBlockStatus.Text = $"{Math.Round(ProgressBarStatus.Value / ProgressBarStatus.Maximum * 100)}";
if (updates == null || updates.Length == 0 || updates[0].Value == action.SourceTag) if (updates == null || updates.Length == 0 || updates[0].Value == action.SourceTag)
continue; continue;
list.Add(new(updates, action)); Model.Updates.Add(new(updates, action));
if (IsClosed)
break;
} }
return new ModUpdates(list); Model.ProgressVisible = false;
} }
protected override void OnLoadData(DoWorkEventArgs e) protected override object GetResult()
{ {
e.Result = Task.Run(FindUpdates).Result; return new ModUpdates(Model.Updates);
} }
protected override void OnLoadDataCompleted(RunWorkerCompletedEventArgs e) private async void Me_OnLoaded(object? sender, RoutedEventArgs e)
{ {
if (e.Result is ModUpdates updates) await FindUpdates();
ItemsControlUpdates.ItemsSource = (CurrentUpdates = updates).List;
}
private void Me_OnLoaded(object? sender, RoutedEventArgs e)
{
LoadData();
} }
private void TextBoxSearch_OnTextChanged(object? sender, TextChangedEventArgs e) private void TextBoxSearch_OnTextChanged(object? sender, TextChangedEventArgs e)
{ {
var searchString = TextBoxSearch.Text?.Trim().ToLowerInvariant(); var searchString = Model.SearchText?.Trim().ToLowerInvariant();
var hasNoSearch = string.IsNullOrWhiteSpace(searchString); var hasNoSearch = string.IsNullOrWhiteSpace(searchString);
foreach (var item in ItemsControlUpdates.Items.OfType<Grid>()) foreach (var item in Model.Updates)
{ item.Visible = hasNoSearch || (item.Origin.Name != null && item.Origin.Name.Contains(searchString!, StringComparison.InvariantCultureIgnoreCase));
item.IsVisible = hasNoSearch || (item.Name != null && item.Name.Contains(searchString!, StringComparison.InvariantCultureIgnoreCase));
}
} }
private void ButtonRemoveUpdate_Click(object? sender, RoutedEventArgs e) private void ButtonRemoveUpdate_Click(object? sender, RoutedEventArgs e)
{ {
if (sender is Button button && button.DataContext is ModUpdateInfo update) if (sender is Button button && button.DataContext is ModUpdateInfo update)
CurrentUpdates?.List.Remove(update); Model.Updates.Remove(update);
} }
} }

View File

@@ -1,4 +1,5 @@
using Pilz.UI.AvaloniaUI.Symbols; using Pilz.UI.AvaloniaUI.Dialogs;
using Pilz.UI.AvaloniaUI.Symbols;
using Pilz.UI.Symbols; using Pilz.UI.Symbols;
namespace ModpackUpdater.Apps; namespace ModpackUpdater.Apps;
@@ -10,5 +11,7 @@ public static class AppGlobals
public static void Initialize() public static void Initialize()
{ {
SymbolGlobals.DefaultImageSmallSize = 17; SymbolGlobals.DefaultImageSmallSize = 17;
AvaloniaFlyoutBase.DefaultConfirmImage = Symbols.GetImageSource(AppSymbols.checkmark);
AvaloniaFlyoutBase.DefaultCancelImage = Symbols.GetImageSource(AppSymbols.cancel);
} }
} }

View File

@@ -17,7 +17,7 @@
<ItemGroup> <ItemGroup>
<PackageReference Include="Pilz" Version="2.6.1" /> <PackageReference Include="Pilz" Version="2.6.1" />
<PackageReference Include="Pilz.UI" Version="3.1.4" /> <PackageReference Include="Pilz.UI" Version="3.1.4" />
<PackageReference Include="Pilz.UI.AvaloniaUI" Version="1.2.15" /> <PackageReference Include="Pilz.UI.AvaloniaUI" Version="1.2.17" />
<PackageReference Include="Avalonia" Version="11.3.8" /> <PackageReference Include="Avalonia" Version="11.3.8" />
<PackageReference Include="Avalonia.Desktop" Version="11.3.8" /> <PackageReference Include="Avalonia.Desktop" Version="11.3.8" />
<PackageReference Include="Avalonia.Svg" Version="11.3.0" /> <PackageReference Include="Avalonia.Svg" Version="11.3.0" />