From 7686680c093bbd8d4e2ba9ff9475dd976d1a5ad6 Mon Sep 17 00:00:00 2001
From: SilicaAndPina <earsyum@gmail.com>
Date: Tue, 16 Mar 2021 23:42:47 +1300
Subject: [PATCH] push changes i have

---
 DataCollection/gamedata.json                  |  4 +-
 .../HorseIsleServer/Game/Messages.cs          | 10 +++
 .../HorseIsleServer/Game/Meta.cs              | 17 ++++
 .../HorseIsleServer/Player/Highscore.cs       | 82 +++++++++++++++++-
 .../HorseIsleServer/Server/Database.cs        | 86 +++++++++++++++++++
 .../HorseIsleServer/Server/GameServer.cs      | 45 +++++++++-
 .../HorseIsleServer/Server/PacketBuilder.cs   |  5 ++
 7 files changed, 244 insertions(+), 5 deletions(-)

diff --git a/DataCollection/gamedata.json b/DataCollection/gamedata.json
index a8afda9..11624b4 100755
--- a/DataCollection/gamedata.json
+++ b/DataCollection/gamedata.json
@@ -864,7 +864,9 @@
 			"game_highscore_header":"<B>Top 20 High Scores for %GAMETITLE%</B><BR>",
 			"game_highscore_format":"#%RANKING%: %SCORE% points --  %USERNAME% [played %TOTALPLAYS% times]<BR>",
 			"game_besttime_header":"<B>Top 20 Best Times for %GAMETITLE%</B><BR>",
