// LT-PGN-VIEWER 3.47 (c) Lutz Tautenhahn (2001-2007)
// http://www.lutanho.net/pgn/
//
// This version has been seriously stripped down and slightly modified by Mekk

var autoScrollNotation = true;

var i, j, s, StartMove, MoveCount, MoveType, CanPass, EnPass, MaxMove=500, isInit=false, isCalculating=false;
var CurVar=0, activeAnchor=-1, startAnchor=-1, activeAnchorBG="#CCCCCC", TargetDocument;
var dragX, dragY, dragObj, dragBorder, dragImgBorder, isDragDrop=false, isAnimating=false, BoardPicLight, BoardPicDark, ParseType=1, AnnotationFile="";
dragImg=new Array(2);
dragPiece=new Array(8);
dragPiece[0]=-1;
dragPiece[4]=-1;

ShortPgnMoveText=new Array(3);
for (i=0; i<3; i++) ShortPgnMoveText[i] = new Array();
ShortPgnMoveText[0][CurVar]="";

PieceType = new Array(2); for (i=0; i<2; i++) PieceType[i] = new Array(16);
PiecePosX = new Array(2); for (i=0; i<2; i++) PiecePosX[i] = new Array(16);
PiecePosY = new Array(2); for (i=0; i<2; i++) PiecePosY[i] = new Array(16);
PieceMoves = new Array(2); for (i=0; i<2; i++) PieceMoves[i] = new Array(16);

var isRotated=false, isRecording=false, isNullMove=true, RecordCount=0, RecordedMoves="", SkipRefresh=0;
var AutoPlayInterval, isAutoPlay=false, Delay=1000;
var PieceName = "KQRBNP", ShowPieceName = "KQRBNP";
PieceCode = new Array(6); for (i=0; i<6; i++) PieceCode[i]=PieceName.charCodeAt(i);
var StandardFen = "rnbqkbnr/pppppppp/8/8/8/8/PPPPPPPP/RNBQKBNR w KQkq - 0 1";
var FenString = StandardFen;
ColorName = new Array("w","b","t"); //white, black, transparent
Castling = new Array(2); for (i=0; i<2; i++) Castling[i] = new Array(2);
Board = new Array(8); for (i=0; i<8; i++) Board[i] = new Array(8);

HalfMove = new Array(MaxMove+1);
HistMove = new Array(MaxMove);
HistPiece = new Array(2);
for (i=0; i<2; i++) HistPiece[i] = new Array(MaxMove);
HistType = new Array(2);
for (i=0; i<2; i++) HistType[i] = new Array(MaxMove);
HistPosX = new Array(2);
for (i=0; i<2; i++) HistPosX[i] = new Array(MaxMove);
HistPosY = new Array(2);
for (i=0; i<2; i++) HistPosY[i] = new Array(MaxMove);
MoveArray = new Array();

// Obrazki figurek
PiecePicWhiteOnLight = new Array(6);
PiecePicWhiteOnDark = new Array(6);
PiecePicBlackOnLight = new Array(6);
PiecePicBlackOnDark = new Array(6);

DocImg=new Array();

var PiecePathOld="-", PiecePath="", TransparentPath="", ImageOffset=0, Border=1, BorderColor="#404040";

function SetPiecePath(pp)
{
    PiecePath=pp;
}
function SetTransparentPath(pp)
{
    TransparentPath=pp;
}

function SetBorder(nn)
{
    Border=parseInt(nn);
}

function SetBorderColor(cc)
{
    if (cc.length==6) BorderColor="#"+cc;
    else BorderColor=cc;
}

function SetImg(ii,oo)
{
    if (DocImg[ii]==oo.src) return;
    DocImg[ii]=oo.src;
    if (isNaN(ii)) document.images[ii].src=oo.src;
    else document.images[ii+ImageOffset].src=oo.src;
}

function GetValue(oo)
{
    var vv="";
    eval("vv="+oo);
    return(vv);
}

function InitImages()
{
    if (PiecePathOld==PiecePath) return;
    var ii, jj;
    BoardPicLight = new Image();
    BoardPicLight.src = PiecePath+"w.gif";
    BoardPicDark = new Image();
    BoardPicDark.src = PiecePath+"b.gif";

    PiecePicWhiteOnLight[0] = new Image(); PiecePicWhiteOnLight[0].src = PiecePath + "wk_w.gif";
    PiecePicWhiteOnLight[1] = new Image(); PiecePicWhiteOnLight[1].src = PiecePath + "wq_w.gif";
    PiecePicWhiteOnLight[2] = new Image(); PiecePicWhiteOnLight[2].src = PiecePath + "wr_w.gif";
    PiecePicWhiteOnLight[3] = new Image(); PiecePicWhiteOnLight[3].src = PiecePath + "wb_w.gif";
    PiecePicWhiteOnLight[4] = new Image(); PiecePicWhiteOnLight[4].src = PiecePath + "wn_w.gif";
    PiecePicWhiteOnLight[5] = new Image(); PiecePicWhiteOnLight[5].src = PiecePath + "wp_w.gif";
    PiecePicWhiteOnDark[0] = new Image(); PiecePicWhiteOnDark[0].src = PiecePath + "wk_b.gif";
    PiecePicWhiteOnDark[1] = new Image(); PiecePicWhiteOnDark[1].src = PiecePath + "wq_b.gif";
    PiecePicWhiteOnDark[2] = new Image(); PiecePicWhiteOnDark[2].src = PiecePath + "wr_b.gif";
    PiecePicWhiteOnDark[3] = new Image(); PiecePicWhiteOnDark[3].src = PiecePath + "wb_b.gif";
    PiecePicWhiteOnDark[4] = new Image(); PiecePicWhiteOnDark[4].src = PiecePath + "wn_b.gif";
    PiecePicWhiteOnDark[5] = new Image(); PiecePicWhiteOnDark[5].src = PiecePath + "wp_b.gif";

    PiecePicBlackOnLight[0] = new Image(); PiecePicBlackOnLight[0].src = PiecePath + "bk_w.gif";
    PiecePicBlackOnLight[1] = new Image(); PiecePicBlackOnLight[1].src = PiecePath + "bq_w.gif";
    PiecePicBlackOnLight[2] = new Image(); PiecePicBlackOnLight[2].src = PiecePath + "br_w.gif";
    PiecePicBlackOnLight[3] = new Image(); PiecePicBlackOnLight[3].src = PiecePath + "bb_w.gif";
    PiecePicBlackOnLight[4] = new Image(); PiecePicBlackOnLight[4].src = PiecePath + "bn_w.gif";
    PiecePicBlackOnLight[5] = new Image(); PiecePicBlackOnLight[5].src = PiecePath + "bp_w.gif";
    PiecePicBlackOnDark[0] = new Image(); PiecePicBlackOnDark[0].src = PiecePath + "bk_b.gif";
    PiecePicBlackOnDark[1] = new Image(); PiecePicBlackOnDark[1].src = PiecePath + "bq_b.gif";
    PiecePicBlackOnDark[2] = new Image(); PiecePicBlackOnDark[2].src = PiecePath + "br_b.gif";
    PiecePicBlackOnDark[3] = new Image(); PiecePicBlackOnDark[3].src = PiecePath + "bb_b.gif";
    PiecePicBlackOnDark[4] = new Image(); PiecePicBlackOnDark[4].src = PiecePath + "bn_b.gif";
    PiecePicBlackOnDark[5] = new Image(); PiecePicBlackOnDark[5].src = PiecePath + "bp_b.gif";

    PiecePathOld=PiecePath;
    //ImageOffset=0;
    DocImg.length=0;
}

function sign(nn)
{
    if (nn>0) return(1);
    if (nn<0) return(-1);
    return(0);
}

