<?php

/*
 * Plugin: Vote Manager
 * ~~~~~~~~~~~~~~~~~~~~
 * For a detailed description and documentation, please refer to:
 * http://labs.undef.de/XAseco2/Vote-Manager.php
 *
 * ----------------------------------------------------------------------------------
 * Author:		undef.de
 * Version:		0.9.8
 * Date:		2012-03-21
 * Copyright:		2012 by undef.de
 * System:		XAseco2/1.00+
 * Game:		ManiaPlanet Trackmania2 (TM2)
 * ----------------------------------------------------------------------------------
 *
 * LICENSE: This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License as published
 * by the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
 * ----------------------------------------------------------------------------------
 *
 * Dependencies:	plugins/plugin.rasp_jukebox.php
 */

/* The following manialink id's are used in this plugin (the 921 part of id can be changed on trouble):
 *
 * ManialinkID's
 * ~~~~~~~~~~~~~
 * 92200		id for manialink Widget
 * 92201		id for manialink CountdownWidget
 * 92202		id for manialink VoteStatistics
 * 92203		id for manialink HelpWindow
 * 92204		id for manialink PlayerVoteMarker
 *
 * ActionID's
 * ~~~~~~~~~~
 * 92200		id for action close Window
 * 92201		id for action YES
 * 92202		id for action NO
 *
 */

Aseco::registerEvent('onSync',				'vm_onSync');
Aseco::registerEvent('onPlayerConnect',			'vm_onPlayerConnect');
Aseco::registerEvent('onPlayerManialinkPageAnswer',	'vm_onPlayerManialinkPageAnswer');
Aseco::registerEvent('onChat',				'vm_onChat');
Aseco::registerEvent('onEverySecond',			'vm_onEverySecond');
Aseco::registerEvent('onBeginMap2',			'vm_onBeginMap2');
Aseco::registerEvent('onRestartMap',			'vm_onRestartMap');
Aseco::registerEvent('onEndMap1',			'vm_onEndMap1');
Aseco::registerEvent('onShutdown',			'vm_onShutdown');

Aseco::addChatCommand('helpvote',			'Displays info about the chat-based votes');
Aseco::addChatCommand('res',				'Start a vote to restart the current Map');
Aseco::addChatCommand('restart',			'Start a vote to restart the current Map');
Aseco::addChatCommand('skip',				'Start a vote to skip the current Map');
Aseco::addChatCommand('next',				'Start a vote to skip the current Map');
Aseco::addChatCommand('yes',				'Accept the current vote');
Aseco::addChatCommand('no',				'Reject the current vote');

