2 Copyright (c) 2006 Paolo Capriotti <p.capriotti@sns.it>
3 (c) 2006 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.
11 #ifndef XCHESS__ANIMATOR_IMPL_H
12 #define XCHESS__ANIMATOR_IMPL_H
15 #include "animationfactory.h"
17 #include "namedsprite.h"
18 #include "variants/xchess/piecetype.h"
20 template <typename Variant
>
21 AnimationGroupPtr BaseAnimator
<Variant
>::warp(const Position
& final
) {
22 const Position
* current
= m_cinterface
->position();
23 AnimationFactory
res(m_cinterface
->inner());
25 for (Point i
= current
->first(); i
<= current
->last(); i
= current
->next(i
)) {
26 Piece c
= current
->get(i
);
27 Piece f
= final
.get(i
);
31 NamedSprite sprite
= m_cinterface
->setPiece(i
, f
, false);
32 res
.addPreAnimation(Animate::appear(sprite
), Animate::Instant
);
35 NamedSprite old_sprite
= m_cinterface
->takeSprite(i
);
36 res
.addPreAnimation(Animate::disappear(old_sprite
), Animate::Instant
);
38 else if(c
&& f
&& !(c
== f
) ) {
39 NamedSprite old_sprite
= m_cinterface
->takeSprite(i
);
40 NamedSprite sprite
= m_cinterface
->setPiece(i
, f
, false);
41 res
.addPreAnimation(Animate::morph(old_sprite
, sprite
), Animate::Instant
);
48 template <typename Variant
>
49 AnimationGroupPtr BaseAnimator
<Variant
>::forward(const Position
& final
, const Move
&) {
54 template <typename Variant
>
55 AnimationGroupPtr BaseAnimator
<Variant
>::back(const Position
& final
, const Move
&) {
59 template <typename Variant
>
60 AnimationGroupPtr SimpleAnimator
<Variant
>::warp(const Position
& final
) {
61 AnimationFactory
res(m_cinterface
->inner());
63 res
.setGroup(Base::warp(final
));
68 template <typename Variant
>
69 SchemePtr SimpleAnimator
<Variant
>::movement(const NamedSprite
& sprite
, const Point
& from
, const Point
& to
) {
70 bool knight
= m_cinterface
->position()->get(from
).type() == KNIGHT
;
72 ? Animate::move::LShaped
| Animate::move::Rotating
73 : Animate::move::Straight
;
74 return SchemePtr(new Animate::move(sprite
, to
, mtype
));
77 template <typename Variant
>
78 AnimationGroupPtr SimpleAnimator
<Variant
>::forward(const Position
& final
, const Move
& move
) {
79 AnimationFactory
res(m_cinterface
->inner());
81 NamedSprite piece
= m_cinterface
->takeSprite(move
.from
);
82 NamedSprite captured
= m_cinterface
->takeSprite(move
.to
);
83 m_cinterface
->setSprite(move
.to
, piece
);
86 res
.addPreAnimation(*movement(piece
, move
.from
, move
.to
));
91 res
.addPostAnimation(Animate::destroy(captured
));
93 if (move
.type() == Move::EnPassantCapture
) {
94 Point
phantom(move
.to
.x
, move
.from
.y
);
95 NamedSprite capturedPawn
= m_cinterface
->takeSprite(phantom
);
98 QPoint real
= m_cinterface
->converter()->toReal(phantom
);
99 res
.addPostAnimation(Animate::disappear(capturedPawn
));
104 else if (move
.type() == Move::Promotion
) {
105 Piece promoted
= final
.get(move
.to
);
108 QPoint real
= m_cinterface
->converter()->toReal(move
.to
);
109 NamedSprite old_sprite
= m_cinterface
->getSprite(move
.to
);
110 NamedSprite new_sprite
= m_cinterface
->setPiece(move
.to
, promoted
, /*false,*/ false);
112 res
.addPostAnimation(Animate::morph(old_sprite
, new_sprite
));
117 else if (move
.type() == Move::KingSideCastling
) {
118 Point rookSquare
= move
.to
+ Point(1,0);
119 Point rookDestination
= move
.from
+ Point(1,0);
121 NamedSprite rook
= m_cinterface
->takeSprite(rookSquare
);
122 m_cinterface
->setSprite(rookDestination
, rook
);
123 res
.addPreAnimation(Animate::move(rook
, rookDestination
));
125 else if (move
.type() == Move::QueenSideCastling
) {
126 Point rookSquare
= move
.to
+ Point(-2,0);
127 Point rookDestination
= move
.from
+ Point(-1,0);
129 NamedSprite rook
= m_cinterface
->takeSprite(rookSquare
);
130 m_cinterface
->setSprite(rookDestination
, rook
);
131 res
.addPreAnimation(Animate::move(rook
, rookDestination
));
137 template <typename Variant
>
138 AnimationGroupPtr SimpleAnimator
<Variant
>::back(const Position
& final
, const Move
& move
) {
139 AnimationFactory
res(m_cinterface
->inner());
141 NamedSprite piece
= m_cinterface
->takeSprite(move
.to
);
142 NamedSprite captured
;
143 if (Piece captured_piece
= final
.get(move
.to
)) {
144 captured
= m_cinterface
->setPiece(move
.to
, captured_piece
, false);
145 res
.addPreAnimation(Animate::appear(captured
));
149 piece
= m_cinterface
->createPiece(move
.to
, final
.get(move
.from
), false);
150 res
.addPreAnimation(Animate::appear(piece
));
153 m_cinterface
->setSprite(move
.from
, piece
);
156 if (move
.type() == Move::EnPassantCapture
) {
157 Point
phantom(move
.to
.x
, move
.from
.y
);
159 if (Piece pawn_piece
= final
.get(phantom
)) {
160 NamedSprite captured_pawn
= m_cinterface
->setPiece(phantom
, pawn_piece
, false);
161 res
.addPreAnimation(Animate::appear(captured_pawn
));
164 else if (move
.type() == Move::Promotion
) {
165 Piece pawn_piece
= final
.get(move
.from
);
167 NamedSprite pawn
= m_cinterface
->createPiece(move
.to
, pawn_piece
, false);
168 res
.addPreAnimation(Animate::morph(piece
, pawn
));
170 // replace piece with pawn
171 m_cinterface
->setSprite(move
.from
, pawn
);
175 else if (move
.type() == Move::KingSideCastling
) {
176 Point rookSquare
= move
.to
+ Point(1,0);
177 Point rookDestination
= move
.from
+ Point(1,0);
179 NamedSprite rook
= m_cinterface
->takeSprite(rookDestination
);
180 m_cinterface
->setSprite(rookSquare
, rook
);
182 res
.addPreAnimation(Animate::move(rook
, rookSquare
));
184 else if (move
.type() == Move::QueenSideCastling
) {
185 Point rookSquare
= move
.to
+ Point(-2,0);
186 Point rookDestination
= move
.from
+ Point(-1,0);
188 NamedSprite rook
= m_cinterface
->takeSprite(rookDestination
);
189 m_cinterface
->setSprite(rookSquare
, rook
);
191 res
.addPreAnimation(Animate::move(rook
, rookSquare
));
194 res
.addPreAnimation(*movement(piece
, move
.to
, move
.from
));
200 #endif // XCHESS__ANIMATOR_IMPL_H