-			"game_besttime_format":"#%RANKING% Best Time: %SCORE% sec  --  %USERNAME% [played %TOTALPLAYS% times]<BR>"
+			"game_besttime_format":"#%RANKING% Best Time: %SCORE% sec  --  %USERNAME% [played %TOTALPLAYS% times]<BR>",
+			"game_winloose_header":"<B>Top 20 Game Winners for %GAMETITLE%</B><BR>",
+			"game_winloose_format":"#%RANKING%: %WINS% Wins (%LOSES% Losses) --  %USERNAME% [played %TOTALPLAYS% times]<BR>",
 		},
 		"quest_log":{
 			"header_meta":"^ATYour Horse Isle Adventure Log^H",
diff --git a/Horse Isle Server/HorseIsleServer/Game/Messages.cs b/Horse Isle Server/HorseIsleServer/Game/Messages.cs
index 253ec68..a2e7edd 100755
--- a/Horse Isle Server/HorseIsleServer/Game/Messages.cs	
+++ b/Horse Isle Server/HorseIsleServer/Game/Messages.cs	
@@ -846,6 +846,8 @@ namespace HISP.Game
         public static string GameBestTimeHeaderFormat;
         public static string GameHighScoreHeaderFormat;
         public static string GameHighScoreFormat;
+        public static string GameWinLooseHeaderFormat;
+        public static string GameWinLooseFormat;
 
         // Awards
 
@@ -2170,6 +2172,14 @@ namespace HISP.Game
         {
             return GameBestTimeFormat.Replace("%RANKING%", ranking.ToString("N0", CultureInfo.InvariantCulture)).Replace("%SCORE%", score.ToString().Insert(score.ToString().Length - 2, ".")).Replace("%USERNAME%", username).Replace("%TOTALPLAYS%", totalplays.ToString("N0", CultureInfo.InvariantCulture));
         }
+        public static string FormatWinlooseHeader(string gameName)
+        {
+            return GameWinLooseHeaderFormat.Replace("%GAMETITLE%", gameName);
+        }
+        public static string FormatWinlooseListEntry(int ranking, int wins, int loose, string username, int totalplays)
+        {
+            return GameWinLooseHeaderFormat.Replace("%RANKING%", ranking.ToString("N0", CultureInfo.InvariantCulture)).Replace("%WINS%", wins.ToString("N0", CultureInfo.InvariantCulture)).Replace("%LOSES%", loose.ToString("N0", CultureInfo.InvariantCulture)).Replace("%USERNAME%", username).Replace("%TOTALPLAYS%", totalplays.ToString("N0", CultureInfo.InvariantCulture));
+        }
         public static string FormatHighscoreHeader(string gameName)
         {
             return GameHighScoreHeaderFormat.Replace("%GAMETITLE%", gameName);
diff --git a/Horse Isle Server/HorseIsleServer/Game/Meta.cs b/Horse Isle Server/HorseIsleServer/Game/Meta.cs
index 0242ea5..445b70b 100755
--- a/Horse Isle Server/HorseIsleServer/Game/Meta.cs	
+++ b/Horse Isle Server/HorseIsleServer/Game/Meta.cs	
@@ -870,6 +870,23 @@ namespace HISP.Game
             message += Messages.MetaTerminator;
             return message;
         }
+        public static string BuildTopWinners(string gameName)
+        {
+            Highscore.HighscoreTableEntry[] scores = Database.GetTopWinners(gameName, 20);
+            if (scores.Length <= 0)
+                return "No wins recorded.";
+            string message = "";
+
+            message += Messages.FormatWinlooseHeader(gameName);
+
+            for (int i = 0; i < scores.Length; i++)
+            {
+                message += Messages.FormatWinlooseListEntry(i + 1, scores[i].Wins, scores[i].Looses, Database.GetUsername(scores[i].UserId), scores[i].TimesPlayed);
+            }
+            message += Messages.BackToMap;
+            message += Messages.MetaTerminator;
+            return message;
+        }
         public static string BuildTopTimes(string gameName)
         {
             Highscore.HighscoreTableEntry[] scores = Database.GetTopScores(gameName, 20);
diff --git a/Horse Isle Server/HorseIsleServer/Player/Highscore.cs b/Horse Isle Server/HorseIsleServer/Player/Highscore.cs
index dce0651..e26c752 100755
--- a/Horse Isle Server/HorseIsleServer/Player/Highscore.cs	
+++ b/Horse Isle Server/HorseIsleServer/Player/Highscore.cs	
@@ -56,7 +56,87 @@ namespace HISP.Player
             return false;
         }
 
-        public bool UpdateHighscore(string gameTitle, int score, bool time)
+    public bool Loose(string gameTitle)
+    {
+        bool isNewScore = true;
+
+        if (!HasHighscore(gameTitle))
+        {
+            Database.AddNewWinner(baseUser.Id, gameTitle, 0, 1);
+
+            HighscoreTableEntry newHighscore = new HighscoreTableEntry();
+            newHighscore.UserId = baseUser.Id;
+            newHighscore.GameName = gameTitle;
+            newHighscore.Wins = 0;
+            newHighscore.Looses = 0;
+            newHighscore.TimesPlayed = 1;
+            newHighscore.Wins = 0;
+            newHighscore.Looses = 1;
+            newHighscore.Type = "WINLOSS";
+            highScoreList.Add(newHighscore);
+
+            return isNewScore;
+        }
+        else
+        {
+            Database.UpdateHighscoreLooseGame(baseUser.Id, gameTitle);
+
+            for (int i = 0; i < highScoreList.Count; i++)
+            {
+
+                if (highScoreList[i].GameName == gameTitle)
+                {
+                    highScoreList[i].TimesPlayed += 1;
+                    highScoreList[i].Looses++;
+                }
+            }
+
+            return isNewScore;
+        }
+
+    }
+    
+public bool Win(string gameTitle)
+    {
+        bool isNewScore = true;
+
+        if (!HasHighscore(gameTitle))
+        {
+            Database.AddNewWinner(baseUser.Id, gameTitle, 1, 0);
+
+            HighscoreTableEntry newHighscore = new HighscoreTableEntry();
+            newHighscore.UserId = baseUser.Id;
+            newHighscore.GameName = gameTitle;
+            newHighscore.Wins = 0;
+            newHighscore.Looses = 0;
+            newHighscore.TimesPlayed = 1;
+            newHighscore.Wins = 1;
+            newHighscore.Looses = 0;
+            newHighscore.Type = "WINLOSS";
+            highScoreList.Add(newHighscore);
+
+            return isNewScore;
+        }
+        else
+        {
+            Database.UpdateHighscoreWinGame(baseUser.Id, gameTitle);
+
+            for (int i = 0; i < highScoreList.Count; i++)
+            {
+
+                if (highScoreList[i].GameName == gameTitle)
+                {
+                    highScoreList[i].TimesPlayed += 1;
+                    highScoreList[i].Wins++;
+                }
+            }
+
+            return isNewScore;
+        }
+
+    }
+    
+    public bool UpdateHighscore(string gameTitle, int score, bool time)
         {
             bool isNewScore = true;
 
diff --git a/Horse Isle Server/HorseIsleServer/Server/Database.cs b/Horse Isle Server/HorseIsleServer/Server/Database.cs
index fe6580a..f629d7c 100755
--- a/Horse Isle Server/HorseIsleServer/Server/Database.cs	
+++ b/Horse Isle Server/HorseIsleServer/Server/Database.cs	
@@ -5025,6 +5025,26 @@ namespace HISP.Server
             }
         }
 