global $vm_config;

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_onSync ($aseco) {
	global $vm_config;

	// Check for the right XAseco2-Version
	$xaseco2_min_version = '1.00';
	if ( defined('XASECO2_VERSION') ) {
		if ( version_compare(XASECO2_VERSION, $xaseco2_min_version, '<') ) {
			trigger_error('[plugin.vote_manager.php] Not supported XAseco2 version ('. XASECO2_VERSION .')! Please update to min. version '. $xaseco2_min_version .'!', E_USER_ERROR);
		}
	}
	else {
		trigger_error('[plugin.vote_manager.php] Can not identify the System, "XASECO2_VERSION" is unset! This plugin runs only with XAseco2/'. $xaseco2_min_version .' and up.', E_USER_ERROR);
	}

	if ($aseco->server->getGame() != 'MP') {
		trigger_error('[plugin.vote_manager.php] This plugin supports only TM2 (ManiaPlanet), can not start with a "'. $aseco->server->getGame() .'" Dedicated-Server!', E_USER_ERROR);
	}

	if (!$vm_config = $aseco->xml_parser->parseXML('vote_manager.xml')) {
		trigger_error('[plugin.vote_manager.php] Could not read/parse config file "vote_manager.xml"!', E_USER_ERROR);
	}

	$vm_config = $vm_config['VOTE_MANAGER'];

	$vm_config['ManialinkId'] = '922';
	$vm_config['Version'] = '0.9.8';

	// Register this to the global version pool (for up-to-date checks)
	$aseco->plugin_versions[] = array(
		'plugin'	=> 'plugin.vote_manager.php',
		'author'	=> 'undef.de',
		'version'	=> $vm_config['Version']
	);


	// Check for forbidden Plugins
	$forbidden = array('jfreu.plugin.php', 'plugin.rasp_votes.php');
	foreach ($forbidden as &$plugin) {
		foreach ($aseco->plugins as &$installed_plugin) {
			if ($plugin == $installed_plugin) {
				// Found show error
	        		trigger_error('[plugin.vote_manager.php] Unmet requirements! You have to deactivate "'. $plugin .'" in your "plugins.xml" to run this Plugin!', E_USER_ERROR);
			}
		}
		unset($installed_plugin);
	}
	unset($plugin);


	// Check for required Plugins
	$found = false;
	$required = array('plugin.rasp_jukebox.php');
	foreach ($required as &$plugin) {
		foreach ($aseco->plugins as &$installed_plugin) {
			if ($plugin == $installed_plugin) {
				$found = true;
				break 2;
			}
		}
		unset($installed_plugin);
	}
	unset($plugin);
	if ($found == false) {
		// Not found show error
		trigger_error('[plugin.vote_manager.php] Unmet requirements! You have to activate "'. $plugin .'" in your "plugins.xml" to run this Plugin!', E_USER_ERROR);
	}


	// Check/Setup the limits
	if ($vm_config['VOTING'][0]['RATIO'][0] < 0.2) {
		$vm_config['VOTING'][0]['RATIO'][0] = 0.2;
	}

	$vm_config['VOTING'][0]['TIMEOUT_LIMIT'][0]			= (int)$vm_config['VOTING'][0]['TIMEOUT_LIMIT'][0];
	$vm_config['VOTING'][0]['COUNTDOWN'][0]				= (int)$vm_config['VOTING'][0]['COUNTDOWN'][0];
	$vm_config['VOTING'][0]['MAX_VOTES'][0]				= (int)$vm_config['VOTING'][0]['MAX_VOTES'][0];
	$vm_config['VOTING'][0]['MAX_RESTARTS'][0]			= (int)$vm_config['VOTING'][0]['MAX_RESTARTS'][0];
	$vm_config['DEDICATED_SERVER'][0]['DISABLE_CALLVOTES'][0]	= ((strtoupper($vm_config['DEDICATED_SERVER'][0]['DISABLE_CALLVOTES'][0]) == 'TRUE') ? true : false);
	$vm_config['DEDICATED_SERVER'][0]['RATIO'][0]['DEFAULT'][0]	= (float)$vm_config['DEDICATED_SERVER'][0]['RATIO'][0]['DEFAULT'][0];
	$vm_config['DEDICATED_SERVER'][0]['RATIO'][0]['KICK'][0]	= (float)$vm_config['DEDICATED_SERVER'][0]['RATIO'][0]['KICK'][0];
	$vm_config['DEDICATED_SERVER'][0]['RATIO'][0]['BAN'][0]		= (float)$vm_config['DEDICATED_SERVER'][0]['RATIO'][0]['BAN'][0];
	$vm_config['NUMBER_FORMAT'][0]					= strtolower($vm_config['NUMBER_FORMAT'][0]);
	$vm_config['MODE'][0]						= strtolower($vm_config['MODE'][0]);


	// Preset defaults
	$vm_config['TimeAttackTimelimit']		= -1;
	$vm_config['RunningVote']['Votes']['Restart']	= 0;
	$vm_config['RunningVote']['Votes']['Skip']	= 0;
	$vm_config['RunningVote']			= vm_cleanupCurrentVote();
	$vm_config['Cache']['Todo']['onEndMap']		= false;
	$vm_config['Cache']['LastMap']['Uid']		= false;
	$vm_config['Cache']['LastMap']['Runs']		= 0;


	// Define the formats for number_format()
	$vm_config['NumberFormat'] = array(
		'english'	=> array(
			'decimal_sep'	=> '.',
			'thousands_sep'	=> ',',
		),
		'german'	=> array(
			'decimal_sep'	=> ',',
			'thousands_sep'	=> '.',
		),
		'french'	=> array(
			'decimal_sep'	=> ',',
			'thousands_sep'	=> ' ',
		),
	);


	// Store the original CallVoteRatios and CallVoteTimeOut for restoring at onShutdown
	$aseco->client->query('GetCallVoteRatios');
	$vm_config['OriginalCallVoteRatios'] = $aseco->client->getResponse();
	$aseco->client->query('GetCallVoteTimeOut');
	$GetCallVoteTimeOut = $aseco->client->getResponse();
	$vm_config['OriginalCallVoteTimeOut'] = $GetCallVoteTimeOut['CurrentValue'];
	unset($GetCallVoteTimeOut);


	// Disable the CallVotes 'RestartMap' and 'NextMap'
	$callvotes = array();
	$callvotes[] = array(
		'Command'	=> 'RestartMap',
		'Ratio'		=> (float)-1,
	);
	$callvotes[] = array(
		'Command'	=> 'NextMap',
		'Ratio'		=> (float)-1,
	);

	// Setup the configured CallVotes
	if ( is_float($vm_config['DEDICATED_SERVER'][0]['RATIO'][0]['KICK'][0]) ) {
		$callvotes[] = array(
			'Command'	=> 'Kick',
			'Ratio'		=> (float)$vm_config['DEDICATED_SERVER'][0]['RATIO'][0]['KICK'][0],
		);
	}
	if ( is_float($vm_config['DEDICATED_SERVER'][0]['RATIO'][0]['BAN'][0]) ) {
		$callvotes[] = array(
			'Command'	=> 'Ban',
			'Ratio'		=> (float)$vm_config['DEDICATED_SERVER'][0]['RATIO'][0]['BAN'][0],
		);
	}
	if ( is_float($vm_config['DEDICATED_SERVER'][0]['RATIO'][0]['DEFAULT'][0]) ) {
		$callvotes[] = array(
			'Command'	=> '*',
			'Ratio'		=> (float)$vm_config['DEDICATED_SERVER'][0]['RATIO'][0]['DEFAULT'][0],
		);
	}
	$aseco->client->query('SetCallVoteRatios', $callvotes);

	if ($vm_config['DEDICATED_SERVER'][0]['DISABLE_CALLVOTES'][0] == true) {
		$aseco->client->query('SetCallVoteTimeOut', (int)0);
	}

}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_onShutdown ($aseco) {
	global $vm_config;

	// Restore the original CallVoteRatios and CallVoteTimeOut
	$aseco->client->query('SetCallVoteRatios', $vm_config['OriginalCallVoteRatios']);
	$aseco->client->query('SetCallVoteTimeOut', $vm_config['OriginalCallVoteTimeOut']);
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

// called @ onPlayerManialinkPageAnswer
// $answer = [0]=PlayerUid, [1]=Login, [2]=Answer
function vm_onPlayerManialinkPageAnswer ($aseco, $answer) {
	global $vm_config;

	// If id = 0, bail out immediately
	if ($answer[2] == 0) {
		return;
	}

	// Get the Player object
	$player = $aseco->server->players->player_list[$answer[1]];

	if ($answer[2] == (int)$vm_config['ManialinkId'] .'00') {
		$xml = '<manialink id="'. $vm_config['ManialinkId'] .'03"></manialink>';	// HelpWindow
		vm_sendManialink($xml, $player->login, 0);
	}
	else if ($answer[2] == (int)$vm_config['ManialinkId'] .'01') {
		$command['author'] = $player;
		chat_yes($aseco, $command);
	}
	else if ($answer[2] == (int)$vm_config['ManialinkId'] .'02') {
		$command['author'] = $player;
		chat_no($aseco, $command);
	}
	else if ($answer[2] == 25) {
		// Admin has clicked "Pass" for the current Vote
		vm_handleAdminAction('pass');
	}
	else if ($answer[2] == 26) {
		// Admin has clicked "Cancel" for the current Vote
		vm_handleAdminAction('cancel');
	}
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_handleAdminAction ($action) {
	global $aseco, $vm_config;


	if ($action == 'pass') {

		// Admin "Pass" for the current Vote
		if ($vm_config['RunningVote']['Active'] == true) {
			if ($vm_config['RunningVote']['Mode'] == 'Restart') {
				// Restart passed, send the info message
				vm_sendChatmessage($vm_config['MESSAGES'][0]['VOTE_RESTART_SUCCESS'][0], false);

				// Setup restart
				$vm_config['Cache']['Todo']['onEndMap'] = $vm_config['RunningVote']['Mode'];

				// Add to Jukebox for replay
				if ($vm_config['MODE'][0] == 'replay') {
					vm_handleTodo('Replay');
				}

				// Release the event
				$aseco->releaseEvent('onVotingRestartMap', null);
			}
			else if ($vm_config['RunningVote']['Mode'] == 'Skip') {
				// Skip passed, send the info message
				vm_sendChatmessage($vm_config['MESSAGES'][0]['VOTE_SKIP_SUCCESS'][0], false);

				// Skip now
				vm_handleTodo('Skip');
			}

			// Cleanup ended vote
			$vm_config['RunningVote'] = vm_cleanupCurrentVote();

			// Hide all Widgets from all Players
			$xml = '<manialink id="'. $vm_config['ManialinkId'] .'00"></manialink>';	// Widget
			$xml .= '<manialink id="'. $vm_config['ManialinkId'] .'01"></manialink>';	// CountdownWidget
			$xml .= '<manialink id="'. $vm_config['ManialinkId'] .'02"></manialink>';	// VoteStatistics
			$xml .= '<manialink id="'. $vm_config['ManialinkId'] .'04"></manialink>';	// PlayerVoteMarker
			vm_sendManialink($xml, false, 0);
		}

	}
	else if ($action == 'cancel') {

		// Admin "Cancel" for the current Vote
		if ($vm_config['RunningVote']['Active'] == true) {
			if ($vm_config['RunningVote']['Mode'] == 'Restart') {
				// Restart did not pass, send the info message
				vm_sendChatmessage($vm_config['MESSAGES'][0]['VOTE_RESTART_FAILED'][0], false);
			}
			else if ($vm_config['RunningVote']['Mode'] == 'Skip') {
				// Skip did not pass, send the info message
				vm_sendChatmessage($vm_config['MESSAGES'][0]['VOTE_SKIP_FAILED'][0], false);
			}

			// Cleanup ended vote
			$vm_config['RunningVote'] = vm_cleanupCurrentVote();

			// Hide all Widgets from all Players
			$xml = '<manialink id="'. $vm_config['ManialinkId'] .'00"></manialink>';	// Widget
			$xml .= '<manialink id="'. $vm_config['ManialinkId'] .'01"></manialink>';	// CountdownWidget
			$xml .= '<manialink id="'. $vm_config['ManialinkId'] .'02"></manialink>';	// VoteStatistics
			$xml .= '<manialink id="'. $vm_config['ManialinkId'] .'04"></manialink>';	// PlayerVoteMarker
			vm_sendManialink($xml, false, 0);
		}

	}
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_onEverySecond ($aseco) {
	global $vm_config;

	if ($vm_config['RunningVote']['Active'] == true) {
		if ($vm_config['RunningVote']['Countdown'] > 0) {
			$xml = str_replace(
				'%COUNTDOWN%',
				formatText($vm_config['MESSAGES'][0]['TIME_REMAINING'][0], $vm_config['RunningVote']['Countdown']),
				vm_buildWidgetCountdown()
			);
			$vm_config['RunningVote']['Countdown'] --;

			// Check if all Players has voted and end voting
			$stop = true;
			foreach ($aseco->server->players->player_list as &$player) {
				if ( (!isset($vm_config['RunningVote']['Votes']['Yes'][$player->login])) && (!isset($vm_config['RunningVote']['Votes']['No'][$player->login])) ) {
					$stop = false;
				}
			}
			unset($player);
			if ($stop == true) {
				$vm_config['RunningVote']['Countdown'] = 0;
			}

			// Add vote statistics
			$xml .= vm_buildWidgetVoteStatistics();

			vm_sendManialink($xml, implode(',', $vm_config['RunningVote']['Players']), 0);
		}
		else if ( ($vm_config['RunningVote']['Countdown'] > -3) && ($vm_config['RunningVote']['Countdown'] <= 0) ) {
			$xml = str_replace(
				'%COUNTDOWN%',
				$vm_config['MESSAGES'][0]['VOTE_FINISHED'][0],
				vm_buildWidgetCountdown()
			);
			$vm_config['RunningVote']['Countdown'] --;

			// Add vote statistics
			$xml .= vm_buildWidgetVoteStatistics();

			vm_sendManialink($xml, implode(',', $vm_config['RunningVote']['Players']), 0);
		}
		else {
			// Turn off current running Vote
			$vm_config['RunningVote']['Active'] = false;

			// Find out if the vote passed
			$count_yes = count($vm_config['RunningVote']['Votes']['Yes']);
			$count_no = count($vm_config['RunningVote']['Votes']['No']);
			$totalvotes = $count_yes + $count_no;
			if ($totalvotes == 0) {
				$totalvotes = 0.0001;
			}
			if ( ($count_yes / $totalvotes * 100) >= ($vm_config['VOTING'][0]['RATIO'][0] * 100) ) {
				if ($vm_config['RunningVote']['Mode'] == 'Restart') {
					// Restart passed, send the info message
					vm_sendChatmessage($vm_config['MESSAGES'][0]['VOTE_RESTART_SUCCESS'][0], false);

					// Setup restart
					$vm_config['Cache']['Todo']['onEndMap'] = $vm_config['RunningVote']['Mode'];

					// Add to Jukebox for replay
					if ($vm_config['MODE'][0] == 'replay') {
						vm_handleTodo('Replay');
					}

					// Release the event
					$aseco->releaseEvent('onVotingRestartMap', null);
				}
				else if ($vm_config['RunningVote']['Mode'] == 'Skip') {
					// Skip passed, send the info message
					vm_sendChatmessage($vm_config['MESSAGES'][0]['VOTE_SKIP_SUCCESS'][0], false);

					// Skip now
					vm_handleTodo('Skip');
				}
			}
			else {
				if ($vm_config['RunningVote']['Mode'] == 'Restart') {
					// Restart did not pass, send the info message
					vm_sendChatmessage($vm_config['MESSAGES'][0]['VOTE_RESTART_FAILED'][0], false);
				}
				else if ($vm_config['RunningVote']['Mode'] == 'Skip') {
					// Skip did not pass, send the info message
					vm_sendChatmessage($vm_config['MESSAGES'][0]['VOTE_SKIP_FAILED'][0], false);
				}
			}

			// Cleanup ended vote
			$vm_config['RunningVote'] = vm_cleanupCurrentVote();

			// Hide all Widgets from all Players
			$xml = '<manialink id="'. $vm_config['ManialinkId'] .'00"></manialink>';	// Widget
			$xml .= '<manialink id="'. $vm_config['ManialinkId'] .'01"></manialink>';	// CountdownWidget
			$xml .= '<manialink id="'. $vm_config['ManialinkId'] .'02"></manialink>';	// VoteStatistics
			$xml .= '<manialink id="'. $vm_config['ManialinkId'] .'04"></manialink>';	// PlayerVoteMarker
			vm_sendManialink($xml, false, 0);
		}
	}
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_onChat ($aseco, $chat) {


	// If server message, bail out immediately
	if ($chat[0] == $aseco->server->id) {
		return;
	}

	if ( $aseco->isAnyAdminL($chat[1]) ) {
		if (strtolower($chat[2]) == '/admin pass') {
			// Admin has used "/admin pass" for the current Vote
			vm_handleAdminAction('pass');
		}
		else if (strtolower($chat[2]) == '/admin cancel') {
			// Admin has used "/admin cancel" for the current Vote
			vm_handleAdminAction('cancel');
		}
	}
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_onPlayerConnect ($aseco, $player) {
	global $vm_config;

	// Send info message "Callvote disabled"
	vm_sendChatmessage($vm_config['MESSAGES'][0]['CALLVOTE_DISABLED'][0], $player->login);

	// Preload the Thumbs-Images
	$xml  = '<manialink id="'. $vm_config['ManialinkId'] .'04">';
	$xml .= '<quad posn="128 128 1.1" sizen="3.2 3.2" image="'. $vm_config['IMAGES'][0]['THUMB_UP'][0] .'"/>';
	$xml .= '<quad posn="128 128 1.1" sizen="3.2 3.2" image="'. $vm_config['IMAGES'][0]['THUMB_DOWN'][0] .'"/>';
	$xml .= '</manialink>';
	vm_sendManialink($xml, $player->login, 0);

	// Check for current vote and show it
	if ($vm_config['RunningVote']['Active'] == true) {
		$vm_config['RunningVote']['Players'][] = $player->login;
		vm_sendOutVote($player->login);
	}
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_onBeginMap2 ($aseco, $map_item) {
	global $vm_config;

	// Reset all before votings
	$vm_config['RunningVote'] = vm_cleanupCurrentVote();
	$vm_config['RunningVote']['Votes']['Restart']	= 0;
	$vm_config['RunningVote']['Votes']['Skip']	= 0;

	// Reset
	$vm_config['Cache']['Todo']['onEndMap'] = false;

	// Store the Timelimit at TA
	if ($aseco->server->gameinfo->mode == Gameinfo::TA) {
		$vm_config['TimeAttackTimelimit'] = time() + ($aseco->server->gameinfo->timelimit / 1000);
	}
	else {
		$vm_config['TimeAttackTimelimit'] = -1;
	}

	// Find Uid and count the restarts or reset
	if ($vm_config['Cache']['LastMap']['Uid'] == $aseco->server->map->uid) {
		// Count the restarts
		$vm_config['Cache']['LastMap']['Runs'] ++;
	}
	else {
		// Reset
		$vm_config['Cache']['LastMap']['Uid'] = $aseco->server->map->uid;
		$vm_config['Cache']['LastMap']['Runs'] = 0;
	}
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

// "Restart Map (instant)"
function vm_onRestartMap ($aseco, $map_item) {
	global $vm_config;

	// -1 because the Admin has restarted
	$vm_config['Cache']['LastMap']['Runs'] --;
	if ($vm_config['Cache']['LastMap']['Runs'] < 0) {
		$vm_config['Cache']['LastMap']['Runs'] = 0;
	}

	// Emulate event onBeginMap2
	vm_onBeginMap2($aseco, $map_item);
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_onEndMap1 ($aseco, $data) {
	global $vm_config;

	// Test for "Restart Map (with ChatTime)"
	if ($aseco->restarting == 2) {
		// Reset Todo's
		$vm_config['Cache']['Todo']['onEndMap'] = false;

		// -1 because the Admin has restarted
		$vm_config['Cache']['LastMap']['Runs'] --;
		if ($vm_config['Cache']['LastMap']['Runs'] < 0) {
			$vm_config['Cache']['LastMap']['Runs'] = 0;
		}
	}

	// Hide all Widgets from all Players
	$xml = '<manialink id="'. $vm_config['ManialinkId'] .'00"></manialink>';	// Widget
	$xml .= '<manialink id="'. $vm_config['ManialinkId'] .'01"></manialink>';	// CountdownWidget
	$xml .= '<manialink id="'. $vm_config['ManialinkId'] .'02"></manialink>';	// VoteStatistics
	$xml .= '<manialink id="'. $vm_config['ManialinkId'] .'03"></manialink>';	// HelpWindow
	$xml .= '<manialink id="'. $vm_config['ManialinkId'] .'04"></manialink>';	// PlayerVoteMarker
	vm_sendManialink($xml, false, 0);

	// Reset all before votings if a running vote was interrupted (by Admin skip/restart)
	if ($vm_config['RunningVote']['Active'] == true) {
		$vm_config['RunningVote'] = vm_cleanupCurrentVote();
		$vm_config['RunningVote']['Votes']['Restart']	= 0;
		$vm_config['RunningVote']['Votes']['Skip']	= 0;
		$vm_config['TimeAttackTimelimit']		= -1;
	}

	if ($vm_config['Cache']['Todo']['onEndMap'] == 'Restart') {
		// Restart if it is the whished mode
		if ($vm_config['MODE'][0] == 'restart') {
			vm_handleTodo('Restart');
		}

		// Set to 'done'
		$vm_config['Cache']['Todo']['onEndMap'] = false;

		vm_sendChatmessage($vm_config['MESSAGES'][0]['VOTE_RESTART_DONE'][0], false);
	}
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

// $jukebox is imported from plugin.rasp_jukebox.php
function vm_handleTodo ($mode) {
	global $aseco, $vm_config, $jukebox;

	if ($mode == 'Restart') {
		if ($aseco->server->gameinfo->mode == Gameinfo::CUP) {
			// Don't clear scores if in Cup mode
			$aseco->client->query('RestartMap', true);
		}
		else {
			$aseco->client->query('RestartMap');
		}
	}
	else if ($mode == 'Replay') {
		// prepend current map to start of jukebox
		$uid = $aseco->server->map->uid;
		$jukebox = array_reverse($jukebox, true);
		$jukebox[$uid]['FileName'] = $aseco->server->map->filename;
		$jukebox[$uid]['Name'] = $aseco->server->map->name;
		$jukebox[$uid]['Env'] = $aseco->server->map->environment;
		$jukebox[$uid]['Login'] = $vm_config['RunningVote']['StartedFrom']['Login'];
		$jukebox[$uid]['Nick'] = $vm_config['RunningVote']['StartedFrom']['Nickname'];
		$jukebox[$uid]['source'] = 'ReplayByVoteManager';		// Prevent from counting = $replays_limit
		$jukebox[$uid]['mx'] = false;
		$jukebox[$uid]['uid'] = $uid;
		$jukebox = array_reverse($jukebox, true);
	}
	else if ($mode == 'Skip') {
		if ($aseco->server->gameinfo->mode == Gameinfo::CUP) {
			// Don't clear scores if in Cup mode
			$aseco->client->query('NextMap', true);
		}
		else {
			$aseco->client->query('NextMap');
		}
	}
	$aseco->console('[plugin.vote_manager.php] "'. $mode .'" the current Map ['. stripColors($aseco->server->map->name) .']');
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_setupNewVote ($mode, $login, $nickname, $question) {
	global $aseco, $vm_config;

	if ($vm_config['Cache']['Todo']['onEndMap'] == 'Restart') {
		vm_sendChatmessage($vm_config['MESSAGES'][0]['VOTE_RESTART_CANCEL'][0], $login);
		return;
	}

	if ( ($vm_config['VOTING'][0]['MAX_VOTES'][0] == 0) || ( ($vm_config['VOTING'][0]['MAX_VOTES'][0] > 0) && ($vm_config['RunningVote']['Votes'][$mode] < $vm_config['VOTING'][0]['MAX_VOTES'][0]) ) ) {
		// Who started the vote and what kind of vote
		$vm_config['RunningVote']['StartedFrom'] = array('Login' => $login, 'Nickname' => vm_handleSpecialChars($nickname));
		$vm_config['RunningVote']['Question'] = $question;
		$vm_config['RunningVote']['Mode'] = $mode;

		// Add all current connected Players
		foreach ($aseco->server->players->player_list as &$player) {
			$vm_config['RunningVote']['Players'][] = $player->login;
		}
		unset($player);

		// Set Timeount and Activate the Voting
		$vm_config['RunningVote']['Countdown'] = $vm_config['VOTING'][0]['COUNTDOWN'][0];
		$vm_config['RunningVote']['Active'] = true;
		$vm_config['RunningVote']['Votes']['Yes'][$login] = true;

		// Count up the current $mode Vote
		$vm_config['RunningVote']['Votes'][$mode] ++;

		vm_sendOutVote(false);

		// Mark the Player Vote
		vm_buildPlayerVoteMarker($login, 'Yes');
	}
	else {
		// Limit reached
		$message = formatText($vm_config['MESSAGES'][0]['VOTE_LIMIT_REACHED'][0],
			$mode,
			$vm_config['VOTING'][0]['MAX_VOTES'][0],
			($vm_config['VOTING'][0]['MAX_VOTES'][0] == 1) ? '' : 's'
		);
		vm_sendChatmessage($message, $login);
	}
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_sendOutVote ($login = false) {
	global $aseco, $vm_config;

	$xml = str_replace(
		array('%USERNAME%', '%QUESTION%'),
		array($vm_config['RunningVote']['StartedFrom']['Nickname'], $vm_config['RunningVote']['Question']),
		vm_buildWidget()
	);
	if ($login == false) {
		// Send to all Players
		vm_sendManialink($xml, implode(',', $vm_config['RunningVote']['Players']), 0);
	}
	else {
		// Send only to given
		vm_sendManialink($xml, $login, 0);
	}
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_buildWidget () {
	global $vm_config;

	// Placeholder: %USERNAME%, %QUESTION%
	$xml  = '<manialink id="'. $vm_config['ManialinkId'] .'00">';
	$xml .= '<frame posn="'. $vm_config['WIDGET'][0]['POS_X'][0] .' '. $vm_config['WIDGET'][0]['POS_Y'][0] .' 0">';
	$xml .= '<quad posn="0 0 0" sizen="41.9 11" bgcolor="'. $vm_config['WIDGET'][0]['BACKGROUND_COLOR'][0] .'"/>';
	$xml .= '<quad posn="-0.2 0.3 0.001" sizen="42.3 11.6" style="'. $vm_config['WIDGET'][0]['BORDER_STYLE'][0] .'" substyle="'. $vm_config['WIDGET'][0]['BORDER_SUBSTYLE'][0] .'"/>';
	$xml .= '<quad posn="0 0 0.002" sizen="42.3 11.6" style="'. $vm_config['WIDGET'][0]['BACKGROUND_STYLE'][0] .'" substyle="'. $vm_config['WIDGET'][0]['BACKGROUND_SUBSTYLE'][0] .'"/>';

	// Icon and Title
	$xml .= '<quad posn="0.4 -0.36 0.003" sizen="41.1 2" style="'. $vm_config['WIDGET'][0]['TITLE_STYLE'][0] .'" substyle="'. $vm_config['WIDGET'][0]['TITLE_SUBSTYLE'][0] .'"/>';
	$xml .= '<quad posn="0.6 0 0.004" sizen="2.5 2.5" style="'. $vm_config['WIDGET'][0]['ICON_STYLE'][0] .'" substyle="'. $vm_config['WIDGET'][0]['ICON_SUBSTYLE'][0] .'"/>';
	$xml .= '<label posn="3.2 -0.65 0.004" sizen="37 0" textsize="1" text="'. $vm_config['WIDGET'][0]['TITLE'][0] .'"/>';
	$xml .= '<format textsize="1" textcolor="FFF"/>';

	// BEGIN: Question
	$xml .= '<frame posn="0 -3 0">';
	$xml .= '<label posn="21 0 0.005" sizen="50 2.3" halign="center" textsize="3" scale="0.8" text="$S%USERNAME%$Z%QUESTION%"/>';
	$xml .= '</frame>';
	// END: Question

	// BEGIN: Ratio marker and Statistic-Background
	$xml .= '<frame posn="8.5 -7.75 0">';
	$xml .= '<quad posn="0 0 0.005" sizen="25 2.45" bgcolor="0003"/>';
	$xml .= '<quad posn="'. (0.25 * ($vm_config['VOTING'][0]['RATIO'][0] * 100)) .' 0.3 0.007" sizen="0.1 3.05" bgcolor="000A"/>';
	$xml .= '</frame>';
	// END: Ratio marker

	// BEGIN: YES Button
	$xml .= '<frame posn="0.8 -7.5 0">';
	$xml .= '<quad posn="0 0 0.005" sizen="7.1 2.9" action="'. $vm_config['ManialinkId'] .'01" actionkey="1" style="'. $vm_config['WIDGET'][0]['BUTTON_STYLE'][0] .'" substyle="'. $vm_config['WIDGET'][0]['BUTTON_SUBSTYLE'][0] .'"/>';
	$xml .= '<label posn="3.55 -0.9 0.006" sizen="7.1 0" halign="center" textsize="1" scale="0.8" text="$5B0$OYES / F5"/>';
	$xml .= '</frame>';
	// END: YES Button

	// BEGIN: NO Button
	$xml .= '<frame posn="34.1 -7.5 0">';
	$xml .= '<quad posn="0 0 0.005" sizen="7.1 2.9" action="'. $vm_config['ManialinkId'] .'02" actionkey="2" style="'. $vm_config['WIDGET'][0]['BUTTON_STYLE'][0] .'" substyle="'. $vm_config['WIDGET'][0]['BUTTON_SUBSTYLE'][0] .'"/>';
	$xml .= '<label posn="3.55 -0.9 0.006" sizen="7.1 0" halign="center" textsize="1" scale="0.8" text="$C10$ONO / F6"/>';
	$xml .= '</frame>';
	// END: NO Button

	$xml .= '</frame>';
	$xml .= '</manialink>';

	return $xml;
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_buildWidgetCountdown () {
	global $vm_config;

	// Placeholder: %COUNTDOWN%
	$xml  = '<manialink id="'. $vm_config['ManialinkId'] .'01">';
	$xml .= '<label posn="'. ($vm_config['WIDGET'][0]['POS_X'][0] + 21) .' '. ($vm_config['WIDGET'][0]['POS_Y'][0] - 5.5) .' 1.01" sizen="40 1.5" halign="center" textsize="1" text="$FFF%COUNTDOWN%"/>';
	$xml .= '</manialink>';

	return $xml;
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_buildPlayerVoteMarker ($login, $vote) {
	global $vm_config;

	$xml  = '<manialink id="'. $vm_config['ManialinkId'] .'04">';
	if ($vote == 'Yes') {
		$xml .= '<quad posn="'. ($vm_config['WIDGET'][0]['POS_X'][0] - 1) .' '. ($vm_config['WIDGET'][0]['POS_Y'][0] - 7.3) .' 1.1" sizen="3.2 3.2" image="'. $vm_config['IMAGES'][0]['THUMB_UP'][0] .'"/>';
	}
	else {
		$xml .= '<quad posn="'. ($vm_config['WIDGET'][0]['POS_X'][0] + 39.9) .' '. ($vm_config['WIDGET'][0]['POS_Y'][0] - 7.3) .' 1.1" sizen="3.2 3.2" image="'. $vm_config['IMAGES'][0]['THUMB_DOWN'][0] .'"/>';
	}
	$xml .= '</manialink>';

	vm_sendManialink($xml, $login, 0);
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_buildWidgetVoteStatistics () {
	global $vm_config;

	$count_yes = count($vm_config['RunningVote']['Votes']['Yes']);
	$count_no = count($vm_config['RunningVote']['Votes']['No']);
	$totalvotes = $count_yes + $count_no;
	if ($totalvotes == 0) {
		$totalvotes = 0.0001;
	}

	$xml  = '<manialink id="'. $vm_config['ManialinkId'] .'02">';
	$xml .= '<frame posn="'. ($vm_config['WIDGET'][0]['POS_X'][0] + 8.5) .' '. ($vm_config['WIDGET'][0]['POS_Y'][0] - 7.75) .' 0">';

	$percent_yes = ($count_yes / $totalvotes * 100);
	$xml .= '<quad posn="0 0 0.006" sizen="'. (0.25 * $percent_yes).' 1.225" bgcolor="390F"/>';
	$xml .= '<label posn="2.1 -0.05 0.007" sizen="2.4 1.225" halign="right" textsize="1" scale="0.8" text="$000'. $count_yes .'"/>';
	$xml .= '<label posn="6.4 -0.05 0.007" sizen="5 1.225" halign="right" textsize="1" scale="0.8" text="$000'. number_format($percent_yes, 2, $vm_config['NumberFormat'][$vm_config['NUMBER_FORMAT'][0]]['decimal_sep'], $vm_config['NumberFormat'][$vm_config['NUMBER_FORMAT'][0]]['thousands_sep']) .'%"/>';

	$percent_no = ($count_no / $totalvotes * 100);
	$xml .= '<quad posn="0 -1.225 0.006" sizen="'. (0.25 * $percent_no).' 1.225" bgcolor="D02F"/>';
	$xml .= '<label posn="2.1 -1.275 0.007" sizen="2.4 1.225" halign="right" textsize="1" scale="0.8" text="$000'. $count_no .'"/>';
	$xml .= '<label posn="6.4 -1.275 0.007" sizen="5 1.225" halign="right" textsize="1" scale="0.8" text="$000'. number_format($percent_no, 2, $vm_config['NumberFormat'][$vm_config['NUMBER_FORMAT'][0]]['decimal_sep'], $vm_config['NumberFormat'][$vm_config['NUMBER_FORMAT'][0]]['thousands_sep']) .'%"/>';

	$xml .= '</frame>';
	$xml .= '</manialink>';

	return $xml;
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_buildHelpWindow ($login) {
	global $vm_config;

	$xml = '<manialink id="'. $vm_config['ManialinkId'] .'03">';
	$xml .= '<frame posn="-40.8 30.55 18.50">';	// BEGIN: Window Frame
	$xml .= '<quad posn="-0.2 0.2 0.01" sizen="81.8 59" style="Bgs1InRace" substyle="BgTitle2"/>';
	$xml .= '<quad posn="1.8 -4.1 0.02" sizen="77.7 49.9" bgcolor="0018"/>';

	// Header Line
	$xml .= '<quad posn="-0.6 0.6 0.02" sizen="82.6 6" style="Bgs1InRace" substyle="BgTitle3_3"/>';
	$xml .= '<quad posn="-0.6 0.6 0.03" sizen="82.6 6" style="Bgs1InRace" substyle="BgTitle3_3"/>';

	// Title
	$xml .= '<quad posn="1.8 -0.8 0.04" sizen="3.2 3.2" style="'. $vm_config['WIDGET'][0]['ICON_STYLE'][0] .'" substyle="'. $vm_config['WIDGET'][0]['ICON_SUBSTYLE'][0] .'"/>';
	$xml .= '<label posn="5.5 -1.7 0.04" sizen="75.4 0" textsize="2" scale="0.9" textcolor="000F" text="Help for Vote Manager"/>';

	// Close Button
	$xml .= '<frame posn="76.7 -0.15 0.05">';
	$xml .= '<quad posn="0 0 0.01" sizen="4.5 4.5" action="'. $vm_config['ManialinkId'] .'00" style="Icons64x64_1" substyle="ArrowUp"/>';
	$xml .= '<quad posn="1.2 -1.2 0.02" sizen="2 2" bgcolor="EEEF"/>';
	$xml .= '<quad posn="0.7 -0.7 0.03" sizen="3.1 3.1" style="Icons64x64_1" substyle="Close"/>';
	$xml .= '</frame>';

	// About
	$xml .= '<label posn="6 -55.8 0.04" sizen="13 2" halign="center" valign="center" textsize="1" scale="0.7" url="http://labs.undef.de/XAseco2/Vote-Manager.php" focusareacolor1="0000" focusareacolor2="FFF5" textcolor="000F" text="VOTE-MANAGER/'. $vm_config['Version'] .'"/>';

	// Set the content
	$xml .= '<frame posn="3 -6 0.01">';

	$xml .= '<label posn="0 0 0.01" sizen="75 0" textsize="1" textcolor="FF0F" autonewline="1" text="With this Plugin you can start a Voting for restarting or skipping the current Map, please use one of the described commands below for a new vote.'. LF.LF .'A restart vote for a Map did not restart as soon as the vote passed, the restart is delayed until the end of the Race. If a restart vote passed and a Player want to start a skip vote, then this is rejected."/>';

	// Command "/helpvote"
	$xml .= '<label posn="0 -10 0.01" sizen="17 2" textsize="1" textcolor="FFFF" text="/helpvote"/>';
	$xml .= '<label posn="19 -10 0.01" sizen="38 2" textsize="1" textcolor="FF0F" text="Display this help"/>';

	// Command "/restart" or "/res"
	$xml .= '<label posn="0 -12 0.01" sizen="17 2" textsize="1" textcolor="FFFF" text="/restart $FF0or$FFF /res"/>';
	$xml .= '<label posn="19 -12 0.01" sizen="38 2" textsize="1" textcolor="FF0F" text="Start a vote to restart the current Map"/>';

	// Command "/skip" or "/next"
	$xml .= '<label posn="0 -14 0.01" sizen="17 2" textsize="1" textcolor="FFFF" text="/skip $FF0or$FFF /next"/>';
	$xml .= '<label posn="19 -14 0.01" sizen="38 2" textsize="1" textcolor="FF0F" text="Start a vote to skip the current Map"/>';

	// Command "/yes" or F5
	$xml .= '<label posn="0 -16 0.01" sizen="17 2" textsize="1" textcolor="FFFF" text="/yes $FF0or$FFF F5"/>';
	$xml .= '<label posn="19 -16 0.01" sizen="38 2" textsize="1" textcolor="FF0F" text="Accept the current vote"/>';

	// Command "/no" or F6
	$xml .= '<label posn="0 -18 0.01" sizen="17 2" textsize="1" textcolor="FFFF" text="/no $FF0or$FFF F6"/>';
	$xml .= '<label posn="19 -18 0.01" sizen="38 2" textsize="1" textcolor="FF0F" text="Reject the current vote"/>';

	$xml .= '</frame>';

	$xml .= '</frame>';	// Window
	$xml .= '</manialink>';

	vm_sendManialink($xml, $login, 0);
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_cleanupCurrentVote () {
	global $vm_config;

	$preset = array();
	$preset['Active']		= false;
	$preset['Players']		= array();
	$preset['StartedFrom']		= array();
	$preset['Countdown']		= -3;
	$preset['Question']		= '';
	$preset['Mode']			= false;
	$preset['Votes']['Yes']		= array();
	$preset['Votes']['No']		= array();
	$preset['Votes']['Restart']	= $vm_config['RunningVote']['Votes']['Restart'];	// Are reseted at onBeginMap2
	$preset['Votes']['Skip']	= $vm_config['RunningVote']['Votes']['Skip'];		// Are reseted at onBeginMap2

	return $preset;
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_sendManialink ($widgets, $logins = false, $timeout = 0) {
	global $aseco;

	$xml  = '<?xml version="1.0" encoding="UTF-8"?>';
	$xml .= '<manialinks>';
	$xml .= $widgets;
	$xml .= '</manialinks>';

	if ($logins != false) {
		// Send to given Players
		$aseco->client->query('SendDisplayManialinkPageToLogin', $logins, $xml, ($timeout * 1000), false);
	}
	else {
		// Send to all connected Players
		$aseco->client->query('SendDisplayManialinkPage', $xml, ($timeout * 1000), false);
	}
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_sendChatmessage ($message, $logins = false) {
	global $aseco, $vm_config;

	if ($logins != false) {
		// Send to given Players
		$aseco->client->query('ChatSendServerMessageToLogin', $aseco->formatColors($message), $logins);
	}
	else {
		// Send to all connected Players
		$aseco->client->query('ChatSendServerMessage', $aseco->formatColors($message));
	}
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_handleVote ($login, $type) {
	global $aseco, $vm_config;

	if ( ($vm_config['RunningVote']['Active'] == true) && ($vm_config['RunningVote']['Countdown'] > 0) ) {
		// Do not allow to change the own started vote
		if ($vm_config['RunningVote']['StartedFrom']['Login'] == $login) {
			vm_sendChatmessage($vm_config['MESSAGES'][0]['VOTE_NO_OWN_VOTE'][0], $login);
			return;
		}

		// Check if Player have already voted before
		$not_voted = (($type == 'Yes') ? 'No' : 'Yes');
		if ( isset($vm_config['RunningVote']['Votes'][$type][$login]) ) {
			// Player voted the same
			return;
		}
		else if ( isset($vm_config['RunningVote']['Votes'][$not_voted][$login]) ) {
			// Player voted already but change his mind, so unset the old vote
			unset($vm_config['RunningVote']['Votes'][$not_voted][$login]);
		}

		// Store the current vote
		$vm_config['RunningVote']['Votes'][$type][$login] = true;

		// Mark the Player Vote
		vm_buildPlayerVoteMarker($login, $type);
	}
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_handleSpecialChars ($string) {

	// Remove links, e.g. "$(L|H|P)[...]...$(L|H|P)"
	$string = preg_replace('/\${1}(L|H|P)\[.*?\](.*?)\$(L|H|P)/i', '$2', $string);
	$string = preg_replace('/\${1}(L|H|P)\[.*?\](.*?)/i', '$2', $string);
	$string = preg_replace('/\${1}(L|H|P)(.*?)/i', '$2', $string);

	// Remove $S (shadow)
	// Remove $H (manialink)
	// Remove $W (wide)
	// Remove $I (italic)
	// Remove $L (link)
	// Remove $O (bold)
	// Remove $N (narrow)
	$string = preg_replace('/\${1}[SHWILON]/i', '', $string);


	// Convert &
	// Convert "
	// Convert '
	// Convert >
	// Convert <
	$string = str_replace(
			array(
				'&',
				'"',
				"'",
				'>',
				'<'
			),
			array(
				'&amp;',
				'&quot;',
				'&apos;',
				'&gt;',
				'&lt;'
			),
			$string
	);
	$string = stripNewlines($string);	// stripNewlines() from basic.inc.php

	return validateUTF8String($string);	// validateUTF8String() from basic.inc.php
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function vm_checkVotePossibility ($type, $login = false) {
	global $aseco, $vm_config;

	if ( ($type == 'Restart') && ($vm_config['Cache']['LastMap']['Runs'] >= $vm_config['VOTING'][0]['MAX_RESTARTS'][0]) ) {
		// Max. restarts reached, cancel this request
		$message = formatText($vm_config['MESSAGES'][0]['VOTE_RESTART_LIMITED'][0],
			$vm_config['VOTING'][0]['MAX_RESTARTS'][0],
			(($vm_config['VOTING'][0]['MAX_RESTARTS'][0] == 1) ? '' : 's')
		);
		vm_sendChatmessage($message, $login);
		return false;
	}

	if ( ($type == 'Skip') && ($vm_config['Cache']['Todo']['onEndMap'] == 'Restart') ) {
		// There was a successfully restart vote before, cancel this skip request
		vm_sendChatmessage($vm_config['MESSAGES'][0]['VOTE_SKIP_CANCEL'][0], $login);
		return false;
	}

	if ($vm_config['RunningVote']['Active'] == true) {
		// There is already a running vote, cancel this request
		vm_sendChatmessage($vm_config['MESSAGES'][0]['VOTE_ALREADY_RUNNING'][0], $login);
		return false;
	}

	if ( ($aseco->server->gameinfo->mode == Gameinfo::TA) && ($vm_config['TimeAttackTimelimit'] != -1) ) {
		if ($vm_config['TimeAttackTimelimit'] > (time() + $vm_config['VOTING'][0]['TIMEOUT_LIMIT'][0])) {
			return true;
		}
		else {
			vm_sendChatmessage($vm_config['MESSAGES'][0]['VOTE_TOO_LATE'][0], $login);
			return false;
		}
	}

	// All ok, go ahead
	return true;
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function chat_helpvote ($aseco, $command) {
	vm_buildHelpWindow($command['author']->login);
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function chat_res ($aseco, $command) {
	// Just a wrapper for /restart
	chat_restart($aseco, $command);
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function chat_restart ($aseco, $command) {
	global $vm_config;

	if ( vm_checkVotePossibility('Restart', $command['author']->login) ) {
		// Setup new vote
		vm_setupNewVote('Restart', $command['author']->login, $command['author']->nickname, $vm_config['MESSAGES'][0]['QUESTION_RESTART'][0]);
	}
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function chat_skip ($aseco, $command) {
	// Just a wrapper for /next
	chat_next($aseco, $command);
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function chat_next ($aseco, $command) {
	global $vm_config;

	if ( vm_checkVotePossibility('Skip', $command['author']->login) ) {
		// Setup new vote
		vm_setupNewVote('Skip', $command['author']->login, $command['author']->nickname, $vm_config['MESSAGES'][0]['QUESTION_SKIP'][0]);
	}
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function chat_yes ($aseco, $command) {
	global $vm_config;

	if ($vm_config['RunningVote']['Active'] == false) {
		// Send info message
		vm_sendChatmessage($vm_config['MESSAGES'][0]['VOTE_NONE_RUNNING'][0], $command['author']->login);
	}
	else {
		vm_handleVote($command['author']->login, 'Yes');
	}
}

/*
#///////////////////////////////////////////////////////////////////////#
#									#
#///////////////////////////////////////////////////////////////////////#
*/

function chat_no ($aseco, $command) {
	global $vm_config;

	if ($vm_config['RunningVote']['Active'] == false) {
		// Send info message
		vm_sendChatmessage($vm_config['MESSAGES'][0]['VOTE_NONE_RUNNING'][0], $command['author']->login);
	}
	else {
		vm_handleVote($command['author']->login, 'No');
	}
}

?>