function Init(rr)
{
    var cc, ii, jj, kk, ll, nn, mm;
    isInit=true;
    if (isAutoPlay) SetAutoPlay(false);
    if (rr!='') {
        FenString=rr;
        while (FenString.indexOf("|")>0) FenString=FenString.replace("|","/");
    }
    if (FenString=='standard')
        FenString=StandardFen;
    if ((document.BoardForm)&&(document.BoardForm.FEN))
        document.BoardForm.FEN.value=FenString;
    if (FenString == StandardFen) {
        for (ii=0; ii<2; ii++) {
            PieceType[ii][0]=0;
            PiecePosX[ii][0]=4;
            PieceType[ii][1]=1;
            PiecePosX[ii][1]=3;
            PieceType[ii][2]=2;
            PiecePosX[ii][2]=0;
            PieceType[ii][3]=2;
            PiecePosX[ii][3]=7;
            PieceType[ii][4]=3;
            PiecePosX[ii][4]=2;
            PieceType[ii][5]=3;
            PiecePosX[ii][5]=5;
            PieceType[ii][6]=4;
            PiecePosX[ii][6]=1;
            PieceType[ii][7]=4;
            PiecePosX[ii][7]=6;
            for (jj=0; jj<8; jj++) {
                PieceType[ii][jj+8]=5;
                PiecePosX[ii][jj+8]=jj;
            }
            for (jj=0; jj<16; jj++) {
                PieceMoves[ii][jj]=0;
                PiecePosY[ii][jj]=(1-ii)*Math.floor(jj/8)+ii*(7-Math.floor(jj/8));
            }
        }
        for (ii=0; ii<8; ii++) {
            for (jj=0; jj<8; jj++) Board[ii][jj]=0;
        }
        for (ii=0; ii<2; ii++) {
            for (jj=0; jj<16; jj++)
                Board[PiecePosX[ii][jj]][PiecePosY[ii][jj]]=(PieceType[ii][jj]+1)*(1-2*ii);
        }
        for (ii=0; ii<2; ii++) {
            for (jj=0; jj<2; jj++)
                Castling[ii][jj]=1;
        }
        EnPass=-1;
        HalfMove[0]=0;
        StartMove=0;
        MoveCount=StartMove;
        MoveType=StartMove%2;
        RecordCount=0;
        CurVar=0;
        MoveArray.length=0;
        if (TargetDocument) HighlightMove("m"+MoveCount+"v"+CurVar);
    }
    else {
        for (ii=0; ii<2; ii++) {
            for (jj=0; jj<16; jj++) {
                PieceType[ii][jj]=-1;
                PiecePosX[ii][jj]=0;
                PiecePosY[ii][jj]=0;
                PieceMoves[ii][jj]=0;
            }
        }
        ii=0; jj=7; ll=0; nn=1; mm=1; cc=FenString.charAt(ll++);
        while (cc!=" ")
        {
            if (cc=="/")
            {
                if (ii!=8)
                {
                    alert("Invalid FEN [1]: char "+ll+" in "+FenString);
                    Init('standard');
                    return;
                }
                ii=0;
                jj--;
            }
            if (ii==8)
            {
                alert("Invalid FEN [2]: char "+ll+" in "+FenString);
                Init('standard');
                return;
            }
            if (! isNaN(cc))
            {
                ii+=parseInt(cc);
                if ((ii<0)||(ii>8))
                {
                    alert("Invalid FEN [3]: char "+ll+" in "+FenString);
                    Init('standard');
                    return;
                }
            }
            if (cc.charCodeAt(0)==PieceName.toUpperCase().charCodeAt(0))
            {
                if (PieceType[0][0]!=-1)
                {
                    alert("Invalid FEN [4]: char "+ll+" in "+FenString);
                    Init('standard');
                    return;
                }
                PieceType[0][0]=0;
                PiecePosX[0][0]=ii;
                PiecePosY[0][0]=jj;
                ii++;
            }
            if (cc.charCodeAt(0)==PieceName.toLowerCase().charCodeAt(0))
            {
                if (PieceType[1][0]!=-1)
                {
                    alert("Invalid FEN [5]: char "+ll+" in "+FenString);
                    Init('standard');
                    return;
                }
                PieceType[1][0]=0;
                PiecePosX[1][0]=ii;
                PiecePosY[1][0]=jj;
                ii++;
            }
            for (kk=1; kk<6; kk++)
            {
                if (cc.charCodeAt(0)==PieceName.toUpperCase().charCodeAt(kk))
                {
                    if (nn==16)
                    {
                        alert("Invalid FEN [6]: char "+ll+" in "+FenString);
                        Init('standard');
                        return;
                    }
                    PieceType[0][nn]=kk;
                    PiecePosX[0][nn]=ii;
                    PiecePosY[0][nn]=jj;
                    nn++;
                    ii++;
                }
                if (cc.charCodeAt(0)==PieceName.toLowerCase().charCodeAt(kk))
                {
                    if (mm==16)
                    {
                        alert("Invalid FEN [7]: char "+ll+" in "+FenString);
                        Init('standard');
                        return;
                    }
                    PieceType[1][mm]=kk;
                    PiecePosX[1][mm]=ii;
                    PiecePosY[1][mm]=jj;
                    mm++;
                    ii++;
                }
            }
            if (ll<FenString.length)
                cc=FenString.charAt(ll++);
            else cc=" ";
        }
        if ((ii!=8)||(jj!=0))
        {
            alert("Invalid FEN [8]: char "+ll+" in "+FenString);
            Init('standard');
            return;
        }
        if ((PieceType[0][0]==-1)||(PieceType[1][0]==-1))
        {
            alert("Invalid FEN [9]: char "+ll+" missing king");
            Init('standard');
            return;
        }
        if (ll==FenString.length)
        {
            FenString+=" w ";
            FenString+=PieceName.toUpperCase().charAt(0);
            FenString+=PieceName.toUpperCase().charAt(1);
            FenString+=PieceName.toLowerCase().charAt(0);
            FenString+=PieceName.toLowerCase().charAt(1);
            FenString+=" - 0 1";
            ll++;
        }
        // alert("Invalid FEN [10]: char "+ll+" missing active color. " + FenString);
        cc=FenString.charAt(ll++);
        if ((cc=="w")||(cc=="b"))
        {
            if (cc=="w") StartMove=0;
            else StartMove=1;
        }
        else
        {
            alert("Invalid FEN [11]: char "+ll+" invalid active color");
            Init('standard');
            return;
        }
        ll++;
        if (ll>=FenString.length)
        {
            alert("Invalid FEN [12]: char "+ll+" missing castling availability");
            Init('standard');
            return;
        }
        Castling[0][0]=0; Castling[0][1]=0; Castling[1][0]=0; Castling[1][1]=0;
        cc=FenString.charAt(ll++);
        while (cc!=" ")
        {
            if (cc.charCodeAt(0)==PieceName.toUpperCase().charCodeAt(0))
                Castling[0][0]=1;
            if (cc.charCodeAt(0)==PieceName.toUpperCase().charCodeAt(1))
                Castling[0][1]=1;
            if (cc.charCodeAt(0)==PieceName.toLowerCase().charCodeAt(0))
                Castling[1][0]=1;
            if (cc.charCodeAt(0)==PieceName.toLowerCase().charCodeAt(1))
                Castling[1][1]=1;
            if (ll<FenString.length)
                cc=FenString.charAt(ll++);
            else cc=" ";
        }
        if (ll==FenString.length)
        {
            alert("Invalid FEN [13]: char "+ll+" missing en passant target square");
            Init('standard');
            return;
        }
        EnPass=-1;
        cc=FenString.charAt(ll++);
        while (cc!=" ")
        {
            if ((cc.charCodeAt(0)-97>=0)&&(cc.charCodeAt(0)-97<=7))
                EnPass=cc.charCodeAt(0)-97;
            if (ll<FenString.length)
                cc=FenString.charAt(ll++);
            else cc=" ";
        }
        if (ll==FenString.length)
        {
            alert("Invalid FEN [14]: char "+ll+" missing halfmove clock");
            Init('standard');
            return;
        }
        HalfMove[0]=0;
        cc=FenString.charAt(ll++);
        while (cc!=" ")
        {
            if (isNaN(cc))
            {
                alert("Invalid FEN [15]: char "+ll+" invalid halfmove clock");
                Init('standard');
                return;
            }
            HalfMove[0]=HalfMove[0]*10+parseInt(cc);
            if (ll<FenString.length)
                cc=FenString.charAt(ll++);
            else cc=" ";
        }
        if (ll==FenString.length)
        {
            alert("Invalid FEN [16]: char "+ll+" missing fullmove number");
            Init('standard');
            return;
        }
        cc=FenString.substring(ll++);
        if (isNaN(cc))
        {
            alert("Invalid FEN [17]: char "+ll+" invalid fullmove number");
            Init('standard');
            return;
        }
        if (cc<=0)
        {
            alert("Invalid FEN [18]: char "+ll+" invalid fullmove number");
            Init('standard');
            return;
        }
        StartMove+=2*(parseInt(cc)-1);
        for (ii=0; ii<8; ii++)
        {
            for (jj=0; jj<8; jj++) Board[ii][jj]=0;
        }
        for (ii=0; ii<2; ii++)
        {
            for (jj=0; jj<16; jj++)
            {
                if (PieceType[ii][jj]!=-1)
                    Board[PiecePosX[ii][jj]][PiecePosY[ii][jj]]=(PieceType[ii][jj]+1)*(1-2*ii);
            }
        }
        if (document.BoardForm)
        {
            RefreshBoard();
            if (document.BoardForm.Position)
            {
                if (StartMove%2==0) document.BoardForm.Position.value="white to move";
                else document.BoardForm.Position.value="black to move";
            }
        }
        MoveCount=StartMove;
        MoveType=StartMove%2;
        RecordCount=0;
        CurVar=0;
        MoveArray.length=0;
        if (TargetDocument) HighlightMove("m"+MoveCount+"v"+CurVar);
    }
}

