SVN_SILENT made messages (.desktop file)
[kdegames.git] / kbattleship / src / networkentity.cpp
blob00286956658b8ed30a7ff52b8c67789a36bae2e3
1 /*
2 Copyright (c) 2007 Paolo Capriotti <p.capriotti@gmail.com>
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation; either version 2 of the License, or
7 (at your option) any later version.
8 */
10 #include "networkentity.h"
12 #include "battlefield.h"
13 #include "shot.h"
14 #include "protocol.h"
16 #include <KIcon>
18 NetworkEntity::NetworkEntity(Sea::Player player, Sea* sea, Protocol* protocol, bool client)
19 : Entity(player)
20 , m_sea(sea)
21 , m_client(client)
23 m_protocol = protocol;
26 NetworkEntity::~NetworkEntity()
30 void NetworkEntity::start(bool ask)
32 connect(m_protocol, SIGNAL(received(MessagePtr)), this, SLOT(received(MessagePtr)));
33 connect(m_protocol, SIGNAL(disconnected()), this, SIGNAL(abortGame()));
34 if (ask) {
35 m_protocol->send(MessagePtr(new RestartMessage()));
37 else {
38 m_protocol->send(MessagePtr(new HeaderMessage()));
42 void NetworkEntity::notifyReady(Sea::Player player)
44 if (player != m_player) {
45 m_protocol->send(MessagePtr(new BeginMessage()));
49 void NetworkEntity::notifyGameOver(Sea::Player)
51 m_protocol->send(MessagePtr(new GameOverMessage));
54 void NetworkEntity::startPlaying()
59 void NetworkEntity::notify(Sea::Player player, const Coord& c, const HitInfo& info)
61 if (info.type == HitInfo::INVALID) {
62 return;
65 if (player == m_player) {
66 bool hit = info.type == HitInfo::HIT;
67 bool death = info.shipDestroyed != 0;
68 Coord begin = Coord::invalid();
69 Coord end = Coord::invalid();
70 if (death) {
71 begin = info.shipPos;
72 end = begin + info.shipDestroyed->increment() * (info.shipDestroyed->size() - 1);
74 m_protocol->send(MessagePtr(new NotificationMessage(c, hit, death, begin, end)));
76 else {
77 // the remote player already knows about the hit
78 // no need to notify it
82 void NetworkEntity::notifyNick(Sea::Player player, const QString& nick)
84 if (player != m_player) {
85 m_protocol->send(MessagePtr(new NickMessage(nick)));
89 void NetworkEntity::notifyChat(const Entity* entity, const QString& text)
91 if (entity != this) {
92 m_protocol->send(MessagePtr(new ChatMessage(entity->nick(), text)));
96 void NetworkEntity::notifyAbort()
98 // TODO: close connection
101 void NetworkEntity::hit(Shot* shot)
103 if (shot->player() != m_player
104 && m_sea->turn() == shot->player()
105 && m_sea->valid(m_player, shot->pos())) {
106 m_pending_shot = shot;
107 m_protocol->send(MessagePtr(new MoveMessage(shot->pos())));
109 else {
110 shot->execute(HitInfo::INVALID);
114 void NetworkEntity::received(MessagePtr msg)
116 msg->accept(*this);
119 void NetworkEntity::visit(const HeaderMessage& msg)
121 if (msg.clientName() == "KBattleship" && msg.clientVersion().toFloat() >= 4.0) {
122 // m_level = COMPAT_KBS4;
124 else {
125 if (m_level != COMPAT_KBS3) {
126 m_level = COMPAT_KBS3;
127 emit compatibility(m_level);
132 void NetworkEntity::visit(const RejectMessage&)
137 void NetworkEntity::visit(const NickMessage& msg)
139 setNick(msg.nickname());
140 emit nick(m_player, m_nick);
143 void NetworkEntity::visit(const BeginMessage&)
145 m_sea->add(m_player, 4);
146 emit ready(m_player);
149 void NetworkEntity::visit(const MoveMessage& msg)
151 emit shoot(m_player, msg.move());
154 void NetworkEntity::visit(const NotificationMessage& msg)
156 if (m_pending_shot) {
157 if (m_pending_shot->pos() != msg.move()) {
158 m_pending_shot->execute(HitInfo::INVALID);
160 else {
161 HitInfo info = msg.hit() ? HitInfo::HIT : HitInfo::MISS;
162 if (msg.death()) {
163 // gather ship data
164 Coord delta = msg.stop() - msg.start();
165 int size = abs(delta.x) + abs(delta.y) + 1;
166 Ship::Direction direction = delta.x == 0 ? Ship::TOP_DOWN : Ship::LEFT_TO_RIGHT;
167 Coord shipPos = (delta.x < 0 || delta.y < 0) ? msg.stop() : msg.start();
168 Ship* ship = new Ship(size, direction);
170 info.shipDestroyed = ship;
171 info.shipPos = shipPos;
174 m_sea->forceHit(msg.move(), info);
175 if (m_level == COMPAT_KBS3 && info.shipDestroyed) {
176 m_sea->addBorder(m_player, info.shipPos);
178 m_pending_shot->execute(info);
181 m_pending_shot = 0;
185 void NetworkEntity::visit(const GameOverMessage&)
190 void NetworkEntity::visit(const RestartMessage&)
192 emit restartRequested();
195 void NetworkEntity::visit(const ChatMessage& msg)
197 emit chat(msg.chat());
200 KIcon NetworkEntity::icon() const
202 return KIcon("network-workgroup");
205 #include "networkentity.moc"