mirror of
https://hacklab.nilfm.cc/felt
synced 2024-10-22 14:31:48 +00:00
125 lines
No EOL
3.3 KiB
JavaScript
125 lines
No EOL
3.3 KiB
JavaScript
let tableKey = {
|
|
name: "",
|
|
passcode: ""
|
|
}
|
|
|
|
let table = null;
|
|
|
|
let conn = null;
|
|
|
|
function showTableModal(show) {
|
|
const modal = document.getElementById("table_modal");
|
|
if (modal) {
|
|
modal.style.display = show ? "block" : "none";
|
|
}
|
|
}
|
|
|
|
function formatDice(r) {
|
|
const date = new Date(r.timestamp)
|
|
const p = document.createElement("p");
|
|
p.innerHTML = `${date.getFullYear()}-${date.getMonth() + 1}-${date.getDate()} ${date.getHours()}:${date.getMinutes()}:${date.getSeconds()} ${r.player} rolled ${r.roll.length}d${r.faces} ${(r.note ? "(" + r.note + ")" : "")}<br>[${r.roll}] (total ${r.roll.reduce((a,c)=>a+c,0)})`;
|
|
return p;
|
|
}
|
|
|
|
function logDice(dice, many) {
|
|
const diceLog = document.getElementById("dice_log");
|
|
if (!many) {
|
|
dice = [ dice ];
|
|
} else {
|
|
if (diceLog) {
|
|
diceLog.innerHTML = "";
|
|
}
|
|
}
|
|
if (diceLog) {
|
|
for(const r of dice) {
|
|
const p = formatDice(r);
|
|
diceLog.append(p);
|
|
p.scrollIntoView();
|
|
}
|
|
}
|
|
}
|
|
|
|
function makeUpToDate(table) {
|
|
if (table) {
|
|
if (table.diceRolls) {
|
|
logDice(table.diceRolls, true);
|
|
}
|
|
if (table.mapImageUrl) {
|
|
setMapImg(table.mapImageUrl);
|
|
}
|
|
}
|
|
}
|
|
|
|
function setMapImg(url) {
|
|
document.getElementById("map").innerHTML = `<img src="${url}"/>`
|
|
}
|
|
|
|
function dial() {
|
|
// get tableKey from UI
|
|
const tblNameInput = document.getElementById("input_table_name");
|
|
const tblPassInput = document.getElementById("input_table_pass");
|
|
if (tblNameInput && tblPassInput && tblNameInput.value && tblPassInput.value) {
|
|
tableKey.name = tblNameInput.value;
|
|
tableKey.passcode = tblPassInput.value;
|
|
|
|
if (conn) {
|
|
conn.close(1000);
|
|
}
|
|
conn = new WebSocket(`ws://${location.host}/subscribe`, `${tableKey.name}.${tableKey.passcode}`);
|
|
conn.addEventListener("close", e => {
|
|
if (e.code > 1001) {
|
|
// TODO: add message to let user know they are reconnecting
|
|
setTimeout(dial, 1000)
|
|
} else {
|
|
tabletop = document.getElementById("tabletop");
|
|
if (tabletop) {
|
|
tabletop.style.display = "none";
|
|
}
|
|
table = null;
|
|
}
|
|
});
|
|
conn.addEventListener("open", e => {
|
|
// TODO: add message to let user know they are at the table
|
|
console.info("socket connected");
|
|
tabletop = document.getElementById("tabletop");
|
|
if (tabletop) {
|
|
tabletop.style.display = "block";
|
|
}
|
|
});
|
|
conn.addEventListener("error", e => {
|
|
setErr(`${e.name}: ${e.message}`);
|
|
conn.close(3000);
|
|
})
|
|
|
|
conn.addEventListener("message", e => {
|
|
const data = JSON.parse(e.data);
|
|
if (table == null) {
|
|
// first fetch comes from mongo, so the rolls array in each diceRoll is a byte array and needs to be decoded
|
|
data.diceRolls.forEach(r=>{
|
|
r.roll = Uint8Array.from(atob(r.roll), c => c.charCodeAt(0))
|
|
})
|
|
table = data;
|
|
makeUpToDate(table);
|
|
} else {
|
|
if (data.diceRoll) {
|
|
logDice(data.diceRoll);
|
|
}
|
|
if (data.mapImageUrl) {
|
|
setMapImg(data.mapImageUrl);
|
|
}
|
|
}
|
|
console.log(data);
|
|
});
|
|
}
|
|
}
|
|
|
|
async function publish(msg) {
|
|
msg.key = tableKey;
|
|
const res = await fetch('/publish', {
|
|
method: 'POST',
|
|
body: JSON.stringify(msg)
|
|
});
|
|
if (!res.ok) {
|
|
setErr("Failed to publish message");
|
|
}
|
|
} |