1//
2// KBlackBox
3//
4// A simple game inspired by an emacs module
5//
6/***************************************************************************
7 * Copyright (c) 1999-2000, Robert Cimrman *
8 * cimrman3@students.zcu.cz *
9 * *
10 * Copyright (c) 2007, Nicolas Roffet *
11 * nicolas-kde@roffet.com *
12 * *
13 * *
14 * This program is free software; you can redistribute it and/or modify *
15 * it under the terms of the GNU General Public License as published by *
16 * the Free Software Foundation; either version 2 of the License, or *
17 * (at your option) any later version. *
18 * *
19 * This program is distributed in the hope that it will be useful, *
20 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
22 * GNU General Public License for more details. *
23 * *
24 * You should have received a copy of the GNU General Public License *
25 * along with this program; if not, write to the *
26 * Free Software Foundation, Inc., *
27 * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA *
28 ***************************************************************************/
29
30#include "kbbgamedoc.h"
31
32
33
34
35
36#include "kbbballsonboard.h"
37#include "kbbtutorial.h"
38
39
40
41//
42// Constructor / Destructor
43//
44
45KBBGameDoc::KBBGameDoc(KBBMainWindow *parent, KBBTutorial* tutorial) : QObject(parent)
46{
47 setRunning(false);
48 m_columns = 1;
49 m_rows = 1;
50 m_tutorial = tutorial;
51
52 m_random.setSeed(0);
53
54 m_balls = new KBBBallsOnBoard(this, m_columns, m_rows);
55 m_ballsPlaced = new KBBBallsOnBoard(this, m_columns, m_rows);
56 connect(m_ballsPlaced, SIGNAL(changes()), parent, SLOT(updateStats()));
57}
58
59
60
61//
62// Public
63//
64
65int KBBGameDoc::columns() const
66{
67 return m_columns;
68}
69
70
71void KBBGameDoc::gameOver()
72{
73 // Clear
74 setRunning(false);
75
76 // Compute final score
77 if (m_ballsPlaced->numberOfBallsNotIn(m_balls)>0)
78 setScore(SCORE_LOST);
79}
80
81
82bool KBBGameDoc::gameReallyStarted()
83{
84 return m_gameReallyStarted;
85}
86
87
88bool KBBGameDoc::mayShootRay(const int incomingPosition) const
89{
90 if (m_tutorial->isVisible() && !m_tutorial->mayShootRay(incomingPosition))
91 return false;
92 else
93 return true;
94}
95
96
97void KBBGameDoc::newGame(int balls, int columns, int rows)
98{
99 clean(columns, rows);
100
101 // Puts the balls in the black box on random positions.
102 int boxPos;
103 for (int i = 0; i < balls; i++) {
104 do {
105 boxPos = m_random.getLong(m_columns * m_rows);
106 } while (m_balls->contains(boxPos));
107 m_balls->add(boxPos);
108 }
109}
110
111
112int KBBGameDoc::numberOfBallsPlaced()
113{
114 return m_ballsPlaced->count();
115}
116
117
118int KBBGameDoc::numberOfBallsToPlace()
119{
120 return m_balls->count();
121}
122
123
124int KBBGameDoc::rows() const
125{
126 return m_rows;
127}
128
129
130int KBBGameDoc::score()
131{
132 return m_score;
133}
134
135
136int KBBGameDoc::shootRay( int borderPosition )
137{
138 int outgoingBorderPosition = m_balls->oppositeBorderPosition(borderPosition);
139
140 if ((outgoingBorderPosition == HIT_POSITION) || (borderPosition == outgoingBorderPosition))
141 setScore(m_score + SCORE_ONE);
142 else
143 setScore(m_score + SCORE_TWO);
144
145 if (!m_tutorial->isVisible())
146 setRunning(true);
147 emit updateStats();
148
149 return outgoingBorderPosition;
150}
151
152
153void KBBGameDoc::startTutorial()
154{
155 clean(KBBTutorial::COLUMNS, KBBTutorial::ROWS);
156 m_balls->add(16);
157 m_balls->add(21);
158 m_balls->add(33);
159 m_tutorial->setStep(1);
160 m_tutorial->start();
161}
162
163
164void KBBGameDoc::timeChanged()
165{
166 setScore(m_score+1);
167}
168
169
170
171//
172// Private
173//
174
175void KBBGameDoc::clean(const int columns, const int rows)
176{
177 m_columns = columns;
178 m_rows = rows;
179
180 // Clear
181 setRunning(false);
182 m_ballsPlaced->newBoard(m_columns, m_rows);
183 setScore(-1); // -1 because a signal "timeChanged" will be send at the beginning and the score will be set to 0.
184
185 m_balls->newBoard(m_columns, m_rows);
186}
187
188
189void KBBGameDoc::setRunning(const bool r)
190{
191 m_gameReallyStarted = r;
192 emit isRunning(r);
193}
194
195
196void KBBGameDoc::setScore( int n )
197{
198 if (n<1000)
199 m_score = n;
200 else
201 m_score = 999;
202 emit updateStats();
203}
204
205#include "kbbgamedoc.moc"
206