diff --git a/.gitignore b/.gitignore
index 1fc58cf..7b80916 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,6 +1,15 @@
*
!README.md
!docs
+!docs/*
!MatchManagerSuite
+!MatchManagerSuite/*
!Beu
+!Beu/ChatAdminColorer.php
+!Beu/GameModeDevTools.php
+!Beu/GuestlistManager.php
+!Beu/MoreModesTools.php
+!Beu/SimpleChatColorer.php
+!Beu/SimpleSkinsRemover.php
!TFH
+!TFH/*
diff --git a/Beu/GameModeDevTools.php b/Beu/GameModeDevTools.php
new file mode 100644
index 0000000..5651906
--- /dev/null
+++ b/Beu/GameModeDevTools.php
@@ -0,0 +1,148 @@
+
+
+
+
+ EOD;
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::prepare()
+ */
+ public static function prepare(ManiaControl $maniaControl) {
+ }
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::getId()
+ */
+ public static function getId() {
+ return self::PLUGIN_ID;
+ }
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::getName()
+ */
+ public static function getName() {
+ return self::PLUGIN_NAME;
+ }
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::getVersion()
+ */
+ public static function getVersion() {
+ return self::PLUGIN_VERSION;
+ }
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::getAuthor()
+ */
+ public static function getAuthor() {
+ return self::PLUGIN_AUTHOR;
+ }
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::getDescription()
+ */
+ public static function getDescription() {
+ return "";
+ }
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::load()
+ */
+ public function load(ManiaControl $maniaControl) {
+ $this->maniaControl = $maniaControl;
+
+ $this->maniaControl->getSettingManager()->initSetting($this, self::GAMEMODE_TO_LOAD, "", "");
+ $this->maniaControl->getCallbackManager()->registerCallbackListener(PlayerManager::CB_PLAYERCONNECT, $this, 'handlePlayerConnect');
+ $this->maniaControl->getManialinkManager()->registerManialinkPageAnswerListener("DEBUG_ReloadGamemode", $this, 'LoadGamemode');
+
+ $players = $this->maniaControl->getPlayerManager()->getPlayers();
+ if (!empty($players)) {
+ $this->maniaControl->getManialinkManager()->sendManialink($this->manialink,$players);
+ }
+ $this->LoadGamemode();
+ }
+ /**
+ * Handle when a player connects
+ *
+ * @param Player $player
+ */
+ public function handlePlayerConnect(Player $player) {
+ $this->maniaControl->getManialinkManager()->sendManialink($this->manialink,$player->login);
+ }
+
+ public function LoadGamemode() {
+ Logger::log('Load Gamemode');
+ $file = $this->maniaControl->getServer()->getDirectory()->getUserDataFolder() . "Scripts/Modes" . DIRECTORY_SEPARATOR . $this->maniaControl->getSettingManager()->getSettingValue($this, self::GAMEMODE_TO_LOAD);
+ if ($file && is_file($file)) {
+ try {
+ $this->maniaControl->getChat()->sendSuccess("Loading In-Dev Script");
+ $this->maniaControl->getClient()->setModeScriptText(file_get_contents($file));
+ } catch (\Exception $e) {
+ Logger::logError($e->getMessage());
+ $this->maniaControl->getChat()->sendErrorToAdmins($e->getMessage());
+ }
+ } else {
+ Logger::logError('No Game mode to load');
+ $this->maniaControl->getChat()->sendErrorToAdmins("No Game mode to load");
+ }
+ }
+
+
+ /**
+ * Unload the plugin and its Resources
+ */
+ public function unload() {
+
+ }
+}
diff --git a/Beu/MoreModesTools.php b/Beu/MoreModesTools.php
new file mode 100644
index 0000000..e4bb835
--- /dev/null
+++ b/Beu/MoreModesTools.php
@@ -0,0 +1,136 @@
+maniaControl = $maniaControl;iaControl\Plugins\Plugin::getAuthor()
+ */
+ public static function getAuthor() {
+ return self::PLUGIN_AUTHOR;
+ }
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::getDescription()
+ */
+ public static function getDescription() {
+ return 'Tool to manage the Guestlist';
+ }
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::load()
+ */
+ public function load(ManiaControl $maniaControl) {
+ $this->maniaControl = $maniaControl;
+
+ $this->maniaControl->getCommandManager()->registerCommandListener('pause', $this, 'onCommandPause', true, 'Launch the pause');
+ $this->maniaControl->getCommandManager()->registerCommandListener('endpause', $this, 'onCommandEndPause', true, 'End the pause');
+ $this->maniaControl->getCommandManager()->registerCommandListener('endround', $this, 'onCommandEndRound', true, 'end the round');
+ $this->maniaControl->getCommandManager()->registerCommandListener(['endwu', 'endwarmup'], $this, 'onCommandEndWarmUp', true, 'End the WarmUp');
+
+ return true;
+ }
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::unload()
+ */
+ public function unload() {
+ }
+
+ /**
+ * Send Pause
+ *
+ * @param array $chat
+ * @param \ManiaControl\Players\Player $player
+ */
+ public function onCommandPause(Array $chat, Player $player) {
+ $this->maniaControl->getModeScriptEventManager()->startPause();
+ $this->maniaControl->getChat()->sendSuccessToAdmins('Pause sent');
+ }
+
+ /**
+ * Send End Pause
+ *
+ * @param array $chat
+ * @param \ManiaControl\Players\Player $player
+ */
+ public function onCommandEndPause(Array $chat, Player $player) {
+ $this->maniaControl->getModeScriptEventManager()->endPause();
+ $this->maniaControl->getChat()->sendSuccessToAdmins('Pause stopped');
+ }
+
+ /**
+ * Send End Round
+ *
+ * @param array $chat
+ * @param \ManiaControl\Players\Player $player
+ */
+ public function onCommandEndRound(Array $chat, Player $player) {
+ $this->maniaControl->getModeScriptEventManager()->forceTrackmaniaRoundEnd();
+ $this->maniaControl->getChat()->sendSuccessToAdmins('End Round sent');
+ }
+ /**
+ * Send End Warmup
+ *
+ * @param array $chat
+ * @param \ManiaControl\Players\Player $player
+ */
+ public function onCommandEndWarmUp(Array $chat, Player $player) {
+ $this->maniaControl->getModeScriptEventManager()->triggerModeScriptEvent("Trackmania.WarmUp.ForceStop");
+ $this->maniaControl->getChat()->sendSuccessToAdmins('End Round sent');
+ }
+}
diff --git a/TFH/TFHChatColorer.php b/TFH/TFHChatColorer.php
new file mode 100644
index 0000000..f08009b
--- /dev/null
+++ b/TFH/TFHChatColorer.php
@@ -0,0 +1,253 @@
+maniaControl->getChat()->sendErrorToAdmins('TFHXmlRpcDataHandler is needed to use TFHChatColorer plugin. Install it and restart Maniacontrol');
+ Logger::logError('TFHXmlRpcDataHandler is needed to use TFHChatColorer plugin. Install it and restart Maniacontrol');
+ return false;
+}
+use TFH\TFHXmlRpcDataHandler;
+
+/**
+ * ManiaControl
+ *
+ * @author Beu
+ * @license http://www.gnu.org/licenses/ GNU General Public License, Version 3
+ */
+class TFHChatColorer implements CommandListener, CallbackListener, Plugin {
+ /*
+ * Constants
+ */
+ const PLUGIN_ID = 167;
+ const PLUGIN_VERSION = 1.0;
+ const PLUGIN_NAME = 'TFHChatColorer';
+ const PLUGIN_AUTHOR = 'Beu';
+
+
+ /*
+ * Private properties
+ */
+ /** @var ManiaControl $maniaControl */
+ private $maniaControl = null;
+ private $enabled = false;
+ private $groups = [];
+ private $betterchatlogins = [];
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::prepare()
+ */
+ public static function prepare(ManiaControl $maniaControl) {
+ }
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::getId()
+ */
+ public static function getId() {
+ return self::PLUGIN_ID;
+ }
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::getName()
+ */
+ public static function getName() {
+ return self::PLUGIN_NAME;
+ }
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::getVersion()
+ */
+ public static function getVersion() {
+ return self::PLUGIN_VERSION;
+ }
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::getAuthor()
+ */
+ public static function getAuthor() {
+ return self::PLUGIN_AUTHOR;
+ }
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::getDescription()
+ */
+ public static function getDescription() {
+ return "A simple plugin that colors the logins in the chat";
+ }
+
+ /**
+ * @see \ManiaControl\Plugins\Plugin::load()
+ */
+ public function load(ManiaControl $maniaControl) {
+ $this->maniaControl = $maniaControl;
+ $this->maniaControl->getCallbackManager()->registerCallbackListener('ManiaPlanet.PlayerChat', $this, 'handlePlayerChat');
+ $this->maniaControl->getCallbackManager()->registerCallbackListener(SettingManager::CB_SETTING_CHANGED, $this, 'updateSettings');
+ $this->maniaControl->getCallbackManager()->registerCallbackListener(PlayerManager::CB_PLAYERDISCONNECT, $this, 'handlePlayerDisconnect');
+
+ $this->maniaControl->getCallbackManager()->registerCallbackListener(TFHXmlRpcDataHandler::CB_InitiatedEventData, $this, 'InitGroupsSettings');
+
+ $this->maniaControl->getCommandManager()->registerCommandListener('chatformat', $this, 'onCommandChatFormat', false, 'Add support of multiple chat formats (for Better Chat Openplanet plugin for exemple');
+ $this->maniaControl->getCommandManager()->registerCommandListener('reloadtrigram', $this, 'onCommandReloadTrigram', true, '[TFH] Reload Players Trigrams');
+
+ $this->InitGroupsSettings();
+
+ try {
+ $this->maniaControl->getClient()->chatEnableManualRouting();
+ $this->enabled = true;
+ } catch (\Exception $ex) {
+ $this->enabled = false;
+ echo "error! \n";
+ }
+ }
+
+ /**
+ * Update Widgets on Setting Changes
+ *
+ * @param Setting $setting
+ */
+ public function updateSettings(Setting $setting) {
+ if ($setting->belongsToClass($this)) {
+ $this->InitGroupsSettings();
+ }
+ }
+
+
+ /**
+ * Init chat prefix, groups, and players logins
+ */
+ public function InitGroupsSettings() {
+ Logger::Log("InitGroupsSettings");
+ $mysqli = $this->maniaControl->getDatabase()->getMysqli();
+ $query = 'select TFH_TeamsData.Trigram, TFH_PlayersData.Login FROM TFH_PlayersData JOIN TFH_TeamsData ON TFH_TeamsData.TeamId = TFH_PlayersData.TeamId;';
+
+ $result = $mysqli->query($query);
+ if ($mysqli->error) {
+ trigger_error($mysqli->error);
+ return false;
+ }
+ while($row = $result->fetch_array()) {
+ $array[] = $row;
+ }
+ if (isset($array[0])) {
+ $this->groups = [];
+ foreach ($array as $index => $value) {
+ $this->groups[$value['Login']] = $value['Trigram'];
+ }
+ }
+ }
+
+ /**
+ * Handle when a player send a message in the chat
+ *
+ * @param array $callback
+ */
+ public function handlePlayerChat($callback) {
+ $playerUid = $callback[1][0];
+ $login = $callback[1][1];
+ $text = $callback[1][2];
+
+ if ($playerUid != 0 && substr($text, 0, 1) != "/" && $this->enabled) {
+ $source_player = $this->maniaControl->getPlayerManager()->getPlayer($login);
+ if ($source_player == null) {
+ return;
+ }
+ $nick = $source_player->nickname;
+ $authLevel = $source_player->authLevel;
+
+ $prefix = "";
+
+ if (isset($this->groups[$login])) {
+ $prefix = '$<'. $this->groups[$login] .'$>$<$n$fff➤$>';
+ } else if ($authLevel > 0) {
+ $prefix = '$<$b33TFH$>$<$n$fff➤$>';
+ } else {
+ $prefix = '$<$6acCAST$>$<$n$fff➤$>';
+ }
+
+ try {
+ if (!empty($this->betterchatlogins)) {
+ $jsonMessage = json_encode(['login' => $source_player->login, 'nickname' => $prefix . $nick, 'text' => $text], JSON_UNESCAPED_UNICODE);
+ $this->maniaControl->getClient()->chatSendServerMessage('CHAT_JSON:' . $jsonMessage, $this->betterchatlogins);
+
+ $defaultchatlogins = array();
+ foreach($this->maniaControl->getPlayerManager()->getPlayers(false) as $player) {
+ if (!in_array($player->login, $this->betterchatlogins)) {
+ array_push($defaultchatlogins, $player->login);
+ }
+ }
+ if (!empty($defaultchatlogins)) {
+ $this->maniaControl->getClient()->chatSendServerMessage('$<' . $prefix . '$>' . $nick . '$<$226$w»$> ' . $text, $defaultchatlogins);
+ }
+ } else {
+ //$this->maniaControl->getClient()->chatSendServerMessage('[$<' . $prefix .'$>'. $nick . '] ' . $text);
+ $this->maniaControl->getClient()->chatSendServerMessage('$<' . $prefix . '$>' . $nick . '$<$226$w»$> ' . $text);
+ }
+ } catch (\Exception $e) {
+ echo "error while sending chat message from $login: " . $e->getMessage() . "\n";
+ }
+ }
+ }
+
+
+ /**
+ * Command /chatformat
+ *
+ * @param array $chatCallback
+ * @param \ManiaControl\Players\Player $player
+ */
+ public function onCommandChatFormat(array $chatCallback, Player $player) {
+ $argument = $chatCallback[1][2];
+ $argument = explode(" ", $argument);
+
+ if (isset($argument[1]) && $argument[1] == "json") {
+ if (!in_array($player->login, $this->betterchatlogins)) {
+ array_push($this->betterchatlogins, $player->login);
+ }
+ } else if (isset($argument[1]) && $argument[1] == "text") {
+ if (($key = array_search($player->login, $this->betterchatlogins)) !== false) {
+ unset($this->betterchatlogins[$key]);
+ }
+ }
+ }
+
+ /**
+ * Command /chatformat
+ *
+ * @param array $chatCallback
+ * @param \ManiaControl\Players\Player $player
+ */
+ public function onCommandReloadTrigram(array $chatCallback, Player $player) {
+ Logger::Log("onCommandReloadTrigram");
+ $this->InitGroupsSettings();
+ $this->maniaControl->getChat()->sendSuccess("Trigrams reloaded", $player);
+ }
+
+
+ /**
+ * Handle when a player disconnects
+ *
+ * @param \ManiaControl\Players\Player $player
+ */
+ public function handlePlayerDisconnect(Player $player) {
+ if (($key = array_search($player->login, $this->betterchatlogins)) !== false) {
+ unset($this->betterchatlogins[$key]);
+ }
+ }
+
+ /**
+ * Unload the plugin and its Resources
+ */
+ public function unload() {
+ $this->maniaControl->getClient()->chatEnableManualRouting(false);
+ $this->maniaControl->getCallbackManager()->unregisterCallbackListening('ManiaPlanet.OnPlayerChat', $this);
+ }
+}
diff --git a/TFH/TFHXmlRpcDataHandler.php b/TFH/TFHXmlRpcDataHandler.php
new file mode 100644
index 0000000..03e5a0b
--- /dev/null
+++ b/TFH/TFHXmlRpcDataHandler.php
@@ -0,0 +1,486 @@
+maniaControl = $maniaControl;
+
+ $this->initTables();
+ $this->maniaControl->getSettingManager()->initSetting($this, self::ST_STOREEVENTSLOGS, true, "Can be useful to disable it if it create issues");
+
+ $this->maniaControl->getCallbackManager()->registerCallbackListener(PlayerManager::CB_PLAYERCONNECT, $this, 'handlePlayerConnect');
+ $this->maniaControl->getCallbackManager()->registerCallbackListener(PlayerManager::CB_PLAYERDISCONNECT, $this, 'handlePlayerDisconnect');
+
+ $this->maniaControl->getCommandManager()->registerCommandListener('setteampoints', $this, 'onCommandSetTeamPoins', true, '[TFH] Set team points');
+ $this->maniaControl->getCommandManager()->registerCommandListener('adminmessage', $this, 'onCommandAdminMessage', true, '[TFH] Send Admin Message');
+
+ $this->maniaControl->getCallbackManager()->registerScriptCallbackListener(self::CB_InitEventData, $this, 'handleInitEventData');
+ $this->maniaControl->getCallbackManager()->registerScriptCallbackListener(self::CB_SetCurrentPlayer, $this, 'handleSetCurrentPlayer');
+ $this->maniaControl->getCallbackManager()->registerScriptCallbackListener(self::CB_WaypointEvent, $this, 'handleWaypointEvent');
+ $this->maniaControl->getCallbackManager()->registerScriptCallbackListener(self::CB_RequestRecovery, $this, 'handleRequestRecovery');
+ $this->maniaControl->getCallbackManager()->registerScriptCallbackListener(self::CB_RequestConfig, $this, 'handleRequestConfig');
+
+ $this->maniaControl->getCallbackManager()->registerScriptCallbackListener(self::CB_IsAFK, $this, 'handleIsAFK');
+ }
+
+ /**
+ * Initialize needed database tables
+ */
+ private function initTables() {
+ $mysqli = $this->maniaControl->getDatabase()->getMysqli();
+ $query = 'CREATE TABLE IF NOT EXISTS `' . self::DB_PLAYERSDATA . '` (
+ `Name` VARCHAR(32) NOT NULL,
+ `Login` VARCHAR(32) NOT NULL,
+ `TimeStamp` DATETIME DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
+ `TeamId` TINYINT UNSIGNED NOT NULL,
+ `CPcount` INT(5) DEFAULT 0 NOT NULL,
+ `BestLapTimes` VARCHAR(1000) DEFAULT NULL,
+ `AverageLapTimes` VARCHAR(1000) DEFAULT NULL,
+ `AveragesComputed` INT(5) DEFAULT 0 NOT NULL,
+ `LastLapTimes` VARCHAR(1000) DEFAULT NULL,
+ `TotalPlayTime` INT(10) DEFAULT 0 NOT NULL,
+ PRIMARY KEY (`Login`)
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;';
+ $mysqli->query($query);
+ if ($mysqli->error) {
+ trigger_error($mysqli->error, E_USER_ERROR);
+ }
+
+ $query = 'CREATE TABLE IF NOT EXISTS `' . self::DB_TEAMSDATA . '` (
+ `TeamId` TINYINT UNSIGNED NOT NULL,
+ `Name` VARCHAR(32) NOT NULL,
+ `Trigram` VARCHAR(30) NOT NULL,
+ `Banned` TINYINT(1) DEFAULT 0 NOT NULL,
+ `CurrentPlayer` VARCHAR(32) NULL,
+ `CurrentPlayerUpdate` TIMESTAMP DEFAULT 0 NULL,
+ `CPcount` INT(5) DEFAULT 0 NOT NULL,
+ `LastTime` INT(10) DEFAULT 0 NOT NULL,
+ PRIMARY KEY (`TeamId`)
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;';
+ $mysqli->query($query);
+ if ($mysqli->error) {
+ trigger_error($mysqli->error, E_USER_ERROR);
+ }
+ $query = 'CREATE TABLE IF NOT EXISTS `' . self::DB_EVENTSLOGS . '` (
+ `id` INT UNSIGNED NOT NULL AUTO_INCREMENT,
+ `TimeStamp` DATETIME DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
+ `Type` TINYINT UNSIGNED NOT NULL,
+ `Login` VARCHAR(32) DEFAULT NULL,
+ `EventRaceTime` INT(10) DEFAULT NULL,
+ `LapTime` INT(10) DEFAULT NULL,
+ `IsEndLap` TINYINT(1) DEFAULT NULL,
+ `LandmarkId` TINYINT UNSIGNED DEFAULT NULL,
+ PRIMARY KEY (`id`)
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;';
+ $mysqli->query($query);
+ if ($mysqli->error) {
+ trigger_error($mysqli->error, E_USER_ERROR);
+ }
+ }
+
+ private function LogEvent(Int $Type, $data) {
+ if ($this->maniaControl->getSettingManager()->getSettingValue($this, self::ST_STOREEVENTSLOGS)) {
+ $mysqli = $this->maniaControl->getDatabase()->getMysqli();
+
+ switch ($Type) {
+ case self::T_WAYPOINT:
+ $query = $mysqli->prepare('INSERT INTO `' . self::DB_EVENTSLOGS . '` (`Type`,`Login`,`EventRaceTime`,`LapTime`,`IsEndLap`,`LandmarkId`) VALUES (?, ?, ?, ?, ?, ?);');
+ $IsEndLap = intval($data->IsEndLap);
+ $query->bind_param('isiiii', $Type, $data->Login, $data->EventRaceTime, $data->LapTime, $IsEndLap, $data->LandmarkId);
+ break;
+ case self::T_SETTEAMPOINTS:
+ case self::T_CONNECT:
+ case self::T_DISCONNECT:
+ case self::T_PLAYERAFK:
+ case self::T_SETCURRENTPLAYER:
+ case self::T_ADMINMESSAGE:
+ $query = $mysqli->prepare('INSERT INTO `' . self::DB_EVENTSLOGS . '` (`Type`,`Login`) VALUES (?, ?);');
+ if (is_string($data)) {
+ $query->bind_param('is', $Type, $data);
+ } else {
+ $query->bind_param('is', $Type, $data->Login);
+ }
+ break;
+
+ default:
+ $query = $mysqli->prepare('INSERT INTO `' . self::DB_EVENTSLOGS . '` (`Type`) VALUES (?);');
+ $query->bind_param('i', $Type);
+ break;
+
+ }
+
+ if (!$query->execute()) {
+ trigger_error('Error executing MySQL query: ' . $query->error);
+ }
+ }
+ }
+
+
+ /**
+ * Handle when a player connects
+ *
+ * @param Player $player
+ */
+ public function handlePlayerConnect(Player $player) {
+ $this->LogEvent(self::T_CONNECT, $player->login);
+ }
+
+ /**
+ * Handle when a player disconnects
+ *
+ * @param Player $player
+ */
+ public function handlePlayerDisconnect(Player $player) {
+ $this->LogEvent(self::T_DISCONNECT, $player->login);
+ }
+
+ /**
+ * Handle when a player disconnects
+ *
+ * @param Player $player
+ */
+ public function handleIsAFK(array $data) {
+ $json = json_decode($data[1][0],false);
+ foreach ($json->accountIds as $accountid) {
+ $this->LogEvent(self::T_PLAYERAFK, $this->getLoginFromAccountID($accountid));
+ }
+ }
+
+ public function handleInitEventData(array $data) {
+ Logger::Log("handleInitEventData");
+ $this->LogEvent(self::T_INITEVENTDATA, null);
+
+ $json = json_decode($data[1][0],false);
+ $mysqli = $this->maniaControl->getDatabase()->getMysqli();
+ $teamquery = $mysqli->prepare('INSERT INTO `' . self::DB_TEAMSDATA . '` (`TeamId`,`Name`,`Trigram`,`Banned`)
+ VALUES (?, ?, ?, ?)
+ ON DUPLICATE KEY UPDATE `Name` = VALUES(`Name`), `Trigram` = VALUES(`Trigram`), `Banned` = VALUES(`Banned`) ;');
+ $teamquery->bind_param('issi', $id, $Name, $Trigram, $Banned);
+ $playerquery = $mysqli->prepare('INSERT INTO `' . self::DB_PLAYERSDATA . '` (`Name`,`Login`,`TeamId`, `TimeStamp`)
+ VALUES (?, ?, ?, NOW())
+ ON DUPLICATE KEY UPDATE `Name` = VALUES(`Name`), `TeamId` = VALUES(`TeamId`), `TimeStamp` = NOW();');
+ $playerquery->bind_param('ssi', $Name, $Login, $id);
+
+ foreach ($json as $id => $team) {
+ $Name = $team->Name;
+ $Trigram = $team->Trigram;
+ $Banned = intval($team->Banned);
+ if (!$teamquery->execute()) {
+ trigger_error('Error executing MySQL query: ' . $teamquery->error);
+ }
+ foreach ($team->Players as $player) {
+ $Name = $player->Name;
+ $Login = $player->Login;
+ if (!$playerquery->execute()) {
+ trigger_error('Error executing MySQL query: ' . $playerquery->error);
+ }
+ }
+ }
+ $deletequery = 'DELETE FROM `' . self::DB_PLAYERSDATA . '` WHERE `TimeStamp` < NOW() - INTERVAL 1 SECOND;';
+ $mysqli->query($deletequery);
+
+ $this->maniaControl->getCallbackManager()->triggerCallback(self::CB_InitiatedEventData);
+ }
+
+
+ public function handleSetCurrentPlayer(array $data) {
+ $json = json_decode($data[1][0],false);
+ $this->LogEvent(self::T_SETCURRENTPLAYER, $json);
+
+ $mysqli = $this->maniaControl->getDatabase()->getMysqli();
+
+ // Update TotalPlayTime
+ $query = $mysqli->prepare('UPDATE `'. self::DB_PLAYERSDATA .'`, `'. self::DB_TEAMSDATA .'`
+ SET `'. self::DB_PLAYERSDATA .'`.`TotalPlayTime` = `'. self::DB_PLAYERSDATA .'`.`TotalPlayTime` + now() - `'. self::DB_TEAMSDATA .'`.`CurrentPlayerUpdate`
+ WHERE `'. self::DB_TEAMSDATA .'`.`TeamId` = ? AND `'. self::DB_TEAMSDATA .'`.`CurrentPlayerUpdate` > 0 AND `'. self::DB_PLAYERSDATA .'`.`Login` = `'. self::DB_TEAMSDATA .'`.`CurrentPlayer`;');
+ $query->bind_param('i', $json->TeamId);
+
+ if (!$query->execute()) {
+ trigger_error('Error executing MySQL query: ' . $query->error);
+ }
+
+ // Update CurrentPlayer
+ $query = $mysqli->prepare('UPDATE `'. self::DB_TEAMSDATA .'`
+ SET `'. self::DB_TEAMSDATA .'`.`CurrentPlayer` = ?,
+ `'. self::DB_TEAMSDATA .'`.`CurrentPlayerUpdate` = now()
+ WHERE `'. self::DB_TEAMSDATA .'`.`TeamId` = ?;');
+ $query->bind_param('si', $json->Login, $json->TeamId);
+
+ if (!$query->execute()) {
+ trigger_error('Error executing MySQL query: ' . $query->error);
+ }
+ }
+
+ public function handleWaypointEvent(array $data) {
+ $json = json_decode($data[1][0],false);
+ $this->LogEvent(self::T_WAYPOINT, $json);
+
+ $mysqli = $this->maniaControl->getDatabase()->getMysqli();
+ if ($json->IsEndLap) {
+ $query = $mysqli->prepare('UPDATE `'. self::DB_TEAMSDATA .'`,`'. self::DB_PLAYERSDATA .'`
+ SET `'. self::DB_TEAMSDATA .'`.`CPcount` = `'. self::DB_TEAMSDATA .'`.`CPcount` + 1,
+ `'. self::DB_TEAMSDATA .'`.`LastTime` = ?,
+ `'. self::DB_PLAYERSDATA .'`.`CPcount` = `'. self::DB_PLAYERSDATA .'`.`CPcount` + 1,
+ `'. self::DB_PLAYERSDATA .'`.`BestLapTimes` = ?,
+ `'. self::DB_PLAYERSDATA .'`.`AverageLapTimes` = ?,
+ `'. self::DB_PLAYERSDATA .'`.`AveragesComputed` = ?,
+ `'. self::DB_PLAYERSDATA .'`.`LastLapTimes` = ?
+ WHERE `'. self::DB_TEAMSDATA .'`.`TeamId` = ? AND `'. self::DB_PLAYERSDATA .'`.`Login` = ?;');
+ $best = implode(",",$json->BestLapTimes);
+ $average = implode(",",$json->AverageLapTimes);
+ $last = implode(",",$json->LastLapTimes);
+ $query->bind_param('issisis', $json->EventRaceTime, $best, $average, $json->AveragesComputed, $last, $json->TeamId, $json->Login);
+ } else {
+ $query = $mysqli->prepare('UPDATE `'. self::DB_TEAMSDATA .'`,`'. self::DB_PLAYERSDATA .'`
+ SET `'. self::DB_TEAMSDATA .'`.`CPcount` = `'. self::DB_TEAMSDATA .'`.`CPcount` + 1,
+ `'. self::DB_TEAMSDATA .'`.`LastTime` = ?,
+ `'. self::DB_PLAYERSDATA .'`.`CPcount` = `'. self::DB_PLAYERSDATA .'`.`CPcount` + 1
+ WHERE `'. self::DB_TEAMSDATA .'`.`TeamId` = ? AND `'. self::DB_PLAYERSDATA .'`.`Login` = ?;');
+ $query->bind_param('iis', $json->EventRaceTime, $json->TeamId, $json->Login);
+ }
+
+ if (!$query->execute()) {
+ trigger_error('Error executing MySQL query: ' . $query->error);
+ }
+ }
+
+ public function handleRequestRecovery(array $data) {
+ Logger::log("handleRequestRecovery");
+ $this->LogEvent(self::T_REQUESTRECOVERY, null);
+
+ $mysqli = $this->maniaControl->getDatabase()->getMysqli();
+ $query = "SELECT `TeamId`,`CPcount`,`LastTime` FROM `" . self::DB_TEAMSDATA . "`";
+
+ $result = $mysqli->query($query);
+ while($row = $result->fetch_array(MYSQLI_ASSOC)) {
+ $array[] = $row;
+ }
+
+ if (isset($array[0])) {
+ Logger::log("Recovery Datas sent to the server");
+ $this->maniaControl->getClient()->triggerModeScriptEvent(self::CB_RestoreScores, [json_encode($array)]);
+ }
+
+ $query = "SELECT `Login`,`BestLapTimes`,`AverageLapTimes`,`AveragesComputed` FROM `" . self::DB_PLAYERSDATA . "`";
+
+ $result = $mysqli->query($query);
+ while($row = $result->fetch_array(MYSQLI_ASSOC)) {
+ $class[$row["Login"]] = (object)[];
+ if (strlen($row["BestLapTimes"]) > 0) {
+ $class[$row["Login"]]->BestLapTimes = array_map('intval',explode(",",$row["BestLapTimes"]));
+ } else {
+ $class[$row["Login"]]->BestLapTimes = [];
+ }
+ if (strlen($row["AverageLapTimes"]) > 0) {
+ $class[$row["Login"]]->AverageLapTimes = array_map('intval',explode(",",$row["AverageLapTimes"])) ;
+ } else {
+ $class[$row["Login"]]->AverageLapTimes = [];
+ }
+ $class[$row["Login"]]->AveragesComputed = intval($row["AveragesComputed"]);
+ }
+
+ $this->maniaControl->getClient()->triggerModeScriptEvent(self::CB_RestoreLapsStats, [json_encode($class)]);
+
+ }
+
+ public function handleRequestConfig(array $data) {
+ Logger::log("handleRequestConfig");
+ $this->LogEvent(self::T_REQUESTCONFIG, null);
+
+ $mysqli = $this->maniaControl->getDatabase()->getMysqli();
+ $query = 'SELECT `TeamId`,`Name`,`Trigram`,`Banned` FROM `' . self::DB_TEAMSDATA . '` ORDER BY `TeamId`';
+ $queryplayer = $mysqli->prepare('SELECT `Login`,`Name` FROM `' . self::DB_PLAYERSDATA . '` WHERE `TeamId` = ?');
+
+ $result = $mysqli->query($query);
+ $array = array();
+ while($row = $result->fetch_array(MYSQLI_ASSOC)) {
+ settype($row["Banned"],"boolean");
+ $queryplayer->bind_param('i', $row["TeamId"]);
+ if (!$queryplayer->execute()) {
+ trigger_error('Error executing MySQL query: ' . $query->error);
+ }
+ $resultplayer = $queryplayer->get_result();
+ $arrayplayer = array();
+ while ($rowplayer = $resultplayer->fetch_assoc()) {
+ array_push($arrayplayer, $rowplayer);
+ }
+ $row += ["Players" => $arrayplayer];
+
+ unset($row["TeamId"]);
+ array_push($array, $row);
+ }
+ if (isset($array[0])) {
+ Logger::log("Config sent to the server");
+ $this->maniaControl->getClient()->triggerModeScriptEvent(self::CB_SetTeamsConfig, [json_encode($array)]);
+ }
+ }
+
+ public function onCommandSetTeamPoins(array $chatCallback, Player $adminplayer) {
+ $text = $chatCallback[1][2];
+ $text = explode(" ", $text);
+
+ if (isset($text[1]) && isset($text[2]) && isset($text[3]) && is_numeric($text[1]) && is_numeric($text[2]) && $text[2] >= 0 && is_numeric($text[3]) && $text[3] >= 0 ) {
+ $mysqli = $this->maniaControl->getDatabase()->getMysqli();
+
+ $query = $mysqli->prepare('UPDATE `'. self::DB_TEAMSDATA .'` SET `CPcount` = ?, `LastTime` = ? WHERE `TeamId` = ?;');
+ $query->bind_param('iii', $text[2], $text[3], $text[1]);
+
+ if (!$query->execute()) {
+ trigger_error('Error executing MySQL query: ' . $query->error);
+ } else {
+ log(mysqli_stmt_affected_rows($query));
+ if (mysqli_stmt_affected_rows($query) === 1) {
+ $data = (object) [
+ "TeamId" => intval($text[1]),
+ "CPcount" => intval($text[2]),
+ "LastTime" => intval($text[3])
+ ];
+ $this->maniaControl->getClient()->triggerModeScriptEvent(self::CB_SetTeamPoints, [json_encode($data)]);
+ $this->LogEvent(self::T_SETTEAMPOINTS, $adminplayer->login);
+ }
+ }
+ } else {
+ $this->maniaControl->getChat()->sendError("usage: //setteampoints ", $adminplayer);
+ }
+ }
+
+ public function onCommandAdminMessage(array $chatCallback, Player $adminplayer) {
+ $text = explode(" ", $chatCallback[1][2]);
+ array_shift($text);
+ $this->LogEvent(self::T_ADMINMESSAGE, $adminplayer->login);
+ $this->maniaControl->getClient()->triggerModeScriptEvent(self::CB_AdminMessage, [implode(" ",$text)]);
+ }
+
+ /**
+ * Unload the plugin and its Resources
+ */
+ public function unload() {
+ $this->maniaControl->getCallbackManager()->unregisterScriptCallbackListener($this);
+ }
+
+ private function getLoginFromAccountID(string $accountid) {
+ $accountid = str_replace("-","", $accountid);
+ $login = "";
+ foreach(str_split($accountid, 2) as $pair){
+ $login .= chr(hexdec($pair));
+ }
+ $login = base64_encode($login);
+ $login = str_replace("+", "-", str_replace("/","_",$login));
+ $login = trim($login,"=");
+
+ return $login;
+ }
+}
\ No newline at end of file