diff --git a/public/src/js/p2.js b/public/src/js/p2.js index 127b622..a8a1d34 100644 --- a/public/src/js/p2.js +++ b/public/src/js/p2.js @@ -116,6 +116,7 @@ class P2Connection{ this.kaAmount = 0 this.results = false this.branch = "normal" + scoreStorage.clearP2() break case "gameend": this.otherConnected = false @@ -130,6 +131,7 @@ class P2Connection{ this.hashLock = false } this.name = null + scoreStorage.clearP2() break case "gameresults": this.results = {} @@ -157,6 +159,7 @@ class P2Connection{ this.clearMessage("users") this.otherConnected = true this.session = true + scoreStorage.clearP2() if("player" in response.value){ this.player = response.value.player === 2 ? 2 : 1 } @@ -164,6 +167,37 @@ class P2Connection{ case "name": this.name = response.value ? response.value.toString() : response.value break + case "getcrowns": + if(response.value){ + var output = {} + for(var i in response.value){ + if(response.value[i]){ + var score = scoreStorage.get(response.value[i], false, true) + if(score){ + var crowns = {} + for(var diff in score){ + if(diff !== "title"){ + crowns[diff] = { + crown: score[diff].crown + } + } + } + }else{ + var crowns = null + } + output[response.value[i]] = crowns + } + } + p2.send("crowns", output) + } + break + case "crowns": + if(response.value){ + for(var i in response.value){ + scoreStorage.addP2(i, false, response.value[i], true) + } + } + break } } onhashchange(){ diff --git a/public/src/js/scorestorage.js b/public/src/js/scorestorage.js index db6dd2b..1bf8ed8 100644 --- a/public/src/js/scorestorage.js +++ b/public/src/js/scorestorage.js @@ -1,6 +1,9 @@ class ScoreStorage{ constructor(){ this.scores = {} + this.scoresP2 = {} + this.requestP2 = new Set() + this.requestedP2 = new Set() this.songTitles = {} this.difficulty = ["oni", "ura", "hard", "normal", "easy"] this.scoreKeys = ["points", "good", "ok", "bad", "maxCombo", "drumroll"] @@ -151,15 +154,40 @@ class ScoreStorage{ } } } + getP2(song, difficulty, isHash){ + if(!song){ + return this.scoresP2 + }else{ + var hash = isHash ? song : this.titleHash(song) + if(!(hash in this.scoresP2) && !this.requestP2.has(hash) && !this.requestedP2.has(hash)){ + this.requestP2.add(hash) + this.requestedP2.add(hash) + } + if(difficulty){ + if(hash in this.scoresP2){ + return this.scoresP2[hash][difficulty] + } + }else{ + return this.scoresP2[hash] + } + } + } add(song, difficulty, scoreObject, isHash, setTitle, saveFailed){ var hash = isHash ? song : this.titleHash(song) if(!(hash in this.scores)){ this.scores[hash] = {} } - if(setTitle){ - this.scores[hash].title = setTitle + if(difficulty){ + if(setTitle){ + this.scores[hash].title = setTitle + } + this.scores[hash][difficulty] = scoreObject + }else{ + this.scores[hash] = scoreObject + if(setTitle){ + this.scores[hash].title = setTitle + } } - this.scores[hash][difficulty] = scoreObject this.writeString(hash) this.write() if(saveFailed){ @@ -186,6 +214,23 @@ class ScoreStorage{ }).catch(() => this.add(song, difficulty, scoreObject, isHash, setTitle, true)) } } + addP2(song, difficulty, scoreObject, isHash, setTitle){ + var hash = isHash ? song : this.titleHash(song) + if(!(hash in this.scores)){ + this.scoresP2[hash] = {} + } + if(difficulty){ + if(setTitle){ + this.scoresP2[hash].title = setTitle + } + this.scoresP2[hash][difficulty] = scoreObject + }else{ + this.scoresP2[hash] = scoreObject + if(setTitle){ + this.scoresP2[hash].title = setTitle + } + } + } template(){ var template = {crown: ""} for(var i in this.scoreKeys){ @@ -257,4 +302,21 @@ class ScoreStorage{ return Promise.resolve() } } + eventLoop(){ + if(p2.session && this.requestP2.size){ + var req = [] + this.requestP2.forEach(hash => { + req.push(hash) + }) + this.requestP2.clear() + if(req.length){ + p2.send("getcrowns", req) + } + } + } + clearP2(){ + this.scoresP2 = {} + this.requestP2.clear() + this.requestedP2.clear() + } } diff --git a/public/src/js/songselect.js b/public/src/js/songselect.js index 63c5b1f..a67e9d0 100644 --- a/public/src/js/songselect.js +++ b/public/src/js/songselect.js @@ -1495,20 +1495,33 @@ class SongSelect{ } var drawDifficulty = (ctx, i, currentUra) => { if(currentSong.courses[this.difficultyId[i]] || currentUra){ - var score = scoreStorage.get(currentSong.hash, false, true) var crownDiff = currentUra ? "ura" : this.difficultyId[i] - var crownType = "" - if(score && score[crownDiff]){ - crownType = score[crownDiff].crown + var players = p2.session ? 2 : 1 + var score = [scoreStorage.get(currentSong.hash, false, true)] + if(p2.session){ + score[p2.player === 1 ? "push" : "unshift"](scoreStorage.getP2(currentSong.hash, false, true)) + } + var reversed = false + for(var a = players; a--;){ + var crownType = "" + var p = reversed ? -(a - 1) : a + if(score[p] && score[p][crownDiff]){ + crownType = score[p][crownDiff].crown + } + if(!reversed && players === 2 && p === 1 && crownType){ + reversed = true + a++ + }else{ + this.draw.crown({ + ctx: ctx, + type: crownType, + x: (songSel ? x + 33 + i * 60 : x + 402 + i * 100) + (players === 2 ? p === 0 ? -13 : 13 : 0), + y: songSel ? y + 75 : y + 30, + scale: 0.25, + ratio: this.ratio / this.pixelRatio + }) + } } - this.draw.crown({ - ctx: ctx, - type: crownType, - x: songSel ? x + 33 + i * 60 : x + 402 + i * 100, - y: songSel ? y + 75 : y + 30, - scale: 0.25, - ratio: this.ratio / this.pixelRatio - }) if(songSel){ var _x = x + 33 + i * 60 var _y = y + 120 @@ -2269,6 +2282,11 @@ class SongSelect{ ctx.restore() } + + if(p2.session && (!this.lastScoreMS || ms > this.lastScoreMS + 1000)){ + this.lastScoreMS = ms + scoreStorage.eventLoop() + } } drawClosedSong(config){ @@ -2327,31 +2345,38 @@ class SongSelect{ drawSongCrown(config){ if(!config.song.action && config.song.hash){ var ctx = config.ctx - var score = scoreStorage.get(config.song.hash, false, true) + var players = p2.session ? 2 : 1 + var score = [scoreStorage.get(config.song.hash, false, true)] + var scoreDrawn = [] + if(p2.session){ + score[p2.player === 1 ? "push" : "unshift"](scoreStorage.getP2(config.song.hash, false, true)) + } for(var i = this.difficultyId.length; i--;){ var diff = this.difficultyId[i] - if(!score){ - break - } - if(config.song.courses[this.difficultyId[i]] && score[diff] && score[diff].crown){ - this.draw.crown({ - ctx: ctx, - type: score[diff].crown, - x: config.x + this.songAsset.width / 2, - y: config.y - 13, - scale: 0.3, - ratio: this.ratio / this.pixelRatio - }) - this.draw.diffIcon({ - ctx: ctx, - diff: i, - x: config.x + this.songAsset.width / 2 + 8, - y: config.y - 8, - scale: diff === "hard" || diff === "normal" ? 0.45 : 0.5, - border: 6.5, - small: true - }) - break + for(var p = players; p--;){ + if(!score[p] || scoreDrawn[p]){ + continue + } + if(config.song.courses[this.difficultyId[i]] && score[p][diff] && score[p][diff].crown){ + this.draw.crown({ + ctx: ctx, + type: score[p][diff].crown, + x: (config.x + this.songAsset.width / 2) + (players === 2 ? p === 0 ? -13 : 13 : 0), + y: config.y - 13, + scale: 0.3, + ratio: this.ratio / this.pixelRatio + }) + this.draw.diffIcon({ + ctx: ctx, + diff: i, + x: (config.x + this.songAsset.width / 2 + 8) + (players === 2 ? p === 0 ? -13 : 13 : 0), + y: config.y - 8, + scale: diff === "hard" || diff === "normal" ? 0.45 : 0.5, + border: 6.5, + small: true + }) + scoreDrawn[p] = true + } } } } diff --git a/server.py b/server.py index 4235c00..587e0db 100644 --- a/server.py +++ b/server.py @@ -283,6 +283,12 @@ async def connection(ws, path): ws.send(sent_msg), user["other_user"]["ws"].send(sent_msg) ]) + elif type == "crowns" or type == "getcrowns": + if user["other_user"]["action"] == "songsel": + sent_msg = msgobj(type, value) + await asyncio.wait([ + user["other_user"]["ws"].send(sent_msg) + ]) elif type == "join": # Start game if value == None: