Files
Soulstorm-tournament-decider/app/assets/javascripts/index.js
T
2026-08-15 13:32:08 +03:00

643 lines
21 KiB
JavaScript

var ws;
var userName = ""
var raceCount = $("#raceCount").html()
var existAdditionalRaces = $("#existAdditionalRaces").html() === "true"
var existTextFieldRaces = $("#existTextFieldRaces").html() === "true"
var isMuted = false;
var isDraftStarted = false;
window.onload = function () {
'use strict';
function getRandomInt(max) {
return Math.floor(Math.random() * Math.floor(max));
}
var LobbyList = Backbone.View.extend({
lobbies: undefined,
initialize: function () {
this.elCount = 0;
},
template: _.template('<table id ="deciderList" class="table"><tbody><tr>\n' +
' <th>Host</th>\n' +
' <th>Status</th>\n' +
' <th>Action</th></tr>\n' +
' </tbody></table>'),
events: {
"click .title": "check" // Обработчик клика на кнопке "Проверить"
},
render: function () {
var lobbiesAsTableRows = _.reduce(this.lobbies, function (memo, lobby) {
if ($("#deciderName").html() !== lobby.deciderName) return memo;
var joinButton = (lobby.status === "NotStarted()") ? '<button class="btn btn-primary join-as-player" onclick="joinDecider(\'' + lobby.lobbyActorName + '\')">' +
'<img src="/assets/images/buttons/isAuto.png" style="height: 25px;"> Join lobby <img src="/assets/images/buttons/isAuto.png" style="height: 25px;">' +
'</button>' : "";
var observerButton = '<button class="btn btn-success join-as-observer" onclick="observerDecider(\'' + lobby.lobbyActorName + '\')">' +
'<img src="/assets/images/buttons/Ulthwe.png" style="height: 25px;"> Observer <img src="/assets/images/buttons/Ulthwe.png" style="height: 25px;">' +
'</button>';
return memo + '<tr>\n' +
' <td>' + lobby.user1Info.name.substring(0, 20) + '</td>\n' +
' <td>' + lobby.user2Info.name.substring(0, 20) + '</td>\n' +
' <td>' + lobby.status + '</td>\n' +
' <td>' + joinButton + ' ' + observerButton +
' </td>' +
'</tr>';
}, "");
var tableStart = '<table id ="deciderList" class="table"><tbody><tr>\n' +
' <th>Player1</th>\n' +
' <th>Player2</th>\n' +
' <th>Status</th>\n' +
' <th style="width: 400px;">Action</th></tr>\n';
var tableEnd = '</tbody></table>';
var res = tableStart + lobbiesAsTableRows + tableEnd;
$("#deciderList tbody", res).append(lobbiesAsTableRows);
console.log(res);
this.$el.html(res);
}
});
var lobbyList = new LobbyList;
$("#lobbiesList").append(lobbyList.$el);
lobbyList.render();
$("#createDecider").click(function (event) {
event.preventDefault();
isObserver = false;
ws.send(JSON.stringify({
type: "createDecider",
deciderName: $("#deciderName").html()
}));
});
$("#submitmsg").click(function (event) {
sendMessage();
});
$("#usermsg").on('keyup', function (e) {
if (e.key === 'Enter' || e.keyCode === 13) {
sendMessage()
}
});
$("#mute").click(function (event) {
if (isMuted) {
isMuted = false;
$("#mute").html("🔊");
} else {
isMuted = true;
$("#mute").html("🔈");
}
});
$("#exit").click(function (event) {
event.preventDefault();
ws.send(JSON.stringify({
type: "leaveDecider"
}));
$("#decider").hide();
$("#lobbies").show();
$(".navbar").show();
});
function requestName() {
if ($.cookie('user') === undefined || $.cookie('user') === "null" || $.cookie('user') === "") {
var result = prompt("Enter nickname: ",);
$.cookie('user', result, {expires: 1337});
userName = result;
requestName();
} else {
userName = $.cookie('user');
}
}
requestName();
$("#playerName").html(userName);
ws = new WebSocket($("body").data("ws-url"));
ws.onmessage = function (event) {
var message;
message = JSON.parse(event.data);
switch (message.type) {
case "refreshLobby":
if (message.lobby.status === "SelectRace()" && (!isObserver)) {
isDraftStarted = false;
renderRaces();
} else {
renderMaps(message.lobby.maps, message.lobby.status);
}
renderPlayersAndStats(message.lobby);
break;
case "switchToLobby":
console.log(message);
switchToLobby(message.lobby.maps, message.lobby.status);
renderPlayersAndStats(message.lobby);
break;
case "sendMessage":
console.log(message);
addMessageToChat(message.message);
break;
case "sendMapBanMessage":
console.log(message);
handleMapBanEvent(message.message);
break;
case "lobbyError":
console.log(message);
disconnectLobby(message.error);
break;
case "lobbies":
lobbyList.lobbies = message.lobbies;
lobbyList.render();
return console.log(message);
break;
default:
}
};
ws.onopen = function () {
ws.send(JSON.stringify({
type: "userName",
name: $.cookie('user')
}));
ws.send(JSON.stringify({
type: "getLobbies"
}));
}
setInterval(() =>
ws.send(JSON.stringify({
type: "getLobbies"
})), 2000);
}
function changeNick() {
result = prompt("Введите ник", $.cookie('user'));
if (result == null) return;
result = result.substr(0, 20);
$.cookie('user', result, {expires: 7});
ws.send(JSON.stringify({
type: "userName",
name: $.cookie('user')
}));
userName = $.cookie('user');
$("#playerName").html(userName);
}
// -----ф-ии прихода с сервера
function switchToLobby(maps, status) {
console.log(maps);
renderMaps(maps, status);
$("#lobbies").hide();
$(".navbar").hide();
$("#decider").show();
$("#chatbox").html("");
}
function disconnectLobby(error) {
$("#decider").hide();
$(".navbar").show();
$("#lobbies").show();
ws.send(JSON.stringify({
type: "getLobbies"
}));
alert(error);
}
// ---------------Выбор рас --------------
function getRaceImageByNumber(number) {
switch (number) {
case 10:
return "/assets/images/raceIcons/cancel.png";
case 1:
return "/assets/images/raceIcons/SM.gif";
case 2:
return "/assets/images/raceIcons/Chaos.gif";
case 3:
return "/assets/images/raceIcons/Eldar.gif";
case 4:
return "/assets/images/raceIcons/Orks.gif";
case 5:
return "/assets/images/raceIcons/IG.gif";
case 6:
return "/assets/images/raceIcons/Nec.gif";
case 7:
return "/assets/images/raceIcons/Tau.gif";
case 8:
return "/assets/images/raceIcons/Sob.gif";
case 9:
return "/assets/images/raceIcons/De.gif";
}
}
function renderRaces() {
function getRaceSelectHtml(raceType, raceArray) {
var resHtml = "";
for(var raceNum = 1; raceNum <= raceCount; raceNum++){
resHtml += "<div class='col-xs-4'><center><h3>" + raceType + " race " + raceNum + "</h3>";
for (var i = 1; i <= 10; i++) {
var selected = "raceNotSelected";
if ($.cookie("race-" + raceType + "-" + raceNum) == i) {
selected = "raceSelected";
console.log("setted: " + i);
raceArray[raceNum] = i;
}
let raceIconClass = "raceIcon-" + raceNum + "-" + raceType;
resHtml += '<a href = "#" class="' + selected + ' ' + raceIconClass + '"' +
' onclick="selectRace(this, '+i+', '+raceNum+', \''+raceType+'\')"><img class="raceIcon" src="' + getRaceImageByNumber(i) + '"></a> ';
}
resHtml += "</center></div>";
}
return resHtml;
}
function renderInputField() {
var raceTextInput = ''
if($.cookie("raceTextInput") !== undefined){
raceTextInput = $.cookie("raceTextInput")
}
return '<center><input type="text" class="form-control" id="raceInput" placeholder="Black fists, Imperial angels, Blood templars" oninput="checkRaceSelectFinish()" value="'+ raceTextInput +'"/></center>';
}
var resHtml = "";
if(!existTextFieldRaces){
resHtml += getRaceSelectHtml("main", selectedRaces);
if(existAdditionalRaces) resHtml += getRaceSelectHtml("additional", selectedAdditionalRaces);
}else {
resHtml += renderInputField();
}
resHtml += "<div style='clear: both;'></div></br>";
resHtml += "<center><button id = 'selectRace' class='btn btn-primary' disabled onclick='sendSelectedRacesToServer()'>OK</button></center>"
$("#mapList").html(resHtml);
checkRaceSelectFinish();
}
var selectedRaces = [];
var selectedAdditionalRaces = [];
function selectRace(button, race, raceNum, raceType) {
if(raceType === "main"){
selectedRaces[raceNum] = race;
}else{
selectedAdditionalRaces[raceNum] = race;
}
$.cookie("race-" + raceType + "-" + raceNum, race, {expires: 1});
_.each($(".raceIcon-" + raceNum + "-" + raceType), function (el) {
$(el).removeClass("raceSelected");
$(el).addClass("raceNotSelected");
});
$(button).removeClass("raceNotSelected");
$(button).addClass("raceSelected");
checkRaceSelectFinish();
}
function checkRaceSelectFinish() {
if(selectedRaces.filter(x => x).length >= raceCount){
$("#selectRace").removeAttr("disabled");
} else if($("#raceInput").val().trim() !== ''){
$("#selectRace").removeAttr("disabled");
}
}
function sendSelectedRacesToServer() {
$.cookie('raceTextInput', $("#raceInput").val(), {expires: 1});
var selectedInput = $("#raceInput").val();
if(selectedInput === undefined){
selectedInput = ""
}
console.log(selectedRaces);
ws.send(JSON.stringify({
type: "selectRace",
mainRaces: selectedRaces.filter(x => x),
additionalRaces: selectedAdditionalRaces.filter(x => x),
raceTextInput: selectedInput
}));
$("#mapList").html("<center>Waiting another player...</center>");
}
// ---------------------------------------------
function renderMaps(maps, lobbyStatus) {
var resHtml = "";
_.each(maps, function (map) {
var banHtml = "";
var banClass = "";
if (map.isBanned) {
banHtml = "<div class = 'banX'>&#x2715;</div>";
banClass = "bannedMap";
}
var title = ""
if (map.description != null) {
title = "title='" + map.description + "'";
}
resHtml = resHtml + '<div class="col-xs-4 col-md-3 col-lg-2"><button class = "mapSelect" onmousedown="banMap(\'' + map.map + '\')">' +
'<div class="mapImageAndText ' + banClass + '">' +
'<img class="img-rounded center-block" ' + title + ' style="width:128px;" src="/assets/images/maps/' + encodeURI(map.map) + '.jpg">' +
'</div>' + convertMapName(map.map) +
banHtml + '</button></div>';
})
$("#mapList").html(resHtml);
}
var isObserver = false;
function renderFinish(maps, firstPlayerInfo, secondPlayerInfo) {
var resHtml = "<center>";
_.each(maps, function (map) {
if (!map.isBanned) {
resHtml = resHtml + '<div class="col-xs-4 col-md-3 col-lg-2"><button class = "mapSelect" >' +
'<div class="mapImageAndText ">' +
'<img class="img-rounded center-block" style="width:128px;" src="/assets/images/maps/' + encodeURI(map.map) + '.jpg">' +
'</div>' + convertMapName(map.map) + '</button></div>';
}
})
resHtml += "<div style='clear: both;'>";
resHtml += getRenderRaces(firstPlayerInfo, secondPlayerInfo);
resHtml += "</center>";
$("#mapList").html(resHtml);
}
function renderPlayersAndStats(lobby) {
var resHtml = "<center>";
var player1ReadyBtn = "";
var player2ReadyBtn = "";
var readyImg = "<img src='/assets/images/buttons/isAuto.png' class='readyImg'/>";
var notReadyImg = "<img src='/assets/images/buttons/isNotAuto.png' class='readyImg'/>";
var warningClass = (lobby.user2Info.name !== "") ? "warningButton" : "";
if (lobby.user1Info.name === userName) {
if (lobby.user1Info.isReady) {
player1ReadyBtn = "<button class='btn btn-default' onclick='setNotReady()'>" + readyImg + " Ready " + readyImg + "</button>"
} else {
player1ReadyBtn = "<button class='btn btn-default " + warningClass + "' onclick='setReady()'>" + notReadyImg + " Not ready " + notReadyImg + "</button>"
}
} else {
if (lobby.user1Info.isReady) {
player1ReadyBtn = readyImg
} else {
player1ReadyBtn = notReadyImg
}
}
if (lobby.user2Info.name === userName) {
if (lobby.user2Info.isReady) {
player2ReadyBtn = "<button class='btn btn-default' onclick='setNotReady()'>" + readyImg + " Ready " + readyImg + "</button>"
} else {
player2ReadyBtn = "<button class='btn btn-default " + warningClass + "' onclick='setReady()'>" + notReadyImg + " Not ready " + notReadyImg + "</button>"
}
} else {
if (lobby.user2Info.isReady) {
player2ReadyBtn = readyImg
} else {
player2ReadyBtn = notReadyImg
}
}
if (lobby.user1Info.name === userName || lobby.user2Info.name === userName) {
$("#inputMsg").show();
} else {
$("#inputMsg").hide();
}
var lobbyTypeText = "";
var last1Selected = "";
var last3Selected = "";
var last5Selected = "";
var last7Selected = "";
var isNecronsSelected = "";
if (lobby.isNecrons) isNecronsSelected = "checked";
switch (lobby.selectedType) {
case "Last1()":
looserPickSelected = "selected";
lobbyTypeText = "Play on last map";
break;
case "Last3()":
last3Selected = "selected";
lobbyTypeText = "Play on last 3 maps";
break;
case "Last5()":
last5Selected = "selected";
lobbyTypeText = "Play on last 5 maps";
break;
case "Last7()":
last7Selected = "selected";
lobbyTypeText = "Play on last 7 maps";
break;
}
console.log(lobby.status);
switch (lobby.status) {
case "NotStarted()":
resHtml = "<div style='float: left; padding-top: 10px;'> <div>" + lobby.user1Info.name + ": " + player1ReadyBtn + "</div><br/>"
if (lobby.user2Info.name !== "") {
var kickBtn = ""
if (lobby.user1Info.name === userName) {
kickBtn = " - <button class='btn btn-danger' onclick='kickSecondPlayer()'>Kick</button>";
}
resHtml += "<div>" + lobby.user2Info.name + ": " + player2ReadyBtn + kickBtn + "</div>"
} else {
resHtml += "<div>waiting 2-nd player...</div>"
}
var disabledText = "";
if (lobby.user1Info.name !== userName) {
disabledText = "disabled";
}
//TODO: here from config
resHtml += "<br/><select class=\"form-control\" id = 'deciderOption' onChange='changeLobbyType()' " + disabledText + " >" +
"<option " + last1Selected + " value = 'last1'>Play on last map</option>" +
"<option " + last3Selected + " value = 'last3'>Play on last 3 maps</option>" +
"<option " + last5Selected + " value = 'last5'>Play on last 5 maps</option>" +
"<option " + last7Selected + " value = 'last7'>Play on last 7 maps</option>" +
"</select>";
if (lobby.user1Info.name !== userName && lobby.user2Info.name !== userName) {
disabledText = "disabled";
} else {
disabledText = "";
}
resHtml += "</div>";
break;
case "SelectRace()":
resHtml = "<center>" + lobby.user1Info.name + " vs " + lobby.user2Info.name + " - " + lobbyTypeText + "<br/> players select races</center>";
break;
case "Draft()":
if (!isDraftStarted) {
isDraftStarted = true;
}
var playerTurn = (lobby.playerTurn === 1) ? lobby.user1Info.name : lobby.user2Info.name
resHtml = "<center><br/>";
resHtml += getRenderRaces(lobby.user1Info, lobby.user2Info);
resHtml += "<br/> <b>" + playerTurn + "</b> turn" + "</center>";
break;
case "Finish()":
renderFinish(lobby.maps, lobby.user1Info, lobby.user2Info);
break;
}
resHtml = resHtml + "</center>"
$("#playersStatsList").html(resHtml);
}
function getRenderRaces(userInfo1, userInfo2) {
function getRacesBlock(playerRaces, name){
let resHtml = "<div style='display: inline-block; border: black 1px solid; background-color: #e3e3e3;'>" + "<h4>" + name + "</h4>";
playerRaces.mainRaces.forEach((raceId) =>
resHtml += "<img class=\"raceIcon\" src=" + getRaceImageByNumber(raceId) + "> ");
playerRaces.additionalRaces.forEach((raceId) =>
resHtml += "<img class=\"raceIcon\" src=" + getRaceImageByNumber(raceId) + "> ");
if(existTextFieldRaces){
resHtml += "<span style='margin: 10px;'>" + playerRaces.raceTextInput + "</span>";
}
resHtml += "</div>";
return resHtml;
}
let resHtml = "";
resHtml += getRacesBlock(userInfo1.selectedRaces, userInfo1.name);
resHtml += "<div style='width: 100px; font-size: 24px; display: inline-block;'><b>VS</b></div>";
resHtml += getRacesBlock(userInfo2.selectedRaces, userInfo2.name);
return resHtml;
}
function addMessageToChat(message) {
var messageHtml = "<div class='msgln'> <b>" + message.userName + "</b>: " + message.message + "<br></div>";
var chatBox = $("#chatbox");
chatBox.append(messageHtml);
chatBox.scrollTop(40000);
}
function handleMapBanEvent(message) {
if (!isMuted) {
var audioPick = new Audio('/assets/sound/pick.mp3.mpeg');
audioPick.volume = 0.1;
audioPick.play();
}
var messageHtml = "<div class='msgln'><span style='color: #2C3D9B'>" + convertMapName(message.mapTechName) + "</span> banned by " + message.user + "<br></div>";
var chatBox = $("#chatbox");
chatBox.append(messageHtml);
chatBox.scrollTop(40000);
}
function banMap(map) {
ws.send(JSON.stringify({
type: "banMap",
map: map
}));
}
function setReady() {
ws.send(JSON.stringify({
type: "setReady"
}));
}
function setNotReady() {
ws.send(JSON.stringify({
type: "setNotReady"
}));
}
function changeLobbyType() {
var lobbyType = $("#deciderOption").val();
ws.send(JSON.stringify({
type: "changeLobbyType",
lobbyType: lobbyType
}));
}
function changeIsNecronSelected() {
var isNecronSelected = $("#isNecron").is(':checked');
ws.send(JSON.stringify({
type: "changeIsNecronSelected",
isNecronSelected: isNecronSelected
}));
}
function joinDecider(actorName) {
isObserver = false;
ws.send(JSON.stringify({
type: "joinDecider",
lobbyActorName: actorName
}));
}
function observerDecider(actorName) {
isObserver = true;
ws.send(JSON.stringify({
type: "observerDecider",
lobbyActorName: actorName
}));
}
function sendMessage() {
var userInput = $("#usermsg");
var message = userInput.val();
userInput.val("");
if (message !== "") {
ws.send(JSON.stringify({
type: "sendMessage",
message: message
}));
}
}
function kickSecondPlayer() {
ws.send(JSON.stringify({
type: "kickSecondPlayer"
}));
}
function convertMapName(techMapName) {
var mapPlayerSize = techMapName.charAt(0);
var mapName = techMapName.replace(mapPlayerSize + "p_", "").replaceAll("_", " ") +
" (" + mapPlayerSize + ")";
return mapName.charAt(0).toUpperCase() + mapName.slice(1);
}