Merge branch 'master' into no-howler
* master: validate chess960 fen in api challenges oauth token input autofocus create API chess960 challenge with defined position update sound test page update sound test page code style avoid analysing empty games (swiss timeout) fix mobile app BC - closes #7195 and #7196 fix prev commit wait for Chessground to render miniGames
This commit is contained in:
commit
886a15f084
|
@ -1,5 +1,7 @@
|
|||
package controllers
|
||||
|
||||
|
||||
|
||||
import play.api.libs.json.Json
|
||||
import play.api.mvc.Result
|
||||
import scala.annotation.nowarn
|
||||
|
@ -231,16 +233,17 @@ final class Challenge(
|
|||
} orElse config.days.map {
|
||||
TimeControl.Correspondence.apply
|
||||
} getOrElse TimeControl.Unlimited
|
||||
val challenge = lila.challenge.Challenge.make(
|
||||
variant = config.variant,
|
||||
initialFen = config.position,
|
||||
timeControl = timeControl,
|
||||
mode = config.mode,
|
||||
color = config.color.name,
|
||||
challenger = ChallengeModel.toRegistered(config.variant, timeControl)(me),
|
||||
destUser = destUser,
|
||||
rematchOf = none
|
||||
)
|
||||
val challenge = lila.challenge.Challenge
|
||||
.make(
|
||||
variant = config.variant,
|
||||
initialFen = config.position,
|
||||
timeControl = timeControl,
|
||||
mode = config.mode,
|
||||
color = config.color.name,
|
||||
challenger = ChallengeModel.toRegistered(config.variant, timeControl)(me),
|
||||
destUser = destUser,
|
||||
rematchOf = none
|
||||
)
|
||||
(destUser, config.acceptByToken) match {
|
||||
case (Some(dest), Some(strToken)) => apiChallengeAccept(dest, challenge, strToken)
|
||||
case _ =>
|
||||
|
|
|
@ -114,7 +114,6 @@ object side {
|
|||
},
|
||||
initialFen
|
||||
.ifTrue(game.variant.chess960)
|
||||
.map(_.value)
|
||||
.flatMap {
|
||||
chess.variant.Chess960.positionNumber
|
||||
}
|
||||
|
|
|
@ -26,7 +26,7 @@ object create {
|
|||
form("description"),
|
||||
raw("Token description"),
|
||||
help = raw("For you to remember what this token is for").some
|
||||
)(form3.input(_)),
|
||||
)(form3.input(_)(autofocus)),
|
||||
br,
|
||||
br,
|
||||
h2("Scopes define the access for personal tokens:"),
|
||||
|
|
|
@ -86,8 +86,8 @@ case class Challenge(
|
|||
|
||||
def notableInitialFen: Option[FEN] =
|
||||
variant match {
|
||||
case FromPosition | Horde | RacingKings => initialFen
|
||||
case _ => none
|
||||
case FromPosition | Horde | RacingKings | Chess960 => initialFen
|
||||
case _ => none
|
||||
}
|
||||
|
||||
def isOpen = ~open
|
||||
|
@ -202,7 +202,9 @@ object Challenge {
|
|||
variant = variant,
|
||||
initialFen =
|
||||
if (variant == FromPosition) initialFen
|
||||
else if (variant == Chess960) none // only decided on game start
|
||||
else if (variant == Chess960) initialFen filter { fen =>
|
||||
Chess960.positionNumber(fen).isDefined
|
||||
}
|
||||
else !variant.standardInitialPosition option FEN(variant.initialFen),
|
||||
timeControl = timeControl,
|
||||
mode = finalMode,
|
||||
|
|
|
@ -23,19 +23,20 @@ final private class Joiner(
|
|||
def makeChess(variant: chess.variant.Variant): chess.Game =
|
||||
chess.Game(situation = Situation(variant), clock = c.clock.map(_.config.toClock))
|
||||
|
||||
val baseState = c.initialFen.ifTrue(c.variant.fromPosition) flatMap { fen =>
|
||||
Forsyth.<<<@(chess.variant.FromPosition, fen.value)
|
||||
val baseState = c.initialFen.ifTrue(c.variant.fromPosition || c.variant.chess960) flatMap { fen =>
|
||||
Forsyth.<<<@(c.variant, fen.value)
|
||||
}
|
||||
val (chessGame, state) = baseState.fold(makeChess(c.variant) -> none[SituationPlus]) {
|
||||
case sit @ SituationPlus(s, _) =>
|
||||
case SituationPlus(sit, turns) =>
|
||||
val game = chess.Game(
|
||||
situation = s,
|
||||
turns = sit.turns,
|
||||
startedAtTurn = sit.turns,
|
||||
situation = sit,
|
||||
turns = turns,
|
||||
startedAtTurn = turns,
|
||||
clock = c.clock.map(_.config.toClock)
|
||||
)
|
||||
if (Forsyth.>>(game) == Forsyth.initial) makeChess(chess.variant.Standard) -> none
|
||||
else game -> baseState
|
||||
if (c.variant.fromPosition && Forsyth.>>(game) == Forsyth.initial)
|
||||
makeChess(chess.variant.Standard) -> none
|
||||
else game -> baseState
|
||||
}
|
||||
val perfPicker = (perfs: lila.user.Perfs) => perfs(c.perfType)
|
||||
val game = Game
|
||||
|
@ -55,10 +56,7 @@ final private class Joiner(
|
|||
g.copy(
|
||||
chess = g.chess.copy(
|
||||
situation = g.situation.copy(
|
||||
board = g.board.copy(
|
||||
history = board.history,
|
||||
variant = chess.variant.FromPosition
|
||||
)
|
||||
board = g.board.copy(history = board.history)
|
||||
),
|
||||
turns = sit.turns
|
||||
)
|
||||
|
|
|
@ -25,8 +25,8 @@ final class Analyser(
|
|||
|
||||
def apply(game: Game, sender: Work.Sender): Fu[Boolean] =
|
||||
(game.metadata.analysed ?? analysisRepo.exists(game.id)) flatMap {
|
||||
case true => fuFalse
|
||||
case _ if Game.isOldHorde(game) => fuFalse
|
||||
case true => fuFalse
|
||||
case _ if game.analysable => fuFalse
|
||||
case _ =>
|
||||
limiter(sender, ignoreConcurrentCheck = false) flatMap { accepted =>
|
||||
accepted ?? {
|
||||
|
|
|
@ -28,7 +28,8 @@ final class Cached(
|
|||
.build(gameRepo.lastPlayedPlayingId)
|
||||
|
||||
lila.common.Bus.subscribeFun("startGame") {
|
||||
case lila.game.actorApi.StartGame(game) => game.userIds foreach { lastPlayedPlayingIdCache.invalidate(_) }
|
||||
case lila.game.actorApi.StartGame(game) =>
|
||||
game.userIds foreach lastPlayedPlayingIdCache.invalidate
|
||||
}
|
||||
|
||||
private val nbPlayingCache = cacheApi[User.ID, Int](256, "game.nbPlaying") {
|
||||
|
|
|
@ -1,11 +1,14 @@
|
|||
package lila.setup
|
||||
|
||||
import chess.{ Clock, Speed }
|
||||
import chess.format.{ FEN, Forsyth }
|
||||
import chess.variant.Chess960
|
||||
import chess.variant.FromPosition
|
||||
import chess.{ Clock, Speed }
|
||||
|
||||
import lila.game.PerfPicker
|
||||
import lila.lobby.Color
|
||||
import lila.rating.PerfType
|
||||
import lila.game.PerfPicker
|
||||
import chess.variant.Variant
|
||||
|
||||
final case class ApiConfig(
|
||||
variant: chess.variant.Variant,
|
||||
|
@ -17,18 +20,11 @@ final case class ApiConfig(
|
|||
acceptByToken: Option[String] = None
|
||||
) {
|
||||
|
||||
val strictFen = false
|
||||
|
||||
def >> = (variant.key.some, clock, days, rated, color.name.some, position.map(_.value), acceptByToken).some
|
||||
|
||||
def perfType: Option[PerfType] = PerfPicker.perfType(chess.Speed(clock), variant, days)
|
||||
|
||||
def validFen =
|
||||
variant != FromPosition || {
|
||||
position ?? { f =>
|
||||
~(Forsyth <<< f.value).map(_.situation playable strictFen)
|
||||
}
|
||||
}
|
||||
def validFen = ApiConfig.validFen(variant, position)
|
||||
|
||||
def validSpeed(isBot: Boolean) =
|
||||
!isBot || clock.fold(true) { c =>
|
||||
|
@ -64,4 +60,12 @@ object ApiConfig extends BaseHumanConfig {
|
|||
position = pos map FEN,
|
||||
acceptByToken = tok
|
||||
).autoVariant
|
||||
|
||||
def validFen(variant: Variant, fen: Option[FEN]) =
|
||||
if (variant.chess960) fen.forall(f => Chess960.positionNumber(f).isDefined)
|
||||
else if (variant.fromPosition)
|
||||
fen exists { f =>
|
||||
(Forsyth <<< f.value).exists(_.situation playable false)
|
||||
}
|
||||
else true
|
||||
}
|
||||
|
|
|
@ -3,8 +3,9 @@ package lila.setup
|
|||
import chess.Clock
|
||||
import chess.format.{ FEN, Forsyth }
|
||||
import chess.variant.FromPosition
|
||||
import lila.rating.PerfType
|
||||
|
||||
import lila.game.PerfPicker
|
||||
import lila.rating.PerfType
|
||||
|
||||
final case class OpenConfig(
|
||||
variant: chess.variant.Variant,
|
||||
|
@ -12,18 +13,11 @@ final case class OpenConfig(
|
|||
position: Option[FEN] = None
|
||||
) {
|
||||
|
||||
val strictFen = false
|
||||
|
||||
def >> = (variant.key.some, clock, position.map(_.value)).some
|
||||
|
||||
def perfType: Option[PerfType] = PerfPicker.perfType(chess.Speed(clock), variant, none)
|
||||
|
||||
def validFen =
|
||||
variant != FromPosition || {
|
||||
position ?? { f =>
|
||||
~(Forsyth <<< f.value).map(_.situation playable strictFen)
|
||||
}
|
||||
}
|
||||
def validFen = ApiConfig.validFen(variant, position)
|
||||
|
||||
def autoVariant =
|
||||
if (variant.standard && position.exists(_.value != Forsyth.initial)) copy(variant = FromPosition)
|
||||
|
|
|
@ -278,6 +278,7 @@ final class JsonView(
|
|||
"id" -> game.id,
|
||||
"fen" -> chess.format.Forsyth.boardAndColor(game.situation),
|
||||
"orientation" -> game.naturalOrientation.name,
|
||||
"color" -> game.naturalOrientation.name, // app BC https://github.com/ornicar/lila/issues/7195
|
||||
"lastMove" -> ~game.lastMoveKeys,
|
||||
"white" -> ofPlayer(featured.white, game player chess.White),
|
||||
"black" -> ofPlayer(featured.black, game player chess.Black)
|
||||
|
|
|
@ -8,7 +8,7 @@ object Dependencies {
|
|||
val scalalib = "com.github.ornicar" %% "scalalib" % "7.0.1"
|
||||
val hasher = "com.roundeights" %% "hasher" % "1.2.1"
|
||||
val jodaTime = "joda-time" % "joda-time" % "2.10.6"
|
||||
val chess = "org.lichess" %% "scalachess" % "10.0.2"
|
||||
val chess = "org.lichess" %% "scalachess" % "10.0.3"
|
||||
val compression = "org.lichess" %% "compression" % "1.6"
|
||||
val maxmind = "com.sanoma.cda" %% "maxmind-geoip2-scala" % "1.3.1-THIB"
|
||||
val prismic = "io.prismic" %% "scala-kit" % "1.2.19-THIB213"
|
||||
|
|
|
@ -1,83 +1,87 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<title>lichess - Sound Test Page</title>
|
||||
<style type="text/css">
|
||||
html, body {
|
||||
font:16px monospace;
|
||||
background: #000;
|
||||
color: #ebd488
|
||||
}
|
||||
button {
|
||||
width: 100%;
|
||||
}
|
||||
</style>
|
||||
<meta content="noindex, nofollow" name="robots">
|
||||
</head>
|
||||
<body>
|
||||
<h1>Sound Test Page</h1>
|
||||
<script src="../compiled/lichess.site.js"></script>
|
||||
<table>
|
||||
<thead>
|
||||
<tr id="sets"></tr>
|
||||
</thead>
|
||||
<tbody id="sounds">
|
||||
</tbody>
|
||||
</table>
|
||||
<script>
|
||||
var soundSets = ["standard", "piano", "nes", "sfx", "futuristic", "robot"];
|
||||
var soundNames = {
|
||||
genericNotify: 'GenericNotify',
|
||||
move: 'Move',
|
||||
capture: 'Capture',
|
||||
explode: 'Explosion',
|
||||
lowtime: 'LowTime',
|
||||
victory: 'Victory',
|
||||
defeat: 'Defeat',
|
||||
draw: 'Draw',
|
||||
tournament1st: 'Tournament1st',
|
||||
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<title>lichess - Sound Test Page</title>
|
||||
<style type="text/css">
|
||||
html,
|
||||
body {
|
||||
font: 16px monospace;
|
||||
background: #000;
|
||||
color: #ebd488
|
||||
}
|
||||
|
||||
button {
|
||||
width: 100%;
|
||||
}
|
||||
</style>
|
||||
<meta content="noindex, nofollow" name="robots">
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<h1>Sound Test Page</h1>
|
||||
<script src="http://l1.org/assets/_dl41cQ/compiled/lichess.deps.js"></script>
|
||||
<script src="http://l1.org/assets/_dl41cQ/compiled/lichess.site.js"></script>
|
||||
<table>
|
||||
<thead>
|
||||
<tr id="sets"></tr>
|
||||
</thead>
|
||||
<tbody id="sounds">
|
||||
</tbody>
|
||||
</table>
|
||||
<script>
|
||||
var soundSets = ["standard", "piano", "nes", "sfx", "futuristic", "robot"];
|
||||
var soundNames = {
|
||||
genericNotify: 'GenericNotify',
|
||||
move: 'Move',
|
||||
capture: 'Capture',
|
||||
explode: 'Explosion',
|
||||
lowtime: 'LowTime',
|
||||
victory: 'Victory',
|
||||
defeat: 'Defeat',
|
||||
draw: 'Draw',
|
||||
tournament1st: 'Tournament1st',
|
||||
tournament2nd: 'Tournament2nd',
|
||||
tournament3rd: 'Tournament3rd',
|
||||
tournamentOther: 'TournamentOther',
|
||||
berserk: 'Berserk',
|
||||
check: 'Check',
|
||||
tournament3rd: 'Tournament3rd',
|
||||
tournamentOther: 'TournamentOther',
|
||||
berserk: 'Berserk',
|
||||
check: 'Check',
|
||||
newChallenge: 'NewChallenge',
|
||||
newPM: 'NewPM',
|
||||
};
|
||||
for(var i = 0; i <= 10; i++) soundNames['countDown' + i] = 'CountDown' + i;
|
||||
$.each(soundSets, function (i, soundSet) {
|
||||
$('#sets').append($('<th>' + soundSet + '</th>'));
|
||||
};
|
||||
for (var i = 0; i <= 10; i++) soundNames['countDown' + i] = 'CountDown' + i;
|
||||
$.each(soundSets, function(i, soundSet) {
|
||||
$('#sets').append($('<th>' + soundSet + '</th>'));
|
||||
});
|
||||
$.each(soundNames, function(soundKey, soundName) {
|
||||
var tr = $('<tr>');
|
||||
$.each(soundSets, function(i, soundSet) {
|
||||
var id = "soundSet_" + soundSet;
|
||||
$('<td>').append($("<button>").click(function() {
|
||||
// lichess.sound.changeSet(soundSet);
|
||||
// lichess.sound[soundKey]();
|
||||
new Audio(`${soundSet}/${soundName}.ogg`).play();
|
||||
}).text(soundName)).appendTo(tr);
|
||||
});
|
||||
$.each(soundNames, function (i, soundName) {
|
||||
var tr = $('<tr>');
|
||||
$.each(soundSets, function (i, soundSet) {
|
||||
var id = "soundSet_" + soundSet;
|
||||
$('<td>').append($("<button>").click(function() {
|
||||
new Howl({
|
||||
src: ["ogg", "mp3"].map(function(ext) {
|
||||
return [soundSet, soundName + "." + ext].join("/");
|
||||
}),
|
||||
}).play();
|
||||
}).text(soundName)).appendTo(tr);
|
||||
});
|
||||
tr.appendTo($('#sounds'));
|
||||
});
|
||||
var tr = $('<tr>');
|
||||
$.each(soundSets, function (i, soundSet) {
|
||||
$('<td>').append($("<button>").click(function() {
|
||||
var i = 10;
|
||||
var tId = setInterval(function() {
|
||||
new Howl({
|
||||
src: ["ogg", "mp3"].map(function(ext) {
|
||||
return [soundSet, "CountDown" + i + "." + ext].join("/");
|
||||
}),
|
||||
}).play();
|
||||
i-- || clearInterval(tId);
|
||||
}, 1000);
|
||||
}).text("CountDown10 --1> 0")).appendTo(tr);
|
||||
tr.appendTo($('#sounds'));
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
tr.appendTo($('#sounds'));
|
||||
});
|
||||
var tr = $('<tr>');
|
||||
$.each(soundSets, function(i, soundSet) {
|
||||
$('<td>').append($("<button>").click(function() {
|
||||
var i = 10;
|
||||
var tId = setInterval(function() {
|
||||
new Howl({
|
||||
src: ["ogg", "mp3"].map(function(ext) {
|
||||
return [soundSet, "CountDown" + i + "." + ext].join("/");
|
||||
}),
|
||||
}).play();
|
||||
i-- || clearInterval(tId);
|
||||
}, 1000);
|
||||
}).text("CountDown10 --1> 0")).appendTo(tr);
|
||||
tr.appendTo($('#sounds'));
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
|
||||
</html>
|
||||
|
|
Loading…
Reference in a new issue