added text shadow, users are broadcasted properly to clients

This commit is contained in:
Meleeman01 2024-12-09 18:17:36 -06:00
parent bf85779edb
commit 24e2c2735e
2 changed files with 119 additions and 11 deletions

View File

@ -4,12 +4,18 @@
<meta charset="UTF-8"> <meta charset="UTF-8">
<title>Multiplayer Game</title> <title>Multiplayer Game</title>
<link rel="stylesheet" type="text/css" href="mflx.min.css"> <link rel="stylesheet" type="text/css" href="mflx.min.css">
<style type="text/css">
.text-with-shadow {
text-shadow: -1px -1px 1px #000, 1px -1px 1px #000,
-1px 1px 1px #000, 1px 1px 1px #000; color: white;
}
</style>
</head> </head>
<body> <body>
<button id="create-room">Create Room</button> <button id="create-room">Create Room</button>
<input id="join-code" placeholder="Enter room code"> <input id="join-code" placeholder="Enter room code">
<button id="join-room">Join Room</button> <button id="join-room">Join Room</button>
<div class="players"></div> <div class="flx(wrap) players"></div>
<div id="status"></div> <div id="status"></div>
<button id="start-game" style="display: none;">Start Game</button> <button id="start-game" style="display: none;">Start Game</button>
<button id="spin-wheel" style="display: none;">Spin Wheel</button> <button id="spin-wheel" style="display: none;">Spin Wheel</button>
@ -23,8 +29,61 @@
</div> </div>
<script> <script>
//================general Purpose functions=========================================//
function cryptoSecureShuffle(array) {
const shuffledArray = [...array]; // Create a copy to avoid mutating the original array
const n = shuffledArray.length;
//wheel========================================================================== // Fisher-Yates shuffle
for (let i = n - 1; i > 0; i--) {
// Generate a cryptographically secure random index
let randIndex;
do {
// Generate a random value in the range [0, 2^32)
const randomBuffer = new Uint32Array(1);
window.crypto.getRandomValues(randomBuffer);
randIndex = randomBuffer[0] >>> 0; // Convert to a non-negative integer
} while (randIndex >= Math.floor(2 ** 32 / (i + 1)) * (i + 1)); // Avoid bias
// Compute the unbiased index
randIndex %= (i + 1);
// Swap the elements
[shuffledArray[i], shuffledArray[randIndex]] = [shuffledArray[randIndex], shuffledArray[i]];
}
return shuffledArray;
}
//====================making Name Tags/ assigning colors to names================//
let nameColors = [
'#ff0000','#ff8700','#ffd300','#deff0a','#a1ff0a',
'#0aff99','#0aefff','#147df5','#580aff','#be0aff'
]
nameColors = cryptoSecureShuffle(nameColors);
function assignColors(names, colors) {
let result = [];
let n = 0; // Keep track of name index
let c = 0; // Keep track of color index
if (names.length > colors.length) {
// Assign colors cyclically
while (n < names.length) {
result.push({ name: names[n], color: colors[c] });
n++;
c = (c + 1) % colors.length; // Cycle through the colors
}
} else {
// Assign colors directly, keeping track of indices
while (n < names.length) {
result.push({ name: names[n], color: colors[c] });
n++;
c++;
}
}
return result;
}
//=========================================wheel==========================================//
const wheel = [ const wheel = [
'lose a turn', 800, 350, 450, 700, 300, 600, 5000, 'lose a turn', 800, 350, 450, 700, 300, 600, 5000,
300, 600, 300, 500, 800, 550, 400, 300, 900, 500, 'spin again', 300, 600, 300, 500, 800, 550, 400, 300, 900, 500, 'spin again',
@ -132,7 +191,6 @@
spinSpeed = wheelSpinSpeedData[targetIndex]; // Initial speed spinSpeed = wheelSpinSpeedData[targetIndex]; // Initial speed
function animate() { function animate() {
if ( spinSpeed < 0.001) { if ( spinSpeed < 0.001) {
spinning = false; spinning = false;
console.log(`Landed on: ${wheel[targetIndex]}`); console.log(`Landed on: ${wheel[targetIndex]}`);
@ -163,6 +221,21 @@
// Trigger spin after 2 seconds // Trigger spin after 2 seconds
//setTimeout(simulateServerResponse, 2000); //setTimeout(simulateServerResponse, 2000);
//==================================end of Wheel=====================================//
function drawPlayers(message) {
let players = document.querySelector('.players');
//assignColors(names, colors) {
let processedNametags = assignColors(message.clients,nameColors);
const playersHtml = processedNametags.map(client => {
if (client.name === message.leaderName) {
return `<span class='mr-2 btn is-round text-with-shadow' style='background-color:${client.color};'>⭐ ${client.name} ⭐</span>`; // Highlight the leader with stars
} else {
return `<span class='mr-2 btn is-round text-with-shadow' style='background-color:${client.color};'>${client.name}</span>`;
}
}).join(""); // Combine all elements into a single string
players.innerHTML = playersHtml;
}
const socket = new WebSocket("ws://localhost:8080"); const socket = new WebSocket("ws://localhost:8080");
document.getElementById("create-room").onclick = () => { document.getElementById("create-room").onclick = () => {
@ -188,18 +261,25 @@
document.getElementById("guess-letter").value = ""; // Clear input document.getElementById("guess-letter").value = ""; // Clear input
}; };
socket.onmessage = (event) => { socket.onmessage = (event) => {
const message = JSON.parse(event.data); const message = JSON.parse(event.data);
if (message.type === "room_created") { if (message.type === "room_created") {
document.getElementById("status").innerText = `Room created! Code: ${message.roomCode}`; document.getElementById("status").innerText = `Room created! Code: ${message.roomCode}`;
drawPlayers(message);
if (message.isLeader) { if (message.isLeader) {
document.getElementById("start-game").style.display = "inline"; document.getElementById("start-game").style.display = "inline";
} }
} }
if (message.type === "joined_room") { if (message.type === "joined_room") {
drawPlayers(message);
const status = message.isLeader ? "You are the party leader!" : "You joined the room!"; const status = message.isLeader ? "You are the party leader!" : "You joined the room!";
// document.querySelector('.players').innerHtml += `<span>${}<span>`
document.getElementById("status").innerText = `Room Code: ${message.roomCode} - ${status}`; document.getElementById("status").innerText = `Room Code: ${message.roomCode} - ${status}`;
if (message.isLeader) { if (message.isLeader) {
document.getElementById("start-game").style.display = "inline"; document.getElementById("start-game").style.display = "inline";
@ -246,6 +326,7 @@
} }
if (message.type === "new_leader") { if (message.type === "new_leader") {
drawPlayers(message);
document.getElementById("status").innerText = "You are now the party leader!"; document.getElementById("status").innerText = "You are now the party leader!";
} }

View File

@ -50,7 +50,7 @@ wss.on("connection", (ws) => {
if (data.type === "create_room") { if (data.type === "create_room") {
const roomCode = uuidv4().slice(0, 5); const roomCode = uuidv4().slice(0, 5);
ws.name = DefaultNames ws.name = getRandomName();
rooms[roomCode] = { rooms[roomCode] = {
clients: [ws], clients: [ws],
leader: ws, leader: ws,
@ -61,7 +61,10 @@ wss.on("connection", (ws) => {
}, },
}; };
ws.roomCode = roomCode; ws.roomCode = roomCode;
ws.send(JSON.stringify({ type: "room_created", roomCode, isLeader: true })); ws.send(JSON.stringify({ type: "room_created", roomCode,
isLeader: true,
clients: rooms[roomCode].clients.map((i)=> i.name),
}));
} }
if (data.type === "join_room") { if (data.type === "join_room") {
@ -76,14 +79,26 @@ wss.on("connection", (ws) => {
ws.send(JSON.stringify({ type: "error", message: "Game has already Started!!!" })); ws.send(JSON.stringify({ type: "error", message: "Game has already Started!!!" }));
} }
else { else {
ws.name = getRandomName();
rooms[roomCode].clients.push(ws); rooms[roomCode].clients.push(ws);
ws.roomCode = roomCode; ws.roomCode = roomCode;
ws.send(JSON.stringify({ const room = rooms[ws.roomCode];
room.clients.forEach((client) => {
client.send(JSON.stringify({
type: "joined_room", roomCode, type: "joined_room", roomCode,
isLeader: rooms[roomCode].leader === ws isLeader: rooms[roomCode].leader === ws ,
clients: rooms[roomCode].clients.map((i)=> i.name),
leaderName:rooms[roomCode].leader.name
}));
});
ws.send(JSON.stringify({
type: "joined_room_you", roomCode,
isLeader: rooms[roomCode].leader === ws,
you:ws.name
})); }));
} }
console.log('clients: ',rooms[roomCode].clients); //console.log('clients: ',rooms[roomCode].leader.name);
} }
if (data.type === "start_game") { if (data.type === "start_game") {
@ -136,12 +151,24 @@ wss.on("connection", (ws) => {
ws.on("close", () => { ws.on("close", () => {
if (ws.roomCode && rooms[ws.roomCode]) { if (ws.roomCode && rooms[ws.roomCode]) {
console.log('closing');
const room = rooms[ws.roomCode]; const room = rooms[ws.roomCode];
const roomCode = ws.roomCode;
room.clients = room.clients.filter((client) => client !== ws); room.clients = room.clients.filter((client) => client !== ws);
if (room.leader === ws && room.clients.length > 0) { if (room.leader === ws && room.clients.length > 0) {
console.log('closing within room leader')
room.leader = room.clients[0]; room.leader = room.clients[0];
room.leader.send(JSON.stringify({ type: "new_leader" })); room.leader.send(JSON.stringify({ type: "new_leader" }));
} }
room.clients.forEach((client) =>
client.send(JSON.stringify({
type: "joined_room", roomCode,
isLeader: rooms[roomCode].leader === ws ,
clients: rooms[roomCode].clients.map((i)=> i.name),
leaderName:rooms[roomCode].leader.name
}))
);
if (room.clients.length === 0) delete rooms[ws.roomCode]; if (room.clients.length === 0) delete rooms[ws.roomCode];
} }
}); });