+mat en 2 échiqueté : brnkr3/pppp1p1p/4ps2/8/2P2P2/P1qP4/2c1s1PP/R1K5
+(Bb3+ Kb1 Ba2#)
+
// TODO: decodeURIComponent() for GET/DELETE parameters
1) Finish problems tab
2) Integrate computer play into rules tab
-3) Retrieve users system from old code
-4) Allow correspondance play (no need for P2P: online moves through the server (which also store them))
-5) Write my-games tab (included current/finished/imported)
+3) Allow correspondance play (no need for P2P: online moves through the server (which also store them))
+4) Write my-games tab (included current/finished/imported)
Use Dexie.js, or anything to store games locally
5) Write room tab
Use this: https://github.com/feross/simple-peer for online games+challenges+chat
{
req.userId = user.id;
res.locals.user = {
+ id: user.id,
name: user.name,
email: user.email,
notify: user.notify,
}
// Get opponent color
- getOppCol(color)
+ static GetOppCol(color)
{
return (color=="w" ? "b" : "w");
}
// Get next color (for compatibility with 3 and 4 players games)
- getNextCol(color)
+ static GetNextCol(color)
{
- return this.getOppCol(color);
+ return V.GetOppCol(color);
}
// Pieces codes (for a clearer code)
data: function () {
return {
problems: [], //oldest first
+ myProblems: [], //same
curIdx: 0, //index in problems array
stage: "nothing", //or "preview" after new problem is filled
newProblem: {
- if (this.mode == "problem")
+board qui bouge et activé que si #hash donnant numéro du problème
+deux listes : tous les problèmes sauf les miens
+ + les miens
+
+
+//TODO: filter "my problems" ==> liste séparée (lors de la requête serveur)
+--> bouton plutôt sous l'échiquier après soluce (sauf si anonymous)
+--> puis dans la vue "my problems (listing échiquier gauche / instrus + soluce cachée à droite
+if (this.mode == "problem")
{
// Show problem instructions
elementArray.push(
created: function() {
// Analyse URL: if a single problem required, show it. Otherwise,
// TODO: fetch most recent problems from server
+ // If the requested problem is in the list, just show it
},
methods: {
translate: function(text) {
// TODO:
// possibilité de supprimer / éditer si peer ID reconnu comme celui du probleme (champ "uploader")
-// --> côté serveur on vérifie un certain "secret"
-// --> filtre possible "mes problèmes"
let email = document.getElementById("userEmail");
let subject = document.getElementById("mailSubject");
let content = document.getElementById("mailContent");
- if (!email.value.match(/^[^@]+@[^@]+\.[^@]+$/))
- return alert("Bad email");
+ const error = checkNameEmail({email: email});
+ if (!!error)
+ return alert(error);
if (content.value.trim().length == 0)
return alert("Empty message");
if (subject.value.trim().length == 0 && !confirm("No subject. Send anyway?"))
computed: {
sortedCounts: function () {
// TODO: priorité aux parties corr où c'est à nous de jouer !
+ const capitalizedPrefix = this.curPrefix.replace(/^\w/, c => c.toUpperCase());
const variantsCounts = variantArray
.filter( v => {
- return v.name.startsWith(this.curPrefix);
+ return v.name.startsWith(capitalizedPrefix);
})
.map( v => {
return {
};
this.conn.onmessage = socketMessageListener;
this.conn.onclose = socketCloseListener;
+
+ // TODO:
+ // si dernier lastMove sur serveur n'est pas le mien et nextColor == moi, alors background orange
+ // ==> background orange si à moi de jouer par corr (sur main index)
+ // (helper: static fonction "GetNextCol()" dans base_rules.js)
},
-// mounted: function() {
-// // Handle key stroke
-// document.onkeydown = event => {
-// // Is it Back or Esc? If yes, apply action on current word
-// if (event.keyCode == 8) //Back
-// {
-// event.preventDefault();
-// this.curPrefix = this.curPrefix.slice(0,-1);
-// }
-// else if (event.keyCode == 27) //Esc
-// {
-// event.preventDefault();
-// this.curPrefix = "";
-// }
-// // Is it alphanumeric? If yes, stack it
-// else if (_.range(48,58).includes(event.keyCode)
-// || _.range(65,91).includes(event.keyCode)
-// || _.range(97,123).includes(event.keyCode))
-// {
-// let newChar = String.fromCharCode(event.keyCode);
-// this.curPrefix += this.curPrefix.length==0
-// ? newChar.toUpperCase()
-// : newChar.toLowerCase();
-// }
-// // ...ignore everything else
-// };
-// },
});
-
-// TODO:
-// si dernier lastMove sur serveur n'est pas le mien et nextColor == moi, alors background orange
-// ==> background orange si à moi de jouer par corr (sur main index)
-// (fonction "getNextCol()" dans base_rules.js ?)
if (m.vanish[0].p == V.PAWN && m.vanish.length == 2
&& this.board[m.end.x][m.end.y] == V.EMPTY)
{
- m.vanish[1].c = this.getOppCol(this.getColor(x,y));
+ m.vanish[1].c = V.GetOppCol(this.getColor(x,y));
// In the special case of en-passant, if
// - board1 takes board2 : vanish[1] --> Alice
// - board2 takes board1 : vanish[1] --> normal
getAllValidMoves()
{
const color = this.turn;
- const oppCol = this.getOppCol(color);
+ const oppCol = V.GetOppCol(color);
var potentialMoves = [];
let sideBoard = [this.getSideBoard(1), this.getSideBoard(2)];
for (var i=0; i<V.size.x; i++)
const mirrorSide = (sideBoard[0][kp[0]][kp[1]] != V.EMPTY ? 1 : 2);
let saveBoard = this.board;
this.board = sideBoard[mirrorSide-1];
- let res = this.isAttacked(kp, [this.getOppCol(color)]);
+ let res = this.isAttacked(kp, [V.GetOppCol(color)]);
this.board = saveBoard;
return res;
}
let sideBoard = this.getSideBoard(mirrorSide);
let saveBoard = this.board;
this.board = sideBoard;
- let res = this.isAttacked(this.kingPos[color], [this.getOppCol(color)])
+ let res = this.isAttacked(this.kingPos[color], [V.GetOppCol(color)])
? [ JSON.parse(JSON.stringify(this.kingPos[color])) ]
: [ ];
this.board = saveBoard;
let saveBoard = this.board;
this.board = sideBoard;
let res = "*";
- if (!this.isAttacked(this.kingPos[color], [this.getOppCol(color)]))
+ if (!this.isAttacked(this.kingPos[color], [V.GetOppCol(color)]))
res = "1/2";
else
res = (color == "w" ? "0-1" : "1-0");
underCheck(color)
{
- const oppCol = this.getOppCol(color);
+ const oppCol = V.GetOppCol(color);
let res = this.isAttacked(this.kingPos[color], [oppCol])
|| !this.isAttacked(this.antikingPos[color], [oppCol]);
return res;
getCheckSquares(color)
{
let res = super.getCheckSquares(color);
- if (!this.isAttacked(this.antikingPos[color], [this.getOppCol(color)]))
+ if (!this.isAttacked(this.antikingPos[color], [V.GetOppCol(color)]))
res.push(JSON.parse(JSON.stringify(this.antikingPos[color])));
return res;
}
checkGameEnd()
{
const color = this.turn;
- const oppCol = this.getOppCol(color);
+ const oppCol = V.GetOppCol(color);
if (!this.isAttacked(this.kingPos[color], [oppCol])
&& this.isAttacked(this.antikingPos[color], [oppCol]))
{
{
super.unupdateVariables(move);
const c = move.vanish[0].c;
- const oppCol = this.getOppCol(c);
+ const oppCol = V.GetOppCol(c);
if ([this.kingPos[c][0],this.kingPos[oppCol][0]].some(e => { return e < 0; }))
{
// There is a chance that last move blowed some king away..
underCheck(color)
{
- const oppCol = this.getOppCol(color);
+ const oppCol = V.GetOppCol(color);
let res = undefined;
// If our king disappeared, move is not valid
if (this.kingPos[color][0] < 0)
{
let res = [ ];
if (this.kingPos[color][0] >= 0 //king might have exploded
- && this.isAttacked(this.kingPos[color], [this.getOppCol(color)]))
+ && this.isAttacked(this.kingPos[color], [V.GetOppCol(color)]))
{
res = [ JSON.parse(JSON.stringify(this.kingPos[color])) ]
}
const kp = this.kingPos[color];
if (kp[0] < 0) //king disappeared
return color == "w" ? "0-1" : "1-0";
- if (!this.isAttacked(kp, [this.getOppCol(color)]))
+ if (!this.isAttacked(kp, [V.GetOppCol(color)]))
return "1/2";
return color == "w" ? "0-1" : "1-0"; //checkmate
}
{
const piece = this.getPiece(x,y);
const color = this.getColor(x,y);
- const oppCol = this.getOppCol(color);
+ const oppCol = V.GetOppCol(color);
const adjacentSteps = V.steps[V.ROOK].concat(V.steps[V.BISHOP]);
outerLoop:
for (let step of adjacentSteps)
{
const steps = V.steps[V.ROOK];
const color = this.turn;
- const oppCol = this.getOppCol(color);
+ const oppCol = V.GetOppCol(color);
moves.forEach(m => {
if (!!byChameleon && m.start.x!=m.end.x && m.start.y!=m.end.y)
return; //chameleon not moving as pawn
addRookCaptures(moves, byChameleon)
{
const color = this.turn;
- const oppCol = this.getOppCol(color);
+ const oppCol = V.GetOppCol(color);
const kp = this.kingPos[color];
moves.forEach(m => {
// Check piece-king rectangle (if any) corners for enemy pieces
// Look in every direction for captures
const steps = V.steps[V.ROOK].concat(V.steps[V.BISHOP]);
const color = this.turn;
- const oppCol = this.getOppCol(color);
+ const oppCol = V.GetOppCol(color);
let moves = [];
const [x,y] = [startSquare[0],startSquare[1]];
const piece = this.getPiece(x,y); //might be a chameleon!
const adjacentSteps = V.steps[V.ROOK].concat(V.steps[V.BISHOP]);
let capturingDirections = [];
const color = this.turn;
- const oppCol = this.getOppCol(color);
+ const oppCol = V.GetOppCol(color);
adjacentSteps.forEach(step => {
const [i,j] = [x+step[0],y+step[1]];
if (V.OnBoard(i,j) && this.board[i][j] != V.EMPTY && this.getColor(i,j) == oppCol
underCheck(color)
{
- return this.isAttacked(this.kingPos[color], [this.getOppCol(color),'c']);
+ return this.isAttacked(this.kingPos[color], [V.GetOppCol(color),'c']);
}
getCheckSquares(color)
{
// Artifically change turn, for checkered pawns
- this.turn = this.getOppCol(color);
+ this.turn = V.GetOppCol(color);
const kingAttacked = this.isAttacked(
- this.kingPos[color], [this.getOppCol(color),'c']);
+ this.kingPos[color], [V.GetOppCol(color),'c']);
let res = kingAttacked
? [JSON.parse(JSON.stringify(this.kingPos[color]))] //need to duplicate!
: [];
{
const color = this.turn;
// Artifically change turn, for checkered pawns
- this.turn = this.getOppCol(this.turn);
- const res = this.isAttacked(this.kingPos[color], [this.getOppCol(color),'c'])
+ this.turn = V.GetOppCol(this.turn);
+ const res = this.isAttacked(this.kingPos[color], [V.GetOppCol(color),'c'])
? (color == "w" ? "0-1" : "1-0")
: "1/2";
- this.turn = this.getOppCol(this.turn);
+ this.turn = V.GetOppCol(this.turn);
return res;
}
getAllValidMoves()
{
const color = this.turn;
- const oppCol = this.getOppCol(color);
+ const oppCol = V.GetOppCol(color);
let potentialMoves = [];
for (let i=0; i<V.size.x; i++)
{
{
super.unupdateVariables(move);
const c = move.vanish[0].c;
- const oppCol = this.getOppCol(c);
+ const oppCol = V.GetOppCol(c);
if (this.kingPos[oppCol][0] < 0)
{
// Last move took opponent's king
{
const maxeval = V.INFINITY;
const color = this.turn;
- const oppCol = this.getOppCol(color);
+ const oppCol = V.GetOppCol(color);
const pawnShift = (color == "w" ? -1 : 1);
const kp = this.kingPos[color];
atLeastOneCapture()
{
const color = this.turn;
- const oppCol = this.getOppCol(color);
+ const oppCol = V.GetOppCol(color);
for (let i=0; i<V.size.x; i++)
{
for (let j=0; j<V.size.y; j++)
if (move.vanish.length >= 2 && move.vanish[1].p == V.KING)
{
// We took opponent king !
- const oppCol = this.getOppCol(c);
+ const oppCol = V.GetOppCol(c);
this.kingPos[oppCol] = [-1,-1];
this.castleFlags[oppCol] = [false,false];
}
// Did we magnetically move our (init) rooks or opponents' ones ?
const firstRank = (c == "w" ? 7 : 0);
const oppFirstRank = 7 - firstRank;
- const oppCol = this.getOppCol(c);
+ const oppCol = V.GetOppCol(c);
move.vanish.forEach(psq => {
if (psq.x == firstRank && this.INIT_COL_ROOK[c].includes(psq.y))
this.castleFlags[c][psq.y==this.INIT_COL_ROOK[c][0] ? 0 : 1] = false;
{
super.unupdateVariables(move);
const c = move.vanish[0].c;
- const oppCol = this.getOppCol(c);
+ const oppCol = V.GetOppCol(c);
if (this.kingPos[oppCol][0] < 0)
{
// Last move took opponent's king
});
if (epSqs.length == 0)
return moves;
- const oppCol = this.getOppCol(color);
+ const oppCol = V.GetOppCol(color);
for (let sq of epSqs)
{
if (this.subTurn == 1 || (epSqs.length == 2 &&
this.epSquares.push([epSq]);
}
// Does this move give check on subturn 1? If yes, skip subturn 2
- else if (this.subTurn==1 && this.underCheck(this.getOppCol(this.turn)))
+ else if (this.subTurn==1 && this.underCheck(V.GetOppCol(this.turn)))
{
- this.turn = this.getOppCol(this.turn);
+ this.turn = V.GetOppCol(this.turn);
this.epSquares.push([epSq]);
move.checkOnSubturn1 = true;
}
{
if (this.subTurn == 2)
{
- this.turn = this.getOppCol(this.turn);
+ this.turn = V.GetOppCol(this.turn);
let lastEpsq = this.epSquares[this.epSquares.length-1];
lastEpsq.push(epSq);
}
}
else if (move.checkOnSubturn1)
{
- this.turn = this.getOppCol(this.turn);
+ this.turn = V.GetOppCol(this.turn);
this.subTurn = 1;
this.epSquares.pop();
}
{
if (this.subTurn == 1)
{
- this.turn = this.getOppCol(this.turn);
+ this.turn = V.GetOppCol(this.turn);
let lastEpsq = this.epSquares[this.epSquares.length-1];
lastEpsq.pop();
}
const maxeval = V.INFINITY;
const color = this.turn;
- const oppCol = this.getOppCol(this.turn);
+ const oppCol = V.GetOppCol(this.turn);
// Search best (half) move for opponent turn
const getBestMoveEval = () => {
const piece = this.getPiece(x,y);
const steps = V.steps[V.ROOK].concat(V.steps[V.BISHOP]);
const kp = this.kingPos[color];
- const oppCol = this.getOppCol(color);
+ const oppCol = V.GetOppCol(color);
for (let step of steps)
{
let [i,j] = [x+step[0],y+step[1]];
getAllValidMoves(computer)
{
const color = this.turn;
- const oppCol = this.getOppCol(color);
+ const oppCol = V.GetOppCol(color);
let potentialMoves = [];
for (let i=0; i<V.size.x; i++)
{
i += step[0];
j += step[1];
}
- if (V.OnBoard(i,j) && this.getColor(i,j) == this.getOppCol(color)
+ if (V.OnBoard(i,j) && this.getColor(i,j) == V.GetOppCol(color)
&& this.getPiece(i,j) == asA)
{
// eat!
img(src="/images/index/wildebeest.svg")
#flagMenu.clickable(onClick="doClick('modalLang')")
img(src="/images/flags/" + lang + ".svg")
- #userMenu.clickable(onClick="doClick('modalUser')")
- .info-container
- if !user.email
- p
- span Login
- i.material-icons person
- else
- p
- span Update
- i.material-icons person
+ include userMenu
#introductionMenu.clickable(onClick="doClick('modalWelcome')")
.info-container
p Introduction
+ .row
+ .col-sm-12.col-md-10.col-md-offset-1.col-lg-8.col-lg-offset-2
+ label(for="prefixFilter") Type first letters...
+ input#prefixFilter(v-model="curPrefix")
.row
my-variant-summary(v-for="(v,idx) in sortedCounts"
v-bind:vobj="v" v-bind:index="idx" v-bind:key="v.name")
block javascripts
script.
const variantArray = !{JSON.stringify(variantArray)};
- script(src="/javascripts/utils/misc.js")
script(src="/javascripts/socket_url.js")
script(src="/javascripts/components/variantSummary.js")
script(src="/javascripts/index.js")
=translations["Contact"]
script(src="//cdnjs.cloudflare.com/ajax/libs/underscore.js/1.9.1/underscore-min.js")
+ script(src="/javascripts/utils/misc.js")
script(src="/javascripts/utils/ajax.js")
script(src="/javascripts/layout.js")
script(src="/javascripts/settings.js")
--- /dev/null
+#userMenu.clickable(onClick="doClick('modalUser')")
+ .info-container
+ if !user.email
+ p
+ span Login
+ i.material-icons person
+ else
+ p
+ span Update
+ i.material-icons person
=translations["Rules"]
a(href="#problems" @click="setDisplay('problems')")
=translations["Problems"]
- #settings.clickable(
- onClick="document.getElementById('modalSettings').checked=true")
+ #settings.clickable(onClick="doClick('modalSettings')")
i.material-icons settings
- #userMenu.clickable(
- onClick="document.getElementById('modalUser').checked=true")
- .info-container
- i.material-icons person
- if !user.email
- p Login
- else
- p Update
+ include userMenu
.row
- my-room(v-show="display=='room'")
- my-game-list(v-show="display=='gameList'")
+ //my-room(v-show="display=='room'")
+ //my-game-list(v-show="display=='gameList'")
my-rules(v-show="display=='rules'")
my-problems(v-show="display=='problems'")
- my-game(v-show="display=='game'" :gameId="gameid")
+ //my-game(v-show="display=='game'" :gameId="gameid")
block javascripts
- script(src="/javascripts/utils/misc.js")
script(src="/javascripts/utils/array.js")
script(src="/javascripts/utils/printDiagram.js")
script(src="/javascripts/utils/datetime.js")
script.
const V = VariantRules; //because this variable is often used
const variant = !{JSON.stringify(variant)};
- script(src="/javascripts/components/room.js")
- script(src="/javascripts/components/gameList.js")
+ //script(src="/javascripts/components/room.js")
+ //script(src="/javascripts/components/gameList.js")
script(src="/javascripts/components/rules.js")
- script(src="/javascripts/components/problemSummary.js")
+ script(src="/javascripts/components/problemPreview.js")
script(src="/javascripts/components/problems.js")
- script(src="/javascripts/components/game.js")
+ //script(src="/javascripts/components/game.js")
script(src="/javascripts/variant.js")