Add Sittuyin + Doublemove2. A few fixes. TODO: fix Ambiguous bugs and playing on...
[vchess.git] / client / src / components / BaseGame.vue
index 228d9c4..1a7e30f 100644 (file)
@@ -61,6 +61,13 @@ div#baseGame
 </template>
 
 <script>
+
+// https://vchess.club/#/game/46
+// Bug 35eme coup blanc Rx(P)e2, d2 et aussi 18eme coup blanc Rd7, Pxe6
+// --> peut-être lié à prise, ou lié à getFen(), ou inMultimove pas changé car concatène à coup précédent...
+// TODO: also fix moves played on smartphone, annoying shift...
+// attention play undo pendant l'autoplay !!
+
 import Board from "@/components/Board.vue";
 import MoveList from "@/components/MoveList.vue";
 import params from "@/parameters";
@@ -94,7 +101,6 @@ export default {
       incheck: [], //for Board
       inMultimove: false,
       autoplay: false,
-      autoplayLoop: null,
       inPlay: false,
       stackToPlay: []
     };
@@ -164,7 +170,8 @@ export default {
       .addEventListener("click", processModalClick);
   },
   beforeDestroy: function() {
-    if (!!this.autoplayLoop) clearInterval(this.autoplayLoop);
+    // TODO: probably not required
+    this.autoplay = false;
   },
   methods: {
     focusBg: function() {
@@ -216,6 +223,10 @@ export default {
       const firstMoveColor = parsedFen.turn;
       this.firstMoveNumber = Math.floor(parsedFen.movesCount / 2) + 1;
       let L = this.moves.length;
+      if (L == 0) {
+        this.incheck = [];
+        this.score = "*";
+      }
       this.moves.forEach((move,idx) => {
         // Strategy working also for multi-moves:
         if (!Array.isArray(move)) move = [move];
@@ -229,8 +240,8 @@ export default {
           if (idxM == Lm - 1) m.fen = this.vr.getFen();
           if (idx == L - 1 && idxM == Lm - 1) {
             this.incheck = checkSquares;
-            const score = this.vr.getCurrentScore();
-            if (["1-0", "0-1"].includes(score)) m.notation += "#";
+            this.score = this.vr.getCurrentScore();
+            if (["1-0", "0-1"].includes(this.score)) m.notation += "#";
           }
         });
       });
@@ -275,6 +286,8 @@ export default {
         }
         this.vr = new V(fen);
         this.incheck = this.vr.getCheckSquares();
+        if (this.cursor >= 0) this.lastMove = this.moves[this.cursor];
+        else this.lastMove = null;
         document.getElementById("analyzeBtn").classList.remove("active");
       }
     },
@@ -331,32 +344,15 @@ export default {
       document.getElementById("modalEog").checked = true;
     },
     runAutoplay: function() {
-      const infinitePlay = () => {
-        if (this.cursor == this.moves.length - 1) {
-          clearInterval(this.autoplayLoop);
-          this.autoplayLoop = null;
-          this.autoplay = false;
-          return;
-        }
-        if (this.inPlay || this.inMultimove)
-          // Wait next tick
-          return;
-        this.play();
-      };
       if (this.autoplay) {
         this.autoplay = false;
-        clearInterval(this.autoplayLoop);
-        this.autoplayLoop = null;
-      } else {
+        if (this.stackToPlay.length > 0)
+          // Move(s) arrived in-between
+          this.play(this.stackToPlay.pop(), "received");
+      }
+      else if (this.cursor < this.moves.length - 1) {
         this.autoplay = true;
-        setTimeout(
-          () => {
-            infinitePlay();
-            this.autoplayLoop = setInterval(infinitePlay, 1500);
-          },
-          // Small delay otherwise the first move is played too fast
-          500
-        );
+        this.play();
       }
     },
     // Animate an elementary move
@@ -415,7 +411,7 @@ export default {
       if (!!move) this.play(move);
     },
     // "light": if gotoMove() or gotoEnd()
