Compare commits

...

16 commits

Author SHA1 Message Date
Nikolay Kuznetsov f905428238
Merge pull request #23 from DubyaDude/master
Move to api/v1 + additional QOL changes
2022-06-16 20:37:22 +02:00
Usman Shafiq b74c421bbb Added IsRetired (ApprovalStatus 3) 2022-06-15 18:15:32 -04:00
Usman Shafiq 71efc3990f Fixed download file name 2022-06-12 02:35:56 -04:00
Usman Shafiq d57e730baa Version bump 2022-06-12 00:57:50 -04:00
Usman Shafiq 2adb976b21 On Agree Removed Windows Notif + Move To Mods. Search bar enabled by default + made bigger 2022-06-12 00:22:23 -04:00
Usman Shafiq 59cd085130 Moved to api/v1 + Moved Broken to bottom 2022-06-12 00:04:03 -04:00
Nikolay Kuznetsov 992480facc Handle missing directories for deleting all mods 2021-07-16 01:59:08 +02:00
Nikolay Kuznetsov 8160521d10 Add a bit of exception handling to headpats/hugs buttons 2021-07-16 01:59:08 +02:00
Nikolay Kuznetsov a6321a9ecc Let SemVer handle four-digit version numbers 2021-07-16 01:59:08 +02:00
Nikolay Kuznetsov 88c987d714 Bump version again 2021-07-16 01:59:08 +02:00
Nikolay Kuznetsov 610098dcbf
Fix formatting 2021-07-15 22:45:05 +02:00
Nikolay Kuznetsov ec8cd210f7 Bump version 2021-07-15 19:43:24 +02:00
Nikolay Kuznetsov 66d2b41de8 Update default mods 2021-07-15 19:42:36 +02:00
Nikolay Kuznetsov ed27510ccc Update hardcoded categories for new mods 2021-07-15 19:42:15 +02:00
Nikolay Kuznetsov 0f60e68c02 Use latest ML installer instead of 0.3.0 2021-07-15 19:41:57 +02:00
Nikolay Kuznetsov f250bb893c Fix hyperlinks in mod info page 2021-05-29 22:02:39 +02:00
14 changed files with 143 additions and 64 deletions

View file

