First working HLVariant.
[tagua.git] / src / hlvariant / animator.impl.h
blob7c8906a59d31731c38e88dfb67b50b292d8bb50c
1 /*
2 Copyright (c) 2007 Paolo Capriotti <p.capriotti@sns.it>
3 (c) 2007 Maurizio Monge <maurizio.monge@kdemail.net>
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 2 of the License, or
8 (at your option) any later version.
9 */
11 #ifndef HLVARIANT__ANIMATOR_IMPL_H
12 #define HLVARIANT__ANIMATOR_IMPL_H
14 #include "animator.h"
15 #include "animationfactory.h"
16 #include "common.h"
17 #include "namedsprite.h"
18 #include "variants/xchess/piecetype.h"
20 namespace HLVariant {
22 template <typename Variant>
23 AnimationGroupPtr BaseAnimator<Variant>::warp(const GameState& final) {
24 const GameState* current = m_cinterface->position();
25 AnimationFactory res(m_cinterface->inner());
27 for (int i = 0; i < current->board().size().x; i++) {
28 for (int j = 0; j < current->board().size().x; j++) {
29 Point p(i, j);
30 Piece c = current->board().get(p);
31 Piece f = final.board().get(p);
33 if (c == Piece() && f != Piece()) {
34 //current->set(i, f);
35 NamedSprite sprite = m_cinterface->setPiece(p, f, false);
36 res.addPreAnimation(Animate::appear(sprite), Animate::Instant);
38 else if (c != Piece() && f == Piece()) {
39 NamedSprite old_sprite = m_cinterface->takeSprite(p);
40 res.addPreAnimation(Animate::disappear(old_sprite), Animate::Instant);
42 else if (c != Piece() && f != Piece() && !(c == f)) {
43 NamedSprite old_sprite = m_cinterface->takeSprite(p);
44 NamedSprite sprite = m_cinterface->setPiece(p, f, false);
45 res.addPreAnimation(Animate::morph(old_sprite, sprite), Animate::Instant);
50 return res;
53 template <typename Variant>
54 AnimationGroupPtr BaseAnimator<Variant>::forward(const GameState& final, const Move&) {
55 return warp(final);
59 template <typename Variant>
60 AnimationGroupPtr BaseAnimator<Variant>::back(const GameState& final, const Move&) {
61 return warp(final);
64 template <typename Variant>
65 AnimationGroupPtr SimpleAnimator<Variant>::warp(const GameState& final) {
66 AnimationFactory res(m_cinterface->inner());
68 res.setGroup(Base::warp(final));
70 return res;
73 template <typename Variant>
74 SchemePtr SimpleAnimator<Variant>::movement(const NamedSprite& sprite, const Point& from, const Point& to) {
75 bool knight = m_cinterface->position()->board().get(from).type() == Piece::KNIGHT;
76 int mtype = knight
77 ? Animate::move::LShaped | Animate::move::Rotating
78 : Animate::move::Straight;
79 return SchemePtr(new Animate::move(sprite, to, mtype));
82 template <typename Variant>
83 AnimationGroupPtr SimpleAnimator<Variant>::forward(const GameState& final, const Move& move) {
84 AnimationFactory res(m_cinterface->inner());
86 NamedSprite piece = m_cinterface->takeSprite(move.from());
87 NamedSprite captured = m_cinterface->takeSprite(move.captureSquare());
88 m_cinterface->setSprite(move.to(), piece);
90 if (piece)
91 res.addPreAnimation(*movement(piece, move.from(), move.to()));
92 else
93 ERROR("Bug!!!");
95 if (captured)
96 res.addPostAnimation(Animate::destroy(captured));
98 if (move.promoteTo() != -1) {
99 Piece promoted = final.board().get(move.to());
101 if (promoted != Piece()) {
102 QPoint real = m_cinterface->converter()->toReal(move.to());
103 NamedSprite old_sprite = m_cinterface->getSprite(move.to());
104 NamedSprite new_sprite = m_cinterface->setPiece(move.to(), promoted, /*false,*/ false);
106 res.addPostAnimation(Animate::morph(old_sprite, new_sprite));
108 else
109 ERROR("Bug!!!");
111 else if (move.kingSideCastling()) {
112 Point rookSquare = move.to() + Point(1,0);
113 Point rookDestination = move.from() + Point(1,0);
115 NamedSprite rook = m_cinterface->takeSprite(rookSquare);
116 m_cinterface->setSprite(rookDestination, rook);
117 res.addPreAnimation(Animate::move(rook, rookDestination));
119 else if (move.queenSideCastling()) {
120 Point rookSquare = move.to() + Point(-2,0);
121 Point rookDestination = move.from() + Point(-1,0);
123 NamedSprite rook = m_cinterface->takeSprite(rookSquare);
124 m_cinterface->setSprite(rookDestination, rook);
125 res.addPreAnimation(Animate::move(rook, rookDestination));
128 return res;
131 template <typename Variant>
132 AnimationGroupPtr SimpleAnimator<Variant>::back(const GameState& final, const Move& move) {
133 AnimationFactory res(m_cinterface->inner());
135 NamedSprite piece = m_cinterface->takeSprite(move.to());
136 NamedSprite captured;
137 Piece captured_piece = final.board().get(move.captureSquare());
138 if (captured_piece != Piece()) {
139 captured = m_cinterface->setPiece(move.to(), captured_piece, false);
140 res.addPreAnimation(Animate::appear(captured));
143 if (!piece) {
144 piece = m_cinterface->createPiece(move.to(), final.board().get(move.from()), false);
145 res.addPreAnimation(Animate::appear(piece));
148 m_cinterface->setSprite(move.from(), piece);
150 if (move.promoteTo() != -1) {
151 Piece pawn_piece = final.board().get(move.from());
152 if (pawn_piece != Piece()) {
153 NamedSprite pawn = m_cinterface->createPiece(move.to(), pawn_piece, false);
154 res.addPreAnimation(Animate::morph(piece, pawn));
156 // replace piece with pawn
157 m_cinterface->setSprite(move.from(), pawn);
158 piece = pawn;
161 else if (move.kingSideCastling()) {
162 Point rookSquare = move.to() + Point(1,0);
163 Point rookDestination = move.from() + Point(1,0);
165 NamedSprite rook = m_cinterface->takeSprite(rookDestination);
166 m_cinterface->setSprite(rookSquare, rook);
168 res.addPreAnimation(Animate::move(rook, rookSquare));
170 else if (move.queenSideCastling()) {
171 Point rookSquare = move.to() + Point(-2,0);
172 Point rookDestination = move.from() + Point(-1,0);
174 NamedSprite rook = m_cinterface->takeSprite(rookDestination);
175 m_cinterface->setSprite(rookSquare, rook);
177 res.addPreAnimation(Animate::move(rook, rookSquare));
180 res.addPreAnimation(*movement(piece, move.to(), move.from()));
182 return res;
190 #endif //HLVARIANT__ANIMATOR_IMPL_H