summaryrefslogtreecommitdiff
path: root/noncore/games/mindbreaker
authorkergoth <kergoth>2002-01-25 22:14:26 (UTC)
committer kergoth <kergoth>2002-01-25 22:14:26 (UTC)
commit15318cad33835e4e2dc620d033e43cd930676cdd (patch) (unidiff)
treec2fa0399a2c47fda8e2cd0092c73a809d17f68eb /noncore/games/mindbreaker
downloadopie-15318cad33835e4e2dc620d033e43cd930676cdd.zip
opie-15318cad33835e4e2dc620d033e43cd930676cdd.tar.gz
opie-15318cad33835e4e2dc620d033e43cd930676cdd.tar.bz2
Initial revision
Diffstat (limited to 'noncore/games/mindbreaker') (more/less context) (ignore whitespace changes)
-rw-r--r--noncore/games/mindbreaker/.cvsignore4
-rw-r--r--noncore/games/mindbreaker/Makefile.in117
-rw-r--r--noncore/games/mindbreaker/main.cpp35
-rw-r--r--noncore/games/mindbreaker/mindbreaker.cpp818
-rw-r--r--noncore/games/mindbreaker/mindbreaker.h122
-rw-r--r--noncore/games/mindbreaker/mindbreaker.pro12
-rw-r--r--noncore/games/mindbreaker/qpe-mindbreaker.control9
7 files changed, 1117 insertions, 0 deletions
diff --git a/noncore/games/mindbreaker/.cvsignore b/noncore/games/mindbreaker/.cvsignore
new file mode 100644
index 0000000..415ec09
--- a/dev/null
+++ b/noncore/games/mindbreaker/.cvsignore
@@ -0,0 +1,4 @@
1Makefile
2moc_*
3helpdialog.cpp
4helpdialog.h
diff --git a/noncore/games/mindbreaker/Makefile.in b/noncore/games/mindbreaker/Makefile.in
new file mode 100644
index 0000000..88f6fb1
--- a/dev/null
+++ b/noncore/games/mindbreaker/Makefile.in
@@ -0,0 +1,117 @@
1#############################################################################
2
3####### Compiler, tools and options
4
5 CXX =$(SYSCONF_CXX) $(QT_CXX_MT)
6 CXXFLAGS=$(SYSCONF_CXXFLAGS_QT) $(SYSCONF_CXXFLAGS)
7 CC =$(SYSCONF_CC) $(QT_C_MT)
8 CFLAGS =$(SYSCONF_CFLAGS)
9 INCPATH =-I$(QPEDIR)/include
10 LFLAGS =$(SYSCONF_LFLAGS_QT) $(SYSCONF_RPATH_QT) $(SYSCONF_LFLAGS) $(QT_LFLAGS_MT)
11 LIBS =$(SUBLIBS) -lqpe $(SYSCONF_LIBS_QT) $(SYSCONF_LIBS) $(SYSCONF_LIBS_QTAPP)
12 MOC =$(SYSCONF_MOC)
13 UIC =$(SYSCONF_UIC)
14
15####### Target
16
17DESTDIR = $(QPEDIR)/bin/
18VER_MAJ = 1
19VER_MIN = 0
20VER_PATCH = 0
21 TARGET= mindbreaker
22TARGET1 = lib$(TARGET).so.$(VER_MAJ)
23
24####### Files
25
26 HEADERS =mindbreaker.h
27 SOURCES =main.cpp \
28 mindbreaker.cpp
29 OBJECTS =main.o \
30 mindbreaker.o
31INTERFACES =
32UICDECLS =
33UICIMPLS =
34 SRCMOC =moc_mindbreaker.cpp
35 OBJMOC =moc_mindbreaker.o
36
37
38####### Implicit rules
39
40.SUFFIXES: .cpp .cxx .cc .C .c
41
42.cpp.o:
43 $(CXX) -c $(CXXFLAGS) $(INCPATH) -o $@ $<
44
45.cxx.o:
46 $(CXX) -c $(CXXFLAGS) $(INCPATH) -o $@ $<
47
48.cc.o:
49 $(CXX) -c $(CXXFLAGS) $(INCPATH) -o $@ $<
50
51.C.o:
52 $(CXX) -c $(CXXFLAGS) $(INCPATH) -o $@ $<
53
54.c.o:
55 $(CC) -c $(CFLAGS) $(INCPATH) -o $@ $<
56
57####### Build rules
58
59
60all: $(DESTDIR)$(TARGET)
61
62$(DESTDIR)$(TARGET): $(UICDECLS) $(OBJECTS) $(OBJMOC) $(SUBLIBS)
63 $(SYSCONF_LINK) $(LFLAGS) -o $(DESTDIR)$(TARGET) $(OBJECTS) $(OBJMOC) $(LIBS)
64
65moc: $(SRCMOC)
66
67tmake:
68 tmake mindbreaker.pro
69
70clean:
71 -rm -f $(OBJECTS) $(OBJMOC) $(SRCMOC) $(UICIMPLS) $(UICDECLS)
72 -rm -f *~ core
73 -rm -f allmoc.cpp
74
75####### Extension Modules
76
77listpromodules:
78 @echo
79
80listallmodules:
81 @echo
82
83listaddonpromodules:
84 @echo
85
86listaddonentmodules:
87 @echo
88
89
90REQUIRES=
91
92####### Sub-libraries
93
94
95###### Combined headers
96
97
98
99####### Compile
100
101main.o: main.cpp \
102 mindbreaker.h \
103 $(QPEDIR)/include/qpe/qpeapplication.h
104
105mindbreaker.o: mindbreaker.cpp \
106 mindbreaker.h \
107 $(QPEDIR)/include/qpe/resource.h \
108 $(QPEDIR)/include/qpe/config.h \
109 $(QPEDIR)/include/qpe/qpetoolbar.h
110
111moc_mindbreaker.o: moc_mindbreaker.cpp \
112 mindbreaker.h
113
114moc_mindbreaker.cpp: mindbreaker.h
115 $(MOC) mindbreaker.h -o moc_mindbreaker.cpp
116
117
diff --git a/noncore/games/mindbreaker/main.cpp b/noncore/games/mindbreaker/main.cpp
new file mode 100644
index 0000000..8ba0fde
--- a/dev/null
+++ b/noncore/games/mindbreaker/main.cpp
@@ -0,0 +1,35 @@
1/**********************************************************************
2** Copyright (C) 2000 Trolltech AS. All rights reserved.
3**
4** This file is part of Qtopia Environment.
5**
6** This file may be distributed and/or modified under the terms of the
7** GNU General Public License version 2 as published by the Free Software
8** Foundation and appearing in the file LICENSE.GPL included in the
9** packaging of this file.
10**
11** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
12** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
13**
14** See http://www.trolltech.com/gpl/ for GPL licensing information.
15**
16** Contact info@trolltech.com if any conditions of this licensing are
17** not clear to you.
18**
19**********************************************************************/
20
21#include "mindbreaker.h"
22
23#include <qpe/qpeapplication.h>
24
25int main( int argc, char **argv )
26{
27 QPEApplication a( argc, argv );
28
29 MindBreaker w(0, "new window");
30 w.setCaption("Mind Breaker");
31 QPEApplication::setInputMethodHint( &w, QPEApplication::AlwaysOff );
32 a.showMainWidget(&w);
33
34 return a.exec();
35}
diff --git a/noncore/games/mindbreaker/mindbreaker.cpp b/noncore/games/mindbreaker/mindbreaker.cpp
new file mode 100644
index 0000000..b0e4d88
--- a/dev/null
+++ b/noncore/games/mindbreaker/mindbreaker.cpp
@@ -0,0 +1,818 @@
1/**********************************************************************
2** Copyright (C) 2000 Trolltech AS. All rights reserved.
3**
4** This file is part of Qtopia Environment.
5**
6** This file may be distributed and/or modified under the terms of the
7** GNU General Public License version 2 as published by the Free Software
8** Foundation and appearing in the file LICENSE.GPL included in the
9** packaging of this file.
10**
11** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
12** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
13**
14** See http://www.trolltech.com/gpl/ for GPL licensing information.
15**
16** Contact info@trolltech.com if any conditions of this licensing are
17** not clear to you.
18**
19**********************************************************************/
20
21#include "mindbreaker.h"
22
23#include <qpe/resource.h>
24#include <qpe/config.h>
25
26#include <qpainter.h>
27#include <qpixmap.h>
28#include <qpe/qpetoolbar.h>
29#include <qtoolbutton.h>
30#include <qpushbutton.h>
31#include <qmessagebox.h>
32#include <qlabel.h>
33#include <qstyle.h>
34
35#include <stdlib.h>
36#include <sys/time.h>
37#include <unistd.h>
38
39static int pegRTTI = 3393393;
40
41/* helper class, */
42class Peg : public QCanvasRectangle
43{
44public:
45 Peg(QCanvas *canvas, int type, int go = -1, int pos = -1);
46 int rtti() const {return pegRTTI; }
47 void advance(int phase);
48
49 bool hit( const QPoint &) const;
50
51/* a placed peg is one that has been set down on the board correctly and
52 should not be moved, only copied */
53 bool placed() const;
54 void setPlaced(bool);
55
56 int pegGo() const;
57 int pegPos() const;
58 void setPegPos(int);
59
60 int type() const;
61
62 static void buildImages();
63 static QImage imageForType(int t);
64
65 static int eggLevel;
66
67protected:
68 void drawShape(QPainter &);
69private:
70 static QVector<QImage> normalPegs;
71 static QVector<QImage> specialPegs;
72
73 bool isplaced;
74 int pegtype;
75 int peg_go;
76 int peg_pos;
77
78 int aniStep;
79};
80
81int Peg::eggLevel = 0;
82QVector<QImage> Peg::normalPegs;
83QVector<QImage> Peg::specialPegs;
84
85void Peg::buildImages()
86{
87
88 QImage pegs = Resource::loadImage("mindbreaker/pegs");
89 int x = 0;
90 int y = 0;
91 int i;
92 eggLevel = 0;
93 normalPegs.resize(10);
94 for (i = 0; i < 6; i++) {
95 normalPegs.insert(i, new QImage(pegs.copy(x, y, peg_size, peg_size)));
96 x += peg_size;
97 }
98 specialPegs.resize(5);
99 for (i = 0; i < 5; i++) {
100 specialPegs.insert(i, new QImage(pegs.copy(x,y,peg_size, peg_size)));
101 x += peg_size;
102 }
103
104 QImage image = Resource::loadImage("mindbreaker/mindbreaker");
105 /* copy from master image to functional images */
106 x = 0;
107 y = panel_height;
108 normalPegs.insert(8,
109 new QImage(image.copy(x, y, panel_width, panel_height)));
110 y += panel_height;
111 y += title_height;
112 normalPegs.insert(9,
113 new QImage(image.copy(x, y, title_width, title_height)));
114 y += title_height;
115
116 x = 6 * peg_size;
117 normalPegs.insert(6,
118 new QImage(image.copy(x, y, answerpeg_size, answerpeg_size)));
119 x += answerpeg_size;
120 normalPegs.insert(7,
121 new QImage(image.copy(x, y, answerpeg_size, answerpeg_size)));
122}
123
124QImage Peg::imageForType(int t)
125{
126 if (eggLevel > t ) {
127 if( t < 5) {
128 return *specialPegs[t];
129 } else {
130 return *normalPegs[rand() % 6];
131 }
132 }
133 return *normalPegs[t];
134}
135
136Peg::Peg(QCanvas *canvas , int t, int g = -1, int p = -1)
137 : QCanvasRectangle(canvas)
138{
139 setSize(normalPegs[t]->width(), normalPegs[t]->height() );
140 pegtype = t;
141 isplaced = FALSE;
142 peg_pos = p;
143 peg_go = g;
144 aniStep = rand() % 6;
145 setAnimated(TRUE);
146}
147
148void Peg::advance(int phase) {
149 if (phase == 0)
150 aniStep = (++aniStep) % 6;
151 else {
152 hide();
153 show();
154 }
155}
156
157void Peg::drawShape(QPainter &p )
158{
159 if ((pegtype == 5) && eggLevel > 5) {
160 p.drawImage(x(), y(), *normalPegs[aniStep]);
161 } else
162 p.drawImage(x(), y(), imageForType(pegtype));
163}
164
165bool Peg::hit( const QPoint &p ) const
166{
167 int ix = p.x() - int(x());
168 int iy = p.y() - int(y());
169 if (!normalPegs[pegtype]->valid(ix, iy))
170 return FALSE;
171 QRgb pixel = normalPegs[pegtype]->pixel(ix, iy);
172 return (qAlpha(pixel ) != 0);
173}
174
175inline bool Peg::placed() const
176{
177 return isplaced;
178}
179
180inline int Peg::pegGo() const
181{
182 return peg_go;
183}
184
185inline int Peg::pegPos() const
186{
187 return peg_pos;
188}
189
190inline void Peg::setPegPos(int p)
191{
192 peg_pos = p;
193}
194
195inline void Peg::setPlaced(bool p)
196{
197 isplaced = p;
198}
199
200inline int Peg::type() const
201{
202 return pegtype;
203}
204
205/* Load the main image, copy from it the pegs, the board, and the answer image
206 * and use these to create the tray, answer and board
207 */
208MindBreaker::MindBreaker( QWidget *parent=0, const char *name=0, int wFlags=0 )
209: QMainWindow(parent, name, wFlags),
210 canvas(board_height, board_width)
211{
212 MindBreakerBoard *m = new MindBreakerBoard(canvas, this);
213 setCentralWidget(m);
214
215 setToolBarsMovable( FALSE );
216
217 QPEToolBar *tb = new QPEToolBar(this);
218 tb->setHorizontalStretchable( TRUE );
219
220 QPixmap newicon = Resource::loadPixmap("new");
221 new QToolButton(newicon, tr("New Game"), 0,
222 m, SLOT(clear()), tb, "NewGame");
223
224 score = new QToolButton(tb);
225 score->setText("");
226 score->setMaximumHeight(20);
227 score->setUsesTextLabel(TRUE);
228 tb->setStretchableWidget(score);
229
230 connect(m, SIGNAL(scoreChanged(int, int)), this, SLOT(setScore(int, int)));
231 connect(score, SIGNAL(clicked()), m, SLOT(resetScore()));
232
233 int a, b;
234 m->getScore(&a, &b);
235 setScore(a,b);
236}
237
238void MindBreaker::setScore(int turns, int games)
239{
240 double average;
241 double total_turns = turns;
242 double total_games = games;
243
244 if(total_games > 0)
245 average = total_turns / total_games;
246 else
247 average = 0.0;
248
249 score->setText(tr("win avg: %1 turns (%2 games)").arg(average).arg(games));
250}
251
252
253MindBreakerBoard::MindBreakerBoard( QCanvas &c, QWidget *parent=0,
254 const char *name=0, int wFlags=0 )
255 : QCanvasView(&c, parent, name, wFlags)
256{
257 int i, x, y;
258 struct timeval tv;
259
260 current_go = 0;
261 gettimeofday(&tv, 0);
262
263 srand(tv.tv_usec);
264
265 canvas()->setAdvancePeriod(500);
266
267 QImage image = Resource::loadImage("mindbreaker/mindbreaker");
268
269 /* copy from master image to functional images */
270 x = 0;
271 y = 0;
272 panelImage = image.copy(x,y, panel_width, panel_height);
273 y += panel_height;
274 y += panel_height;
275
276 titleImage = image.copy(x, y, title_width, title_height);
277
278 Peg::buildImages(); // must be done BEFORE any pegs are made
279
280 current_highlight = new Peg(canvas(), 8);
281 current_highlight->setPlaced(TRUE);
282 current_highlight->setX(0);
283 current_highlight->setY(board_height - ((current_go + 1) * panel_height));
284 current_highlight->setZ(0);
285 current_highlight->show();
286
287
288 /* set up the game */
289 Config c("MindBreaker", Config::User);
290 c.setGroup("Board");
291 game_over = FALSE;
292 if (c.readNumEntry("Answer0") < 0) {
293 for (i = 0; i < 4; i++) {
294 answer[i] = rand() % 6;
295 current_guess[i] = 6;
296 }
297 total_turns = 0;
298 total_games = 0;
299 } else {
300 int j;
301 c.setGroup("Score");
302 total_turns = c.readNumEntry("Turns");
303 total_games = c.readNumEntry("Games");
304 if(total_turns < 0)
305 total_turns = 0;
306 if(total_games < 0)
307 total_games = 0;
308
309
310 checkScores();
311 c.setGroup("Board");
312 for(i = 0; i < 4; i++)
313 answer[i] = c.readNumEntry(QString("Answer%1").arg(i));
314 /* read, and parse past guesses */
315 current_go = 0;
316 for(j=0; j < 9; j++) {
317 current_guess[0] = c.readNumEntry(QString("Go%1p0").arg(j));
318 if (current_guess[0] < 0)
319 break;
320 placeGuessPeg(0, current_guess[0]);
321 current_guess[1] = c.readNumEntry(QString("Go%1p1").arg(j));
322 placeGuessPeg(1, current_guess[1]);
323 current_guess[2] = c.readNumEntry(QString("Go%1p2").arg(j));
324 placeGuessPeg(2, current_guess[2]);
325 current_guess[3] = c.readNumEntry(QString("Go%1p3").arg(j));
326 placeGuessPeg(3, current_guess[3]);
327 checkGuess();
328 }
329 for(i = 0; i < 4; i++) {
330 current_guess[i] = c.readNumEntry(QString("CurrentGo%1").arg(i));
331 if (current_guess[i] != 6)
332 placeGuessPeg(i, current_guess[i]);
333 }
334 }
335
336 /* draw initial screen */
337 drawBackground();
338 canvas()->update();
339}
340
341MindBreakerBoard::~MindBreakerBoard()
342{
343 int i, j;
344 if (game_over) {
345 current_go = 0;
346 /* clear the answer, clear the guess */
347 for (i = 0; i < 4; i++) {
348 answer[i] = rand() % 6;
349 current_guess[i] = 6;
350 }
351 }
352
353 Config c("MindBreaker", Config::User);
354 c.setGroup("Board");
355 c.clearGroup();
356 /* write the board */
357 for (i = 0; i < current_go; i++) {
358 for(j = 0; j < 4; j++)
359 c.writeEntry(tr("Go%1p%2").arg(i).arg(j), past_guesses[4*i+j]);
360 }
361 for(j = 0; j < 4; j++)
362 c.writeEntry(tr("CurrentGo%1").arg(j), current_guess[j]);
363 for(j = 0; j < 4; j++)
364 c.writeEntry(tr("Answer%1").arg(j), answer[j]);
365
366 c.setGroup("Score");
367 /* write the score */
368
369 c.writeEntry("Turns", total_turns);
370 c.writeEntry("Games", total_games);
371}
372
373void MindBreakerBoard::getScore(int *a, int *b)
374{
375 *a = total_turns;
376 *b = total_games;
377 return;
378}
379
380void MindBreakerBoard::placeGuessPeg(int pos, int pegId)
381{
382 int x = first_peg_x_diff + (pos * peg_spacing);
383 int y = board_height - ((current_go + 1) * panel_height)
384 + first_peg_y_diff;
385
386 Peg *peg = new Peg(canvas(), pegId, current_go, pos);
387 peg->setPegPos(pos);
388 peg->setPlaced(TRUE);
389 peg->setX(x);
390 peg->setY(y);
391 peg->setZ(2);
392 peg->show();
393}
394
395void MindBreakerBoard::drawBackground()
396{
397 int i, j, x, y, x_gap, y_gap;
398 QPixmap background = QPixmap(canvas()->width(), canvas()->height());
399
400 QPainter painter(&background);
401
402 painter.fillRect(0, 0, canvas()->width(), canvas()->height(), QColor(0,0,0));
403 /* very first thing is to draw the bins, as everything else needs
404 * to be drawn over them */
405
406 QPen pen(QColor(85, 45, 27), 4);
407 painter.setPen(pen);
408 x_gap = canvas()->width() - (panel_width + (2 * bin_margin));
409 //x_gap += peg_size >> 1;
410 if (x_gap < 1)
411 x_gap = 1;
412
413 y_gap = board_height / 6;
414 y_gap -= (2 * bin_margin);
415 //y_gap += peg_size >> 1;
416 if (y_gap < 1)
417 y_gap = 1;
418 x = panel_width + bin_margin - (peg_size >> 1);
419 y = bin_margin - (peg_size >> 1) + 2;
420
421 for (i = 0; i < 6; i++) {
422 for (j = 0; j < 10; j++) {
423 int rx = x + (rand() % x_gap);
424 int ry = y + (rand() % y_gap);
425 painter.drawImage(rx,ry, Peg::imageForType(i));
426 }
427 y += board_height / 6;
428 }
429 /* now draw the surrounding boxes */
430 x_gap = canvas()->width() - panel_width;
431 if (x_gap < 1) x_gap = 1;
432 y_gap = board_height / 6;
433 x = panel_width;
434 y = 1;
435
436 for (i = 0; i < 6; i++) {
437 painter.drawRect(x, y, x_gap, y_gap);
438 y += y_gap;
439 }
440
441 x = 0;
442 y = 0;
443
444 painter.drawImage(x,y, titleImage);
445 y = title_height;
446 /* now nine gues panels */
447 for (i = 0; i < 9; i ++) {
448 painter.drawImage(x, y, panelImage);
449 y += panel_height;
450 }
451
452 painter.flush();
453 canvas()->setBackgroundPixmap(background);
454}
455
456void MindBreakerBoard::checkGuess()
457{
458 int i,j;
459 int num_white = 0;
460 int num_black = 0;
461 int copy_answer[4];
462 int copy_guess[4];
463
464 for(i = 0; i < 4; i++) {
465 copy_answer[i] = answer[i];
466 copy_guess[i] = current_guess[i];
467 if (current_guess[i] == 6)
468 return;
469 if (answer[i] == current_guess[i]) {
470 num_black++;
471 copy_answer[i] = 6;
472 copy_guess[i] = 7;
473 }
474 }
475
476 /* now sure that user has completed a 'guess' */
477 for (i = 0; i < 4; i++) {
478 if (copy_guess[i] == 7)
479 continue; // already marked for a black
480 for (j = 0; j < 4; j++) {
481 if(copy_guess[i] == copy_answer[j]) {
482 copy_answer[j] = 6;
483 num_white++;
484 break;
485 }
486 }
487 }
488
489 int x = answerpegx;
490 int y = (board_height - ((current_go + 1) * panel_height)) + answerpegy;
491
492 if (num_black == 4)
493 game_over = TRUE;
494
495 while(num_black > 0) {
496 Peg *p = new Peg(canvas(), 7);
497 p->setPlaced(TRUE);
498 p->setX(x);
499 p->setY(y);
500 p->setZ(1);
501 p->show();
502 num_black--;
503
504 if (x == answerpegx)
505 x = answerpegx + answerpeg_diff;
506 else {
507 x = answerpegx;
508 y += answerpeg_diff;
509 }
510 }
511 while(num_white > 0){
512 Peg *p = new Peg(canvas(), 6);
513 p->setPlaced(TRUE);
514 p->setX(x);
515 p->setY(y);
516 p->setZ(1);
517 p->show();
518 num_white--;
519
520 if (x == answerpegx)
521 x = answerpegx + answerpeg_diff;
522 else {
523 x = answerpegx;
524 y += answerpeg_diff;
525 }
526 }
527 /* move to next go */
528 for(i = 0; i < 4; i++) {
529 past_guesses[4*current_go+i] = current_guess[i];
530 current_guess[i] = 6;
531 }
532
533 current_go++;
534 if((current_go > 8) || game_over) {
535 total_games++;
536 if(!game_over)
537 total_turns += 10;
538 else
539 total_turns += current_go;
540
541 emit scoreChanged(total_turns, total_games);
542 Peg *p = new Peg(canvas(), 9);
543 game_over = TRUE;
544 p->setPlaced(TRUE);
545 p->setX(0);
546 p->setY(0);
547 p->setZ(0);
548 p->show();
549
550 for (i = 0; i < 4; i++) {
551 p = new Peg(canvas(), answer[i], -1);
552 p->setX(first_peg_x_diff + (i * peg_spacing));
553 p->setY(5);
554 p->setZ(3);
555 p->show();
556 }
557 } else {
558 current_highlight->setY(board_height - ((current_go + 1) * panel_height));
559 }
560 canvas()->update();
561}
562
563void MindBreakerBoard::clear()
564{
565 if(!game_over) {
566 total_games++;
567 total_turns += 10;
568 emit scoreChanged(total_turns, total_games);
569 }
570 int i;
571 /* reset the game board */
572 game_over = FALSE;
573 /* clear the answer, clear the guess */
574 for (i = 0; i < 4; i++) {
575 answer[i] = rand() % 6;
576 current_guess[i] = 6;
577 }
578 current_go = 0;
579
580 QCanvasItemList list = canvas()->allItems();
581 QCanvasItemList::Iterator it = list.begin();
582 for (; it != list.end(); ++it) {
583 if (*it == current_highlight)
584 continue;
585 if (*it)
586 delete *it;
587 }
588
589 current_highlight->setY(board_height - ((current_go + 1) * panel_height));
590 checkScores();
591 drawBackground();
592 canvas()->update();
593}
594
595void MindBreakerBoard::resetScore()
596{
597 /* are u sure */
598
599 if (QMessageBox::information(this, tr( "Reset Statistics" ),
600 tr( "Reset the win ratio?" ),
601 tr( "OK" ), tr( "Cancel" ) ) == 0) {
602 total_turns = 0;
603 total_games = 0;
604 Peg::eggLevel = 0;
605 drawBackground();
606 canvas()->update();
607 emit scoreChanged(total_turns, total_games);
608 }
609}
610
611/* EVENTS */
612
613void MindBreakerBoard::contentsMousePressEvent(QMouseEvent *e)
614{
615 copy_press = FALSE;
616 null_press = FALSE;
617 /* ok, first work out if it is one of the bins that
618 got clicked */
619 if (e->x() > panel_width) {
620 /* its a bin, but which bin */
621 if(e->y() > board_height)
622 return; // missed everything
623 int bin = (e->y() + 2) / (board_height / 6);
624
625 /* make new peg... set it moving */
626 moving_pos = e->pos();
627 moving = new Peg(canvas(), bin, current_go);
628 moving->setX(e->x() - (peg_size >> 1));
629 moving->setY(e->y() - (peg_size >> 1));
630 moving->setZ(5);
631 moving->show();
632 canvas()->update();
633 return;
634 }
635
636 QCanvasItemList l = canvas()->collisions(e->pos());
637 for (QCanvasItemList::Iterator it=l.begin(); it !=l.end(); ++it) {
638 if ( (*it)->rtti() == pegRTTI ) {
639 Peg *item = (Peg *)(*it);
640 if (!item->hit(e->pos()))
641 continue;
642 if (item->type() > 5) {
643 null_press = TRUE;
644 null_point = e->pos();
645 continue; /* not a color peg */
646 }
647 if (item->placed()) {
648 /* copy */
649 if(item->pegGo() == -1)
650 return;
651 if(item->pegGo() == current_go) {
652 copy_press = TRUE;
653 copy_peg = item;
654 }
655 moving = new Peg(canvas(),
656 item->type(), current_go);
657 moving->setX(e->x() - (peg_size >> 1));
658 moving->setY(e->y() - (peg_size >> 1));
659 moving->setZ(5);
660 moving->show();
661 moving_pos = QPoint(e->x(), e->y());
662 canvas()->update();
663 return;
664 }
665 moving = (Peg *)*it;
666 moving_pos = e->pos();
667 canvas()->update();
668 return;
669 }
670 }
671 null_press = TRUE;
672 null_point = e->pos();
673 moving = 0;
674}
675
676void MindBreakerBoard::contentsMouseMoveEvent(QMouseEvent* e)
677{
678 if (moving ) {
679 moving->moveBy(e->pos().x() - moving_pos.x(),
680 e->pos().y() - moving_pos.y());
681 moving_pos = e->pos();
682 canvas()->update();
683 return;
684 }
685}
686
687void MindBreakerBoard::contentsMouseReleaseEvent(QMouseEvent* e)
688{
689 /* time to put down the peg */
690 if(moving) {
691 if(copy_press) {
692 /* check if collided with original. if so, delete both */
693 copy_press = FALSE;
694 QCanvasItemList l = canvas()->collisions(e->pos());
695 for (QCanvasItemList::Iterator it=l.begin(); it !=l.end(); ++it) {
696 if (*it == copy_peg)
697 copy_press = TRUE;
698 }
699 if (copy_press) {
700 current_guess[copy_peg->pegPos()] = 6;
701 delete copy_peg;
702 delete moving;
703 copy_press = FALSE;
704 moving = 0;
705 copy_peg = 0;
706 canvas()->update();
707 return;
708 }
709 }
710
711 /* first work out if in y */
712 if (e->y() > (board_height - (current_go * panel_height))) {
713 delete moving;
714 moving = 0;
715 canvas()->update();
716 return;
717 }
718 if (e->y() < (board_height - ((current_go + 1) * panel_height))) {
719 delete moving;
720 moving = 0;
721 canvas()->update();
722 return;
723 }
724 /* ok, a valid go, but which peg */
725 int x_bar = first_peg_x_diff - (peg_size >> 1);
726 x_bar += peg_spacing;
727 int pos = 0;
728 if (e->x() > x_bar)
729 pos = 1;
730 x_bar += peg_spacing;
731 if (e->x() > x_bar)
732 pos = 2;
733 x_bar += peg_spacing;
734 if (e->x() > x_bar)
735 pos = 3;
736 x_bar += peg_spacing;
737
738 if (e->x() > x_bar) {
739 /* invalid x */
740 delete moving;
741 moving = 0;
742 canvas()->update();
743 return;
744 }
745
746 int x = first_peg_x_diff + (pos * peg_spacing);
747 int y = board_height - ((current_go + 1) * panel_height)
748 + first_peg_y_diff;
749 moving->setPegPos(pos);
750 moving->setX(x);
751 moving->setY(y);
752 moving->setZ(2);
753
754 /* remove all other pegs from this position */
755 QCanvasItemList l = canvas()->collisions(QPoint(x,y));
756 for (QCanvasItemList::Iterator it=l.begin(); it !=l.end(); ++it) {
757 if ( (*it)->rtti() == pegRTTI ) {
758 Peg *item = (Peg *)(*it);
759 if ((item != moving) && (item != current_highlight))
760 delete item;
761 }
762 }
763 current_guess[pos] = ((Peg *)moving)->type();
764
765 ((Peg *)moving)->setPlaced(true);
766 canvas()->update();
767 return;
768 }
769 moving = 0;
770 null_point -= e->pos();
771 if(null_point.manhattanLength() < 6) {
772 if (game_over)
773 clear();
774 else
775 checkGuess();
776 }
777}
778
779void MindBreakerBoard::resizeEvent(QResizeEvent *e)
780{
781 QSize s = e->size();
782 int fw = style().defaultFrameWidth();
783 s.setWidth(s.width() - fw);
784 s.setHeight(s.height() - fw);
785
786 /* min size is 200 x 260 */
787 if (s.width() < board_width)
788 s.setWidth(board_width);
789
790 if (s.height() < board_height)
791 s.setHeight(board_height);
792
793 canvas()->resize(s.width() - fw, s.height() - fw);
794 drawBackground();
795}
796
797
798/* Easter egg function... beat the clock */
799void MindBreakerBoard::checkScores()
800{
801 double games = total_games;
802 double turns = total_turns;
803 double g = games / 10.0;
804 Peg::eggLevel = 0;
805
806 double break_even = 5.0;
807 if (g < 1.0)
808 return;
809 double avg = turns / games;
810 g--;
811 while (break_even >= 0.0) {
812 if (avg >= (break_even + g))
813 return;
814 // score a peg.
815 break_even -= 1.0;
816 Peg::eggLevel = int(5.0 - break_even);
817 }
818}
diff --git a/noncore/games/mindbreaker/mindbreaker.h b/noncore/games/mindbreaker/mindbreaker.h
new file mode 100644
index 0000000..fca649a
--- a/dev/null
+++ b/noncore/games/mindbreaker/mindbreaker.h
@@ -0,0 +1,122 @@
1/**********************************************************************
2** Copyright (C) 2000 Trolltech AS. All rights reserved.
3**
4** This file is part of Qtopia Environment.
5**
6** This file may be distributed and/or modified under the terms of the
7** GNU General Public License version 2 as published by the Free Software
8** Foundation and appearing in the file LICENSE.GPL included in the
9** packaging of this file.
10**
11** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
12** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
13**
14** See http://www.trolltech.com/gpl/ for GPL licensing information.
15**
16** Contact info@trolltech.com if any conditions of this licensing are
17** not clear to you.
18**
19**********************************************************************/
20
21#ifndef MINDBREAKER_H
22#define MINDBREAKER_H
23
24#include <qwidget.h>
25#include <qmainwindow.h>
26#include <qimage.h>
27#include <qvector.h>
28#include <qcanvas.h>
29#include <qlabel.h>
30
31static const int panel_height = 26;
32static const int panel_width = 180;
33
34static const int title_height = 25;
35static const int title_width = 180;
36
37static const int bin_margin = 10;
38static const int peg_size = 20;
39static const int answerpeg_size = 13;
40
41static const int first_peg_x_diff = 21;
42static const int first_peg_y_diff = ((panel_height - peg_size) >> 1);
43static const int peg_spacing = 30;
44
45static const int answerpegx = 152;
46static const int answerpegy = 2;
47static const int answerpeg_diff = 9;
48
49static const int board_height = (title_height + (panel_height * 9));
50static const int board_width = (panel_width + (bin_margin * 2) + peg_size);
51
52class Peg;
53class QToolButton;
54
55class MindBreakerBoard : public QCanvasView // QWidget
56{
57 Q_OBJECT
58public:
59 MindBreakerBoard(QCanvas &c, QWidget *parent=0, const char *name=0, int wFlags=0 );
60 ~MindBreakerBoard();
61
62 void getScore(int *, int *);
63signals:
64 void scoreChanged(int, int);
65
66public slots:
67 void clear();
68 void resetScore();
69
70protected:
71 void contentsMousePressEvent(QMouseEvent *);
72 void contentsMouseMoveEvent(QMouseEvent *);
73 void contentsMouseReleaseEvent(QMouseEvent *);
74 void resizeEvent(QResizeEvent *);
75
76private:
77 void drawBackground();
78 void checkGuess();
79 void checkScores();
80 void placeGuessPeg(int pos, int pegId);
81
82 QImage panelImage;
83 QImage titleImage;
84
85 Peg *moving;
86 Peg *current_highlight;
87 QPoint moving_pos;
88
89 // the game stuff
90 int answer[4];
91 int current_guess[4];
92 int past_guesses[4*9];
93 int current_go;
94
95 int null_press;
96 QPoint null_point;
97 bool copy_press;
98 Peg *copy_peg;
99 bool game_over;
100
101 int total_turns;
102 int total_games;
103};
104
105class MindBreaker : public QMainWindow // QWidget
106{
107 Q_OBJECT
108public:
109 MindBreaker(QWidget *parent=0, const char *name=0, int wFlags=0 );
110
111public slots:
112 void setScore(int, int);
113
114private:
115 QCanvas canvas;
116 MindBreakerBoard *board;
117 QToolButton *score;
118
119};
120
121
122#endif
diff --git a/noncore/games/mindbreaker/mindbreaker.pro b/noncore/games/mindbreaker/mindbreaker.pro
new file mode 100644
index 0000000..12944d1
--- a/dev/null
+++ b/noncore/games/mindbreaker/mindbreaker.pro
@@ -0,0 +1,12 @@
1TEMPLATE = app
2CONFIG += qt warn_on release
3DESTDIR = $(QPEDIR)/bin
4 HEADERS = mindbreaker.h
5 SOURCES = main.cpp \
6 mindbreaker.cpp
7TARGET = mindbreaker
8INCLUDEPATH += $(QPEDIR)/include
9DEPENDPATH += $(QPEDIR)/include
10LIBS += -lqpe
11
12TRANSLATIONS = ../i18n/de/mindbreaker.ts
diff --git a/noncore/games/mindbreaker/qpe-mindbreaker.control b/noncore/games/mindbreaker/qpe-mindbreaker.control
new file mode 100644
index 0000000..3bad93d
--- a/dev/null
+++ b/noncore/games/mindbreaker/qpe-mindbreaker.control
@@ -0,0 +1,9 @@
1Files: bin/mindbreaker apps/Games/mindbreaker.desktop pics/mindbreaker
2Priority: optional
3Section: qpe/games
4Maintainer: Warwick Allison <warwick@trolltech.com>
5Architecture: arm
6Version: $QPE_VERSION-3
7Depends: qpe-base ($QPE_VERSION)
8Description: Game: crack the coloured code
9 A game for the Qtopia environment.