+        public static void AddNewWinner(int playerId, string gameTitle, int wins, int looses)
+        {
+            using (MySqlConnection db = new MySqlConnection(ConnectionString))
+            {
+
+                db.Open();
+                MySqlCommand sqlCommand = db.CreateCommand();
+                sqlCommand.CommandText = "INSERT INTO Leaderboards VALUES(@playerId,@gameTitle,@wins,@loose,1,0,@type)";
+                sqlCommand.Parameters.AddWithValue("@playerId", playerId);
+                sqlCommand.Parameters.AddWithValue("@gameTitle", gameTitle);
+                sqlCommand.Parameters.AddWithValue("@wins", wins);
+                sqlCommand.Parameters.AddWithValue("@loose", looses);
+                sqlCommand.Parameters.AddWithValue("@type", "WINLOSS");
+                sqlCommand.Prepare();
+                sqlCommand.ExecuteNonQuery();
+
+                sqlCommand.Dispose();
+                return;
+            }
+        }
         public static void AddNewHighscore(int playerId, string gameTitle, int score, string type)
         {
             using (MySqlConnection db = new MySqlConnection(ConnectionString))
@@ -5076,6 +5096,38 @@ namespace HISP.Server
             }
         }
 
+        public static Highscore.HighscoreTableEntry[] GetTopWinners(string gameTitle, int limit)
+        {
+            List<Highscore.HighscoreTableEntry> entires = new List<Highscore.HighscoreTableEntry>();
+            using (MySqlConnection db = new MySqlConnection(ConnectionString))
+            {
+                db.Open();
+                MySqlCommand sqlCommand = db.CreateCommand();
+                sqlCommand.CommandText = "SELECT * FROM Leaderboards WHERE minigame=@gameTitle ORDER BY wins DESC LIMIT @limit";
+                sqlCommand.Parameters.AddWithValue("@gameTitle", gameTitle);
+                sqlCommand.Parameters.AddWithValue("@limit", limit);
+                sqlCommand.Prepare();
+                MySqlDataReader reader = sqlCommand.ExecuteReader();
+
+                while (reader.Read())
+                {
+                    Highscore.HighscoreTableEntry highscoreEntry = new Highscore.HighscoreTableEntry();
+                    highscoreEntry.UserId = reader.GetInt32(0);
+                    highscoreEntry.GameName = gameTitle;
+                    highscoreEntry.Wins = reader.GetInt32(2);
+                    highscoreEntry.Looses = reader.GetInt32(3);
+                    highscoreEntry.TimesPlayed = reader.GetInt32(4);
+                    highscoreEntry.Score = reader.GetInt32(5);
+                    highscoreEntry.Type = reader.GetString(6);
+                    entires.Add(highscoreEntry);
+                }
+
+
+                sqlCommand.Dispose();
+                return entires.ToArray();
+            }
+        }
+
         public static Highscore.HighscoreTableEntry[] GetTopScores(string gameTitle, int limit)
         {
             List<Highscore.HighscoreTableEntry> entires = new List<Highscore.HighscoreTableEntry>();
@@ -5131,6 +5183,40 @@ namespace HISP.Server
                 return i;
             }
         }