-    play: function(move, received, light, noemit) {
+    play: function(move, received, light) {
       // Freeze while choices are shown:
       if (this.$refs["board"].choices.length > 0) return;
       const navigate = !move;
@@ -430,22 +426,17 @@ export default {
         return;
       }
       if (!!received) {
-
-        if (this.mode == "analyze") { console.log("received move");
-          console.log(move); }
-
-        if (this.mode == "analyze") this.toggleAnalyze();
-        if (this.cursor < this.moves.length - 1)
-          // To play a received move, cursor must be at the end of the game:
-          this.gotoEnd();
-      }
-      if (!!noemit) {
-        if (this.inPlay) {
-          // Received moves in observed games can arrive too fast:
+        if (this.autoplay || this.inPlay) {
+          // Received moves while autoplaying are stacked,
+          // and in observed games they could arrive too fast:
           this.stackToPlay.unshift(move);
           return;
         }
         this.inPlay = true;
+        if (this.mode == "analyze") this.toggleAnalyze();
+        if (this.cursor < this.moves.length - 1)
+          // To play a received move, cursor must be at the end of the game:
+          this.gotoEnd();
       }
       // The board may show some the possible moves: (TODO: bad solution)
       this.$refs["board"].resetCurrentAttempt();
@@ -496,11 +487,7 @@ export default {
           if (animate && smove.start.x >= 0) {
             self.animateMove(smove, () => {
               playSubmove(smove);
-
-console.log(moveIdx + " " + move.length);
-
-              if (moveIdx < move.length)
-                setTimeout(executeMove, 500);
+              if (moveIdx < move.length) setTimeout(executeMove, 500);
               else afterMove(smove, initurn);
             });
           } else {
@@ -513,7 +500,7 @@ console.log(moveIdx + " " + move.length);
       const computeScore = () => {
         const score = this.vr.getCurrentScore();
         if (!navigate) {
-          if (["1-0","0-1"].includes(score)) {
+          if (["1-0", "0-1"].includes(score)) {
             if (Array.isArray(this.lastMove)) {
               const L = this.lastMove.length;
               this.lastMove[L - 1].notation += "#";
@@ -521,18 +508,15 @@ console.log(moveIdx + " " + move.length);
             else this.lastMove.notation += "#";
           }
         }
-        if (score != "*" && this.mode == "analyze") {
+        if (score != "*" && ["analyze", "versus"].includes(this.mode)) {
           const message = getScoreMessage(score);
-          // Just show score on screen (allow undo)
+          // Show score on screen
           this.showEndgameMsg(score + " . " + this.st.tr[message]);
         }
         return score;
       };
       const afterMove = (smove, initurn) => {
         if (this.vr.turn != initurn) {
-
-console.log(smove);
-
           // Turn has changed: move is complete
           if (!smove.fen)
             // NOTE: only FEN of last sub-move is required (=> setting it here)
@@ -540,18 +524,27 @@ console.log(smove);
           this.emitFenIfAnalyze();
           this.inMultimove = false;
           this.score = computeScore();
+          if (this.autoplay) {
+            if (this.cursor < this.moves.length - 1)
+              setTimeout(this.play, 1000);
+            else {
+              this.autoplay = false;
+              if (this.stackToPlay.length > 0)
+                // Move(s) arrived in-between
+                this.play(this.stackToPlay.pop(), "received");
+            }
+          }
           if (this.mode != "analyze" && !navigate) {
-            if (!noemit && this.mode != "analyze") {
+            if (!received) {
               // Post-processing (e.g. computer play).
               const L = this.moves.length;
-              // NOTE: always emit the score, even in unfinished,
-              // to tell Game::processMove() that it's not a received move.
+              // NOTE: always emit the score, even in unfinished
               this.$emit("newmove", this.moves[L-1], { score: this.score });
             } else {
               this.inPlay = false;
               if (this.stackToPlay.length > 0)
                 // Move(s) arrived in-between
-                this.play(this.stackToPlay.pop(), received, light, noemit);
+                this.play(this.stackToPlay.pop(), "received");
             }
           }
         }
@@ -668,6 +661,7 @@ console.log(smove);
 <style lang="sass" scoped>
 [type="checkbox"]#modalEog+div .card
   min-height: 45px
+  max-width: 350px
 
 #baseGame
   width: 100%