00001
00002
00003 #ifndef _PIN_H
00004 #define _PIN_H
00005
00006 #include "osl/state/numEffectState.h"
00007 #include "osl/container/pieceMask.h"
00008 #include <boost/static_assert.hpp>
00009 namespace osl
00010 {
00011 namespace effect_util
00012 {
00013
00018 class Pin
00019 {
00020 private:
00021 template <Direction DIR>
00022 static void findDirection(const SimpleState& state, Position target,
00023 Player defense, PieceMask& pins)
00024 {
00025 const Offset diff = Board_Table.getOffset(defense, DIR);
00026 const Piece pin = state.nextPiece(target, diff);
00027 if (! pin.isPiece())
00028 return;
00029 if (pin.owner() != defense)
00030 return;
00031 const Piece attack_piece = state.nextPiece(pin.position(), diff);
00032 if (! attack_piece.isPiece())
00033 return;
00034 if (attack_piece.owner() == defense)
00035 return;
00036 if (Ptype_Table.getMoveMask(attack_piece.ptype())
00037 & DirectionTraits<DirectionTraits<DIR>::longDir>::mask)
00038 pins.set(pin.number());
00039 }
00045 template<Player P>
00046 static void findLance(const NumEffectState& state, Position target,
00047 PieceMask& pins)
00048 {
00049 assert(target==state.getKingPosition<P>());
00050 const Offset diff = DirectionPlayerTraits<U,P>::offset();
00051 Position pos = target+diff;
00052 Piece pin;
00053 while ((pin=state.getPieceAt(pos)) == Piece::EMPTY())
00054 pos += diff;
00055 if (! pin.isOnBoardByOwner<P>() )
00056 return;
00057 NumBitmapEffect effect=state.getEffect(pos);
00058 mask_t mask=(effect.getMask(1)&mask_t::makeDirect(PtypeFuns<LANCE>::indexMask<<8));
00059 if(mask.any()){
00060 pins.set(pin.number());
00061 }
00062 }
00063 public:
00068 static PieceMask makeNaive(const SimpleState& state, Position target,
00069 Player defense);
00070 private:
00071 static bool hasEffectWithOffset(const SimpleState& state,
00072 Piece attack_piece, Piece pin, Offset diff)
00073 {
00074 const Piece attack_piece2 = state.nextPiece(pin.position(), diff);
00075 return attack_piece == attack_piece2;
00076 }
00077 static bool hasEffectWithOffset(const NumEffectState& state,
00078 Piece attack_piece, Piece pin, Offset)
00079 {
00080 return state.hasEffectByPiece(attack_piece, pin.position());
00081 }
00082 static void findOffset(const NumEffectState& state,
00083 Piece attack_piece, Position target,
00084 Player defense, Offset diff, PieceMask& pins)
00085 {
00086 const Piece pin = state.nextPiece(target, diff);
00087 assert(pin.isPiece());
00088 if (pin.owner() != defense)
00089 return;
00090 if (! hasEffectWithOffset(state, attack_piece, pin, diff))
00091 return;
00092 pins.set(pin.number());
00093 }
00094 template <Ptype PTYPE>
00095 static void findPtype(const NumEffectState& state, Position target,
00096 Player attack, Player defense, PieceMask& result)
00097 {
00098 BOOST_STATIC_ASSERT((PTYPE == ROOK) || (PTYPE == BISHOP));
00099 const PtypeO attack_ptypeo = newPtypeO(attack, PTYPE);
00100 for (int i=PtypeTraits<PTYPE>::indexMin;
00101 i < PtypeTraits<PTYPE>::indexLimit; ++i)
00102 {
00103 const Piece attack_piece = state.getPieceOf(i);
00104 if (attack_piece.isOnBoardByOwner(attack))
00105 {
00106 const Position attack_position = attack_piece.position();
00107 const Offset32 diff(attack_position, target);
00108 const EffectContent effect
00109 = Ptype_Table.getEffect(attack_ptypeo, diff);
00110 if (!effect.hasBlockableEffect())
00111 continue;
00112 const Offset offset = effect.offset();
00113 #if 0
00114 if (offset.zero())
00115 continue;
00116 #endif
00117 findOffset(state, attack_piece, target, defense,
00118 offset, result);
00119 }
00120 }
00121 }
00122 public:
00127 static PieceMask makeByPiece(const NumEffectState& state, Position target,
00128 Player defense);
00129
00134 static PieceMask makeByPieceKing(const NumEffectState& state, Position target,
00135 Player defense);
00136
00143 static PieceMask make(const NumEffectState& state, Position target,
00144 Player defense)
00145 {
00146 return makeByPiece(state, target, defense);
00147 }
00151 static PieceMask make(const NumEffectState& state, Player defense)
00152 {
00153 return makeByPiece(state, defense);
00154 }
00155 static PieceMask makeNaive(const SimpleState& state, Player defense)
00156 {
00157 return makeNaive(state, state.getKingPosition(defense), defense);
00158 }
00159 static PieceMask makeByPiece(const NumEffectState& state, Player defense)
00160 {
00161 return makeByPieceKing(state, state.getKingPosition(defense), defense);
00162 }
00166 static int count(const NumEffectState& state, Player defense)
00167 {
00168 const PieceMask pins = make(state, defense);
00169 return pins.countBit();
00170 }
00171 static int count(const NumEffectState& state, Position target,
00172 Player defense)
00173 {
00174 const PieceMask pins = make(state, target, defense);
00175 return pins.countBit();
00176 }
00177 };
00178
00179
00180 }
00181 }
00182
00183 #endif
00184
00185
00186
00187