using System; using System.Collections.Generic; using System.IO; using System.IO.Compression; using System.Runtime.Serialization.Formatters.Binary; namespace TeslaConsole.BattleTech; /// /// The recorded outcome of one BattleTech mission, saved as a gzip'd /// BinaryFormatter blob (.btm) exactly like the RP .rpm mechanism. Mirrors /// RPMissionResults minus the football branches; the score-sheet print /// document (RPPrintDocument's counterpart) is deferred until a real BT match /// has been recorded to design it against. /// [Serializable] internal class BTMissionResults { private BTMission mMission; internal DateTime mMissionStart; internal TimeSpan mActuallMissionTime; internal readonly List mEvents = new List(); internal readonly Dictionary mFinalScores = new Dictionary(); public BTMission Mission => mMission; public DateTime MissionStart => mMissionStart; public TimeSpan ActuallMissionTime => mActuallMissionTime; public IEnumerable Events => mEvents; internal BTMissionResults(BTMission mission) { mMission = mission; } public static string GetBTMissionsDirectory() { string text = Path.Combine(Program.GetCommonAppDataDirectory(), "BT Missions"); if (!Directory.Exists(text)) { Directory.CreateDirectory(text); } return text; } public static BTMissionResults Load(string file) { using GZipStream gZipStream = new GZipStream(File.OpenRead(file), CompressionMode.Decompress); BinaryFormatter binaryFormatter = new BinaryFormatter(); BTMissionResults result = (BTMissionResults)binaryFormatter.Deserialize(gZipStream); gZipStream.Close(); return result; } public void Save() { string path = Path.Combine(GetBTMissionsDirectory(), mMissionStart.ToString("yyyy-MM-dd HH-mm-ss.ffff") + ".btm"); using GZipStream gZipStream = new GZipStream(File.OpenWrite(path), CompressionMode.Compress); BinaryFormatter binaryFormatter = new BinaryFormatter(); binaryFormatter.Serialize(gZipStream, this); gZipStream.Close(); } public int GetScore(BTPlayer player) { return GetScore(player, TimeSpan.MaxValue); } public int GetScore(BTPlayer player, TimeSpan gameTime) { if (gameTime == TimeSpan.MaxValue && mFinalScores.ContainsKey(player)) { return mFinalScores[player]; } int result = 1000; TimeSpan timeSpan = TimeSpan.MinValue; foreach (BTMissionEvent mEvent in mEvents) { if (mEvent is BTScoreUpdateEvent && mEvent.ReportingPilot == player && mEvent.GameTime > timeSpan && mEvent.GameTime <= gameTime) { result = ((BTScoreUpdateEvent)mEvent).Score; timeSpan = mEvent.GameTime; } } return result; } public int GetFinalPlace(BTPlayer player) { int num = 1; int score = GetScore(player, TimeSpan.MaxValue); foreach (BTPlayer player2 in mMission.Players) { if (player2 != player && GetScore(player2, TimeSpan.MaxValue) > score) { num++; } } return num; } }