function MoveBack(nn)
{
    var ii, jj, cc;
    for (jj=0; (jj<nn)&&(MoveCount>StartMove); jj++)
    {
        if (RecordCount>0) RecordCount--;
        MoveCount--;
        MoveType=1-MoveType;
        cc=MoveCount-StartMove;
        ii=HistPiece[1][cc];
        if ((0<=ii)&&(ii<16)) //we must do this here because of Chess960 castling
        {
            Board[PiecePosX[MoveType][ii]][PiecePosY[MoveType][ii]]=0;
            Board[HistPosX[1][cc]][HistPosY[1][cc]]=(HistType[1][cc]+1)*(1-2*MoveType);
        }
        ii=HistPiece[0][cc];
        Board[PiecePosX[MoveType][ii]][PiecePosY[MoveType][ii]]=0;
        Board[HistPosX[0][cc]][HistPosY[0][cc]]=(HistType[0][cc]+1)*(1-2*MoveType);
        PieceType[MoveType][ii]=HistType[0][cc];
        PiecePosX[MoveType][ii]=HistPosX[0][cc];
        PiecePosY[MoveType][ii]=HistPosY[0][cc];
        PieceMoves[MoveType][ii]--;
        ii=HistPiece[1][cc];
        if ((0<=ii)&&(ii<16))
        {
            PieceType[MoveType][ii]=HistType[1][cc];
            PiecePosX[MoveType][ii]=HistPosX[1][cc];
            PiecePosY[MoveType][ii]=HistPosY[1][cc];
            PieceMoves[MoveType][ii]--;
        }
        ii-=16;
        if (0<=ii)
        {
            Board[HistPosX[1][cc]][HistPosY[1][cc]]=(HistType[1][cc]+1)*(2*MoveType-1);
            PieceType[1-MoveType][ii]=HistType[1][cc];
            PiecePosX[1-MoveType][ii]=HistPosX[1][cc];
            PiecePosY[1-MoveType][ii]=HistPosY[1][cc];
            PieceMoves[1-MoveType][ii]--;
        }
        if (CurVar!=0)
        {
            if (MoveCount==ShortPgnMoveText[2][CurVar])
            {
                CurVar=ShortPgnMoveText[1][CurVar];
                if ((!isCalculating)&&(document.BoardForm)&&(document.BoardForm.PgnMoveText))
                    document.BoardForm.PgnMoveText.value=ShortPgnMoveText[0][CurVar];
            }
        }
    }
    if (isCalculating) return;
    if (document.BoardForm)
    {
        RefreshBoard();
        if (document.BoardForm.Position)
        {
            if (MoveCount>StartMove)
                document.BoardForm.Position.value=TransformSAN(HistMove[MoveCount-StartMove-1]);
            else
                document.BoardForm.Position.value="";
        }
    }
    if (TargetDocument) HighlightMove("m"+MoveCount+"v"+CurVar);
    if (AutoPlayInterval) clearTimeout(AutoPlayInterval);
    if (isAutoPlay) AutoPlayInterval=setTimeout("MoveBack("+nn+")", Delay);
}

function Uncomment(ss)
{
    if (! ss) return(ss);
    var ii, jj, llist=ss.split("{"), ll=llist.length, uu=llist[0], tt, kk;
    for (ii=1; ii<ll; ii++)
    {
        tt=llist[ii];
        jj=tt.indexOf("}")+1;
        if (jj>0) uu+=tt.substring(jj);
    }
    llist=uu.split("$");
    ll=llist.length;
    uu=llist[0];
    for (ii=1; ii<ll; ii++)
    {
        tt=llist[ii];
        kk=tt.length;
        for (jj=0; jj<kk; jj++)
        {
            if (isNaN(parseInt(tt.charAt(jj))))
                //if (tt.charAt(jj)==" ")
            {
                uu+=tt.substring(jj+1);
                jj=kk;
            }
        }
    }
    return(uu);
}

function GetComment(ss)
{
    if (! ss) return(ss);
    var ii, jj, llist=ss.split("}"), ll=llist.length, uu="", tt, kk;
    for (ii=0; ii<ll; ii++)
    {
        tt=llist[ii];
        jj=tt.indexOf("{")+1;
        if (jj>0) uu+=tt.substring(jj);
    }
    return(uu);
}

function MoveForward(nn, rr)
{
    var ii,ffst=0,llst,ssearch,ssub,ffull,mmove0="",mmove1="";
    if (rr);
    else
    {
        if ((document.BoardForm)&&(document.BoardForm.PgnMoveText))
            ShortPgnMoveText[0][CurVar]=document.BoardForm.PgnMoveText.value;
    }
    ffull=Uncomment(ShortPgnMoveText[0][CurVar]);
    for (ii=0; (ii<nn)&&(ffst>=0)&&(MoveCount<MaxMove); ii++)
    {
        ssearch=Math.floor(MoveCount/2+2)+".";
        llst=ffull.indexOf(ssearch);
        ssearch=Math.floor(MoveCount/2+1)+".";
        ffst=ffull.indexOf(ssearch);
        if (ffst>=0)
        {
            ffst+=ssearch.length;
            if (llst<0)
                ssub=ffull.substring(ffst);
            else
                ssub=ffull.substring(ffst, llst);
            mmove0=GetMove(ssub,MoveType);
            if (mmove0!="")
            {
                if (ParseMove(mmove0, true)>0)
                {
                    mmove1=mmove0;
                    if (MoveType==0)
                        HistMove[MoveCount-StartMove]=Math.floor((MoveCount+2)/2)+"."+mmove1;
                    else
                        HistMove[MoveCount-StartMove]=Math.floor((MoveCount+2)/2)+". ... "+mmove1;
                    MoveCount++;
                    MoveType=1-MoveType;
                }
                else
                {
                    if (MoveType==1)
                    {
                        ssub=Math.floor(MoveCount/2+1);
                        ssearch=ssub+"....";
                        ffst=ffull.indexOf(ssearch);
                        if (ffst<0) {
                            ssearch=ssub+". ..."; ffst=ffull.indexOf(ssearch); }
                        if (ffst<0) {
                            ssearch=ssub+". .."; ffst=ffull.indexOf(ssearch); }
                        if (ffst<0) {
                            ssearch=ssub+" ..."; ffst=ffull.indexOf(ssearch); }
                        if (ffst<0) {
                            ssearch=ssub+"..."; ffst=ffull.indexOf(ssearch); }
                        if (ffst<0) {
                            ssearch=ssub+" .."; ffst=ffull.indexOf(ssearch); }
                        if (ffst>=0)
                        {
                            ffst+=ssearch.length;
                            if (llst<0) ssub=ffull.substring(ffst);
                            else ssub=ffull.substring(ffst, llst);
                            mmove0=GetMove(ssub,0);
                            if (mmove0!="")
                            {
                                if (ParseMove(mmove0, true)>0)
                                {
                                    mmove1=mmove0;
                                    HistMove[MoveCount-StartMove]=Math.floor((MoveCount+2)/2)+". ... "+mmove1;
                                    MoveCount++;
                                    MoveType=1-MoveType;
                                }
                                else
                                {
                                    ffst=-1;
                                    //alert(mmove0+" is not a valid move.");
                                }
                            }
                        }
                    }
                    else
                    {
                        ffst=-1;
                        //alert(mmove0+" is not a valid move.");
                    }
                }
            }
            else ffst=-1;
        }
    }
    if (isCalculating) return;
    if (document.BoardForm)
    {
        if ((document.BoardForm.Position)&&(mmove1!=""))
            document.BoardForm.Position.value=TransformSAN(HistMove[MoveCount-StartMove-1]);
        if ((mmove1!="")&&(isDragDrop)&&(nn==1)&&(!dragObj)&&(dragPiece[0]>=0)&&(!rr)&&(!isAnimating)) AnimateBoard(1);
        else RefreshBoard();
    }
    if (TargetDocument) HighlightMove("m"+MoveCount+"v"+CurVar);
    if (AutoPlayInterval) clearTimeout(AutoPlayInterval);
    if (isAutoPlay) AutoPlayInterval=setTimeout("MoveForward("+nn+")", Delay);
}