@ -1,4 +1,4 @@
#[Download here!](https://github.com/knah/VRCMelonAssistant/releases/latest)
# [Download here!](https://github.com/knah/VRCMelonAssistant/releases/latest)
VRChat Melon Assistant is a PC mod installer for VRChat. It uses mods published in [VRChat Modding Group Discord](https://discord.gg/rCqKSvR).
It's a (very stripped down) fork of [Assistant's Mod Assistant](https://github.com/Assistant/ModAssistant), a mod manager for Beat Saber.

View file

@ -6,8 +6,8 @@ namespace VRCMelonAssistant
{
private static readonly Dictionary<string, List<string>> CategoryContents = new()
{
{"Safety & Security", new() {"Advanced Safety", "Finitizer", "True Shader Anticrash", "Safety-Presets"}},
{"Core mods and libraries", new() {"UI Expansion Kit", "ActionMenuApi", "VRCModUpdater.Loader"}},
{"Safety & Security", new() {"Advanced Safety", "Finitizer", "True Shader Anticrash", "Safety-Presets", "Final IK Sanity"}},
{"Core mods and libraries", new() {"UI Expansion Kit", "ActionMenuApi", "VRCModUpdater.Loader", "VRChatUtilityKit"}},
{"All-in-one mods", new() {"emmVRCLoader"}},
{"Camera mods", new() {
"CameraMinus", "DesktopCamera", "BetterSteadycam", "ITR's Melon Cameras", "CameraResChanger",
@ -15,16 +15,17 @@ namespace VRCMelonAssistant
}},
{"Performance & Fidelity", new() {
"Core Limiter", "MirrorResolutionUnlimiter", "AvatarHider", "Runtime Graphics Settings",
"GamePriority", "FrameFocus", "ClearVRAM", "NoPerformanceStats"
"GamePriority", "FrameFocus", "ClearVRAM", "NoPerformanceStats", "Turbones"
}},
{"Utilities & Tweaks", new() {
"ReloadAvatars", "KeyboardPaste", "No Outlines", "UnmuteSound", "SparkleBeGone",
"BTKSAImmersiveHud", "OGTrustRanks", "ToggleMicIcon", "Friends+ home",
"MicSensitivity", "CloningBeGone", "ToggleFullScreen", "View Point Tweaker",
"SettingsRestart", "SmallUserVolume", "TeleportCameraToYou",
"BetterPortalPlacement"
"BetterPortalPlacement", "BetterDirections", "ChairExitController",
"Panic Button Rework", "SelectYourself", "Trust Color Changer", "Voice Falloff Override"
}},
{"Hardware support", new() {"LeapMotionExtension", "ThumbParams", "VRCFaceTracking", "VRCPimaxEyeTracker"}},
{"Hardware support", new() {"LeapMotionExtension", "ThumbParams", "VRCFaceTracking", "VRCPimaxEyeTracker", "VRCBhapticsIntegration"}},
{"Dynamic bones", new() {
"ImmersiveTouch", "Dynamic Bones Safety", "MultiplayerDynamicBonesMod", "Multiplayer Dynamic Bones",
}},
@ -36,12 +37,14 @@ namespace VRCMelonAssistant
"IKTweaks", "JoinNotifier", "FBT Saver", "BTKSANameplateMod", "AdvancedInvites", "VRCVideoLibrary",
"BTKSASelfPortrait", "OldMate", "BetterLoadingScreen", "Loading Screen Pictures", "FavCat",
"ActionMenuUtils", "WorldPredownload", "AskToPortal", "Headlight", "ITR's Player Tracer",
"InstanceHistory", "PortableMirrorMod", "VRCBonesController"
"InstanceHistory", "PortableMirrorMod", "VRCBonesController", "CalibrationLinesVisualizer",
"ITR's Collider Mod", "RememberMe", "TriggerESP"
}},
{"UI mods", new() {
"Particle and DynBone limiter settings UI", "CalibrateConfirm", "Emoji Page Buttons",
"UserInfoExtensions", "MLConsoleViewer", "OwO Mod", "ActiveBackground", "PlayerList", "ComfyVRMenu",
"DiscordMute", "MicToggle", "VRCPlusPet"
"DiscordMute", "MicToggle", "VRCPlusPet", "AMMusic", "Friend Notes", "GestureIndicator",
"NameplateStats", "PreviewScroller", "ProPlates", "QuickMenuVolume", "ToggleUIStickers"
}},
{"Movement", new() {
"TeleporterVR", "ImmobilizePlayerMod", "TrackingRotator", "OculusPlayspaceMover",

View file

@ -46,7 +46,7 @@ namespace VRCMelonAssistant
{
MainWindow.Instance.MainText = $"{(string) App.Current.FindResource("Mods:DownloadingMelonLoader")}...";
using var installerZip = await DownloadFileToMemory("https://github.com/LavaGang/MelonLoader/releases/download/v0.3.0/MelonLoader.x64.zip");
using var installerZip = await DownloadFileToMemory("https://github.com/LavaGang/MelonLoader/releases/latest/download/MelonLoader.x64.zip");
using var zipReader = new ZipArchive(installerZip, ZipArchiveMode.Read);
MainWindow.Instance.MainText = $"{(string) App.Current.FindResource("Mods:UnpackingMelonLoader")}...";
@ -80,7 +80,7 @@ namespace VRCMelonAssistant
public static async Task InstallMod(Mod mod)
{
string downloadLink = mod.versions[0].downloadlink;
string downloadLink = mod.versions[0].downloadLink;
if (string.IsNullOrEmpty(downloadLink))
{
@ -90,22 +90,28 @@ namespace VRCMelonAssistant
if (mod.installedFilePath != null)
File.Delete(mod.installedFilePath);
var modUri = new Uri(downloadLink);
var targetFilePath = Path.Combine(App.VRChatInstallDirectory, mod.versions[0].IsPlugin ? "Plugins" : "Mods",
mod.versions[0].IsBroken ? "Broken" : "", modUri.Segments.Last());
string targetFilePath = "";
Directory.CreateDirectory(Path.GetDirectoryName(targetFilePath));
using (Stream stream = await DownloadFileToMemory(downloadLink))
using (var resp = await Http.HttpClient.GetAsync(downloadLink))
{
var stream = new MemoryStream();
await resp.Content.CopyToAsync(stream);
stream.Position = 0;
targetFilePath = Path.Combine(App.VRChatInstallDirectory, mod.versions[0].IsPlugin ? "Plugins" : "Mods",
mod.versions[0].IsBroken ? "Broken" : (mod.versions[0].IsRetired ? "Retired" : ""), resp.RequestMessage.RequestUri.Segments.Last());
Directory.CreateDirectory(Path.GetDirectoryName(targetFilePath));
using var targetFile = File.OpenWrite(targetFilePath);
await stream.CopyToAsync(targetFile);
}
mod.ListItem.IsInstalled = true;
mod.installedFilePath = targetFilePath;
mod.ListItem.InstalledVersion = mod.versions[0].modversion;
mod.ListItem.InstalledVersion = mod.versions[0].modVersion;
mod.ListItem.InstalledModInfo = mod;
}
}

View file

@ -7,7 +7,7 @@ namespace VRCMelonAssistant
public class Mod
{
public int _id;
public string uploaddate;
public string uploadDate;
public string category;
public string[] aliases;
public ModVersion[] versions;
@ -15,25 +15,27 @@ namespace VRCMelonAssistant
public string installedFilePath;
public string installedVersion;
public bool installedInBrokenDir;
public bool installedInRetiredDir;
public class ModVersion
{
public int _version;
public string name;
public string modversion;
public string modtype;
public string modVersion;
public string modType;
public string author;
public string description;
public string downloadlink;
public string sourcelink;
public string downloadLink;
public string sourceLink;
public string hash;
public string updatedate;
public string vrchatversion;
public string loaderversion;
public string updateDate;
public string vrchatVersion;
public string loaderVersion;
public int approvalStatus;
public bool IsBroken => approvalStatus == 2;
public bool IsPlugin => modtype.Equals("plugin", StringComparison.InvariantCultureIgnoreCase);
public bool IsRetired => approvalStatus == 3;
public bool IsPlugin => modType.Equals("plugin", StringComparison.InvariantCultureIgnoreCase);
}
}
}

View file

@ -25,7 +25,7 @@ namespace VRCMelonAssistant
public class Constants
{
public const string VRChatAppId = "438100";
public const string VRCMGModsJson = "https://api.vrcmg.com/v0/mods.json";
public const string VRCMGModsJson = "https://api.vrcmg.com/v1/mods";
public const string WeebCDNAPIURL = "https://pat.assistant.moe/api/v1.0/";
public const string MD5Spacer = " ";
public static readonly char[] IllegalCharacters = new char[]

View file

@ -46,6 +46,7 @@ namespace VRCMelonAssistant.Libs
new Regex(@"^(?<major>\d+)" +
@"(?>\.(?<minor>\d+))?" +
@"(?>\.(?<patch>\d+))?" +
@"(?>\.(?<extra>\d+))?" +
@"(?>\-(?<pre>[0-9A-Za-z\-\.]+))?" +
@"(?>\+(?<build>[0-9A-Za-z\-\.]+))?$",
#if NETSTANDARD
@ -82,11 +83,12 @@ namespace VRCMelonAssistant.Libs
/// <param name="patch">The patch version.</param>
/// <param name="prerelease">The prerelease version (e.g. "alpha").</param>
/// <param name="build">The build metadata (e.g. "nightly.232").</param>
public SemVersion(int major, int minor = 0, int patch = 0, string prerelease = "", string build = "")
public SemVersion(int major, int minor = 0, int patch = 0, int extra = 0, string prerelease = "", string build = "")
{
Major = major;
Minor = minor;
Patch = patch;
Extra = extra;
Prerelease = prerelease ?? "";
Build = build ?? "";
@ -151,10 +153,17 @@ namespace VRCMelonAssistant.Libs
else if (strict)
throw new InvalidOperationException("Invalid version (no patch version given in strict mode)");
var extraMatch = match.Groups["extra"];
int extra = 0;
if (extraMatch.Success)
extra = int.Parse(extraMatch.Value, CultureInfo.InvariantCulture);
var prerelease = match.Groups["pre"].Value;
var build = match.Groups["build"].Value;
return new SemVersion(major, minor, patch, prerelease, build);
return new SemVersion(major, minor, patch, extra, prerelease, build);
}
/// <summary>
@ -197,10 +206,18 @@ namespace VRCMelonAssistant.Libs
}
else if (strict) return false;
var extraMatch = match.Groups["extra"];
int extra = 0;
if (extraMatch.Success)
{
if (!int.TryParse(extraMatch.Value, NumberStyles.Integer, CultureInfo.InvariantCulture, out extra))
return false;
}
var prerelease = match.Groups["pre"].Value;
var build = match.Groups["build"].Value;
semver = new SemVersion(major, minor, patch, prerelease, build);
semver = new SemVersion(major, minor, patch, extra, prerelease, build);
return true;
}
@ -248,13 +265,14 @@ namespace VRCMelonAssistant.Libs
/// To change only the patch version:
/// <code>version.Change(patch: 4)</code>
/// </example>
public SemVersion Change(int? major = null, int? minor = null, int? patch = null,
public SemVersion Change(int? major = null, int? minor = null, int? patch = null, int? extra = null,
string prerelease = null, string build = null)
{
return new SemVersion(
major ?? Major,
minor ?? Minor,
patch ?? Patch,
extra ?? Extra,
prerelease ?? Prerelease,
build ?? Build);
}
@ -283,6 +301,11 @@ namespace VRCMelonAssistant.Libs
/// </value>
public int Patch { get; }
/// <summary>
/// Handles the fourth number present in assembly versions
/// </summary>
public int Extra { get; }
/// <summary>
/// Gets the prerelease version.
/// </summary>
@ -316,6 +339,12 @@ namespace VRCMelonAssistant.Libs
version.Append(Minor);
version.Append('.');
version.Append(Patch);
if (Extra != 0)
{
version.Append('.');
version.Append(Extra);
}
if (Prerelease.Length > 0)
{
version.Append('-');
@ -409,6 +438,9 @@ namespace VRCMelonAssistant.Libs
r = Patch.CompareTo(other.Patch);
if (r != 0) return r;
r = Extra.CompareTo(other.Extra);
if (r != 0) return r;
return CompareComponent(Prerelease, other.Prerelease, true);
}

View file

@ -103,7 +103,7 @@ namespace VRCMelonAssistant
InstallButton.IsEnabled = false;
}
private async Task ShowModsPage()
public async Task ShowModsPage()
{
void OpenModsPage()
{

View file

@ -1,4 +1,4 @@
using System.Linq;
using System;
using System.Windows;
using System.Windows.Documents;
@ -18,29 +18,30 @@ namespace VRCMelonAssistant
ModDescription.Text = mod.versions[0].description ?? (string) FindResource("ModInfoWindow:NoDescription");
ModName.Text = mod.versions[0].name;
ModAuthor.Text = string.Format((string) FindResource("ModInfoWindow:Author"), mod.versions[0].author ?? FindResource("ModInfoWindow:NoAuthor"));
ModVersion.Text = mod.versions[0].modversion;
ModVersion.Text = mod.versions[0].modVersion;
var dlLink = mod.versions[0].downloadlink;
var dlLink = mod.versions[0].downloadLink;
DownloadLink.Text = (string) FindResource("ModInfoWindow:DownloadLink");
DownloadLink.Inlines.Add(new Run(" "));
if (dlLink?.StartsWith("http") == true)
DownloadLink.Inlines.Add(WrapNavigator(new Hyperlink(new Run(dlLink))));
DownloadLink.Inlines.Add(CreateHyperlink(dlLink));
else
DownloadLink.Inlines.Add(new Run(dlLink));
var srcLink = mod.versions[0].sourcelink;
var srcLink = mod.versions[0].sourceLink;
SourceCodeLink.Text = (string) FindResource("ModInfoWindow:SourceCodeLink");
SourceCodeLink.Inlines.Add(new Run(" "));
if (srcLink?.StartsWith("http") == true)
SourceCodeLink.Inlines.Add(WrapNavigator(new Hyperlink(new Run(srcLink))));
SourceCodeLink.Inlines.Add(CreateHyperlink(srcLink));
else
SourceCodeLink.Inlines.Add(new Run(srcLink));
InternalIds.Text = string.Format((string) FindResource("ModInfoWindow:InternalIds"), mod._id, mod.versions[0]._version);
}
private static Hyperlink WrapNavigator(Hyperlink link)
private static Hyperlink CreateHyperlink(string uri)
{
var link = new Hyperlink(new Run(uri)) {NavigateUri = new Uri(uri)};
link.RequestNavigate += HyperlinkExtensions.Hyperlink_RequestNavigate;
return link;
}

View file

@ -1,3 +1,4 @@
using System;
using System.Diagnostics;
using System.Threading.Tasks;
using System.Windows;
@ -50,12 +51,32 @@ namespace VRCMelonAssistant.Pages
private async Task HeadPat()
{
PatImage.Load(await WeebCDN("pats"));
try
{
PatImage.Load(await WeebCDN("pats"));
}
catch (Exception ex)
{
Application.Current.Dispatcher.Invoke(() =>
{
Utils.ShowErrorMessageBox("Oops! Can't get headpats right now!", ex);
});
}
}
private async Task Hug()
{
HugImage.Load(await WeebCDN("hugs"));
try
{
HugImage.Load(await WeebCDN("hugs"));
}
catch (Exception ex)
{
Application.Current.Dispatcher.Invoke(() =>
{
Utils.ShowErrorMessageBox("Oops! Can't get hugs right now!", ex);
});
}
}
}
}

View file

@ -37,10 +37,11 @@ namespace VRCMelonAssistant.Pages
MainWindow.Instance.ModsButton.IsEnabled = true;
string text = (string) FindResource("Intro:ModsTabEnabled");
Utils.SendNotify(text);
MainWindow.Instance.MainText = text;
Properties.Settings.Default.Agreed = true;
Properties.Settings.Default.Save();
MainWindow.Instance.ShowModsPage().NoAwait();
}
}
}