+        public static void UpdateHighscoreWinGame(int playerId, string gameTitle)
+        {
+            using (MySqlConnection db = new MySqlConnection(ConnectionString))
+            {
+
+                db.Open();
+                MySqlCommand sqlCommand = db.CreateCommand();
+                sqlCommand.CommandText = "UPDATE Leaderboards SET wins=wins+1, timesplayed=timesplayed+1 WHERE playerId=@playerId AND minigame=@gameTitle";
+                sqlCommand.Parameters.AddWithValue("@playerId", playerId);
+                sqlCommand.Parameters.AddWithValue("@gameTitle", gameTitle);
+                sqlCommand.Prepare();
+                sqlCommand.ExecuteNonQuery();
+
+                sqlCommand.Dispose();
+                return;
+            }
+        }
+        public static void UpdateHighscoreLooseGame(int playerId, string gameTitle)
+        {
+            using (MySqlConnection db = new MySqlConnection(ConnectionString))
+            {
+
+                db.Open();
+                MySqlCommand sqlCommand = db.CreateCommand();
+                sqlCommand.CommandText = "UPDATE Leaderboards SET looses=looses+1, timesplayed=timesplayed+1 WHERE playerId=@playerId AND minigame=@gameTitle";
+                sqlCommand.Parameters.AddWithValue("@playerId", playerId);
+                sqlCommand.Parameters.AddWithValue("@gameTitle", gameTitle);
+                sqlCommand.Prepare();
+                sqlCommand.ExecuteNonQuery();
+
+                sqlCommand.Dispose();
+                return;
+            }
+        }
         public static void UpdateHighscore(int playerId, string gameTitle, int score)
         {
             using (MySqlConnection db = new MySqlConnection(ConnectionString))
diff --git a/Horse Isle Server/HorseIsleServer/Server/GameServer.cs b/Horse Isle Server/HorseIsleServer/Server/GameServer.cs
index 1b83e86..e17d205 100755
--- a/Horse Isle Server/HorseIsleServer/Server/GameServer.cs	
+++ b/Horse Isle Server/HorseIsleServer/Server/GameServer.cs	
@@ -4020,9 +4020,10 @@ namespace HISP.Server
                     return;
                 }
             }