function ParseMove(mm, sstore)
{
    var ii, ffrom="", ccapt=0, ll, yy1i=-1;
    var ttype0=-1, xx0=-1, yy0=-1, ttype1=-1, xx1=-1, yy1=-1;
    if (MoveCount>StartMove)
    {
        CanPass=-1;
        ii=HistPiece[0][MoveCount-StartMove-1];
        if ((HistType[0][MoveCount-StartMove-1]==5)&&(Math.abs(HistPosY[0][MoveCount-StartMove-1]-PiecePosY[1-MoveType][ii])==2))
            CanPass=PiecePosX[1-MoveType][ii];
    }
    else
        CanPass=EnPass;
    ii=1;
    while (ii<mm.length)
    {
        if (! isNaN(mm.charAt(ii)))
        {
            xx1=mm.charCodeAt(ii-1)-97;
            yy1=mm.charAt(ii)-1;
            yy1i=ii;
            ffrom=mm.substring(0, ii-1);
        }
        ii++;
    }
    if ((xx1<0)||(xx1>7)||(yy1<0)||(yy1>7))
    {
        if ((mm.indexOf("O")>=0)||(mm.indexOf("0")>=0))
        {
            if ((mm.indexOf("O-O-O")>=0)||(mm.indexOf("0-0-0")>=0)||(mm.indexOf("O–O–O")>=0)||(mm.indexOf("0–0–0")>=0))
            {
                if (EvalMove(ttype0, 6, xx0, yy0, ttype1, xx1, yy1, ccapt, sstore))
                    return(1);
                return(0);
            }
            if ((mm.indexOf("O-O")>=0)||(mm.indexOf("0-0")>=0)||(mm.indexOf("O–O")>=0)||(mm.indexOf("0–0")>=0))
            {
                if (EvalMove(ttype0, 7, xx0, yy0, ttype1, xx1, yy1, ccapt, sstore))
                    return(1);
                return(0);
            }
            return(0);
        }
        if ((mm.indexOf("---")>=0)||(mm.indexOf("–––")>=0))
            //if (mm.indexOf("...")>=0) //is buggy
        {
            if (EvalMove(ttype0, 8, xx0, yy0, ttype1, xx1, yy1, ccapt, sstore))
                return(1);
            return(0);
        }
        return(0);
    }
    ll=ffrom.length;
    ttype0=5;
    if (ll>0)
    {
        for (ii=0; ii<5; ii++)
        {
            if (ffrom.charCodeAt(0)==PieceCode[ii])
                ttype0=ii;
        }
        if (ffrom.charAt(ll-1)=="x") ccapt=1;
        else
        {
            if ((ffrom.charAt(ll-1)=="-")||(ffrom.charAt(ll-1)=="–")) ll--; //Smith Notation
        }
        if (isNaN(mm.charAt(ll-1-ccapt)))
        {
            xx0=ffrom.charCodeAt(ll-1-ccapt)-97;
            if ((xx0<0)||(xx0>7)) xx0=-1;
        }
        else
        {
            yy0=ffrom.charAt(ll-1-ccapt)-1;
            if ((yy0<0)||(yy0>7)) yy0=-1;
        }
        if ((yy0>=0)&&(isNaN(mm.charAt(ll-2-ccapt)))) //Smith Notation
        {
            xx0=ffrom.charCodeAt(ll-2-ccapt)-97;
            if ((xx0<0)||(xx0>7)) xx0=-1;
            else
            {
                ttype0=Math.abs(Board[xx0][yy0])-1;
                if ((ttype0==0)&&(xx0-xx1>1)&&(yy0==yy1))
                {
                    if (EvalMove(ttype0, 6, xx0, yy0, -1, -1, -1, 0, sstore))
                        return(1);
                    return(0);
                }
                if ((ttype0==0)&&(xx1-xx0>1)&&(yy0==yy1))
                {
                    if (EvalMove(ttype0, 7, xx0, yy0, -1, -1, -1, 0, sstore))
                        return(1);
                    return(0);
                }
            }
        }
    }
    if (Board[xx1][yy1]!=0) ccapt=1;
    else
    {
        if ((ttype0==5)&&(xx1==CanPass)&&(yy1==5-3*MoveType)) ccapt=1;
    }
    ttype1=ttype0;
    ii=mm.indexOf("=");
    if (ii<0) ii=yy1i;
    if ((ii>0)&&(ii<mm.length-1))
    {
        if (ttype0==5)
        {
            ii=mm.charCodeAt(ii+1);
            if (ii==PieceCode[1]) ttype1=1;
            if (ii==PieceCode[2]) ttype1=2;
            if (ii==PieceCode[3]) ttype1=3;
            if (ii==PieceCode[4]) ttype1=4;
        }
    }
    if (sstore)
    {
        for (ii=0; ii<16; ii++)
        {
            if (PieceType[MoveType][ii]==ttype0)
            {
                if (EvalMove(ii, ttype0, xx0, yy0, ttype1, xx1, yy1, ccapt, true))
                    return(1);
            }
        }
    }
    else
    {
        ll=0;
        for (ii=0; ii<16; ii++)
        {
            if (PieceType[MoveType][ii]==ttype0)
            {
                if (EvalMove(ii, ttype0, xx0, yy0, ttype1, xx1, yy1, ccapt, false))
                    ll++;
            }
        }
        return(ll);
    }
    return(0);
}

function CanCastleLong()
{
    if (Castling[MoveType][1]==0) return(-1);
    if (PieceMoves[MoveType][0]>0) return(-1);
    var jj=0;
    while (jj<16)
    {
        if ((PiecePosX[MoveType][jj]<PiecePosX[MoveType][0])&&
            (PiecePosY[MoveType][jj]==MoveType*7)&&
            (PieceType[MoveType][jj]==2)&&
            (PieceMoves[MoveType][jj]==0))
            jj+=100;
        else jj++;
    }
    if (jj==16) return(-1);
    jj-=100;
    Board[PiecePosX[MoveType][0]][MoveType*7]=0;
    Board[PiecePosX[MoveType][jj]][MoveType*7]=0;
    var ff=PiecePosX[MoveType][jj];
    if (ff>2) ff=2;
    while ((ff<PiecePosX[MoveType][0])||(ff<=3))
    {
        if (Board[ff][MoveType*7]!=0)
        {
            Board[PiecePosX[MoveType][0]][MoveType*7]=1-2*MoveType;
            Board[PiecePosX[MoveType][jj]][MoveType*7]=(1-2*MoveType)*3;
            return(-1);
        }
        ff++;
    }
    Board[PiecePosX[MoveType][0]][MoveType*7]=1-2*MoveType;
    Board[PiecePosX[MoveType][jj]][MoveType*7]=(1-2*MoveType)*3;
    return(jj);
}