View file

@ -28,7 +28,7 @@
<TextBlock
Name="SearchText"
Grid.Row="0"
Height="0"
Height="20"
Padding="5,0,0,0"
Panel.ZIndex="1"
Background="{DynamicResource BottomStatusBarBackground}"
@ -37,7 +37,7 @@
<TextBox
Name="SearchBar"
Grid.Row="0"
Height="0"
Height="20"
Margin="0,-1,0,0"
Padding="3,1,0,0"
Panel.ZIndex="2"

View file

@ -31,10 +31,11 @@ namespace VRCMelonAssistant.Pages
public static Mods Instance = new Mods();
private static readonly ModListItem.CategoryInfo BrokenCategory = new("Broken", "These mods were broken by a game update. They will be temporarily removed and restored once they are updated for the current game version");
private static readonly ModListItem.CategoryInfo RetiredCategory = new("Retired", "These mods are either no longer needed due to VRChat updates or are no longer being maintained");
private static readonly ModListItem.CategoryInfo UncategorizedCategory = new("Uncategorized", "Mods without a category assigned");
private static readonly ModListItem.CategoryInfo UnknownCategory = new("Unknown/Unverified", "Mods not coming from VRCMG. Potentially dangerous.");
public List<string> DefaultMods = new List<string>() { "UI Expansion Kit", "Finitizer", "VRCModUpdater.Loader" };
public List<string> DefaultMods = new List<string>() { "UI Expansion Kit", "Finitizer", "VRCModUpdater.Loader", "VRChatUtilityKit", "Final IK Sanity", "ActionMenuApi" };
public Mod[] AllModsList;
public List<Mod> UnknownMods = new List<Mod>();
public CollectionView view;
@ -138,10 +139,12 @@ namespace VRCMelonAssistant.Pages
await Task.Run(() =>
{
CheckInstallDir("Plugins", false);
CheckInstallDir("Mods", false);
CheckInstallDir("Plugins/Broken", true);
CheckInstallDir("Mods/Broken", true);
CheckInstallDir("Plugins");
CheckInstallDir("Mods");
CheckInstallDir("Plugins/Broken", isBrokenDir: true);
CheckInstallDir("Mods/Broken", isBrokenDir: true);
CheckInstallDir("Plugins/Retired", isRetiredDir: true);
CheckInstallDir("Mods/Retired", isRetiredDir: true);
});
}
@ -168,7 +171,7 @@ namespace VRCMelonAssistant.Pages
}
}
private void CheckInstallDir(string directory, bool isBrokenDir)
private void CheckInstallDir(string directory, bool isBrokenDir = false, bool isRetiredDir = false)
{
if (!Directory.Exists(Path.Combine(App.VRChatInstallDirectory, directory)))
{
@ -193,6 +196,7 @@ namespace VRCMelonAssistant.Pages
mod.installedFilePath = file;
mod.installedVersion = modInfo.ModVersion;
mod.installedInBrokenDir = isBrokenDir;
mod.installedInRetiredDir = isRetiredDir;
break;
}
@ -203,12 +207,13 @@ namespace VRCMelonAssistant.Pages
installedFilePath = file,
installedVersion = modInfo.ModVersion,
installedInBrokenDir = isBrokenDir,
installedInRetiredDir = isRetiredDir,
versions = new []
{
new Mod.ModVersion()
{
name = modInfo.ModName,
modversion = modInfo.ModVersion,
modVersion = modInfo.ModVersion,
author = modInfo.ModAuthor,
description = ""
}
@ -255,11 +260,17 @@ namespace VRCMelonAssistant.Pages
public async Task PopulateModsList()
{
foreach (Mod mod in AllModsList)
foreach (Mod mod in AllModsList.Where(x => !x.versions[0].IsBroken && !x.versions[0].IsRetired))
AddModToList(mod);
foreach (var mod in UnknownMods)
AddModToList(mod, UnknownCategory);
foreach (Mod mod in AllModsList.Where(x => x.versions[0].IsBroken))
AddModToList(mod);
foreach (Mod mod in AllModsList.Where(x => x.versions[0].IsRetired))
AddModToList(mod);
}
private void AddModToList(Mod mod, ModListItem.CategoryInfo categoryOverride = null)
@ -285,14 +296,14 @@ namespace VRCMelonAssistant.Pages
IsSelected = preSelected,
IsEnabled = true,
ModName = latestVersion.name,
ModVersion = latestVersion.modversion,
ModVersion = latestVersion.modVersion,
ModAuthor = HardcodedCategories.FixupAuthor(latestVersion.author),
ModDescription = latestVersion.description.Replace("\r\n", " ").Replace("\n", " "),
ModInfo = mod,
IsInstalled = mod.installedFilePath != null,
InstalledVersion = mod.installedVersion,
InstalledModInfo = mod,
Category = categoryOverride ?? (latestVersion.IsBroken ? BrokenCategory : GetCategory(mod))
Category = categoryOverride ?? (latestVersion.IsBroken ? BrokenCategory : (latestVersion.IsRetired ? RetiredCategory : GetCategory(mod)))
};
foreach (Promotion promo in Promotions.ActivePromotions)
@ -319,7 +330,7 @@ namespace VRCMelonAssistant.Pages
foreach (Mod mod in AllModsList)
{
// Ignore mods that are newer than installed version or up-to-date
if (mod.ListItem.GetVersionComparison >= 0 && mod.installedInBrokenDir == mod.versions[0].IsBroken) continue;
if (mod.ListItem.GetVersionComparison >= 0 && mod.installedInBrokenDir == mod.versions[0].IsBroken && mod.installedInRetiredDir == mod.versions[0].IsRetired) continue;
if (mod.ListItem.IsSelected)
{
@ -506,14 +517,14 @@ namespace VRCMelonAssistant.Pages
if (SearchBar.Height == 0)
{
SearchBar.Focus();
Animate(SearchBar, 0, 16, new TimeSpan(0, 0, 0, 0, 300));
Animate(SearchText, 0, 16, new TimeSpan(0, 0, 0, 0, 300));
Animate(SearchBar, 0, 20, new TimeSpan(0, 0, 0, 0, 300));
Animate(SearchText, 0, 20, new TimeSpan(0, 0, 0, 0, 300));
ModsListView.Items.Filter = new Predicate<object>(SearchFilter);
}
else
{
Animate(SearchBar, 16, 0, new TimeSpan(0, 0, 0, 0, 300));
Animate(SearchText, 16, 0, new TimeSpan(0, 0, 0, 0, 300));
Animate(SearchBar, 20, 0, new TimeSpan(0, 0, 0, 0, 300));
Animate(SearchText, 20, 0, new TimeSpan(0, 0, 0, 0, 300));
ModsListView.Items.Filter = null;
}
}

View file

@ -88,9 +88,11 @@ namespace VRCMelonAssistant.Pages
if (resp == System.Windows.Forms.DialogResult.Yes)
{
var modsDir = Path.Combine(App.VRChatInstallDirectory, "Mods");
Directory.Delete(modsDir, true);
if (Directory.Exists(modsDir))
Directory.Delete(modsDir, true);
var pluginsDir = Path.Combine(App.VRChatInstallDirectory, "Plugins");
Directory.Delete(pluginsDir, true);
if (Directory.Exists(pluginsDir))
Directory.Delete(pluginsDir, true);
Directory.CreateDirectory(modsDir);
Directory.CreateDirectory(pluginsDir);

View file

@ -51,5 +51,5 @@ using System.Windows;
// You can specify all the values or you can default the Build and Revision Numbers
// by using the '*' as shown below:
// [assembly: AssemblyVersion("1.0.*")]
[assembly: AssemblyVersion("1.1.20.1029")]
[assembly: AssemblyFileVersion("1.1.20.1029+vrc")]
[assembly: AssemblyVersion("1.1.26.1029")]
[assembly: AssemblyFileVersion("1.1.26.1029+vrc")]