Don't allow deletion of the selected character slot.

This commit is contained in:
Pieter-Jan Briers
2020-10-07 18:02:10 +02:00
parent a984076574
commit 882ed619fd
3 changed files with 56 additions and 14 deletions

View File

@@ -39,21 +39,22 @@ namespace Content.Server.Database
{
await using var db = await GetDb();
var prefs = await db.DbContext.Preference.SingleAsync(p => p.UserId == userId.UserId);
prefs.SelectedCharacterSlot = index;
await SetSelectedCharacterSlotAsync(userId, index, db.DbContext);
await db.DbContext.SaveChangesAsync();
}
public async Task SaveCharacterSlotAsync(NetUserId userId, ICharacterProfile? profile, int slot)
{
await using var db = await GetDb();
if (profile is null)
{
await DeleteCharacterSlotAsync(userId, slot);
DeleteCharacterSlot(db.DbContext, userId, slot);
await db.DbContext.SaveChangesAsync();
return;
}
await using var db = await GetDb();
if (!(profile is HumanoidCharacterProfile humanoid))
{
// TODO: Handle other ICharacterProfile implementations properly
@@ -80,17 +81,12 @@ namespace Content.Server.Database
await db.DbContext.SaveChangesAsync();
}
private async Task DeleteCharacterSlotAsync(NetUserId userId, int slot)
private static void DeleteCharacterSlot(ServerDbContext db, NetUserId userId, int slot)
{
await using var db = await GetDb();
db.DbContext
.Preference
db.Preference
.Single(p => p.UserId == userId.UserId)
.Profiles
.RemoveAll(h => h.Slot == slot);
await db.DbContext.SaveChangesAsync();
}
public async Task<PlayerPreferences> InitPrefsAsync(NetUserId userId, ICharacterProfile defaultProfile)
@@ -113,6 +109,22 @@ namespace Content.Server.Database
return new PlayerPreferences(new[] {new KeyValuePair<int, ICharacterProfile>(0, defaultProfile)}, 0);
}
public async Task DeleteSlotAndSetSelectedIndex(NetUserId userId, int deleteSlot, int newSlot)
{
await using var db = await GetDb();
DeleteCharacterSlot(db.DbContext, userId, deleteSlot);
await SetSelectedCharacterSlotAsync(userId, newSlot, db.DbContext);
await db.DbContext.SaveChangesAsync();
}
private static async Task SetSelectedCharacterSlotAsync(NetUserId userId, int newSlot, ServerDbContext db)
{
var prefs = await db.Preference.SingleAsync(p => p.UserId == userId.UserId);
prefs.SelectedCharacterSlot = newSlot;
}
private static HumanoidCharacterProfile ConvertProfiles(Profile profile)
{
var jobs = profile.Jobs.ToDictionary(j => j.JobName, j => (JobPriority) j.Priority);
@@ -188,6 +200,7 @@ namespace Content.Server.Database
await db.DbContext.SaveChangesAsync();
}
/*
* BAN STUFF
*/

View File

@@ -1,4 +1,4 @@
using System;
using System;
using System.IO;
using System.Net;
using System.Threading.Tasks;
@@ -28,6 +28,8 @@ namespace Content.Server.Database
Task<PlayerPreferences> InitPrefsAsync(NetUserId userId, ICharacterProfile defaultProfile);
Task SaveSelectedCharacterIndexAsync(NetUserId userId, int index);
Task SaveCharacterSlotAsync(NetUserId userId, ICharacterProfile? profile, int slot);
// Single method for two operations for transaction.
Task DeleteSlotAndSetSelectedIndex(NetUserId userId, int deleteSlot, int newSlot);
Task<PlayerPreferences?> GetPlayerPreferencesAsync(NetUserId userId);
// Username assignment (for guest accounts, so they persist GUID)
@@ -95,6 +97,11 @@ namespace Content.Server.Database
return _db.SaveCharacterSlotAsync(userId, profile, slot);
}
public Task DeleteSlotAndSetSelectedIndex(NetUserId userId, int deleteSlot, int newSlot)
{
return _db.DeleteSlotAndSetSelectedIndex(userId, deleteSlot, newSlot);
}
public Task<PlayerPreferences?> GetPlayerPreferencesAsync(NetUserId userId)
{
return _db.GetPlayerPreferencesAsync(userId);

View File

@@ -131,14 +131,36 @@ namespace Content.Server.Preferences
var curPrefs = prefsData.Prefs!;
// If they try to delete the slot they have selected then we switch to another one.
// Of course, that's only if they HAVE another slot.
int? nextSlot = null;
if (curPrefs.SelectedCharacterIndex == slot)
{
var (ns, profile) = curPrefs.Characters.FirstOrDefault(p => p.Key != message.Slot);
if (profile == null)
{
// Only slot left, can't delete.
return;
}
nextSlot = ns;
}
var arr = new Dictionary<int, ICharacterProfile>(curPrefs.Characters);
arr.Remove(slot);
prefsData.Prefs = new PlayerPreferences(arr, slot);
prefsData.Prefs = new PlayerPreferences(arr, nextSlot ?? curPrefs.SelectedCharacterIndex);
if (ShouldStorePrefs(message.MsgChannel.AuthType))
{
await _db.SaveCharacterSlotAsync(message.MsgChannel.UserId, null, message.Slot);
if (nextSlot != null)
{
await _db.DeleteSlotAndSetSelectedIndex(userId, slot, nextSlot.Value);
}
else
{
await _db.SaveCharacterSlotAsync(userId, null, slot);
}
}
}