36 files changed, 3035 insertions, 0 deletions
diff --git a/apps/Games/backgammon.desktop b/apps/Games/backgammon.desktop new file mode 100644 index 0000000..a61be25 --- a/dev/null +++ b/apps/Games/backgammon.desktop @@ -0,0 +1,6 @@ +[Desktop Entry] +Comment=Backgammon +Exec=backgammon +Icon=backgammon/backgammon +Type=Application +Name=BackGammon diff --git a/help/en/html/backgammon.html b/help/en/html/backgammon.html new file mode 100755 index 0000000..886a901 --- a/dev/null +++ b/help/en/html/backgammon.html @@ -0,0 +1,71 @@ +<html> +<head> +<title>Backgammon</title> +</head> +<body> + +<a name="top"></a> +<b><u>Backgammon</u></b><br> +version 0.9.5<br> +relased under GPL<br> +(c) Ralf Waspe 2002/2003<br> +rwaspe@web.de<br> +<hr> +<ul> +<li><a href="#how">How the game works</a></li> +<li><a href="#game">The Game menu</a></li> +<li><a href="#theme">The Theme menu</a></li> +<li><a href="#options">The Options menu</a></li> +<li><a href="#todo">ToDo List</a></li> +</ul> +<a href="#top">top</a><br> +<hr> + +<a name="how"><b>How the game works</b><br></a> +If you don not know the rules of backgammon try google : "backgammon rules" <br> +Details on how this game works soon<br> +<a href="#top">top</a><br> +<hr> + +<a name="game"><b>The Game menu</b><br></a> +<ul> +<li><b>new</b><br> +start a new game</li> +<li><b>load</b><br> +load a previusly saved game here</li> +<li><b>save</b><br> +save the current game.<br> +The game will be named automatically with the current date and time</li> +<li><b>delete</b><br> +delete a saved game</li> +</ul> +<a href="#top">top</a><br> +<hr> + +<a name="theme"><b>The Theme menu</b><br></a> +<ul> +<li><b>new</b><br> +create a new theme or alter an existing one based on the componts save on your z.<br> +make sure to give it a unique name, so you do not overwrite an existing theme !</li> +<li><b>load</b><br> +load a theme</li> +<li><b>save</b><br> +save the current theme<br> +<li><b>default</b><br> +make the current theme the default theme (the one that gets loaded when you start the game)</li> +<li><b>delete</b><br> +delete a theme (the theme with the name default can not be deleted)</li> +</ul> +<a href="#top">top</a><br> +<hr> + +<a name="options"><b>The Options menu</b><br></a> +blah<br> +<a href="#top">top</a><br> +<hr> + +<a name="todo"><b>ToDo list</b><br></a> +eliminate bugs<br> +<a href="#top">top</a><br> +</body> +</html> diff --git a/noncore/games/backgammon/aidialog.cpp b/noncore/games/backgammon/aidialog.cpp new file mode 100644 index 0000000..9642ca5 --- a/dev/null +++ b/noncore/games/backgammon/aidialog.cpp @@ -0,0 +1,211 @@ +#include "aidialog.h" + +#include <qgroupbox.h> + + +AI_Dialog::AI_Dialog(QWidget* parent,const char* name,bool modal,WFlags f) + : QDialog(parent,name,modal,f) +{ + setCaption("AI Configuration"); + + QGroupBox* settings=new QGroupBox("Settings",this); + settings->setGeometry(10,5,220,170); + + QLabel* rescue_label=new QLabel("<b>Rescue</b>",settings); + rescue_label->setGeometry(50,20,50,20); + rescue=new QSpinBox(0,6,1,settings); + rescue->setGeometry(100,20,40,20); + QPushButton* rescuehelp=new QPushButton("?",settings); + rescuehelp->setGeometry(140,20,20,20); + connect(rescuehelp,SIGNAL(pressed()),this,SLOT(rescuehelp_pressed())); + connect(rescuehelp,SIGNAL(released()),this,SLOT(rescuehelp_released())); + + QLabel* eliminate_label=new QLabel("<b>Eliminate</b>",settings); + eliminate_label->setGeometry(50,40,50,20); + eliminate=new QSpinBox(0,6,1,settings); + eliminate->setGeometry(100,40,40,20); + QPushButton* eliminatehelp=new QPushButton("?",settings); + eliminatehelp->setGeometry(140,40,20,20); + connect(eliminatehelp,SIGNAL(pressed()),this,SLOT(eliminatehelp_pressed())); + connect(eliminatehelp,SIGNAL(released()),this,SLOT(eliminatehelp_released())); + + QLabel* expose_label=new QLabel("<b>Expose</b>",settings); + expose_label->setGeometry(50,60,50,20); + expose=new QSpinBox(0,6,1,settings); + expose->setGeometry(100,60,40,20); + QPushButton* exposeehelp=new QPushButton("?",settings); + exposeehelp->setGeometry(140,60,20,20); + connect(exposeehelp,SIGNAL(pressed()),this,SLOT(exposehelp_pressed())); + connect(exposeehelp,SIGNAL(released()),this,SLOT(exposehelp_released())); + + QLabel* protect_label=new QLabel("<b>Protect</b>",settings); + protect_label->setGeometry(50,80,50,20); + protect=new QSpinBox(0,6,1,settings); + protect->setGeometry(100,80,40,20); + QPushButton* protecthelp=new QPushButton("?",settings); + protecthelp->setGeometry(140,80,20,20); + connect(protecthelp,SIGNAL(pressed()),this,SLOT(protecthelp_pressed())); + connect(protecthelp,SIGNAL(released()),this,SLOT(protecthelp_released())); + + QLabel* safe_label=new QLabel("<b>Safe</b>",settings); + safe_label->setGeometry(50,100,50,20); + safe=new QSpinBox(0,6,1,settings); + safe->setGeometry(100,100,40,20); + QPushButton* safeehelp=new QPushButton("?",settings); + safeehelp->setGeometry(140,100,20,20); + connect(safeehelp,SIGNAL(pressed()),this,SLOT(safehelp_pressed())); + connect(safeehelp,SIGNAL(released()),this,SLOT(safehelp_released())); + + QLabel* empty_label=new QLabel("<b>Empty</b>",settings); + empty_label->setGeometry(50,120,50,20); + empty=new QSpinBox(0,6,1,settings); + empty->setGeometry(100,120,40,20); + QPushButton* emptyhelp=new QPushButton("?",settings); + emptyhelp->setGeometry(140,120,20,20); + connect(emptyhelp,SIGNAL(pressed()),this,SLOT(emptyhelp_pressed())); + connect(emptyhelp,SIGNAL(released()),this,SLOT(emptyhelp_released())); + + defaultvalues=new QPushButton("Default Values",settings); + defaultvalues->setGeometry(60,140,90,20); + connect(defaultvalues,SIGNAL(clicked()),this,SLOT(setDefaultValues())); + + QGroupBox* helpbox=new QGroupBox("Help",this); + helpbox->setGeometry(10,185,220,90); + + help=new QLabel(helpbox); + help->setGeometry(10,15,200,65); + + setHelpText(); + showMaximized(); +} + + +AI_Dialog::~AI_Dialog() +{ +} + +void AI_Dialog::rescuehelp_pressed() +{ + setHelpText("rescue"); +} + +void AI_Dialog::rescuehelp_released() +{ + setHelpText(); +} + +void AI_Dialog::eliminatehelp_pressed() +{ + setHelpText("eliminate"); +} + +void AI_Dialog::eliminatehelp_released() +{ + setHelpText(); +} + +void AI_Dialog::exposehelp_pressed() +{ + setHelpText("expose"); +} + +void AI_Dialog::exposehelp_released() +{ + setHelpText(); +} + +void AI_Dialog::protecthelp_pressed() +{ + setHelpText("protect"); +} + +void AI_Dialog::protecthelp_released() +{ + setHelpText(); +} + +void AI_Dialog::safehelp_pressed() +{ + setHelpText("safe"); +} + +void AI_Dialog::safehelp_released() +{ + setHelpText(); +} + +void AI_Dialog::emptyhelp_pressed() +{ + setHelpText("empty"); +} + +void AI_Dialog::emptyhelp_released() +{ + setHelpText(); +} + + + +void AI_Dialog::setDefaultValues() +{ + rescue->setValue(6); + eliminate->setValue(4); + expose->setValue(1); + protect->setValue(5); + safe->setValue(3); + empty->setValue(2); +} + +void AI_Dialog::setAISettings(const AISettings& values) +{ + rescue->setValue(values.rescue); + eliminate->setValue(values.eliminate); + expose->setValue(values.expose); + protect->setValue(values.protect); + safe->setValue(values.safe); + empty->setValue(values.empty); +} + +AISettings AI_Dialog::getAISettings() +{ + AISettings ai; + ai.rescue=rescue->value(); + ai.eliminate=eliminate->value(); + ai.expose=expose->value(); + ai.protect=protect->value(); + ai.safe= safe->value(); + ai.empty=empty->value(); + return ai; +} + +void AI_Dialog::setHelpText(const QString& type) +{ + if(type=="rescue") + { + help->setText("Bring the pieces out of the endzone"); + } + else if(type=="eliminate") + { + help->setText("Eliminate an opponents piece"); + } + else if(type=="expose") + { + help->setText("Expose you own pieces.\nAfter such a move only one piece will remain in the slot"); + } + else if(type=="protect") + { + help->setText("Protect a single piece by\nputting another one in this slot"); + } + else if(type=="safe") + { + help->setText("Move piece to a slot already\noccupied by the player"); + } + else if(type=="empty") + { + help->setText("Move piece to an empty slot"); + } + else + { + help->setText("Press and hold the ? buttton\nnext to a field for help"); + } +} diff --git a/noncore/games/backgammon/aidialog.h b/noncore/games/backgammon/aidialog.h new file mode 100644 index 0000000..2597f8b --- a/dev/null +++ b/noncore/games/backgammon/aidialog.h @@ -0,0 +1,48 @@ +#ifndef AIDIALOG_H_ +#define AIDIALOG_H_ + +#include "moveengine.h" + +#include <qdialog.h> +#include <qlabel.h> +#include <qpushbutton.h> +#include <qspinbox.h> + +class AI_Dialog : public QDialog +{ + Q_OBJECT +private: + //GUI stuff + QPushButton* defaultvalues; + QSpinBox* rescue; + QSpinBox* eliminate; + QSpinBox* expose; + QSpinBox* protect; + QSpinBox* safe; + QSpinBox* empty; + QLabel* help; +public: + AI_Dialog(QWidget* parent=0,const char* name=0,bool modal=TRUE,WFlags f=0); + ~AI_Dialog(); +private slots: + void rescuehelp_pressed(); + void rescuehelp_released(); + void eliminatehelp_pressed(); + void eliminatehelp_released(); + void exposehelp_pressed(); + void exposehelp_released(); + void protecthelp_pressed(); + void protecthelp_released(); + void safehelp_pressed(); + void safehelp_released(); + void emptyhelp_pressed(); + void emptyhelp_released(); + void setDefaultValues(); +public: + void setAISettings(const AISettings& values); + AISettings getAISettings(); +private: + void setHelpText(const QString& type="default"); +}; + +#endif //AIDIALOG_H diff --git a/noncore/games/backgammon/backgammon.control b/noncore/games/backgammon/backgammon.control new file mode 100644 index 0000000..528a8c3 --- a/dev/null +++ b/noncore/games/backgammon/backgammon.control @@ -0,0 +1,9 @@ +Files: bin/backgammon apps/Games/backgammon.desktop pics/backgammon help/en/html/backgammon.html +Priority: optional +Section: opie/games +Maintainer: Ralf Waspe <rwaspe@web.de> +Architecture: arm +Version: $QPE_VERSION-$SUB_VERSION +Depends: opie-base +Description: Backgammon Game + A Backgammon game for the Opie environment. diff --git a/noncore/games/backgammon/backgammon.cpp b/noncore/games/backgammon/backgammon.cpp new file mode 100644 index 0000000..38ccb49 --- a/dev/null +++ b/noncore/games/backgammon/backgammon.cpp @@ -0,0 +1,1043 @@ +#include "backgammon.h" + +#include "aidialog.h" +#include "displaydialog.h" +#include "filedialog.h" +#include "playerdialog.h" +#include "rulesdialog.h" +#include "themedialog.h" + +#include <qdatetime.h> +#include <qfile.h> +#include <qmessagebox.h> +#include <qstring.h> +#include <qtimer.h> +#include <qpe/qpeapplication.h> +#include <qpe/config.h> +#include <qpe/qpemenubar.h> +#include <qpe/resource.h> + +#include <stdlib.h> + +BackGammonView::BackGammonView(QCanvas* canvas,QWidget* parent) + :QCanvasView(canvas,parent) +{ + //do nothing +} + + + +BackGammonView::~BackGammonView() +{ + //do nothing +} + + + +void BackGammonView::contentsMousePressEvent(QMouseEvent* e) +{ + int x=e->x(); + int y=e->y(); + emit mouse(x,y); +} + +BackGammon::BackGammon(QWidget* parent, const char* name, WFlags fl) + : QWidget(parent, name, fl) +{ + if (!name) setName("BackGammon"); + setCaption("Backgammon"); + setIcon( Resource::loadPixmap( "backgammon" ) ); + //general counter varaible + int a=0; + //the game engine + move=new MoveEngine(); + + //load the default theme + Config conf("backgammon"); + if(!conf.isValid()) + { + qDebug("config file does not exist"); + conf.setGroup("general"); + conf.writeEntry("theme","default"); + conf.setGroup("rules"); + conf.writeEntry("move_with_pieces_out",false); + conf.writeEntry("nice_dice",false); + conf.setGroup("display"); + conf.writeEntry("small",false); + conf.writeEntry("warning",true); + conf.setGroup("ai"); + conf.writeEntry("rescue",6); + conf.writeEntry("eliminate",4); + conf.writeEntry("expose",1); + conf.writeEntry("protect",5); + conf.writeEntry("safe",3); + conf.writeEntry("empty",2); + + } + conf.setGroup("general"); + theme_name=conf.readEntry("theme","default"); + QString theme_file=QPEApplication::qpeDir()+"/backgammon/"+theme_name+".theme"; + + //the rules + conf.setGroup("rules"); + rules.move_with_pieces_out=conf.readBoolEntry("move_with_pieces_out",false); + rules.generous_dice=conf.readBoolEntry("nice_dice",false); + + move->setRules(rules); + + //get the AI settings + AISettings ai; + conf.setGroup("ai"); + ai.rescue=conf.readNumEntry("rescue",6); + ai.eliminate=conf.readNumEntry("eliminate",4); + ai.expose=conf.readNumEntry("expose",1); + ai.protect=conf.readNumEntry("protect",5); + ai.safe=conf.readNumEntry("safe",3); + ai.empty=conf.readNumEntry("empty",2); + move->setAISettings(ai); + + //non qte styles are smaller + conf.setGroup("display"); + display.small=conf.readBoolEntry("small",false); + display.warning=conf.readBoolEntry("warning",true); + non_qte=display.small; + if(display.warning) + { + Config test("qpe"); + test.setGroup("Appearance"); + if(test.readEntry("Style")!="QPE") + { + displaySettings(); + } + } + offset=(non_qte) ? 5 : 0; + + //get the theme component names + Config theme(theme_file,Config::File); + if(!theme.isValid()) + { + qDebug("theme file does not exist"); + theme.setGroup("theme"); + theme.writeEntry("board","casino_board_1"); + theme.writeEntry("pieces1","casino_pieces_blue"); + theme.writeEntry("pieces2","casino_pieces_white"); + theme.writeEntry("dice1","casino_dice"); + theme.writeEntry("dice2","casino_dice"); + theme.writeEntry("table","casino_table_green"); + theme.writeEntry("odds","casino_odds"); + } + theme.setGroup("theme"); + board_name=theme.readEntry("board","casino_board_1"); + piecesA_name=theme.readEntry("pieces1","casino_pieces_blue"); + piecesB_name=theme.readEntry("pieces2","casino_pieces_white"); + diceA_name=theme.readEntry("dice1","casino_dice"); + diceB_name=theme.readEntry("dice2","casino_dice"); + table_name=theme.readEntry("table","casino_table_green"); + odds_name=theme.readEntry("odds","casino_odds"); + + + //the menu + QPEMenuBar* menuBar = new QPEMenuBar(this); + + QPopupMenu* gamemenu= new QPopupMenu(this); + gamemenu->insertItem("New",this,SLOT(newgame())); + gamemenu->insertSeparator(); + gamemenu->insertItem("Load",this,SLOT(loadgame())); + gamemenu->insertItem("Save",this,SLOT(savegame())); + gamemenu->insertSeparator(); + gamemenu->insertItem("Delete",this,SLOT(deletegame())); + menuBar->insertItem("Game",gamemenu); + + QPopupMenu* thememenu= new QPopupMenu(this); + thememenu->insertItem("New",this,SLOT(newtheme())); + thememenu->insertSeparator(); + thememenu->insertItem("Load",this,SLOT(loadtheme())); + thememenu->insertItem("Save",this,SLOT(savetheme())); + thememenu->insertSeparator(); + thememenu->insertItem("Default",this,SLOT(themedefault())); + thememenu->insertItem("Delete",this,SLOT(deletetheme())); + menuBar->insertItem("Theme",thememenu); + + QPopupMenu* optionmenu=new QPopupMenu(this); + optionmenu->insertItem("Player",this,SLOT(playerselect())); + optionmenu->insertSeparator(); + optionmenu->insertItem("AI",this,SLOT(modify_AI())); + optionmenu->insertItem("Rules",this,SLOT(setrules())); + optionmenu->insertItem("Display",this,SLOT(displaySettings())); + menuBar->insertItem("Options",optionmenu); + + //status bar + message=new QLabel("<b>Backgammon</b>",this); + message->setGeometry(0,260,237,20); + message->setAlignment(AlignHCenter); + + //the main area + area=new QCanvas(235-2*offset,235-2*offset); + boardview=new BackGammonView(area,this); + connect(boardview,SIGNAL(mouse(int,int)),this,SLOT(mouse(int,int))); + if(non_qte) + { + boardview->setGeometry(5,20,229,229); + } + else + { + boardview->setGeometry(1,20,237,237); + } + + //the marker + marker_current=new QCanvasRectangle(area); + marker_current->setBrush(QColor(0,0,255)); + marker_current->setSize(15,5); + marker_current->setZ(1); + + for(a=0;a<4;a++) + { + marker_next[a]=new QCanvasRectangle(area); + marker_next[a]->setBrush(QColor(0,255,0)); + marker_next[a]->setSize(15,5); + marker_next[a]->setZ(1); + } + + connect(move,SIGNAL(done_dice1()),this,SLOT(done_dice1())); + connect(move,SIGNAL(done_dice2()),this,SLOT(done_dice2())); + connect(move,SIGNAL(done_dice3()),this,SLOT(done_dice3())); + connect(move,SIGNAL(done_dice4()),this,SLOT(done_dice4())); + connect(move,SIGNAL(nomove()),this,SLOT(nomove())); + connect(move,SIGNAL(player_finished(int)),this,SLOT(finished(int))); + + //the pieces + p1=new CanvasImageItem*[15]; + p1_side=new CanvasImageItem*[15]; + QImage piece_1_all(Resource::loadImage("backgammon/pieces/"+piecesA_name)); + QImage piece_1_front=piece_1_all.copy(0,0,15,15); + QImage piece_1_side=piece_1_all.copy(0,15,15,5); + + p2=new CanvasImageItem*[15]; + p2_side=new CanvasImageItem*[15]; + QImage piece_2_all(Resource::loadImage("backgammon/pieces/"+piecesB_name)); + QImage piece_2_front=piece_2_all.copy(0,0,15,15); + QImage piece_2_side=piece_2_all.copy(0,15,15,5); + + + for(a=0;a<15;a++) + { + p1[a]=new CanvasImageItem(piece_1_front,area); + p1[a]->setSize(15,15); + p1_side[a]=new CanvasImageItem(piece_1_side,area); + p1_side[a]->setSize(15,5); + + p2[a]=new CanvasImageItem(piece_2_front,area); + p2[a]->setSize(15,15); + p2_side[a]=new CanvasImageItem(piece_2_side,area); + p2_side[a]->setSize(15,5); + } + draw(); + + //the dice + QImage dicebgA_all(Resource::loadImage("backgammon/dice/"+diceA_name)); + diceA1=new CanvasImageItem*[7]; + diceA2=new CanvasImageItem*[7]; + QImage dicebgB_all(Resource::loadImage("backgammon/dice/"+diceB_name)); + diceB1=new CanvasImageItem*[7]; + diceB2=new CanvasImageItem*[7]; + QImage oddsbg_all=(Resource::loadImage("backgammon/odds/"+odds_name)); + //oddsDice=new CanvasImageItem*[6]; + + + for(a=0;a<7;a++) + { + QImage dicebgA=dicebgA_all.copy(a*25,0,25,25); + diceA1[a]=new CanvasImageItem(dicebgA,area); + diceA1[a]->setX(5-offset); + diceA1[a]->setY(205-2*offset); + diceA1[a]->setZ(1); + diceA1[a]->setSize(25,25); + diceA2[a]=new CanvasImageItem(dicebgA,area); + diceA2[a]->setX(35-offset); + diceA2[a]->setY(205-2*offset); + diceA2[a]->setZ(1); + diceA2[a]->setSize(25,25); + + QImage dicebgB=dicebgB_all.copy(a*25,0,25,25); + diceB1[a]=new CanvasImageItem(dicebgB,area); + diceB1[a]->setX(175-offset); + diceB1[a]->setY(205-2*offset); + diceB1[a]->setZ(1); + diceB1[a]->setSize(25,25); + diceB2[a]=new CanvasImageItem(dicebgB,area); + diceB2[a]->setX(205-offset); + diceB2[a]->setY(205-2*offset); + diceB2[a]->setZ(1); + diceB2[a]->setSize(25,25); + + /* + if(a<6) + { + QImage oddsbg=oddsbg_all.copy(a*15,0,15,15); + oddsDice[a]=new CanvasImageItem(oddsbg,area); + oddsDice[a]->setX(110-offset); + oddsDice[a]->setY(210-2*offset); + oddsDice[a]->setZ(1); + oddsDice[a]->setSize(15,15); + oddsDice[a]->hide(); + } + */ + } + //oddsDice[0]->show(); + + //set the board + QImage boardbg(Resource::loadImage("backgammon/boards/"+board_name)); + if(non_qte) + { + boardbg=boardbg.copy(offset,offset,235-2*offset,200-2*offset); + } + board=new CanvasImageItem(boardbg,area); + board->setX(0); + board->setY(0); + board->setZ(0); + board->setSize(235-2*offset,200-2*offset); + board->show(); + + //the table + QImage tablebg(Resource::loadImage("backgammon/table/"+table_name)); + if(non_qte) + { + tablebg=tablebg.copy(offset,0,235-offset,200); + } + table=new CanvasImageItem(tablebg,area); + table->setX(0); + table->setY(200-2*offset); + table->setZ(0); + table->setSize(235-2*offset,20); + table->show(); + + //the no move marker + QImage nomovebg(Resource::loadImage("backgammon/no_move")); + nomove_marker=new CanvasImageItem(nomovebg,area); + nomove_marker->setX(0); + nomove_marker->setY(200); + nomove_marker->setZ(2); + nomove_marker->hide(); + + //default human against computer + player1_auto=false; + player2_auto=true; + //start new game + newgame(); +} + +BackGammon::~BackGammon() +{ + //DESTRUCTOR +} + +void BackGammon::newgame() +{ + gameFinished=false; + QDateTime now=QDateTime::currentDateTime(); + game_name=now.date().toString()+"_"+now.time().toString(); + move->reset(); + draw(); + diceA1_value=7; + diceA2_value=7; + diceA3_value=7; + diceA4_value=7; + diceB1_value=7; + diceB2_value=7; + diceB3_value=7; + diceB4_value=7; + showdice(); + player=2; + dice1_played=true; + dice2_played=true; + dice3_played=true; + dice4_played=true; + dice_rolled=false; + setplayer(); + area->update(); +} + +void BackGammon::playerselect() +{ + PlayerDialog* playerdialog=new PlayerDialog(this); + playerdialog->setAuto1(player1_auto); + playerdialog->setAuto2(player2_auto); + if(!playerdialog->exec()) + return; + player1_auto=playerdialog->getAuto1(); + player2_auto=playerdialog->getAuto2(); +} + +void BackGammon::loadgame() +{ + FileDialog* file=new FileDialog(this,"Load Game",".game"); + if(!file->exec()) + return; + + game_name=file->filename(); + QString game_file=QPEApplication::qpeDir()+"/backgammon/"+game_name+".game"; + + Config game(game_file,Config::File); + game.setGroup("dice"); + diceA1_value=game.readNumEntry("diceA1_value"); + diceA2_value=game.readNumEntry("diceA2_value"); + diceA3_value=game.readNumEntry("diceA3_value"); + diceA4_value=game.readNumEntry("diceA4_value"); + diceB1_value=game.readNumEntry("diceB1_value"); + diceB2_value=game.readNumEntry("diceB2_value"); + diceB3_value=game.readNumEntry("diceB3_value"); + diceB4_value=game.readNumEntry("diceB4_value"); + player=game.readNumEntry("player"); + dice1_played=game.readBoolEntry("dice1_played"); + dice2_played=game.readBoolEntry("dice2_played"); + dice3_played=game.readBoolEntry("dice3_played"); + dice4_played=game.readBoolEntry("dice4_played"); + dice_rolled=game.readBoolEntry("dice_rolled"); + player1_auto=game.readBoolEntry("player1_auto"); + player2_auto=game.readBoolEntry("player2_auto"); + + game.setGroup("pieces"); + QString label; + LoadSave load; + for(int a=0;a<28;a++) + { + label.setNum(a); + load.pop[a].total = game.readNumEntry(label,0); + } + + move->loadGame(load); + setplayer(); + showdice(); + draw(); + area->update(); +} + +void BackGammon::savegame() +{ + QString game_file=QPEApplication::qpeDir()+"/backgammon/"+game_name+".game"; + + Config game(game_file,Config::File); + game.setGroup("dice"); + game.writeEntry("diceA1_value",diceA1_value); + game.writeEntry("diceA2_value",diceA2_value); + game.writeEntry("diceA3_value",diceA3_value); + game.writeEntry("diceA4_value",diceA4_value); + game.writeEntry("diceB1_value",diceB1_value); + game.writeEntry("diceB2_value",diceB3_value); + game.writeEntry("diceB3_value",diceB4_value); + game.writeEntry("diceB4_value",diceB4_value); + game.writeEntry("player",player); + game.writeEntry("dice1_played",dice1_played); + game.writeEntry("dice2_played",dice2_played); + game.writeEntry("dice3_played",dice3_played); + game.writeEntry("dice4_played",dice4_played); + game.writeEntry("dice_rolled",dice_rolled); + game.writeEntry("player1_auto",player1_auto); + game.writeEntry("player2_auto",player2_auto); + + game.setGroup("pieces"); + QString label; + LoadSave save=move->saveGame(); + for(int a=0;a<28;a++) + { + label.setNum(a); + game.writeEntry(label,save.pop[a].total); + } + QMessageBox::information(this,"Backgammon","Game saved","OK"); +} + +void BackGammon::deletegame() +{ + FileDialog* file=new FileDialog(this,"Delete Game",".game"); + if(!file->exec()) + return; + + game_name=file->filename(); + QString game_file=QPEApplication::qpeDir()+"/backgammon/"+game_name+".game"; + + if(!QMessageBox::warning(this,"Backgammon","deleted game\n"+game_name+" ?","OK","Cancel")) + { + QFile(game_file).remove(); + } +} + + +void BackGammon::newtheme() +{ + ThemeDialog* theme=new ThemeDialog(this); + + ImageNames names; + names.theme=theme_name; + names.board=board_name; + names.pieces1=piecesA_name; + names.pieces2=piecesB_name; + names.dice1=diceA_name; + names.dice2=diceB_name; + names.odds=odds_name; + names.table=table_name; + + theme->setCurrent(names); + if(!theme->exec()) + return; + + names=theme->getNames(); + theme_name=names.theme; + board_name=names.board; + piecesA_name=names.pieces1; + piecesB_name=names.pieces2; + diceA_name=names.dice1; + diceB_name=names.dice2; + odds_name=names.odds; + table_name=names.table; + + applytheme(); +} + +void BackGammon::loadtheme() +{ + FileDialog* file=new FileDialog(this,"Load Theme",".theme"); + if(!file->exec()) + return; + + theme_name=file->filename(); + QString theme_file=QPEApplication::qpeDir()+"/backgammon/"+theme_name+".theme"; + + Config theme(theme_file,Config::File); + theme.setGroup("theme"); + board_name=theme.readEntry("board","board_1"); + piecesA_name=theme.readEntry("pieces1","pieces_1"); + piecesB_name=theme.readEntry("pieces2","pieces_2"); + diceA_name=theme.readEntry("dice1","dice_1"); + diceB_name=theme.readEntry("dice2","dice_2"); + table_name=theme.readEntry("table","table_1"); + odds_name=theme.readEntry("odds","odds_1"); + + applytheme(); + +} + +void BackGammon::savetheme() +{ + if(theme_name=="default") + { + QMessageBox::information(this,"Backgammon","Sorry\nCannot overwrite default.theme","OK"); + return; + } + QString theme_file=QPEApplication::qpeDir()+"/backgammon/"+theme_name+".theme"; + if(QMessageBox::information(this,"Backgammon","Save Theme\n"+theme_name,"Yes","No")) + return; + + Config theme(theme_file,Config::File); + theme.setGroup("theme"); + theme.writeEntry("board",board_name); + theme.writeEntry("pieces1",piecesA_name); + theme.writeEntry("pieces2",piecesB_name); + theme.writeEntry("dice1",diceA_name); + theme.writeEntry("dice2",diceB_name); + theme.writeEntry("table",table_name); + theme.writeEntry("odds",odds_name); + +} + +void BackGammon::themedefault() +{ + if(QMessageBox::information(this,"Backgammon","Make Theme\n"+theme_name+"\nthe default theme","Yes","No")) + return; + + Config conf("backgammon"); + conf.setGroup("general"); + conf.writeEntry("theme",theme_name); +} + +void BackGammon::deletetheme() +{ + FileDialog* file=new FileDialog(this,"Delete Theme",".theme"); + if(!file->exec()) + return; + + theme_name=file->filename(); + QString theme_file=QPEApplication::qpeDir()+"/backgammon/"+theme_name+".theme"; + + if(!QMessageBox::warning(this,"Backgammon","deleted theme "+theme_name+" ?","OK","Cancel")) + { + QFile(theme_file).remove(); + } +} + +void BackGammon::modify_AI() +{ + AI_Dialog* ai_mod=new AI_Dialog(this,"Load Theme",".theme"); + ai_mod->setAISettings(move->getAISettings()); + if(!ai_mod->exec()) + return; + + //get the AI settings + AISettings ai=ai_mod->getAISettings(); + move->setAISettings(ai); + //write new settings to conf file + Config conf("backgammon"); + conf.setGroup("ai"); + conf.writeEntry("rescue",ai.rescue); + conf.writeEntry("eliminate",ai.eliminate); + conf.writeEntry("expose",ai.expose); + conf.writeEntry("protect",ai.protect); + conf.writeEntry("safe",ai.safe); + conf.writeEntry("empty",ai.empty); +} + +void BackGammon::setrules() +{ + RulesDialog* rulesdialog=new RulesDialog(this,"Load Theme",".theme"); + rulesdialog->setRules(rules); + if(!rulesdialog->exec()) + return; + rules=rulesdialog->getRules(); + Config conf("backgammon"); + conf.setGroup("rules"); + conf.writeEntry("move_with_pieces_out",rules.move_with_pieces_out); + conf.writeEntry("nice_dice",rules.generous_dice); + move->setRules(rules); +} + +void BackGammon::displaySettings() +{ + DisplayDialog* displaydialog=new DisplayDialog(this); + displaydialog->setDisplaySettings(display); + if(!displaydialog->exec()) + return; + display=displaydialog->getDisplaySettings(); + Config conf("backgammon"); + conf.setGroup("display"); + conf.writeEntry("small",display.small); + conf.writeEntry("warning",display.warning); + QMessageBox::warning(this,"Backgammon","changed display settings will\nonly take place after game has\nbeen restarted","OK"); +} + +void BackGammon::draw() +{ + Pieces pieces; + move->position(pieces,non_qte); + for(int a=0;a<15;a++) + { + if(!pieces.player1[a].side) + { + p1[a]->setX(pieces.player1[a].x); + p1[a]->setY(pieces.player1[a].y); + p1[a]->setZ(pieces.player1[a].z); + p1[a]->show(); + p1_side[a]->hide(); + } + else + { + p1_side[a]->setX(pieces.player1[a].x); + p1_side[a]->setY(pieces.player1[a].y); + p1_side[a]->setZ(pieces.player1[a].z); + p1_side[a]->show(); + p1[a]->hide(); + } + + if(!pieces.player2[a].side) + { + p2[a]->setX(pieces.player2[a].x); + p2[a]->setY(pieces.player2[a].y); + p2[a]->setZ(pieces.player2[a].z); + p2[a]->show(); + p2_side[a]->hide(); + } + else + { + p2_side[a]->setX(pieces.player2[a].x); + p2_side[a]->setY(pieces.player2[a].y); + p2_side[a]->setZ(pieces.player2[a].z); + p2_side[a]->show(); + p2[a]->hide(); + } + } +} + +void BackGammon::mouse(int x,int y) +{ + if(gameFinished) + { + newgame(); + return; + } + if(y<=200) //move pieces + { + if((player==1 && player1_auto) || (player==2 && player2_auto)) + return; + + Marker marker; + + move->boardpressed(x,y,marker,non_qte); + if(marker.visible_current) + { + marker_current->setX(marker.x_current-offset); + marker_current->setY(marker.y_current); + marker_current->show(); + } + else + { + marker_current->hide(); + } + + for(int a=0;a<4;a++) + { + if(marker.visible_next[a]) + { + marker_next[a]->setX(marker.x_next[a]-offset); + marker_next[a]->setY(marker.y_next[a]); + marker_next[a]->show(); + } + else + { + marker_next[a]->hide(); + } + } + area->update(); + } + else //roll dice + { + if(x>=10 && x<=65 && player==1 && !dice_rolled) + { + dice1_played=false; + dice2_played=false; + dice3_played=false; + dice4_played=false; + dice_rolled=true; + srand(QTime::currentTime().msec()); + diceA1_value=1+(int) (6.0*rand()/(RAND_MAX+1.0)); + diceA2_value=1+(int) (6.0*rand()/(RAND_MAX+1.0)); + if(diceA1_value==diceA2_value) + { + diceA3_value=diceA1_value; + diceA4_value=diceA1_value; + } + else + { + diceA3_value=7; + dice3_played=true; + diceA4_value=7; + dice4_played=true; + } + showdice(); + area->update(); + move->diceroll(1,diceA1_value,diceA2_value,diceA3_value,diceA4_value,player1_auto); + + } + else if(x>=160 && x<=225 && player==2 && !dice_rolled) + { + dice1_played=false; + dice2_played=false; + dice3_played=false; + dice4_played=false; + dice_rolled=true; + srand(QTime::currentTime().msec()); + diceB1_value=1+(int) (6.0*rand()/(RAND_MAX+1.0)); + diceB2_value=1+(int) (6.0*rand()/(RAND_MAX+1.0)); + if(diceB1_value==diceB2_value) + { + diceB3_value=diceB1_value; + diceB4_value=diceB1_value; + } + else + { + diceB3_value=7; + dice3_played=true; + diceB4_value=7; + dice4_played=true; + } + showdice(); + area->update(); + move->diceroll(2,diceB1_value,diceB2_value,diceB3_value,diceB4_value,player2_auto); + } + } +} + +void BackGammon::done_dice1() +{ + dice1_played=true; + if(player==1) + diceA1_value=7; + else + diceB1_value=7; + setplayer(); + showdice(); + draw(); + area->update(); + if(!dice2_played || !dice3_played || !dice4_played) + { + if(player==1) + { + move->diceroll(1,diceA1_value,diceA2_value,diceA3_value,diceA4_value,player1_auto); + } + else + { + move->diceroll(2,diceB1_value,diceB2_value,diceB3_value,diceB4_value,player2_auto); + } + } +} + +void BackGammon::done_dice2() +{ + dice2_played=true; + if(player==1) + diceA2_value=7; + else + diceB2_value=7; + setplayer(); + showdice(); + draw(); + area->update(); + if(!dice1_played || !dice3_played || !dice4_played) + { + if(player==1) + { + move->diceroll(1,diceA1_value,diceA2_value,diceA3_value,diceA4_value,player1_auto); + } + else + { + move->diceroll(2,diceB1_value,diceB2_value,diceB3_value,diceB4_value,player2_auto); + } + } +} + + +void BackGammon::done_dice3() +{ + dice3_played=true; + if(player==1) + diceA3_value=7; + else + diceB3_value=7; + setplayer(); + showdice(); + draw(); + area->update(); + if(!dice1_played || !dice2_played || !dice4_played) + { + if(player==1) + { + move->diceroll(1,diceA1_value,diceA2_value,diceA3_value,diceA4_value,player1_auto); + } + else + { + move->diceroll(2,diceB1_value,diceB2_value,diceB3_value,diceB4_value,player2_auto); + } + } +} + + +void BackGammon::done_dice4() +{ + dice4_played=true; + if(player==1) + diceA4_value=7; + else + diceB4_value=7; + setplayer(); + showdice(); + draw(); + area->update(); + if(!dice1_played || !dice2_played || !dice3_played) + { + if(player==1) + { + move->diceroll(1,diceA1_value,diceA2_value,diceA3_value,diceA4_value,player1_auto); + } + else + { + move->diceroll(2,diceB1_value,diceB2_value,diceB3_value,diceB4_value,player2_auto); + } + } +} + + +void BackGammon::nomove() +{ + if(player==1) + nomove_marker->setX(0); + else + nomove_marker->setX(170); + nomove_marker->show(); + message->setText("<b>no move</b>"); + dice1_played=true; + dice2_played=true; + dice3_played=true; + dice4_played=true; + if(player==1) + { + diceA1_value=7; + diceA2_value=7; + diceA3_value=7; + diceA4_value=7; + } + else + { + diceB1_value=7; + diceB2_value=7; + diceB3_value=7; + diceB4_value=7; + } + area->update(); + QTimer::singleShot(2000,this,SLOT(nomove2())); +} + +void BackGammon::nomove2() +{ + nomove_marker->hide(); + setplayer(); + showdice(); + draw(); + area->update(); +} + +void BackGammon::finished(int theplayer) +{ + nomove_marker->hide(); + if(theplayer==1) + message->setText("<b>Player 1 wins. Click on board for new game.</b>"); + else + message->setText("<b>Player 2 wins. Click on board for new game.</b>"); + diceA1_value=7; + diceA2_value=7; + diceB1_value=7; + diceB2_value=7; + player=0; + showdice(); + draw(); + area->update(); + gameFinished=true; +} + +void BackGammon::showdice() +{ + int value_diceA1=diceA1_value-1; + if(diceA1_value==7 && diceA3_value!=7) + value_diceA1=diceA3_value-1; + + int value_diceA2=diceA2_value-1; + if(diceA2_value==7 && diceA4_value!=7) + value_diceA2=diceA4_value-1; + + int value_diceB1=diceB1_value-1; + if(diceB1_value==7 && diceB3_value!=7) + value_diceB1=diceB3_value-1; + + int value_diceB2=diceB2_value-1; + if(diceB2_value==7 && diceB4_value!=7) + value_diceB2=diceB4_value-1; + + for(int index=0;index<7;index++) + { + if(value_diceA1==index) + diceA1[index]->show(); + else + diceA1[index]->hide(); + + if(value_diceA2==index) + diceA2[index]->show(); + else + diceA2[index]->hide(); + + if(value_diceB1==index) + diceB1[index]->show(); + else + diceB1[index]->hide(); + + if(value_diceB2==index) + diceB2[index]->show(); + else + diceB2[index]->hide(); + } +} + +void BackGammon::setplayer() +{ + if(dice1_played && dice2_played && dice3_played && dice4_played && player==1) + { + message->setText("<b>P2 turn</b>"); + dice_rolled=false; + player=2; + if(player2_auto) + QTimer::singleShot(2000,this,SLOT(autoroll_dice2())); + } + else if(dice1_played && dice2_played && dice3_played && dice4_played && player==2) + { + message->setText("<b>P1 turn</b>"); + dice_rolled=false; + player=1; + if(player1_auto) + QTimer::singleShot(2000,this,SLOT(autoroll_dice1())); + } +} + +void BackGammon::autoroll_dice1() +{ + mouse(20,210); +} + +void BackGammon::autoroll_dice2() +{ + mouse(170,210); +} + +void BackGammon::applytheme() +{ + QImage boardbg(Resource::loadImage("backgammon/boards/"+board_name)); + if(non_qte) + { + boardbg=boardbg.copy(offset,offset,235-2*offset,200-2*offset); + } + board->setImage(boardbg); + + QImage tablebg(Resource::loadImage("backgammon/table/"+table_name)); + if(non_qte) + { + tablebg=tablebg.copy(offset,0,235-offset,200); + } + table->setImage(tablebg); + + QImage piece_1_all(Resource::loadImage("backgammon/pieces/"+piecesA_name)); + QImage piece_1_front=piece_1_all.copy(0,0,15,15); + QImage piece_1_side=piece_1_all.copy(0,15,15,5); + + QImage piece_2_all(Resource::loadImage("backgammon/pieces/"+piecesB_name)); + QImage piece_2_front=piece_2_all.copy(0,0,15,15); + QImage piece_2_side=piece_2_all.copy(0,15,15,5); + + int a=0; + for(a=0;a<15;a++) + { + p1[a]->setImage(piece_1_front); + p1_side[a]->setImage(piece_1_side); + + p2[a]->setImage(piece_2_front); + p2_side[a]->setImage(piece_2_side); + } + draw(); + + QImage dicebgA_all(Resource::loadImage("backgammon/dice/"+diceA_name)); + QImage dicebgB_all(Resource::loadImage("backgammon/dice/"+diceB_name)); + QImage oddsbg_all=(Resource::loadImage("backgammon/odds/"+odds_name)); + + for(a=0;a<7;a++) + { + QImage dicebgA=dicebgA_all.copy(a*25,0,25,25); + diceA1[a]->setImage(dicebgA); + diceA2[a]->setImage(dicebgA); + + QImage dicebgB=dicebgB_all.copy(a*25,0,25,25); + diceB1[a]->setImage(dicebgB); + diceB2[a]->setImage(dicebgB); + /* + if(a<6) + { + QImage oddsbg=oddsbg_all.copy(a*15,0,15,15); + oddsDice[a]->setImage(oddsbg); + } + */ + } +} + + diff --git a/noncore/games/backgammon/backgammon.h b/noncore/games/backgammon/backgammon.h new file mode 100644 index 0000000..40dbaba --- a/dev/null +++ b/noncore/games/backgammon/backgammon.h @@ -0,0 +1,134 @@ +#ifndef BACKGAMMON_H +#define BACKGAMMON_H + +#include "canvasimageitem.h" +#include "definition.h" +//#include "rulesdialog.h" +#include "moveengine.h" + +#include <qcanvas.h> +#include <qlabel.h> +#include <qlineedit.h> +#include <qwidget.h> + + +class BackGammonView : public QCanvasView +{ + Q_OBJECT +public: + BackGammonView(QCanvas* canvas,QWidget* parent); + ~BackGammonView(); +signals: + void mouse(int,int); +private: + void contentsMousePressEvent(QMouseEvent* e); +}; + +class BackGammon : public QWidget +{ + Q_OBJECT +private: + //GUI + //is the style not qte ? + bool non_qte; + int offset; + //the "status" bar + QLineEdit* inputfield; + //the main drawing area + QCanvas* area; + BackGammonView* boardview; + CanvasImageItem* board; + CanvasImageItem* table; + CanvasImageItem** p1; + CanvasImageItem** p2; + CanvasImageItem** p1_side; + CanvasImageItem** p2_side; + + CanvasImageItem** diceA1; + CanvasImageItem** diceA2; + CanvasImageItem** diceB1; + CanvasImageItem** diceB2; + //CanvasImageItem** oddsDice; + CanvasImageItem* nomove_marker; + + QCanvasRectangle* marker_current; + QCanvasRectangle* marker_next[4]; + QLabel* message; + //ENGINE + MoveEngine* move; + //the dice values + int diceA1_value; + int diceA2_value; + int diceA3_value; + int diceA4_value; + int diceB1_value; + int diceB2_value; + int diceB3_value; + int diceB4_value; + + int player; + bool dice1_played; + bool dice2_played; + bool dice3_played; + bool dice4_played; + bool dice_rolled; + //computer opponent + bool player1_auto; + bool player2_auto; + + //the images; + QString theme_name; + QString board_name; + QString piecesA_name; + QString piecesB_name; + QString diceA_name; + QString diceB_name; + QString odds_name; + QString table_name; + + //save game + QString game_name; + + //the rules + Rules rules; + + //display settings + Display display; + //is the game finished ? + bool gameFinished; + +public: + BackGammon( QWidget* parent = 0, const char* name = 0, WFlags fl = 0 ); + ~BackGammon(); +private slots: + void newgame(); + void playerselect(); + void loadgame(); + void savegame(); + void deletegame(); + void newtheme(); + void loadtheme(); + void savetheme(); + void themedefault(); + void deletetheme(); + void modify_AI(); + void setrules(); + void displaySettings(); + void mouse(int x,int y); + void done_dice1(); + void done_dice2(); + void done_dice3(); + void done_dice4(); + void nomove(); + void nomove2(); + void finished(int theplayer); + void autoroll_dice1(); + void autoroll_dice2(); +private: + void draw(); + void showdice(); + void setplayer(); + void applytheme(); +}; + +#endif //BACKGAMMON_H diff --git a/noncore/games/backgammon/backgammon.pro b/noncore/games/backgammon/backgammon.pro new file mode 100644 index 0000000..6f77a14 --- a/dev/null +++ b/noncore/games/backgammon/backgammon.pro @@ -0,0 +1,34 @@ +TEMPLATE = app +CONFIG = qt warn_on release + +HEADERS = backgammon.h \ + canvasimageitem.h \ + themedialog.h \ + moveengine.h \ + filedialog.h \ + playerdialog.h \ + aidialog.h \ + rulesdialog.h \ + displaydialog.h \ + definition.h + +SOURCES = main.cpp \ + backgammon.cpp \ + canvasimageitem.cpp \ + themedialog.cpp \ + moveengine.cpp \ + filedialog.cpp \ + playerdialog.cpp \ + aidialog.cpp \ + rulesdialog.cpp \ + displaydialog.cpp \ + definition.cpp + +TARGET = backgammon +INCLUDEPATH += $(OPIEDIR)/include +DEPENDPATH += $(OPIEDIR)/include +LIBS += -lqpe -lstdc++ +DESTDIR = $(OPIEDIR)/bin + + +include ( $(OPIEDIR)/include.pro ) diff --git a/noncore/games/backgammon/backgammonview.cpp b/noncore/games/backgammon/backgammonview.cpp new file mode 100644 index 0000000..ecbc12b --- a/dev/null +++ b/noncore/games/backgammon/backgammonview.cpp @@ -0,0 +1,17 @@ +#include "backgammonview.h" + +BackGammonView::BackGammonView(QCanvas* canvas,QWidget* parent) + :QCanvasView(canvas,parent) +{ +} + +BackGammonView::~BackGammonView() +{ +} + +void BackGammonView::contentsMousePressEvent(QMouseEvent* e) +{ + int x=e->x(); + int y=e->y(); + //emit mousepressed(x,y); +}
\ No newline at end of file diff --git a/noncore/games/backgammon/backgammonview.h b/noncore/games/backgammon/backgammonview.h new file mode 100644 index 0000000..e50f2b0 --- a/dev/null +++ b/noncore/games/backgammon/backgammonview.h @@ -0,0 +1,18 @@ +#ifndef BACKGAMMONVIEW_H +#define BACKGAMMONVIEW_H + +#include <qcanvas.h> + +class BackGammonView : public QCanvasView +{ + Q_OBJECT +public: + BackGammonView(QCanvas* canvas,QWidget* parent); + ~BackGammonView(); +signals: + //void mousepressed(int,int); +private: + void contentsMousePressEvent(QMouseEvent* e); +}; + +#endif //BACKGAMMONVIEW_H
\ No newline at end of file diff --git a/noncore/games/backgammon/canvasimageitem.cpp b/noncore/games/backgammon/canvasimageitem.cpp new file mode 100644 index 0000000..8d0297c --- a/dev/null +++ b/noncore/games/backgammon/canvasimageitem.cpp @@ -0,0 +1,23 @@ +#include "canvasimageitem.h" + +CanvasImageItem::CanvasImageItem( QImage img, QCanvas *canvas ) + : QCanvasRectangle( canvas ) +{ + image=img; + setSize( image.width(), image.height() ); +} + +CanvasImageItem::~CanvasImageItem() +{} + + + +void CanvasImageItem::drawShape( QPainter &p ) +{ + p.drawImage( int(x()), int(y()), image, 0, 0, -1, -1, OrderedAlphaDither ); +} + +void CanvasImageItem::setImage(QImage newImage) +{ + image=newImage; +} diff --git a/noncore/games/backgammon/canvasimageitem.h b/noncore/games/backgammon/canvasimageitem.h new file mode 100644 index 0000000..60d5498 --- a/dev/null +++ b/noncore/games/backgammon/canvasimageitem.h @@ -0,0 +1,21 @@ +#ifndef CNAVASIMAGEITEM_H +#define CNAVASIMAGEITEM_H + +#include <qcanvas.h> +#include <qimage.h> + + +class CanvasImageItem: public QCanvasRectangle +{ +private: + QImage image; +public: + CanvasImageItem( QImage img, QCanvas *canvas ); + ~CanvasImageItem(); +protected: + void drawShape( QPainter & ); +public: + void setImage(QImage newImage); +}; + +#endif //CNAVASIMAGEITEM_H diff --git a/noncore/games/backgammon/config.in b/noncore/games/backgammon/config.in new file mode 100644 index 0000000..c725fcc --- a/dev/null +++ b/noncore/games/backgammon/config.in @@ -0,0 +1,4 @@ + config BACKGAMMON + boolean "backgammon" + default "y" + depends ( LIBQPE || LIBQPE-X11 ) && LIBOPIE diff --git a/noncore/games/backgammon/definition.cpp b/noncore/games/backgammon/definition.cpp new file mode 100644 index 0000000..9e0029d --- a/dev/null +++ b/noncore/games/backgammon/definition.cpp @@ -0,0 +1,3 @@ +#include "definition.h" + +static bool debug=false; diff --git a/noncore/games/backgammon/definition.h b/noncore/games/backgammon/definition.h new file mode 100644 index 0000000..6a23801 --- a/dev/null +++ b/noncore/games/backgammon/definition.h @@ -0,0 +1,74 @@ +#ifndef DEFINITION_H +#define DEFINITION_H + + +struct Coord +{ + int x; + int y; + int z; + bool side; +}; + +struct Pieces +{ + Coord player1[15]; + Coord player2[15]; +}; + +struct Population +{ + //positive = player 1 + //negative = player 2 + //zero = no pieces + int total; +}; + +struct Marker +{ + int x_current; + int y_current; + bool visible_current; + + int x_next[4]; + int y_next[4]; + bool visible_next[4]; +}; + +struct LoadSave +{ + Population pop[28]; +}; + +struct Possiblilites +{ + int weight[4]; + int to[4]; +}; + +struct AISettings +{ + int rescue; + int eliminate; + int expose; + int protect; + int safe; + int empty; +}; + +struct Rules +{ + bool move_with_pieces_out; + bool generous_dice; +}; + + +struct Display +{ + bool small; + bool warning; +}; + + + +#endif //DEFINITION_H diff --git a/noncore/games/backgammon/displaydialog.cpp b/noncore/games/backgammon/displaydialog.cpp new file mode 100644 index 0000000..8b97545 --- a/dev/null +++ b/noncore/games/backgammon/displaydialog.cpp @@ -0,0 +1,89 @@ +#include "displaydialog.h" + +#include <qgroupbox.h> +#include <qlabel.h> + +DisplayDialog::DisplayDialog(QWidget* parent,const char* name,bool modal,WFlags f) + : QDialog(parent,name,modal,f) +{ + setCaption("Display Configuration"); + QLabel* header=new QLabel("<b>Change the display settings</b>",this); + header->setGeometry(10,10,200,20); + + // + QGroupBox* settings_frame=new QGroupBox("Settings",this); + settings_frame->setGeometry(10,10,220,120); + + small_box=new QRadioButton("Big display, e.g. for QPE Style",settings_frame); + small_box->setGeometry(10,20,200,20); + connect(small_box,SIGNAL(clicked()),this,SLOT(small_clicked())); + + big_box=new QRadioButton("Small display, e.g. for Windows Style",settings_frame); + big_box->setGeometry(10,50,200,20); + connect(big_box,SIGNAL(clicked()),this,SLOT(big_clicked())); + + // + QGroupBox* warning_frame=new QGroupBox("Warning",this); + warning_frame->setGeometry(10,140,220,120); + + warning_box=new QCheckBox("show style warning",warning_frame); + warning_box->setGeometry(10,20,200,20); + connect(warning_box,SIGNAL(clicked()),this,SLOT(warning_clicked())); + + QLabel* warning_help=new QLabel("show style warning at statup if the system style is not QPE\nif not set to small you may have\nscrollbars on the palying area",warning_frame); + warning_help->setGeometry(10,50,200,60); + + showMaximized(); +} + + +DisplayDialog::~DisplayDialog() +{ +} + +void DisplayDialog::big_clicked() +{ + big_box->setChecked(true); + small_box->setChecked(false); +} + +void DisplayDialog::small_clicked() +{ + big_box->setChecked(false); + small_box->setChecked(true); +} + +void DisplayDialog::warning_clicked() +{ +} + +void DisplayDialog::setDisplaySettings(const Display& display) +{ + if(!display.small) + { + big_box->setChecked(false); + small_box->setChecked(true); + } + else + { + big_box->setChecked(true); + small_box->setChecked(false); + } + if(display.warning) + warning_box->setChecked(true); + else + warning_box->setChecked(false); + +} + +Display DisplayDialog::getDisplaySettings() +{ + Display display; + display.small=!small_box->isChecked(); + display.warning=warning_box->isChecked(); + return display; +} + + + + diff --git a/noncore/games/backgammon/displaydialog.h b/noncore/games/backgammon/displaydialog.h new file mode 100644 index 0000000..26b77f0 --- a/dev/null +++ b/noncore/games/backgammon/displaydialog.h @@ -0,0 +1,30 @@ +#ifndef DISPLAYDLAOG_H +#define DISPLAYDLAOG_H + +#include <qcheckbox.h> +#include <qdialog.h> +#include <qradiobutton.h> + +#include "definition.h" + + +class DisplayDialog : public QDialog +{ + Q_OBJECT +private: + QRadioButton* small_box; + QRadioButton* big_box; + QCheckBox* warning_box; +public: + DisplayDialog(QWidget* parent=0,const char* name=0,bool modal=TRUE,WFlags f=0); + ~DisplayDialog(); +private slots: + void big_clicked(); + void small_clicked(); + void warning_clicked(); +public: + void setDisplaySettings(const Display& display); + Display getDisplaySettings(); +}; + +#endif //DISPLAYDLAOG_H diff --git a/noncore/games/backgammon/filedialog.cpp b/noncore/games/backgammon/filedialog.cpp new file mode 100644 index 0000000..6c858a2 --- a/dev/null +++ b/noncore/games/backgammon/filedialog.cpp @@ -0,0 +1,64 @@ +#include "filedialog.h" + +#include <qdir.h> +#include <qfileinfo.h> +#include <qmessagebox.h> +#include <qpixmap.h> +#include <qpushbutton.h> +#include <qpe/qpeapplication.h> + +FileDialog::FileDialog(QWidget* parent,QString header,QString extension,const char* name,bool modal,WFlags f) + :QDialog(parent,name,modal,f) +{ + setCaption(header); + ext=extension; + dirselector=new QListView(this); + dirselector->setGeometry(1,10,235,200); + dirselector->addColumn("Files"); + connect(dirselector,SIGNAL(clicked(QListViewItem*)),this,SLOT(selectorclicked(QListViewItem*))); + + getCurrentDir(); + + file_name="user"; + fileinput=new QLineEdit(file_name,this); + fileinput->setGeometry(1,220,235,20); + showMaximized(); +} + +FileDialog::~FileDialog() +{} + + +void FileDialog::selectorclicked(QListViewItem* entry) +{ + if(entry==NULL) + return; + file_name=entry->text(0); + fileinput->setText(file_name); +} + +void FileDialog::getCurrentDir() +{ + dirselector->clear(); + QDir dir(QPEApplication::qpeDir()+"/backgammon"); + dir.setFilter(QDir::Files); + QFileInfoListIterator it(*(dir.entryInfoList())); + QFileInfo* fi; + + int ext_length=ext.length(); + while((fi=it.current())) // go through all file and subdirs + { + QString file=fi->fileName(); + if(file.right(ext_length)==ext && file) + { + file=file.left(file.length()-ext_length); + new QListViewItem(dirselector,file); + } + ++it; + } +} + +QString FileDialog::filename() +{ + return file_name; +} diff --git a/noncore/games/backgammon/filedialog.h b/noncore/games/backgammon/filedialog.h new file mode 100644 index 0000000..2dfa557 --- a/dev/null +++ b/noncore/games/backgammon/filedialog.h @@ -0,0 +1,30 @@ +#ifndef FILEWIDGET_H +#define FILEWIDGET_H + +#include <qdialog.h> +#include <qlineedit.h> +#include <qlistview.h> +#include <qstring.h> + + +class FileDialog : public QDialog +{ + Q_OBJECT +private: + QListView* dirselector; + QLineEdit* fileinput; + QString ext; + QString file_name; + +public: + FileDialog(QWidget* parent,QString header,QString extension,const char* name=0,bool modal=TRUE,WFlags f=0); + ~FileDialog(); +private slots: + void selectorclicked(QListViewItem* entry); +private: + void getCurrentDir(); +public: + QString filename(); +}; + +#endif //FILEWIDGET_H diff --git a/noncore/games/backgammon/main.cpp b/noncore/games/backgammon/main.cpp new file mode 100644 index 0000000..86b452d --- a/dev/null +++ b/noncore/games/backgammon/main.cpp @@ -0,0 +1,14 @@ +#include <qpe/qpeapplication.h> +#include "backgammon.h" + + +int main( int argc, char** argv ) +{ + QPEApplication app( argc, argv ); + + BackGammon* view= new BackGammon(); + app.showMainWidget(view); + + return app.exec(); +} + diff --git a/noncore/games/backgammon/moveengine.cpp b/noncore/games/backgammon/moveengine.cpp new file mode 100644 index 0000000..009c449 --- a/dev/null +++ b/noncore/games/backgammon/moveengine.cpp @@ -0,0 +1,558 @@ +#include "moveengine.h" + +#include <qmessagebox.h> + +#include <qtimer.h> + +MoveEngine::MoveEngine() + : QObject() +{ + int offset=7; + int a=0; //counter variable + int xfill[]={210,185,170,155,140,125,110,85,70,55,40,25,10,10,25,40,55,70,85,110,125,140,155,170,185,210}; + for(a=0;a<26;a++) + { + x_coord[a]=xfill[a]; + } + + int yfill[]={10,25,40,55,70,10+offset,25+offset,40+offset,55+offset,25,40,55, 25+offset,40+offset,40}; + int zfill[]={1,1,1,1,1,2,2,2,2,3,3,3,4,4,5}; + for(a=0;a<15;a++) + { + yup_coord[a]=yfill[a]; + ylow_coord[a]=185-(yfill[a]); + z_coord[a]=zfill[a]; + } + for(a=0;a<5;a++) + { + if(a<3) + { + x_fin1[a]=65+a*15; + x_fin2[a]=155-a*15; + } + y_fin[a]=225-a*5; + } + z_fin=1; + + reset(); +} + +MoveEngine::~MoveEngine() +{} + +void MoveEngine::position(Pieces& pieces,bool non_qte) +{ + int player1_counter=0; + int player2_counter=0; + + //non qte styles are smaller !! + int offset=(non_qte) ? 5 : 0; + + for(int a=0;a<28;a++) + { + for(int b=0;b<abs(population[a].total);b++) + { + if(population[a].total>0) //player 1 pieces + { + pieces.player1[player1_counter].x=x_coord[a]-offset; + if(a>=0 && a<13) + { + pieces.player1[player1_counter].y=yup_coord[b]-offset; + pieces.player1[player1_counter].z=z_coord[b]; + pieces.player1[player1_counter].side=false; + player1_counter++; + } + else if(a>12 && a<26) + { + pieces.player1[player1_counter].y=ylow_coord[b]-offset; + pieces.player1[player1_counter].z=z_coord[b]; + pieces.player1[player1_counter].side=false; + player1_counter++; + } + else if(a==26) + { + if(b<5) + { + pieces.player1[player1_counter].x=x_fin1[0]-offset; + pieces.player1[player1_counter].y=y_fin[b]-offset; + pieces.player1[player1_counter].z=z_fin; + } + else if(b>=5 && b<10) + { + pieces.player1[player1_counter].x=x_fin1[1]-offset; + pieces.player1[player1_counter].y=y_fin[b-5]-offset; + pieces.player1[player1_counter].z=z_fin; + } + else + { + pieces.player1[player1_counter].x=x_fin1[2]-offset; + pieces.player1[player1_counter].y=y_fin[b-10]-offset; + pieces.player1[player1_counter].z=z_fin; + } + pieces.player1[player1_counter].side=true; + player1_counter++; + + } + } + + else if(population[a].total<0) //player 2 pieces + { + pieces.player2[player2_counter].x=x_coord[a]-offset; + if(a>=0 && a<13) + { + pieces.player2[player2_counter].y=yup_coord[b]-offset; + pieces.player2[player2_counter].z=z_coord[b]; + pieces.player2[player2_counter].side=false; + player2_counter++; + } + else if(a>12 && a<26) + { + pieces.player2[player2_counter].y=ylow_coord[b]-offset; + pieces.player2[player2_counter].z=z_coord[b]; + pieces.player2[player2_counter].side=false; + player2_counter++; + } + else if(a==27) + { + if(b<5) + { + pieces.player2[player2_counter].x=x_fin2[0]-offset; + pieces.player2[player2_counter].y=y_fin[b]-offset; + pieces.player2[player2_counter].z=z_fin; + } + else if(b>=5 && b<10) + { + pieces.player2[player2_counter].x=x_fin2[1]-offset; + pieces.player2[player2_counter].y=y_fin[b-5]-offset; + pieces.player2[player2_counter].z=z_fin; + } + else + { + pieces.player2[player2_counter].x=x_fin2[2]-offset; + pieces.player2[player2_counter].y=y_fin[b-10]-offset; + pieces.player2[player2_counter].z=z_fin; + } + pieces.player2[player2_counter].side=true; + player2_counter++; + + } + } + } + } +} + +void MoveEngine::diceroll(const int& newplayer,const int& face1,const int& face2,const int& face3,const int& face4,bool computer) +{ + checkstate(); + player=newplayer; + otherplayer=(player==1) ? 2 : 1; + dice[0]=face1; + dice[1]=face2; + dice[2]=face3; + dice[3]=face4; + marker_current=-1; + if(getPossibleMoves()==0) + { + emit nomove(); + return; // player will be changed + } + if(!computer) + return; //human intervention required + + QTimer::singleShot(2000,this,SLOT(automove())); +} + + +void MoveEngine::automove() +{ + //the maximimum possibility + int maxpos=0; + //the position in the moves array + int from=-1; + int to=-1; + //dice1 or dice 2 ?? + int index_dice=0; + for(int counter=0;counter<26;counter++) + { + int a=(player==1) ? counter : 25-counter; + for(int b=0;b<4;b++) + { + if(moves[a].weight[b]>maxpos) + { + maxpos=moves[a].weight[b]; + from=a; + to=moves[a].to[b]; + index_dice=b+1; + } + } + } + move(from,to,index_dice); +} + + +void MoveEngine::boardpressed(const int& x,const int& y,Marker& marker,bool non_qte) +{ + //get the position of the mouse click + bool upper=true; + bool found=false; + + int offset=(non_qte) ? 5 : 0; + + if(y<=85) // board slots 0 to 12 + marker.y_current=0; + else if(y>=105) //board slots 13 to 25 + { + marker.y_current=195-2*offset; + upper=false; + } + + int index=13; // the clicked board slot + + while(index<25 && !found) + { + if(x>=x_coord[index] && x<x_coord[index+1]) + { + marker.x_current=x_coord[index]; + found=true; + ; + } + else + { + index++; + } + } + if(!found) + { + marker.x_current=x_coord[25]; + index=25; + } + if(upper) + { + index=25-index; + } + + int a=0; + int usedice=-1; + int dice_value=7; + for(a=0;a<4;a++) + { + if(index==marker_next[a] && marker_next[a]!=-1 && dice_value>dice[a]) + { + usedice=a; + dice_value=dice[0]; + } + } + if(usedice!=-1) + { + move(marker_current,marker_next[usedice],usedice+1); + nomarker(marker); + return; + + } + + + if(dice[0]==7 && dice[1]==7 && dice[2]==7 && dice[3]==7) //no dice rolled + { + nomarker(marker); + return; + } + else if(fieldColor(index)==player) + { + marker.visible_current=true; + marker_current=index; + } + else + { + nomarker(marker); + return; + } + + for(a=0;a<4;a++) + { + if(moves[index].weight[a]>0) + { + int nextfield=moves[index].to[a]; + marker.x_next[a]=x_coord[nextfield]; + marker_next[a]=nextfield; + if(nextfield<13) //upper half + marker.y_next[a]=0; + else //lower half + marker.y_next[a]=195-2*offset; + marker.visible_next[a]=true; + } + else + { + marker.x_next[a]=0; + marker.y_next[a]=0; + marker_next[a]=-1; + marker.visible_next[a]=false; + } + } + return; +} + +void MoveEngine::reset() +{ + int a=0; + for(a=0;a<28;a++) + { + population[a].total=0; + } + + int p1_index[]={1,1,12,12,12,12,12,17,17,17,19,19,19,19,19}; + int p2_index[]={24,24,13,13,13,13,13,8,8,8,6,6,6,6,6}; + //int p1_index[]={19,20,21,22,22,23,23,18,18,23,24,24,24,24,24}; + //int p2_index[]={6,5,4,3,3,2,2,2,2,2,1,7,7,1,1}; + for(a=0;a<15;a++) + { + population[p1_index[a]].total++; + population[p2_index[a]].total--; + } + + player=0; + dice[0]=7; + dice[1]=7; + dice[2]=7; + dice[3]=7; + + marker_current=-1; + marker_next[0]=-1; + marker_next[1]=-1; + marker_next[2]=-1; + marker_next[3]=-1; + //allclear[0]==false; + allclear[1]=false; + allclear[2]=false; + last_piece[1]=0; + last_piece[2]=25; +} + +void MoveEngine::loadGame(const LoadSave& load) +{ + for(int a=0;a<28;a++) + { + population[a].total=load.pop[a].total; + } + checkstate(); +} + +LoadSave MoveEngine::saveGame() +{ + LoadSave save; + for(int a=0;a<28;a++) + { + save.pop[a].total=population[a].total; + } + return save; +} + +AISettings MoveEngine::getAISettings() +{ + return ai; +} + +void MoveEngine::setAISettings(const AISettings& new_ai) +{ + ai=new_ai; +} + +void MoveEngine::setRules(Rules rules) +{ + move_with_pieces_out=rules.move_with_pieces_out; + nice_dice=rules.generous_dice; +} + + +int MoveEngine::getPossibleMoves() +{ + int homezone[]={0,25,0}; + int lastToHomeZone=abs(last_piece[player]-homezone[player]); + for(int field=0;field<26;field++) + { + + for(int b=0;b<4;b++) + { + int dice_tmp=dice[b]; + if(dice[b]!=7 && dice[b]> lastToHomeZone) + dice_tmp=lastToHomeZone; + + int nextfield=(player==1) ? field+dice_tmp : field-dice_tmp; + + if(nice_dice) + { + if(player==1 && nextfield>homezone[1]) + nextfield=homezone[1]; + else if(player==2 && nextfield<homezone[2]) + nextfield=homezone[2]; + } + + moves[field].weight[b]=0; + moves[field].to[b]=nextfield; + + int out_of_board[]={-1,0,25}; + if(!move_with_pieces_out && field!=out_of_board[player] && pieces_out[player]) + { + continue; + } + + + + if(dice[b]!=7 && fieldColor(field)==player ) //player can only move his own pieces + { + if((player==1 && nextfield > homezone[1]) || (player==2 && nextfield < homezone[2])) + { + moves[field].weight[b]=0; //movement would be far out of board + } + else if(nextfield==homezone[player] && !allclear[player]) + { + moves[field].weight[b]=0; //can not rescue pieces until all are in the endzone + } + else if(nextfield==homezone[player] && allclear[player]) + { + moves[field].weight[b]=ai.rescue; //rescue your pieces : nuff said ;-) + } + else if(fieldColor(nextfield)==otherplayer) + { + if(abs(population[nextfield].total)>1) //can not move to this field + moves[field].weight[b]=0; + else if(abs(population[nextfield].total)==1) //eliminate opponent : very nice + moves[field].weight[b]=ai.eliminate; + } + else if(fieldColor(nextfield)==player) //nextfield already occupied by player + { + if(abs(population[field].total)==2) //expose own piece : not diserable + moves[field].weight[b]=ai.expose; + else if(abs(population[nextfield].total)>1) //own pices already there : safe + moves[field].weight[b]=ai.safe; + else if(abs(population[nextfield].total)==1) //protect own piece : most importatnt + moves[field].weight[b]=ai.protect; + } + else if(population[nextfield].total==0) //nextfield empty + { + if(abs(population[field].total)==2) //expose own piece : not diserable + moves[field].weight[b]=ai.expose; + else + moves[field].weight[b]=ai.empty; + } + else + moves[field].weight[b]=0; //default. + } + + + + else + moves[field].weight[b]=0; //dice already used or field not used by player + } + + + + } + + int total=0; + for(int field=0;field<26;field++) + { + total+=moves[field].weight[0]+moves[field].weight[1]+moves[field].weight[2]+moves[field].weight[3]; + } + return total; +} + +void MoveEngine::move(const int& from, int to, const int& dice) +{ + //qDebug("%d moves from %d to %d (%d) with dice %d",player,from,to,to-from,dice); + + if(player==1 && to==25) + to=26; + if(player==2 && to==0) + to=27; + + //if space is occupied by enemy move pieces to startzone + if(fieldColor(to)==otherplayer) + { + population[to].total=0; + if(otherplayer==1) + population[0].total++; + else + population[25].total--; + } + + if(player==1) + { + population[from].total--; + population[to].total++; + } + else //player=2 + { + population[from].total++; + population[to].total--; + } + + if(dice==1) + emit done_dice1(); + else if(dice==2) + emit done_dice2(); + else if(dice==3) + emit done_dice3(); + else + emit done_dice4(); + + if(abs(population[26].total)==15) + emit player_finished(1); + if(abs(population[27].total)==15) + emit player_finished(2); +} + +void MoveEngine::checkstate() +{ + //check if pieces are out + pieces_out[1]=(population[0].total>0) ? true : false; + pieces_out[2]=(population[25].total<0) ? true : false; + + //check if all pieces are in the endzones + allclear[1]=true; + allclear[2]=true; + + last_piece[1]=25; + bool found_last_piece1=false; + last_piece[2]=0; + + for(int a=0;a<26;a++) + { + if(a<19 && population[a].total>0) + allclear[1]=false; + if(a>6 && population[a].total<0) + allclear[2]=false; + + if(population[a].total>0 && !found_last_piece1) + { + last_piece[1]=a; + found_last_piece1=true; + } + if(population[a].total<0) + last_piece[2]=a; + } +} + +void MoveEngine::nomarker(Marker& marker) +{ + marker.visible_current=false; + marker_current=-1; + for(int a=0;a<4;a++) + { + marker.x_next[a]=0; + marker.y_next[a]=0; + marker_next[a]=-1; + marker.visible_next[a]=false; + } +} + +int MoveEngine::fieldColor(const int& index) const +{ + if(population[index].total>0) + return 1; + else if(population[index].total<0) + return 2; + else + return 0; +} + + diff --git a/noncore/games/backgammon/moveengine.h b/noncore/games/backgammon/moveengine.h new file mode 100644 index 0000000..a2d4a52 --- a/dev/null +++ b/noncore/games/backgammon/moveengine.h @@ -0,0 +1,76 @@ +#ifndef MOVEENGINE_H +#define MOVEENGINE_H + +#include <qobject.h> +#include "definition.h" + +class MoveEngine : public QObject +{ + Q_OBJECT +private: + //normal pieses + int x_coord[26]; //26 posssible x-positions or piece is not on the board + int yup_coord[15]; // the 15 posssible y-positions on the upper half of the board + int ylow_coord[15]; // the 15 posssible y-positions on the lower half of the board + int z_coord[15]; //the 15 possible z-positionson the board + //finshed pieces + int x_fin1[3]; + int x_fin2[3]; + int y_fin[5]; + int z_fin; + //the board population + // |12|11|10|09|08|07|06|05|04|03|02|01|00| + // ======================================= + // |13|14|15|16|17|18|19|20|21|22|23|24|25| + // endzones 26 player1, 27 player 2 + Population population[28]; + AISettings ai; + //move information + int player; + int otherplayer; + int dice[4]; + //index of the markers + int marker_current; + int marker_next[4]; + //player pieces are all in the end zone + bool allclear[3]; + //player must bring pieces back into game + bool pieces_out[3]; + bool move_with_pieces_out; + //player can rescue pieces with dice bigger than move, even if there are poeces "behind" it + bool nice_dice; + int last_piece[3]; + //possible moves + Possiblilites moves[26]; +public: +public: + MoveEngine(); + ~MoveEngine(); +signals: + void done_dice1(); + void done_dice2(); + void done_dice3(); + void done_dice4(); + void nomove(); + void player_finished(int); +private slots: + void automove(); +public: + void position(Pieces& pieces,bool non_qte=false); + void diceroll(const int& player,const int& face1,const int& face2,const int& face3,const int& face4,bool computer); + void boardpressed(const int& x,const int& y,Marker& marker,bool non_qte=false); + void reset(); + void loadGame(const LoadSave& load); + LoadSave saveGame(); + AISettings getAISettings(); + void setAISettings(const AISettings& new_ai); + void setRules(Rules rules); +private: + int getPossibleMoves(); + void move(const int& from, int to, const int& dice); + void checkstate(); + void nomarker(Marker& marker); + int fieldColor(const int& index) const; +}; + +#endif //MOVEENGINE_H diff --git a/noncore/games/backgammon/playerdialog.cpp b/noncore/games/backgammon/playerdialog.cpp new file mode 100644 index 0000000..c16f202 --- a/dev/null +++ b/noncore/games/backgammon/playerdialog.cpp @@ -0,0 +1,114 @@ +#include "playerdialog.h" + +#include <qgroupbox.h> + +PlayerDialog::PlayerDialog(QWidget* parent,const char* name,bool modal,WFlags f) + :QDialog(parent,name,modal,f) +{ + auto2=false; + auto2=true; + setCaption("Player Settings"); + + QGroupBox* player1_box=new QGroupBox("Player 1",this); + player1_box->setGeometry(10,30,220,60); + + manual_button1=new QRadioButton("Human",player1_box); + connect(manual_button1,SIGNAL(clicked()),this,SLOT(button_manual1())); + manual_button1->setGeometry(10,20,100,20); + auto_button1=new QRadioButton("Computer",player1_box); + connect(auto_button1,SIGNAL(clicked()),this,SLOT(button_auto1())); + auto_button1->setGeometry(110,20,100,20); + button1_state(auto1); + + QGroupBox* player2_box=new QGroupBox("Player 2",this); + player2_box->setGeometry(10,150,220,60); + + manual_button2=new QRadioButton("Human",player2_box); + connect(manual_button2,SIGNAL(clicked()),this,SLOT(button_manual2())); + manual_button2->setGeometry(10,20,100,20); + auto_button2=new QRadioButton("Computer",player2_box); + connect(auto_button2,SIGNAL(clicked()),this,SLOT(button_auto2())); + auto_button2->setGeometry(110,20,100,20); + button2_state(auto2); + + showMaximized(); +} + +PlayerDialog::~PlayerDialog() +{} + + +void PlayerDialog::button_manual1() +{ + auto1=false; + button1_state(auto1); +} + +void PlayerDialog::button_auto1() +{ + auto1=true; + button1_state(auto1); +} + +void PlayerDialog::button_manual2() +{ + auto2=false; + button2_state(auto2); +} + +void PlayerDialog::button_auto2() +{ + auto2=true; + button2_state(auto2); +} + +void PlayerDialog::button1_state(bool computer) +{ + if(computer) + { + manual_button1->setChecked(false); + auto_button1->setChecked(true); + } + else + { + manual_button1->setChecked(true); + auto_button1->setChecked(false); + } +} + +void PlayerDialog::button2_state(bool computer) +{ + if(computer) + { + manual_button2->setChecked(false); + auto_button2->setChecked(true); + } + else + { + manual_button2->setChecked(true); + auto_button2->setChecked(false); + } +} + + +void PlayerDialog::setAuto1(bool newstate) +{ + auto1=newstate; + button1_state(auto1); +} + +bool PlayerDialog::getAuto1() +{ + return auto1; +} + +void PlayerDialog::setAuto2(bool newstate) +{ + auto2=newstate; + button2_state(auto2); +} + +bool PlayerDialog::getAuto2() +{ + return auto2; +} diff --git a/noncore/games/backgammon/playerdialog.h b/noncore/games/backgammon/playerdialog.h new file mode 100644 index 0000000..8fccaa7 --- a/dev/null +++ b/noncore/games/backgammon/playerdialog.h @@ -0,0 +1,35 @@ +#ifndef PLAYERDIALOG_H +#define PLAYERDIALOG_H + +#include <qradiobutton.h> +#include <qdialog.h> + +class PlayerDialog : public QDialog +{ + Q_OBJECT +private: + bool auto1; + bool auto2; + QRadioButton* manual_button1; + QRadioButton* auto_button1; + QRadioButton* manual_button2; + QRadioButton* auto_button2; +public: + PlayerDialog(QWidget* parent=0,const char* name=0,bool modal=TRUE,WFlags f=0); + ~PlayerDialog(); +private slots: + void button_manual1(); + void button_auto1(); + void button_manual2(); + void button_auto2(); +private: + void button1_state(bool computer); + void button2_state(bool computer); +public: + void setAuto1(bool newstate); + bool getAuto1(); + void setAuto2(bool newstate); + bool getAuto2(); +}; + +#endif //PLAYERDIALOG_H diff --git a/noncore/games/backgammon/rulesdialog.cpp b/noncore/games/backgammon/rulesdialog.cpp new file mode 100644 index 0000000..85c3db3 --- a/dev/null +++ b/noncore/games/backgammon/rulesdialog.cpp @@ -0,0 +1,77 @@ +#include "rulesdialog.h" + +#include <qgroupbox.h> +#include <qlabel.h> + +RulesDialog::RulesDialog(QWidget* parent,const char* name,bool modal,WFlags f) + : QDialog(parent,name,modal,f) +{ + setCaption("Rules Configuration"); + QLabel* header=new QLabel("<b>Change the game rules here</b>",this); + header->setGeometry(10,10,200,20); + + // + QGroupBox* pieces_out_box=new QGroupBox("Movement",this); + pieces_out_box->setGeometry(10,10,220,120); + + pieces_out=new QCheckBox("Don't care about others",pieces_out_box); + pieces_out->setGeometry(10,20,200,20); + connect(pieces_out,SIGNAL(clicked()),this,SLOT(pieces_out_clicked())); + + QLabel* pieces_out_help=new QLabel("allow movement of the pieses\neven if there are pieces knocked\nout by the opponent",pieces_out_box); + pieces_out_help->setGeometry(10,40,200,60); + + // + QGroupBox* nice_dice_box=new QGroupBox("Dice",this); + nice_dice_box->setGeometry(10,140,220,120); + + nice_dice=new QCheckBox("Big dice for small numbers",nice_dice_box); + nice_dice->setGeometry(10,20,200,20); + connect(nice_dice,SIGNAL(clicked()),this,SLOT(nice_dice_clicked())); + + QLabel* nice_dice_help=new QLabel("allow to rescue pieces with dice\nvalues graeter than the distance\nto the players endzone.",nice_dice_box); + nice_dice_help->setGeometry(10,40,200,60); + + showMaximized(); +} + + +RulesDialog::~RulesDialog() +{ +} + +void RulesDialog::pieces_out_clicked() +{ + if(pieces_out->isChecked()) + rules.move_with_pieces_out=true; + else + rules.move_with_pieces_out=false; +} + +void RulesDialog::nice_dice_clicked() +{ + if(nice_dice->isChecked()) + rules.generous_dice=true; + else + rules.generous_dice=false; +} + +void RulesDialog::setRules(const Rules& new_rules) +{ + rules=new_rules; + if(rules.move_with_pieces_out) + pieces_out->setChecked(true); + else + pieces_out->setChecked(false); + + if(rules.generous_dice) + nice_dice->setChecked(true); + else + nice_dice->setChecked(false); +} + +Rules RulesDialog::getRules() +{ + return rules; +} + diff --git a/noncore/games/backgammon/rulesdialog.h b/noncore/games/backgammon/rulesdialog.h new file mode 100644 index 0000000..9269a0e --- a/dev/null +++ b/noncore/games/backgammon/rulesdialog.h @@ -0,0 +1,27 @@ +#ifndef RULESDIALOG_H_ +#define RULESDIALOG_H_ + +#include <qcheckbox.h> +#include <qdialog.h> +#include "definition.h" + + +class RulesDialog : public QDialog +{ + Q_OBJECT +private: + QCheckBox* pieces_out; + QCheckBox* nice_dice; + Rules rules; +public: + RulesDialog(QWidget* parent=0,const char* name=0,bool modal=TRUE,WFlags f=0); + ~RulesDialog(); +private slots: + void pieces_out_clicked(); + void nice_dice_clicked(); +public: + void setRules(const Rules& new_rules); + Rules getRules(); +}; + +#endif //RULESDIALOG_H diff --git a/noncore/games/backgammon/themedialog.cpp b/noncore/games/backgammon/themedialog.cpp new file mode 100644 index 0000000..dcb957c --- a/dev/null +++ b/noncore/games/backgammon/themedialog.cpp @@ -0,0 +1,163 @@ +#include "themedialog.h" + +#include <qdir.h> +#include <qfileinfo.h> +#include <qlabel.h> +#include <qpushbutton.h> +#include <qpe/qpeapplication.h> + + +ThemeDialog::ThemeDialog(QWidget* parent,const char* name,bool modal,WFlags f) + :QDialog(parent,name,modal,f) +{ + setCaption("Theme Dialog"); + QLabel* labelname=new QLabel("name",this); + labelname->setGeometry(0,5,40,20); + lineName=new QLineEdit("user",this); + lineName->setGeometry(40,5,195,20); + + QLabel* labelboard=new QLabel("board",this); + labelboard->setGeometry(0,30,40,20); + boxboard=new QComboBox(this,""); + boxboard->setGeometry(40,30,195,20); + fillBox("boards",boxboard); + + QLabel* labelpiecesA=new QLabel("pieces1",this); + labelpiecesA->setGeometry(0,70,40,20); + boxpiecesA=new QComboBox(this); + boxpiecesA->setGeometry(40,70,195,20); + fillBox("pieces",boxpiecesA); + + QLabel* labelpiecesB=new QLabel("pieces2",this); + labelpiecesB->setGeometry(0,95,40,20); + boxpiecesB=new QComboBox(this); + boxpiecesB->setGeometry(40,95,195,20); + fillBox("pieces",boxpiecesB); + + QLabel* labeldiceA=new QLabel("dice1",this); + labeldiceA->setGeometry(0,135,40,20); + boxdiceA=new QComboBox(this); + boxdiceA->setGeometry(40,135,195,20); + fillBox("dice",boxdiceA); + + QLabel* labeldiceB=new QLabel("dice2",this); + labeldiceB->setGeometry(0,160,40,20); + boxdiceB=new QComboBox(this); + boxdiceB->setGeometry(40,160,195,20); + fillBox("dice",boxdiceB); + + QLabel* labelodds=new QLabel("odds",this); + labelodds->setGeometry(0,200,40,20); + boxodds=new QComboBox(this); + boxodds->setGeometry(40,200,195,20); + fillBox("odds",boxodds); + boxodds->setEnabled(false); + + QLabel* labeltable=new QLabel("table",this); + labeltable->setGeometry(0,225,40,20); + boxtable=new QComboBox(this); + boxtable->setGeometry(40,225,195,20); + fillBox("table",boxtable); + + showMaximized(); +} + +ThemeDialog::~ThemeDialog() +{} + + +ImageNames ThemeDialog::getNames() +{ + ImageNames names; + names.theme=lineName->text(); + names.board=boxboard->currentText(); + names.pieces1=boxpiecesA->currentText(); + names.pieces2=boxpiecesB->currentText(); + names.dice1=boxdiceA->currentText(); + names.dice2=boxdiceB->currentText(); + names.odds=boxodds->currentText(); + names.table=boxtable->currentText(); + return names; +} + +void ThemeDialog::setCurrent(const ImageNames& current) +{ + int a=0; + lineName->setText(current.theme); + for(a=0;a<boxboard->count();a++) + { + if(boxboard->text(a)==current.board) + { + boxboard->setCurrentItem(a); + break; + } + } + for(a=0;a<boxpiecesA->count();a++) + { + if(boxpiecesA->text(a)==current.pieces1) + { + boxpiecesA->setCurrentItem(a); + break; + } + } + for(a=0;a<boxpiecesB->count();a++) + { + if(boxpiecesB->text(a)==current.pieces2) + { + boxpiecesB->setCurrentItem(a); + break; + } + } + for(a=0;a<boxdiceA->count();a++) + { + if(boxdiceA->text(a)==current.dice1) + { + boxdiceA->setCurrentItem(a); + break; + } + } + for(a=0;a<boxdiceB->count();a++) + { + if(boxdiceB->text(a)==current.dice2) + { + boxdiceB->setCurrentItem(a); + break; + } + } + for(a=0;a<boxodds->count();a++) + { + if(boxodds->text(a)==current.odds) + { + boxodds->setCurrentItem(a); + break; + } + } + for(a=0;a<boxtable->count();a++) + { + if(boxtable->text(a)==current.table) + { + boxtable->setCurrentItem(a); + break; + } + } +} + +void ThemeDialog::fillBox(QString dirname,QComboBox* thebox) +{ + thebox->clear(); + QDir dir(QPEApplication::qpeDir()+"/pics/backgammon/"+dirname); + dir.setFilter(QDir::Dirs | QDir::Files); + QFileInfoListIterator it(*(dir.entryInfoList())); + QFileInfo* fi; + + while((fi=it.current())) // go through all file and subdirs + { + QString file=fi->fileName(); + if(file.right(4)==".png") + { + thebox->insertItem(file.left(file.find(".png"))); + } + ++it; + } + delete fi; +} diff --git a/noncore/games/backgammon/themedialog.h b/noncore/games/backgammon/themedialog.h new file mode 100644 index 0000000..45a61f2 --- a/dev/null +++ b/noncore/games/backgammon/themedialog.h @@ -0,0 +1,42 @@ +#ifndef THEMEDIALOG_H +#define THEMEDIALOG_H + +#include <qcombobox.h> +#include <qdialog.h> +#include <qlineedit.h> + +struct ImageNames +{ + QString theme; + QString board; + QString pieces1; + QString pieces2; + QString dice1; + QString dice2; + QString odds; + QString table; +}; + +class ThemeDialog : public QDialog +{ + Q_OBJECT +private: + QLineEdit* lineName; + QComboBox* boxboard; + QComboBox* boxpiecesA; + QComboBox* boxpiecesB; + QComboBox* boxdiceA; + QComboBox* boxdiceB; + QComboBox* boxodds; + QComboBox* boxtable; +public: + ThemeDialog(QWidget* parent=0,const char* name=0,bool modal=TRUE,WFlags f=0); + ~ThemeDialog(); +public: + ImageNames getNames(); + void setCurrent(const ImageNames& current); +private: + void fillBox(QString dirname,QComboBox* thebox); +}; + +#endif //THEMEDIALOG_H diff --git a/pics/backgammon/backgammon.png b/pics/backgammon/backgammon.png Binary files differnew file mode 100644 index 0000000..762994e --- a/dev/null +++ b/pics/backgammon/backgammon.png diff --git a/pics/backgammon/boards/casino_board_1.png b/pics/backgammon/boards/casino_board_1.png Binary files differnew file mode 100644 index 0000000..2e5bbaf --- a/dev/null +++ b/pics/backgammon/boards/casino_board_1.png diff --git a/pics/backgammon/dice/casino_dice.png b/pics/backgammon/dice/casino_dice.png Binary files differnew file mode 100755 index 0000000..4dfc9c9 --- a/dev/null +++ b/pics/backgammon/dice/casino_dice.png diff --git a/pics/backgammon/no_move.png b/pics/backgammon/no_move.png Binary files differnew file mode 100755 index 0000000..5dcf479 --- a/dev/null +++ b/pics/backgammon/no_move.png diff --git a/pics/backgammon/odds/casino_odds.png b/pics/backgammon/odds/casino_odds.png Binary files differnew file mode 100644 index 0000000..92cf4b7 --- a/dev/null +++ b/pics/backgammon/odds/casino_odds.png diff --git a/pics/backgammon/pieces/casino_pieces_blue.png b/pics/backgammon/pieces/casino_pieces_blue.png Binary files differnew file mode 100755 index 0000000..cf70960 --- a/dev/null +++ b/pics/backgammon/pieces/casino_pieces_blue.png diff --git a/pics/backgammon/pieces/casino_pieces_white.png b/pics/backgammon/pieces/casino_pieces_white.png Binary files differnew file mode 100755 index 0000000..c23b6e6 --- a/dev/null +++ b/pics/backgammon/pieces/casino_pieces_white.png diff --git a/pics/backgammon/table/casino_table_green.png b/pics/backgammon/table/casino_table_green.png Binary files differnew file mode 100644 index 0000000..003e0d4 --- a/dev/null +++ b/pics/backgammon/table/casino_table_green.png |