a javascript library for managing shogi games
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 

357 lines
8.0 KiB

/**
@license Copyright (c) 2012, Christopher Ramey | http://github.com/cramey/shogi.js/LICENSE"
*/
var Shogi = {
KING : 0,
ROOK : 1,
BISHOP : 2,
GOLD_GENERAL : 3,
SILVER_GENERAL : 4,
KNIGHT : 5,
LANCE : 6,
PAWN : 7,
PROMOTED_ROOK : 9,
PROMOTED_BISHOP : 10,
PROMOTED_SILVER : 12,
PROMOTED_KNIGHT : 13,
PROMOTED_LANCE : 14,
PROMOTED_PAWN : 15,
desc_king : [
'reigning', 'challenging'
],
desc_piece : [
'King', 'Rook', 'Bishop', 'Gold General',
'Silver General', 'Knight', 'Lance', 'Pawn'
],
piecePromoted : function(n)
{
return (n & 8) != 0;
},
pieceCanPromote : function(b, l){
var piece = b[l];
if(piece == -1){ return false; }
var pe = piece & 15;
if(pe < 1 || pe > 7){ return false; }
var player = this.piecePlayer(piece);
if(player == 0 && l > 26){ return false; }
if(player == 1 && l < 54){ return false; }
return true;
},
piecePlayer : function(n)
{
return (n & 16) >> 4;
},
pieceName : function(n)
{
return this.desc_piece[n & 7];
},
pieceMoves : function(b, l)
{
var piece = b[l];
var player = this.piecePlayer(piece);
var moves = [];
switch(piece & 15){
case this.KING:
var i = l + 9;
if(i <= 80 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l - 9;
if(i >= 0 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l + 1;
if(i <= 80 && i % 9 != 0 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l - 1;
if(i >= 0 && i % 9 != 8 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l + 8;
if(i <= 80 && i % 9 != 8 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l + 10;
if(i <= 80 && i % 9 != 0 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l - 10;
if(i >= 0 && i % 9 != 8 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l - 8;
if(i >= 0 && i % 9 != 0 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
break;
case this.GOLD_GENERAL:
case this.PROMOTED_SILVER:
case this.PROMOTED_PAWN:
case this.PROMOTED_LANCE:
case this.PROMOTED_KNIGHT:
var i = l + 9;
if(i <= 80 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l - 9;
if(i >= 0 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l + 1;
if(i <= 80 && i % 9 != 0 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l - 1;
if(i >= 0 && i % 9 != 8 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
if(player){
i = l + 8;
if(i <= 80 && i % 9 != 8 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l + 10;
if(i <= 80 && i % 9 != 0 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
} else {
i = l - 10;
if(i >= 0 && i % 9 != 8 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l - 8;
if(i >= 0 && i % 9 != 0 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
}
break;
case this.KNIGHT:
var i = l + (player ? 19 : -19);
if(i >= 0 && i % 9 != 8 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l + (player ? 17 : -17);
if(i >= 0 && i % 9 != 0 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
break;
case this.LANCE:
if(player){
for(var i = l + 9; i <= 80; i += 9){
if(b[i] == -1){ moves.push(i); }
else if(this.piecePlayer(b[i]) != player){
moves.push(i); break;
} else { break; }
}
} else {
for(var i = l - 9; i >= 0; i -= 9){
if(b[i] == -1){ moves.push(i); }
else if(this.piecePlayer(b[i]) != player){
moves.push(i); break;
} else { break; }
}
}
break;
case this.PROMOTED_ROOK:
var i = l - 10;
if(i >= 0 && i % 9 != 8 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l - 8;
if(i >= 0 && i % 9 != 0 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l + 8;
if(i <= 80 && i % 9 != 8 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l + 10;
if(i <= 80 && i % 9 != 0 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
case this.ROOK:
for(var i = l - 9; i >= 0; i -= 9){
if(b[i] == -1){ moves.push(i); }
else if(this.piecePlayer(b[i]) != player){
moves.push(i); break;
} else { break; }
}
for(var i = l - 1; i % 9 != 8; i--){
if(b[i] == -1){ moves.push(i); }
else if(this.piecePlayer(b[i]) != player){
moves.push(i); break;
} else { break; }
}
for(var i = l + 1; i % 9 != 0; i++){
if(b[i] == -1){ moves.push(i); }
else if(this.piecePlayer(b[i]) != player){
moves.push(i); break;
} else { break; }
}
for(var i = l + 9; i <= 80; i += 9){
if(b[i] == -1){ moves.push(i); }
else if(this.piecePlayer(b[i]) != player){
moves.push(i); break;
} else { break; }
}
break;
case this.PROMOTED_BISHOP:
var i = l + 9;
if(i <= 80 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l - 9;
if(i >= 0 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l + 1;
if(i <= 80 && i % 9 != 0 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l - 1;
if(i >= 0 && i % 9 != 8 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
case this.BISHOP:
for(var i = l - 8; i >= 0 && i % 9 != 0; i -= 8){
if(b[i] == -1){ moves.push(i); }
else if(this.piecePlayer(b[i]) != player){
moves.push(i); break;
} else { break; }
}
for(var i = l - 10; i >= 0 && i % 9 != 8; i -= 10){
if(b[i] == -1){ moves.push(i); }
else if(this.piecePlayer(b[i]) != player){
moves.push(i); break;
} else { break; }
}
for(var i = l + 8; i <= 80 && i % 9 != 8; i += 8){
if(b[i] == -1){ moves.push(i); }
else if(this.piecePlayer(b[i]) != player){
moves.push(i); break;
} else { break; }
}
for(var i = l + 10; i <= 80 && i % 9 != 0; i += 10){
if(b[i] == -1){ moves.push(i); }
else if(this.piecePlayer(b[i]) != player){
moves.push(i); break;
} else { break; }
}
break;
case this.PAWN:
var i = l + (player ? 9 : -9);
if(i >= 0 && i <= 80 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
break;
case this.SILVER_GENERAL:
i = l + (player ? 9 : -9);
if(i >= 0 && i <= 80 && (b[i] == -1 || this.piecePlayer(b[i]))){
moves.push(i);
}
var i = l - 10;
if(i >= 0 && i % 9 != 8 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l - 8;
if(i >= 0 && i % 9 != 0 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l + 8;
if(i <= 80 && i % 9 != 8 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
i = l + 10;
if(i <= 80 && i % 9 != 0 && (b[i] == -1 || this.piecePlayer(b[i]) != player)){
moves.push(i);
}
break;
}
return moves;
},
pieceDescription : function(n)
{
var pl = (n & 16) >> 4;
var pe = n & 7;
return (this.piecePromoted(n) ? 'Promoted ' : '') +
this.pieceName(n) +
(pe == this.KING ? ' (' + this.desc_king[pl] + ')' : '');
},
boardStandard: function()
{
return [
22,21,20,19,16,19,20,21,22,
-1,18,-1,-1,-1,-1,-1,17,-1,
23,23,23,23,23,23,23,23,23,
-1,-1,-1,-1,-1,-1,-1,-1,-1,
-1,-1,-1,-1,-1,-1,-1,-1,-1,
-1,-1,-1,-1,-1,-1,-1,-1,-1,
7, 7, 7, 7, 7, 7, 7, 7, 7,
-1, 1,-1,-1,-1,-1,-1, 2,-1,
6, 5, 4, 3, 0, 3, 4, 5, 6
];
}
};