function CanCastleShort()
{
    if (Castling[MoveType][0]==0) return(-1);
    if (PieceMoves[MoveType][0]>0) return(-1);
    var jj=0;
    while (jj<16)
    {
        if ((PiecePosX[MoveType][jj]>PiecePosX[MoveType][0])&&
            (PiecePosY[MoveType][jj]==MoveType*7)&&
            (PieceType[MoveType][jj]==2)&&
            (PieceMoves[MoveType][jj]==0))
            jj+=100;
        else jj++;
    }
    if (jj==16) return(-1);
    jj-=100;
    Board[PiecePosX[MoveType][0]][MoveType*7]=0;
    Board[PiecePosX[MoveType][jj]][MoveType*7]=0;
    var ff=PiecePosX[MoveType][jj];
    if (ff<6) ff=6;
    while ((ff>PiecePosX[MoveType][0])||(ff>=5))
    {
        if (Board[ff][MoveType*7]!=0)
        {
            Board[PiecePosX[MoveType][0]][MoveType*7]=1-2*MoveType;
            Board[PiecePosX[MoveType][jj]][MoveType*7]=(1-2*MoveType)*3;
            return(-1);
        }
        ff--;
    }
    Board[PiecePosX[MoveType][0]][MoveType*7]=1-2*MoveType;
    Board[PiecePosX[MoveType][jj]][MoveType*7]=(1-2*MoveType)*3;
    return(jj);
}
function EvalMove(ii, ttype0, xx0, yy0, ttype1, xx1, yy1, ccapt, sstore)
{
    var ddx, ddy, xx, yy, jj=-1, ttype2=-1, xx2=xx1, yy2=xx1, ttype3=-1, xx3=-1, yy3=-1, ff;
    if (ttype0==6) //O-O-O with Chess960 rules
    {
        jj=CanCastleLong();
        if (jj<0) return(false);
        if (StoreMove(0, 0, 2, MoveType*7, jj, 2, 3, MoveType*7, sstore))
            return(true);
        else return(false);
    }
    if (ttype0==7) //O-O with Chess960 rules
    {
        jj=CanCastleShort();
        if (jj<0) return(false);
        if (StoreMove(0, 0, 6, MoveType*7, jj, 2, 5, MoveType*7, sstore))
            return(true);
        return(false);
    }
    if (ttype0==8) // --- NullMove
    {
        if (StoreMove(0, 0, PiecePosX[MoveType][0], PiecePosY[MoveType][0], -1, -1, -1, -1, sstore))
            return(true);
        return(false);
    }
    if ((PiecePosX[MoveType][ii]==xx1)&&(PiecePosY[MoveType][ii]==yy1))
        return(false);
    if ((ccapt==0)&&(Board[xx1][yy1]!=0))
        return(false);
    if ((ccapt>0)&&(sign(Board[xx1][yy1])!=(2*MoveType-1)))
    {
        if ((ttype0!=5)||(CanPass!=xx1)||(yy1!=5-3*MoveType))
            return(false);
    }
    if ((xx0>=0)&&(xx0!=PiecePosX[MoveType][ii])) return(false);
    if ((yy0>=0)&&(yy0!=PiecePosY[MoveType][ii])) return(false);
    if (ttype0==0)
    {
        //if ((xx0>=0)||(yy0>=0)) return(false); //because of Smith Notation
        if (Math.abs(PiecePosX[MoveType][ii]-xx1)>1) return(false);
        if (Math.abs(PiecePosY[MoveType][ii]-yy1)>1) return(false);
    }
    if (ttype0==1)
    {
        if ((Math.abs(PiecePosX[MoveType][ii]-xx1)!=Math.abs(PiecePosY[MoveType][ii]-yy1))&&
            ((PiecePosX[MoveType][ii]-xx1)*(PiecePosY[MoveType][ii]-yy1)!=0))
            return(false);
    }
    if (ttype0==2)
    {
        if ((PiecePosX[MoveType][ii]-xx1)*(PiecePosY[MoveType][ii]-yy1)!=0)
            return(false);
    }
    if (ttype0==3)
    {
        if (Math.abs(PiecePosX[MoveType][ii]-xx1)!=Math.abs(PiecePosY[MoveType][ii]-yy1))
            return(false);
    }
    if (ttype0==4)
    {
        if (Math.abs(PiecePosX[MoveType][ii]-xx1)*Math.abs(PiecePosY[MoveType][ii]-yy1)!=2)
            return(false);
    }
    if ((ttype0==1)||(ttype0==2)||(ttype0==3))
    {
        ddx=sign(xx1-PiecePosX[MoveType][ii]);
        ddy=sign(yy1-PiecePosY[MoveType][ii]);
        xx=PiecePosX[MoveType][ii]+ddx;
        yy=PiecePosY[MoveType][ii]+ddy;
        while ((xx!=xx1)||(yy!=yy1))
        {
            if (Board[xx][yy]!=0) return(false);
            xx+=ddx;
            yy+=ddy;
        }
    }
    if (ttype0==5)
    {
        if (Math.abs(PiecePosX[MoveType][ii]-xx1)!=ccapt) return(false);
        if ((yy1==7*(1-MoveType))&&(ttype0==ttype1)) return(false);
        if (ccapt==0)
        {
            if (PiecePosY[MoveType][ii]-yy1==4*MoveType-2)
            {
                if (PiecePosY[MoveType][ii]!=1+5*MoveType) return(false);
                if (Board[xx1][yy1+2*MoveType-1]!=0) return(false);
            }
            else
            {
                if (PiecePosY[MoveType][ii]-yy1!=2*MoveType-1) return(false);
            }
        }
        else
        {
            if (PiecePosY[MoveType][ii]-yy1!=2*MoveType-1) return(false);
        }
    }
    if (ttype1!=ttype0)
    {
        if (ttype0!=5) return(false);
        if (ttype1>=5) return(false);
        if (yy1!=7-7*MoveType) return(false);
    }
    if ((ttype0<=5)&&(ccapt>0))
    {
        jj=15;
        while ((jj>=0)&&(ttype3<0))
        {
            if ((PieceType[1-MoveType][jj]>0)&&
                (PiecePosX[1-MoveType][jj]==xx1)&&
                (PiecePosY[1-MoveType][jj]==yy1))
                ttype3=PieceType[1-MoveType][jj];
            else
                jj--;
        }
        if ((ttype3==-1)&&(ttype0==5)&&(CanPass>=0))
        {
            jj=15;
            while ((jj>=0)&&(ttype3<0))
            {
                if ((PieceType[1-MoveType][jj]==5)&&
                    (PiecePosX[1-MoveType][jj]==xx1)&&
                    (PiecePosY[1-MoveType][jj]==yy1-1+2*MoveType))
                    ttype3=PieceType[1-MoveType][jj];
                else
                    jj--;
            }
        }
        ttype3=-1;
    }
    if (StoreMove(ii, ttype1, xx1, yy1, jj, ttype3, xx3, yy3, sstore))
        return(true);
    return(false);
}

function StoreMove(ii, ttype1, xx1, yy1, jj, ttype3, xx3, yy3, sstore)
{
    var iis_check=0, ll, cc=MoveCount-StartMove, ff=PiecePosX[MoveType][0], dd=0;
    if ((ttype1==5)||((jj>=0)&&(ttype3<0)))
        HalfMove[cc+1]=0;
    else
        HalfMove[cc+1]=HalfMove[cc]+1;
    HistPiece[0][cc] = ii;
    HistType[0][cc] = PieceType[MoveType][ii];
    HistPosX[0][cc] = PiecePosX[MoveType][ii];
    HistPosY[0][cc] = PiecePosY[MoveType][ii];
    if (!isAnimating)
    {
        dragPiece[0]=PiecePosX[MoveType][ii];
        dragPiece[1]=PiecePosY[MoveType][ii];
        dragPiece[2]=xx1;
        dragPiece[3]=yy1;
        dragPiece[4]=-1;
    }
    if (jj<0)
        HistPiece[1][cc] = -1;
    else
    {
        if (ttype3>=0)
        {
            HistPiece[1][cc] = jj;
            HistType[1][cc] = PieceType[MoveType][jj];
            HistPosX[1][cc] = PiecePosX[MoveType][jj];
            HistPosY[1][cc] = PiecePosY[MoveType][jj];
            if (!isAnimating)
            {
                dragPiece[4]=PiecePosX[MoveType][jj];
                dragPiece[5]=PiecePosY[MoveType][jj];
                dragPiece[6]=xx3;
                dragPiece[7]=yy3;
            }
        }
        else
        {
            HistPiece[1][cc] = 16+jj;
            HistType[1][cc] = PieceType[1-MoveType][jj];
            HistPosX[1][cc] = PiecePosX[1-MoveType][jj];
            HistPosY[1][cc] = PiecePosY[1-MoveType][jj];
        }
    }

    Board[PiecePosX[MoveType][ii]][PiecePosY[MoveType][ii]]=0;
    if (jj>=0)
    {
        if (ttype3<0)
            Board[PiecePosX[1-MoveType][jj]][PiecePosY[1-MoveType][jj]]=0;
        else
            Board[PiecePosX[MoveType][jj]][PiecePosY[MoveType][jj]]=0;
    }
    PieceType[MoveType][ii]=ttype1;
    if ((PiecePosX[MoveType][ii]!=xx1)||(PiecePosY[MoveType][ii]!=yy1)||(jj>=0))
    {
        PieceMoves[MoveType][ii]++; dd++; } //not a nullmove
    PiecePosX[MoveType][ii]=xx1;
    PiecePosY[MoveType][ii]=yy1;
    if (jj>=0)
    {
        if (ttype3<0)
        {
            PieceType[1-MoveType][jj]=ttype3;
            PieceMoves[1-MoveType][jj]++;
        }
        else
        {
            PiecePosX[MoveType][jj]=xx3;
            PiecePosY[MoveType][jj]=yy3;
            PieceMoves[MoveType][jj]++;
        }
    }
    if (jj>=0)
    {
        if (ttype3<0)
            Board[PiecePosX[1-MoveType][jj]][PiecePosY[1-MoveType][jj]]=0;
        else
            Board[PiecePosX[MoveType][jj]][PiecePosY[MoveType][jj]]=(PieceType[MoveType][jj]+1)*(1-2*MoveType);
    }
    Board[PiecePosX[MoveType][ii]][PiecePosY[MoveType][ii]]=(PieceType[MoveType][ii]+1)*(1-2*MoveType);

    if ((ttype1==0)&&(ttype3==2)) //O-O-O, O-O
    {
        while (ff>xx1)
        {
            iis_check+=IsCheck(ff, MoveType*7, MoveType);
            ff--;
        }
        while (ff<xx1)
        {
            iis_check+=IsCheck(ff, MoveType*7, MoveType);
            ff++;
        }
    }
    iis_check+=IsCheck(PiecePosX[MoveType][0], PiecePosY[MoveType][0], MoveType);

    if ((iis_check==0)&&(sstore))
    {
        MoveArray[cc]=String.fromCharCode(97+HistPosX[0][cc])+(HistPosY[0][cc]+1)+String.fromCharCode(97+PiecePosX[MoveType][ii])+(PiecePosY[MoveType][ii]+1);
        if (HistType[0][cc] != PieceType[MoveType][ii])
        {
            if (MoveType==0) MoveArray[cc]+=PieceName.charAt(PieceType[MoveType][ii]);
            else MoveArray[cc]+=PieceName.charAt(PieceType[MoveType][ii]).toLowerCase();
        }
        MoveArray.length=cc+1;
        return(true);
    }

    Board[PiecePosX[MoveType][ii]][PiecePosY[MoveType][ii]]=0;
    Board[HistPosX[0][cc]][HistPosY[0][cc]]=(HistType[0][cc]+1)*(1-2*MoveType);
    PieceType[MoveType][ii]=HistType[0][cc];
    PiecePosX[MoveType][ii]=HistPosX[0][cc];
    PiecePosY[MoveType][ii]=HistPosY[0][cc];
    PieceMoves[MoveType][ii]-=dd;
    if (jj>=0)
    {
        if (ttype3>=0)
        {
            Board[PiecePosX[MoveType][jj]][PiecePosY[MoveType][jj]]=0;
            Board[HistPosX[0][cc]][HistPosY[0][cc]]=(HistType[0][cc]+1)*(1-2*MoveType);
            Board[HistPosX[1][cc]][HistPosY[1][cc]]=(HistType[1][cc]+1)*(1-2*MoveType);
            PieceType[MoveType][jj]=HistType[1][cc];
            PiecePosX[MoveType][jj]=HistPosX[1][cc];
            PiecePosY[MoveType][jj]=HistPosY[1][cc];
            PieceMoves[MoveType][jj]--;
        }
        else
        {
            Board[HistPosX[1][cc]][HistPosY[1][cc]]=(HistType[1][cc]+1)*(2*MoveType-1);
            PieceType[1-MoveType][jj]=HistType[1][cc];
            PiecePosX[1-MoveType][jj]=HistPosX[1][cc];
            PiecePosY[1-MoveType][jj]=HistPosY[1][cc];
            PieceMoves[1-MoveType][jj]--;
        }
    }
    if (iis_check==0) return(true);
    return(false);
}

