• Skip to content
  • Skip to link menu
KDE API Reference
  • KDE API Reference
  • kdegames API Reference
  • KDE Home
  • Contact Us
 

kapman

  • sources
  • kde-4.14
  • kdegames
  • kapman
gamescene.cpp
Go to the documentation of this file.
1 /*
2  * Copyright 2007-2008 Thomas Gallinari <tg8187@yahoo.fr>
3  * Copyright 2007-2008 Alexandre Galinier <alex.galinier@hotmail.com>
4  *
5  * This program is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU General Public License as
7  * published by the Free Software Foundation; either version 2 of
8  * the License, or (at your option) any later version.
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13  * GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this program. If not, see <http://www.gnu.org/licenses/>.
17  */
18 
19 #include "gamescene.h"
20 #include "cell.h"
21 #include "bonus.h"
22 #include "settings.h"
23 
24 #include <KLocale>
25 
26 GameScene::GameScene(Game* p_game) : m_game(p_game), m_kapmanItem(0), m_mazeItem(0) {
27  connect(p_game, SIGNAL(levelStarted(bool)), SLOT(intro(bool)));
28  connect(p_game, SIGNAL(gameStarted()), this, SLOT(start()));
29  connect(p_game, SIGNAL(pauseChanged(bool,bool)), this, SLOT(setPaused(bool,bool)));
30  connect(p_game, SIGNAL(elementEaten(qreal,qreal)), this, SLOT(hideElement(qreal,qreal)));
31  connect(p_game, SIGNAL(bonusOn()), this, SLOT(displayBonus()));
32  connect(p_game, SIGNAL(bonusOff()), this, SLOT(hideBonus()));
33 
34  // Connection between Game and GameScene for the display of won points when a bonus or a ghost is eaten
35  connect(p_game, SIGNAL(pointsToDisplay(long,qreal,qreal)), this, SLOT(displayPoints(long,qreal,qreal)));
36 
37  // Create the theme instance
38  m_theme = new KGameTheme();
39 
40  // Load the SVG file
41  m_renderer = new QSvgRenderer();
42  loadTheme();
43 
44  // Create the MazeItem
45  m_mazeItem = new MazeItem();
46  // Give the maze the shared renderer to avoid loading the whole SVG file again
47  m_mazeItem->setSharedRenderer(m_renderer);
48  // Set the element Id to the right value
49  m_mazeItem->setElementId("maze");
50  m_mazeItem->setZValue(-2);
51 
52  // Create the KapmanItem
53  m_kapmanItem = new KapmanItem(p_game->getKapman());
54  m_kapmanItem->setSharedRenderer(m_renderer);
55  m_kapmanItem->setElementId("kapman_0");
56  // Corrects the position of the KapmanItem
57  m_kapmanItem->update(p_game->getKapman()->getX(), p_game->getKapman()->getY());
58  m_kapmanItem->setZValue(2);
59  // Stops the Kapman animation
60  m_kapmanItem->stopAnim();
61 
62  // Create the GhostItems
63  for (int i = 0; i < p_game->getGhosts().size(); ++i) {
64  GhostItem* ghost = new GhostItem(p_game->getGhosts()[i]);
65  ghost->setSharedRenderer(m_renderer);
66  ghost->setElementId(p_game->getGhosts()[i]->getImageId());
67  ghost->update(p_game->getGhosts()[i]->getX(), p_game->getGhosts()[i]->getY());
68  // At the beginning, the ghosts are above the kapman because they eat him
69  ghost->setZValue(3);
70  m_ghostItems.append(ghost);
71  }
72  // Create the Pill and Energizer items
73  m_elementItems = new ElementItem**[m_game->getMaze()->getNbRows()];
74  for (int i = 0; i < m_game->getMaze()->getNbRows(); ++i) {
75  m_elementItems[i] = new ElementItem*[m_game->getMaze()->getNbColumns()];
76  for (int j = 0; j < m_game->getMaze()->getNbColumns(); ++j) {
77  if (m_game->getMaze()->getCell(i, j).getElement() != NULL) {
78  // Create the element and set the image
79  ElementItem* element = new ElementItem(m_game->getMaze()->getCell(i, j).getElement());
80  element->setSharedRenderer(m_renderer);
81  element->setElementId(m_game->getMaze()->getCell(i,j).getElement()->getImageId());
82  element->update(m_game->getMaze()->getCell(i, j).getElement()->getX(), m_game->getMaze()->getCell(i, j).getElement()->getY());
83  m_elementItems[i][j] = element;
84  } else {
85  m_elementItems[i][j] = NULL;
86  }
87  }
88  }
89  // Create the Bonus item
90  m_bonusItem = new ElementItem(m_game->getBonus());
91  m_bonusItem->setSharedRenderer(m_renderer);
92  m_bonusItem->setElementId("bonus1");
93 
94  // All elements are created, update theme properties
95  updateSvgIds();
96  updateThemeProperties();
97 
98  // Create the introduction labels
99  m_introLabel = new QGraphicsTextItem(i18n("GET READY!!!"));
100  m_introLabel->setFont(QFont("Helvetica", 25, QFont::Bold, false));
101  m_introLabel->setDefaultTextColor(QColor("#FFFF00"));
102  m_introLabel->setZValue(4);
103  m_introLabel2 = new QGraphicsTextItem(i18n("Press any arrow key to start"));
104  m_introLabel2->setFont(QFont("Helvetica", 15, QFont::Bold, false));
105  m_introLabel2->setDefaultTextColor(QColor("#FFFF00"));
106  m_introLabel2->setZValue(4);
107  // Create the new level label
108  m_newLevelLabel = new QGraphicsTextItem();
109  m_newLevelLabel->setFont(QFont("Helvetica", 35, QFont::Bold, false));
110  m_newLevelLabel->setDefaultTextColor(QColor("#FFFF00"));
111  m_newLevelLabel->setZValue(4);
112  // Create the pause label
113  m_pauseLabel = new QGraphicsTextItem(i18n("PAUSED"));
114  m_pauseLabel->setFont(QFont("Helvetica", 35, QFont::Bold, false));
115  m_pauseLabel->setDefaultTextColor(QColor("#FFFF00"));
116  m_pauseLabel->setZValue(4);
117 
118  // Display the MazeItem
119  addItem(m_mazeItem);
120  // Display the KapmanItem
121  addItem(m_kapmanItem);
122  // Display each GhostItem
123  for (int i = 0; i < m_ghostItems.size(); ++i) {
124  addItem(m_ghostItems[i]);
125  }
126  // Display each Pill and Energizer item and introduction labels
127  intro(true);
128 }
129 
130 GameScene::~GameScene() {
131  delete m_mazeItem;
132  delete m_kapmanItem;
133  for (int i = 0; i < m_ghostItems.size(); ++i) {
134  delete m_ghostItems[i];
135  }
136  for (int i = 0; i < m_game->getMaze()->getNbRows();++i) {
137  for (int j = 0; j < m_game->getMaze()->getNbColumns(); ++j) {
138  if (m_elementItems[i][j] != NULL) {
139  delete m_elementItems[i][j];
140  }
141  }
142  delete[] m_elementItems[i];
143  }
144  delete[] m_elementItems;
145  delete m_bonusItem;
146  delete m_introLabel;
147  delete m_introLabel2;
148  delete m_newLevelLabel;
149  delete m_pauseLabel;
150  delete m_renderer;
151  delete m_theme;
152 }
153 
154 Game* GameScene::getGame() const {
155  return m_game;
156 }
157 
158 void GameScene::loadTheme() {
159  if (!m_theme->load(Settings::self()->theme())) {
160  return;
161  }
162  if (!m_renderer->load(m_theme->graphics())) {
163  return;
164  }
165 
166  //Update elementIDs, theme properties
167  updateSvgIds();
168  updateThemeProperties();
169 
170  update(0, 0, width(), height());
171 
172  // Update the theme config: if the default theme is selected, no theme entry is written -> the theme selector does not select the theme
173  Settings::self()->config()->group("General").writeEntry("Theme", Settings::self()->theme());
174 }
175 
176 void GameScene::updateSvgIds() {
177  //Needed so new boundingRects() are read for all SVG elements after a theme change
178  // Sanity check, see if game elements already exist
179  if (!m_kapmanItem) return;
180 
181  // Set the element Id to the right value
182  m_mazeItem->setElementId("maze");
183 
184  // Create the KapmanItem
185  m_kapmanItem->setElementId("kapman_0");
186  // Corrects the position of the KapmanItem
187  m_kapmanItem->update(m_game->getKapman()->getX(), m_game->getKapman()->getY());
188 
189  for (int i = 0; i < m_ghostItems.size(); ++i) {
190  GhostItem* ghost = m_ghostItems[i];
191  ghost->setElementId(m_game->getGhosts()[i]->getImageId());
192  ghost->update(m_game->getGhosts()[i]->getX(), m_game->getGhosts()[i]->getY());
193  }
194  for (int i = 0; i < m_game->getMaze()->getNbRows();++i) {
195  for (int j = 0; j < m_game->getMaze()->getNbColumns(); ++j) {
196  if (m_elementItems[i][j] != NULL) {
197  ElementItem* element = m_elementItems[i][j];
198  element->setElementId(m_game->getMaze()->getCell(i,j).getElement()->getImageId());
199  element->update(m_game->getMaze()->getCell(i, j).getElement()->getX(), m_game->getMaze()->getCell(i, j).getElement()->getY());
200  }
201  }
202  }
203 }
204 
205 void GameScene::updateThemeProperties() {
206  // Sanity check, see if game elements already exist
207  if (!m_kapmanItem) return;
208 
209  // Set the Rotation flag for KapmanItem
210  if (m_theme->themeProperty("RotateKapman")=="0") {
211  m_kapmanItem->setRotationFlag(false);
212  } else {
213  m_kapmanItem->setRotationFlag(true);
214  }
215 }
216 
217 void GameScene::intro(const bool p_newLevel) {
218  // If a new level has begun
219  if (p_newLevel) {
220  // Set each Pill and Energizer item to its original coordinates
221  for (int i = 0; i < m_game->getMaze()->getNbRows(); ++i) {
222  for (int j = 0; j < m_game->getMaze()->getNbColumns(); ++j) {
223  if (m_elementItems[i][j] != NULL) {
224  if (!items().contains(m_elementItems[i][j])) {
225  addItem(m_elementItems[i][j]);
226  }
227  }
228  }
229  }
230  // Display the new level label
231  m_newLevelLabel->setPlainText(i18nc("The number of the game level", "Level %1", m_game->getLevel()));
232  if (!items().contains(m_newLevelLabel)) {
233  addItem(m_newLevelLabel);
234  m_newLevelLabel->setPos((width() - m_newLevelLabel->boundingRect().width()) / 2, (height() - m_newLevelLabel->boundingRect().height()) / 2);
235  }
236  // Display the introduction label
237  if (!items().contains(m_introLabel2)) {
238  addItem(m_introLabel2);
239  m_introLabel2->setPos((width() - m_introLabel2->boundingRect().width()) / 2,
240  (height() - m_introLabel2->boundingRect().height() + m_newLevelLabel->boundingRect().height()) / 2);
241  }
242  } else {
243  // Display the introduction labels
244  if (!items().contains(m_introLabel)) {
245  addItem(m_introLabel);
246  m_introLabel->setPos((width() - m_introLabel->boundingRect().width()) / 2, (height() - m_introLabel->boundingRect().height()) / 2);
247  }
248  if (!items().contains(m_introLabel2)) {
249  addItem(m_introLabel2);
250  m_introLabel2->setPos((width() - m_introLabel2->boundingRect().width()) / 2,
251  (height() - m_introLabel2->boundingRect().height() + m_introLabel->boundingRect().height()) / 2);
252  }
253  }
254 }
255 
256 void GameScene::start() {
257  // If the introduction and new level labels were displayed then remove them
258  if (items().contains(m_introLabel)) {
259  removeItem(m_introLabel);
260  }
261  if (items().contains(m_introLabel2)) {
262  removeItem(m_introLabel2);
263  }
264  if (items().contains(m_newLevelLabel)) {
265  removeItem(m_newLevelLabel);
266  }
267 }
268 
269 void GameScene::setPaused(const bool p_pause, const bool p_fromUser) {
270  // If the game has paused
271  if (p_pause) {
272  // If the pause is due to an action from the user
273  if (p_fromUser) {
274  // If the label was not displayed yet
275  if (!items().contains(m_pauseLabel)) {
276  // FIXME: Hack to remove labels when pausing game while init labels are shown (icwiener)
277  // This should be done cleaner
278  // FIXME #2: start() is a misleading method name ...
279  start();
280  // Display the pause label
281  addItem(m_pauseLabel);
282  m_pauseLabel->setPos((width() - m_pauseLabel->boundingRect().width()) / 2, (height() - m_pauseLabel->boundingRect().height()) / 2);
283  }
284  }
285  // Stop kapman animation
286  m_kapmanItem->pauseAnim();
287  } else { // If the game has resumed
288  // If the pause was due to an action from the user
289  if (p_fromUser) {
290  // If the label was displayed
291  if (items().contains(m_pauseLabel)) {
292  removeItem(m_pauseLabel);
293  }
294  }
295  // Resume kapman animation
296  m_kapmanItem->resumeAnim();
297  }
298 }
299 
300 void GameScene::hideElement(const qreal p_x, const qreal p_y) {
301  if (items().contains(m_elementItems[(int)((p_y - (Cell::SIZE * 0.5)) / Cell::SIZE)][(int)((p_x - (Cell::SIZE * 0.5)) / Cell::SIZE)])) {
302  removeItem(m_elementItems[(int)((p_y - (Cell::SIZE * 0.5)) / Cell::SIZE)][(int)((p_x - (Cell::SIZE * 0.5)) / Cell::SIZE)]);
303  }
304 }
305 
306 void GameScene::displayBonus() {
307  if (!items().contains(m_bonusItem)) {
308  switch (m_game->getLevel()) {
309  case 1:
310  m_bonusItem->setElementId("bonus1");
311  break;
312  case 2:
313  m_bonusItem->setElementId("bonus2");
314  break;
315  case 3:
316  m_bonusItem->setElementId("bonus3");
317  break;
318  case 4:
319  m_bonusItem->setElementId("bonus4");
320  break;
321  case 5:
322  m_bonusItem->setElementId("bonus5");
323  break;
324  case 6:
325  m_bonusItem->setElementId("bonus6");
326  break;
327  default:
328  m_bonusItem->setElementId("bonus7");
329  break;
330  }
331  m_bonusItem->update(m_game->getBonus()->getX(), m_game->getBonus()->getY());
332  addItem(m_bonusItem);
333  }
334 }
335 
336 void GameScene::hideBonus() {
337  if (items().contains(m_bonusItem)) {
338  removeItem(m_bonusItem);
339  }
340 }
341 
342 
343 void GameScene::displayPoints(long p_wonPoints, qreal p_xPos, qreal p_yPos) {
344  // Launch a singleShot timer
345  QTimer::singleShot(1000, this, SLOT(hidePoints()));
346 
347  // Add a label in the list of won points Labels
348  m_wonPointsLabels.prepend(new QGraphicsTextItem(QString::number(p_wonPoints)));
349  addItem(m_wonPointsLabels.first());
350 
351  // Temporary reference to the first item in the list
352  QGraphicsTextItem* tempRef = m_wonPointsLabels.first();
353 
354  // Positioning and customization of the point label
355  tempRef->setDefaultTextColor(QColor("#FFFF00"));
356  tempRef->setFont(QFont("Helvetica", 15, QFont::Normal, false));
357  tempRef->setPos(p_xPos-(tempRef->boundingRect().width() / 2), p_yPos-(tempRef->boundingRect().height() / 2));
358  tempRef->setZValue(-1);
359 }
360 
361 void GameScene::hidePoints() {
362  // Remove the oldest item of the list from the scene
363  removeItem(m_wonPointsLabels.last());
364  // Remove the oldest item from the list
365  delete m_wonPointsLabels.takeLast();
366 }
QGraphicsTextItem::setFont
void setFont(const QFont &font)
Cell::getElement
Element * getElement() const
Gets the Element that is on the Cell.
Definition: cell.cpp:39
Maze::getCell
Cell getCell(const int p_row, const int p_column) const
Gets the Cell at the given coordinates.
Definition: maze.cpp:180
Element::getX
qreal getX() const
Gets the Element x-coordinate.
Definition: element.cpp:32
ElementItem::update
virtual void update(qreal p_x, qreal p_y)
Updates the ElementItem coordinates.
Definition: elementitem.cpp:45
KapmanItem
This class manage the display of the Kapman.
Definition: kapmanitem.h:29
QGraphicsScene::items
QList< QGraphicsItem * > items() const
Maze::getNbRows
int getNbRows() const
Gets the number of rows of the Maze.
Definition: maze.cpp:211
QFont
QGraphicsTextItem::boundingRect
virtual QRectF boundingRect() const
KapmanItem::pauseAnim
void pauseAnim()
Pauses the KapmanItem animation.
Definition: kapmanitem.cpp:129
QSvgRenderer
Settings::theme
static QString theme()
Get The graphical theme to be used.
Definition: settings.h:30
Element::getImageId
QString getImageId() const
Gets the path to the Element image.
Definition: element.cpp:58
GameScene::loadTheme
void loadTheme()
Loads the game theme.
Definition: gamescene.cpp:158
Game::getGhosts
QList< Ghost * > getGhosts() const
Definition: game.cpp:172
GameScene::~GameScene
~GameScene()
Deletes the Game instance.
Definition: gamescene.cpp:130
QGraphicsScene::height
qreal height() const
Game::getKapman
Kapman * getKapman() const
Definition: game.cpp:168
KapmanItem::stopAnim
void stopAnim()
Stops the KapmanItem animation.
Definition: kapmanitem.cpp:139
QList::size
int size() const
KapmanItem::update
void update(qreal p_x, qreal p_y)
Updates the KapmanItem coordinates.
Definition: kapmanitem.cpp:113
Settings::self
static Settings * self()
Definition: settings.cpp:17
Cell::SIZE
static const qreal SIZE
The Cell side size.
Definition: cell.h:33
KapmanItem::setRotationFlag
void setRotationFlag(bool rotate)
Set if the KapmanItem should be rotated (set by theme flag RotateKapman).
Definition: kapmanitem.h:121
QString::number
QString number(int n, int base)
cell.h
QList::append
void append(const T &value)
QSvgRenderer::load
bool load(const QString &filename)
QGraphicsScene::removeItem
void removeItem(QGraphicsItem *item)
QGraphicsItem::setPos
void setPos(const QPointF &pos)
Game
This class manages the game main loop : it regularly checks the key press events, computes the charac...
Definition: game.h:35
KapmanItem::resumeAnim
void resumeAnim()
Resumes the KapmanItem animation.
Definition: kapmanitem.cpp:134
QGraphicsTextItem
Game::getLevel
int getLevel() const
Definition: game.cpp:199
ElementItem
This class is the graphical representation of a game Element.
Definition: elementitem.h:28
QList::first
T & first()
QColor
gamescene.h
GameScene::getGame
Game * getGame() const
Definition: gamescene.cpp:154
bonus.h
Maze::getNbColumns
int getNbColumns() const
Gets the number of columns of the Maze.
Definition: maze.cpp:207
Element::getY
qreal getY() const
Gets the Element y-coordinate.
Definition: element.cpp:36
QList::takeLast
T takeLast()
QRectF::width
qreal width() const
settings.h
QGraphicsSvgItem::setElementId
void setElementId(const QString &id)
QList::last
T & last()
Game::getBonus
Bonus * getBonus() const
Definition: game.cpp:228
QGraphicsScene::update
void update(qreal x, qreal y, qreal w, qreal h)
GhostItem
This class is the graphical representation of a Ghost.
Definition: ghostitem.h:28
QGraphicsTextItem::setPlainText
void setPlainText(const QString &text)
QRectF::height
qreal height() const
QList::prepend
void prepend(const T &value)
QGraphicsTextItem::setDefaultTextColor
void setDefaultTextColor(const QColor &col)
QGraphicsScene::addItem
void addItem(QGraphicsItem *item)
QObject::connect
bool connect(const QObject *sender, const char *signal, const QObject *receiver, const char *method, Qt::ConnectionType type)
Game::getMaze
Maze * getMaze() const
Definition: game.cpp:180
QGraphicsItem::setZValue
void setZValue(qreal z)
GameScene::GameScene
GameScene(Game *p_game)
Creates a new GameScene instance.
Definition: gamescene.cpp:26
QGraphicsScene::width
qreal width() const
MazeItem
This class is the graphical view of the Maze.
Definition: mazeitem.h:27
QTimer::singleShot
singleShot
QGraphicsSvgItem::setSharedRenderer
void setSharedRenderer(QSvgRenderer *renderer)
GhostItem::update
void update(qreal p_x, qreal p_y)
Updates the view coordinates.
Definition: ghostitem.cpp:53
This file is part of the KDE documentation.
Documentation copyright © 1996-2020 The KDE developers.
Generated on Mon Jun 22 2020 13:18:15 by doxygen 1.8.7 written by Dimitri van Heesch, © 1997-2006

KDE's Doxygen guidelines are available online.

kapman

Skip menu "kapman"
  • Main Page
  • Alphabetical List
  • Class List
  • Class Hierarchy
  • Class Members
  • File List
  • File Members

kdegames API Reference

Skip menu "kdegames API Reference"
  • granatier
  • kapman
  • kblackbox
  • kgoldrunner
  • kigo
  • kmahjongg
  • KShisen
  • ksquares
  • libkdegames
  •   highscore
  •   libkdegamesprivate
  •     kgame
  • libkmahjongg
  • palapeli
  •   libpala

Search



Report problems with this website to our bug tracking system.
Contact the specific authors with questions and comments about the page contents.

KDE® and the K Desktop Environment® logo are registered trademarks of KDE e.V. | Legal