From 21e3294ee03fdcf5ad59e5c9b9c2c9592c1763dd Mon Sep 17 00:00:00 2001 From: Geoffrey Allott Date: Thu, 11 Feb 2021 19:10:26 +0000 Subject: [PATCH] modernise javascript --- site/main.js | 12 +++--- site/modules/socket.js | 92 +++++++++++++++++++++++++--------------- site/style.css | 4 +- site/style/chatroom.css | 15 ++++--- site/style/game-list.css | 52 +++++++++++++++++++++-- site/style/login.css | 12 +++--- 6 files changed, 127 insertions(+), 60 deletions(-) diff --git a/site/main.js b/site/main.js index bfee369..3edbdda 100644 --- a/site/main.js +++ b/site/main.js @@ -1,21 +1,21 @@ import { Auth } from "./modules/auth.js"; import { Socket } from "./modules/socket.js"; -var sockets = []; +const sockets = []; function login() { - var username = document.getElementById("username-input").value; - var password = document.getElementById("password-input").value; + const username = document.getElementById("username-input").value; + const password = document.getElementById("password-input").value; delete document.getElementById("login-button").onclick; delete document.getElementById("password-input").onchange; - var auth = new Auth(username, password); - for (var socket of sockets) { + const auth = new Auth(username, password); + for (const socket of sockets) { socket.login(auth); } } window.onload = function() { - var container = document.getElementById("game-tile-background"); + const container = document.getElementById("game-tile-background"); sockets.push(new Socket(container, login)); sockets[0].show_login(); }; diff --git a/site/modules/socket.js b/site/modules/socket.js index 7f25db1..526a4ee 100644 --- a/site/modules/socket.js +++ b/site/modules/socket.js @@ -5,9 +5,9 @@ export class Socket { let proto = window.location.protocol === "https:" ? "wss:" : "ws:"; let uri = proto + "//" + window.location.host + "/api"; this.socket = new WebSocket(uri); - this.socket.onopen = this.onopen.bind(this); - this.socket.onmessage = this.onmessage.bind(this); - this.socket.onclose = this.onclose.bind(this); + this.socket.onopen = () => this.onopen(); + this.socket.onmessage = (msg) => this.onmessage(msg); + this.socket.onclose = () => this.onclose(); this.state = "Connecting"; } @@ -27,8 +27,12 @@ export class Socket { this.state = "LoginSent"; } + logout() { + this.send({type: "Logout"}); + } + onmessage(msg) { - var message = JSON.parse(msg.data); + const message = JSON.parse(msg.data); console.log("<<", message); switch (message.type) { case "LoginAuthChallenge": @@ -68,9 +72,6 @@ export class Socket { break; case "TakeActionSuccess": this.add_action({username: this.auth.username, action: this.action}); - if (this.action.action === "Leave") { - this.send({type: "JoinLobby", filter: ""}); - } delete this.action; break; case "TakeActionFailure": @@ -108,29 +109,29 @@ export class Socket { game_element(game) { console.log("getting game element for ", game); - var game_element = document.createElement("div"); + const game_element = document.createElement("div"); game_element.classList.add("game-summary"); - var id = document.createElement("div"); + const id = document.createElement("div"); id.innerText = "#" + game.id; id.classList.add("game-id"); game_element.append(id); - var title = document.createElement("div"); + const title = document.createElement("div"); title.innerText = game.settings.title; title.classList.add("game-title"); game_element.append(title); - var format = document.createElement("div"); + const format = document.createElement("div"); format.innerText = game.settings.format; format.classList.add("game-format"); game_element.append(format); - var settings = document.createElement("ul"); + const settings = document.createElement("ul"); settings.classList.add("game-settings"); - for (var setting of Object.keys(game.settings)) { + for (const setting of Object.keys(game.settings)) { if (setting !== "id" && setting !== "title" && setting !== "format") { - var li = document.createElement("li"); + const li = document.createElement("li"); li.innerText = setting + ": " + game.settings[setting]; settings.append(li); } @@ -143,9 +144,9 @@ export class Socket { } new_game(game) { - var is_at_end = this.game_list_container.scrollTop + this.game_list_container.clientHeight == this.game_list_container.scrollHeight; + const is_at_end = this.game_list_container.scrollTop + this.game_list_container.clientHeight == this.game_list_container.scrollHeight; this.games.push(game); - var game_element = this.game_element(game); + const game_element = this.game_element(game); this.game_list.append(game_element); if (is_at_end) { this.game_list_container.scrollTo({ @@ -162,23 +163,39 @@ export class Socket { create_game_list() { this.container.textContent = ""; + const game_list_outside = document.createElement("div"); + game_list_outside.classList.add("game-list-outside"); this.game_list_container = document.createElement("div"); this.game_list_container.classList.add("game-list-container"); this.game_list = document.createElement("div"); this.game_list.classList.add("game-list"); this.game_list_container.append(this.game_list); - this.container.append(this.game_list_container); + game_list_outside.append(this.game_list_container); + this.game_list_filter_input = document.createElement("input"); + game_list_outside.append(this.game_list_filter_input); + const game_list_options = document.createElement("button"); + const game_list_option_menu = document.createElement("div"); + game_list_option_menu.classList.add("game-list-option-menu"); + game_list_option_menu.classList.add("hidden"); + const game_list_option_logout = document.createElement("div"); + game_list_option_logout.innerText = "Logout"; + game_list_option_logout.onclick = () => this.logout(); + game_list_option_menu.append(game_list_option_logout); + game_list_options.append(game_list_option_menu); + game_list_options.onclick = () => game_list_option_menu.classList.toggle("hidden"); + game_list_outside.append(game_list_options); + this.container.append(game_list_outside); this.redraw_games(); } redraw_games() { this.game_list.textContent = ""; - for (var game of this.games) { - var game_element = this.game_element(game); + for (const game of this.games) { + const game_element = this.game_element(game); this.game_list.append(game_element); } this.game_list_container.scrollTo({ - top: this.game_list.clientHeight - this.container.clientHeight, + top: this.game_list_container.scrollHeight - this.game_list_container.clientHeight, behavior: "auto" }); } @@ -201,7 +218,7 @@ export class Socket { this.chatroom_input.value = ""; }; this.chatroom.append(this.chatroom_input); - var chatroom_close = document.createElement("button"); + const chatroom_close = document.createElement("button"); chatroom_close.classList.add("chatroom-close"); chatroom_close.innerText = "✗"; chatroom_close.onclick = () => this.take_action({action: "Leave"}); @@ -211,13 +228,13 @@ export class Socket { } join_element(username) { - var join_element = document.createElement("div"); + const join_element = document.createElement("div"); join_element.classList.add("chatroom-join"); - var username_element = document.createElement("div"); + const username_element = document.createElement("div"); username_element.classList.add("chatroom-username"); username_element.innerText = username; join_element.append(username_element); - var text_element = document.createElement("div"); + const text_element = document.createElement("div"); text_element.classList.add("chatroom-text"); text_element.innerText = "Joined"; join_element.append(text_element); @@ -225,13 +242,13 @@ export class Socket { } message_element(username, message) { - var message_element = document.createElement("div"); + const message_element = document.createElement("div"); message_element.classList.add("chatroom-message"); - var username_element = document.createElement("div"); + const username_element = document.createElement("div"); username_element.classList.add("chatroom-username"); username_element.innerText = username; message_element.append(username_element); - var text_element = document.createElement("div"); + const text_element = document.createElement("div"); text_element.classList.add("chatroom-text"); text_element.innerText = message; message_element.append(text_element); @@ -239,23 +256,23 @@ export class Socket { } leave_element(username) { - var leave_element = document.createElement("div"); + const leave_element = document.createElement("div"); leave_element.classList.add("chatroom-leave"); - var username_element = document.createElement("div"); + const username_element = document.createElement("div"); username_element.classList.add("chatroom-username"); username_element.innerText = username; leave_element.append(username_element); - var text_element = document.createElement("div"); + const text_element = document.createElement("div"); text_element.classList.add("chatroom-text"); text_element.innerText = "Left"; leave_element.append(text_element); return leave_element; } - add_action(user_action) { + add_action(user_action, initialising) { switch (this.game.summary.settings.format) { case "Chatroom": - var is_at_end = this.chatroom_chat.scrollTop + this.chatroom_chat.clientHeight == this.chatroom_chat.scrollHeight; + const is_at_end = this.chatroom_chat.scrollTop + this.chatroom_chat.clientHeight == this.chatroom_chat.scrollHeight; switch (user_action.action.action) { case "Join": this.game.users.add(user_action.username); @@ -267,6 +284,9 @@ export class Socket { case "Leave": this.game.users.delete(user_action.username); this.chatroom_chat.append(this.leave_element(user_action.username)); + if (!initialising && user_action.username === this.auth.username) { + this.send({type: "JoinLobby", filter: ""}); + } break; default: console.error("Unknown action for chatroom", user_action); @@ -284,8 +304,8 @@ export class Socket { redraw_chatroom() { this.chatroom_chat.textContent = ""; - for (var user_action of this.game.state.actions) { - this.add_action(user_action); + for (const user_action of this.game.state.actions) { + this.add_action(user_action, true); } } @@ -303,7 +323,9 @@ export class Socket { } onclose() { - console.error("Websocket closed unexpectedly"); + const reconnect_timeout = 3000; + console.error("Websocket closed unexpectedly - attempting reconnect in " + reconnect_timeout + "ms"); this.state = "Disconnected"; + setTimeout(() => window.location.reload(), reconnect_timeout); } } diff --git a/site/style.css b/site/style.css index a661bdc..1528a1d 100644 --- a/site/style.css +++ b/site/style.css @@ -6,7 +6,7 @@ html, body { width: 100%; height: 100%; margin: 0; - overflow: hidden; + overflow: clip; } .hidden { @@ -18,5 +18,5 @@ html, body { height: 100%; display: grid; grid: 1fr / 1fr; - overflow: hidden; + overflow: clip; } diff --git a/site/style/chatroom.css b/site/style/chatroom.css index e5846e5..cc08952 100644 --- a/site/style/chatroom.css +++ b/site/style/chatroom.css @@ -2,7 +2,7 @@ width: 100%; height: 100%; display: grid; - font-size: 1.5rem; + font-size: 4vw; overflow: hidden; position: relative; background-color: #dfefff; @@ -16,7 +16,7 @@ .chatroom > input { width: 100%; - height: 3rem; + height: 10vw; font-size: inherit; align-self: end; } @@ -27,13 +27,13 @@ .chatroom-username { justify-self: left; - width: 12rem; + width: 36vw; height: 100%; - margin: 0.25rem; + margin: 0.5vw; background-color: grey; color: white; text-align: center; - border-radius: 1rem; + border-radius: 3vw; } .chatroom-join > .chatroom-username { @@ -53,8 +53,8 @@ justify-self: right; text-align: left; height: 100%; - margin: 0.25rem; - width: calc(100% - 12rem); + margin: 0.5vw; + width: calc(100% - 36vw); } .chatroom-close { @@ -62,4 +62,5 @@ position: absolute; right: 0; top: 0; + font-size: inherit; } diff --git a/site/style/game-list.css b/site/style/game-list.css index 6780aaf..d2506f5 100644 --- a/site/style/game-list.css +++ b/site/style/game-list.css @@ -1,4 +1,50 @@ +.game-list-outside { + width: 100%; + height: 100%; + display: grid; + overflow: hidden; + font-size: 4vw; + grid: auto-flow / 1fr 8vw; +} + +.game-list-outside > input { + grid-column: 1; + grid-row: 2; + align-self: end; + height: 10vw; + font-size: inherit; +} + +.game-list-outside > button { + grid-column: 2; + grid-row: 2; + align-self: end; + height: 10vw; + font-size: inherit; +} + +.game-list-option-menu { + display: block; + position: absolute; + bottom: 6vw; + right: 0; +} + +.game-list-option-menu > div { + padding-left: 2vw; + padding-right: 2vw; + border: 1px solid grey; + font-size: 8vw; + background-color: white; +} + +.game-list-option-menu > div:hover { + background-color: #dfefff; +} + .game-list-container { + grid-column: 1 / span 2; + grid-row: 1; width: 100%; height: 100%; overflow-x: clip; @@ -7,8 +53,6 @@ .game-list { width: 100%; - display: grid; - grid-auto-rows: 30vw; } @keyframes new-game { @@ -29,13 +73,13 @@ .game-summary { border: 1px solid grey; border-top: none; + height: 30vw; font-family: sans; - font-size: 4vw; display: grid; grid: 'id title format' 'settings settings settings' 'settings settings settings'; - animation: new-game 2s; + /*animation: new-game 2s; TODO */ cursor: pointer; } diff --git a/site/style/login.css b/site/style/login.css index 53d4020..4279b3a 100644 --- a/site/style/login.css +++ b/site/style/login.css @@ -11,11 +11,11 @@ grid-column: 2 / 3; grid-row: 2 / 3; background-color: skyblue; - border-radius: 2vmax; - padding: 4vmax; + border-radius: 2vw; + padding: 4vw; display: grid; grid: 1fr; - font-size: 4vmax; + font-size: 4vw; } #login > label { @@ -24,16 +24,16 @@ #login > input { font-size: inherit; - margin-bottom: 1vmax; + margin-bottom: 1vw; } #login > button { font-size: inherit; - margin-top: 2vmax; + margin-top: 2vw; } #login > #login-error { - font-size: 2vmax; + font-size: 2vw; color: red; margin-bottom: 0; } -- 2.34.1