function IsCheck(xx, yy, tt)
{
    var ii0=xx, jj0=yy, ddi, ddj, bb;
    for (ddi=-2; ddi<=2; ddi+=4)
    {
        for (ddj=-1; ddj<=1; ddj+=2)
        {
            if (IsOnBoard(ii0+ddi, jj0+ddj))
            {
                if (Board[ii0+ddi][jj0+ddj]==10*tt-5) return(1);
            }
        }
    }
    for (ddi=-1; ddi<=1; ddi+=2)
    {
        for (ddj=-2; ddj<=2; ddj+=4)
        {
            if (IsOnBoard(ii0+ddi, jj0+ddj))
            {
                if (Board[ii0+ddi][jj0+ddj]==10*tt-5) return(1);
            }
        }
    }
    for (ddi=-1; ddi<=1; ddi+=2)
    {
        ddj=1-2*tt;
        {
            if (IsOnBoard(ii0+ddi, jj0+ddj))
            {
                if (Board[ii0+ddi][jj0+ddj]==12*tt-6) return(1);
            }
        }
    }
    if ((Math.abs(PiecePosX[1-tt][0]-xx)<2)&&(Math.abs(PiecePosY[1-tt][0]-yy)<2))
        return(1);
    for (ddi=-1; ddi<=1; ddi+=1)
    {
        for (ddj=-1; ddj<=1; ddj+=1)
        {
            if ((ddi!=0)||(ddj!=0))
            {
                ii0=xx+ddi;
                jj0=yy+ddj;
                bb=0;
                while ((IsOnBoard(ii0, jj0))&&(bb==0))
                {
                    bb=Board[ii0][jj0];
                    if (bb==0)
                    {
                        ii0+=ddi;
                        jj0+=ddj;
                    }
                    else
                    {
                        if (bb==4*tt-2) return(1);
                        if ((bb==6*tt-3)&&((ddi==0)||(ddj==0))) return(1);
                        if ((bb==8*tt-4)&&(ddi!=0)&&(ddj!=0)) return(1);
                    }
                }
            }
        }
    }
    return(0);
}

function IsOnBoard(ii, jj)
{
    if (ii<0) return(false);
    if (ii>7) return(false);
    if (jj<0) return(false);
    if (jj>7) return(false);
    return(true);
}

function GetMove(tt,nn)
{
    var ii=0, jj=0, mm="", ll=-1, cc, ss=tt;
    while (ss.indexOf("<br />")>0) ss=ss.replace("<br />","");
    var kk=ss.length;
    while (ii<kk)
    {
        cc=ss.charCodeAt(ii);
        if ((cc<=32))//||(cc==46)) //||(cc>=127))
        {
            if (ll+1!=ii) jj++;
            ll=ii;
        }
        else
        {
            if (jj==nn)
            {
                if ((cc==46)&&(!isNaN(mm))) {
                    mm=""; ll=ii; }
                else mm+=ss.charAt(ii);
            }
        }
        ii++;
    }
    if ((nn==1)&&(mm=="")&&(ss.charAt(0)=="."))
    {
        ii=0;
        while (ii<kk)
        {
            cc=ss.charAt(ii);
            if ((cc!=".")&&(cc!=" ")) mm+=cc;
            ii++;
        }
    }
    if (mm!="")
    {
        ii=mm.indexOf("<");
        jj=mm.indexOf(">");
        while ((ii>=0)&&(jj>=0)&&(ii<jj))
        {
            mm=mm.substr(0,ii)+mm.substr(jj+1);
            ii=mm.indexOf("<");
            jj=mm.indexOf(">");
        }
    }
    return(mm);
}

function SkipRefreshBoard(nn)
{
    SkipRefresh=nn;
}

function RefreshBoard(rr)
{
    if (SkipRefresh>0) return;
    InitImages();
    if (rr) DocImg.length=0;
    var ii, jj, kk, kk0, ll, mm=1;
    for (ii=0; ii<8; ii++)
    {
        for (jj=0; jj<8; jj++)
        {
            if (Board[ii][jj]==0)
            {
                var sq = ii+(7-jj)*8;
                if (isRotated) {
                    sq = 63 - sq;
                }
                var dk = (ii + jj) % 2;
                SetImg(sq,dk ? BoardPicLight : BoardPicDark);
            }
        }
    }
    for (ii=0; ii<2; ii++)
    {
        for (jj=0; jj<16; jj++)
        {
            if (PieceType[ii][jj]>=0)
            {
                kk=PiecePosX[ii][jj]+8*(7-PiecePosY[ii][jj]);
                var dk = (PiecePosX[ii][jj] + PiecePosY[ii][jj]) % 2;
                if (isRotated) {
                    kk = 63 - kk;
                }
                if (ii) {
                    if (dk) {
                        SetImg(kk,PiecePicBlackOnLight[PieceType[ii][jj]]);
                    } else {
                        SetImg(kk,PiecePicBlackOnDark[PieceType[ii][jj]]);
                    }
                } else {
                    if (dk) {
                        SetImg(kk,PiecePicWhiteOnLight[PieceType[ii][jj]]);
                    } else {
                        SetImg(kk,PiecePicWhiteOnDark[PieceType[ii][jj]]);
                    }
                }
            }
        }
    }
}

function SwitchAutoPlay()
{
    if (isAutoPlay) SetAutoPlay(false);
    else SetAutoPlay(true);
}

function SetAutoPlay(bb)
{
    isAutoPlay=bb;
    if (AutoPlayInterval) clearTimeout(AutoPlayInterval);
    if (isAutoPlay)
    {
        if ((document.BoardForm)&&(document.BoardForm.AutoPlay))
            document.BoardForm.AutoPlay.value="stop";
        MoveForward(1);
    }
    else
    {
        if ((document.BoardForm)&&(document.BoardForm.AutoPlay))
            document.BoardForm.AutoPlay.value="play";
    }
}

