docker-tmserver/xaseco/plugins/plugin.autotime.php

158 lines
5.1 KiB
PHP

<?php
/* vim: set noexpandtab tabstop=2 softtabstop=2 shiftwidth=2: */
/**
* Auto TimeLimit plugin.
* Changes Timelimit for TimeAttack dynamically depending on the next
* track's author time.
*
* Original by ck|cyrus
* Rewrite by Xymph
*
* Dependencies: none (but must be after plugin.rasp_jukebox.php in plugins.xml)
*/
Aseco::registerEvent('onSync', 'load_atlconfig');
Aseco::registerEvent('onEndRace', 'autotimelimit');
global $atl_config, $atl_active, $atl_restart;
// load ATL configuration
function load_atlconfig($aseco) {
global $atl_config, $atl_active, $atl_restart;
// initialize flags
$atl_active = false;
$atl_restart = false;
// load config file
$config_file = 'autotime.xml';
if (file_exists($config_file)) {
$aseco->console('Load auto timelimit config [' . $config_file . ']');
if ($xml = $aseco->xml_parser->parseXml($config_file)) {
$atl_config = $xml['AUTOTIME'];
$atl_active = true;
} else {
trigger_error('[ATL] Could not read/parse config file ' . $config_file . ' !', E_USER_WARNING);
}
} else {
trigger_error('[ATL] Could not find config file ' . $config_file . ' !', E_USER_WARNING);
}
} // load_atlconfig
// called @ onEndRace
function autotimelimit($aseco, $data) {
global $atl_config, $atl_active, $atl_restart;
// if not active, bail out immediately
if (!$atl_active) return;
// if restarting, bail out immediately
if ($atl_restart) {
$atl_restart = false;
return;
}
// get next game settings
$aseco->client->query('GetNextGameInfo');
$nextgame = $aseco->client->getResponse();
// check for TimeAttack on next track
if ($nextgame['GameMode'] == Gameinfo::TA) {
// check if auto timelimit enabled
if ($atl_config['MULTIPLICATOR'][0] > 0) {
// check if at least one active player on the server
if (active_player($aseco)) {
// get next track details
$challenge = get_trackinfo($aseco, 1);
$newtime = intval($challenge->authortime);
} else {
// server already switched so get current track name
$challenge = get_trackinfo($aseco, 0);
$newtime = 0; // force default
$newtime = intval($challenge->authortime);
}
// compute new timelimit
if ($newtime <= 0) {
$newtime = $atl_config['DEFAULTTIME'][0] * 60 * 1000;
$tag = 'default';
} else {
$newtime *= $atl_config['MULTIPLICATOR'][0];
$newtime -= ($newtime % 1000); // round down to seconds
$tag = 'new';
}
// check for min/max times
if ($newtime < $atl_config['MINTIME'][0] * 60 * 1000) {
$newtime = $atl_config['MINTIME'][0] * 60 * 1000;
$tag = 'min';
} elseif ($newtime > $atl_config['MAXTIME'][0] * 60 * 1000) {
$newtime = $atl_config['MAXTIME'][0] * 60 * 1000;
$tag = 'max';
}
// set and log timelimit (strip .00 sec)
$aseco->client->addcall('SetTimeAttackLimit', array($newtime));
$aseco->console('set {1} timelimit for [{2}]: {3} (Author time: {4})',
$tag, stripColors($challenge->name, false),
substr(formatTime($newtime), 0, -3),
formatTime($challenge->authortime));
// display timelimit (strip .00 sec)
$message = formatText($atl_config['MESSAGE'][0], $tag,
stripColors($challenge->name),
substr(formatTime($newtime), 0, -3),
formatTime($challenge->authortime));
if ($atl_config['DISPLAY'][0] == 2 && function_exists('send_window_message'))
send_window_message($aseco, $message, true);
elseif ($atl_config['DISPLAY'][0] > 0)
$aseco->client->query('ChatSendServerMessage', $aseco->formatColors($message));
}
}
} // autotimelimit
// get info on current/next track
function get_trackinfo($aseco, $offset) {
// get current/next track using /nextmap algorithm
if ($aseco->server->getGame() != 'TMF') {
$aseco->client->query('GetCurrentChallengeIndex');
$trkid = $aseco->client->getResponse();
$trkid += $offset;
$aseco->client->resetError();
$rtn = $aseco->client->query('GetChallengeList', 1, $trkid);
$track = $aseco->client->getResponse();
if ($aseco->client->isError()) {
// get first track
$rtn = $aseco->client->query('GetChallengeList', 1, 0);
$track = $aseco->client->getResponse();
}
} else { // TMF
if ($offset == 1)
$aseco->client->query('GetNextChallengeIndex');
else
$aseco->client->query('GetCurrentChallengeIndex');
$trkid = $aseco->client->getResponse();
$rtn = $aseco->client->query('GetChallengeList', 1, $trkid);
$track = $aseco->client->getResponse();
}
// get track info
$rtn = $aseco->client->query('GetChallengeInfo', $track[0]['FileName']);
$trackinfo = $aseco->client->getResponse();
return new Challenge($trackinfo);
} // get_trackinfo
// check for at least one active player
function active_player($aseco) {
$total = 0;
// check all connected players
foreach ($aseco->server->players->player_list as $player) {
// get current player status
if (!$aseco->isSpectator($player))
return true;
}
return false;
} // active_player
?>