diff --git a/public/assets/img/vectors.json b/public/assets/img/vectors.json index 536fb30..eb64b07 100644 --- a/public/assets/img/vectors.json +++ b/public/assets/img/vectors.json @@ -66,5 +66,14 @@ "", "logo5": +"", + +"category": +"", + +"categoryShadow": +"", + +"categoryHighlight": "" } diff --git a/public/src/js/canvasdraw.js b/public/src/js/canvasdraw.js index baea01c..df8a25c 100644 --- a/public/src/js/canvasdraw.js +++ b/public/src/js/canvasdraw.js @@ -45,6 +45,12 @@ shadow: new Path2D(vectors.optionsShadow) } + this.categoryPath = { + main: new Path2D(vectors.category), + shadow: new Path2D(vectors.categoryShadow), + highlight: new Path2D(vectors.categoryHighlight) + } + this.regex = { comma: /[,.]/, ideographicComma: /[、。]/, @@ -225,10 +231,14 @@ highlight(config){ var ctx = config.ctx ctx.save() - var _x = config.x + 3.5 - var _y = config.y + 3.5 - var _w = config.w - 7 - var _h = config.h - 7 + if(config.shape){ + ctx.translate(config.x, config.y) + }else{ + var _x = config.x + 3.5 + var _y = config.y + 3.5 + var _w = config.w - 7 + var _h = config.h - 7 + } if(config.animate){ ctx.globalAlpha = this.fade((this.getMS() - config.animateMS) % 2000 / 2000) }else if(config.opacity){ @@ -243,19 +253,25 @@ h: _h, radius: config.radius }) - }else{ + }else if(!config.shape){ ctx.beginPath() ctx.rect(_x, _y, _w, _h) } + if(config.shape){ + var stroke = () => ctx.stroke(config.shape) + }else{ + var stroke = () => ctx.stroke() + } + var size = config.size || 14 ctx.strokeStyle = "rgba(255, 249, 1, 0.45)" - ctx.lineWidth = 14 - ctx.stroke() + ctx.lineWidth = size + stroke() ctx.strokeStyle = "rgba(255, 249, 1, .8)" - ctx.lineWidth = 8 - ctx.stroke() + ctx.lineWidth = 8 / 14 * size + stroke() ctx.strokeStyle = "#fff" - ctx.lineWidth = 6 - ctx.stroke() + ctx.lineWidth = 6 / 14 * size + stroke() ctx.restore() } @@ -1472,6 +1488,48 @@ ctx.restore() } + category(config){ + var ctx = config.ctx + ctx.save() + + ctx.translate(config.x, config.y) + if(config.scale || config.right){ + ctx.scale((config.right ? -1 : 1) * (config.scale || 1), config.scale || 1) + } + ctx.translate(-15.5 + 14, -11) + for(var i = 0; i < 4; i++){ + if(i < 2){ + ctx.lineWidth = 6 + ctx.strokeStyle = "#000" + ctx.stroke(this.categoryPath.main) + }else{ + ctx.fillStyle = config.fill + ctx.fill(this.categoryPath.main) + ctx.fillStyle = "rgba(255, 255, 255, 0.25)" + ctx.fill(this.categoryPath.main) + ctx.fillStyle = "rgba(0, 0, 0, 0.25)" + ctx.fill(this.categoryPath.shadow) + } + if(i % 2 === 0){ + ctx.translate(-14, 0) + }else if(i === 1){ + ctx.translate(14, 0) + } + } + if(config.highlight){ + this.highlight({ + ctx: ctx, + x: 0, + y: 0, + opacity: 0.8, + shape: this.categoryPath.highlight, + size: 8 + }) + } + + ctx.restore() + } + alpha(amount, ctx, callback, winW, winH){ if(amount >= 1){ return callback(ctx) diff --git a/public/src/js/songselect.js b/public/src/js/songselect.js index dfa2368..926d1e1 100644 --- a/public/src/js/songselect.js +++ b/public/src/js/songselect.js @@ -358,7 +358,7 @@ class SongSelect{ } } - keyPress(pressed, name, event){ + keyPress(pressed, name, event, repeat){ if(pressed){ if(!this.pressedKeys[name]){ this.pressedKeys[name] = this.getMS() + 300 @@ -370,6 +370,7 @@ class SongSelect{ if(name === "ctrl" || name === "shift" || !this.redrawRunning){ return } + var shift = event ? event.shiftKey : this.pressedKeys["shift"] if(this.state.screen === "song"){ if(name === "confirm"){ this.toSelectDifficulty() @@ -378,20 +379,24 @@ class SongSelect{ }else if(name === "session"){ this.toSession() }else if(name === "left"){ - if(this.pressedKeys["shift"]){ - this.categoryJump(-1) + if(shift){ + if(!repeat){ + this.categoryJump(-1) + } }else{ this.moveToSong(-1) } }else if(name === "right"){ - if(this.pressedKeys["shift"]){ - this.categoryJump(1) + if(shift){ + if(!repeat){ + this.categoryJump(1) + } }else{ this.moveToSong(1) } - }else if(name === "jump_left"){ + }else if(name === "jump_left" && !repeat){ this.categoryJump(-1) - }else if(name === "jump_right"){ + }else if(name === "jump_right" && !repeat){ this.categoryJump(1) } }else if(this.state.screen === "difficulty"){ @@ -401,7 +406,7 @@ class SongSelect{ }else if(this.selectedDiff === 1){ this.toOptions(1) }else{ - this.toLoadSong(this.selectedDiff - this.diffOptions.length, this.pressedKeys["shift"], this.pressedKeys["ctrl"]) + this.toLoadSong(this.selectedDiff - this.diffOptions.length, shift, this.pressedKeys["ctrl"]) } }else if(name === "back" || name === "session"){ this.toSongSelect() @@ -441,7 +446,9 @@ class SongSelect{ var touch = true } if(this.state.screen === "song"){ - if(mouse.x > 641 && mouse.y > 603){ + if(20 < mouse.y && mouse.y < 90 && 410 < mouse.x && mouse.x < 880 && (mouse.x < 540 || mouse.x > 750)){ + this.categoryJump(mouse.x < 640 ? -1 : 1) + }else if(mouse.x > 641 && mouse.y > 603){ this.toSession() }else{ var moveBy = this.songSelMouse(mouse.x, mouse.y) @@ -490,7 +497,9 @@ class SongSelect{ var mouse = this.mouseOffset(event.offsetX, event.offsetY) var moveTo = null if(this.state.screen === "song"){ - if(mouse.x > 641 && mouse.y > 603 && p2.socket.readyState === 1 && !assets.customSongs){ + if(20 < mouse.y && mouse.y < 90 && 410 < mouse.x && mouse.x < 880 && (mouse.x < 540 || mouse.x > 750)){ + moveTo = mouse.x < 640 ? "categoryPrev" : "categoryNext" + }else if(mouse.x > 641 && mouse.y > 603 && p2.socket.readyState === 1 && !assets.customSongs){ moveTo = "session" }else{ var moveTo = this.songSelMouse(mouse.x, mouse.y) @@ -608,7 +617,7 @@ class SongSelect{ this.state.locked = 1 this.endPreview() - assets.sounds["se_jump"].play() + this.playSound("se_jump") } moveToDiff(moveBy){ @@ -818,7 +827,7 @@ class SongSelect{ for(var key in this.pressedKeys){ if(this.pressedKeys[key]){ if(ms >= this.pressedKeys[key] + 50){ - this.keyPress(true, key) + this.keyPress(true, key, null, true) this.pressedKeys[key] = ms } } @@ -980,16 +989,31 @@ class SongSelect{ }) var category = this.songs[this.selectedSong].category - if(category){ - var selectedSong = this.songs[this.selectedSong] - this.categoryCache.get({ - ctx: ctx, - x: winW / 2 - 280 / 2, - y: frameTop, - w: 280, - h: this.songAsset.marginTop, - id: category + selectedSong.skin.outline - }, ctx => { + var selectedSong = this.songs[this.selectedSong] + this.draw.category({ + ctx: ctx, + x: winW / 2 - 280 / 2 - 30, + y: frameTop + 60, + fill: selectedSong.skin.background, + highlight: this.state.moveHover === "categoryPrev" + }) + this.draw.category({ + ctx: ctx, + x: winW / 2 + 280 / 2 + 30, + y: frameTop + 60, + right: true, + fill: selectedSong.skin.background, + highlight: this.state.moveHover === "categoryNext" + }) + this.categoryCache.get({ + ctx: ctx, + x: winW / 2 - 280 / 2, + y: frameTop, + w: 280, + h: this.songAsset.marginTop, + id: category + selectedSong.skin.outline + }, ctx => { + if(category){ if(category in strings.categories){ var categoryName = strings.categories[category] }else{ @@ -1009,8 +1033,8 @@ class SongSelect{ {outline: selectedSong.skin.outline, letterBorder: 12, shadow: [3, 3, 3]}, {fill: "#fff"} ]) - }) - } + } + }) } if(screen === "song"){ @@ -1031,7 +1055,7 @@ class SongSelect{ var previousSelectedSong = this.selectedSong if(!isJump){ - assets.sounds["se_ka"].play() + this.playSound("se_ka") this.selectedSong = this.mod(this.songs.length, this.selectedSong + this.state.move) }else{ var currentCat = this.songs[this.selectedSong].category @@ -1079,7 +1103,13 @@ class SongSelect{ } this.state.move = 0 this.state.locked = 2 - localStorage["selectedSong"] = this.selectedSong + if(assets.customSongs){ + assets.customSelected = this.selectedSong + }else if(!p2.session){ + try{ + localStorage["selectedSong"] = this.selectedSong + }catch(e){} + } if(this.songs[this.selectedSong].action !== "back"){ var cat = this.songs[this.selectedSong].category