function SetDelay(vv)
{
    Delay=vv;
}

function RotateBoard(bb)
{
    var ii, cc=new Array();
    isRotated=bb;
    if ((document.BoardForm)&&(document.BoardForm.Rotated))
        document.BoardForm.Rotated.checked=bb;
    RefreshBoard();
}

function SetPgnMoveText(ss, vvariant, rroot, sstart)
{
    if ((document.BoardForm)&&(document.BoardForm.PgnMoveText))
        document.BoardForm.PgnMoveText.value=ss;
    if (vvariant)
    {
        ShortPgnMoveText[0][vvariant]=ss;
        ShortPgnMoveText[1][vvariant]=rroot;
        ShortPgnMoveText[2][vvariant]=sstart;
    }
    else ShortPgnMoveText[0][0]=ss;
}

function TransformSAN(ss)
{
    if (ss=="") return("");
    if ((ShowPieceName=="")||(ShowPieceName==PieceName)) return(ss);
    var jj, rr, tt="";
    for (jj=0; jj<ss.length; jj++)
    {
        rr=PieceName.indexOf(ss.charAt(jj));
        if (rr>=0) tt+=ShowPieceName.charAt(rr);
        else tt+=ss.charAt(jj);
    }
    return(tt);
}

function SetMove(mmove, vvariant)
{
    if (isNaN(mmove)) return;
    var ii=isCalculating;
    isCalculating=true;
    if (RecordCount>0) MoveBack(MaxMove);
    if (vvariant)
    {
        if (vvariant>=ShortPgnMoveText[0].length) {
            isCalculating=ii; return; }
        if (CurVar!=vvariant)
        {
            SetMove(ShortPgnMoveText[2][vvariant], ShortPgnMoveText[1][vvariant]);
            CurVar=vvariant;
        }
    }
    else
    {
        while (CurVar!=0)
        {
            if (MoveCount==ShortPgnMoveText[2][CurVar])
            {
                CurVar=ShortPgnMoveText[1][CurVar];
                if ((!isCalculating)&&(document.BoardForm)&&(document.BoardForm.PgnMoveText))
                    document.BoardForm.PgnMoveText.value=ShortPgnMoveText[0][CurVar];
            }
            else MoveBack(1);
        }
    }
    isCalculating=ii;
    var dd=mmove-MoveCount;
    if (dd<=0) MoveBack(-dd);
    else MoveForward(dd, 1);
    if (isCalculating) return;
    if ((document.BoardForm)&&(document.BoardForm.PgnMoveText))
        document.BoardForm.PgnMoveText.value=ShortPgnMoveText[0][CurVar];
    if (AutoPlayInterval) clearTimeout(AutoPlayInterval);
    if (isAutoPlay) AutoPlayInterval=setTimeout("MoveForward(1)", Delay);
}

function ApplyPgnMoveText(ss, rroot)
{
    var vv=0;
    if (! isNaN(rroot))
    {
        vv=ShortPgnMoveText[0].length;
        ShortPgnMoveText[0][vv]="";
    }
    else
    {
        ShortPgnMoveText[0].length=1;
        TargetDocument=window.document;
        if (rroot) activeAnchorBG=rroot;
        startAnchor=-1;
    }
    var ii, uu="", uuu="", cc, bb=0, bbb=0, ll=ss.length;
    for (ii=0; ii<ll; ii++)
    {
        cc=ss.substr(ii,1);
        if (cc=="{") bbb++;
        if (cc=="}") bbb--;
        if (((cc==")")||(cc=="]"))&&(bbb==0))
        {
            bb--;
            if (bb==0)
            {
                if (bbb==0) uu+=ApplyPgnMoveText(uuu, vv);
                else uu+=uuu;
                uuu="";
            }
        }
        if (bb==0) uu+=cc;
        else uuu+=cc;
        if (((cc=="(")||(cc=="["))&&(bbb==0)) bb++;
    }
    if (! isNaN(rroot))
    {
        ii=0, jj=0, bb=0;
        while ((ii<uu.length-1)&&(((ii>0)&&(uu.charAt(ii-1)!=" "))||(isNaN(parseInt(uu.charAt(ii)))))) ii++;
        while ((ii<uu.length-1)&&(! isNaN(parseInt(uu.charAt(ii))))) {
            bb=10*bb+parseInt(uu.charAt(ii)); ii++; }
        if (ii<uu.length-1)
        {
            uuu=uu.substr(ii, 3);
            switch (uuu)
            {
            case "...": jj=1; break;
            case " ..": jj=1; break;
            }
            if (jj==0)
            {
                uuu=uu.substr(ii, 4);
                switch (uuu)
                {
                case "....": jj=1; break;
                case ". ..": jj=1; break;
                case " ...": jj=1; break;
                }
            }
            if (jj==0)
            {
                uuu=uu.substr(ii, 5);
                if (uuu==". ...") jj=1;
            }
        }
        bb=2*(bb-1)+jj;
        //if (bb<0) bb=MoveCount;
        SetPgnMoveText(uu, vv, rroot, bb);
    }
    else SetPgnMoveText(uu);
    return(vv);
}

