KoogleApp/KoogleApp/Services/GameStatusDataService.cs

252 lines
8.1 KiB
C#

using KoogleApp.Model;
using System.Text.Json;
namespace KoogleApp.Services
{
public interface IGameStatusDataService
{
GameStatusSnapshot GetCurrentData();
void UpdateData(GameStatus content, string username);
bool Undo();
bool Redo();
void SaveToFile();
void LoadFromFile();
bool CanUndo();
bool CanRedo();
}
public class GameStatusDataService : IGameStatusDataService
{
private GameStatusSnapshot _currentData;
private readonly Stack<GameStatusSnapshot> _undoStack;
private readonly Stack<GameStatusSnapshot> _redoStack;
private readonly Lock _lock = new Lock();
private readonly string _dataFilePath = "appdata.json";
private const int MaxUndoSteps = 50;
public GameStatusDataService()
{
_currentData = new GameStatusSnapshot
{
Status = new GameStatus
{
Content = "Willkommen! Starte die Zusammenarbeit.",
},
Version = 1,
LastModified = DateTime.Now,
LastModifiedBy = "System"
};
_undoStack = new Stack<GameStatusSnapshot>();
_redoStack = new Stack<GameStatusSnapshot>();
LoadFromFile();
}
public GameStatusSnapshot GetCurrentData()
{
lock (_lock)
{
return new GameStatusSnapshot
{
Status = _currentData.Status,
LastModified = _currentData.LastModified,
LastModifiedBy = _currentData.LastModifiedBy,
Version = _currentData.Version
};
}
}
public void UpdateData(GameStatus content, string username)
{
lock (_lock)
{
// Aktuellen Zustand in Undo-Stack speichern
var snapshot = new GameStatusSnapshot
{
Status = content,
LastModified = _currentData.LastModified,
LastModifiedBy = _currentData.LastModifiedBy,
Version = _currentData.Version
};
_undoStack.Push(snapshot);
_redoStack.Clear();
// Undo-Stack begrenzen
if (_undoStack.Count > MaxUndoSteps)
{
var tempStack = new Stack<GameStatusSnapshot>(_undoStack.Reverse().Take(MaxUndoSteps));
_undoStack.Clear();
foreach (var item in tempStack.Reverse())
{
_undoStack.Push(item);
}
}
// Neue Daten setzen
_currentData.Status = content;
_currentData.LastModified = DateTime.Now;
_currentData.LastModifiedBy = username;
_currentData.Version++;
SaveToFile();
}
}
public bool Undo()
{
lock (_lock)
{
if (_undoStack.Count == 0)
return false;
// Aktuellen Zustand in Redo-Stack speichern
var currentSnapshot = new GameStatusSnapshot
{
Status = _currentData.Status,
LastModified = _currentData.LastModified,
LastModifiedBy = _currentData.LastModifiedBy,
Version = _currentData.Version
};
_redoStack.Push(currentSnapshot);
// Vorherigen Zustand aus Undo-Stack wiederherstellen
var snapshot = _undoStack.Pop();
_currentData.Status = snapshot.Status;
_currentData.LastModified = snapshot.LastModified;
_currentData.LastModifiedBy = snapshot.LastModifiedBy;
_currentData.Version = snapshot.Version;
SaveToFile();
return true;
}
}
public bool Redo()
{
lock (_lock)
{
if (_redoStack.Count == 0)
return false;
// Aktuellen Zustand in Undo-Stack speichern
var currentSnapshot = new GameStatusSnapshot
{
Status = _currentData.Status,
LastModified = _currentData.LastModified,
LastModifiedBy = _currentData.LastModifiedBy,
Version = _currentData.Version
};
_undoStack.Push(currentSnapshot);
// Zustand aus Redo-Stack wiederherstellen
var snapshot = _redoStack.Pop();
_currentData.Status = snapshot.Status;
_currentData.LastModified = snapshot.LastModified;
_currentData.LastModifiedBy = snapshot.LastModifiedBy;
_currentData.Version = snapshot.Version;
SaveToFile();
return true;
}
}
public bool CanUndo()
{
lock (_lock)
{
return _undoStack.Count > 0;
}
}
public bool CanRedo()
{
lock (_lock)
{
return _redoStack.Count > 0;
}
}
public void SaveToFile()
{
try
{
var data = new
{
CurrentData = _currentData,
UndoHistory = _undoStack.ToList(),
RedoHistory = _redoStack.ToList()
};
var json = JsonSerializer.Serialize(data, new JsonSerializerOptions
{
WriteIndented = true
});
File.WriteAllText(_dataFilePath, json);
}
catch (Exception ex)
{
Console.WriteLine($"Fehler beim Speichern: {ex.Message}");
}
}
public void LoadFromFile()
{
try
{
if (File.Exists(_dataFilePath))
{
var json = File.ReadAllText(_dataFilePath);
var data = JsonSerializer.Deserialize<Dictionary<string, JsonElement>>(json);
if (data != null && data.ContainsKey("CurrentData"))
{
_currentData = JsonSerializer.Deserialize<GameStatusSnapshot>(
data["CurrentData"].GetRawText()
) ?? _currentData;
if (data.ContainsKey("UndoHistory"))
{
var history = JsonSerializer.Deserialize<List<GameStatusSnapshot>>(
data["UndoHistory"].GetRawText()
);
if (history != null)
{
_undoStack.Clear();
foreach (var snapshot in history.AsEnumerable().Reverse())
{
_undoStack.Push(snapshot);
}
}
}
if (data.ContainsKey("RedoHistory"))
{
var redoHistory = JsonSerializer.Deserialize<List<GameStatusSnapshot>>(
data["RedoHistory"].GetRawText()
);
if (redoHistory != null)
{
_redoStack.Clear();
foreach (var snapshot in redoHistory.AsEnumerable().Reverse())
{
_redoStack.Push(snapshot);
}
}
}
}
}
}
catch (Exception ex)
{
Console.WriteLine($"Fehler beim Laden: {ex.Message}");
}
}
}
}