From 4a6e9231eb0f2dbd6de9230991396905eeaa13f3 Mon Sep 17 00:00:00 2001 From: H.G. Muller Date: Fri, 6 Nov 2009 09:05:09 -0800 Subject: [PATCH] variation-support patch It allows you to Revert to the main line (or previous variation) when playing variations on an existing game in EditGame or Analyze mode. --- backend.c | 134 ++++++++++++++++++++++++++++++++++++++++++++++----- frontend.h | 2 + winboard/winboard.c | 14 +++-- xboard.c | 14 +++++ 4 files changed, 145 insertions(+), 19 deletions(-) diff --git a/backend.c b/backend.c index c4e9316..8cf3a43 100755 --- a/backend.c +++ b/backend.c @@ -450,6 +450,20 @@ int loadFlag = 0; int shuffleOpenings; int mute; // mute all sounds +// [HGM] vari: next 12 to save and restore variations +#define MAX_VARIATIONS 10 +int framePtr = MAX_MOVES-1; // points to free stack entry +int storedGames = 0; +int savedFirst[MAX_VARIATIONS]; +int savedLast[MAX_VARIATIONS]; +int savedFramePtr[MAX_VARIATIONS]; +char *savedDetails[MAX_VARIATIONS]; +ChessMove savedResult[MAX_VARIATIONS]; + +void PushTail P((int firstMove, int lastMove)); +Boolean PopTail P((void)); +void CleanupTail P((void)); + ChessSquare FIDEArray[2][BOARD_FILES] = { { WhiteRook, WhiteKnight, WhiteBishop, WhiteQueen, WhiteKing, WhiteBishop, WhiteKnight, WhiteRook }, @@ -641,7 +655,7 @@ InitBackEnd1() { int i, j; - for( i=0; i= MAX_MOVES) { + if (moveNum > framePtr) { // [HGM] vari: do not run into saved variations DisplayFatalError(_("Game too long; increase MAX_MOVES and recompile"), 0, 1); return; @@ -4611,7 +4625,7 @@ InitPosition(redraw) /* [AS] Initialize pv info list [HGM] and game status */ { - for( i=0; i= MAX_MOVES) { + if (forwardMostMove+1 > framePtr) { // [HGM] vari: do not run into saved variations DisplayFatalError(_("Game too long; increase MAX_MOVES and recompile"), 0, 1); return; @@ -8468,6 +8478,7 @@ Reset(redraw, init) fprintf(debugFP, "Reset(%d, %d) from gameMode %d\n", redraw, init, gameMode); } + CleanupTail(); // [HGM] vari: delete any stored variations pausing = pauseExamInvalid = FALSE; startedFromSetupPosition = blackPlaysFirst = FALSE; firstMove = TRUE; @@ -10861,7 +10872,8 @@ TwoMachinesEvent P((void)) break; } - forwardMostMove = currentMove; +// forwardMostMove = currentMove; + TruncateGame(); // [HGM] vari: MachineWhite and MachineBlack do this... ResurrectChessProgram(); /* in case first program isn't running */ if (second.pr == NULL) { @@ -11826,6 +11838,9 @@ ToNrEvent(int to) void RevertEvent() { + if(PopTail()) { // [HGM] vari: restore old game tail + return; + } if (gameMode != IcsExamining) { DisplayError(_("You are not examining a game"), 0); return; @@ -11923,6 +11938,7 @@ TruncateGameEvent() void TruncateGame() { + CleanupTail(); // [HGM] vari: only keep current variation if we explicitly truncate if (forwardMostMove > currentMove) { if (gameInfo.resultDetails != NULL) { free(gameInfo.resultDetails); @@ -14117,3 +14133,95 @@ int wrap(char *dest, char *src, int count, int width, int *lp) return len; } + +// [HGM] vari: routines for shelving variations + +void +PushTail(int firstMove, int lastMove) +{ + int i, j, nrMoves = lastMove - firstMove; + + if(appData.icsActive) { // only in local mode + forwardMostMove = currentMove; // mimic old ICS behavior + return; + } + if(storedGames >= MAX_VARIATIONS-1) return; + + // push current tail of game on stack + savedResult[storedGames] = gameInfo.result; + savedDetails[storedGames] = gameInfo.resultDetails; + gameInfo.resultDetails = NULL; + savedFirst[storedGames] = firstMove; + savedLast [storedGames] = lastMove; + savedFramePtr[storedGames] = framePtr; + framePtr -= nrMoves; // reserve space for the boards + for(i=nrMoves; i>=1; i--) { // copy boards to stack, working downwards, in case of overlap + CopyBoard(boards[framePtr+i], boards[firstMove+i]); + for(j=0; j forwardMostMove) currentMove = forwardMostMove; - if(currentMove < backwardMostMove) currentMove = backwardMostMove; + ToNrEvent(2*n-1); EndDialog(hDlg, TRUE); - DrawPosition(TRUE, boards[currentMove]); - if(currentMove > backwardMostMove) DisplayMove(currentMove - 1); - else DisplayMessage("", ""); return TRUE; } } @@ -8493,6 +8488,13 @@ typedef struct { } Enables; VOID +GreyRevert(Boolean grey) +{ // [HGM] vari: for retracting variations in local mode + HMENU hmenu = GetMenu(hwndMain); + EnableMenuItem(hmenu, IDM_Revert, MF_BYCOMMAND|(grey ? MF_GRAYED : MF_ENABLED)); +} + +VOID SetMenuEnables(HMENU hmenu, Enables *enab) { while (enab->item > 0) { diff --git a/xboard.c b/xboard.c index cefa62c..0f30640 100644 --- a/xboard.c +++ b/xboard.c @@ -3311,6 +3311,20 @@ typedef struct { } Enables; void +GreyRevert(grey) + Boolean grey; +{ + Widget w; + if (!menuBarWidget) return; + w = XtNameToWidget(menuBarWidget, "menuStep.Revert"); + if (w == NULL) { + DisplayError("menuStep.Revert", 0); + } else { + XtSetSensitive(w, !grey); + } +} + +void SetMenuEnables(enab) Enables *enab; { -- 1.7.0.4