-            else if (method == PacketBuilder.SECCODE_SCORE || method == PacketBuilder.SECCODE_TIME)
+            else if (method == PacketBuilder.SECCODE_SCORE || method == PacketBuilder.SECCODE_TIME || method == PacketBuilder.SECCODE_WINLOOSE)
             {
                 bool time = (method == PacketBuilder.SECCODE_TIME);
+                bool winloose = (method == PacketBuilder.SECCODE_WINLOOSE);
 
                 byte[] ExpectedSecCode = sender.LoggedinUser.GenerateSecCode();
                 byte[] GotSecCode = new byte[4];
@@ -4032,12 +4033,39 @@ namespace HISP.Server
                 {
                     if (packet.Length < 6)
                     {
-                        Logger.ErrorPrint(sender.LoggedinUser.Username + " Sent a seccode score request with invalid size");
+                        Logger.ErrorPrint(sender.LoggedinUser.Username + " Sent a seccode score/time/winloose request with invalid size");
                         return;
                     }
 
+                    
                     string packetStr = Encoding.UTF8.GetString(packet);
                     string gameInfoStr = packetStr.Substring(6, packetStr.Length - 6 - 2);
+                    if (winloose)
+                    {
+                        string gameTitle = gameInfoStr.Substring(1);
+                        byte pmethod = packet[6];
+                        if(pmethod == PacketBuilder.WINLOOSE_WIN)
+                        {
+                            sender.LoggedinUser.Highscores.Win(gameTitle);
+                        }
+                        else if(pmethod == PacketBuilder.WINLOOSE_LOOSE)
+                        {
+                            sender.LoggedinUser.Highscores.Loose(gameTitle);
+                        }
+
+                        if (sender.LoggedinUser.Highscores.HighscoreList.Length >= 30)
+                            sender.LoggedinUser.Awards.AddAward(Award.GetAwardById(12)); // Minigame Player
+
+                        if (sender.LoggedinUser.Highscores.HighscoreList.Length >= 60)
+                            sender.LoggedinUser.Awards.AddAward(Award.GetAwardById(13)); // Minigame Master
+
+                        if (Database.GetPlayerTotalMinigamesPlayed(sender.LoggedinUser.Id) >= 1000)
+                            sender.LoggedinUser.Awards.AddAward(Award.GetAwardById(14)); // Minigame Nut
+
+                        if (Database.GetPlayerTotalMinigamesPlayed(sender.LoggedinUser.Id) >= 10000)
+                            sender.LoggedinUser.Awards.AddAward(Award.GetAwardById(15)); // Minigame Crazy
+                        return;
+                    }
                     if (gameInfoStr.Contains("|"))
                     {
                         string[] gameInfo = gameInfoStr.Split('|');
@@ -4348,7 +4376,18 @@ namespace HISP.Server
                 byte[] metaTag = PacketBuilder.CreateMetaPacket(Meta.BuildTopTimes(gameName));
                 sender.SendPacket(metaTag);
             }
-
+            else if (method == PacketBuilder.PROFILE_WINLOOSE_LIST)
+            {
+                sender.LoggedinUser.MetaPriority = true;
+                string packetStr = Encoding.UTF8.GetString(packet);
+                string gameName = packetStr.Substring(2, packetStr.Length - 4);
+                byte[] metaTag = PacketBuilder.CreateMetaPacket(Meta.BuildTopWinners(gameName));
+                sender.SendPacket(metaTag);
+            }
+            else
+            {
+                Logger.DebugPrint("Unknown Profile Packet! " + BitConverter.ToString(packet).Replace("-", " "));
+            }
         }
         public static void OnMovementPacket(GameClient sender, byte[] packet)
         {
diff --git a/Horse Isle Server/HorseIsleServer/Server/PacketBuilder.cs b/Horse Isle Server/HorseIsleServer/Server/PacketBuilder.cs
index 53197c5..5c5a4b7 100755
--- a/Horse Isle Server/HorseIsleServer/Server/PacketBuilder.cs	
+++ b/Horse Isle Server/HorseIsleServer/Server/PacketBuilder.cs	
@@ -141,10 +141,14 @@ namespace HISP.Server
         public const byte SECCODE_GIVE_ITEM = 0x28;
         public const byte SECCODE_DELETE_ITEM = 0x29;
         public const byte SECCODE_SCORE = 0x3D;
+        public const byte SECCODE_WINLOOSE = 0x3C;
         public const byte SECCODE_TIME = 0x3E;
         public const byte SECCODE_MONEY = 0x1E;
         public const byte SECCODE_AWARD = 0x33;
 
+        public const byte WINLOOSE_WIN = 0x14;
+        public const byte WINLOOSE_LOOSE = 0x15;
+
         public const byte NPC_START_CHAT = 0x14;
         public const byte NPC_CONTINUE_CHAT = 0x15;
 
@@ -152,6 +156,7 @@ namespace HISP.Server
         public const byte PLAYERINFO_UPDATE_OR_CREATE = 0x15;
         public const byte PLAYERINFO_PLAYER_LIST = 0x14;
 
+        public const byte PROFILE_WINLOOSE_LIST = 0x50;
         public const byte PROFILE_HIGHSCORES_LIST = 0x51;
         public const byte PROFILE_BESTTIMES_LIST = 0x52;