Ported verbose deserialization.
[tagua/yd.git] / src / hlvariant / tagua_wrapped.h
blob835e4149d4b4e3d74c2fd2e0c386a9c0a7522486
1 #ifndef HLVARIANT__TAGUA_WRAPPED_H
2 #define HLVARIANT__TAGUA_WRAPPED_H
4 #include "tagua.h"
5 #include "fwd.h"
6 #include "movefactory.h"
7 #include "nopool.h"
8 #include "variantdata.h"
10 #ifdef Q_CC_GNU
11 #define __FUNC__ __PRETTY_FUNCTION__
12 #else
13 #define __FUNC__ __FUNCTION__
14 #endif
16 #define MISMATCH(x,y) (std::cout << " --> Error in "<<__FUNC__<<", MISMATCH!" << std::endl \
17 << " got type " << prettyTypeName(typeid(x).name()) << std::endl \
18 << " instead of " << prettyTypeName(typeid(y).name()) << std::endl \
19 << " this is " << prettyTypeName(typeid(*this).name()) << std::endl)
21 namespace HLVariant {
23 template <typename Variant> class WrappedPosition;
25 template <typename Variant>
26 class WrappedPiece : public AbstractPiece {
27 typedef typename VariantData<Variant>::Piece Piece;
29 Piece m_piece;
30 public:
31 const Piece& inner() const { return m_piece; }
33 WrappedPiece(const Piece& piece)
34 : m_piece(piece) { }
36 virtual bool equals(const PiecePtr& _other) const {
37 if (!_other) return false;
38 WrappedPiece<Variant>* other = dynamic_cast<WrappedPiece<Variant>*>(_other.get());
40 if (other)
41 return m_piece == other->inner();
42 else {
43 MISMATCH(*_other.get(),WrappedPiece<Variant>);
44 return false;
48 virtual QString name() const {
49 return m_piece.name();
52 virtual PiecePtr clone() const {
53 return PiecePtr(new WrappedPiece<Variant>(m_piece));
57 template <typename Variant>
58 class WrappedPool : public AbstractPool {
59 typedef typename VariantData<Variant>::Pool Pool;
60 typedef typename VariantData<Variant>::Piece Piece;
62 Pool& m_pool;
63 public:
64 WrappedPool(Pool& pool)
65 : m_pool(pool) { }
67 WrappedPool(const Pool& pool)
68 : m_pool(const_cast<Pool&>(pool)) {
69 // FIXME: const_cast is not necessary, here, but to avoid it
70 // we would need to change the API, adding for example an
71 // AbstractConstPool with only const functions and changing the
72 // wrapper accordingly.
75 virtual int size() {
76 return m_pool.size();
79 virtual int insert(int pref_index, const PiecePtr& _piece) {
80 if (!_piece) {
81 return m_pool.insert(pref_index, Piece());
83 else {
84 WrappedPiece<Variant>* piece = dynamic_cast<WrappedPiece<Variant>*>(_piece.get());
86 if (piece)
87 return m_pool.insert(pref_index, Piece(piece->inner()) );
88 else {
89 MISMATCH(*_piece.get(), WrappedPiece<Variant>);
90 return -1;
95 virtual PiecePtr get(int index) {
96 Piece piece = m_pool.get(index);
97 if (piece != Piece())
98 return PiecePtr(new WrappedPiece<Variant>(piece));
99 else
100 return PiecePtr();
103 virtual PiecePtr take(int index) {
104 Piece piece = m_pool.take(index);
105 if (piece != Piece())
106 return PiecePtr(new WrappedPiece<Variant>(piece));
107 else
108 return PiecePtr();
112 template <typename Variant>
113 class WrappedMove : public AbstractMove {
114 typedef typename VariantData<Variant>::LegalityCheck LegalityCheck;
115 typedef typename VariantData<Variant>::Serializer Serializer;
116 typedef typename VariantData<Variant>::Move Move;
117 typedef typename VariantData<Variant>::GameState GameState;
119 Move m_move;
120 public:
121 const Move& inner() const { return m_move; }
122 Move& inner() { return m_move; }
124 WrappedMove(const Move& move)
125 : m_move(move) { }
127 virtual QString SAN(const PositionPtr& _ref) const {
128 WrappedPosition<Variant>* ref = dynamic_cast<WrappedPosition<Variant>*>(_ref.get());
130 if (ref) {
131 Serializer serializer(Serializer::COMPACT);
132 return serializer.serialize(m_move, ref->inner());
134 else {
135 MISMATCH(*_ref.get(), WrappedPosition<Variant>);
136 return "$@%";
140 virtual DecoratedMove toDecoratedMove(const PositionPtr& _ref) const {
141 WrappedPosition<Variant>* ref = dynamic_cast<WrappedPosition<Variant>*>(_ref.get());
143 if (ref) {
144 Serializer serializer(Serializer::DECORATED);
145 return DecoratedMove(serializer.serialize(m_move, ref->inner()));
147 else {
148 MISMATCH(*_ref.get(), WrappedPosition<Variant>);
149 return DecoratedMove("$@%");
153 virtual QString toString(const PositionPtr& _ref) const {
154 WrappedPosition<Variant>* ref = dynamic_cast<WrappedPosition<Variant>*>(_ref.get());
156 if (ref) {
157 Serializer serializer(Serializer::SIMPLE);
158 return serializer.serialize(m_move, ref->inner());
160 else {
161 MISMATCH(*_ref.get(), WrappedPosition<Variant>);
162 return "$@%";
166 virtual NormalUserMove toUserMove() const {
167 typename VariantData<Variant>::MoveFactory factory;
168 return factory.toNormal(m_move);
171 virtual bool equals(const MovePtr& _other) const {
172 WrappedMove<Variant>* other = dynamic_cast<WrappedMove<Variant>*>(_other.get());
174 if (other)
175 return m_move == other->inner();
176 else {
177 MISMATCH(*_other.get(), WrappedMove<Variant>);
178 return false;
184 * Metafunction that returns a null pointer when
185 * its template argument is NoPool.
187 template <typename Variant, typename Pool>
188 struct ReturnPoolAux {
189 static PoolPtr apply(typename VariantData<Variant>::GameState& state, int player) {
190 return PoolPtr(new WrappedPool<Variant>(state.pools().pool(
191 static_cast<typename VariantData<Variant>::Piece::Color>(player))));
195 template <typename Variant>
196 struct ReturnPoolAux<Variant, NoPool> {
197 static PoolPtr apply(typename VariantData<Variant>::GameState&, int) {
198 return PoolPtr();
202 template <typename Variant>
203 struct ReturnPool {
204 static PoolPtr apply(typename VariantData<Variant>::GameState& state, int player) {
205 return ReturnPoolAux<Variant, typename VariantData<Variant>::Pool>::apply(state, player);
209 template <typename Variant>
210 class WrappedPosition : public AbstractPosition {
211 typedef typename VariantData<Variant>::LegalityCheck LegalityCheck;
212 typedef typename VariantData<Variant>::GameState GameState;
213 typedef typename VariantData<Variant>::Board Board;
214 typedef typename VariantData<Variant>::Piece Piece;
215 typedef typename VariantData<Variant>::Move Move;
216 typedef typename VariantData<Variant>::Serializer Serializer;
218 GameState m_state;
219 public:
220 const GameState& inner() const { return m_state; }
221 GameState& inner() { return m_state; }
223 WrappedPosition(const GameState& state)
224 : m_state(state) { }
226 virtual Point size() const {
227 return m_state.board().size();
230 virtual QStringList borderCoords() const {
231 return m_state.board().borderCoords();
234 virtual void setup() {
235 m_state.setup();
238 virtual PiecePtr get(const Point& p) const {
239 Piece piece = m_state.board().get(p);
240 if (piece != Piece())
241 return PiecePtr(new WrappedPiece<Variant>(piece));
242 else
243 return PiecePtr();
246 virtual void set(const Point& p, const PiecePtr& _piece) {
247 if (!_piece) {
248 m_state.board().set(p, Piece());
250 else {
251 WrappedPiece<Variant>* piece = dynamic_cast<WrappedPiece<Variant>*>(_piece.get());
253 if (piece)
254 m_state.board().set(p, piece->inner());
255 else
256 MISMATCH(*_piece.get(), WrappedPiece<Variant>);
260 virtual PoolPtr pool(int player) {
261 return ReturnPool<Variant>::apply(m_state, player);
264 virtual void copyPoolFrom(const PositionPtr&) {
265 // BROKEN
268 virtual InteractionType movable(const TurnTest& test, const Point& p) const {
269 LegalityCheck check(m_state);
270 return check.movable(test, p);
273 virtual InteractionType droppable(const TurnTest& test, int index) const {
274 LegalityCheck check(m_state);
275 return check.droppable(test, index);
278 virtual int turn() const {
279 return static_cast<int>(m_state.turn());
282 virtual void setTurn(int turn) {
283 m_state.setTurn(static_cast<typename Piece::Color>(turn));
286 virtual int previousTurn() const {
287 return static_cast<int>(m_state.previousTurn());
290 virtual void switchTurn() {
291 m_state.switchTurn();
294 virtual bool testMove(const MovePtr& _move) const {
295 if (!_move)
296 return false;
298 WrappedMove<Variant>* move = dynamic_cast<WrappedMove<Variant>*>(_move.get());
300 if (move) {
301 LegalityCheck check(m_state);
302 return check.legal(move->inner());
304 else {
305 MISMATCH(*_move.get(), WrappedMove<Variant>);
306 return false;
310 virtual void move(const MovePtr& _move) {
311 if (!_move)
312 return;
314 WrappedMove<Variant>* move = dynamic_cast<WrappedMove<Variant>*>(_move.get());
316 if (move)
317 m_state.move(move->inner());
318 else
319 MISMATCH(*_move.get(), WrappedMove<Variant>);
322 virtual PositionPtr clone() const {
323 return PositionPtr(new WrappedPosition<Variant>(m_state));
326 virtual void copyFrom(const PositionPtr& _p) {
327 // TODO: check if this is used somewhere
328 WrappedPosition<Variant>* p = dynamic_cast<WrappedPosition<Variant>*>(_p.get());
330 if (p)
331 m_state = p->inner();
332 else
333 MISMATCH(*_p.get(), WrappedPosition);
336 virtual bool equals(const PositionPtr& _other) const {
337 WrappedPosition<Variant>* other = dynamic_cast<WrappedPosition<Variant>*>(_other.get());
339 if (other)
340 return m_state == other->inner();
341 else {
342 MISMATCH(*_other.get(), WrappedPosition<Variant>);
343 return false;
347 virtual MovePtr getMove(const QString& san) const {
348 Serializer serializer(Serializer::COMPACT);
349 Move res = serializer.deserialize(san, m_state);
350 if (res.valid()) {
351 return MovePtr(new WrappedMove<Variant>(res));
353 else
354 return MovePtr();
357 virtual QString state() const {
358 return ""; // BROKEN
361 virtual QString fen(int, int) const {
362 return ""; // BROKEN
365 virtual PiecePtr moveHint(const MovePtr&) const {
366 return PiecePtr(); // BROKEN
369 virtual QString variant() const {
370 return Variant::m_name;
373 virtual void dump() const {
374 // BROKEN
380 #include "graphicalapi_unwrapped.h"
381 #include "icsapi_wrapped.h"
383 namespace HLVariant {
385 template <typename Variant>
386 class WrappedAnimator : public AbstractAnimator {
387 typedef typename VariantData<Variant>::GameState GameState;
388 typedef typename VariantData<Variant>::Animator Animator;
389 typedef typename VariantData<Variant>::Move Move;
391 Animator m_animator;
392 public:
393 const Animator& inner() const { return m_animator; }
395 WrappedAnimator(const Animator& animator)
396 : m_animator(animator) { }
398 virtual AnimationPtr warp(const PositionPtr& _pos) {
399 WrappedPosition<Variant>* pos = dynamic_cast<WrappedPosition<Variant>*>(_pos.get());
400 if (pos)
401 return m_animator.warp(pos->inner());
402 else {
403 MISMATCH(*_pos.get(), WrappedPosition<Variant>);
404 return AnimationPtr();
408 virtual AnimationPtr forward(const PositionPtr& _pos, const MovePtr& _move) {
409 WrappedPosition<Variant>* pos = dynamic_cast<WrappedPosition<Variant>*>(_pos.get());
410 WrappedMove<Variant>* move = dynamic_cast<WrappedMove<Variant>*>(_move.get());
412 if (move && pos)
413 return m_animator.forward(pos->inner(), move->inner());
414 else {
415 if (!move)
416 MISMATCH(*_move.get(), WrappedMove<Variant>);
417 if (!pos)
418 MISMATCH(*_pos.get(), WrappedPosition<Variant>);
419 return AnimationPtr();
423 virtual AnimationPtr back(const PositionPtr& _pos, const MovePtr& _move) {
424 WrappedPosition<Variant>* pos = dynamic_cast<WrappedPosition<Variant>*>(_pos.get());
425 WrappedMove<Variant>* move = dynamic_cast<WrappedMove<Variant>*>(_move.get());
427 if (move && pos)
428 return m_animator.back(pos->inner(), move->inner());
429 else {
430 if (!move)
431 MISMATCH(*_move.get(), WrappedMove<Variant>);
432 if (!pos)
433 MISMATCH(*_pos.get(), WrappedPosition<Variant>);
434 return AnimationPtr();
441 template <typename Variant>
442 class WrappedVariantInfo : public VariantInfo {
443 typedef typename VariantData<Variant>::Animator Animator;
444 typedef typename VariantData<Variant>::GameState GameState;
445 typedef typename VariantData<Variant>::Piece Piece;
446 typedef typename VariantData<Variant>::Move Move;
447 // typedef typename VariantData<Variant>::Pool Pool;
448 public:
449 virtual PositionPtr createPosition() {
450 return PositionPtr(
451 new WrappedPosition<Variant>(GameState()));
454 virtual PositionPtr createCustomPosition(const OptList&) {
455 return PositionPtr(
456 new WrappedPosition<Variant>(GameState())); // BROKEN
459 virtual PositionPtr createPositionFromFEN(const QString&) {
460 return PositionPtr(); // BROKEN
463 virtual void forallPieces(class PieceFunction&) {
464 // BROKEN
467 virtual int moveListLayout() const {
468 return Variant::moveListLayout();
471 virtual AnimatorPtr createAnimator(GraphicalAPI* graphical_api) {
472 return AnimatorPtr(new WrappedAnimator<Variant>(
473 Animator(
474 typename UnwrappedGraphicalAPIPtr<Variant>::type(
475 new UnwrappedGraphicalAPI<Variant>(graphical_api)))));
478 virtual MovePtr createNormalMove(const NormalUserMove& move) {
479 typename VariantData<Variant>::MoveFactory factory;
480 Move m = factory.createNormalMove(move);
481 return MovePtr(new WrappedMove<Variant>(m));
484 virtual MovePtr createDropMove(const DropUserMove& move) {
485 typename VariantData<Variant>::MoveFactory factory;
486 Move m = factory.createDropMove(move);
487 return MovePtr(new WrappedMove<Variant>(m));
490 virtual MovePtr getVerboseMove(int, const VerboseNotation&) const {
491 return MovePtr();
494 virtual bool simpleMoves() {
495 return Variant::m_simple_moves;
498 virtual QString name() const {
499 return Variant::m_name;
502 virtual QString themeProxy() const {
503 return Variant::m_theme_proxy;
506 virtual OptList positionOptions() const {
507 return Variant::positionOptions();
510 virtual ICSAPIPtr icsAPI() const {
511 return ICSAPIPtr(ReturnICSAPI<Variant>::apply());
516 #endif // HLVARIANT__TAGUA_WRAPPED_H