function GetHTMLMoveText(vvariant, nnoscript, ccommenttype)
{
    var vv=0, tt, ii, uu="", uuu="", cc, bb=0, bbb=0;
    var ss="", sstart=0, nn=MaxMove, ffst=0,llst,ssearch,ssub,ffull,mmove0="",mmove1="", gg="";
    if (startAnchor!=-1) gg=",'"+startAnchor+"'";
    isCalculating=true;
    if (vvariant)
    {
        vv=vvariant;
        if (! isNaN(ShortPgnMoveText[0][vv]))
        {
            SetMove(ShortPgnMoveText[0][vv], ShortPgnMoveText[1][vv]);
            if (MoveCount!=ShortPgnMoveText[0][vv]) return("("+ShortPgnMoveText[0][vv]+")");
            CurVar=ShortPgnMoveText[1][vv];
        }
        if (ShortPgnMoveText[2][vv]<0) return(ShortPgnMoveText[0][vv]);
        SetMove(ShortPgnMoveText[2][vv], ShortPgnMoveText[1][vv]);
        if (MoveCount!=ShortPgnMoveText[2][vv]) return(ShortPgnMoveText[0][vv]);
        CurVar=vvariant;
    }
    else MoveBack(MaxMove);
    tt=ShortPgnMoveText[0][vv];

    ffull=Uncomment(ShortPgnMoveText[0][CurVar]);
    for (ii=0; (ii<nn)&&(ffst>=0)&&(MoveCount<MaxMove); ii++)
    {
        ssearch=Math.floor(MoveCount/2+2)+".";
        llst=ffull.indexOf(ssearch);
        ssearch=Math.floor(MoveCount/2+1)+".";
        ffst=ffull.indexOf(ssearch);
        mmove1="";
        if (ffst>=0)
        {
            ffst+=ssearch.length;
            if (llst<0)
                ssub=ffull.substring(ffst);
            else
                ssub=ffull.substring(ffst, llst);
            mmove0=GetMove(ssub,MoveType);
            if (mmove0!="")
            {
                if (ParseMove(mmove0, true)>0)
                {
                    mmove1=mmove0;
                    if (MoveType==0)
                        HistMove[MoveCount-StartMove]=Math.floor((MoveCount+2)/2)+"."+mmove1;
                    else
                        HistMove[MoveCount-StartMove]=Math.floor((MoveCount+2)/2)+". ... "+mmove1;
                    MoveCount++;
                    MoveType=1-MoveType;
                }
                else
                {
                    if (MoveType==1)
                    {
                        ssub=Math.floor(MoveCount/2+1);
                        ssearch=ssub+"....";
                        ffst=ffull.indexOf(ssearch);
                        if (ffst<0) {
                            ssearch=ssub+". ..."; ffst=ffull.indexOf(ssearch); }
                        if (ffst<0) {
                            ssearch=ssub+". .."; ffst=ffull.indexOf(ssearch); }
                        if (ffst<0) {
                            ssearch=ssub+" ..."; ffst=ffull.indexOf(ssearch); }
                        if (ffst<0) {
                            ssearch=ssub+"..."; ffst=ffull.indexOf(ssearch); }
                        if (ffst<0)
                        {
                            ssearch=ssub+" ..";
                            ffst=ffull.indexOf(ssearch);
                        }
                        if (ffst>=0)
                        {
                            ffst+=ssearch.length;
                            if (llst<0) ssub=ffull.substring(ffst);
                            else ssub=ffull.substring(ffst, llst);
                            mmove0=GetMove(ssub,0);
                            if (mmove0!="")
                            {
                                if (ParseMove(mmove0, true)>0)
                                {
                                    mmove1=mmove0;
                                    HistMove[MoveCount-StartMove]=Math.floor((MoveCount+2)/2)+". ... "+mmove1;
                                    MoveCount++;
                                    MoveType=1-MoveType;
                                }
                                else
                                {
                                    ffst=-1;
                                    //alert(mmove0+" is not a valid move.");
                                }
                            }
                        }
                    }
                    else
                    {
                        ffst=-1;
                        //alert(mmove0+" is not a valid move.");
                    }
                }
            }
            else ffst=-1;
        }
        if (mmove1!="")
        {
            sstart=-1;
            do sstart=tt.indexOf(mmove1, sstart+1);
            while ((sstart>0)&&(IsInComment(tt, sstart)));
            if (sstart>=0)
            {
                ss+=tt.substr(0,sstart);
                if (! nnoscript) ss+="<a href=\"javascript:SetMove{{"+MoveCount+","+vv+gg+"}}\" name=\"m"+MoveCount+"v"+vv+"\">";
                if (vv==0) ss+="<b>";
                ss+=TransformSAN(mmove1);
                if (vv==0) ss+="</b>";
                if (! nnoscript) ss+="</a>";
                tt=tt.substr(sstart+mmove1.length);
            }
            else ffst=-1;
        }
    }
    ss+=tt;

    var ll=ss.length;
    for (ii=0; ii<ll; ii++)
    {
        cc=ss.substr(ii,1);
        if (cc=="{") bbb++;
        if (cc=="}") bbb--;
        if (((cc==")")||(cc=="]"))&&(bbb==0))
        {
            bb--;
            if (bb==0)
            {
                if (bbb==0)
                {
                    if (! isNaN(ShortPgnMoveText[0][uuu]))
                    {
                        cc=uu.length-1;
                        uu=uu.substr(0,cc);
                        cc="";
                    }
                    uu+=GetHTMLMoveText(uuu, nnoscript);
                    isCalculating=true;
                }
                else uu+=uuu;
                uuu="";
            }
        }
        if (bb==0) uu+=cc;
        else uuu+=cc;
        if (((cc=="(")||(cc=="["))&&(bbb==0)) bb++;
    }

    if (! vvariant)
    {
        SetMove(0,0);
        tt=uu.split("{{");
        ll=tt.length;
        uu=tt[0];
        for (ii=1; ii<ll; ii++) uu+="("+tt[ii];
        tt=uu.split("}}");
        ll=tt.length;
        uu=tt[0];
        for (ii=1; ii<ll; ii++) uu+=")"+tt[ii];
        if ((ccommenttype==1)||(ccommenttype==true))
        {
            tt=uu.split("{");
            ll=tt.length;
            uu=tt[0];
            for (ii=1; ii<ll; ii++) uu+="<i>"+tt[ii];
            tt=uu.split("}");
            ll=tt.length;
            uu=tt[0];
            for (ii=1; ii<ll; ii++) uu+="</i>"+tt[ii];
        }
        if (ccommenttype>=1)
        {
            tt=uu.split("{");
            ll=tt.length;
            uu=tt[0];
            for (ii=1; ii<ll; ii++) uu+="<a href=\"javascript:SetMove()\"><span title=\""+tt[ii];
            tt=uu.split("}");
            ll=tt.length;
            uu=tt[0];
            for (ii=1; ii<ll; ii++) uu+="\" onMouseDown=\"if (this.innerHTML==\'{\'+this.title+\'}\') this.innerHTML=\'<I>{...}</I>\'; else this.innerHTML=\'{\'+this.title+\'}\';\"><I>{...}</I></span></a>"+tt[ii];
        }
    }
    isCalculating=false;
    return(uu);
}

function IsInComment(ss, nn)
{
    var ii=-1, bb=0;
    do {
        ii=ss.indexOf("{",ii+1); bb++; }
    while ((ii>=0)&&(ii<nn));
    ii=-1;
    do {
        ii=ss.indexOf("}",ii+1); bb--; }
    while ((ii>=0)&&(ii<nn));
    return(bb);
}

function HighlightMove(nn)
{
    var ii, cc, bb, jj=0, ll=TargetDocument.anchors.length;
    if (ll==0) return;
    if (! TargetDocument.anchors[0].style) return;
    if ((activeAnchor>=0)&&(ll>activeAnchor))
    {
        TargetDocument.anchors[activeAnchor].style.backgroundColor="";
        activeAnchor=-1;
    }
    if (isNaN(startAnchor))
    {
        while ((jj<ll)&&(TargetDocument.anchors[jj].name!=startAnchor)) jj++;
    }
    for (ii=jj; ((ii<ll)&&(activeAnchor<0)); ii++)
    {
        if (TargetDocument.anchors[ii].name==nn)
        {
            activeAnchor=ii;
            TargetDocument.anchors[activeAnchor].style.backgroundColor=activeAnchorBG;
            // if ((document!=TargetDocument)&&(parent.document!=TargetDocument)&&(TargetDocument.anchors[activeAnchor].scrollIntoView))
            //    TargetDocument.anchors[activeAnchor].scrollIntoView(false);
            if (autoScrollNotation) {
                TargetDocument.anchors[activeAnchor].scrollIntoView(true);
            }
            return;
        }
    }
}

function AnimateBoard(nn)
{
    var pp=0, mm=parseInt(Delay)/100;
    isAnimating=true;
    if (dragPiece[4]>=0) mm*=0.75;
    mm=Math.floor(mm);
    if (mm>10) mm=10;
    if (nn>mm) pp=4;
    if (nn%mm==1)
    {
        if (isRotated) dragImg[pp%3]=document.images[63-dragPiece[pp+2]-(7-dragPiece[pp+3])*8+ImageOffset];
        else dragImg[pp%3]=document.images[dragPiece[pp+2]+(7-dragPiece[pp+3])*8+ImageOffset];
        dragPiece[pp+2]=dragImg[pp%3].offsetLeft;
        dragPiece[pp+3]=dragImg[pp%3].offsetTop;
        if (isRotated) dragImg[pp%3]=document.images[63-dragPiece[pp+0]-(7-dragPiece[pp+1])*8+ImageOffset];
        else dragImg[pp%3]=document.images[dragPiece[pp+0]+(7-dragPiece[pp+1])*8+ImageOffset];
        dragPiece[pp+0]=dragImg[pp%3].offsetLeft;
        dragPiece[pp+1]=dragImg[pp%3].offsetTop;
    }
    if (nn%mm!=0)
    {
        if (nn%mm==1)
        {
            dragImg[pp%3].style.zIndex=200+pp;
            dragImgBorder=parseInt(dragImg[pp%3].style.borderWidth);
            if (dragImgBorder) dragImg[pp%3].style.borderWidth="0px";
            else dragImgBorder=0;
        }
        dragImg[pp%3].style.left=(Math.round((nn%mm)*(dragPiece[pp+2]-dragPiece[pp+0])/(mm-1))+dragImgBorder)+"px";
        dragImg[pp%3].style.top=(Math.round((nn%mm)*(dragPiece[pp+3]-dragPiece[pp+1])/(mm-1))+dragImgBorder)+"px";
        if ((dragPiece[4]>=0)&&(mm-1==nn)) setTimeout("AnimateBoard("+(mm+1)+")",50);
        else setTimeout("AnimateBoard("+(nn+1)+")",50);
        return;
    }
    RefreshBoard();
    for (mm=0; mm<=pp; mm+=4)
    {
        dragImg[mm%3].style.left = 0;
        dragImg[mm%3].style.top  = 0;
        dragImg[mm%3].style.zIndex=1;
        if (dragImgBorder) dragImg[mm%3].style.borderWidth=dragImgBorder+"px";
        dragImg[mm%3]=null;
        dragPiece[mm+0]=-1;
    }
    isAnimating=false;
}

function SetDragDrop(bb)
{
    if ((document.BoardForm)&&(document.BoardForm.DragDrop))
        document.BoardForm.DragDrop.checked=bb;
    isDragDrop=bb;
}

function KeyDown(e)
{
    var kk=0;
    if (e) kk=e.which;
    else if (window.event) kk=event.keyCode;
    if ((kk==37)||(kk==52)||(kk==65460)) MoveBack(1);
    if ((kk==39)||(kk==54)||(kk==65462)) MoveForward(1);
}

