diff --git a/plugins/qsolocards_plugin/._.DS_Store b/plugins/qsolocards_plugin/._.DS_Store new file mode 100644 index 000000000..460d887a2 Binary files /dev/null and b/plugins/qsolocards_plugin/._.DS_Store differ diff --git a/plugins/qsolocards_plugin/._QSoloCards.icns b/plugins/qsolocards_plugin/._QSoloCards.icns new file mode 100644 index 000000000..f98f3396f Binary files /dev/null and b/plugins/qsolocards_plugin/._QSoloCards.icns differ diff --git a/plugins/qsolocards_plugin/About.cpp b/plugins/qsolocards_plugin/About.cpp new file mode 100644 index 000000000..4112ad3ee --- /dev/null +++ b/plugins/qsolocards_plugin/About.cpp @@ -0,0 +1,96 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "About.h" +#include +#include +#include +#include +#include +//////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////// +About::About(QWidget * pParent) + :QDialog(pParent) +{ + this->setWindowTitle(tr("About QSoloCards").trimmed()); + + // Layout the dialog a Vbox that will be the top level. And contain the HBox that has the icon and text + // and then the dialogButtonBox for the close button. + QVBoxLayout * pLayout=new QVBoxLayout; + + QHBoxLayout * pMainLayout=new QHBoxLayout; + + QLabel * pIconLabel=new QLabel(this); + + pIconLabel->setPixmap(QPixmap(":/images/sol128x128.png")); + + pMainLayout->addWidget(pIconLabel,0,Qt::AlignTop|Qt::AlignLeft); + + QLabel * pWordsLabel=new QLabel(this); + + pWordsLabel->setWordWrap(true); + + // set the text for the about box. The .pro file is setup to pass + // VER_MAJ, VER_MIN, VER_PAT as a param when the file is compiled + // So, version info is contained only in the .pro file and can be + // easily changed in one place. + pWordsLabel->setText(tr("

QSoloCards %1.%2.%3

" + "

A collection of Solitaire Games written in Qt.

" + "

" + "

" + "

Copyright 2009 Steve Moore

" + "

" + "

License: GPLv3

" + "

" + "

" + "

Graphics: Playing cards are a modified version of the anglo_bitmap cards from Gnome-Games' AisleRiot.

" + ).arg(QString::number(VER_MAJ)).arg(QString::number(VER_MIN)).arg(QString::number(VER_PAT))); + + connect(pWordsLabel,SIGNAL(linkActivated(QString)), + this,SLOT(slotLinkActivated(QString))); + + pMainLayout->addWidget(pWordsLabel,0,Qt::AlignTop|Qt::AlignHCenter); + + + pLayout->addLayout(pMainLayout,20); + + QDialogButtonBox * pButtonBox=new QDialogButtonBox(this); + + pButtonBox->addButton(QDialogButtonBox::Close); + + pLayout->addWidget(pButtonBox,1); + + connect(pButtonBox, SIGNAL(rejected()), this, SLOT(reject())); + + // don't allow resizing the window. + pLayout->setSizeConstraint(QLayout::SetFixedSize); + + this->setLayout(pLayout); +} +//////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////// +About::~About() +{ +} + +//////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////// +void About::slotLinkActivated(const QString & link) +{ + emit showLink(link); +} diff --git a/plugins/qsolocards_plugin/About.h b/plugins/qsolocards_plugin/About.h new file mode 100644 index 000000000..39fce3eb1 --- /dev/null +++ b/plugins/qsolocards_plugin/About.h @@ -0,0 +1,34 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef ABOUT_H +#define ABOUT_H +#include + +class About: public QDialog +{ + Q_OBJECT +public: + About(QWidget * pParent); + ~About(); +public slots: + void slotLinkActivated(const QString & link); +signals: + void showLink(const QString & link); +}; +#endif // ABOUT_H diff --git a/plugins/qsolocards_plugin/CardAnimationLock.cpp b/plugins/qsolocards_plugin/CardAnimationLock.cpp new file mode 100644 index 000000000..80ecd7949 --- /dev/null +++ b/plugins/qsolocards_plugin/CardAnimationLock.cpp @@ -0,0 +1,66 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "CardAnimationLock.h" +#include "CardStack.h" + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +CardAnimationLock::~CardAnimationLock() +{ +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +CardAnimationLock & CardAnimationLock::getInst() +{ + static CardAnimationLock aniLock; + + return aniLock; +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void CardAnimationLock::lock() +{ + if (m_aniEnabled && !m_demoStarted) + { + CardStack::lockUserInteration(); + emit animationStarted(); + } +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void CardAnimationLock::unlock() +{ + if (m_aniEnabled && !m_demoStarted) + { + CardStack::lockUserInteration(false); + emit animationComplete(); + } +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +CardAnimationLock::CardAnimationLock() + :m_aniEnabled(true), + m_demoStarted(false) +{ +} + diff --git a/plugins/qsolocards_plugin/CardAnimationLock.h b/plugins/qsolocards_plugin/CardAnimationLock.h new file mode 100644 index 000000000..30ef47338 --- /dev/null +++ b/plugins/qsolocards_plugin/CardAnimationLock.h @@ -0,0 +1,57 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef CARDANIMATIONLOCK_H +#define CARDANIMATIONLOCK_H + +#include + +class CardAnimationLock:public QObject +{ + Q_OBJECT +public: + virtual ~CardAnimationLock(); + + static CardAnimationLock & getInst(); + + inline void setDemoMode(bool isDemo){m_demoStarted=isDemo;} + inline bool isDemoRunning()const{return m_demoStarted;} + + inline bool animationsEnabled()const{return m_aniEnabled;} + inline void enableAnimations(bool enabled){m_aniEnabled=enabled;} + + // The lock just sends a single not to allow user interaction, + // and calls the static lockUserInteraction function of CardStack. + // The signal is used by mainwindow to know when not to allow menu + // items to be clicked. + void lock(); + void unlock(); + +signals: + void animationStarted(); + void animationComplete(); + +protected: + CardAnimationLock(); + +private: + bool m_aniEnabled; + bool m_demoStarted; +}; + +#endif diff --git a/plugins/qsolocards_plugin/CardDeck.cpp b/plugins/qsolocards_plugin/CardDeck.cpp new file mode 100644 index 000000000..7281de1cf --- /dev/null +++ b/plugins/qsolocards_plugin/CardDeck.cpp @@ -0,0 +1,123 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "CardDeck.h" + +#include + + +/////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////// +CardDeck::CardDeck(unsigned short numDecks) + :m_deckOfCards(), + m_shuffledCardVector(), + m_numDecks(numDecks) +{ + // This creates the default deck of cards that will be used + for (unsigned short i=0;ishuffle(); +} + +////////////////////////////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////////////////////////////// +CardDeck::CardDeck(const PlayingCardVector & cardsForDeck, unsigned short numDecks) + :m_deckOfCards(), + m_shuffledCardVector(), + m_numDecks(numDecks) +{ + for (unsigned short i=0;im_deckOfCards.push_back(cardsForDeck[j]); + } + } + + this->shuffle(); +} + +////////////////////////////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////////////////////////////// +CardDeck::~CardDeck() +{ +} + +////////////////////////////////////////////////////////////////////////////////////////////////////////// +// Create a shuffled deck by generating a vector of playing cards. And then randomly generating an index +// into that vector. And then pull the card out of that vector and adding it to the end of another vector. +// +////////////////////////////////////////////////////////////////////////////////////////////////////////// +void CardDeck::shuffle() +{ + PlayingCardVector cardVector; + + cardVector=this->m_deckOfCards; + + if (this->m_shuffledCardVector.size()>0) + { + this->m_shuffledCardVector.clear(); + } + + qsrand(QDateTime::currentDateTime().toTime_t()); + + + while(cardVector.size()>0) + { + unsigned int index=qrand()%cardVector.size(); + + // make sure our random number is not off the end of the vector + if (index>=cardVector.size()) + { + index=cardVector.size()-1; + } + + this->m_shuffledCardVector.push_back(cardVector[index]); + cardVector.erase(cardVector.begin()+index); + } +} + +////////////////////////////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////////////////////////////// +PlayingCard CardDeck::next() +{ + // create an invalid card. + PlayingCard playingCard(PlayingCard::MaxSuit,PlayingCard::MaxCardIndex); + + // if we have any cards left get the first one and return it. + // then remove that card from the vector. + if (this->m_shuffledCardVector.size()>0) + { + playingCard=this->m_shuffledCardVector[0]; + this->m_shuffledCardVector.erase(this->m_shuffledCardVector.begin()); + } + + return playingCard; +} diff --git a/plugins/qsolocards_plugin/CardDeck.h b/plugins/qsolocards_plugin/CardDeck.h new file mode 100644 index 000000000..47de6992d --- /dev/null +++ b/plugins/qsolocards_plugin/CardDeck.h @@ -0,0 +1,56 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef CARDDECK_H +#define CARDDECK_H + +#include + +#include "PlayingCard.h" + +typedef std::vector PlayingCardVector; + +class CardDeck +{ + public: + // by default we just want to include one complete deck. + CardDeck(unsigned short numDecks=1); + + // this constructor adds a little flexibility. So, that a deck of only certain cards + // can be built easily. + CardDeck(const PlayingCardVector & cardsForDeck, unsigned short numDecks=1); + ~CardDeck(); + + // will clear any remaining cards in the shuffled deck and create a new shuffled deck + // this function is automatically called by the constructor. + void shuffle(); + + inline bool isEmpty() const {return m_shuffledCardVector.empty();} + + // get the next card in the shuffled deck. + PlayingCard next(); + + private: + PlayingCardVector m_deckOfCards; + PlayingCardVector m_shuffledCardVector; + + unsigned short m_numDecks; +}; + + +#endif // CARDDECK_H diff --git a/plugins/qsolocards_plugin/CardMoveRecord.cpp b/plugins/qsolocards_plugin/CardMoveRecord.cpp new file mode 100644 index 000000000..0fc433bc3 --- /dev/null +++ b/plugins/qsolocards_plugin/CardMoveRecord.cpp @@ -0,0 +1,68 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "CardMoveRecord.h" + + +////////////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////////////// +CardMoveRecordItem::CardMoveRecordItem(const std::string & stackName, + int flipIndex) + :m_moveType(CardMoveRecordItem::FlipCard), + m_cardVector(), + m_flipIndex(flipIndex), + m_stackName(stackName) +{ +} + +////////////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////////////// +CardMoveRecordItem::CardMoveRecordItem(const std::string & stackName, + MoveType m_type, + const PlayingCardVector & cardVector) + :m_moveType(m_type), + m_cardVector(cardVector), + m_flipIndex(-1), + m_stackName(stackName) +{ +} + +////////////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////////////// +CardMoveRecordItem::CardMoveRecordItem(const CardMoveRecordItem & rh) +{ + *this=rh; +} + +////////////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////////////// +CardMoveRecordItem::~CardMoveRecordItem() +{ +} + +////////////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////////////// +CardMoveRecordItem & CardMoveRecordItem::operator=(const CardMoveRecordItem & rh) +{ + m_moveType=rh.moveType(); + m_cardVector=rh.cardVector(); + m_flipIndex=rh.flipIndex(); + m_stackName=rh.stackName(); + + return *this; +} diff --git a/plugins/qsolocards_plugin/CardMoveRecord.h b/plugins/qsolocards_plugin/CardMoveRecord.h new file mode 100644 index 000000000..2e15f372b --- /dev/null +++ b/plugins/qsolocards_plugin/CardMoveRecord.h @@ -0,0 +1,62 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef CARDMOVERECORD_H +#define CARDMOVERECORD_H + +#include "CardDeck.h" +#include +#include + +class CardMoveRecordItem +{ + public: + enum MoveType + { + AddCards=0, + RemoveCards=1, + FlipCard=2 + }; + + CardMoveRecordItem(const std::string & stackName, + int flipIndex=-1); // Case where we are just flipping a card + CardMoveRecordItem(const std::string & stackName, + MoveType m_type, + const PlayingCardVector & cardVector); // case where we are adding or removing cards + CardMoveRecordItem(const CardMoveRecordItem & rh); + + virtual ~CardMoveRecordItem(); + + CardMoveRecordItem & operator=(const CardMoveRecordItem & rh); + + inline MoveType moveType() const {return m_moveType;} + inline const PlayingCardVector & cardVector() const {return m_cardVector;} + inline int flipIndex() const {return m_flipIndex;} + inline const std::string & stackName() const{return m_stackName;} + + private: + MoveType m_moveType; + PlayingCardVector m_cardVector; + int m_flipIndex; + std::string m_stackName; +}; + +typedef std::list CardMoveRecord; + + +#endif // CARDMOVERECORD_H diff --git a/plugins/qsolocards_plugin/CardPixmaps.cpp b/plugins/qsolocards_plugin/CardPixmaps.cpp new file mode 100644 index 000000000..95090de82 --- /dev/null +++ b/plugins/qsolocards_plugin/CardPixmaps.cpp @@ -0,0 +1,193 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "CardPixmaps.h" +#include +#include + +const qreal CardPixmaps::CardWidthToHeight=.66; +const QString CardPixmaps::EmptyStackName("empty"); +const QString CardPixmaps::EmptyStackRedealName("emtpy_redeal"); +const QString CardPixmaps::CardBackName("back"); +const QString CardPixmaps::TransparentNoCard("transparent"); + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +CardPixmaps::~CardPixmaps() +{ + delete m_pSvgRendCard; +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +CardPixmaps & CardPixmaps::getInst() +{ + static CardPixmaps cardPixmaps; + + return cardPixmaps; +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +void CardPixmaps::setCardWidth(unsigned int width) +{ + m_cardSize.setWidth(width); + m_cardSize.setHeight(width/CardWidthToHeight); +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +void CardPixmaps::setCardHeight(unsigned int height) +{ + m_cardSize.setHeight(height); + m_cardSize.setWidth(height*CardWidthToHeight); +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +CardPixmaps::CardPixmaps() + :m_pSvgRendCard(new QSvgRenderer(QString(":/images/anglo_bitmap.svg"))), + m_pixmapMap(), + m_cardSize(0,0) +{ +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +const QPixmap & CardPixmaps::getCardPixmap(const QString & imageName,bool highlighted) +{ + QString fullImageName(""); + + if (highlighted) + { + fullImageName+="hl_"; + } + fullImageName+=imageName; + + CardPixmapMap::iterator it=m_pixmapMap.find(fullImageName.toStdString()); + + if (m_pixmapMap.end()!=it) + { + return it->second; + } + + QPainter painter; + + QPixmap dummyPix(m_cardSize); + + dummyPix.fill(Qt::transparent); + + m_pixmapMap[fullImageName.toStdString()]=dummyPix; + painter.begin(&m_pixmapMap[fullImageName.toStdString()]); + if (imageName==EmptyStackName || imageName==EmptyStackRedealName) + { + drawEmptyStack(painter,highlighted,imageName==EmptyStackRedealName); + } + else if (imageName==TransparentNoCard) + { + } + else if (highlighted) + { + drawHighlightedCard(painter,imageName); + } + else + { + QRect pixRect(QPoint(0,0),m_cardSize); + + m_pSvgRendCard->render(&painter,imageName,pixRect); + } + + painter.end(); + + return m_pixmapMap[fullImageName.toStdString()]; +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +void CardPixmaps::drawEmptyStack(QPainter & painter,bool highlighted,bool redealCircle) +{ + QPoint topLeft(0,0); + QPen pen; + + + pen.setColor(QColor("#006520")); + + pen.setWidth(3); + painter.setPen(pen); + + + QRect rect(topLeft,m_cardSize); + + painter.setRenderHint(QPainter::Antialiasing,true); + + + if (redealCircle) + { + QPoint ellipseCenter(rect.left()+rect.width()/2, + rect.top()+rect.height()/2); + + pen.setWidth(10); + painter.setBrush(QColor("#006520")); + painter.drawEllipse(ellipseCenter, + rect.width()/3,rect.width()/3); + } + + painter.setBrush(Qt::transparent); + + // draw the highlight rect if necessary. + if (highlighted) + { + painter.setBrush(QBrush(QColor("#806000"),Qt::Dense4Pattern)); + } + + painter.drawRoundedRect(rect.adjusted(1,1,-1,-1),6.0,6.0); +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +void CardPixmaps::drawHighlightedCard(QPainter & painter,const QString & imageName) +{ + // for the highlighted case we are going to manipulate the original + // image and change the background of the card to a yellowish color + // to highlight it. + + // A QImage is necessary in Format_ARGB32_Premultiplied or Format_ARGB32 + // is required to use the composite modes. So, draw the pixmap on the + // QImage. And then render the result in our pixmap. + + QRect pixRect(QPoint(0,0),m_cardSize); + + QImage image(m_cardSize,QImage::Format_ARGB32_Premultiplied); + + image.fill(Qt::transparent); + + QPainter imagePainter; + + imagePainter.begin(&image); + + imagePainter.setPen(Qt::NoPen); + + imagePainter.setBrush(QColor("#ffff90")); + imagePainter.drawPixmap(QPoint(0,0),getCardPixmap(imageName)); + + imagePainter.setCompositionMode(QPainter::CompositionMode_Darken); + imagePainter.drawRoundedRect(pixRect.adjusted(0,0,-1,-1),4.0,4.0); + + imagePainter.end(); + painter.drawImage(QPoint(0,0),image); +} diff --git a/plugins/qsolocards_plugin/CardPixmaps.h b/plugins/qsolocards_plugin/CardPixmaps.h new file mode 100644 index 000000000..47bce4f67 --- /dev/null +++ b/plugins/qsolocards_plugin/CardPixmaps.h @@ -0,0 +1,93 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef CARDPIXMAPS_H +#define CARDPIXMAPS_H + +#include "PlayingCard.h" +#include +#include +#include +#include + +typedef std::map CardPixmapMap; + + +class CardPixmaps +{ +public: + static const qreal CardWidthToHeight; // This is the percentage of the height to the width + // that is used to render a card. + + static const QString EmptyStackName; + static const QString EmptyStackRedealName; + static const QString CardBackName; + static const QString TransparentNoCard; + + ~CardPixmaps(); + + static CardPixmaps & getInst(); + + + void setCardWidth(unsigned int width); + void setCardHeight(unsigned int height); + + inline const QSize & getCardSize() {return m_cardSize;} + + inline void clearPixmapCache(){m_pixmapMap.clear();} + + // functions to make it easier to get card pixmaps. + const QPixmap & getCardPixmap(const PlayingCard & card,bool highlighted=false) + {return getCardPixmap(card.asString(),highlighted);} + + const QPixmap & getCardBackPixmap(bool highlighted=false) + {return getCardPixmap(CardBackName,highlighted);} + + const QPixmap & getTransparentPixmap() + {return getCardPixmap(TransparentNoCard);} + + // the redeal circle is just a circle in the middle of the empty stack that indicates that + // you can d-click on the stack to recycle the cards. Used in games like Klondike where + // can go through the flip stack multiple times + const QPixmap & getCardNonePixmap(bool highlighted=false,bool redealCircle=false) + {return getCardPixmap(redealCircle?EmptyStackRedealName:EmptyStackName,highlighted);} + + +protected: + CardPixmaps(); + +private: + const QPixmap & getCardPixmap(const QString & imageName, bool highlighted=false); + void drawEmptyStack(QPainter & painter,bool highlighted,bool redealCircle); + void drawHighlightedCard(QPainter & painter,const QString & imageName); + + + QSvgRenderer * m_pSvgRendCard; // the svg render will be created the first time + // it is needed. It has to be done after Qt is initialized. + // And we just want to create it once. Loading it is fairly + // expensive. + CardPixmapMap m_pixmapMap; // this is a map of cards that is built as a card is needed. + // It will also contain the card back. And highlighted + // versions of cards. + QSize m_cardSize; // this is the card size that is used for every card + // that is drawn. The height of a card is determined + // from the width. So, the value is set by calling + // setCardWidth. +}; + +#endif diff --git a/plugins/qsolocards_plugin/CardStack.cpp b/plugins/qsolocards_plugin/CardStack.cpp new file mode 100644 index 000000000..0e4e36325 --- /dev/null +++ b/plugins/qsolocards_plugin/CardStack.cpp @@ -0,0 +1,857 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "CardStack.h" +#include +#include +#include +#include +#include +#include +#include "CardPixmaps.h" +#include "CardAnimationLock.h" + +#include + +CardStackMap CardStack::m_cardStackMap; +bool CardStack::m_lockUserInteraction=false; + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +CardStack::CardStack() + :QObject(),QGraphicsPixmapItem(), + m_hintHighlightIndex(-1), + m_stackName(), + m_cardVector(), + m_highlighted(false), + m_showRedealCircle(false), + m_autoFaceUp(false), + m_mouseMoved(false), + m_dragStartPos(0,0), + m_flipAni(), + m_dragStack(this) +{ + // set the name of this stack and add it to the map of stacks. + m_stackName=QString::number((qlonglong)this); + m_cardStackMap[this->stackName()]=this; + + // accept drops and mouse hover events + this->setAcceptDrops(true); + this->setAcceptHoverEvents(true); + + this->setZValue(1); + + this->setCursor(Qt::PointingHandCursor); + this->setShapeMode(QGraphicsPixmapItem::BoundingRectShape); + + // call update stack to set the initial view of the stack as empty. + this->updateStack(); + + + this->connect(&m_flipAni,SIGNAL(flipComplete(CardStack *)), + this,SLOT(slotFlipComplete(CardStack *))); + + this->connect(&m_dragStack,SIGNAL(cardsMoved(const CardMoveRecord &)), + this,SLOT(slotDragCardsMoved(const CardMoveRecord &))); +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +CardStack::~CardStack() +{ + // remove the pointer from the map of stacks to the class. + m_cardStackMap.erase(this->stackName()); +} + + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +bool CardStack::allCardsFaceUp()const +{ + bool rc=true; + unsigned int i; + + for(i=0;im_cardVector.size();i++) + { + if (!this->m_cardVector[i].isFaceUp()) + { + rc=false; + break; + } + } + + return rc; +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +bool CardStack::cardsAscendingTopToBottom()const +{ + bool rc=true; + const PlayingCardVector & cardVector=this->getCardVector(); + int i; + + // see if the cards are in descending order from + // index 0 to n. + for (i=cardVector.size()-1;i>0;i--) + { + if (cardVector[i]>cardVector[i-1]) + { + rc=false; + break; + } + } + + return rc; +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +bool CardStack::cardsDecendingTopToBottom()const +{ + bool rc=true; + const PlayingCardVector & cardVector=this->getCardVector(); + int i; + + // see if the cards are in descending order from + // index 0 to n. + for (i=cardVector.size()-1;i>0;i--) + { + if (cardVector[i]m_cardVector.size()>0 && faceUp!=this->m_cardVector[this->m_cardVector.size()-1].isFaceUp()) + { + flipCard(-1); + } +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +bool CardStack::flipCard(int index,bool aniIfEnabled) +{ + bool rc=false; + if (this->m_cardVector.size()>0) + { + // if index is less than 0 assume it is the last card. + if (index<0) + { + index=this->m_cardVector.size()-1; + } + + if (index<(int)this->m_cardVector.size()) + { + if (aniIfEnabled) + { + m_flipAni.flipCard(this); + } + this->m_cardVector[index].setFaceUp(!this->m_cardVector[index].isFaceUp()); + this->updateStack(); + rc=true; + } + } + + return rc; +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +bool CardStack::flipCard(int index,CardMoveRecord & moveRecord,bool aniIfEnabled) +{ + bool rc=flipCard(index,aniIfEnabled); + if (rc) + { + // if index is less than 0 assume it is the last card. + if (index<0) + { + index=this->m_cardVector.size()-1; + } + + moveRecord.push_back(CardMoveRecordItem(this->stackName(),index)); + } + + return rc; +} + + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void CardStack::addCard(const PlayingCard & newCard) +{ + m_cardVector.push_back(newCard); + + if (isFlipAniRunning()) + { + m_flipAni.stopAni(); + this->updateStack(); + } +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void CardStack::addCards(const PlayingCardVector & cardVector) +{ + for(unsigned int i=0;iupdateStack(); + } +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void CardStack::addCard(const PlayingCard & newCard,CardMoveRecord & moveRecord,bool justUpdateRec) +{ + if (!justUpdateRec) + { + this->addCard(newCard); + } + + PlayingCardVector cardVector; + cardVector.push_back(newCard); + moveRecord.push_back(CardMoveRecordItem(this->stackName(),CardMoveRecordItem::AddCards,cardVector)); +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void CardStack::addCards(const PlayingCardVector & cardVector,CardMoveRecord & moveRecord,bool justUpdateRec) +{ + if (!justUpdateRec) + { + this->addCards(cardVector); + } + moveRecord.push_back(CardMoveRecordItem(this->stackName(),CardMoveRecordItem::AddCards,cardVector)); +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +PlayingCard CardStack::removeTopCard() +{ + PlayingCard card(PlayingCard::MaxSuit,PlayingCard::MaxCardIndex); + + if (!this->m_cardVector.empty()) + { + card=m_cardVector.back(); + this->m_cardVector.pop_back(); + } + return card; +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +PlayingCard CardStack::removeTopCard(CardMoveRecord & moveRecord) +{ + PlayingCard card(PlayingCard::MaxSuit,PlayingCard::MaxCardIndex); + card=this->removeTopCard(); + + // if the card is valid update the moveRecord + if (card.isValid()) + { + PlayingCardVector cardVector; + cardVector.push_back(card); + + moveRecord.push_back(CardMoveRecordItem(this->stackName(),CardMoveRecordItem::RemoveCards,cardVector)); + } + + return card; +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +bool CardStack::removeCardsStartingAt(unsigned int index,PlayingCardVector & removedCards) +{ + bool rc=false; + + if (indexm_cardVector.size()) + { + rc=true; + + unsigned int i; + + removedCards.clear(); + + for(i=index;im_cardVector.size();i++) + { + removedCards.push_back(this->m_cardVector[i]); + } + + while(m_cardVector.size()>index) + { + this->m_cardVector.pop_back(); + } + } + + return rc; +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +bool CardStack::removeCardsStartingAt(unsigned int index, + PlayingCardVector & removedCards, + CardMoveRecord & moveRecord, + bool justUpdateRec) +{ + bool rc=false; + + + if (!justUpdateRec) + { + rc=this->removeCardsStartingAt(index,removedCards); + } + else if (indexm_cardVector.size()) + { + rc=true; + + unsigned int i; + + removedCards.clear(); + + for(i=index;im_cardVector.size();i++) + { + removedCards.push_back(this->m_cardVector[i]); + } + } + + if (rc) + { + // ok now add the move records for removal of the cards from this stack + // it will be a remove and then a flip of the card before if it is face down + moveRecord.push_back(CardMoveRecordItem(this->stackName(),CardMoveRecordItem::RemoveCards,removedCards)); + + // also if we are in autoflip mode add that to the flip record. + if (0!=index && this->m_autoFaceUp && !this->m_cardVector[index-1].isFaceUp()) + { + moveRecord.push_back(CardMoveRecordItem(this->stackName(),index-1)); + } + } + + return rc; +} + + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +void CardStack::removeAllCards() +{ + // stop any flip animation we have going. + m_flipAni.stopAni(); + + m_cardVector.clear(); +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +bool CardStack::getMovableCards(PlayingCardVector & cardVector, + unsigned int & index) const +{ + bool rc=false; + + if (this->m_cardVector.size()>0) + { + int moveIndex=-1; + // ok let's go up the stack and find the last card that we can move + for (int i=this->m_cardVector.size()-1;i>=0;i--) + { + if (this->canMoveCard((unsigned int)i)) + { + moveIndex=i; + } + else + { + break; + } + } + + // did we get an index of a card. + if (moveIndex>=0) + { + rc=true; + + + for(unsigned int j=(unsigned int)moveIndex;jm_cardVector.size();j++) + { + cardVector.push_back(this->m_cardVector[j]); + } + + index=(unsigned int)moveIndex; + } + } + + return rc; +} + + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +void CardStack::updateStack() +{ + QPixmap * pPixmap=NULL; + + if (this->isFlipAniRunning()) + { + PlayingCardVector cardVector(this->m_cardVector); + + // the stack should have at least one card ie the one being flipped + // but make sure. + if (this->m_cardVector.size()>0) + { + cardVector.pop_back(); + } + + pPixmap=getStackPixmap(cardVector,m_highlighted,m_hintHighlightIndex); + } + else + { + pPixmap=getStackPixmap(this->m_cardVector,m_highlighted,m_hintHighlightIndex); + } + + if (NULL!=pPixmap) + { + this->setPixmap(*pPixmap); + delete pPixmap; + } +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +QPixmap * CardStack::getStackPixmap(const PlayingCardVector & cardVector, + bool highlighted, + int hintHighlightIndex) +{ + bool hl=((hintHighlightIndex>=0 || + (HintHighlightNoCards==hintHighlightIndex && 0==cardVector.size()))|| + highlighted); + + QPixmap * pPixmap=NULL; + + // if the stack is not empty either show a card or the card back + if (cardVector.size()>0) + { + PlayingCard card(cardVector[cardVector.size()-1]); + + + if (card.isFaceUp()) + { + pPixmap=new QPixmap(CardPixmaps::getInst().getCardPixmap(card,hl)); + } + else + { + pPixmap=new QPixmap(CardPixmaps::getInst().getCardBackPixmap(hl)); + } + } + // if the stack is empty show the empty pixmap. + else + { + pPixmap=new QPixmap(CardPixmaps::getInst().getCardNonePixmap(hl,this->m_showRedealCircle)); + } + + return pPixmap; +} + + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +void CardStack::updateAllStacks() +{ + CardStackMap::iterator it; + + CardPixmaps::getInst().clearPixmapCache(); + + for (it=m_cardStackMap.begin();it!=m_cardStackMap.end();it++) + { + it->second->updateStack(); + } +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +void CardStack::clearAllStacks() +{ + CardStackMap::iterator it; + + for (it=m_cardStackMap.begin();it!=m_cardStackMap.end();it++) + { + it->second->removeAllCards(); + } +} + + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +CardStack * CardStack::getStackByName(const std::string & stackName) +{ + CardStack * pStack=NULL; + + CardStackMap::iterator it=m_cardStackMap.find(stackName); + + if (m_cardStackMap.end()!=it) + { + pStack=it->second; + } + + return pStack; +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +bool CardStack::isCardStack(QGraphicsItem * pGraphicsItem) +{ + CardStack * pCardStack=getStackByName(QString::number((qlonglong)pGraphicsItem).toStdString()); + bool rc=false; + + if (NULL!=pCardStack) + { + rc=true; + } + + return true; +} + + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +void CardStack::processCardMoveRecord(ProcessCardMoveRecordType type, + CardMoveRecord moveRecord) +{ + while(!moveRecord.empty()) + { + CardMoveRecordItem currItem(((CardStack::RedoMove==type)?moveRecord.front():moveRecord.back())); + CardStack * pStack=CardStack::m_cardStackMap[currItem.stackName()]; + const PlayingCardVector & cardVector=currItem.cardVector(); + unsigned int i; + + CardMoveRecordItem::MoveType moveType=currItem.moveType(); + + // for undo we are actually undoing something that was done + // so we need to AddCards if they were removed or RemoveCards + // if they were added + if (CardStack::UndoMove==type) + { + if (CardMoveRecordItem::RemoveCards==moveType) + { + moveType=CardMoveRecordItem::AddCards; + } + else if (CardMoveRecordItem::AddCards==moveType) + { + moveType=CardMoveRecordItem::RemoveCards; + } + } + + switch(moveType) + { + // remove cards to a stack + case CardMoveRecordItem::RemoveCards: + { + for (i=0;iremoveTopCard(); + } + pStack->updateStack(); + } + break; + // add cards to a stack + case CardMoveRecordItem::AddCards: + { + pStack->addCards(cardVector); + pStack->updateStack(); + } + break; + + // for this case we are just going to flip the card over + case CardMoveRecordItem::FlipCard: + { + // in this case we just want to flip the last card + if (pStack->m_cardVector.size()>0) + { + unsigned int flipIndex=0; + bool isValid=false; + if (currItem.flipIndex()<0) + { + flipIndex=pStack->m_cardVector.size()-1; + isValid=true; + } + else if (currItem.flipIndex()<(int)(pStack->m_cardVector.size())) + { + flipIndex=(unsigned int)currItem.flipIndex(); + isValid=true; + } + + if (isValid) + { + pStack->m_cardVector[flipIndex].setFaceUp(!pStack->m_cardVector[flipIndex].isFaceUp()); + pStack->updateStack(); + } + } + } + break; + }; + + if (CardStack::RedoMove==type) + { + moveRecord.pop_front(); + } + else + { + moveRecord.pop_back(); + } + } +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +void CardStack::showHint(CardStack * pSrc, + unsigned int srcCardIndex, + CardStack * pDst) +{ + if (NULL!=pSrc && NULL!=pDst) + { + pSrc->slotHintHighlight(srcCardIndex); + pDst->slotDelayedHintHighlight(); + } +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void CardStack::slotDelayedHintHighlight() +{ + QTimer::singleShot(1000,this,SLOT(slotHintHighlight())); +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void CardStack::slotHintHighlight(int index) +{ + // if the index is less than 0 then the last card should be highlighted + // or the card pad if no cards are in the stack. + if (index<0) + { + this->m_hintHighlightIndex=HintHighlightNoCards; + + if (this->m_cardVector.size()>0) + { + this->m_hintHighlightIndex=this->m_cardVector.size()-1; + } + } + else if (index<(int)this->m_cardVector.size()) + { + this->m_hintHighlightIndex=index; + } + + this->updateStack(); + + QTimer::singleShot(1000,this,SLOT(slotHintHighlightComplete())); +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void CardStack::slotHintHighlightComplete() +{ + this->m_hintHighlightIndex=-1; + this->updateStack(); +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void CardStack::slotFlipComplete(CardStack * pSrc) +{ + Q_UNUSED(pSrc); + + this->updateStack(); +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void CardStack::slotDragCardsMoved(const CardMoveRecord & initRecord) +{ + CardMoveRecord moveRecord(initRecord); + + // if we are in autotop card up flip the top card. and emit a signal + // that we moved the cards. + if (!this->isEmpty() && this->isAutoTopCardUp()) + { + int lastIndex=this->m_cardVector.size()-1; + + if (!this->m_cardVector[lastIndex].isFaceUp()) + { + this->flipCard(lastIndex,moveRecord); + } + } + + emit cardsMovedByDragDrop(moveRecord); +} + + +////////////////////////////////////////////////////////////////////////// +// for this case when all cards are directly stacked on top of each other +// if there are cards in the stack we will always just return the last card. +////////////////////////////////////////////////////////////////////////// +bool CardStack::getCardIndex(const QPointF & pos,unsigned int & index) +{ + Q_UNUSED(pos); + + bool rc=false; + + if (this->m_cardVector.size()>0) + { + index=this->m_cardVector.size()-1; + rc=true; + } + + return rc; +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void CardStack::mousePressEvent(QGraphicsSceneMouseEvent *event) +{ + if (m_lockUserInteraction || this->isFlipAniRunning() || CardAnimationLock::getInst().isDemoRunning()) + { + QGraphicsPixmapItem::mousePressEvent(event); + return; + } + + + this->m_mouseMoved=false; + this->m_dragStartPos=event->pos(); + +} +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void CardStack::mouseReleaseEvent(QGraphicsSceneMouseEvent *event) +{ + if (m_lockUserInteraction || this->isFlipAniRunning() || CardAnimationLock::getInst().isDemoRunning()) + { + QGraphicsPixmapItem::mouseReleaseEvent(event); + return; + } + + if (!m_mouseMoved) + { + + unsigned int index; + + if (this->isEmpty()) + { + emit padClicked(this); + } + else if (this->getCardIndex(event->pos(),index)) + { + if (this->canMoveCard(index)) + { + PlayingCardVector moveCards; + CardMoveRecord moveRecord; + + // create a move record and a vector containing the cards + // but don't remove them. + if (CardStack::removeCardsStartingAt(index,moveCards, + moveRecord,true)) + { + emit movableCardsClicked(this,moveCards,moveRecord); + } + } + else + { + emit cardClicked(this,index); + } + } + + } + else if (m_dragStack.cardDragStarted()) + { + m_dragStack.mouseReleaseEvent(event); + } +} +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void CardStack::mouseMoveEvent(QGraphicsSceneMouseEvent *event) +{ + if (m_lockUserInteraction || this->isFlipAniRunning() || CardAnimationLock::getInst().isDemoRunning()) + { + QGraphicsPixmapItem::mouseMoveEvent(event); + return; + } + + + QPointF posDiff=(event->pos()-this->m_dragStartPos); + if ( (qAbs(posDiff.x()) + qAbs((int)posDiff.y()))< QApplication::startDragDistance()) + { + return; + } + + m_mouseMoved=true; + + if (!m_dragStack.cardDragStarted()) + { + unsigned int index=0; + bool haveCardIndex=this->getCardIndex(event->pos(),index); + + if (haveCardIndex && this->canMoveCard(index)) + { + unsigned int i; + PlayingCardVector dragCardVector; + + for (i=index;im_cardVector.size();i++) + { + dragCardVector.push_back(this->m_cardVector[i]); + } + + m_dragStack.startCardMove(event->scenePos(),index,dragCardVector); + } + } + else + { + m_dragStack.mouseMoveEvent(event); + } +} + + + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void CardStack::hoverMoveEvent(QGraphicsSceneHoverEvent * event) +{ + unsigned int index; + + if (this->getCardIndex(event->pos(),index) && + this->canMoveCard(index)) + { + this->setCursor(Qt::OpenHandCursor); + } + else + { + this->setCursor(Qt::PointingHandCursor); + } + + QGraphicsPixmapItem::hoverMoveEvent(event); +} diff --git a/plugins/qsolocards_plugin/CardStack.h b/plugins/qsolocards_plugin/CardStack.h new file mode 100644 index 000000000..6e07cdf63 --- /dev/null +++ b/plugins/qsolocards_plugin/CardStack.h @@ -0,0 +1,238 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef CARDSTACK_H +#define CARDSTACK_H + +#include +#include + +#include "CardMoveRecord.h" + +#include "FlipAnimation.h" +#include "DragCardStack.h" + +#include +#include + +class CardStack; + +typedef std::map CardStackMap; + + +class CardStack: public QObject,public QGraphicsPixmapItem +{ + Q_OBJECT +public: + enum ProcessCardMoveRecordType + { + UndoMove=0, + RedoMove=1 + }; + + enum + { + HintHighlightNoCards=-2 + }; + + CardStack(); + virtual ~CardStack(); + + inline const std::string stackName()const{return m_stackName.toStdString();} + + inline bool isFlipAniRunning()const {return m_flipAni.isAniRunning();} + + + bool allCardsFaceUp()const; + + // top is in this case the last card in the stack. bottom is index 0 + bool cardsAscendingTopToBottom()const; + bool cardsDecendingTopToBottom()const; + + void setTopCardUp(bool faceUp=true); + + bool flipCard(int index,bool aniIfEnabled=true); + bool flipCard(int index,CardMoveRecord & moveRecord,bool aniIfEnabled=true); + + inline void setAutoTopCardUp(bool autoFaceUp=true){this->m_autoFaceUp=autoFaceUp;} + inline bool isAutoTopCardUp()const {return m_autoFaceUp;} + + + inline bool isHighlighted() const {return m_highlighted;} + inline void setHighlighted(bool state=true){m_highlighted=state;} + + inline int hintHighlightIndex() const {return m_hintHighlightIndex;} + + + inline bool showRedealCircle(){return m_showRedealCircle;} + inline void setShowRedealCircle(bool state=true){m_showRedealCircle=state;} + + void addCard(const PlayingCard & newCard); + void addCards(const PlayingCardVector & cardVector); + + void addCard(const PlayingCard & newCard,CardMoveRecord & moveRecord,bool justUpdateRec=false); + void addCards(const PlayingCardVector & cardVector,CardMoveRecord & moveRecord,bool justUpdateRec=false); + + + // pull the top card off of the stack + PlayingCard removeTopCard(); + PlayingCard removeTopCard(CardMoveRecord & moveRecord); + + // the cardVector contains the cards that were removed if the index is valid. + bool removeCardsStartingAt(unsigned int index,PlayingCardVector & removedCards); + bool removeCardsStartingAt(unsigned int index,PlayingCardVector & removedCards, + CardMoveRecord & moveRecord,bool justUpdateRec=false); + + void removeAllCards(); + + inline bool isEmpty() const {return m_cardVector.empty();} + + const PlayingCardVector & getCardVector()const{return m_cardVector;} + + virtual bool canAddCards(const PlayingCardVector &){return false;} + + // this function will return the cards at the end of the stack that can be moved. + // the function canMoveCards that can be overridden by subclasses controls the + // cards that can be moved. This function can also be overridden if something other + // than the default of just cards at the end of the stack is desired. + // + // the cards that can be moved will be added to the end of the card vector passed in + // the start index of the cards is also set if the function returns true + // the function returns true if it has cards that can be moved or false if it has none. + + // this function has been added to aid in creating hints for moving cards + virtual bool getMovableCards(PlayingCardVector &, unsigned int & index) const; + + // this function gets the point in the scene that a card would be added to this stack. + inline virtual QPointF getGlobalCardAddPt() const {return mapToScene(QPointF(0,0));}; + inline virtual QPointF getGlobalLastCardPt() const {return mapToScene(QPointF(0,0));}; + inline virtual QPointF getGlobalCardPt(int index) const {Q_UNUSED(index);return mapToScene(QPointF(0,0));}; + + // this function will update the bounding rectangle for the cards. And update the + // pixmap for the stack. The default implementation implementation just calls + // getStackPixmap. Subclasses may want to override this version to record bounding + // rectangles for cards and then call the base class. + virtual void updateStack(); + + // this function returns a pointer to a pixmap of the stack. The pixmap is the responsiblity + // of the caller to free. This function can be overridden in subclasses to create + // different look for the stack when drawn or cards from it are dragged to a different + // stack. + virtual QPixmap * getStackPixmap(const PlayingCardVector & cardVector, + bool highlighted=false, + int hintHighlightIndex=-1); + + // override in subclasses for scoring per stack if desired. + virtual int score() const{return 0;} + + /////////////////////////////////////////////////////////////////////////////// + // public static functions + /////////////////////////////////////////////////////////////////////////////// + static void updateAllStacks(); + + static void clearAllStacks(); + + static inline void lockUserInteration(bool lock=true){m_lockUserInteraction=lock;} + static inline bool isUserInteractionLocked() {return m_lockUserInteraction;} + + static CardStack * getStackByName(const std::string & stackName); + + static bool isCardStack(QGraphicsItem *); + + static void processCardMoveRecord(ProcessCardMoveRecordType type, + CardMoveRecord moveRecord); + + // this is a helper function that will show a move hint by highlighting the src widget starting with the + // srcCardIndex in the stack for one second. And then highlighting the last card in the dest stack for + // one second. + static void showHint(CardStack * pSrcWidget,unsigned int srcCardIndex,CardStack * pDstWidget); + +public slots: + // the slotDelayedHintHighlight() allows you to call slotHintHighlight() for the src stack + // and slotDelayedHintHighlight() for the destination stack at the same time. + void slotDelayedHintHighlight(); // show a hint highlight delayed + void slotHintHighlight(int index=-1); // show the highlight hint immediately it will timeout in one second + void slotHintHighlightComplete(); + + void slotFlipComplete(CardStack * pSrc); + + void slotDragCardsMoved(const CardMoveRecord & moveRecord); + +signals: + // when a card is clicked this signal is emitted + void cardClicked(CardStack * pCardStackWidget,unsigned int index); + // This signal is emitted when there are no cards + // in the stack and the pad area where the first card would be is clicked + void padClicked(CardStack * pCardStackWidget); + + // this signal indicates that cards where clicked, but they are also movable + // and it includes a move record of what would happen if the card was moved. This + // can be used to make the move by calling processCardMoveRecord. If the move is accepted + // the add move can be added to the move record. And then processCardMoveRecord can be + // called to perform the move. The index is the index of the card that was clicked. + void movableCardsClicked(CardStack * pCardStack, + const PlayingCardVector & cardVector, + const CardMoveRecord &); + + // the card record will contain all changes made by the drag and + // drop. The remove from one stack. The flip of the card if in + // autoCardUp mode and the card under the remove cards was face + // down. And then the add of the cards to the other stack. + // The signal will be emitted by the stack that started the drag + // operation. + void cardsMovedByDragDrop(const CardMoveRecord &); + +protected: + int m_hintHighlightIndex; + + // subclasses should reimplement canMoveCard and canAddCards + // for the rules of whatever game they are implementing. + virtual bool canMoveCard(unsigned int index) const{Q_UNUSED(index); return false;} + virtual bool getCardIndex(const QPointF & pos,unsigned int & index); + + virtual void mousePressEvent(QGraphicsSceneMouseEvent *event); + virtual void mouseReleaseEvent(QGraphicsSceneMouseEvent *event); + virtual void mouseMoveEvent(QGraphicsSceneMouseEvent *event); + + virtual void hoverMoveEvent ( QGraphicsSceneHoverEvent * event ); + +private: + QString m_stackName; + PlayingCardVector m_cardVector; + bool m_highlighted; + bool m_showRedealCircle; + bool m_autoFaceUp; + bool m_mouseMoved; // set to true if the mouse is moved while the button is down + // using this to determine a mouse click on the CardStack. The + // mouse should not move. + QPointF m_dragStartPos; // used to figure out when the mouse has been moved enough to + // start a drag operation + + FlipAnimation m_flipAni; + DragCardStack m_dragStack; + + /////////////////////////////////////////////////////////////////////////////// + // static variables + /////////////////////////////////////////////////////////////////////////////// + static CardStackMap m_cardStackMap; // this is a map that contains all of the current instances + // of CardStack. They are mapped by a unique name to a + // pointer to the instance. + static bool m_lockUserInteraction; +}; + +#endif diff --git a/plugins/qsolocards_plugin/DealAnimation.cpp b/plugins/qsolocards_plugin/DealAnimation.cpp new file mode 100644 index 000000000..b4ef55e10 --- /dev/null +++ b/plugins/qsolocards_plugin/DealAnimation.cpp @@ -0,0 +1,480 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "DealAnimation.h" +#include "CardAnimationLock.h" + + +#include +#include +#include +#include + +#include + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +DealItem::DealItem(CardStack * pDst,CardStack * pSrc) + :m_pDst(pDst), + m_pSrc(pSrc), + m_flipList() +{ +} + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +DealItem::DealItem(const DealItem & rh) + :m_pDst(NULL), + m_pSrc(NULL), + m_flipList() +{ + *this=rh; +} + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +DealItem::~DealItem() +{ +} + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +bool DealItem::getNextCard() +{ + bool rc=false; + + if (!m_flipList.empty()) + { + rc=m_flipList.front(); + m_flipList.pop_front(); + } + + + return rc; +} + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +DealItem & DealItem::operator=(const DealItem & rh) +{ + m_pSrc=rh.m_pSrc; + m_pDst=rh.m_pDst; + m_flipList=rh.m_flipList; + + return *this; +} + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +DealGraphicsItem::DealGraphicsItem(DealItem & dealItem,CardMoveRecord &moveRecord) + :QObject(), + QGraphicsPixmapItem(), + m_dealItem(dealItem), + m_flipCard(dealItem.getNextCard()), + m_card(PlayingCard::MaxSuit,PlayingCard::MaxCardIndex), + m_pGItemAni(new QGraphicsItemAnimation), + m_moveRecord(moveRecord), + m_timeLine(), + m_delayTimer(), + m_emitFinished(true) +{ + this->setShapeMode(QGraphicsPixmapItem::BoundingRectShape); +} +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +DealGraphicsItem::~DealGraphicsItem() +{ + +} + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +void DealGraphicsItem::slotAniFinished() +{ + // add the card + m_dealItem.dst()->addCard(m_card,m_moveRecord); + + // now update the destination + m_dealItem.dst()->updateStack(); + + // remove the item from the scene + m_dealItem.src()->scene()->removeItem(this); + + // now if the card needs to be flipped. Flip it. If we are not + // emitting a finish signal. Then disable animation for the flip. + if (m_flipCard) + { + m_dealItem.dst()->flipCard(m_dealItem.dst()->getCardVector().size()-1,m_moveRecord,m_emitFinished); + } + + delete m_pGItemAni; + + m_pGItemAni=NULL; + + if (m_emitFinished) + { + emit aniFinished(this); + } +} + + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +void DealGraphicsItem::slotTimeToStart() +{ + m_timeLine.start(); +} + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +void DealGraphicsItem::setupAnimation(unsigned int duration,unsigned int delay,unsigned int zValue) +{ + m_timeLine.setDuration(duration); + this->connect(&m_timeLine,SIGNAL(finished()), + this,SLOT(slotAniFinished())); + + QPointF startPt(m_dealItem.src()->getGlobalLastCardPt()); + + this->m_card=m_dealItem.src()->removeTopCard(m_moveRecord); + + PlayingCardVector cardVector; + + cardVector.push_back(this->m_card); + + QPixmap * pPixmap=m_dealItem.src()->getStackPixmap(cardVector); + + if (pPixmap) + { + this->setPixmap(*pPixmap); + delete pPixmap; + } + + // set the z value passed in + this->setZValue(zValue); + + // add the item to the scene and move it over the stack in the + // place of the cards we are going to move + m_dealItem.src()->scene()->addItem(this); + this->setPos(startPt); + + + + // setup the animation + m_pGItemAni->setItem(this); + m_pGItemAni->setTimeLine(&m_timeLine); + + m_pGItemAni->setPosAt (0, startPt); + m_pGItemAni->setPosAt (1, m_dealItem.dst()->getGlobalCardAddPt()); + m_pGItemAni->setRotationAt (0, 0); + + // change the rotation slightly depending on how far apart in the + // x direction that stacks are apart. + if (qAbs((int)(startPt.x()-m_dealItem.dst()->getGlobalCardAddPt().x()))<5) + { + } + else if (startPt.x()>=m_dealItem.dst()->getGlobalCardAddPt().x()) + { + m_pGItemAni->setRotationAt (.5, 90); + } + else + { + m_pGItemAni->setRotationAt (.5, -90); + } + + m_pGItemAni->setRotationAt (1, 0); + + // redraw the source stack. + m_dealItem.src()->updateStack(); + + if (delay>0) + { + m_delayTimer.setSingleShot(true); + m_delayTimer.setInterval(delay); + this->connect(&m_delayTimer,SIGNAL(timeout()), + this,SLOT(slotTimeToStart())); + m_delayTimer.start(); + } + else + { + this->slotTimeToStart(); + } +} + +void DealGraphicsItem::stopAni() +{ + bool stopping=false; + if (QTimeLine::Running==m_timeLine.state()) + { + m_timeLine.stop(); + stopping=true; + } + + if (m_delayTimer.isActive()) + { + m_delayTimer.stop(); + stopping=true; + } + + if (stopping) + { + m_emitFinished=false; + this->slotAniFinished(); + } +} + + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +DealAnimation::DealAnimation() + :m_moveRecord(), + m_dealItemVector(), + m_graphicsItemVector(), + m_aniRunning(false), + m_stopAni(false), + m_duration(DealAnimation::PerDealDuration), + m_createMoveRecord(true) +{ +} + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +DealAnimation::~DealAnimation() +{ + this->stopAni(); +} + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +bool DealAnimation::dealCards(const DealItemVector & itemVector, bool createMoveRecord) +{ + if (m_aniRunning) + { + return false; + } + + + m_createMoveRecord=createMoveRecord; + + + // clear any previous items in the move record. + m_moveRecord.clear(); + + // clear any previous items in the dealItemVector + // and set it equal to the new one. + m_dealItemVector.clear(); + m_dealItemVector=itemVector; + + if (!CardAnimationLock::getInst().animationsEnabled()) + { + this->noAniStackUdpates(); + } + else + { + this->buildAniStackUpdates(); + CardAnimationLock::getInst().lock(); + + this->m_aniRunning=true; + } + + return true; +} + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +void DealAnimation::stopAni() +{ + // ok we only want to do this if animation is running. + if (m_aniRunning) + { + m_aniRunning=false; + + unsigned int i; + + // different from the case when we are cleaning these up as we go we want a hard update, and then + // delete of the objects. + for (i=0;istopAni(); + delete m_graphicsItemVector[i]; + } + + m_graphicsItemVector.clear(); + } +} + + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +void DealAnimation::slotAniFinished(DealGraphicsItem * pDealGraphicsItem) +{ + if (m_aniRunning) + { + // cleanup and finialize addition of items to new stacks. + this->cleanUpGraphicsItem(pDealGraphicsItem); + + if (m_graphicsItemVector.empty()) + { + m_aniRunning=false; + + CardAnimationLock::getInst().unlock(); + + if (!m_createMoveRecord) + { + m_moveRecord.clear(); + } + + emit cardsMoved(m_moveRecord); + } + } +} + + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +bool DealAnimation::cardsRemaining() +{ + bool rc=false; + unsigned int i; + + for (i=0;ideleteLater(); + break; + } + } +} + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +void DealAnimation::cleanUpGraphicsItems() +{ + unsigned int i; + + for (i=0;ideleteLater(); + } + + m_graphicsItemVector.clear(); +} + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +void DealAnimation::noAniStackUdpates() +{ + unsigned int i; + bool oneNotEmpty=true; + + while (oneNotEmpty) + { + oneNotEmpty=false; + for (i=0;iremoveTopCard(m_moveRecord)); + + m_dealItemVector[i].dst()->addCard(card,m_moveRecord); + + if (flip) + { + m_dealItemVector[i].dst()->flipCard(-1,m_moveRecord); + } + m_dealItemVector[i].src()->updateStack(); + m_dealItemVector[i].dst()->updateStack(); + + oneNotEmpty=true; + } + } + } + + if (!m_createMoveRecord) + { + m_moveRecord.clear(); + } + + if (m_aniRunning) + { + emit cardsMoved(m_moveRecord); + } +} + +/////////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////////// +void DealAnimation::buildAniStackUpdates() +{ + unsigned int i; + unsigned int j=0; + + bool oneNotEmpty=true; + + while (oneNotEmpty) + { + oneNotEmpty=false; + + + for (i=0;isetupAnimation(m_duration,j*PerCardDelay,j+2); + + this->connect(pCurrGraphicsItem,SIGNAL(aniFinished(DealGraphicsItem *)), + this,SLOT(slotAniFinished(DealGraphicsItem *))); + + m_graphicsItemVector.push_back(pCurrGraphicsItem); + + oneNotEmpty=true; + j++; + } + } + } +} diff --git a/plugins/qsolocards_plugin/DealAnimation.h b/plugins/qsolocards_plugin/DealAnimation.h new file mode 100644 index 000000000..1f5ae29a3 --- /dev/null +++ b/plugins/qsolocards_plugin/DealAnimation.h @@ -0,0 +1,149 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef __DEALANIMATION_H__ +#define __DEALANIMATION_H__ + +#include + +#include "CardStack.h" +#include "CardMoveRecord.h" +#include +#include + +#include +#include +#include + +// DealItems can be used to define the cards that will be dealt to a stack. +// The DealItem can then be added to the DealItemVector which is the overall +// definition of the deal. +class DealItem +{ +public: + DealItem(CardStack * pDst,CardStack * pSrc); + DealItem(const DealItem & rh); + ~DealItem(); + + inline bool isEmpty()const{return (m_flipList.empty() || m_pSrc->isEmpty());} + inline void addCard(bool flip){m_flipList.push_back(flip);} + + // returns the flip value of the next card and pops it off the list. + bool getNextCard(); + + inline CardStack * dst(){return m_pDst;} + inline CardStack * src(){return m_pSrc;} + + DealItem & operator=(const DealItem & rh); + +private: + CardStack * m_pDst; + CardStack * m_pSrc; + std::list m_flipList; // the list allows a record of how many cards to deal from the + // src to the dst and which ones need to be flipped. + // The cards will only be flipped once added to the dst stack. +}; + +typedef std::vector DealItemVector; + +class DealGraphicsItem:public QObject,public QGraphicsPixmapItem +{ + Q_OBJECT +public: + DealGraphicsItem(DealItem & dealItem,CardMoveRecord & moveRecord); + virtual ~DealGraphicsItem(); + + inline DealItem & getItem(){return m_dealItem;} + + void setupAnimation(unsigned int duration,unsigned int delay,unsigned int zValue); + + inline bool flipCard()const{return m_flipCard;} + + inline const PlayingCard & card()const{return m_card;} + + void stopAni(); + +signals: + void aniFinished(DealGraphicsItem *); +public slots: + void slotAniFinished(); + void slotTimeToStart(); + +private: + DealItem & m_dealItem; + bool m_flipCard; + PlayingCard m_card; + QGraphicsItemAnimation * m_pGItemAni; + CardMoveRecord & m_moveRecord; + QTimeLine m_timeLine; + QTimer m_delayTimer; + bool m_emitFinished; +}; + +typedef std::vector DealGraphicsItemVector; + +class DealAnimation: public QObject +{ + Q_OBJECT +public: + enum + { + PerDealDuration=400, + PerCardDelay=60 + }; + + DealAnimation(); + virtual ~DealAnimation(); + + // this duration may not be the total for the entire deal. This the duration for one round. + // So, if you have ten stacks and are dealing 5 cards to eacy stack. The entire duration will + // be the duration x 5. + inline void setDuration(int durInMilSecs=PerDealDuration){m_duration=durInMilSecs;} + inline int getDuration()const{return m_duration;} + + // the option of sending the complete signal is for cases like the initial deal of the cards. + // In that case the caller does not care when it is done as long as the user can't do anything + // until the deal is complete. The use of the CardAnimationLock will ensure this whether or not + // the caller wants to get the notification. + bool dealCards(const DealItemVector & itemVector,bool createMoveRecord=true); + + void stopAni(); + +signals: + void cardsMoved(const CardMoveRecord & moveRecord); + +public slots: + void slotAniFinished(DealGraphicsItem * pDealGraphicsItem); + +private: + bool cardsRemaining(); + void cleanUpGraphicsItem(DealGraphicsItem * pDealGraphicsItem); + void cleanUpGraphicsItems(); + void noAniStackUdpates(); + void buildAniStackUpdates(); + + CardMoveRecord m_moveRecord; + DealItemVector m_dealItemVector; + DealGraphicsItemVector m_graphicsItemVector; + bool m_aniRunning; + bool m_stopAni; + int m_duration; + bool m_createMoveRecord; +}; + +#endif diff --git a/plugins/qsolocards_plugin/DragCardStack.cpp b/plugins/qsolocards_plugin/DragCardStack.cpp new file mode 100644 index 000000000..d4d0460f6 --- /dev/null +++ b/plugins/qsolocards_plugin/DragCardStack.cpp @@ -0,0 +1,209 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "DragCardStack.h" +#include "CardStack.h" + +#include +#include +#include +#include + +////////////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////////////// +DragCardStack::DragCardStack(CardStack * pSrc) + :QObject(),QGraphicsPixmapItem(), + m_cardVector(), + m_pSrc(pSrc), + m_size(0,0), + m_cursorPt(0,0), + m_dragStarted(false), + m_pDst(NULL) +{ + this->setShapeMode(QGraphicsPixmapItem::BoundingRectShape); + this->setCursor(Qt::ClosedHandCursor); +} + +////////////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////////////// +DragCardStack::~DragCardStack() +{ +} + +////////////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////////////// +void DragCardStack::startCardMove(const QPointF & globalMousePt, + unsigned int startCardIndex, + const PlayingCardVector & moveCards) +{ + if (startCardIndexgetCardVector().size() && + moveCards.size()>0) + { + this->m_cardVector.clear(); + this->m_cardVector=moveCards; + + QPixmap * pPixmap=m_pSrc->getStackPixmap(this->m_cardVector); + + if (NULL!=pPixmap) + { + this->setPixmap(*pPixmap); + m_size=pPixmap->size(); + delete pPixmap; + } + + // set the z value to 2 so it will be on top of the + // stacks. + this->setZValue(2); + + + QPointF startPt=m_pSrc->getGlobalCardPt(startCardIndex); + + // this gets the relative position of the mouse on the new object. + m_cursorPt.setX(globalMousePt.x()-startPt.x()); + m_cursorPt.setY(globalMousePt.y()-startPt.y()); + + // add the item to the scene and move it over the stack in the + // place of the cards that we want to move + m_pSrc->scene()->addItem(this); + this->setPos(startPt); + + // remove the cards from the stack and repaint + unsigned int i; + + for(i=m_pSrc->getCardVector().size()-1;i>=startCardIndex && !m_pSrc->isEmpty();i--) + { + m_pSrc->removeTopCard(); + } + m_pSrc->updateStack(); + m_pSrc->setCursor(Qt::ClosedHandCursor); + + + m_dragStarted=true; + + m_pDst=NULL; + } +} + +////////////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////////////// +void DragCardStack::mouseReleaseEvent(QGraphicsSceneMouseEvent *event) +{ + Q_UNUSED(event); + + if (m_dragStarted) + { + m_dragStarted=false; + m_pSrc->scene()->removeItem(this); + + if (NULL!=m_pDst && + this->m_pDst->canAddCards(this->m_cardVector)) + { + CardMoveRecord moveRecord; + + moveRecord.push_back(CardMoveRecordItem(this->m_pSrc->stackName(), + CardMoveRecordItem::RemoveCards, + this->m_cardVector)); + + m_pDst->addCards(this->m_cardVector,moveRecord); + m_pDst->setHighlighted(false); + m_pDst->updateStack(); + + emit cardsMoved(moveRecord); + + m_pDst=NULL; + } + else + { + m_pSrc->addCards(this->m_cardVector); + m_pSrc->updateStack(); + } + } +} + +////////////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////////////// +void DragCardStack::mouseMoveEvent(QGraphicsSceneMouseEvent *event) +{ + if (m_dragStarted) + { + // get the topleft from the mouse pos and then adjust for where the mouse + // is positioned on the card. + QPointF topLeft(event->scenePos()); + topLeft.rx()-=m_cursorPt.x(); + topLeft.ry()-=m_cursorPt.y(); + + // move the card to it's new place. + this->setPos(topLeft); + + // calc our bounding rect. + QRectF boundingRect(topLeft,QSizeF(m_size.width(),m_size.height())); + + // now find which items this item intersects with. + QList intersectItems=this->scene()->items(boundingRect); + + CardStack * pNewDst=NULL; + + qreal largestArea=0; + + for(int i=0;isceneBoundingRect(); + + if (boundingCurr.contains(event->scenePos())) + { + pNewDst=pCurrDst; + break; + } + else + { + QRectF commonRect(boundingRect.intersected(boundingCurr)); + + qreal currArea=commonRect.width()*commonRect.height(); + + if (currArea>largestArea) + { + largestArea=currArea; + pNewDst=pCurrDst; + } + } + } + } + + if (pNewDst!=this->m_pDst) + { + if (NULL!=this->m_pDst) + { + this->m_pDst->setHighlighted(false); + this->m_pDst->updateStack(); + } + this->m_pDst=pNewDst; + + if (NULL!=this->m_pDst && + this->m_pDst->canAddCards(this->m_cardVector)) + { + this->m_pDst->setHighlighted(true); + this->m_pDst->updateStack(); + } + } + } +} diff --git a/plugins/qsolocards_plugin/DragCardStack.h b/plugins/qsolocards_plugin/DragCardStack.h new file mode 100644 index 000000000..be4d7d4e2 --- /dev/null +++ b/plugins/qsolocards_plugin/DragCardStack.h @@ -0,0 +1,58 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ +#ifndef __DRAGCARDSTACK_H__ +#define __DRAGCARDSTACK_H__ + +#include +#include +#include "CardDeck.h" +#include "CardMoveRecord.h" + +class CardStack; + +class DragCardStack:public QObject,public QGraphicsPixmapItem +{ + Q_OBJECT +public: + DragCardStack(CardStack * pSrc); + virtual ~DragCardStack(); + + inline bool cardDragStarted()const{return m_dragStarted;} + + void startCardMove(const QPointF & globalMousePt, + unsigned int startCardIndex, + const PlayingCardVector & moveCards); + +signals: + void cardsMoved(const CardMoveRecord & moveRecord); + +protected: + friend class CardStack; + virtual void mouseReleaseEvent(QGraphicsSceneMouseEvent *event); + virtual void mouseMoveEvent(QGraphicsSceneMouseEvent *event); + +private: + PlayingCardVector m_cardVector; + CardStack * m_pSrc; + QSize m_size; + QPoint m_cursorPt; + bool m_dragStarted; + CardStack * m_pDst; +}; + +#endif diff --git a/plugins/qsolocards_plugin/FlipAnimation.cpp b/plugins/qsolocards_plugin/FlipAnimation.cpp new file mode 100644 index 000000000..679d8f0f8 --- /dev/null +++ b/plugins/qsolocards_plugin/FlipAnimation.cpp @@ -0,0 +1,193 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "FlipAnimation.h" +#include "CardStack.h" +#include "CardAnimationLock.h" + +#include + + +/////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////// +FlipAnimation::FlipAnimation() + :m_pSrc(NULL), + m_card(), + m_timeLine(), + m_pItemAni(NULL), + m_pPixmapItem(NULL), + m_flipPtReached(false), + m_aniRunning(false) +{ + // connect up the slot so we will know when it is finished. + this->connect(&m_timeLine,SIGNAL(finished()), + this,SLOT(slotAniFinished())); + + this->connect(&m_timeLine,SIGNAL(valueChanged(qreal)), + this,SLOT(slotFlipAniProgress(qreal))); +} + +/////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////// +FlipAnimation::~FlipAnimation() +{ + delete m_pItemAni; +} + +/////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////// +void FlipAnimation::flipCard(CardStack * pSrc,int duration) +{ + // if animation is off just immediately emit the flipComplete + // signal + if (!CardAnimationLock::getInst().animationsEnabled() || + pSrc->isEmpty()) + { + emit flipComplete(pSrc); + } + else + { + // first if we have an animation running stop it. + this->stopAni(); + m_pSrc=pSrc; + runAnimation(duration); + } + +} + + +/////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////// +void FlipAnimation::stopAni() +{ + if (this->isAniRunning()) + { + m_aniRunning=false; + + this->m_timeLine.stop(); + + // remove the animation object + m_pSrc->scene()->removeItem(m_pPixmapItem); + delete m_pPixmapItem; + m_pPixmapItem=NULL; + } +} + +/////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////// +bool FlipAnimation::isAniRunning() const +{ + return m_aniRunning; +} + +/////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////// +void FlipAnimation::slotAniFinished() +{ + m_aniRunning=false; + + emit flipComplete(m_pSrc); + + // remove the animation object + m_pSrc->scene()->removeItem(m_pPixmapItem); + delete m_pPixmapItem; + m_pPixmapItem=NULL; +} + +/////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////// +void FlipAnimation::slotFlipAniProgress(qreal currProgress) +{ + if (currProgress>=.5 && !m_flipPtReached) + { + m_flipPtReached=true; + + m_card.setFaceUp(!m_card.isFaceUp()); + + PlayingCardVector cardVector; + + cardVector.push_back(m_card); + + QPixmap * pPixmap=m_pSrc->getStackPixmap(cardVector); + + if (pPixmap) + { + m_pPixmapItem->setPixmap(*pPixmap); + delete pPixmap; + } + } +} + +/////////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////////// +void FlipAnimation::runAnimation(int duration) +{ + m_flipPtReached=false; + + delete m_pItemAni; + delete m_pPixmapItem; + + m_timeLine.setDuration(duration); + m_pItemAni=new QGraphicsItemAnimation; + m_pPixmapItem=new QGraphicsPixmapItem; + + m_card=m_pSrc->getCardVector()[m_pSrc->getCardVector().size()-1]; + + PlayingCardVector cardVector; + + cardVector.push_back(m_card); + + QPixmap * pPixmap=m_pSrc->getStackPixmap(cardVector); + + if (pPixmap) + { + m_pPixmapItem->setPixmap(*pPixmap); + delete pPixmap; + } + + m_pPixmapItem->setShapeMode(QGraphicsPixmapItem::BoundingRectShape); + + QPointF initPt(m_pSrc->getGlobalLastCardPt()); + + QPoint halfWayPt(initPt.x()+pPixmap->width()/2,initPt.y()+pPixmap->height()/2); + + // set the z value to 2 so it will be on top of the + // stacks. + m_pPixmapItem->setZValue(2); + + // add the item to the scene and move it over the stack in the + // place of the card we are going to flip + m_pSrc->scene()->addItem(m_pPixmapItem); + m_pPixmapItem->setPos(initPt); + + // setup the animation + m_pItemAni->setItem(m_pPixmapItem); + m_pItemAni->setTimeLine(&m_timeLine); + + m_pItemAni->setPosAt (0, initPt); + m_pItemAni->setPosAt (.5, halfWayPt); + m_pItemAni->setPosAt (1, initPt); + + m_pItemAni->setScaleAt( 0, 1, 1 ); + m_pItemAni->setScaleAt( 0.5, 0.0, 1 ); + m_pItemAni->setScaleAt( 1, 1, 1 ); + + + m_aniRunning=true; + m_timeLine.start(); +} diff --git a/plugins/qsolocards_plugin/FlipAnimation.h b/plugins/qsolocards_plugin/FlipAnimation.h new file mode 100644 index 000000000..5d13b05cd --- /dev/null +++ b/plugins/qsolocards_plugin/FlipAnimation.h @@ -0,0 +1,75 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ +#ifndef __FLIPANIMATION_H__ +#define __FLIPANIMATION_H__ + +#include "CardMoveRecord.h" + +#include +#include +#include +#include +#include + +class CardStack; + +// This animation is different from the DealAnimation and StackToStackAniMove in that +// it will require the stack to change during the animation. Since, the effect of the +// animation is to show a card flipping the stack below it will be shown. And the stack +// needs to be shown without the card in it when it is exposed by the animation. So, the +// animation is a combination of the FlipAnimation object and CardStack object to get the +// flip effect. +class FlipAnimation: public QObject +{ + Q_OBJECT +public: + FlipAnimation(); + virtual ~FlipAnimation(); + + // This animation is specifically for flipping the last card in a + // stack. Cases where a card is flipped that is under other cards + // is not covered. If needed it can be added later. Something where + // the cards on top of it are pivoted out of the way, doing + // a flip of the desired card, and pivoting the cards back down on + // top of the flip card would be a very nice effect. + void flipCard(CardStack * pSrc,int duration=300); + + void stopAni(); + + bool isAniRunning() const; + +signals: + void flipComplete(CardStack * pSrc); + +public slots: + void slotAniFinished(); + void slotFlipAniProgress(qreal currProgress); + +private: + void runAnimation(int duration); + + CardStack * m_pSrc; + PlayingCard m_card; + QTimeLine m_timeLine; + QGraphicsItemAnimation * m_pItemAni; + QGraphicsPixmapItem * m_pPixmapItem; + bool m_flipPtReached; + bool m_aniRunning; +}; + +#endif diff --git a/plugins/qsolocards_plugin/FreeCellBoard.cpp b/plugins/qsolocards_plugin/FreeCellBoard.cpp new file mode 100644 index 000000000..32fc04daa --- /dev/null +++ b/plugins/qsolocards_plugin/FreeCellBoard.cpp @@ -0,0 +1,693 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "FreeCellBoard.h" +#include "CardPixmaps.h" +#include "CardDeck.h" +#include "CardAnimationLock.h" + +#include + +#include + +//////////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////////// +FreeCellBoard::FreeCellBoard() + :GameBoard(NULL,QString(tr("Freecell")).trimmed(),QString("Freecell")), + m_pDeck(NULL), + m_freeVector(), + m_stackVector(), + m_homeVector(), + m_cheat(false) +{ + this->setHelpFile(":/help/FreeCellHelp.html"); +} + +//////////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////////// +FreeCellBoard::~FreeCellBoard() +{ +} + +//////////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////////// +void FreeCellBoard::undoMove() +{ + GameBoard::undoMove(); + + this->setNumStackMoveCards(); +} + +//////////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////////// +void FreeCellBoard::redoMove() +{ + GameBoard::redoMove(); + + this->setNumStackMoveCards(); +} + +//////////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////////// +bool FreeCellBoard::getHint(CardStack * & pSrc, + unsigned int & srcIndex, + CardStack * & pDst) +{ + bool rc=false; + unsigned int i; + unsigned int j; + + + // first see if we have any cards from the free cells to move + // home + for (i=0;im_freeVector.size() && !rc;i++) + { + if (!this->m_freeVector[i]->isEmpty()) + { + const PlayingCardVector & cardVector=this->m_freeVector[i]->getCardVector(); + PlayingCardVector moveCards; + + srcIndex=cardVector.size()-1; + + moveCards.push_back(cardVector[srcIndex]); + + for (j=0;jm_homeVector.size();j++) + { + if (this->m_homeVector[j]->canAddCards(moveCards)) + { + pSrc=this->m_freeVector[i]; + pDst=this->m_homeVector[j]; + rc=true; + break; + } + } + } + } + + // now see if there are any cards in the stacks to move home + if (!rc) + { + for (i=0;im_stackVector.size() && !rc;i++) + { + if (!this->m_stackVector[i]->isEmpty()) + { + const PlayingCardVector & cardVector=this->m_stackVector[i]->getCardVector(); + PlayingCardVector moveCards; + + srcIndex=cardVector.size()-1; + + moveCards.push_back(cardVector[srcIndex]); + + for (j=0;jm_homeVector.size();j++) + { + if (this->m_homeVector[j]->canAddCards(moveCards)) + { + pSrc=this->m_stackVector[i]; + pDst=this->m_homeVector[j]; + rc=true; + break; + } + } + } + } + } + + // now see if we can move cards from the free cells to the stacks + if (!rc) + { + for (i=0;im_freeVector.size() && !rc;i++) + { + if (!this->m_freeVector[i]->isEmpty()) + { + PlayingCardVector moveCards; + + if (this->m_freeVector[i]->getMovableCards(moveCards,srcIndex)) + { + for (j=0;jm_stackVector.size();j++) + { + if (this->m_stackVector[j]->canAddCards(moveCards)) + { + pSrc=this->m_freeVector[i]; + pDst=this->m_stackVector[j]; + rc=true; + break; + } + } + } + } + } + } + + // now look for stack to stack moves + if (!rc) + { + for (i=0;im_stackVector.size() && !rc;i++) + { + if (!this->m_stackVector[i]->isEmpty()) + { + PlayingCardVector moveCards; + + if (this->m_stackVector[i]->getMovableCards(moveCards,srcIndex)) + { + // look through the stacks if we couldn't move the card home + for (j=0;jm_stackVector.size();j++) + { + // make sure not the same stackVector and that we are not moving + // the last card in a stack to an empty stack. Moving the last + // card in a stack to an empty stack doesn't do anything. And lastly + // if the cards can be added we have a match. + if (i!=j && + !(0==srcIndex && this->m_stackVector[j]->isEmpty()) && + this->m_stackVector[j]->canAddCards(moveCards)) + { + pSrc=this->m_stackVector[i]; + pDst=this->m_stackVector[j]; + rc=true; + break; + } + } + } + } + } + } + + + // now look to move something to a free cell if all else has failed + // for now just going to be a basic move an available card from the first + // stack with cards in it to the free cell. + if (!rc) + { + // first find an open free cell. If we don't have one no need to continue. + pDst=NULL; + + for (i=0;im_freeVector.size();i++) + { + if (this->m_freeVector[i]->isEmpty()) + { + pDst=this->m_freeVector[i]; + break; + } + } + + if (NULL!=pDst) + { + for (i=0;im_stackVector.size();i++) + { + if (!this->m_stackVector[i]->isEmpty()) + { + PlayingCardVector moveCards; + + + if (this->m_stackVector[i]->getMovableCards(moveCards,srcIndex) && + pDst->canAddCards(moveCards)) + { + pSrc=this->m_stackVector[i]; + rc=true; + break; + } + } + } + } + } + + + return rc; +} + +//////////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////////// +void FreeCellBoard::newGame() +{ + // call the base class to clean up + GameBoard::newGame(); + + CardDeck deck; + unsigned int i; + + + // add all the cards to the deck + while(!deck.isEmpty()) + { + this->m_pDeck->addCard(deck.next()); + } + + // setup the deal of cards + DealItemVector dealItemVector; + + // Create the dealItemVector to direct the DealAnimation object on + // how to deal the cards. + for (i=0;im_stackVector.size();i++) + { + unsigned int j; + unsigned int cardsInStack=((i<4)?7:6); + + dealItemVector.push_back(DealItem(this->m_stackVector[i],m_pDeck)); + + for (j=0;jsetCheat(cheat); + } +} + + +//////////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////////// +void FreeCellBoard::slotCardsMoved(const CardMoveRecord & moveRecord) +{ + GameBoard::slotCardsMoved(moveRecord); + + this->setNumStackMoveCards(); +} + +//////////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////////// +void FreeCellBoard::slotFreeCardsClicked(CardStack * pCardStack, + const PlayingCardVector & cardVector, + const CardMoveRecord & startMoveRecord) +{ + Q_UNUSED(pCardStack); + + CardStack * pEmptyStack=NULL; + CardStack * pMoveStack=NULL; + unsigned int i; + + // ok look for where we would move the cards to. We will look first at the home stacks. + // After the home stacks the next priority will be a non-empty stack and then lastly + // an empty stack. + + for (i=0;im_homeVector.size();i++) + { + if (this->m_homeVector[i]->canAddCards(cardVector)) + { + pMoveStack=this->m_homeVector[i]; + break; + } + } + + // if we did not find a match continue to look + if (NULL==pMoveStack) + { + for (i=0;im_stackVector.size();i++) + { + if (this->m_stackVector[i]->canAddCards(cardVector)) + { + if (this->m_stackVector[i]->isEmpty()) + { + pEmptyStack=this->m_stackVector[i]; + } + else + { + pMoveStack=this->m_stackVector[i]; + break; + } + } + } + } + + if (NULL!=pMoveStack || NULL!=pEmptyStack) + { + if (NULL==pMoveStack) + { + pMoveStack=pEmptyStack; + } + + CardMoveRecord moveRecord(startMoveRecord); + pMoveStack->addCards(cardVector,moveRecord,true); + + // perform the move of the cards and animate it if animations + // are enabled + m_sToSAniMove.moveCards(moveRecord); + } +} + +//////////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////////// +void FreeCellBoard::slotStackCardsClicked(CardStack * pCardStack, + const PlayingCardVector & cardVector, + const CardMoveRecord & startMoveRecord) +{ + CardStack * pEmptyStack=NULL; + CardStack * pMoveStack=NULL; + unsigned int i; + + // ok look for where we would move the cards to. We will look first at the home stacks. + // After the home stacks the next priority will be a non-empty stack then an empty stack. + // And lastly a free cell. + + for (i=0;im_homeVector.size();i++) + { + if (this->m_homeVector[i]->canAddCards(cardVector)) + { + pMoveStack=this->m_homeVector[i]; + break; + } + } + + // if we did not find a match continue to look + if (NULL==pMoveStack) + { + for (i=0;im_stackVector.size();i++) + { + if (this->m_stackVector[i]!=pCardStack) + { + if (this->m_stackVector[i]->canAddCards(cardVector)) + { + if (this->m_stackVector[i]->isEmpty()) + { + pEmptyStack=this->m_stackVector[i]; + } + else + { + pMoveStack=this->m_stackVector[i]; + break; + } + } + } + } + } + + // now look in the free cells + if (NULL==pMoveStack) + { + for (i=0;im_freeVector.size();i++) + { + if (this->m_freeVector[i]->canAddCards(cardVector)) + { + pMoveStack=this->m_freeVector[i]; + break; + } + } + } + + if (NULL!=pMoveStack || NULL!=pEmptyStack) + { + if (NULL==pMoveStack) + { + pMoveStack=pEmptyStack; + } + + CardMoveRecord moveRecord(startMoveRecord); + pMoveStack->addCards(cardVector,moveRecord,true); + + // perform the move of the cards and animate it if animations + // are enabled + m_sToSAniMove.moveCards(moveRecord); + } + +} + + +//////////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////////// +void FreeCellBoard::calcScore() +{ + int score=0; + + for(unsigned int i=0;im_homeVector.size();i++) + { + score+=this->m_homeVector[i]->score(); + } + + emit scoreChanged(score,""); +} + +//////////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////////// +void FreeCellBoard::resizeEvent (QResizeEvent * event) +{ + unsigned int i; + + GameBoard::resizeEvent(event); + + + QSize cardSize(CardPixmaps::getInst().getCardSize()); + + QPointF currPos(GameBoard::LayoutSpacing,GameBoard::LayoutSpacing); + + for (i=0;isetPos(currPos); + currPos.rx()+=cardSize.width()+GameBoard::LayoutSpacing; + } + + currPos.rx()+=(cardSize.width() + GameBoard::LayoutSpacing)/2; + + m_pDeck->setPos(currPos); + + currPos.setX(GameBoard::LayoutSpacing*7 + cardSize.width()*6); + + + for (i=0;isetPos(currPos); + currPos.rx()+=cardSize.width()+GameBoard::LayoutSpacing; + } + + currPos.setY(GameBoard::LayoutSpacing*2+cardSize.height()); + currPos.setX(GameBoard::LayoutSpacing*2+cardSize.width()); + for (i=0;isetPos(currPos); + currPos.rx()+=cardSize.width()+GameBoard::LayoutSpacing; + } +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +bool FreeCellBoard::runDemo(bool stopWhenNoMore) +{ + bool rc=true; + + if (!GameBoard::runDemo(false)) + { + // if we didn't find a move. Try to just move a card to a freecell. + CardStack * pDst=NULL; + bool foundMove=false; + CardStack * pSrc=NULL; + unsigned int srcIndex=0; + PlayingCardVector moveCards; + unsigned int i; + + for (i=0;im_freeVector.size();i++) + { + if (this->m_freeVector[i]->isEmpty()) + { + pDst=this->m_freeVector[i]; + break; + } + } + + if (NULL!=pDst) + { + for (i=0;im_stackVector.size();i++) + { + if (!this->m_stackVector[i]->isEmpty()) + { + if (this->m_stackVector[i]->getMovableCards(moveCards,srcIndex) && + pDst->canAddCards(moveCards)) + { + pSrc=this->m_stackVector[i]; + foundMove=true; + break; + } + } + } + } + + // if we found a move create the move record. And call the stack to stack + // animation to move it. + if (foundMove) + { + CardMoveRecord moveRecord; + + pSrc->removeCardsStartingAt(srcIndex,moveCards,moveRecord,true); + pDst->addCards(moveCards,moveRecord,true); + + m_sToSAniMove.moveCards(moveRecord,this->getDemoCardAniTime()); + } + else + { + if (stopWhenNoMore) + { + stopDemo(); + rc=false; + } + else + { + rc=false; + } + } + } + + return rc; + +} + +//////////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////////// +void FreeCellBoard::createStacks() +{ + this->setCardResizeAlg(10,ResizeByWidth); + + unsigned int i; + + // first create the home widgets where the cards need to be eventually stacked to + // win the game. + for(i=0;i<4;i++) + { + this->m_homeVector.push_back(new FreeCellHome); + this->m_scene.addItem(m_homeVector[i]); + } + + // now create the free cells + for(i=0;i<4;i++) + { + this->m_freeVector.push_back(new FreeCellFree); + this->m_scene.addItem(m_freeVector[i]); + this->connect(this->m_freeVector[i],SIGNAL(cardsMovedByDragDrop(CardMoveRecord)), + this,SLOT(slotCardsMoved(CardMoveRecord))); + this->connect(this->m_freeVector[i],SIGNAL(movableCardsClicked(CardStack*,PlayingCardVector,CardMoveRecord)), + this,SLOT(slotFreeCardsClicked(CardStack*,PlayingCardVector,CardMoveRecord))); + } + + // now create the 8 rows for the stacks. + for (i=0;i<8;i++) + { + this->m_stackVector.push_back(new FreeCellStack); + this->m_scene.addItem(m_stackVector[i]); + this->connect(this->m_stackVector[i],SIGNAL(cardsMovedByDragDrop(CardMoveRecord)), + this,SLOT(slotCardsMoved(CardMoveRecord))); + this->connect(this->m_stackVector[i],SIGNAL(movableCardsClicked(CardStack*,PlayingCardVector,CardMoveRecord)), + this,SLOT(slotStackCardsClicked(CardStack*,PlayingCardVector,CardMoveRecord))); + } + + this->m_pDeck=new FreeCellDeck; + this->m_scene.addItem(this->m_pDeck); +} + +//////////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////////// +bool FreeCellBoard::isGameWon()const +{ + bool rc=true; + + for (unsigned int i=0;im_homeVector.size();i++) + { + if (!this->m_homeVector[i]->isStackComplete()) + { + rc=false; + break; + } + } + + return rc; +} + +//////////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////////// +bool FreeCellBoard::isGameWonNotComplete()const +{ + bool rc=true; + + for (unsigned int i=0;im_stackVector.size();i++) + { + if (!this->m_stackVector[i]->cardsAscendingTopToBottom()) + { + rc=false; + break; + } + } + + return rc; +} + +//////////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////////// +void FreeCellBoard::setNumStackMoveCards() +{ + // as a convience allow dragging of cards if there would be enough + // freecells to move the cards + unsigned int numDragCards=1; + unsigned int i; + + for (i=0;iisEmpty()) + { + numDragCards++; + } + } + + // in the case that we might be dragging the cards to a free + // space, we don't want the free space to count. It would not + // be a free space to dump a card. So, it can't be counted. + if (numDragCards>1) + { + numDragCards--; + } + + for (i=0;iisEmpty()) + { + numDragCards++; + } + } + + for (i=0;isetMaxMoveCards(numDragCards); + } +} diff --git a/plugins/qsolocards_plugin/FreeCellBoard.h b/plugins/qsolocards_plugin/FreeCellBoard.h new file mode 100644 index 000000000..a35aedb9f --- /dev/null +++ b/plugins/qsolocards_plugin/FreeCellBoard.h @@ -0,0 +1,93 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef __FREECELLBOARD_H__ +#define __FREECELLBOARD_H__ + +#include "GameBoard.h" +#include "FreeCellDeck.h" +#include "FreeCellFree.h" +#include "FreeCellStack.h" +#include "FreeCellHome.h" +#include "VCardStack.h" + +#include + +class FreeCellBoard: public GameBoard +{ + Q_OBJECT +public: + FreeCellBoard(); + virtual ~FreeCellBoard(); + + virtual void undoMove(); + virtual void redoMove(); + + bool getHint(CardStack * & pSrc, + unsigned int & srcIndex, + CardStack * & pDst); + + inline bool hasDemo() const {return true;} + + void newGame(); + + void addGameMenuItems(QMenu & menu); + + void loadSettings(const QSettings & settings); + void saveSettings(QSettings & settings); + + inline bool isCheating() const {return m_cheat;} + + void setCheat(bool cheat); + + inline bool supportsScore() const{return true;} +public slots: + virtual void slotCardsMoved(const CardMoveRecord &); + + void slotFreeCardsClicked(CardStack * pCardStackWidget, + const PlayingCardVector & cardVector, + const CardMoveRecord &); + void slotStackCardsClicked(CardStack * pCardStackWidget, + const PlayingCardVector & cardVector, + const CardMoveRecord &); + +protected: + void calcScore(); + + virtual void resizeEvent (QResizeEvent * event); + + bool runDemo(bool stopWhenNoMore=true); + + void createStacks(); + bool isGameWon()const; + bool isGameWonNotComplete()const; + + void setNumStackMoveCards(); + +private: + + FreeCellDeck * m_pDeck; // the deck will only be used for the initial deal of cards + + std::vector m_freeVector; // free cells that any card can be placed in there will be 4 + std::vector m_stackVector; // we will have 8 items in this vector + std::vector m_homeVector; // we will have 4 items in this vector one for each suit + + bool m_cheat; +}; + +#endif diff --git a/plugins/qsolocards_plugin/FreeCellDeck.cpp b/plugins/qsolocards_plugin/FreeCellDeck.cpp new file mode 100644 index 000000000..83416dded --- /dev/null +++ b/plugins/qsolocards_plugin/FreeCellDeck.cpp @@ -0,0 +1,50 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "FreeCellDeck.h" +#include "CardPixmaps.h" + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +FreeCellDeck::FreeCellDeck() + :CardStack() +{ +} + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +FreeCellDeck::~FreeCellDeck() +{ +} + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +void FreeCellDeck::updateStack() +{ + // after the initial deal of cards we want this + // stack to be transparent. So, if the stack + // is empty use the transparent card pixmap. + if (this->isEmpty()) + { + this->setPixmap(CardPixmaps::getInst().getTransparentPixmap()); + } + else + { + CardStack::updateStack(); + } +} diff --git a/plugins/qsolocards_plugin/FreeCellDeck.h b/plugins/qsolocards_plugin/FreeCellDeck.h new file mode 100644 index 000000000..658204d55 --- /dev/null +++ b/plugins/qsolocards_plugin/FreeCellDeck.h @@ -0,0 +1,35 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef __FREECELLDECK_H__ +#define __FREECELLDECK_H__ + +#include "CardStack.h" + +class FreeCellDeck: public CardStack +{ + Q_OBJECT +public: + FreeCellDeck(); + virtual ~FreeCellDeck(); + + virtual void updateStack(); + +}; + +#endif diff --git a/plugins/qsolocards_plugin/FreeCellFree.cpp b/plugins/qsolocards_plugin/FreeCellFree.cpp new file mode 100644 index 000000000..5f7ad6cf0 --- /dev/null +++ b/plugins/qsolocards_plugin/FreeCellFree.cpp @@ -0,0 +1,59 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "FreeCellFree.h" + +////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////// +FreeCellFree::FreeCellFree() + :CardStack() +{ +} + +////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////// +FreeCellFree::~FreeCellFree() +{ +} + +////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////// +bool FreeCellFree::canAddCards(const PlayingCardVector & newCardVector) +{ + bool rc=false; + + if (1==newCardVector.size() && this->isEmpty()) + { + rc=true; + } + + return rc; +} + +////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////// +bool FreeCellFree::canMoveCard(unsigned int index) const +{ + bool rc=false; + + if (0==index && this->getCardVector().size()==1) + { + rc=true; + } + return rc; +} diff --git a/plugins/qsolocards_plugin/FreeCellFree.h b/plugins/qsolocards_plugin/FreeCellFree.h new file mode 100644 index 000000000..65e1832ef --- /dev/null +++ b/plugins/qsolocards_plugin/FreeCellFree.h @@ -0,0 +1,36 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef __FREECELLFREE_H__ +#define __FREECELLFREE_H__ + +#include "CardStack.h" + +class FreeCellFree : public CardStack +{ + Q_OBJECT +public: + FreeCellFree(); + ~FreeCellFree(); + + bool canAddCards(const PlayingCardVector &); +protected: + bool canMoveCard(unsigned int index) const; +}; + +#endif // __FREECELLFREE_H__ diff --git a/plugins/qsolocards_plugin/FreeCellHome.cpp b/plugins/qsolocards_plugin/FreeCellHome.cpp new file mode 100644 index 000000000..3a3a44ba6 --- /dev/null +++ b/plugins/qsolocards_plugin/FreeCellHome.cpp @@ -0,0 +1,57 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "FreeCellHome.h" + +////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////// +FreeCellHome::FreeCellHome() + :CardStack() +{ +} + +////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////// +FreeCellHome::~FreeCellHome() +{ +} + +////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////// +bool FreeCellHome::canAddCards(const PlayingCardVector & newCardVector) +{ + bool rc=false; + const PlayingCardVector & cardVector=this->getCardVector(); + + if (1==newCardVector.size()) + { + + if (this->isEmpty() && PlayingCard::Ace==newCardVector[0].getIndex()) + { + rc=true; + } + else if (!this->isEmpty() && + cardVector[cardVector.size()-1].isSameSuit(newCardVector[0]) && + cardVector[cardVector.size()-1].isNextCardIndex(newCardVector[0])) + { + rc=true; + } + } + + return rc; +} diff --git a/plugins/qsolocards_plugin/FreeCellHome.h b/plugins/qsolocards_plugin/FreeCellHome.h new file mode 100644 index 000000000..dfabb73f7 --- /dev/null +++ b/plugins/qsolocards_plugin/FreeCellHome.h @@ -0,0 +1,37 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef __FREECELLHOME_H__ +#define __FREECELLHOME_H__ + +#include "CardStack.h" + +class FreeCellHome : public CardStack +{ + Q_OBJECT +public: + FreeCellHome(); + ~FreeCellHome(); + + inline bool isStackComplete(){return getCardVector().size()==PlayingCard::MaxCardIndex;} + + inline int score() const {return getCardVector().size();} + bool canAddCards(const PlayingCardVector &); +}; + +#endif // __FREECELLHOME_H__ diff --git a/plugins/qsolocards_plugin/FreeCellStack.cpp b/plugins/qsolocards_plugin/FreeCellStack.cpp new file mode 100644 index 000000000..978e2f6f4 --- /dev/null +++ b/plugins/qsolocards_plugin/FreeCellStack.cpp @@ -0,0 +1,95 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "FreeCellStack.h" + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +FreeCellStack::FreeCellStack() + :m_cheat(false), + m_maxMoveCards(1) +{ +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +FreeCellStack::~FreeCellStack() +{ +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +bool FreeCellStack::canAddCards(const PlayingCardVector & newCardVector) +{ + if (m_cheat) + { + return true; + } + + bool rc=false; + const PlayingCardVector & cardVector=this->getCardVector(); + + if (newCardVector.size()>0) + { + // if there are no cards in the stack then we will accept any cards + if (0==cardVector.size()) + { + rc=true; + } + else if (cardVector.size()>0 && + (cardVector[cardVector.size()-1].isRed() ^ newCardVector[0].isRed()) && + cardVector[cardVector.size()-1].isPrevCardIndex(newCardVector[0])) + { + rc=true; + } + } + + return rc; +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +bool FreeCellStack::canMoveCard(unsigned int index) const +{ + bool rc=false; + const PlayingCardVector & cardVector=this->getCardVector(); + + if (index. +*/ + +#ifndef __FREECELLSTACK_H__ +#define __FREECELLSTACK_H__ + +#include "VCardStack.h" + +class FreeCellStack : public VCardStack +{ + Q_OBJECT +public: + FreeCellStack(); + ~FreeCellStack(); + inline bool isCheating() const{return m_cheat;} + + inline void setCheat(bool cheat=true){m_cheat=cheat;} + + bool canAddCards(const PlayingCardVector &); + + inline void setMaxMoveCards(unsigned int maxMoveCards){m_maxMoveCards=((maxMoveCards>1)?(maxMoveCards):(1));} +protected: + bool canMoveCard(unsigned int index) const; + +private: + bool m_cheat; + unsigned int m_maxMoveCards; +}; + +#endif // __FREECELLSTACK_H__ diff --git a/plugins/qsolocards_plugin/GameBoard.cpp b/plugins/qsolocards_plugin/GameBoard.cpp new file mode 100644 index 000000000..d438b7ce6 --- /dev/null +++ b/plugins/qsolocards_plugin/GameBoard.cpp @@ -0,0 +1,434 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "GameBoard.h" +#include +#include "CardPixmaps.h" +#include +#include +#include + +#include "CardAnimationLock.h" + +#include + +/////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////// +GameBoard::GameBoard(QWidget * pParent, + const QString & gameName, + const QString & gameSettingsId) + :QGraphicsView(pParent), + m_scene(), + m_sToSAniMove(), + m_dealAni(), + m_gameName(gameName), + m_gameSettingsId(gameSettingsId), + m_gamePixmap(":/images/sol32x32.png"), + m_undoStack(), + m_redoStack(), + m_helpFile(""), + m_numColsOrRows(1), + m_resizeType(ResizeByWidth), + m_demoRunning(false), + m_pDemoSrcPrev(NULL), + m_pDemoDstPrev(NULL), + m_demoCardsPrev(), + m_demoCardAniTime(GameBoard::DemoNormalCardAniTime), + m_stacksCreated(false) +{ + // set the background image + this->setBackgroundBrush(QImage(":/images/greenfelt.png")); + this->setCacheMode(QGraphicsView::CacheBackground); + + // add the scene to the view. + // and set it to rescale. + this->setScene(&m_scene); + + // turnoff the scroll bars on the view + setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff); + setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff); + + + // hook up the animation signal for stack to stack moves. This will enable us + // to update things just like it was a drag and drop move + this->connect(&m_sToSAniMove,SIGNAL(cardsMoved(CardMoveRecord)), + this,SLOT(slotCardsMoved(CardMoveRecord))); + + this->connect(&m_dealAni,SIGNAL(cardsMoved(CardMoveRecord)), + this,SLOT(slotCardsMoved(CardMoveRecord))); +} + +/////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////// +GameBoard::~GameBoard() +{ + CardAnimationLock::getInst().setDemoMode(false); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void GameBoard::setCardResizeAlg(unsigned int colsOrRows,CardResizeType resizeType) +{ + if (colsOrRows<1) + { + colsOrRows=1; + } + + m_numColsOrRows=colsOrRows; + + m_resizeType=resizeType; + + this->updateCardSize(this->size()); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void GameBoard::updateCardSize(const QSize & newSize) +{ + if (GameBoard::ResizeByHeight==m_resizeType) + { + CardPixmaps::getInst().setCardHeight((newSize.height()-(LayoutSpacing*(m_numColsOrRows+1)))/m_numColsOrRows); + } + else + { + CardPixmaps::getInst().setCardWidth((newSize.width()-(LayoutSpacing*(m_numColsOrRows+1)))/m_numColsOrRows); + } +} +//////////////////////////////////////////////////////////////////////////////// +// ok go through and restore the last state of all stacks +//////////////////////////////////////////////////////////////////////////////// +void GameBoard::undoMove() +{ + if (!this->m_undoStack.empty()) + { + CardMoveRecord moveRecord(m_undoStack.top()); + + CardStack::processCardMoveRecord(CardStack::UndoMove,m_undoStack.top()); + m_undoStack.pop(); + + // if we no longer have any undo info let users know. + if (!this->canUndoMove()) + { + emit undoAvail(false); + } + + bool canRedo=this->canRedoMove(); + + m_redoStack.push(moveRecord); + + // if we didn't have a redo previously and now have one + // emit a signal to tell listeners about it. + if (!canRedo) + { + emit redoAvail(true); + } + + // calc the score with the changes + this->calcScore(); + } +} + +//////////////////////////////////////////////////////////////////////////////// +// ok go through and redo the last state of all stacks +//////////////////////////////////////////////////////////////////////////////// +void GameBoard::redoMove() +{ + if (!this->m_redoStack.empty()) + { + CardMoveRecord moveRecord(m_redoStack.top()); + + CardStack::processCardMoveRecord(CardStack::RedoMove,m_redoStack.top()); + m_redoStack.pop(); + + // emit a signal that we are out of redo info + if (!this->canRedoMove()) + { + emit redoAvail(false); + } + + bool canUndo=this->canUndoMove(); + m_undoStack.push(moveRecord); + + // emit a signal that we now have undo info + if (!canUndo) + { + emit undoAvail(true); + } + + // calc the score with the changes + this->calcScore(); + } +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +bool GameBoard::canUndoMove() const +{ + return !m_undoStack.empty(); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +bool GameBoard::canRedoMove() const +{ + return !m_redoStack.empty(); +} + +//////////////////////////////////////////////////////////////////////////////// +// adding some to the undo stack also means that the redo stack is cleared. +// since +//////////////////////////////////////////////////////////////////////////////// +void GameBoard::addUndoMove(const CardMoveRecord &moveRecord) +{ + bool canUndo=this->canUndoMove(); + + m_undoStack.push(moveRecord); + + // send a signal that we now have undo info + if (!canUndo) + { + emit undoAvail(true); + } + + // clear the redo stack because we have made a move + while(!m_redoStack.empty()) + { + m_redoStack.pop(); + } + + // since we have made a move the redo stack is now gone. + emit redoAvail(false); + + // calc the score with the changes + this->calcScore(); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void GameBoard::clearUndoRedoStacks() +{ + while (!this->m_undoStack.empty()) + { + m_undoStack.pop(); + } + + while (!this->m_redoStack.empty()) + { + m_redoStack.pop(); + } + + emit undoAvail(false); + emit redoAvail(false); + + // calc the score with the changes + this->calcScore(); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void GameBoard::restartGame() +{ + this->stopDemo(); + while (!this->m_undoStack.empty()) + { + CardMoveRecord moveRecord(m_undoStack.top()); + + CardStack::processCardMoveRecord(CardStack::UndoMove,m_undoStack.top()); + m_undoStack.pop(); + } + + this->clearUndoRedoStacks(); + + // update the screen for the new layout + this->update(); + + // calc the score with the changes + this->calcScore(); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void GameBoard::showHint() +{ + unsigned int index; + CardStack * pFromStack=NULL; + CardStack * pToStack=NULL; + + // show hint if we found one. + if (this->getHint(pFromStack,index,pToStack) && pToStack && pFromStack) + { + CardStack::showHint(pFromStack,index,pToStack); + } + else + { + QMessageBox::critical(this,this->gameName(), + tr("No move found involving full sets of movable cards. " + "It might be possible to make a move not using the full set of movable cards.").trimmed()); + } +} + + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void GameBoard::startDemo(GameBoard::DemoCardAniTime demoCardAniTime) +{ + if (!m_demoRunning) + { + m_pDemoSrcPrev=NULL; + m_pDemoDstPrev=NULL; + m_demoCardsPrev.clear(); + + m_demoCardAniTime=demoCardAniTime; + + m_demoRunning=true; + CardAnimationLock::getInst().setDemoMode(true); + emit demoStarted(); + runDemo(); + } +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void GameBoard::stopDemo() +{ + if (m_demoRunning) + { + m_demoRunning=false; + CardAnimationLock::getInst().setDemoMode(false); + emit demoStopped(); + } +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void GameBoard::newGame() +{ + m_dealAni.stopAni(); + m_sToSAniMove.stopAni(); + + stopDemo(); + + CardStack::clearAllStacks(); + CardStack::updateAllStacks(); + + // clear the undo and redo info + this->clearUndoRedoStacks(); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void GameBoard::slotCardsMoved(const CardMoveRecord & moveRecord) +{ + // calc the score with the changes + this->calcScore(); + + // if the move record is not empty add it. + if (!moveRecord.empty()) + { + this->addUndoMove(moveRecord); + } + + if (this->hasDemo()&& this->isDemoRunning()) + { + runDemo(); + } + // if all suits are sent home the game is over. Show a dialog stating that + // and start the game over. + if (this->isGameWon()) + { + QMessageBox::information(this,this->gameName(),tr("Congratulations you won!").trimmed()); + this->newGame(); + } + else if (CardAnimationLock::getInst().animationsEnabled() && + this->hasDemo() && !this->isDemoRunning() && + this->isGameWonNotComplete()) + { + this->startDemo(DemoEndGameCardAniTime); + } + +} + + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void GameBoard::resizeEvent (QResizeEvent * event) +{ + QGraphicsView::resizeEvent(event); + + this->updateCardSize(event->size()); + this->m_scene.setSceneRect(QRectF(QPointF(0,0),event->size())); + + if (!m_stacksCreated) + { + m_stacksCreated=true; + this->createStacks(); + } + + CardStack::updateAllStacks(); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +bool GameBoard::runDemo(bool stopWhenNoMore) +{ + bool rc=false; + unsigned int index; + CardStack * pFromStack=NULL; + CardStack * pToStack=NULL; + PlayingCardVector moveCards; + CardMoveRecord moveRecord; + + // here we are looking to stop moving cards back and forth over and over + // between two stacks + if (this->getHint(pFromStack,index,pToStack) && pToStack && pFromStack) + { + rc=true; + if (pFromStack->removeCardsStartingAt(index,moveCards,moveRecord,true)) + { + if (m_pDemoSrcPrev==pToStack && + m_pDemoDstPrev==pFromStack && + m_demoCardsPrev==moveCards) + { + rc=false; + } + } + } + + // if there is a hint perform the move + if (rc) + { + pToStack->addCards(moveCards,moveRecord,true); + + m_pDemoSrcPrev=pFromStack; + m_pDemoDstPrev=pToStack; + m_demoCardsPrev=moveCards; + + this->m_sToSAniMove.moveCards(moveRecord,m_demoCardAniTime); + } + else if (stopWhenNoMore) + { + stopDemo(); + rc=false; + } + else + { + rc=false; + } + + return rc; +} diff --git a/plugins/qsolocards_plugin/GameBoard.h b/plugins/qsolocards_plugin/GameBoard.h new file mode 100644 index 000000000..3b68acb14 --- /dev/null +++ b/plugins/qsolocards_plugin/GameBoard.h @@ -0,0 +1,213 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef GAMEBOARD_H +#define GAMEBOARD_H + +#include +#include +#include +#include +#include +#include + +#include + +#include "CardStack.h" +#include "CardMoveRecord.h" +#include "StackToStackAniMove.h" +#include "DealAnimation.h" + +// Generic base class for a games board +class GameBoard : public QGraphicsView +{ + Q_OBJECT + +public: + enum + { + LayoutSpacing=10 + }; + + enum CardResizeType + { + ResizeByWidth=0, + ResizeByHeight=1 + }; + + enum DemoCardAniTime + { + DemoEndGameCardAniTime=100, + DemoNormalCardAniTime=400 + }; + + GameBoard(QWidget * pWidget, + const QString & gameName, + const QString & gameSettingsId); + virtual ~GameBoard(); + + virtual void setGameName(const QString & gameName){m_gameName=gameName;} + virtual void setGameId(const QString & gameId){ m_gameSettingsId=gameId;} + + // this function show be called in the constructor of classes inheriting from this + // class to set the way that cards will be resized. + virtual void setCardResizeAlg(unsigned int colsOrRows,CardResizeType resizeType); + + // this function is called when setCardResizeAlg is called or when the GameBoard is resized. + virtual void updateCardSize(const QSize & newSize); + + // undoMove and redoMove pop items off there respective stacks + // and process the move. They also call calcScore to update the + // score. + // signals undoAvail and redoAvail are also emitted if necessary + virtual void undoMove(); + virtual void redoMove(); + + virtual bool canUndoMove() const; + virtual bool canRedoMove() const; + + // addUndoMove will add the move to the undo stack. clear the redo stack + // and call calcScore. + // signals undoAvail and redoAvail are also emitted if necessary + virtual void addUndoMove(const CardMoveRecord &); + + // will clear all contents of both the redo and undo stacks, call calcScore, and + // signals undoAvail and redoAvail are also emitted if necessary + virtual void clearUndoRedoStacks(); + + virtual void restartGame(); + + virtual void showHint(); + + // this function is split into a separate virtual function + // it will allow the function to be used both for showing a + // hint and for demo mode. + virtual bool getHint(CardStack * & pSrcWidget, + unsigned int & srcStackIndex, + CardStack * & pDstWidget)=0; + + virtual void startDemo(DemoCardAniTime demoCardAniTime=DemoNormalCardAniTime); + virtual void stopDemo(); + inline bool isDemoRunning() const { return m_demoRunning;} + + inline DemoCardAniTime getDemoCardAniTime()const{return m_demoCardAniTime;} + + // override this function if the game is implementing demo mode. + // The runDemo() function will need to be called after + // each move. Bestway would be to add something at the end of the slot + // that catches the cardsMoved signal from the move animations. + // By default runDemo will call getHint and if a move is returned it will + // perform the move. If something else is desired the function can be overridden. + // it also returns a bool. So, if it is overridden the base class can be called + // first to see if there is a basic move. If not something else can be done. + virtual bool hasDemo() const {return false;} + + virtual void newGame(); + + virtual bool isCheating() const=0; + + virtual void setCheat(bool cheat)=0; + + virtual void addGameMenuItems(QMenu &)=0; + + virtual void loadSettings(const QSettings & settings)=0; + virtual void saveSettings(QSettings & settings)=0; + + virtual bool supportsScore() const=0; + + virtual const QString & helpFile() const { return m_helpFile;} + + const QPixmap & getGamePixmap() const{return m_gamePixmap;} + + const QString & gameName() const{return m_gameName;} + + const QString & gameSettingsId() const {return m_gameSettingsId;} + +public slots: + virtual void slotCardsMoved(const CardMoveRecord &); + +signals: + // this signal should be emitted on a state change of undo from available + // to unavailable or unavailable to available by sub classes + void undoAvail(bool avail); + + // this signal should be emitted on a state change of redo from available + // to unavailable or unavailable to available by sub classes + void redoAvail(bool avail); + + // signal emitted by a game when its score changed. + // The string is extra info the game can pass to show + // additional info. + void scoreChanged(int score,const QString &); + + + void demoStarted(); + void demoStopped(); + +protected: + virtual void calcScore()=0; // called when the score is changed by add to rewinding the undo and redo stacks + // subclasses should override for customizing score calculations + + virtual void setHelpFile(const QString & helpFile){m_helpFile=helpFile;} + + virtual void resizeEvent (QResizeEvent * event); + + // called to create the CardStacks for the game. + virtual void createStacks()=0; + + // this function can be overloaded for more complex behavior for the demo. By default it + // will just peform the hint returned if it found one. + virtual bool runDemo(bool stopWhenNoMore=true); + + // implement in subclasses to determine if the game is won. + virtual bool isGameWon()const=0; + + // implement in subclasses when cards are in position that the + // game will be won. When this function returns true the demo + // will be started if it is available to move the remaining cards + virtual bool isGameWonNotComplete()const=0; + + + QGraphicsScene m_scene; + StackToStackAniMove m_sToSAniMove; + DealAnimation m_dealAni; + +private: + QString m_gameName; + QString m_gameSettingsId; + QPixmap m_gamePixmap; + + std::stack m_undoStack; // stack to keep track of moves + std::stack m_redoStack; // stack to keep track of moves + + QString m_helpFile; + + unsigned int m_numColsOrRows; + CardResizeType m_resizeType; + + bool m_demoRunning; + + CardStack * m_pDemoSrcPrev; + CardStack * m_pDemoDstPrev; + PlayingCardVector m_demoCardsPrev; + DemoCardAniTime m_demoCardAniTime; + + bool m_stacksCreated; // variable to keep track if we have called createStacks +}; + +#endif // GAMEBOARD_H diff --git a/plugins/qsolocards_plugin/GameMgr.cpp b/plugins/qsolocards_plugin/GameMgr.cpp new file mode 100644 index 000000000..aedd5b183 --- /dev/null +++ b/plugins/qsolocards_plugin/GameMgr.cpp @@ -0,0 +1,107 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "GameMgr.h" +#include "SpiderBoard.h" +#include "Spider3DeckBoard.h" +#include "SpideretteBoard.h" +#include "KlondikeBoard.h" +#include "FreeCellBoard.h" +#include "YukonBoard.h" +#include + +/////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////// +GameMgr::GameMgr() + :m_lastGameId(GameMgr::NoGame) +{ + // build the list of games + m_gameDspNameList<m_gameDspNameList.at(i),pGameGroup); + pCurrAction->setData(QVariant(i)); + pCurrAction->setCheckable(true); + if (i==this->m_lastGameId) + { + pCurrAction->setChecked(true); + } + menu.addAction(pCurrAction); + } +} + +/////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////// +GameBoard * GameMgr::getGame(GameId gameId) +{ + GameBoard * pGame=NULL; + + switch(gameId) + { + case GameMgr::Spider: + pGame=new SpiderBoard(NULL); + break; + case GameMgr::Klondike: + pGame=new KlondikeBoard(NULL); + break; + case GameMgr::FreeCell: + pGame=new FreeCellBoard; + break; + case GameMgr::ThreeDeckSpider: + pGame=new Spider3DeckBoard; + break; + case GameMgr::Spiderette: + pGame=new SpideretteBoard; + break; + case GameMgr::Yukon: + pGame=new YukonBoard; + break; + case GameMgr::NoGame: + default: + pGame=NULL; + break; + }; + + // if we were able to create a valid game board. Set the last + // game id + if (NULL!=pGame) + { + this->m_lastGameId=gameId; + } + + return pGame; +} diff --git a/plugins/qsolocards_plugin/GameMgr.h b/plugins/qsolocards_plugin/GameMgr.h new file mode 100644 index 000000000..a2d408148 --- /dev/null +++ b/plugins/qsolocards_plugin/GameMgr.h @@ -0,0 +1,62 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef GAMEMGR_H +#define GAMEMGR_H + +#include "GameBoard.h" +#include +#include + +class GameMgr +{ +public: + enum GameId + { + Spider=0, + Klondike=1, + FreeCell=2, + ThreeDeckSpider=3, + Spiderette=4, + Yukon=5, + NoGame=6, + DefaultGame=Spider + }; + GameMgr(); + virtual ~GameMgr(); + + // Add menu items for the games. A menu item will be created with the data object set + // as an integer with the GameId value. The caller can connect to the menus triggered + // signal and then get the data object from the QAction and call getGame with the id + // to create a game board. + void buildGameListMenu(QMenu & menu) const; + + // get a game based on the gameId. The returned GameBoard ptr + // is the responsibility of the caller to delete. If the game id is not valid + // NULL is returned. + GameBoard * getGame(GameId gameId=DefaultGame); + + GameId getGameId() const {return m_lastGameId;} + +private: + GameId m_lastGameId; // the game id of the game requested at the last call to + // getGame. The default is NoGame. + QStringList m_gameDspNameList; +}; + +#endif // GAMEMGR_H diff --git a/plugins/qsolocards_plugin/Help.cpp b/plugins/qsolocards_plugin/Help.cpp new file mode 100644 index 000000000..77675f838 --- /dev/null +++ b/plugins/qsolocards_plugin/Help.cpp @@ -0,0 +1,76 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "Help.h" + +#include +#include +#include + +////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////// +Help::Help(QWidget * pParent,const QString & helpFile) + :QDialog(pParent), + m_pBrowser(NULL) +{ + this->setWindowTitle(tr("QSoloCards: Game Help").trimmed()); + + this->setAttribute(Qt::WA_DeleteOnClose,true); + + m_pBrowser=new QTextBrowser; + + QHBoxLayout * pLayout=new QHBoxLayout; + + pLayout->addWidget(m_pBrowser,20); + + this->setLayout(pLayout); + + this->setHelpFile(helpFile); +} + +////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////// +Help::~Help() +{ +} + +////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////// +void Help::setHelpFile(const QString & helpFile) +{ + QFile file(helpFile); + if (!file.open(QIODevice::ReadOnly | QIODevice::Text)) + { + return; + } + + QTextStream in(&file); + QString line = in.readLine(); + + QString text; + + while (!line.isNull()) + { + text.append(line); + text.append(" "); + line = in.readLine(); + } + + m_pBrowser->setHtml(text); +} + diff --git a/plugins/qsolocards_plugin/Help.h b/plugins/qsolocards_plugin/Help.h new file mode 100644 index 000000000..18f349d06 --- /dev/null +++ b/plugins/qsolocards_plugin/Help.h @@ -0,0 +1,40 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef HELP_H +#define HELP_H + +#include +#include +#include + +class Help: public QDialog +{ + Q_OBJECT +public: + Help(QWidget * pParent,const QString & helpFile); + ~Help(); + + void setHelpFile(const QString &); + +private: + + QTextBrowser * m_pBrowser; +}; + +#endif // HELP_H diff --git a/plugins/qsolocards_plugin/KlondikeBoard.cpp b/plugins/qsolocards_plugin/KlondikeBoard.cpp new file mode 100644 index 000000000..ef6c7eed3 --- /dev/null +++ b/plugins/qsolocards_plugin/KlondikeBoard.cpp @@ -0,0 +1,770 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "KlondikeBoard.h" +#include + +#include "CardDeck.h" +#include "CardPixmaps.h" +#include "CardAnimationLock.h" + +const QString KlondikeBoard::GameTypeKeyStr("GameType"); + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +KlondikeBoard::KlondikeBoard(QWidget * pWidget) + :GameBoard(pWidget,QString(tr("Klondike Solitaire")).trimmed(),QString("Klondike")), + m_pDeck(NULL), + m_pFlipDeck(NULL), + m_homeVector(), + m_stackVector(), + m_cheat(false), + m_gameType(KlondikeBoard::FlipOne), + m_flipNum(0), + m_sToSFlipAni() +{ + this->setHelpFile(":/help/KlondikeHelp.html"); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +KlondikeBoard::~KlondikeBoard() +{ +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::undoMove() +{ + bool emptyBefore=false; + bool emptyAfter=false; + + emptyBefore=m_pDeck->isEmpty(); + + GameBoard::undoMove(); + + emptyAfter=m_pDeck->isEmpty(); + + // if we undone a redeal decrement the flip count + if (!emptyBefore && emptyAfter) + { + this->m_flipNum--; + if (!(KlondikeBoard::FlipOne==this->m_gameType && + this->m_flipNum<2) && + !(KlondikeBoard::FlipThree==this->m_gameType)) + { + this->m_pDeck->setShowRedealCircle(false); + this->m_pDeck->updateStack(); + } + else + { + this->m_pDeck->setShowRedealCircle(true); + this->m_pDeck->updateStack(); + } + } +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::redoMove() +{ + bool emptyBefore=false; + bool emptyAfter=false; + + emptyBefore=m_pDeck->isEmpty(); + + GameBoard::redoMove(); + + emptyAfter=m_pDeck->isEmpty(); + + // if we are redoing a redeal increment the flip count + if (emptyBefore && !emptyAfter) + { + this->m_flipNum++; + + if (!(KlondikeBoard::FlipOne==this->m_gameType && + this->m_flipNum<2) && + !(KlondikeBoard::FlipThree==this->m_gameType)) + { + this->m_pDeck->setShowRedealCircle(false); + this->m_pDeck->updateStack(); + } + else + { + this->m_pDeck->setShowRedealCircle(true); + this->m_pDeck->updateStack(); + } + } + +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::restartGame() +{ + // call the base class to rewind the undo stack + GameBoard::restartGame(); + + // reset the flip count + this->m_flipNum=0; + // and set the redeal circle depending on game type + if (KlondikeBoard::NoRedeals==this->m_gameType) + { + this->m_pDeck->setShowRedealCircle(false); + } + else + { + this->m_pDeck->setShowRedealCircle(true); + } + +} + + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +bool KlondikeBoard::getHint(CardStack * & pFromStack, + unsigned int & index, + CardStack * & pToStack) +{ + // first see if we can move anything to one of the home stacks. + PlayingCardVector moveCards; + unsigned int i; + bool matchFound=false; + + + // ok check to see if we have a card from the stacks that can + // be added to a home stack + for (i=0;im_stackVector.size() && !matchFound;i++) + { + if (!this->m_stackVector[i]->isEmpty()) + { + const PlayingCardVector & currCards=this->m_stackVector[i]->getCardVector(); + moveCards.clear(); + moveCards.push_back(currCards[currCards.size()-1]); // just get the last card since we are moving to the home stack + index=currCards.size()-1; + + for (unsigned int j=0;jm_homeVector.size();j++) + { + if (this->m_homeVector[j]->canAddCards(moveCards)) + { + pToStack=this->m_homeVector[j]; + pFromStack=this->m_stackVector[i]; + matchFound=true; + break; + } + } + } + } + + // next check for stack to stack moves. + if (!matchFound) + { + moveCards.clear(); + pToStack=NULL; + pFromStack=NULL; + + for (i=0;im_stackVector.size() && !matchFound;i++) + { + moveCards.clear(); + if (!this->m_stackVector[i]->isEmpty() && + this->m_stackVector[i]->getMovableCards(moveCards,index)) + { + // we want to eliminate a move that starts with a stack that + // has a faceup king as the first card. We will just end up + // suggesting to move it to another empty row. Which is not + // really a move. + if (PlayingCard::King==moveCards[0].getIndex() && + moveCards.size()== this->m_stackVector[i]->getCardVector().size()) + { + continue; + } + for (unsigned int j=0;jm_stackVector.size();j++) + { + if (this->m_stackVector[i]!=this->m_stackVector[j] && + this->m_stackVector[j]->canAddCards(moveCards)) + { + pToStack=this->m_stackVector[j]; + pFromStack=this->m_stackVector[i]; + matchFound=true; + break; + } + } + } + } + } + + + // check the flip deck. We can just call getMovableCards for it + // since, it will always be just one card. + if (!matchFound) + { + moveCards.clear(); + pToStack=NULL; + pFromStack=NULL; + + if (!this->m_pFlipDeck->isEmpty() && + this->m_pFlipDeck->getMovableCards(moveCards,index)) + { + // first see if we can send a card to one of the home + // stacks + for(i=0;im_homeVector.size();i++) + { + if (this->m_homeVector[i]->canAddCards(moveCards)) + { + pToStack=this->m_homeVector[i]; + pFromStack=this->m_pFlipDeck; + matchFound=true; + break; + } + } + + // if no match now check to see if we can add the card to the + // normal stacks + if (!matchFound) + { + for(i=0;im_stackVector.size();i++) + { + if (this->m_stackVector[i]->canAddCards(moveCards)) + { + pToStack=this->m_stackVector[i]; + pFromStack=this->m_pFlipDeck; + matchFound=true; + break; + } + } + } + } + } + + + return matchFound; +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::newGame() +{ + // stop any animation of flipping cards + m_sToSFlipAni.stopAni(); + // call the base class + GameBoard::newGame(); + + CardDeck deck; + unsigned int i; + + this->m_flipNum=0; + + // only show the redeal circle in the cases that we can redeal + if (KlondikeBoard::NoRedeals==this->m_gameType) + { + this->m_pDeck->setShowRedealCircle(false); + } + else + { + this->m_pDeck->setShowRedealCircle(true); + } + + + this->m_pFlipDeck->cardsToShow(((KlondikeBoard::FlipThree==this->m_gameType)?3:1)); + + + + while(!deck.isEmpty()) + { + this->m_pDeck->addCard(deck.next()); + } + + + DealItemVector dealItemVector; + + + // Create the dealItemVector to direct the DealAnimation object on + // how to deal the cards. + for (i=0;im_stackVector.size();i++) + { + dealItemVector.push_back(DealItem(this->m_stackVector[i],m_pDeck)); + + unsigned int j; + + for (j=0;jsetShortcut(QKeySequence(Qt::CTRL + Qt::Key_1)); + pFlipOneAction->setCheckable(true); + connect(pFlipOneAction,SIGNAL(triggered()), + this,SLOT(slotSetFlipOne())); + + QAction * pFlipThreeAction=new QAction(tr("Flip three").trimmed(),pFlipCardsGroup); + pFlipThreeAction->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_3)); + pFlipThreeAction->setCheckable(true); + connect(pFlipThreeAction,SIGNAL(triggered()), + this,SLOT(slotSetFlipThree())); + + QAction * pNoRedealsAction=new QAction(tr("No redeals (flip one)").trimmed(),pFlipCardsGroup); + pNoRedealsAction->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_0)); + pNoRedealsAction->setCheckable(true); + connect(pNoRedealsAction,SIGNAL(triggered()), + this,SLOT(slotSetNoRedeals())); + + // select the correct item in the list + switch (this->m_gameType) + { + case KlondikeBoard::FlipOne: + pFlipOneAction->setChecked(true); + break; + + case KlondikeBoard::FlipThree: + pFlipThreeAction->setChecked(true); + break; + + case KlondikeBoard::NoRedeals: + pNoRedealsAction->setChecked(true); + break; + }; + + + menu.addAction(pFlipOneAction); + menu.addAction(pFlipThreeAction); + menu.addAction(pNoRedealsAction); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::loadSettings(const QSettings & settings) +{ + int gameType=settings.value(this->GameTypeKeyStr,KlondikeBoard::FlipOne).toInt(); + + switch (gameType) + { + case KlondikeBoard::NoRedeals: + this->m_gameType=KlondikeBoard::NoRedeals; + break; + + case KlondikeBoard::FlipThree: + this->m_gameType=KlondikeBoard::FlipThree; + break; + + case KlondikeBoard::FlipOne: + default: + this->m_gameType=KlondikeBoard::FlipOne; + break; + }; +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::saveSettings(QSettings & settings) +{ + settings.setValue(this->GameTypeKeyStr,this->m_gameType); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::setCheat(bool cheat) +{ + this->m_cheat=cheat; + + for(unsigned int i=0;im_stackVector.size();i++) + { + m_stackVector[i]->setCheat(cheat); + } +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::slotFlipCards(CardStack * pCardStack, + unsigned int index) +{ + Q_UNUSED(pCardStack); + Q_UNUSED(index); + // just use the game type to indicate the number of flip cards + // the enum is assigned the number of cards that will be flipped + // the exception is the NoRedeals in that case we are just flipping + // one card. + unsigned int numFlipCards=this->m_gameType; + if (KlondikeBoard::NoRedeals==this->m_gameType) + { + numFlipCards=KlondikeBoard::FlipOne; + } + + + m_sToSFlipAni.moveCards(m_pFlipDeck,m_pDeck,numFlipCards); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::slotRedealCards(CardStack * pCardStack) +{ + Q_UNUSED(pCardStack); + // ignore an attempt to redeal if the game type is NoRedeals. + // otherwise take all the cards from the Flip stack and put them back + // in the deal stack + if (KlondikeBoard::NoRedeals!=this->m_gameType && + ((KlondikeBoard::FlipOne==this->m_gameType && + this->m_flipNum<2) || + KlondikeBoard::FlipThree==this->m_gameType)) + { + unsigned int numFlipCards=this->m_gameType; + if (KlondikeBoard::NoRedeals==this->m_gameType) + { + numFlipCards=KlondikeBoard::FlipOne; + } + + // flip the cards back. Flip the cards back over. Show the bottom 3 if in FlipThree mode. Otherwise + // just show one. + m_sToSFlipAni.moveCards(m_pDeck,m_pFlipDeck,this->m_pFlipDeck->getCardVector().size(),numFlipCards); + + this->m_flipNum++; + + if (!(KlondikeBoard::FlipOne==this->m_gameType && + this->m_flipNum<2) && + !(KlondikeBoard::FlipThree==this->m_gameType)) + { + this->m_pDeck->setShowRedealCircle(false); + } + } + else + { + // if a demo is running stop it. Can't redeal any more. + this->stopDemo(); + } +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::slotStackCardsClicked(CardStack * pCardStack, + const PlayingCardVector & cardVector, + const CardMoveRecord & startMoveRecord) +{ + unsigned int i=0; + CardStack * pFoundStack=NULL; + + if (NULL==pCardStack) + { + return; + } + + // first see if the card can be added to the sent home stack + if (cardVector.size()==1) + { + for(i=0;im_homeVector.size();i++) + { + if (pCardStack!=this->m_homeVector[i] && + this->m_homeVector[i]->canAddCards(cardVector)) + { + pFoundStack=this->m_homeVector[i]; + break; + } + } + } + + // if we did not find a match look at the stacks. + // the home will use the same logic so just call that slot + if (NULL==pFoundStack) + { + this->slotHomeCardsClicked(pCardStack,cardVector,startMoveRecord); + } + + if (pFoundStack) + { + CardMoveRecord moveRecord(startMoveRecord); + pFoundStack->addCards(cardVector,moveRecord,true); + + // perform the move of the cards and animate it if animations + // are enabled + m_sToSAniMove.moveCards(moveRecord); + } +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::slotHomeCardsClicked(CardStack * pCardStack, + const PlayingCardVector & cardVector, + const CardMoveRecord & startMoveRecord) +{ + unsigned int i=0; + CardStack * pFoundStack=NULL; + + if (NULL==pCardStack) + { + return; + } + + for(i=0;im_stackVector.size();i++) + { + if (pCardStack!=this->m_stackVector[i] && + this->m_stackVector[i]->canAddCards(cardVector)) + { + pFoundStack=this->m_stackVector[i]; + break; + } + } + + if (pFoundStack) + { + CardMoveRecord moveRecord(startMoveRecord); + pFoundStack->addCards(cardVector,moveRecord,true); + + // perform the move of the cards and animate it if animations + // are enabled + m_sToSAniMove.moveCards(moveRecord); + } +} + + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::slotSetNoRedeals() +{ + this->m_gameType=KlondikeBoard::NoRedeals; + this->newGame(); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::slotSetFlipOne() +{ + this->m_gameType=KlondikeBoard::FlipOne; + this->newGame(); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::slotSetFlipThree() +{ + this->m_gameType=KlondikeBoard::FlipThree; + this->newGame(); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::calcScore() +{ + int score=0; + + for(unsigned int i=0;im_homeVector.size();i++) + { + score+=this->m_homeVector[i]->score(); + } + + emit scoreChanged(score,""); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::resizeEvent (QResizeEvent * event) +{ + unsigned int i; + + GameBoard::resizeEvent(event); + + + QSize cardSize(CardPixmaps::getInst().getCardSize()); + + QPointF currPos(GameBoard::LayoutSpacing,GameBoard::LayoutSpacing); + + m_pDeck->setPos(currPos); + + currPos.rx()+=GameBoard::LayoutSpacing + cardSize.width(); + + m_pFlipDeck->setPos(currPos); + + currPos.rx()+=GameBoard::LayoutSpacing*3 + cardSize.width()*3; + + + for (i=0;isetPos(currPos); + currPos.rx()+=cardSize.width()+GameBoard::LayoutSpacing; + } + + currPos.setY(GameBoard::LayoutSpacing*2+cardSize.height()); + currPos.setX(GameBoard::LayoutSpacing*2+cardSize.width()); + for (i=0;isetPos(currPos); + currPos.rx()+=cardSize.width()+GameBoard::LayoutSpacing; + } +} + + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +bool KlondikeBoard::runDemo(bool stopWhenNoMore) +{ + bool rc=true; + + if (!GameBoard::runDemo(false)) + { + if (!m_pDeck->isEmpty()) + { + this->slotFlipCards(); + } + else if (!m_pFlipDeck->isEmpty()) + { + this->slotRedealCards(); + } + else if (stopWhenNoMore) + { + stopDemo(); + rc=false; + } + else + { + rc=false; + } + } + + return rc; + +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void KlondikeBoard::createStacks() +{ + setCardResizeAlg(8,ResizeByWidth); + + + unsigned int i; + + // first create the home widgets where the cards need to be eventually stacked to + // win the game. + for(i=0;i<4;i++) + { + this->m_homeVector.push_back(new KlondikeHomeStack); + this->m_scene.addItem(m_homeVector[i]); + this->connect(this->m_homeVector[i],SIGNAL(cardsMovedByDragDrop(CardMoveRecord)), + this,SLOT(slotCardsMoved(CardMoveRecord))); + this->connect(this->m_homeVector[i],SIGNAL(movableCardsClicked(CardStack*,PlayingCardVector,CardMoveRecord)), + this,SLOT(slotHomeCardsClicked(CardStack*,PlayingCardVector,CardMoveRecord))); + } + + // now create the 7 rows for the stacks. + for (i=0;i<7;i++) + { + this->m_stackVector.push_back(new KlondikeStack); + this->m_scene.addItem(m_stackVector[i]); + this->connect(this->m_stackVector[i],SIGNAL(cardsMovedByDragDrop(CardMoveRecord)), + this,SLOT(slotCardsMoved(CardMoveRecord))); + this->connect(this->m_stackVector[i],SIGNAL(movableCardsClicked(CardStack*,PlayingCardVector,CardMoveRecord)), + this,SLOT(slotStackCardsClicked(CardStack*,PlayingCardVector,CardMoveRecord))); + } + + this->m_pDeck=new CardStack; + this->m_scene.addItem(this->m_pDeck); + + this->m_pDeck->setShowRedealCircle(); + + + // if a card is double clicked that means we need to flip over the next set of cards + this->connect(this->m_pDeck,SIGNAL(cardClicked(CardStack*,uint)), + this,SLOT(slotFlipCards(CardStack*,uint))); + + // if there are no cards in the deck and the pad is clicked that means we need + // to flip the deck back over. If the version of the game is not No redeals. + this->connect(this->m_pDeck,SIGNAL(padClicked(CardStack*)), + this,SLOT(slotRedealCards(CardStack*))); + + this->m_pFlipDeck=new KlondikeFlipStack; + this->m_scene.addItem(this->m_pFlipDeck); + + this->connect(this->m_pFlipDeck,SIGNAL(cardsMovedByDragDrop(CardMoveRecord)), + this,SLOT(slotCardsMoved(CardMoveRecord))); + this->connect(this->m_pFlipDeck,SIGNAL(movableCardsClicked(CardStack*,PlayingCardVector,CardMoveRecord)), + this,SLOT(slotStackCardsClicked(CardStack*,PlayingCardVector,CardMoveRecord))); + + + + // hook up the animation signal for flipping cards over from the deck to the flip + // stack. And then back. + this->connect(&m_sToSFlipAni,SIGNAL(cardsMoved(CardMoveRecord)), + this,SLOT(slotCardsMoved(CardMoveRecord))); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +bool KlondikeBoard::isGameWon()const +{ + bool rc=true; + + for (unsigned int i=0;im_homeVector.size();i++) + { + if (!this->m_homeVector[i]->isStackComplete()) + { + rc=false; + break; + } + } + + return rc; +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +bool KlondikeBoard::isGameWonNotComplete()const +{ + bool rc=false; + + rc=m_pDeck->isEmpty(); + + if (rc) + { + rc=this->m_pFlipDeck->cardsAscendingTopToBottom(); + } + + if (rc) + { + for (unsigned int i=0;im_stackVector.size();i++) + { + if (!(this->m_stackVector[i]->cardsAscendingTopToBottom() && + this->m_stackVector[i]->allCardsFaceUp())) + { + rc=false; + break; + } + } + } + + return rc; + +} diff --git a/plugins/qsolocards_plugin/KlondikeBoard.h b/plugins/qsolocards_plugin/KlondikeBoard.h new file mode 100644 index 000000000..016871466 --- /dev/null +++ b/plugins/qsolocards_plugin/KlondikeBoard.h @@ -0,0 +1,115 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef KLONDIKEBOARD_H +#define KLONDIKEBOARD_H + +#include "GameBoard.h" +#include "KlondikeStack.h" +#include "KlondikeHomeStack.h" +#include "KlondikeFlipStack.h" +#include "CardStack.h" +#include "StackToStackFlipAni.h" + +#include + + +class KlondikeBoard : public GameBoard +{ + Q_OBJECT +public: + enum GameType + { + NoRedeals=0, + FlipOne=1, + FlipThree=3 + }; + + static const QString GameTypeKeyStr; + + KlondikeBoard(QWidget * pParent=NULL); + ~KlondikeBoard(); + + virtual void undoMove(); + virtual void redoMove(); + + void restartGame(); + + bool getHint(CardStack * & pSrcWidget, + unsigned int & srcStackIndex, + CardStack * & pDstWidget); + + inline bool hasDemo() const {return true;} + + void newGame(); + + void addGameMenuItems(QMenu & menu); + + void loadSettings(const QSettings & settings); + void saveSettings(QSettings & settings); + + inline bool isCheating() const {return m_cheat;} + + void setCheat(bool cheat); + + inline bool supportsScore() const{return true;} + +public slots: + void slotFlipCards(CardStack * pCardStackWidget=NULL,unsigned int index=0); + void slotRedealCards(CardStack * pCardStackWidget=NULL); + + void slotStackCardsClicked(CardStack * pCardStackWidget, + const PlayingCardVector & cardVector, + const CardMoveRecord &); + void slotHomeCardsClicked(CardStack * pCardStackWidget, + const PlayingCardVector & cardVector, + const CardMoveRecord &); + + void slotSetNoRedeals(); + void slotSetFlipOne(); + void slotSetFlipThree(); + +protected: + void calcScore(); + + virtual void resizeEvent (QResizeEvent * event); + + bool runDemo(bool stopWhenNoMore=true); + + virtual void createStacks(); + + bool isGameWon()const; + bool isGameWonNotComplete()const; + +private: + + CardStack * m_pDeck; + KlondikeFlipStack * m_pFlipDeck; + + std::vector m_homeVector; // we will have 4 items in this vector one for each suit + std::vector m_stackVector; // we will have 7 items in this vector + + bool m_cheat; + + GameType m_gameType; + unsigned int m_flipNum; + + StackToStackFlipAni m_sToSFlipAni; +}; + +#endif // KLONDIKEBOARD_H diff --git a/plugins/qsolocards_plugin/KlondikeFlipStack.cpp b/plugins/qsolocards_plugin/KlondikeFlipStack.cpp new file mode 100644 index 000000000..3db1d2a8c --- /dev/null +++ b/plugins/qsolocards_plugin/KlondikeFlipStack.cpp @@ -0,0 +1,259 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "KlondikeFlipStack.h" +#include "CardPixmaps.h" + +#include +#include + +const qreal KlondikeFlipStack::ExposedPrecent=.18; + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +KlondikeFlipStack::KlondikeFlipStack() + :CardStack(), + m_bRectVector(), + m_cardsShown(1), + m_firstShowCard(0) +{ +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +KlondikeFlipStack::~KlondikeFlipStack() +{ +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +QPointF KlondikeFlipStack::getGlobalCardAddPt() const +{ + QPointF pt(0,0); + + const PlayingCardVector & cardVector=this->getCardVector(); + + // We are going to do this by the bounding rects and not by actual cards + // in the stacks. That way we can add something before doing animations + // and then update the display when the animation is complete + if (m_bRectVector.size()>0 && cardVector.size()>=m_bRectVector.size()) + { + pt=m_bRectVector[m_bRectVector.size()-1].topLeft(); + + pt.rx()+=this->getOverlapIncrement(cardVector,m_bRectVector.size()-1,m_firstShowCard); + } + + return mapToScene(pt); +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +QPointF KlondikeFlipStack::getGlobalLastCardPt() const +{ + QPointF pt(0,0); + + const PlayingCardVector & cardVector=this->getCardVector(); + + // We are going to do this by the bounding rects and not by actual cards + // in the stacks. That way we can add something before doing animations + // and then update the display when the animation is complete + if (m_bRectVector.size()>0 && cardVector.size()>=m_bRectVector.size()) + { + pt=m_bRectVector[m_bRectVector.size()-1].topLeft(); + } + + return mapToScene(pt); +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +QPointF KlondikeFlipStack::getGlobalCardPt(int index) const +{ + QPointF pt(0,0); + + if (index>=0 && index<(int)m_bRectVector.size()) + { + pt=m_bRectVector[index].topLeft(); + } + + return mapToScene(pt); +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +void KlondikeFlipStack::updateStack() +{ + PlayingCardVector cardVector=this->getCardVector(); + m_bRectVector.clear(); + + // if the stack has no cards in it just call the base + // class to render the empty stack. + if (0==cardVector.size()) + { + CardStack::updateStack(); + return; + } + + // figure out the index of the first card to show + if (m_cardsShown>=cardVector.size()) + { + m_firstShowCard=0; + } + else + { + m_firstShowCard=cardVector.size()-m_cardsShown; + } + + // now calc the size of the pixmap we will need + QSize pixmapSize; + + this->calcPixmapSize(cardVector,pixmapSize,m_firstShowCard); + + QPixmap pixmap(pixmapSize); + // for linux the transparent fill must be done before + // we associate the pixmap with the painter + pixmap.fill(Qt::transparent); + + QPainter painter; + + painter.begin(&pixmap); + + QPoint pt(0,0); + QSize cardSize(CardPixmaps::getInst().getCardSize()); + unsigned int i; + + for (i=0;i=m_firstShowCard) + { + bool hl=((hintHighlightIndex()>=0 && hintHighlightIndex()<=(int)i) || + ((cardVector.size()-1==i) && isHighlighted())); + + if (cardVector[i].isFaceUp()) + { + painter.drawPixmap(pt,CardPixmaps::getInst().getCardPixmap(cardVector[i],hl)); + } + else + { + painter.drawPixmap(pt,CardPixmaps::getInst().getCardBackPixmap(hl)); + } + } + + if (cardVector.size()-1==i) + { + m_bRectVector.push_back(QRectF(QPoint(pt.x(),0), + cardSize)); + } + else + { + m_bRectVector.push_back(QRectF(QPoint(pt.x(),0), + QSize(incrementValue,cardSize.height()))); + } + + // increment the point that we are going to paint the + // card pixmap onto this pixmap + pt.rx()+=incrementValue; + } + + painter.end(); + + this->setPixmap(pixmap); +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +bool KlondikeFlipStack::getCardIndex(const QPointF & pos,unsigned int & index) +{ + bool rc=false; + unsigned int i; + + // go through the bounding rect backwards. The ones lower for cards that are + // not visible are just place holders. + for(i=m_bRectVector.size();i>0;i--) + { + if (m_bRectVector[i-1].contains(pos)) + { + index=i-1; + rc=true; + break; + } + } + + return rc; +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +void KlondikeFlipStack::calcPixmapSize(const PlayingCardVector & cardVector, + QSize & size,unsigned int showIndex) +{ + QSize cardSize(CardPixmaps::getInst().getCardSize()); + unsigned int i; + + size.setWidth(0); + size.setHeight(cardSize.height()); + + for(i=0;igetOverlapIncrement(cardVector,i,showIndex); + } + } +} + +/////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////// +int KlondikeFlipStack::getOverlapIncrement(const PlayingCardVector & cardVector, + unsigned int index,unsigned int showIndex) const +{ + int increment=0; + + if (index=showIndex) + { + increment=CardPixmaps::getInst().getCardSize().width()*ExposedPrecent; + } + } + + return increment; +} + + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +bool KlondikeFlipStack::canMoveCard(unsigned int index) const +{ + bool rc=false; + + // ok the only time a card can be moved is if the card is the last in the stack. + if (!this->isEmpty() && (index==(this->getCardVector().size()-1))) + { + rc=true; + } + + return rc; +} diff --git a/plugins/qsolocards_plugin/KlondikeFlipStack.h b/plugins/qsolocards_plugin/KlondikeFlipStack.h new file mode 100644 index 000000000..43035f46a --- /dev/null +++ b/plugins/qsolocards_plugin/KlondikeFlipStack.h @@ -0,0 +1,62 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef KLONDIKEFLIPSTACK_H +#define KLONDIKEFLIPSTACK_H + +#include "CardStack.h" +#include +#include + +class KlondikeFlipStack : public CardStack +{ + Q_OBJECT +public: + static const qreal ExposedPrecent; + + KlondikeFlipStack(); + virtual ~KlondikeFlipStack(); + + inline void cardsToShow(unsigned int cardsToShow=1){m_cardsShown=((0==cardsToShow)?1:cardsToShow);} + + // this function gets the point in the scene that a card would be added to this stack. + virtual QPointF getGlobalCardAddPt() const; + virtual QPointF getGlobalLastCardPt() const; + virtual QPointF getGlobalCardPt(int index) const; + + virtual void updateStack(); + +protected: + virtual bool getCardIndex(const QPointF & pos,unsigned int & index); + + void calcPixmapSize(const PlayingCardVector & cardVector, + QSize & size,unsigned int showIndex); + + int getOverlapIncrement(const PlayingCardVector & cardVector, + unsigned int index, + unsigned int showIndex) const; + + bool canMoveCard(unsigned int index) const; + +private: + std::vector m_bRectVector; + unsigned int m_cardsShown; + unsigned int m_firstShowCard; +}; + +#endif // KLONDIKEFLIPSTACK_H diff --git a/plugins/qsolocards_plugin/KlondikeHomeStack.cpp b/plugins/qsolocards_plugin/KlondikeHomeStack.cpp new file mode 100644 index 000000000..acca976a2 --- /dev/null +++ b/plugins/qsolocards_plugin/KlondikeHomeStack.cpp @@ -0,0 +1,75 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "KlondikeHomeStack.h" + +////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////// +KlondikeHomeStack::KlondikeHomeStack() + :CardStack() +{ +} + +////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////// +KlondikeHomeStack::~KlondikeHomeStack() +{ +} + +////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////// +bool KlondikeHomeStack::canAddCards(const PlayingCardVector & newCardVector) +{ + bool rc=false; + const PlayingCardVector & cardVector=this->getCardVector(); + + if (1==newCardVector.size()) + { + + if (this->isEmpty() && PlayingCard::Ace==newCardVector[0].getIndex()) + { + rc=true; + } + else if (!this->isEmpty() && + cardVector[cardVector.size()-1].isSameSuit(newCardVector[0]) && + cardVector[cardVector.size()-1].isNextCardIndex(newCardVector[0])) + { + rc=true; + } + } + + return rc; +} + +////////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////////// +bool KlondikeHomeStack::canMoveCard(unsigned int index) const +{ + bool rc=false; + + if (!this->isEmpty()) + { + const PlayingCardVector & cardVector=this->getCardVector(); + + if ((cardVector.size()-1)==index) + { + rc=true; + } + } + return rc; +} diff --git a/plugins/qsolocards_plugin/KlondikeHomeStack.h b/plugins/qsolocards_plugin/KlondikeHomeStack.h new file mode 100644 index 000000000..4d4d0f307 --- /dev/null +++ b/plugins/qsolocards_plugin/KlondikeHomeStack.h @@ -0,0 +1,40 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef KLONDIKEHOMESTACK_H +#define KLONDIKEHOMESTACK_H + +#include "CardStack.h" + +class KlondikeHomeStack : public CardStack +{ + Q_OBJECT +public: + KlondikeHomeStack(); + ~KlondikeHomeStack(); + + inline bool isStackComplete(){return getCardVector().size()==PlayingCard::MaxCardIndex;} + + inline int score() const {return getCardVector().size();} + bool canAddCards(const PlayingCardVector &); +protected: + bool canMoveCard(unsigned int index) const; + +}; + +#endif // KLONDIKEHOMESTACK_H diff --git a/plugins/qsolocards_plugin/KlondikeStack.cpp b/plugins/qsolocards_plugin/KlondikeStack.cpp new file mode 100644 index 000000000..ee95fea99 --- /dev/null +++ b/plugins/qsolocards_plugin/KlondikeStack.cpp @@ -0,0 +1,91 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "KlondikeStack.h" + +/////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////// +KlondikeStack::KlondikeStack() + :VCardStack(), + m_cheat(false) +{ + this->setAutoTopCardUp(); +} + +/////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////// +KlondikeStack::~KlondikeStack() +{ +} + +/////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////// +bool KlondikeStack::canAddCards(const PlayingCardVector & newCardVector) +{ + if (m_cheat) + { + return true; + } + + bool rc=false; + const PlayingCardVector & cardVector=this->getCardVector(); + + if (newCardVector.size()>0) + { + // if there are no cards in the stack then the first card + // must be a king. + if (0==cardVector.size() && + PlayingCard::King==newCardVector[0].getIndex()) + { + rc=true; + } + else if (cardVector.size()>0 && + (cardVector[cardVector.size()-1].isRed() ^ newCardVector[0].isRed()) && + cardVector[cardVector.size()-1].isPrevCardIndex(newCardVector[0]) && + cardVector[cardVector.size()-1].isFaceUp()) + { + rc=true; + } + } + + return rc; +} + +/////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////// +bool KlondikeStack::canMoveCard(unsigned int index) const +{ + if (m_cheat) + { + return true; + } + + bool rc=false; + const PlayingCardVector & cardVector=this->getCardVector(); + + // ok if we have cards in the stack and the index is valid + // see if we can move it. + // For klondike as long as the card is faceup we should be able to move the + // card and all cards after it in the stack. + if (cardVector.size()>0 && index. +*/ + +#ifndef KLONDIKESTACK_H +#define KLONDIKESTACK_H + +#include "VCardStack.h" + +class KlondikeStack : public VCardStack +{ + Q_OBJECT +public: + KlondikeStack(); + ~KlondikeStack(); + inline bool isCheating() const{return m_cheat;} + + inline void setCheat(bool cheat=true){m_cheat=cheat;} + + bool canAddCards(const PlayingCardVector &); + +protected: + bool canMoveCard(unsigned int index) const; + +private: + bool m_cheat; + +}; + +#endif // KLONDIKESTACK_H diff --git a/plugins/qsolocards_plugin/Makefile b/plugins/qsolocards_plugin/Makefile new file mode 100644 index 000000000..f1b3f1738 --- /dev/null +++ b/plugins/qsolocards_plugin/Makefile @@ -0,0 +1,142 @@ +############################################################################# +# Makefile for building: qsolocards_plugin +# Generated by qmake (2.01a) (Qt 4.6.1) on: Mo 15. Feb 12:18:27 2010 +# Project: qsolocards_plugin.pro +# Template: lib +# Command: d:\qt\2010.01\qt\bin\qmake.exe -win32 -o Makefile qsolocards_plugin.pro +############################################################################# + +first: release +install: release-install +uninstall: release-uninstall +MAKEFILE = Makefile +QMAKE = d:\qt\2010.01\qt\bin\qmake.exe +DEL_FILE = del +CHK_DIR_EXISTS= if not exist +MKDIR = mkdir +COPY = copy /y +COPY_FILE = $(COPY) +COPY_DIR = xcopy /s /q /y /i +INSTALL_FILE = $(COPY_FILE) +INSTALL_PROGRAM = $(COPY_FILE) +INSTALL_DIR = $(COPY_DIR) +DEL_FILE = del +SYMLINK = +DEL_DIR = rmdir +MOVE = move +CHK_DIR_EXISTS= if not exist +MKDIR = mkdir +SUBTARGETS = \ + release \ + debug + +release: $(MAKEFILE).Release FORCE + $(MAKE) -f $(MAKEFILE).Release +release-make_default: $(MAKEFILE).Release FORCE + $(MAKE) -f $(MAKEFILE).Release +release-make_first: $(MAKEFILE).Release FORCE + $(MAKE) -f $(MAKEFILE).Release first +release-all: $(MAKEFILE).Release FORCE + $(MAKE) -f $(MAKEFILE).Release all +release-clean: $(MAKEFILE).Release FORCE + $(MAKE) -f $(MAKEFILE).Release clean +release-distclean: $(MAKEFILE).Release FORCE + $(MAKE) -f $(MAKEFILE).Release distclean +release-install: $(MAKEFILE).Release FORCE + $(MAKE) -f $(MAKEFILE).Release install +release-uninstall: $(MAKEFILE).Release FORCE + $(MAKE) -f $(MAKEFILE).Release uninstall +debug: $(MAKEFILE).Debug FORCE + $(MAKE) -f $(MAKEFILE).Debug +debug-make_default: $(MAKEFILE).Debug FORCE + $(MAKE) -f $(MAKEFILE).Debug +debug-make_first: $(MAKEFILE).Debug FORCE + $(MAKE) -f $(MAKEFILE).Debug first +debug-all: $(MAKEFILE).Debug FORCE + $(MAKE) -f $(MAKEFILE).Debug all +debug-clean: $(MAKEFILE).Debug FORCE + $(MAKE) -f $(MAKEFILE).Debug clean +debug-distclean: $(MAKEFILE).Debug FORCE + $(MAKE) -f $(MAKEFILE).Debug distclean +debug-install: $(MAKEFILE).Debug FORCE + $(MAKE) -f $(MAKEFILE).Debug install +debug-uninstall: $(MAKEFILE).Debug FORCE + $(MAKE) -f $(MAKEFILE).Debug uninstall + +Makefile: qsolocards_plugin.pro d:/Qt/2010.01/qt/mkspecs/default/qmake.conf d:/Qt/2010.01/qt/mkspecs/qconfig.pri \ + d:/Qt/2010.01/qt/mkspecs/features/qt_functions.prf \ + d:/Qt/2010.01/qt/mkspecs/features/qt_config.prf \ + d:/Qt/2010.01/qt/mkspecs/features/exclusive_builds.prf \ + d:/Qt/2010.01/qt/mkspecs/features/default_pre.prf \ + d:/Qt/2010.01/qt/mkspecs/features/win32/default_pre.prf \ + d:/Qt/2010.01/qt/mkspecs/features/release.prf \ + d:/Qt/2010.01/qt/mkspecs/features/debug_and_release.prf \ + d:/Qt/2010.01/qt/mkspecs/features/default_post.prf \ + d:/Qt/2010.01/qt/mkspecs/features/win32/default_post.prf \ + d:/Qt/2010.01/qt/mkspecs/features/win32/rtti.prf \ + d:/Qt/2010.01/qt/mkspecs/features/win32/exceptions.prf \ + d:/Qt/2010.01/qt/mkspecs/features/win32/stl.prf \ + d:/Qt/2010.01/qt/mkspecs/features/shared.prf \ + d:/Qt/2010.01/qt/mkspecs/features/dll.prf \ + d:/Qt/2010.01/qt/mkspecs/features/warn_on.prf \ + d:/Qt/2010.01/qt/mkspecs/features/qt.prf \ + d:/Qt/2010.01/qt/mkspecs/features/win32/thread.prf \ + d:/Qt/2010.01/qt/mkspecs/features/moc.prf \ + d:/Qt/2010.01/qt/mkspecs/features/win32/windows.prf \ + d:/Qt/2010.01/qt/mkspecs/features/resources.prf \ + d:/Qt/2010.01/qt/mkspecs/features/uic.prf \ + d:/Qt/2010.01/qt/mkspecs/features/yacc.prf \ + d:/Qt/2010.01/qt/mkspecs/features/lex.prf + $(QMAKE) -win32 -o Makefile qsolocards_plugin.pro +d:\Qt\2010.01\qt\mkspecs\qconfig.pri: +d:\Qt\2010.01\qt\mkspecs\features\qt_functions.prf: +d:\Qt\2010.01\qt\mkspecs\features\qt_config.prf: +d:\Qt\2010.01\qt\mkspecs\features\exclusive_builds.prf: +d:\Qt\2010.01\qt\mkspecs\features\default_pre.prf: +d:\Qt\2010.01\qt\mkspecs\features\win32\default_pre.prf: +d:\Qt\2010.01\qt\mkspecs\features\release.prf: +d:\Qt\2010.01\qt\mkspecs\features\debug_and_release.prf: +d:\Qt\2010.01\qt\mkspecs\features\default_post.prf: +d:\Qt\2010.01\qt\mkspecs\features\win32\default_post.prf: +d:\Qt\2010.01\qt\mkspecs\features\win32\rtti.prf: +d:\Qt\2010.01\qt\mkspecs\features\win32\exceptions.prf: +d:\Qt\2010.01\qt\mkspecs\features\win32\stl.prf: +d:\Qt\2010.01\qt\mkspecs\features\shared.prf: +d:\Qt\2010.01\qt\mkspecs\features\dll.prf: +d:\Qt\2010.01\qt\mkspecs\features\warn_on.prf: +d:\Qt\2010.01\qt\mkspecs\features\qt.prf: +d:\Qt\2010.01\qt\mkspecs\features\win32\thread.prf: +d:\Qt\2010.01\qt\mkspecs\features\moc.prf: +d:\Qt\2010.01\qt\mkspecs\features\win32\windows.prf: +d:\Qt\2010.01\qt\mkspecs\features\resources.prf: +d:\Qt\2010.01\qt\mkspecs\features\uic.prf: +d:\Qt\2010.01\qt\mkspecs\features\yacc.prf: +d:\Qt\2010.01\qt\mkspecs\features\lex.prf: +qmake: qmake_all FORCE + @$(QMAKE) -win32 -o Makefile qsolocards_plugin.pro + +qmake_all: FORCE + +make_default: release-make_default debug-make_default FORCE +make_first: release-make_first debug-make_first FORCE +all: release-all debug-all FORCE +clean: release-clean debug-clean FORCE + -$(DEL_FILE) ..\..\bin\libqsolocards_plugin0.a +distclean: release-distclean debug-distclean FORCE + -$(DEL_FILE) Makefile + +release-mocclean: $(MAKEFILE).Release + $(MAKE) -f $(MAKEFILE).Release mocclean +debug-mocclean: $(MAKEFILE).Debug + $(MAKE) -f $(MAKEFILE).Debug mocclean +mocclean: release-mocclean debug-mocclean + +release-mocables: $(MAKEFILE).Release + $(MAKE) -f $(MAKEFILE).Release mocables +debug-mocables: $(MAKEFILE).Debug + $(MAKE) -f $(MAKEFILE).Debug mocables +mocables: release-mocables debug-mocables +FORCE: + +$(MAKEFILE).Release: Makefile +$(MAKEFILE).Debug: Makefile diff --git a/plugins/qsolocards_plugin/Makefile.Debug b/plugins/qsolocards_plugin/Makefile.Debug new file mode 100644 index 000000000..4f842faa9 --- /dev/null +++ b/plugins/qsolocards_plugin/Makefile.Debug @@ -0,0 +1,991 @@ +############################################################################# +# Makefile for building: qsolocards_plugin +# Generated by qmake (2.01a) (Qt 4.6.1) on: Mo 15. Feb 12:18:27 2010 +# Project: qsolocards_plugin.pro +# Template: lib +############################################################################# + +####### Compiler, tools and options + +CC = gcc +CXX = g++ +DEFINES = -DUNICODE -DQT_LARGEFILE_SUPPORT -DQT_DLL -DQT_PLUGIN -DQT_SVG_LIB -DQT_GUI_LIB -DQT_CORE_LIB -DQT_THREAD_SUPPORT +CFLAGS = -g -Wall $(DEFINES) +CXXFLAGS = -DVER_MAJ=0 -DVER_MIN=99 -DVER_PAT=1 -frtti -fexceptions -mthreads -Wall $(DEFINES) +INCPATH = -I"d:\Qt\2010.01\qt\include\QtCore" -I"d:\Qt\2010.01\qt\include\QtGui" -I"d:\Qt\2010.01\qt\include\QtSvg" -I"d:\Qt\2010.01\qt\include" -I".." -I"d:\Qt\2010.01\qt\include\ActiveQt" -I"temp\moc" -I"d:\Qt\2010.01\qt\mkspecs\default" +LINK = g++ +LFLAGS = -enable-stdcall-fixup -Wl,-enable-auto-import -Wl,-enable-runtime-pseudo-reloc -mthreads -Wl -shared -Wl,--out-implib,..\..\bin\libqsolocards_plugin0.a +LIBS = -L"d:\Qt\2010.01\qt\lib" -lQtSvgd4 -lQtGuid4 -lQtCored4 +QMAKE = d:\qt\2010.01\qt\bin\qmake.exe +IDC = d:\Qt\2010.01\qt\bin\idc.exe +IDL = midl +ZIP = zip -r -9 +DEF_FILE = +RES_FILE = +COPY = copy /y +COPY_FILE = $(COPY) +COPY_DIR = xcopy /s /q /y /i +DEL_FILE = del +DEL_DIR = rmdir +MOVE = move +CHK_DIR_EXISTS= if not exist +MKDIR = mkdir +INSTALL_FILE = $(COPY_FILE) +INSTALL_PROGRAM = $(COPY_FILE) +INSTALL_DIR = $(COPY_DIR) + +####### Output directory + +OBJECTS_DIR = temp\obj + +####### Files + +SOURCES = QSoloCardsPlugin.cpp \ + main.cpp \ + mainwindow.cpp \ + PlayingCard.cpp \ + CardDeck.cpp \ + CardPixmaps.cpp \ + CardStack.cpp \ + DragCardStack.cpp \ + VCardStack.cpp \ + CardAnimationLock.cpp \ + StackToStackAniMove.cpp \ + DealAnimation.cpp \ + FlipAnimation.cpp \ + StackToStackFlipAni.cpp \ + GameBoard.cpp \ + CardMoveRecord.cpp \ + About.cpp \ + Help.cpp \ + GameMgr.cpp \ + SpiderBoard.cpp \ + SpiderHomeStack.cpp \ + SpiderStack.cpp \ + KlondikeStack.cpp \ + KlondikeFlipStack.cpp \ + KlondikeHomeStack.cpp \ + KlondikeBoard.cpp \ + FreeCellBoard.cpp \ + FreeCellDeck.cpp \ + FreeCellStack.cpp \ + FreeCellHome.cpp \ + FreeCellFree.cpp \ + Spider3DeckBoard.cpp \ + SpideretteBoard.cpp \ + YukonBoard.cpp temp\moc\moc_QSoloCardsPlugin.cpp \ + temp\moc\moc_mainwindow.cpp \ + temp\moc\moc_CardStack.cpp \ + temp\moc\moc_DragCardStack.cpp \ + temp\moc\moc_VCardStack.cpp \ + temp\moc\moc_CardAnimationLock.cpp \ + temp\moc\moc_StackToStackAniMove.cpp \ + temp\moc\moc_DealAnimation.cpp \ + temp\moc\moc_FlipAnimation.cpp \ + temp\moc\moc_StackToStackFlipAni.cpp \ + temp\moc\moc_GameBoard.cpp \ + temp\moc\moc_About.cpp \ + temp\moc\moc_Help.cpp \ + temp\moc\moc_SpiderBoard.cpp \ + temp\moc\moc_SpiderStack.cpp \ + temp\moc\moc_KlondikeStack.cpp \ + temp\moc\moc_KlondikeFlipStack.cpp \ + temp\moc\moc_KlondikeHomeStack.cpp \ + temp\moc\moc_KlondikeBoard.cpp \ + temp\moc\moc_FreeCellBoard.cpp \ + temp\moc\moc_FreeCellDeck.cpp \ + temp\moc\moc_FreeCellStack.cpp \ + temp\moc\moc_FreeCellHome.cpp \ + temp\moc\moc_FreeCellFree.cpp \ + temp\moc\moc_Spider3DeckBoard.cpp \ + temp\moc\moc_SpideretteBoard.cpp \ + temp\moc\moc_YukonBoard.cpp \ + temp\qrc\qrc_QSoloCards.cpp +OBJECTS = temp/obj/QSoloCardsPlugin.o \ + temp/obj/main.o \ + temp/obj/mainwindow.o \ + temp/obj/PlayingCard.o \ + temp/obj/CardDeck.o \ + temp/obj/CardPixmaps.o \ + temp/obj/CardStack.o \ + temp/obj/DragCardStack.o \ + temp/obj/VCardStack.o \ + temp/obj/CardAnimationLock.o \ + temp/obj/StackToStackAniMove.o \ + temp/obj/DealAnimation.o \ + temp/obj/FlipAnimation.o \ + temp/obj/StackToStackFlipAni.o \ + temp/obj/GameBoard.o \ + temp/obj/CardMoveRecord.o \ + temp/obj/About.o \ + temp/obj/Help.o \ + temp/obj/GameMgr.o \ + temp/obj/SpiderBoard.o \ + temp/obj/SpiderHomeStack.o \ + temp/obj/SpiderStack.o \ + temp/obj/KlondikeStack.o \ + temp/obj/KlondikeFlipStack.o \ + temp/obj/KlondikeHomeStack.o \ + temp/obj/KlondikeBoard.o \ + temp/obj/FreeCellBoard.o \ + temp/obj/FreeCellDeck.o \ + temp/obj/FreeCellStack.o \ + temp/obj/FreeCellHome.o \ + temp/obj/FreeCellFree.o \ + temp/obj/Spider3DeckBoard.o \ + temp/obj/SpideretteBoard.o \ + temp/obj/YukonBoard.o \ + temp/obj/moc_QSoloCardsPlugin.o \ + temp/obj/moc_mainwindow.o \ + temp/obj/moc_CardStack.o \ + temp/obj/moc_DragCardStack.o \ + temp/obj/moc_VCardStack.o \ + temp/obj/moc_CardAnimationLock.o \ + temp/obj/moc_StackToStackAniMove.o \ + temp/obj/moc_DealAnimation.o \ + temp/obj/moc_FlipAnimation.o \ + temp/obj/moc_StackToStackFlipAni.o \ + temp/obj/moc_GameBoard.o \ + temp/obj/moc_About.o \ + temp/obj/moc_Help.o \ + temp/obj/moc_SpiderBoard.o \ + temp/obj/moc_SpiderStack.o \ + temp/obj/moc_KlondikeStack.o \ + temp/obj/moc_KlondikeFlipStack.o \ + temp/obj/moc_KlondikeHomeStack.o \ + temp/obj/moc_KlondikeBoard.o \ + temp/obj/moc_FreeCellBoard.o \ + temp/obj/moc_FreeCellDeck.o \ + temp/obj/moc_FreeCellStack.o \ + temp/obj/moc_FreeCellHome.o \ + temp/obj/moc_FreeCellFree.o \ + temp/obj/moc_Spider3DeckBoard.o \ + temp/obj/moc_SpideretteBoard.o \ + temp/obj/moc_YukonBoard.o \ + temp/obj/qrc_QSoloCards.o +DIST = +QMAKE_TARGET = qsolocards_plugin +DESTDIR = ..\..\bin\ #avoid trailing-slash linebreak +TARGET = qsolocards_plugin0.dll +DESTDIR_TARGET = ..\..\bin\qsolocards_plugin0.dll + +####### Implicit rules + +.SUFFIXES: .cpp .cc .cxx .c + +.cpp.o: + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o $@ $< + +.cc.o: + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o $@ $< + +.cxx.o: + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o $@ $< + +.c.o: + $(CC) -c $(CFLAGS) $(INCPATH) -o $@ $< + +####### Build rules + +first: all +all: Makefile.Debug $(DESTDIR_TARGET) + +$(DESTDIR_TARGET): $(OBJECTS) + $(LINK) $(LFLAGS) -o $(DESTDIR_TARGET) object_script.qsolocards_plugin.Debug $(LIBS) + + +qmake: FORCE + @$(QMAKE) -win32 -o Makefile.Debug qsolocards_plugin.pro + +dist: + $(ZIP) qsolocards_plugin.zip $(SOURCES) $(DIST) qsolocards_plugin.pro d:\Qt\2010.01\qt\mkspecs\qconfig.pri d:\Qt\2010.01\qt\mkspecs\features\qt_functions.prf d:\Qt\2010.01\qt\mkspecs\features\qt_config.prf d:\Qt\2010.01\qt\mkspecs\features\exclusive_builds.prf d:\Qt\2010.01\qt\mkspecs\features\default_pre.prf d:\Qt\2010.01\qt\mkspecs\features\win32\default_pre.prf d:\Qt\2010.01\qt\mkspecs\features\debug.prf d:\Qt\2010.01\qt\mkspecs\features\debug_and_release.prf d:\Qt\2010.01\qt\mkspecs\features\default_post.prf d:\Qt\2010.01\qt\mkspecs\features\win32\default_post.prf d:\Qt\2010.01\qt\mkspecs\features\build_pass.prf d:\Qt\2010.01\qt\mkspecs\features\win32\rtti.prf d:\Qt\2010.01\qt\mkspecs\features\win32\exceptions.prf d:\Qt\2010.01\qt\mkspecs\features\win32\stl.prf d:\Qt\2010.01\qt\mkspecs\features\shared.prf d:\Qt\2010.01\qt\mkspecs\features\dll.prf d:\Qt\2010.01\qt\mkspecs\features\warn_on.prf d:\Qt\2010.01\qt\mkspecs\features\qt.prf d:\Qt\2010.01\qt\mkspecs\features\win32\thread.prf d:\Qt\2010.01\qt\mkspecs\features\moc.prf d:\Qt\2010.01\qt\mkspecs\features\win32\windows.prf d:\Qt\2010.01\qt\mkspecs\features\resources.prf d:\Qt\2010.01\qt\mkspecs\features\uic.prf d:\Qt\2010.01\qt\mkspecs\features\yacc.prf d:\Qt\2010.01\qt\mkspecs\features\lex.prf HEADERS RESOURCES IMAGES SOURCES OBJECTIVE_SOURCES FORMS YACCSOURCES YACCSOURCES LEXSOURCES + +clean: compiler_clean + -$(DEL_FILE) temp\obj\QSoloCardsPlugin.o temp\obj\main.o temp\obj\mainwindow.o temp\obj\PlayingCard.o temp\obj\CardDeck.o temp\obj\CardPixmaps.o temp\obj\CardStack.o temp\obj\DragCardStack.o temp\obj\VCardStack.o temp\obj\CardAnimationLock.o temp\obj\StackToStackAniMove.o temp\obj\DealAnimation.o temp\obj\FlipAnimation.o temp\obj\StackToStackFlipAni.o temp\obj\GameBoard.o temp\obj\CardMoveRecord.o temp\obj\About.o temp\obj\Help.o temp\obj\GameMgr.o temp\obj\SpiderBoard.o temp\obj\SpiderHomeStack.o temp\obj\SpiderStack.o temp\obj\KlondikeStack.o temp\obj\KlondikeFlipStack.o temp\obj\KlondikeHomeStack.o temp\obj\KlondikeBoard.o temp\obj\FreeCellBoard.o temp\obj\FreeCellDeck.o temp\obj\FreeCellStack.o temp\obj\FreeCellHome.o temp\obj\FreeCellFree.o temp\obj\Spider3DeckBoard.o temp\obj\SpideretteBoard.o temp\obj\YukonBoard.o temp\obj\moc_QSoloCardsPlugin.o temp\obj\moc_mainwindow.o temp\obj\moc_CardStack.o temp\obj\moc_DragCardStack.o temp\obj\moc_VCardStack.o temp\obj\moc_CardAnimationLock.o temp\obj\moc_StackToStackAniMove.o temp\obj\moc_DealAnimation.o temp\obj\moc_FlipAnimation.o temp\obj\moc_StackToStackFlipAni.o temp\obj\moc_GameBoard.o temp\obj\moc_About.o temp\obj\moc_Help.o temp\obj\moc_SpiderBoard.o temp\obj\moc_SpiderStack.o temp\obj\moc_KlondikeStack.o temp\obj\moc_KlondikeFlipStack.o temp\obj\moc_KlondikeHomeStack.o temp\obj\moc_KlondikeBoard.o temp\obj\moc_FreeCellBoard.o temp\obj\moc_FreeCellDeck.o temp\obj\moc_FreeCellStack.o temp\obj\moc_FreeCellHome.o temp\obj\moc_FreeCellFree.o temp\obj\moc_Spider3DeckBoard.o temp\obj\moc_SpideretteBoard.o temp\obj\moc_YukonBoard.o temp\obj\qrc_QSoloCards.o + -$(DEL_FILE) ..\..\bin\libqsolocards_plugin0.a + +distclean: clean + -$(DEL_FILE) $(DESTDIR_TARGET) + -$(DEL_FILE) Makefile.Debug + +mocclean: compiler_moc_header_clean compiler_moc_source_clean + +mocables: compiler_moc_header_make_all compiler_moc_source_make_all + +compiler_moc_header_make_all: temp/moc/moc_QSoloCardsPlugin.cpp temp/moc/moc_mainwindow.cpp temp/moc/moc_CardStack.cpp temp/moc/moc_DragCardStack.cpp temp/moc/moc_VCardStack.cpp temp/moc/moc_CardAnimationLock.cpp temp/moc/moc_StackToStackAniMove.cpp temp/moc/moc_DealAnimation.cpp temp/moc/moc_FlipAnimation.cpp temp/moc/moc_StackToStackFlipAni.cpp temp/moc/moc_GameBoard.cpp temp/moc/moc_About.cpp temp/moc/moc_Help.cpp temp/moc/moc_SpiderBoard.cpp temp/moc/moc_SpiderStack.cpp temp/moc/moc_KlondikeStack.cpp temp/moc/moc_KlondikeFlipStack.cpp temp/moc/moc_KlondikeHomeStack.cpp temp/moc/moc_KlondikeBoard.cpp temp/moc/moc_FreeCellBoard.cpp temp/moc/moc_FreeCellDeck.cpp temp/moc/moc_FreeCellStack.cpp temp/moc/moc_FreeCellHome.cpp temp/moc/moc_FreeCellFree.cpp temp/moc/moc_Spider3DeckBoard.cpp temp/moc/moc_SpideretteBoard.cpp temp/moc/moc_YukonBoard.cpp +compiler_moc_header_clean: + -$(DEL_FILE) temp\moc\moc_QSoloCardsPlugin.cpp temp\moc\moc_mainwindow.cpp temp\moc\moc_CardStack.cpp temp\moc\moc_DragCardStack.cpp temp\moc\moc_VCardStack.cpp temp\moc\moc_CardAnimationLock.cpp temp\moc\moc_StackToStackAniMove.cpp temp\moc\moc_DealAnimation.cpp temp\moc\moc_FlipAnimation.cpp temp\moc\moc_StackToStackFlipAni.cpp temp\moc\moc_GameBoard.cpp temp\moc\moc_About.cpp temp\moc\moc_Help.cpp temp\moc\moc_SpiderBoard.cpp temp\moc\moc_SpiderStack.cpp temp\moc\moc_KlondikeStack.cpp temp\moc\moc_KlondikeFlipStack.cpp temp\moc\moc_KlondikeHomeStack.cpp temp\moc\moc_KlondikeBoard.cpp temp\moc\moc_FreeCellBoard.cpp temp\moc\moc_FreeCellDeck.cpp temp\moc\moc_FreeCellStack.cpp temp\moc\moc_FreeCellHome.cpp temp\moc\moc_FreeCellFree.cpp temp\moc\moc_Spider3DeckBoard.cpp temp\moc\moc_SpideretteBoard.cpp temp\moc\moc_YukonBoard.cpp +temp/moc/moc_QSoloCardsPlugin.cpp: QSoloCardsPlugin.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 QSoloCardsPlugin.h -o temp\moc\moc_QSoloCardsPlugin.cpp + +temp/moc/moc_mainwindow.cpp: GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + Help.h \ + About.h \ + GameMgr.h \ + mainwindow.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 mainwindow.h -o temp\moc\moc_mainwindow.cpp + +temp/moc/moc_CardStack.cpp: CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + CardStack.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 CardStack.h -o temp\moc\moc_CardStack.cpp + +temp/moc/moc_DragCardStack.cpp: CardDeck.h \ + PlayingCard.h \ + CardMoveRecord.h \ + DragCardStack.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 DragCardStack.h -o temp\moc\moc_DragCardStack.cpp + +temp/moc/moc_VCardStack.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + VCardStack.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 VCardStack.h -o temp\moc\moc_VCardStack.cpp + +temp/moc/moc_CardAnimationLock.cpp: CardAnimationLock.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 CardAnimationLock.h -o temp\moc\moc_CardAnimationLock.cpp + +temp/moc/moc_StackToStackAniMove.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 StackToStackAniMove.h -o temp\moc\moc_StackToStackAniMove.cpp + +temp/moc/moc_DealAnimation.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + DealAnimation.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 DealAnimation.h -o temp\moc\moc_DealAnimation.cpp + +temp/moc/moc_FlipAnimation.cpp: CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 FlipAnimation.h -o temp\moc\moc_FlipAnimation.cpp + +temp/moc/moc_StackToStackFlipAni.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackFlipAni.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 StackToStackFlipAni.h -o temp\moc\moc_StackToStackFlipAni.cpp + +temp/moc/moc_GameBoard.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + GameBoard.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 GameBoard.h -o temp\moc\moc_GameBoard.cpp + +temp/moc/moc_About.cpp: About.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 About.h -o temp\moc\moc_About.cpp + +temp/moc/moc_Help.cpp: Help.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 Help.h -o temp\moc\moc_Help.cpp + +temp/moc/moc_SpiderBoard.cpp: GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + SpiderStack.h \ + VCardStack.h \ + SpiderHomeStack.h \ + SpiderBoard.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 SpiderBoard.h -o temp\moc\moc_SpiderBoard.cpp + +temp/moc/moc_SpiderStack.cpp: VCardStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + SpiderStack.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 SpiderStack.h -o temp\moc\moc_SpiderStack.cpp + +temp/moc/moc_KlondikeStack.cpp: VCardStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + KlondikeStack.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 KlondikeStack.h -o temp\moc\moc_KlondikeStack.cpp + +temp/moc/moc_KlondikeFlipStack.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + KlondikeFlipStack.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 KlondikeFlipStack.h -o temp\moc\moc_KlondikeFlipStack.cpp + +temp/moc/moc_KlondikeHomeStack.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + KlondikeHomeStack.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 KlondikeHomeStack.h -o temp\moc\moc_KlondikeHomeStack.cpp + +temp/moc/moc_KlondikeBoard.cpp: GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + KlondikeStack.h \ + VCardStack.h \ + KlondikeHomeStack.h \ + KlondikeFlipStack.h \ + StackToStackFlipAni.h \ + KlondikeBoard.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 KlondikeBoard.h -o temp\moc\moc_KlondikeBoard.cpp + +temp/moc/moc_FreeCellBoard.cpp: GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + FreeCellDeck.h \ + FreeCellFree.h \ + FreeCellStack.h \ + VCardStack.h \ + FreeCellHome.h \ + FreeCellBoard.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 FreeCellBoard.h -o temp\moc\moc_FreeCellBoard.cpp + +temp/moc/moc_FreeCellDeck.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + FreeCellDeck.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 FreeCellDeck.h -o temp\moc\moc_FreeCellDeck.cpp + +temp/moc/moc_FreeCellStack.cpp: VCardStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + FreeCellStack.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 FreeCellStack.h -o temp\moc\moc_FreeCellStack.cpp + +temp/moc/moc_FreeCellHome.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + FreeCellHome.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 FreeCellHome.h -o temp\moc\moc_FreeCellHome.cpp + +temp/moc/moc_FreeCellFree.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + FreeCellFree.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 FreeCellFree.h -o temp\moc\moc_FreeCellFree.cpp + +temp/moc/moc_Spider3DeckBoard.cpp: SpiderBoard.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + SpiderStack.h \ + VCardStack.h \ + SpiderHomeStack.h \ + Spider3DeckBoard.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 Spider3DeckBoard.h -o temp\moc\moc_Spider3DeckBoard.cpp + +temp/moc/moc_SpideretteBoard.cpp: SpiderBoard.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + SpiderStack.h \ + VCardStack.h \ + SpiderHomeStack.h \ + SpideretteBoard.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 SpideretteBoard.h -o temp\moc\moc_SpideretteBoard.cpp + +temp/moc/moc_YukonBoard.cpp: GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + FreeCellHome.h \ + FreeCellDeck.h \ + KlondikeStack.h \ + VCardStack.h \ + YukonBoard.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 YukonBoard.h -o temp\moc\moc_YukonBoard.cpp + +compiler_rcc_make_all: temp/qrc/qrc_QSoloCards.cpp +compiler_rcc_clean: + -$(DEL_FILE) temp\qrc\qrc_QSoloCards.cpp +temp/qrc/qrc_QSoloCards.cpp: QSoloCards.qrc \ + images/greenfelt.png \ + images/anglo_bitmap.svg \ + images/sol128x128.png \ + images/sol32x32.png \ + help/FreeCellHelp.html \ + help/SpideretteHelp.html \ + help/YukonHelp.html \ + help/SpiderHelp.html \ + help/Spider3DeckHelp.html \ + help/KlondikeHelp.html \ + help/gpl3.html + d:\Qt\2010.01\qt\bin\rcc.exe -name QSoloCards QSoloCards.qrc -o temp\qrc\qrc_QSoloCards.cpp + +compiler_image_collection_make_all: qmake_image_collection.cpp +compiler_image_collection_clean: + -$(DEL_FILE) qmake_image_collection.cpp +compiler_moc_source_make_all: +compiler_moc_source_clean: +compiler_uic_make_all: +compiler_uic_clean: +compiler_yacc_decl_make_all: +compiler_yacc_decl_clean: +compiler_yacc_impl_make_all: +compiler_yacc_impl_clean: +compiler_lex_make_all: +compiler_lex_clean: +compiler_clean: compiler_moc_header_clean compiler_rcc_clean + + + +####### Compile + +temp/obj/QSoloCardsPlugin.o: QSoloCardsPlugin.cpp QSoloCardsPlugin.h \ + mainwindow.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + Help.h \ + About.h \ + GameMgr.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\QSoloCardsPlugin.o QSoloCardsPlugin.cpp + +temp/obj/main.o: main.cpp mainwindow.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + Help.h \ + About.h \ + GameMgr.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\main.o main.cpp + +temp/obj/mainwindow.o: mainwindow.cpp mainwindow.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + Help.h \ + About.h \ + GameMgr.h \ + CardAnimationLock.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\mainwindow.o mainwindow.cpp + +temp/obj/PlayingCard.o: PlayingCard.cpp PlayingCard.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\PlayingCard.o PlayingCard.cpp + +temp/obj/CardDeck.o: CardDeck.cpp CardDeck.h \ + PlayingCard.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\CardDeck.o CardDeck.cpp + +temp/obj/CardPixmaps.o: CardPixmaps.cpp CardPixmaps.h \ + PlayingCard.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\CardPixmaps.o CardPixmaps.cpp + +temp/obj/CardStack.o: CardStack.cpp CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + CardPixmaps.h \ + CardAnimationLock.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\CardStack.o CardStack.cpp + +temp/obj/DragCardStack.o: DragCardStack.cpp DragCardStack.h \ + CardDeck.h \ + PlayingCard.h \ + CardMoveRecord.h \ + CardStack.h \ + FlipAnimation.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\DragCardStack.o DragCardStack.cpp + +temp/obj/VCardStack.o: VCardStack.cpp VCardStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + CardPixmaps.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\VCardStack.o VCardStack.cpp + +temp/obj/CardAnimationLock.o: CardAnimationLock.cpp CardAnimationLock.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\CardAnimationLock.o CardAnimationLock.cpp + +temp/obj/StackToStackAniMove.o: StackToStackAniMove.cpp StackToStackAniMove.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + CardAnimationLock.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\StackToStackAniMove.o StackToStackAniMove.cpp + +temp/obj/DealAnimation.o: DealAnimation.cpp DealAnimation.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + CardAnimationLock.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\DealAnimation.o DealAnimation.cpp + +temp/obj/FlipAnimation.o: FlipAnimation.cpp FlipAnimation.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + CardStack.h \ + DragCardStack.h \ + CardAnimationLock.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\FlipAnimation.o FlipAnimation.cpp + +temp/obj/StackToStackFlipAni.o: StackToStackFlipAni.cpp StackToStackFlipAni.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + CardAnimationLock.h \ + CardPixmaps.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\StackToStackFlipAni.o StackToStackFlipAni.cpp + +temp/obj/GameBoard.o: GameBoard.cpp GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + CardPixmaps.h \ + CardAnimationLock.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\GameBoard.o GameBoard.cpp + +temp/obj/CardMoveRecord.o: CardMoveRecord.cpp CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\CardMoveRecord.o CardMoveRecord.cpp + +temp/obj/About.o: About.cpp About.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\About.o About.cpp + +temp/obj/Help.o: Help.cpp Help.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\Help.o Help.cpp + +temp/obj/GameMgr.o: GameMgr.cpp GameMgr.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + SpiderBoard.h \ + SpiderStack.h \ + VCardStack.h \ + SpiderHomeStack.h \ + Spider3DeckBoard.h \ + SpideretteBoard.h \ + KlondikeBoard.h \ + KlondikeStack.h \ + KlondikeHomeStack.h \ + KlondikeFlipStack.h \ + StackToStackFlipAni.h \ + FreeCellBoard.h \ + FreeCellDeck.h \ + FreeCellFree.h \ + FreeCellStack.h \ + FreeCellHome.h \ + YukonBoard.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\GameMgr.o GameMgr.cpp + +temp/obj/SpiderBoard.o: SpiderBoard.cpp SpiderBoard.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + SpiderStack.h \ + VCardStack.h \ + SpiderHomeStack.h \ + CardPixmaps.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\SpiderBoard.o SpiderBoard.cpp + +temp/obj/SpiderHomeStack.o: SpiderHomeStack.cpp SpiderHomeStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\SpiderHomeStack.o SpiderHomeStack.cpp + +temp/obj/SpiderStack.o: SpiderStack.cpp SpiderStack.h \ + VCardStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + SpiderHomeStack.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\SpiderStack.o SpiderStack.cpp + +temp/obj/KlondikeStack.o: KlondikeStack.cpp KlondikeStack.h \ + VCardStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\KlondikeStack.o KlondikeStack.cpp + +temp/obj/KlondikeFlipStack.o: KlondikeFlipStack.cpp KlondikeFlipStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + CardPixmaps.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\KlondikeFlipStack.o KlondikeFlipStack.cpp + +temp/obj/KlondikeHomeStack.o: KlondikeHomeStack.cpp KlondikeHomeStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\KlondikeHomeStack.o KlondikeHomeStack.cpp + +temp/obj/KlondikeBoard.o: KlondikeBoard.cpp KlondikeBoard.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + KlondikeStack.h \ + VCardStack.h \ + KlondikeHomeStack.h \ + KlondikeFlipStack.h \ + StackToStackFlipAni.h \ + CardPixmaps.h \ + CardAnimationLock.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\KlondikeBoard.o KlondikeBoard.cpp + +temp/obj/FreeCellBoard.o: FreeCellBoard.cpp FreeCellBoard.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + FreeCellDeck.h \ + FreeCellFree.h \ + FreeCellStack.h \ + VCardStack.h \ + FreeCellHome.h \ + CardPixmaps.h \ + CardAnimationLock.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\FreeCellBoard.o FreeCellBoard.cpp + +temp/obj/FreeCellDeck.o: FreeCellDeck.cpp FreeCellDeck.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + CardPixmaps.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\FreeCellDeck.o FreeCellDeck.cpp + +temp/obj/FreeCellStack.o: FreeCellStack.cpp FreeCellStack.h \ + VCardStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\FreeCellStack.o FreeCellStack.cpp + +temp/obj/FreeCellHome.o: FreeCellHome.cpp FreeCellHome.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\FreeCellHome.o FreeCellHome.cpp + +temp/obj/FreeCellFree.o: FreeCellFree.cpp FreeCellFree.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\FreeCellFree.o FreeCellFree.cpp + +temp/obj/Spider3DeckBoard.o: Spider3DeckBoard.cpp Spider3DeckBoard.h \ + SpiderBoard.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + SpiderStack.h \ + VCardStack.h \ + SpiderHomeStack.h \ + CardPixmaps.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\Spider3DeckBoard.o Spider3DeckBoard.cpp + +temp/obj/SpideretteBoard.o: SpideretteBoard.cpp SpideretteBoard.h \ + SpiderBoard.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + SpiderStack.h \ + VCardStack.h \ + SpiderHomeStack.h \ + CardPixmaps.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\SpideretteBoard.o SpideretteBoard.cpp + +temp/obj/YukonBoard.o: YukonBoard.cpp YukonBoard.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + FreeCellHome.h \ + FreeCellDeck.h \ + KlondikeStack.h \ + VCardStack.h \ + CardPixmaps.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\YukonBoard.o YukonBoard.cpp + +temp/obj/moc_QSoloCardsPlugin.o: temp/moc/moc_QSoloCardsPlugin.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_QSoloCardsPlugin.o temp\moc\moc_QSoloCardsPlugin.cpp + +temp/obj/moc_mainwindow.o: temp/moc/moc_mainwindow.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_mainwindow.o temp\moc\moc_mainwindow.cpp + +temp/obj/moc_CardStack.o: temp/moc/moc_CardStack.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_CardStack.o temp\moc\moc_CardStack.cpp + +temp/obj/moc_DragCardStack.o: temp/moc/moc_DragCardStack.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_DragCardStack.o temp\moc\moc_DragCardStack.cpp + +temp/obj/moc_VCardStack.o: temp/moc/moc_VCardStack.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_VCardStack.o temp\moc\moc_VCardStack.cpp + +temp/obj/moc_CardAnimationLock.o: temp/moc/moc_CardAnimationLock.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_CardAnimationLock.o temp\moc\moc_CardAnimationLock.cpp + +temp/obj/moc_StackToStackAniMove.o: temp/moc/moc_StackToStackAniMove.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_StackToStackAniMove.o temp\moc\moc_StackToStackAniMove.cpp + +temp/obj/moc_DealAnimation.o: temp/moc/moc_DealAnimation.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_DealAnimation.o temp\moc\moc_DealAnimation.cpp + +temp/obj/moc_FlipAnimation.o: temp/moc/moc_FlipAnimation.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_FlipAnimation.o temp\moc\moc_FlipAnimation.cpp + +temp/obj/moc_StackToStackFlipAni.o: temp/moc/moc_StackToStackFlipAni.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_StackToStackFlipAni.o temp\moc\moc_StackToStackFlipAni.cpp + +temp/obj/moc_GameBoard.o: temp/moc/moc_GameBoard.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_GameBoard.o temp\moc\moc_GameBoard.cpp + +temp/obj/moc_About.o: temp/moc/moc_About.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_About.o temp\moc\moc_About.cpp + +temp/obj/moc_Help.o: temp/moc/moc_Help.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_Help.o temp\moc\moc_Help.cpp + +temp/obj/moc_SpiderBoard.o: temp/moc/moc_SpiderBoard.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_SpiderBoard.o temp\moc\moc_SpiderBoard.cpp + +temp/obj/moc_SpiderStack.o: temp/moc/moc_SpiderStack.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_SpiderStack.o temp\moc\moc_SpiderStack.cpp + +temp/obj/moc_KlondikeStack.o: temp/moc/moc_KlondikeStack.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_KlondikeStack.o temp\moc\moc_KlondikeStack.cpp + +temp/obj/moc_KlondikeFlipStack.o: temp/moc/moc_KlondikeFlipStack.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_KlondikeFlipStack.o temp\moc\moc_KlondikeFlipStack.cpp + +temp/obj/moc_KlondikeHomeStack.o: temp/moc/moc_KlondikeHomeStack.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_KlondikeHomeStack.o temp\moc\moc_KlondikeHomeStack.cpp + +temp/obj/moc_KlondikeBoard.o: temp/moc/moc_KlondikeBoard.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_KlondikeBoard.o temp\moc\moc_KlondikeBoard.cpp + +temp/obj/moc_FreeCellBoard.o: temp/moc/moc_FreeCellBoard.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_FreeCellBoard.o temp\moc\moc_FreeCellBoard.cpp + +temp/obj/moc_FreeCellDeck.o: temp/moc/moc_FreeCellDeck.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_FreeCellDeck.o temp\moc\moc_FreeCellDeck.cpp + +temp/obj/moc_FreeCellStack.o: temp/moc/moc_FreeCellStack.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_FreeCellStack.o temp\moc\moc_FreeCellStack.cpp + +temp/obj/moc_FreeCellHome.o: temp/moc/moc_FreeCellHome.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_FreeCellHome.o temp\moc\moc_FreeCellHome.cpp + +temp/obj/moc_FreeCellFree.o: temp/moc/moc_FreeCellFree.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_FreeCellFree.o temp\moc\moc_FreeCellFree.cpp + +temp/obj/moc_Spider3DeckBoard.o: temp/moc/moc_Spider3DeckBoard.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_Spider3DeckBoard.o temp\moc\moc_Spider3DeckBoard.cpp + +temp/obj/moc_SpideretteBoard.o: temp/moc/moc_SpideretteBoard.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_SpideretteBoard.o temp\moc\moc_SpideretteBoard.cpp + +temp/obj/moc_YukonBoard.o: temp/moc/moc_YukonBoard.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_YukonBoard.o temp\moc\moc_YukonBoard.cpp + +temp/obj/qrc_QSoloCards.o: temp/qrc/qrc_QSoloCards.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\qrc_QSoloCards.o temp\qrc\qrc_QSoloCards.cpp + +####### Install + +install: FORCE + +uninstall: FORCE + +FORCE: + diff --git a/plugins/qsolocards_plugin/Makefile.Release b/plugins/qsolocards_plugin/Makefile.Release new file mode 100644 index 000000000..df4410744 --- /dev/null +++ b/plugins/qsolocards_plugin/Makefile.Release @@ -0,0 +1,991 @@ +############################################################################# +# Makefile for building: qsolocards_plugin +# Generated by qmake (2.01a) (Qt 4.6.1) on: Mo 15. Feb 12:18:26 2010 +# Project: qsolocards_plugin.pro +# Template: lib +############################################################################# + +####### Compiler, tools and options + +CC = gcc +CXX = g++ +DEFINES = -DUNICODE -DQT_LARGEFILE_SUPPORT -DQT_DLL -DQT_NO_DEBUG -DQT_PLUGIN -DQT_SVG_LIB -DQT_GUI_LIB -DQT_CORE_LIB -DQT_THREAD_SUPPORT +CFLAGS = -O2 -Wall $(DEFINES) +CXXFLAGS = -DVER_MAJ=0 -DVER_MIN=99 -DVER_PAT=1 -frtti -fexceptions -mthreads -Wall $(DEFINES) +INCPATH = -I"d:\Qt\2010.01\qt\include\QtCore" -I"d:\Qt\2010.01\qt\include\QtGui" -I"d:\Qt\2010.01\qt\include\QtSvg" -I"d:\Qt\2010.01\qt\include" -I".." -I"d:\Qt\2010.01\qt\include\ActiveQt" -I"temp\moc" -I"d:\Qt\2010.01\qt\mkspecs\default" +LINK = g++ +LFLAGS = -enable-stdcall-fixup -Wl,-enable-auto-import -Wl,-enable-runtime-pseudo-reloc -Wl,-s -mthreads -Wl -shared -Wl,--out-implib,..\..\bin\libqsolocards_plugin0.a +LIBS = -L"d:\Qt\2010.01\qt\lib" -lQtSvg4 -lQtGui4 -lQtCore4 +QMAKE = d:\qt\2010.01\qt\bin\qmake.exe +IDC = d:\Qt\2010.01\qt\bin\idc.exe +IDL = midl +ZIP = zip -r -9 +DEF_FILE = +RES_FILE = +COPY = copy /y +COPY_FILE = $(COPY) +COPY_DIR = xcopy /s /q /y /i +DEL_FILE = del +DEL_DIR = rmdir +MOVE = move +CHK_DIR_EXISTS= if not exist +MKDIR = mkdir +INSTALL_FILE = $(COPY_FILE) +INSTALL_PROGRAM = $(COPY_FILE) +INSTALL_DIR = $(COPY_DIR) + +####### Output directory + +OBJECTS_DIR = temp\obj + +####### Files + +SOURCES = QSoloCardsPlugin.cpp \ + main.cpp \ + mainwindow.cpp \ + PlayingCard.cpp \ + CardDeck.cpp \ + CardPixmaps.cpp \ + CardStack.cpp \ + DragCardStack.cpp \ + VCardStack.cpp \ + CardAnimationLock.cpp \ + StackToStackAniMove.cpp \ + DealAnimation.cpp \ + FlipAnimation.cpp \ + StackToStackFlipAni.cpp \ + GameBoard.cpp \ + CardMoveRecord.cpp \ + About.cpp \ + Help.cpp \ + GameMgr.cpp \ + SpiderBoard.cpp \ + SpiderHomeStack.cpp \ + SpiderStack.cpp \ + KlondikeStack.cpp \ + KlondikeFlipStack.cpp \ + KlondikeHomeStack.cpp \ + KlondikeBoard.cpp \ + FreeCellBoard.cpp \ + FreeCellDeck.cpp \ + FreeCellStack.cpp \ + FreeCellHome.cpp \ + FreeCellFree.cpp \ + Spider3DeckBoard.cpp \ + SpideretteBoard.cpp \ + YukonBoard.cpp temp\moc\moc_QSoloCardsPlugin.cpp \ + temp\moc\moc_mainwindow.cpp \ + temp\moc\moc_CardStack.cpp \ + temp\moc\moc_DragCardStack.cpp \ + temp\moc\moc_VCardStack.cpp \ + temp\moc\moc_CardAnimationLock.cpp \ + temp\moc\moc_StackToStackAniMove.cpp \ + temp\moc\moc_DealAnimation.cpp \ + temp\moc\moc_FlipAnimation.cpp \ + temp\moc\moc_StackToStackFlipAni.cpp \ + temp\moc\moc_GameBoard.cpp \ + temp\moc\moc_About.cpp \ + temp\moc\moc_Help.cpp \ + temp\moc\moc_SpiderBoard.cpp \ + temp\moc\moc_SpiderStack.cpp \ + temp\moc\moc_KlondikeStack.cpp \ + temp\moc\moc_KlondikeFlipStack.cpp \ + temp\moc\moc_KlondikeHomeStack.cpp \ + temp\moc\moc_KlondikeBoard.cpp \ + temp\moc\moc_FreeCellBoard.cpp \ + temp\moc\moc_FreeCellDeck.cpp \ + temp\moc\moc_FreeCellStack.cpp \ + temp\moc\moc_FreeCellHome.cpp \ + temp\moc\moc_FreeCellFree.cpp \ + temp\moc\moc_Spider3DeckBoard.cpp \ + temp\moc\moc_SpideretteBoard.cpp \ + temp\moc\moc_YukonBoard.cpp \ + temp\qrc\qrc_QSoloCards.cpp +OBJECTS = temp/obj/QSoloCardsPlugin.o \ + temp/obj/main.o \ + temp/obj/mainwindow.o \ + temp/obj/PlayingCard.o \ + temp/obj/CardDeck.o \ + temp/obj/CardPixmaps.o \ + temp/obj/CardStack.o \ + temp/obj/DragCardStack.o \ + temp/obj/VCardStack.o \ + temp/obj/CardAnimationLock.o \ + temp/obj/StackToStackAniMove.o \ + temp/obj/DealAnimation.o \ + temp/obj/FlipAnimation.o \ + temp/obj/StackToStackFlipAni.o \ + temp/obj/GameBoard.o \ + temp/obj/CardMoveRecord.o \ + temp/obj/About.o \ + temp/obj/Help.o \ + temp/obj/GameMgr.o \ + temp/obj/SpiderBoard.o \ + temp/obj/SpiderHomeStack.o \ + temp/obj/SpiderStack.o \ + temp/obj/KlondikeStack.o \ + temp/obj/KlondikeFlipStack.o \ + temp/obj/KlondikeHomeStack.o \ + temp/obj/KlondikeBoard.o \ + temp/obj/FreeCellBoard.o \ + temp/obj/FreeCellDeck.o \ + temp/obj/FreeCellStack.o \ + temp/obj/FreeCellHome.o \ + temp/obj/FreeCellFree.o \ + temp/obj/Spider3DeckBoard.o \ + temp/obj/SpideretteBoard.o \ + temp/obj/YukonBoard.o \ + temp/obj/moc_QSoloCardsPlugin.o \ + temp/obj/moc_mainwindow.o \ + temp/obj/moc_CardStack.o \ + temp/obj/moc_DragCardStack.o \ + temp/obj/moc_VCardStack.o \ + temp/obj/moc_CardAnimationLock.o \ + temp/obj/moc_StackToStackAniMove.o \ + temp/obj/moc_DealAnimation.o \ + temp/obj/moc_FlipAnimation.o \ + temp/obj/moc_StackToStackFlipAni.o \ + temp/obj/moc_GameBoard.o \ + temp/obj/moc_About.o \ + temp/obj/moc_Help.o \ + temp/obj/moc_SpiderBoard.o \ + temp/obj/moc_SpiderStack.o \ + temp/obj/moc_KlondikeStack.o \ + temp/obj/moc_KlondikeFlipStack.o \ + temp/obj/moc_KlondikeHomeStack.o \ + temp/obj/moc_KlondikeBoard.o \ + temp/obj/moc_FreeCellBoard.o \ + temp/obj/moc_FreeCellDeck.o \ + temp/obj/moc_FreeCellStack.o \ + temp/obj/moc_FreeCellHome.o \ + temp/obj/moc_FreeCellFree.o \ + temp/obj/moc_Spider3DeckBoard.o \ + temp/obj/moc_SpideretteBoard.o \ + temp/obj/moc_YukonBoard.o \ + temp/obj/qrc_QSoloCards.o +DIST = +QMAKE_TARGET = qsolocards_plugin +DESTDIR = ..\..\bin\ #avoid trailing-slash linebreak +TARGET = qsolocards_plugin0.dll +DESTDIR_TARGET = ..\..\bin\qsolocards_plugin0.dll + +####### Implicit rules + +.SUFFIXES: .cpp .cc .cxx .c + +.cpp.o: + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o $@ $< + +.cc.o: + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o $@ $< + +.cxx.o: + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o $@ $< + +.c.o: + $(CC) -c $(CFLAGS) $(INCPATH) -o $@ $< + +####### Build rules + +first: all +all: Makefile.Release $(DESTDIR_TARGET) + +$(DESTDIR_TARGET): $(OBJECTS) + $(LINK) $(LFLAGS) -o $(DESTDIR_TARGET) object_script.qsolocards_plugin.Release $(LIBS) + + +qmake: FORCE + @$(QMAKE) -win32 -o Makefile.Release qsolocards_plugin.pro + +dist: + $(ZIP) qsolocards_plugin.zip $(SOURCES) $(DIST) qsolocards_plugin.pro d:\Qt\2010.01\qt\mkspecs\qconfig.pri d:\Qt\2010.01\qt\mkspecs\features\qt_functions.prf d:\Qt\2010.01\qt\mkspecs\features\qt_config.prf d:\Qt\2010.01\qt\mkspecs\features\exclusive_builds.prf d:\Qt\2010.01\qt\mkspecs\features\default_pre.prf d:\Qt\2010.01\qt\mkspecs\features\win32\default_pre.prf d:\Qt\2010.01\qt\mkspecs\features\release.prf d:\Qt\2010.01\qt\mkspecs\features\debug_and_release.prf d:\Qt\2010.01\qt\mkspecs\features\default_post.prf d:\Qt\2010.01\qt\mkspecs\features\win32\default_post.prf d:\Qt\2010.01\qt\mkspecs\features\build_pass.prf d:\Qt\2010.01\qt\mkspecs\features\win32\rtti.prf d:\Qt\2010.01\qt\mkspecs\features\win32\exceptions.prf d:\Qt\2010.01\qt\mkspecs\features\win32\stl.prf d:\Qt\2010.01\qt\mkspecs\features\shared.prf d:\Qt\2010.01\qt\mkspecs\features\dll.prf d:\Qt\2010.01\qt\mkspecs\features\warn_on.prf d:\Qt\2010.01\qt\mkspecs\features\qt.prf d:\Qt\2010.01\qt\mkspecs\features\win32\thread.prf d:\Qt\2010.01\qt\mkspecs\features\moc.prf d:\Qt\2010.01\qt\mkspecs\features\win32\windows.prf d:\Qt\2010.01\qt\mkspecs\features\resources.prf d:\Qt\2010.01\qt\mkspecs\features\uic.prf d:\Qt\2010.01\qt\mkspecs\features\yacc.prf d:\Qt\2010.01\qt\mkspecs\features\lex.prf HEADERS RESOURCES IMAGES SOURCES OBJECTIVE_SOURCES FORMS YACCSOURCES YACCSOURCES LEXSOURCES + +clean: compiler_clean + -$(DEL_FILE) temp\obj\QSoloCardsPlugin.o temp\obj\main.o temp\obj\mainwindow.o temp\obj\PlayingCard.o temp\obj\CardDeck.o temp\obj\CardPixmaps.o temp\obj\CardStack.o temp\obj\DragCardStack.o temp\obj\VCardStack.o temp\obj\CardAnimationLock.o temp\obj\StackToStackAniMove.o temp\obj\DealAnimation.o temp\obj\FlipAnimation.o temp\obj\StackToStackFlipAni.o temp\obj\GameBoard.o temp\obj\CardMoveRecord.o temp\obj\About.o temp\obj\Help.o temp\obj\GameMgr.o temp\obj\SpiderBoard.o temp\obj\SpiderHomeStack.o temp\obj\SpiderStack.o temp\obj\KlondikeStack.o temp\obj\KlondikeFlipStack.o temp\obj\KlondikeHomeStack.o temp\obj\KlondikeBoard.o temp\obj\FreeCellBoard.o temp\obj\FreeCellDeck.o temp\obj\FreeCellStack.o temp\obj\FreeCellHome.o temp\obj\FreeCellFree.o temp\obj\Spider3DeckBoard.o temp\obj\SpideretteBoard.o temp\obj\YukonBoard.o temp\obj\moc_QSoloCardsPlugin.o temp\obj\moc_mainwindow.o temp\obj\moc_CardStack.o temp\obj\moc_DragCardStack.o temp\obj\moc_VCardStack.o temp\obj\moc_CardAnimationLock.o temp\obj\moc_StackToStackAniMove.o temp\obj\moc_DealAnimation.o temp\obj\moc_FlipAnimation.o temp\obj\moc_StackToStackFlipAni.o temp\obj\moc_GameBoard.o temp\obj\moc_About.o temp\obj\moc_Help.o temp\obj\moc_SpiderBoard.o temp\obj\moc_SpiderStack.o temp\obj\moc_KlondikeStack.o temp\obj\moc_KlondikeFlipStack.o temp\obj\moc_KlondikeHomeStack.o temp\obj\moc_KlondikeBoard.o temp\obj\moc_FreeCellBoard.o temp\obj\moc_FreeCellDeck.o temp\obj\moc_FreeCellStack.o temp\obj\moc_FreeCellHome.o temp\obj\moc_FreeCellFree.o temp\obj\moc_Spider3DeckBoard.o temp\obj\moc_SpideretteBoard.o temp\obj\moc_YukonBoard.o temp\obj\qrc_QSoloCards.o + -$(DEL_FILE) ..\..\bin\libqsolocards_plugin0.a + +distclean: clean + -$(DEL_FILE) $(DESTDIR_TARGET) + -$(DEL_FILE) Makefile.Release + +mocclean: compiler_moc_header_clean compiler_moc_source_clean + +mocables: compiler_moc_header_make_all compiler_moc_source_make_all + +compiler_moc_header_make_all: temp/moc/moc_QSoloCardsPlugin.cpp temp/moc/moc_mainwindow.cpp temp/moc/moc_CardStack.cpp temp/moc/moc_DragCardStack.cpp temp/moc/moc_VCardStack.cpp temp/moc/moc_CardAnimationLock.cpp temp/moc/moc_StackToStackAniMove.cpp temp/moc/moc_DealAnimation.cpp temp/moc/moc_FlipAnimation.cpp temp/moc/moc_StackToStackFlipAni.cpp temp/moc/moc_GameBoard.cpp temp/moc/moc_About.cpp temp/moc/moc_Help.cpp temp/moc/moc_SpiderBoard.cpp temp/moc/moc_SpiderStack.cpp temp/moc/moc_KlondikeStack.cpp temp/moc/moc_KlondikeFlipStack.cpp temp/moc/moc_KlondikeHomeStack.cpp temp/moc/moc_KlondikeBoard.cpp temp/moc/moc_FreeCellBoard.cpp temp/moc/moc_FreeCellDeck.cpp temp/moc/moc_FreeCellStack.cpp temp/moc/moc_FreeCellHome.cpp temp/moc/moc_FreeCellFree.cpp temp/moc/moc_Spider3DeckBoard.cpp temp/moc/moc_SpideretteBoard.cpp temp/moc/moc_YukonBoard.cpp +compiler_moc_header_clean: + -$(DEL_FILE) temp\moc\moc_QSoloCardsPlugin.cpp temp\moc\moc_mainwindow.cpp temp\moc\moc_CardStack.cpp temp\moc\moc_DragCardStack.cpp temp\moc\moc_VCardStack.cpp temp\moc\moc_CardAnimationLock.cpp temp\moc\moc_StackToStackAniMove.cpp temp\moc\moc_DealAnimation.cpp temp\moc\moc_FlipAnimation.cpp temp\moc\moc_StackToStackFlipAni.cpp temp\moc\moc_GameBoard.cpp temp\moc\moc_About.cpp temp\moc\moc_Help.cpp temp\moc\moc_SpiderBoard.cpp temp\moc\moc_SpiderStack.cpp temp\moc\moc_KlondikeStack.cpp temp\moc\moc_KlondikeFlipStack.cpp temp\moc\moc_KlondikeHomeStack.cpp temp\moc\moc_KlondikeBoard.cpp temp\moc\moc_FreeCellBoard.cpp temp\moc\moc_FreeCellDeck.cpp temp\moc\moc_FreeCellStack.cpp temp\moc\moc_FreeCellHome.cpp temp\moc\moc_FreeCellFree.cpp temp\moc\moc_Spider3DeckBoard.cpp temp\moc\moc_SpideretteBoard.cpp temp\moc\moc_YukonBoard.cpp +temp/moc/moc_QSoloCardsPlugin.cpp: QSoloCardsPlugin.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 QSoloCardsPlugin.h -o temp\moc\moc_QSoloCardsPlugin.cpp + +temp/moc/moc_mainwindow.cpp: GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + Help.h \ + About.h \ + GameMgr.h \ + mainwindow.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 mainwindow.h -o temp\moc\moc_mainwindow.cpp + +temp/moc/moc_CardStack.cpp: CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + CardStack.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 CardStack.h -o temp\moc\moc_CardStack.cpp + +temp/moc/moc_DragCardStack.cpp: CardDeck.h \ + PlayingCard.h \ + CardMoveRecord.h \ + DragCardStack.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 DragCardStack.h -o temp\moc\moc_DragCardStack.cpp + +temp/moc/moc_VCardStack.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + VCardStack.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 VCardStack.h -o temp\moc\moc_VCardStack.cpp + +temp/moc/moc_CardAnimationLock.cpp: CardAnimationLock.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 CardAnimationLock.h -o temp\moc\moc_CardAnimationLock.cpp + +temp/moc/moc_StackToStackAniMove.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 StackToStackAniMove.h -o temp\moc\moc_StackToStackAniMove.cpp + +temp/moc/moc_DealAnimation.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + DealAnimation.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 DealAnimation.h -o temp\moc\moc_DealAnimation.cpp + +temp/moc/moc_FlipAnimation.cpp: CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 FlipAnimation.h -o temp\moc\moc_FlipAnimation.cpp + +temp/moc/moc_StackToStackFlipAni.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackFlipAni.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 StackToStackFlipAni.h -o temp\moc\moc_StackToStackFlipAni.cpp + +temp/moc/moc_GameBoard.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + GameBoard.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 GameBoard.h -o temp\moc\moc_GameBoard.cpp + +temp/moc/moc_About.cpp: About.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 About.h -o temp\moc\moc_About.cpp + +temp/moc/moc_Help.cpp: Help.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 Help.h -o temp\moc\moc_Help.cpp + +temp/moc/moc_SpiderBoard.cpp: GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + SpiderStack.h \ + VCardStack.h \ + SpiderHomeStack.h \ + SpiderBoard.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 SpiderBoard.h -o temp\moc\moc_SpiderBoard.cpp + +temp/moc/moc_SpiderStack.cpp: VCardStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + SpiderStack.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 SpiderStack.h -o temp\moc\moc_SpiderStack.cpp + +temp/moc/moc_KlondikeStack.cpp: VCardStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + KlondikeStack.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 KlondikeStack.h -o temp\moc\moc_KlondikeStack.cpp + +temp/moc/moc_KlondikeFlipStack.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + KlondikeFlipStack.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 KlondikeFlipStack.h -o temp\moc\moc_KlondikeFlipStack.cpp + +temp/moc/moc_KlondikeHomeStack.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + KlondikeHomeStack.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 KlondikeHomeStack.h -o temp\moc\moc_KlondikeHomeStack.cpp + +temp/moc/moc_KlondikeBoard.cpp: GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + KlondikeStack.h \ + VCardStack.h \ + KlondikeHomeStack.h \ + KlondikeFlipStack.h \ + StackToStackFlipAni.h \ + KlondikeBoard.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 KlondikeBoard.h -o temp\moc\moc_KlondikeBoard.cpp + +temp/moc/moc_FreeCellBoard.cpp: GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + FreeCellDeck.h \ + FreeCellFree.h \ + FreeCellStack.h \ + VCardStack.h \ + FreeCellHome.h \ + FreeCellBoard.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 FreeCellBoard.h -o temp\moc\moc_FreeCellBoard.cpp + +temp/moc/moc_FreeCellDeck.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + FreeCellDeck.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 FreeCellDeck.h -o temp\moc\moc_FreeCellDeck.cpp + +temp/moc/moc_FreeCellStack.cpp: VCardStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + FreeCellStack.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 FreeCellStack.h -o temp\moc\moc_FreeCellStack.cpp + +temp/moc/moc_FreeCellHome.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + FreeCellHome.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 FreeCellHome.h -o temp\moc\moc_FreeCellHome.cpp + +temp/moc/moc_FreeCellFree.cpp: CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + FreeCellFree.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 FreeCellFree.h -o temp\moc\moc_FreeCellFree.cpp + +temp/moc/moc_Spider3DeckBoard.cpp: SpiderBoard.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + SpiderStack.h \ + VCardStack.h \ + SpiderHomeStack.h \ + Spider3DeckBoard.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 Spider3DeckBoard.h -o temp\moc\moc_Spider3DeckBoard.cpp + +temp/moc/moc_SpideretteBoard.cpp: SpiderBoard.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + SpiderStack.h \ + VCardStack.h \ + SpiderHomeStack.h \ + SpideretteBoard.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 SpideretteBoard.h -o temp\moc\moc_SpideretteBoard.cpp + +temp/moc/moc_YukonBoard.cpp: GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + FreeCellHome.h \ + FreeCellDeck.h \ + KlondikeStack.h \ + VCardStack.h \ + YukonBoard.h + d:/Qt/2010.01/qt/bin\moc.exe $(DEFINES) $(INCPATH) -D__GNUC__ -DWIN32 YukonBoard.h -o temp\moc\moc_YukonBoard.cpp + +compiler_rcc_make_all: temp/qrc/qrc_QSoloCards.cpp +compiler_rcc_clean: + -$(DEL_FILE) temp\qrc\qrc_QSoloCards.cpp +temp/qrc/qrc_QSoloCards.cpp: QSoloCards.qrc \ + images/greenfelt.png \ + images/anglo_bitmap.svg \ + images/sol128x128.png \ + images/sol32x32.png \ + help/FreeCellHelp.html \ + help/SpideretteHelp.html \ + help/YukonHelp.html \ + help/SpiderHelp.html \ + help/Spider3DeckHelp.html \ + help/KlondikeHelp.html \ + help/gpl3.html + d:\Qt\2010.01\qt\bin\rcc.exe -name QSoloCards QSoloCards.qrc -o temp\qrc\qrc_QSoloCards.cpp + +compiler_image_collection_make_all: qmake_image_collection.cpp +compiler_image_collection_clean: + -$(DEL_FILE) qmake_image_collection.cpp +compiler_moc_source_make_all: +compiler_moc_source_clean: +compiler_uic_make_all: +compiler_uic_clean: +compiler_yacc_decl_make_all: +compiler_yacc_decl_clean: +compiler_yacc_impl_make_all: +compiler_yacc_impl_clean: +compiler_lex_make_all: +compiler_lex_clean: +compiler_clean: compiler_moc_header_clean compiler_rcc_clean + + + +####### Compile + +temp/obj/QSoloCardsPlugin.o: QSoloCardsPlugin.cpp QSoloCardsPlugin.h \ + mainwindow.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + Help.h \ + About.h \ + GameMgr.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\QSoloCardsPlugin.o QSoloCardsPlugin.cpp + +temp/obj/main.o: main.cpp mainwindow.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + Help.h \ + About.h \ + GameMgr.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\main.o main.cpp + +temp/obj/mainwindow.o: mainwindow.cpp mainwindow.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + Help.h \ + About.h \ + GameMgr.h \ + CardAnimationLock.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\mainwindow.o mainwindow.cpp + +temp/obj/PlayingCard.o: PlayingCard.cpp PlayingCard.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\PlayingCard.o PlayingCard.cpp + +temp/obj/CardDeck.o: CardDeck.cpp CardDeck.h \ + PlayingCard.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\CardDeck.o CardDeck.cpp + +temp/obj/CardPixmaps.o: CardPixmaps.cpp CardPixmaps.h \ + PlayingCard.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\CardPixmaps.o CardPixmaps.cpp + +temp/obj/CardStack.o: CardStack.cpp CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + CardPixmaps.h \ + CardAnimationLock.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\CardStack.o CardStack.cpp + +temp/obj/DragCardStack.o: DragCardStack.cpp DragCardStack.h \ + CardDeck.h \ + PlayingCard.h \ + CardMoveRecord.h \ + CardStack.h \ + FlipAnimation.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\DragCardStack.o DragCardStack.cpp + +temp/obj/VCardStack.o: VCardStack.cpp VCardStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + CardPixmaps.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\VCardStack.o VCardStack.cpp + +temp/obj/CardAnimationLock.o: CardAnimationLock.cpp CardAnimationLock.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\CardAnimationLock.o CardAnimationLock.cpp + +temp/obj/StackToStackAniMove.o: StackToStackAniMove.cpp StackToStackAniMove.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + CardAnimationLock.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\StackToStackAniMove.o StackToStackAniMove.cpp + +temp/obj/DealAnimation.o: DealAnimation.cpp DealAnimation.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + CardAnimationLock.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\DealAnimation.o DealAnimation.cpp + +temp/obj/FlipAnimation.o: FlipAnimation.cpp FlipAnimation.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + CardStack.h \ + DragCardStack.h \ + CardAnimationLock.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\FlipAnimation.o FlipAnimation.cpp + +temp/obj/StackToStackFlipAni.o: StackToStackFlipAni.cpp StackToStackFlipAni.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + CardAnimationLock.h \ + CardPixmaps.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\StackToStackFlipAni.o StackToStackFlipAni.cpp + +temp/obj/GameBoard.o: GameBoard.cpp GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + CardPixmaps.h \ + CardAnimationLock.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\GameBoard.o GameBoard.cpp + +temp/obj/CardMoveRecord.o: CardMoveRecord.cpp CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\CardMoveRecord.o CardMoveRecord.cpp + +temp/obj/About.o: About.cpp About.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\About.o About.cpp + +temp/obj/Help.o: Help.cpp Help.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\Help.o Help.cpp + +temp/obj/GameMgr.o: GameMgr.cpp GameMgr.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + SpiderBoard.h \ + SpiderStack.h \ + VCardStack.h \ + SpiderHomeStack.h \ + Spider3DeckBoard.h \ + SpideretteBoard.h \ + KlondikeBoard.h \ + KlondikeStack.h \ + KlondikeHomeStack.h \ + KlondikeFlipStack.h \ + StackToStackFlipAni.h \ + FreeCellBoard.h \ + FreeCellDeck.h \ + FreeCellFree.h \ + FreeCellStack.h \ + FreeCellHome.h \ + YukonBoard.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\GameMgr.o GameMgr.cpp + +temp/obj/SpiderBoard.o: SpiderBoard.cpp SpiderBoard.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + SpiderStack.h \ + VCardStack.h \ + SpiderHomeStack.h \ + CardPixmaps.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\SpiderBoard.o SpiderBoard.cpp + +temp/obj/SpiderHomeStack.o: SpiderHomeStack.cpp SpiderHomeStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\SpiderHomeStack.o SpiderHomeStack.cpp + +temp/obj/SpiderStack.o: SpiderStack.cpp SpiderStack.h \ + VCardStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + SpiderHomeStack.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\SpiderStack.o SpiderStack.cpp + +temp/obj/KlondikeStack.o: KlondikeStack.cpp KlondikeStack.h \ + VCardStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\KlondikeStack.o KlondikeStack.cpp + +temp/obj/KlondikeFlipStack.o: KlondikeFlipStack.cpp KlondikeFlipStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + CardPixmaps.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\KlondikeFlipStack.o KlondikeFlipStack.cpp + +temp/obj/KlondikeHomeStack.o: KlondikeHomeStack.cpp KlondikeHomeStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\KlondikeHomeStack.o KlondikeHomeStack.cpp + +temp/obj/KlondikeBoard.o: KlondikeBoard.cpp KlondikeBoard.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + KlondikeStack.h \ + VCardStack.h \ + KlondikeHomeStack.h \ + KlondikeFlipStack.h \ + StackToStackFlipAni.h \ + CardPixmaps.h \ + CardAnimationLock.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\KlondikeBoard.o KlondikeBoard.cpp + +temp/obj/FreeCellBoard.o: FreeCellBoard.cpp FreeCellBoard.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + FreeCellDeck.h \ + FreeCellFree.h \ + FreeCellStack.h \ + VCardStack.h \ + FreeCellHome.h \ + CardPixmaps.h \ + CardAnimationLock.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\FreeCellBoard.o FreeCellBoard.cpp + +temp/obj/FreeCellDeck.o: FreeCellDeck.cpp FreeCellDeck.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + CardPixmaps.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\FreeCellDeck.o FreeCellDeck.cpp + +temp/obj/FreeCellStack.o: FreeCellStack.cpp FreeCellStack.h \ + VCardStack.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\FreeCellStack.o FreeCellStack.cpp + +temp/obj/FreeCellHome.o: FreeCellHome.cpp FreeCellHome.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\FreeCellHome.o FreeCellHome.cpp + +temp/obj/FreeCellFree.o: FreeCellFree.cpp FreeCellFree.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\FreeCellFree.o FreeCellFree.cpp + +temp/obj/Spider3DeckBoard.o: Spider3DeckBoard.cpp Spider3DeckBoard.h \ + SpiderBoard.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + SpiderStack.h \ + VCardStack.h \ + SpiderHomeStack.h \ + CardPixmaps.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\Spider3DeckBoard.o Spider3DeckBoard.cpp + +temp/obj/SpideretteBoard.o: SpideretteBoard.cpp SpideretteBoard.h \ + SpiderBoard.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + SpiderStack.h \ + VCardStack.h \ + SpiderHomeStack.h \ + CardPixmaps.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\SpideretteBoard.o SpideretteBoard.cpp + +temp/obj/YukonBoard.o: YukonBoard.cpp YukonBoard.h \ + GameBoard.h \ + CardStack.h \ + CardMoveRecord.h \ + CardDeck.h \ + PlayingCard.h \ + FlipAnimation.h \ + DragCardStack.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + FreeCellHome.h \ + FreeCellDeck.h \ + KlondikeStack.h \ + VCardStack.h \ + CardPixmaps.h + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\YukonBoard.o YukonBoard.cpp + +temp/obj/moc_QSoloCardsPlugin.o: temp/moc/moc_QSoloCardsPlugin.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_QSoloCardsPlugin.o temp\moc\moc_QSoloCardsPlugin.cpp + +temp/obj/moc_mainwindow.o: temp/moc/moc_mainwindow.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_mainwindow.o temp\moc\moc_mainwindow.cpp + +temp/obj/moc_CardStack.o: temp/moc/moc_CardStack.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_CardStack.o temp\moc\moc_CardStack.cpp + +temp/obj/moc_DragCardStack.o: temp/moc/moc_DragCardStack.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_DragCardStack.o temp\moc\moc_DragCardStack.cpp + +temp/obj/moc_VCardStack.o: temp/moc/moc_VCardStack.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_VCardStack.o temp\moc\moc_VCardStack.cpp + +temp/obj/moc_CardAnimationLock.o: temp/moc/moc_CardAnimationLock.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_CardAnimationLock.o temp\moc\moc_CardAnimationLock.cpp + +temp/obj/moc_StackToStackAniMove.o: temp/moc/moc_StackToStackAniMove.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_StackToStackAniMove.o temp\moc\moc_StackToStackAniMove.cpp + +temp/obj/moc_DealAnimation.o: temp/moc/moc_DealAnimation.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_DealAnimation.o temp\moc\moc_DealAnimation.cpp + +temp/obj/moc_FlipAnimation.o: temp/moc/moc_FlipAnimation.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_FlipAnimation.o temp\moc\moc_FlipAnimation.cpp + +temp/obj/moc_StackToStackFlipAni.o: temp/moc/moc_StackToStackFlipAni.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_StackToStackFlipAni.o temp\moc\moc_StackToStackFlipAni.cpp + +temp/obj/moc_GameBoard.o: temp/moc/moc_GameBoard.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_GameBoard.o temp\moc\moc_GameBoard.cpp + +temp/obj/moc_About.o: temp/moc/moc_About.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_About.o temp\moc\moc_About.cpp + +temp/obj/moc_Help.o: temp/moc/moc_Help.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_Help.o temp\moc\moc_Help.cpp + +temp/obj/moc_SpiderBoard.o: temp/moc/moc_SpiderBoard.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_SpiderBoard.o temp\moc\moc_SpiderBoard.cpp + +temp/obj/moc_SpiderStack.o: temp/moc/moc_SpiderStack.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_SpiderStack.o temp\moc\moc_SpiderStack.cpp + +temp/obj/moc_KlondikeStack.o: temp/moc/moc_KlondikeStack.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_KlondikeStack.o temp\moc\moc_KlondikeStack.cpp + +temp/obj/moc_KlondikeFlipStack.o: temp/moc/moc_KlondikeFlipStack.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_KlondikeFlipStack.o temp\moc\moc_KlondikeFlipStack.cpp + +temp/obj/moc_KlondikeHomeStack.o: temp/moc/moc_KlondikeHomeStack.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_KlondikeHomeStack.o temp\moc\moc_KlondikeHomeStack.cpp + +temp/obj/moc_KlondikeBoard.o: temp/moc/moc_KlondikeBoard.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_KlondikeBoard.o temp\moc\moc_KlondikeBoard.cpp + +temp/obj/moc_FreeCellBoard.o: temp/moc/moc_FreeCellBoard.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_FreeCellBoard.o temp\moc\moc_FreeCellBoard.cpp + +temp/obj/moc_FreeCellDeck.o: temp/moc/moc_FreeCellDeck.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_FreeCellDeck.o temp\moc\moc_FreeCellDeck.cpp + +temp/obj/moc_FreeCellStack.o: temp/moc/moc_FreeCellStack.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_FreeCellStack.o temp\moc\moc_FreeCellStack.cpp + +temp/obj/moc_FreeCellHome.o: temp/moc/moc_FreeCellHome.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_FreeCellHome.o temp\moc\moc_FreeCellHome.cpp + +temp/obj/moc_FreeCellFree.o: temp/moc/moc_FreeCellFree.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_FreeCellFree.o temp\moc\moc_FreeCellFree.cpp + +temp/obj/moc_Spider3DeckBoard.o: temp/moc/moc_Spider3DeckBoard.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_Spider3DeckBoard.o temp\moc\moc_Spider3DeckBoard.cpp + +temp/obj/moc_SpideretteBoard.o: temp/moc/moc_SpideretteBoard.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_SpideretteBoard.o temp\moc\moc_SpideretteBoard.cpp + +temp/obj/moc_YukonBoard.o: temp/moc/moc_YukonBoard.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\moc_YukonBoard.o temp\moc\moc_YukonBoard.cpp + +temp/obj/qrc_QSoloCards.o: temp/qrc/qrc_QSoloCards.cpp + $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp\obj\qrc_QSoloCards.o temp\qrc\qrc_QSoloCards.cpp + +####### Install + +install: FORCE + +uninstall: FORCE + +FORCE: + diff --git a/plugins/qsolocards_plugin/PlayingCard.cpp b/plugins/qsolocards_plugin/PlayingCard.cpp new file mode 100644 index 000000000..3528d7f52 --- /dev/null +++ b/plugins/qsolocards_plugin/PlayingCard.cpp @@ -0,0 +1,174 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "PlayingCard.h" + +#include +#include +#include + +//////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////// +PlayingCard::PlayingCard(PlayingCard::Suit suit, + PlayingCard::CardIndex index, + bool isFaceUp) + :m_suit(suit), + m_index(index), + m_isFaceUp(isFaceUp), + m_textStr(NULL) +{ + this->setTextStr(); +} + +//////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////// +PlayingCard::PlayingCard(const PlayingCard & playingCard) + :m_textStr(NULL) +{ + *this=playingCard; +} + + +//////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////// +PlayingCard::~PlayingCard() +{ + delete []m_textStr; +} + +//////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////// +unsigned short PlayingCard::hashValue() const +{ + return m_suit*MaxCardIndex + m_index; +} + +//////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////// +PlayingCard PlayingCard::cardFromHashValue(unsigned short value) +{ + PlayingCard card(PlayingCard::MaxSuit,PlayingCard::MaxCardIndex); + // if the value is valid set the suit and index + if (value(const PlayingCard & rh) const +{ + return m_index>rh.getIndex(); +} + +//////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////// +PlayingCard & PlayingCard::operator=(const PlayingCard & rh) +{ + m_suit=rh.getSuit(); + m_index=rh.getIndex(); + this->setFaceUp(rh.isFaceUp()); + setTextStr(); + return *this; +} + + +//////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////// +bool PlayingCard::isNextCardIndex(const PlayingCard & rh) const +{ + return m_index+1==rh.getIndex(); +} + +//////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////// +bool PlayingCard::isPrevCardIndex(const PlayingCard & rh) const +{ + return m_index-1==rh.getIndex(); +} + + +//////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////// +void PlayingCard::setTextStr() +{ + std::string cardValue; + + switch (m_index) + { + case Ace: + cardValue="1"; + break; + case Jack: + cardValue="jack"; + break; + case Queen: + cardValue="queen"; + break; + case King: + cardValue="king"; + break; + case MaxCardIndex: + cardValue="invalid"; + break; + default: + { + char cardNumStr[20]; + sprintf(cardNumStr,"%i",(int)m_index+1); + cardValue=cardNumStr; + }; + break; + }; + + cardValue+="_"; + + switch (m_suit) + { + case Clubs: + cardValue+="club"; + break; + case Spades: + cardValue+="spade"; + break; + case Hearts: + cardValue+="heart"; + break; + case Diamonds: + cardValue+="diamond"; + break; + default: + cardValue+="Invalid Suit"; + break; + }; + + delete []m_textStr; + + this->m_textStr=new char[cardValue.size()+1]; + + strcpy(this->m_textStr,cardValue.c_str()); +} diff --git a/plugins/qsolocards_plugin/PlayingCard.h b/plugins/qsolocards_plugin/PlayingCard.h new file mode 100644 index 000000000..585460e51 --- /dev/null +++ b/plugins/qsolocards_plugin/PlayingCard.h @@ -0,0 +1,100 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef PLAYINGCARD_H +#define PLAYINGCARD_H + +class PlayingCard +{ + public: + enum Suit + { + Clubs=0, + Diamonds=1, + Hearts=2, + Spades=3, + MaxSuit=4 + }; + + + enum CardIndex + { + Ace=0, + Two=1, + Three=2, + Four=3, + Five=4, + Six=5, + Seven=6, + Eight=7, + Nine=8, + Ten=9, + Jack=10, + Queen=11, + King=12, + MaxCardIndex=13 + }; + + PlayingCard(Suit suit=PlayingCard::MaxSuit, + CardIndex index=PlayingCard::MaxCardIndex, + bool isFaceUp=false); + PlayingCard(const PlayingCard & playingCard); + + virtual ~PlayingCard(); + + // a value to uniquely id the card + unsigned short hashValue() const; + static PlayingCard cardFromHashValue(unsigned short value); + + Suit getSuit() const {return m_suit;} + CardIndex getIndex() const {return m_index;} + + inline bool isValid() const{return (MaxSuit!=m_suit && MaxCardIndex!=m_index);} + + inline bool isSameSuit(const PlayingCard & cmp) const{return cmp.getSuit()==m_suit;} + inline bool isSameIndex(const PlayingCard & cmp) const{return cmp.getIndex()==m_index;} + + inline bool isRed() const{return ((PlayingCard::Diamonds==m_suit || PlayingCard::Hearts==m_suit)?true:false);} + inline bool isBlack() const{return ((PlayingCard::Spades==m_suit || PlayingCard::Clubs==m_suit)?true:false);} + + inline bool isFaceUp() const {return m_isFaceUp;} + inline void setFaceUp(bool state=true) {m_isFaceUp=state;} + + + inline bool operator==(const PlayingCard & rh) const {return (isSameSuit(rh) && isSameIndex(rh));} + + PlayingCard & operator=(const PlayingCard & rh); + + virtual bool operator<(const PlayingCard & rh) const; + virtual bool operator>(const PlayingCard & rh) const; + + virtual bool isNextCardIndex(const PlayingCard & rh) const; + virtual bool isPrevCardIndex(const PlayingCard & rh) const; + + inline const char * asString() const{return m_textStr;} + + private: + + void setTextStr(); + + Suit m_suit; + CardIndex m_index; + bool m_isFaceUp; + char * m_textStr; +}; +#endif // PLAYINGCARD_H diff --git a/plugins/qsolocards_plugin/QSoloCards.icns b/plugins/qsolocards_plugin/QSoloCards.icns new file mode 100644 index 000000000..e148c0daa Binary files /dev/null and b/plugins/qsolocards_plugin/QSoloCards.icns differ diff --git a/plugins/qsolocards_plugin/QSoloCards.qrc b/plugins/qsolocards_plugin/QSoloCards.qrc new file mode 100644 index 000000000..fe8c2c4c3 --- /dev/null +++ b/plugins/qsolocards_plugin/QSoloCards.qrc @@ -0,0 +1,15 @@ + + + images/greenfelt.png + images/anglo_bitmap.svg + images/sol32x32.png + images/sol128x128.png + help/SpiderHelp.html + help/Spider3DeckHelp.html + help/SpideretteHelp.html + help/KlondikeHelp.html + help/FreeCellHelp.html + help/YukonHelp.html + help/gpl3.html + + diff --git a/plugins/qsolocards_plugin/QSoloCardsPlugin.cpp b/plugins/qsolocards_plugin/QSoloCardsPlugin.cpp new file mode 100644 index 000000000..dcb4d6760 --- /dev/null +++ b/plugins/qsolocards_plugin/QSoloCardsPlugin.cpp @@ -0,0 +1,53 @@ +/**************************************************************** + * RetroShare is distributed under the following license: + * + * Copyright (C) 2010 RetroShare Team + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, + * Boston, MA 02110-1301, USA. + ****************************************************************/ + +//#include +//#include +//#include + +#include "QSoloCardsPlugin.h" +#include "mainwindow.h" + +QString +QSoloCardsPlugin::pluginDescription() const +{ + QString res; + res = "a QSoloCards plugin" ; + + return res; +} + +QString +QSoloCardsPlugin::pluginName() const +{ + return "QSoloCards" ; +} + +QWidget* +QSoloCardsPlugin::pluginWidget(QWidget * parent ) +{ + MainWindow* window = new MainWindow(); + + return window; +} + + +Q_EXPORT_PLUGIN2(qsolocards_plugin, QSoloCardsPlugin) diff --git a/plugins/qsolocards_plugin/QSoloCardsPlugin.h b/plugins/qsolocards_plugin/QSoloCardsPlugin.h new file mode 100644 index 000000000..9537132df --- /dev/null +++ b/plugins/qsolocards_plugin/QSoloCardsPlugin.h @@ -0,0 +1,48 @@ +/**************************************************************** + * RetroShare is distributed under the following license: + * + * Copyright (C) 2010 RetroShare Team + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, + * Boston, MA 02110-1301, USA. + ****************************************************************/ + +#ifndef _QSOLOCARDS_PLUGIN_H_ +#define _QSOLOCARDS_PLUGIN_H_ + +#include + +#include +#include + +#include + +#include + +class QSoloCardsPlugin: public QObject, public PluginInterface +{ + Q_OBJECT + Q_INTERFACES(PluginInterface) + + public slots: + + virtual QString pluginDescription() const ; + virtual QString pluginName() const ; + + virtual QWidget* pluginWidget(QWidget * parent = 0) ; + +}; + +#endif diff --git a/plugins/qsolocards_plugin/Spider3DeckBoard.cpp b/plugins/qsolocards_plugin/Spider3DeckBoard.cpp new file mode 100644 index 000000000..1bd4ecc94 --- /dev/null +++ b/plugins/qsolocards_plugin/Spider3DeckBoard.cpp @@ -0,0 +1,181 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "Spider3DeckBoard.h" +#include "CardPixmaps.h" + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +Spider3DeckBoard::Spider3DeckBoard() + :SpiderBoard() +{ + this->setGameName(QString(tr("Three Deck Spider Solitaire")).trimmed()); + this->setGameId("ThreeDeckSpider"); + + this->setHelpFile(":/help/Spider3DeckHelp.html"); +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +Spider3DeckBoard::~Spider3DeckBoard() +{ +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +void Spider3DeckBoard::newGame() +{ + // call the base class to do cleanup for us. + GameBoard::newGame(); + + CardDeck deck(3); + + // Put all cards in the m_pDeck stack. We will deal + // from this stack. + while(!deck.isEmpty()) + { + this->m_pDeck->addCard(deck.next()); + } + + unsigned int i; + unsigned int j; + + DealItemVector dealItemVector; + + // Create the dealItemVector to direct the DealAnimation object on + // how to deal the cards. + for (i=0;im_stackVector.size();i++) + { + unsigned int cardsInStack=((i<6)?5:4); + + dealItemVector.push_back(DealItem(this->m_stackVector[i],m_pDeck)); + + for (j=0;jsetPos(currPos); + + currPos.rx()+=GameBoard::LayoutSpacing+cardSize.width(); + + for (i=0;isetPos(currPos); + currPos.setX(currPos.x()+cardSize.width()+GameBoard::LayoutSpacing); + } + + currPos.setY(GameBoard::LayoutSpacing*2+cardSize.height()); + currPos.setX(GameBoard::LayoutSpacing*2+cardSize.width()); + for (i=0;isetPos(currPos); + currPos.setX(currPos.x()+cardSize.width()+GameBoard::LayoutSpacing); + } + +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +void Spider3DeckBoard::createStacks() +{ + setCardResizeAlg(13,ResizeByWidth); + + unsigned int i; + // create all the widgets for the board + for(i=0;i<12;i++) + { + this->m_homeVector.push_back(new SpiderHomeStack); + this->m_scene.addItem(m_homeVector[i]); + + // get signals when cards are added to the stack. So, we can add undo info and + // see when the game is over. + this->connect(this->m_homeVector[i],SIGNAL(cardsMovedByDragDrop(CardMoveRecord)), + this,SLOT(slotCardsMoved(CardMoveRecord))); + } + + for(i=0;i<12;i++) + { + this->m_stackVector.push_back(new SpiderStack); + this->m_scene.addItem(m_stackVector[i]); + + // get signals when cards are added to the stack. So, we can add undo info and + // see when the game is over. + this->connect(this->m_stackVector[i],SIGNAL(cardsMovedByDragDrop(CardMoveRecord)), + this,SLOT(slotCardsMoved(CardMoveRecord))); + this->connect(this->m_stackVector[i],SIGNAL(sendSuitHome(SpiderStack *,PlayingCardVector,CardMoveRecord)), + this,SLOT(slotSendSuitHome(SpiderStack*,PlayingCardVector,CardMoveRecord))); + this->connect(this->m_stackVector[i],SIGNAL(moveCardsToDiffStack(SpiderStack *,PlayingCardVector,CardMoveRecord)), + this,SLOT(slotMoveCardsToDiffStack(SpiderStack*,PlayingCardVector,CardMoveRecord))); + } + + m_pDeck=new CardStack; + this->m_scene.addItem(m_pDeck); + + // get signals when the deck is clicked on so we can deal the next set of cards + this->connect(this->m_pDeck,SIGNAL(cardClicked(CardStack*,uint)), + this,SLOT(slotDealNextCards(CardStack*,uint))); +} diff --git a/plugins/qsolocards_plugin/Spider3DeckBoard.h b/plugins/qsolocards_plugin/Spider3DeckBoard.h new file mode 100644 index 000000000..3ce28bc07 --- /dev/null +++ b/plugins/qsolocards_plugin/Spider3DeckBoard.h @@ -0,0 +1,43 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef __SPIDER3DECKBOARD_H__ +#define __SPIDER3DECKBOARD_H__ + +#include "SpiderBoard.h" + +class Spider3DeckBoard:public SpiderBoard +{ + Q_OBJECT +public: + Spider3DeckBoard(); + virtual ~Spider3DeckBoard(); + + virtual void newGame(); + + virtual void addGameMenuItems(QMenu & menu); + + virtual void loadSettings(const QSettings & settings); + virtual void saveSettings(QSettings & settings); + +protected: + virtual void resizeEvent (QResizeEvent * event); + virtual void createStacks(); +}; + +#endif diff --git a/plugins/qsolocards_plugin/SpiderBoard.cpp b/plugins/qsolocards_plugin/SpiderBoard.cpp new file mode 100644 index 000000000..ae7a58bc4 --- /dev/null +++ b/plugins/qsolocards_plugin/SpiderBoard.cpp @@ -0,0 +1,754 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "SpiderBoard.h" +#include +#include +#include +#include +#include + +#include "CardPixmaps.h" +#include "CardDeck.h" + + +#include + +const QString SpiderBoard::GameTypeKeyStr("GameType"); + + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +SpiderBoard::SpiderBoard(QWidget * pWidget) + :GameBoard(pWidget,QString(tr("Spider Solitaire")).trimmed(),QString("Spider")), + m_pDeck(NULL), + m_homeVector(), + m_stackVector(), + m_cheat(false), + m_gameType(SpiderBoard::FourSuits) +{ + this->setHelpFile(":/help/SpiderHelp.html"); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +SpiderBoard::~SpiderBoard() +{ +} + +//////////////////////////////////////////////////////////////////////////////// +// ok this is an attempt to offer hint moves. It will prefer same suit moves, then +// consecutive index matches, and then card to empty stack moves. It will try to +// move all cards that are movable in a stack. So, there are possibilities for +// tweaks. +//////////////////////////////////////////////////////////////////////////////// +bool SpiderBoard::getHint(CardStack * & pSrcWidget, + unsigned int & srcStackIndex, + CardStack * & pDstWidget) +{ + bool moveFound=false; + bool sameSuitFound=false; + bool nonSameSuitFound=false; + + CardStack * pCanMoveToEmpty=NULL; + CardStack * pCanMoveTo=NULL; + CardStack * pCanMoveToSameSuit=NULL; + bool newMoveFound=false; + int j; + + qsrand(QDateTime::currentDateTime().toTime_t()); + bool fromZero=((0==qrand()%2 ^ 1==qrand()%3)?true:false); // this introduces some randomness by selecting whether we are going + // to go through the stacks forward or backwards. + + + for ((fromZero?(j=0):(j=this->m_stackVector.size()-1)); + ((fromZero)?(j<(int)this->m_stackVector.size()):(j>=0))&& !sameSuitFound ;((fromZero)?(j++):(j--))) + { + PlayingCardVector cardVector; + unsigned int currSrcStackIndex; + bool fromZeroInner=((0==qrand()%2 ^ 1==qrand()%3)?true:false); // this introduces some randomness by selecting whether we are going + // to go through the stacks forward or backwards. + int i; + + newMoveFound=false; + + if (this->m_stackVector[j]->getMovableCards(cardVector,currSrcStackIndex)) + { + + // first see if the cards can be sent home + // the priority will be the same as a move to + // cards of the same suit + if (SpiderHomeStack::canSendHome(cardVector)) + { + // find an open home widget + for(unsigned int k=0;km_homeVector.size();k++) + { + if (this->m_homeVector[k]->isEmpty()) + { + pDstWidget=this->m_homeVector[k]; + break; + } + } + + if (NULL!=pDstWidget) + { + pSrcWidget=this->m_stackVector[j]; + srcStackIndex=currSrcStackIndex; + moveFound=true; + break; + } + } + + for ((fromZeroInner?(i=0):(i=this->m_stackVector.size()-1)); + ((fromZeroInner)?(i<(int)this->m_stackVector.size()):(i>=0)); + ((fromZeroInner)?(i++):(i--))) + { + + // ok we are only moving the cards if the hit is not on the same + // stack they are already located in + if (this->m_stackVector[i]!=this->m_stackVector[j]) + { + // see if we have a perferred move to a stack that has the same suit + // we will break out if we find a perferred match + if (this->m_stackVector[i]->canAddCardsSameSuit(cardVector)) + { + pCanMoveToSameSuit=this->m_stackVector[i]; + newMoveFound=true; + break; + } + // otherwise see if we can move the cards to the stack at all + else if (this->m_stackVector[i]->canAddCards(cardVector)) + { + if (this->m_stackVector[i]->isEmpty()) + { + pCanMoveToEmpty=this->m_stackVector[i]; + } + else + { + pCanMoveTo=this->m_stackVector[i]; + } + newMoveFound=true; + } + } + } + + if (newMoveFound) + { + // ok the best move is to a matching suit and consecutive + // next best is to a consecutive + // and lastly to an empty stack. + if (NULL!=pCanMoveToSameSuit) + { + pDstWidget=pCanMoveToSameSuit; + pSrcWidget=this->m_stackVector[j]; + srcStackIndex=currSrcStackIndex; + sameSuitFound=true; + } + else if (NULL!=pCanMoveTo && !nonSameSuitFound) + { + pDstWidget=pCanMoveTo; + pSrcWidget=this->m_stackVector[j]; + srcStackIndex=currSrcStackIndex; + nonSameSuitFound=true; + } + else if (NULL!=pCanMoveToEmpty && !nonSameSuitFound) + { + pDstWidget=pCanMoveToEmpty; + pSrcWidget=this->m_stackVector[j]; + srcStackIndex=currSrcStackIndex; + } + moveFound=true; + } + } + } + + + return moveFound; +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void SpiderBoard::newGame() +{ + // call the base class to do cleanup for us. + GameBoard::newGame(); + + CardDeck * pDeck=NULL; + + unsigned int i; + unsigned int j; + + switch(this->m_gameType) + { + case SpiderBoard::FourSuits: + pDeck=new CardDeck(2); + break; + + case SpiderBoard::TwoSuits: + { + PlayingCardVector cardVector; + // use hearts and spades as the two suits + for (i=PlayingCard::Ace;iisEmpty()) + { + this->m_pDeck->addCard(pDeck->next()); + } + + delete pDeck; + + + DealItemVector dealItemVector; + + + // Create the dealItemVector to direct the DealAnimation object on + // how to deal the cards. + for (i=0;im_stackVector.size();i++) + { + unsigned int cardsInStack=((i<4)?6:5); + + dealItemVector.push_back(DealItem(this->m_stackVector[i],m_pDeck)); + + for (j=0;jsetShortcut(QKeySequence(Qt::CTRL + Qt::Key_4)); + pFourSuitsAction->setCheckable(true); + connect(pFourSuitsAction,SIGNAL(triggered()), + this,SLOT(slotSetFourSuits())); + + QAction * pTwoSuitsAction=new QAction(tr("Two Suits").trimmed(),pNumSuitsGroup); + pTwoSuitsAction->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_2)); + pTwoSuitsAction->setCheckable(true); + connect(pTwoSuitsAction,SIGNAL(triggered()), + this,SLOT(slotSetTwoSuits())); + + QAction * pOneSuitAction=new QAction(tr("One Suit").trimmed(),pNumSuitsGroup); + pOneSuitAction->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_1)); + pOneSuitAction->setCheckable(true); + connect(pOneSuitAction,SIGNAL(triggered()), + this,SLOT(slotSetOneSuit())); + + // select the correct item in the list + switch (this->m_gameType) + { + case SpiderBoard::FourSuits: + pFourSuitsAction->setChecked(true); + break; + + case SpiderBoard::TwoSuits: + pTwoSuitsAction->setChecked(true); + break; + + case SpiderBoard::OneSuit: + pOneSuitAction->setChecked(true); + break; + }; + + menu.addAction(pFourSuitsAction); + menu.addAction(pTwoSuitsAction); + menu.addAction(pOneSuitAction); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void SpiderBoard::loadSettings(const QSettings & settings) +{ + int gameType=settings.value(this->GameTypeKeyStr,SpiderBoard::FourSuits).toInt(); + + switch (gameType) + { + case SpiderBoard::OneSuit: + this->m_gameType=SpiderBoard::OneSuit; + break; + + case SpiderBoard::TwoSuits: + this->m_gameType=SpiderBoard::TwoSuits; + break; + + case SpiderBoard::FourSuits: + default: + this->m_gameType=SpiderBoard::FourSuits; + break; + }; +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void SpiderBoard::saveSettings(QSettings & settings) +{ + settings.setValue(this->GameTypeKeyStr,this->m_gameType); +} + + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void SpiderBoard::setCheat(bool cheat) +{ + this->m_cheat=cheat; + + for(unsigned int i=0;im_stackVector.size();i++) + { + this->m_stackVector[i]->setCheat(cheat); + } +} + + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void SpiderBoard::slotDealNextCards(CardStack * pCardStackWidget, + unsigned int index) +{ + bool aStackIsEmpty=false; + unsigned int i; + + Q_UNUSED(pCardStackWidget); + Q_UNUSED(index); + + // if the deck has cards to deal make sure all the stacks have cards + // and deal them out + if (!this->m_pDeck->isEmpty()) + { + // first make sure none of the 10 stacks is empty. All must have at least one card. + // to be able to deal the cards. + for(i=0;im_stackVector.size();i++) + { + if (this->m_stackVector[i]->isEmpty()) + { + aStackIsEmpty=true; + break; + } + } + + + if (aStackIsEmpty) + { + QMessageBox::critical(this,this->gameName(), + tr("All stacks must contain at least one card before the next set of cards can be dealt!").trimmed()); + this->stopDemo(); + return; + } + + + DealItemVector dealItemVector; + + + // Create the dealItemVector to direct the DealAnimation object on + // how to deal the cards. + for (i=0;im_stackVector.size();i++) + { + dealItemVector.push_back(DealItem(this->m_stackVector[i],m_pDeck)); + + dealItemVector[i].addCard(true); + } + // ok now start the deal. + m_dealAni.dealCards(dealItemVector); + } +} + +//////////////////////////////////////////////////////////////////////////////// +// ok we need to perform the move from the stackWidget to the sentHome widget +// and create the CardMoveRecord. Then just call slotCardsMoved and let the +// move be processed as if it was a drag and drop +//////////////////////////////////////////////////////////////////////////////// +void SpiderBoard::slotSendSuitHome(SpiderStack * pStack, + const PlayingCardVector & cardVector, + const CardMoveRecord & startMoveRecord) +{ + if (NULL!=pStack) + { + // ok first find an empty sentHome widget to add the cards too. + SpiderHomeStack * pHome=NULL; + unsigned int i; + for (i=0;im_homeVector.size();i++) + { + if (this->m_homeVector[i]->isEmpty()) + { + pHome=this->m_homeVector[i]; + break; + } + } + + // we should always find an empty home widget. But check just in case + if (pHome) + { + CardMoveRecord moveRecord(startMoveRecord); + // add the cards to the update record. But don't move the + // cards + pHome->addCards(cardVector,moveRecord,true); + + // perform the move of the cards and animate it if animations + // are enabled + m_sToSAniMove.moveCards(moveRecord); + } + } +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void SpiderBoard::slotMoveCardsToDiffStack(SpiderStack * pStack, + const PlayingCardVector & cardVector, + const CardMoveRecord & startMoveRecord) +{ + if (NULL!=pStack) + { + SpiderStack * pCanMoveToEmpty=NULL; + SpiderStack * pCanMoveTo=NULL; + SpiderStack * pCanMoveToSameSuit=NULL; + bool cardsWillMove=false; + + for (unsigned int i=0;im_stackVector.size();i++) + { + // ok we are only moving the cards if the hit is not on the same + // stack they are already located in + if (this->m_stackVector[i]!=pStack) + { + // see if we have a perferred move to a stack that has the same suit + // we will break out if we find a perferred match + if (this->m_stackVector[i]->canAddCardsSameSuit(cardVector)) + { + pCanMoveToSameSuit=this->m_stackVector[i]; + cardsWillMove=true; + break; + } + // otherwise see if we can move the cards to the stack at all + else if (this->m_stackVector[i]->canAddCards(cardVector)) + { + if (this->m_stackVector[i]->isEmpty()) + { + pCanMoveToEmpty=this->m_stackVector[i]; + } + else + { + pCanMoveTo=this->m_stackVector[i]; + } + cardsWillMove=true; + } + } + } + + // if we are going to move the cards + if (cardsWillMove) + { + SpiderStack * pNewStack=NULL; + + // ok the best move is to a matching suit and consecutive + // next best is to a consecutive + // and lastly to an empty stack. + if (NULL!=pCanMoveToSameSuit) + { + pNewStack=pCanMoveToSameSuit; + } + else if (NULL!=pCanMoveTo) + { + pNewStack=pCanMoveTo; + } + else + { + pNewStack=pCanMoveToEmpty; + } + + CardMoveRecord moveRecord(startMoveRecord); + pNewStack->addCards(cardVector,moveRecord,true); + + // perform the move of the cards and animate it if animations + // are enabled + m_sToSAniMove.moveCards(moveRecord); + } + } +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void SpiderBoard::slotSetFourSuits() +{ + if (SpiderBoard::FourSuits!=this->m_gameType) + { + this->m_gameType=SpiderBoard::FourSuits; + this->newGame(); + } +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void SpiderBoard::slotSetTwoSuits() +{ + if (SpiderBoard::TwoSuits!=this->m_gameType) + { + this->m_gameType=SpiderBoard::TwoSuits; + this->newGame(); + } +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void SpiderBoard::slotSetOneSuit() +{ + if (SpiderBoard::OneSuit!=this->m_gameType) + { + this->m_gameType=SpiderBoard::OneSuit; + this->newGame(); + } +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void SpiderBoard::calcScore() +{ + int score=0; + unsigned int i; + + for(i=0;im_homeVector.size();i++) + { + score+=this->m_homeVector[i]->score(); + } + + for(i=0;im_stackVector.size();i++) + { + score+=this->m_stackVector[i]->score(); + } + + int deals=0; + + // The number of deals left is the number of cards in the deck widget divided by the number of stack widgets + if (!this->m_pDeck->isEmpty() && this->m_stackVector.size()>0) + { + const PlayingCardVector & cardVector=this->m_pDeck->getCardVector(); + + deals=cardVector.size()/this->m_stackVector.size(); + + if (cardVector.size()%this->m_stackVector.size()) + { + deals++; + } + } + + QString dealsLeft(tr("Deals remaining: %1").arg(QString::number(deals)).trimmed()); + + emit scoreChanged(score,dealsLeft); +} + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void SpiderBoard::resizeEvent (QResizeEvent * event) +{ + unsigned int i; + + GameBoard::resizeEvent(event); + + + QSize cardSize(CardPixmaps::getInst().getCardSize()); + + QPointF currPos(GameBoard::LayoutSpacing,GameBoard::LayoutSpacing); + + m_pDeck->setPos(currPos); + + currPos.setX(GameBoard::LayoutSpacing*3 + cardSize.width()*2); + + for (i=0;isetPos(currPos); + currPos.setX(currPos.x()+cardSize.width()+GameBoard::LayoutSpacing); + } + + currPos.setY(GameBoard::LayoutSpacing*2+cardSize.height()); + currPos.setX(GameBoard::LayoutSpacing); + for (i=0;isetPos(currPos); + currPos.setX(currPos.x()+cardSize.width()+GameBoard::LayoutSpacing); + } + + std::cout<<__FUNCTION__<isEmpty()) + { + slotDealNextCards(); + } + else if (stopWhenNoMore) + { + stopDemo(); + rc=false; + } + else + { + rc=false; + } + } + + return rc; +} + + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +void SpiderBoard::createStacks() +{ + setCardResizeAlg(10,ResizeByWidth); + + unsigned int i; + // create all the widgets for the board + for(i=0;i<8;i++) + { + this->m_homeVector.push_back(new SpiderHomeStack); + this->m_scene.addItem(m_homeVector[i]); + + // get signals when cards are added to the stack. So, we can add undo info and + // see when the game is over. + this->connect(this->m_homeVector[i],SIGNAL(cardsMovedByDragDrop(CardMoveRecord)), + this,SLOT(slotCardsMoved(CardMoveRecord))); + } + + for(i=0;i<10;i++) + { + this->m_stackVector.push_back(new SpiderStack); + this->m_scene.addItem(m_stackVector[i]); + + // get signals when cards are added to the stack. So, we can add undo info and + // see when the game is over. + + this->connect(this->m_stackVector[i],SIGNAL(cardsMovedByDragDrop(CardMoveRecord)), + this,SLOT(slotCardsMoved(CardMoveRecord))); + this->connect(this->m_stackVector[i],SIGNAL(sendSuitHome(SpiderStack *,PlayingCardVector,CardMoveRecord)), + this,SLOT(slotSendSuitHome(SpiderStack*,PlayingCardVector,CardMoveRecord))); + this->connect(this->m_stackVector[i],SIGNAL(moveCardsToDiffStack(SpiderStack *,PlayingCardVector,CardMoveRecord)), + this,SLOT(slotMoveCardsToDiffStack(SpiderStack*,PlayingCardVector,CardMoveRecord))); + + + } + + m_pDeck=new CardStack; + this->m_scene.addItem(m_pDeck); + + // get signals when the deck is clicked on so we can deal the next set of cards + this->connect(this->m_pDeck,SIGNAL(cardClicked(CardStack*,uint)), + this,SLOT(slotDealNextCards(CardStack*,uint))); + + std::cout<<__FUNCTION__<<__FILE__<m_homeVector.size();i++) + { + if (this->m_homeVector[i]->isEmpty()) + { + allSuitsSentHome=false; + break; + } + } + + return allSuitsSentHome; +} + + +//////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////// +bool SpiderBoard::isGameWonNotComplete()const +{ + bool rc=m_pDeck->isEmpty(); + + if (rc) + { + for (unsigned int i=0;im_stackVector.size();i++) + { + if (!(this->m_stackVector[i]->cardsAscendingTopToBottom() && + this->m_stackVector[i]->allCardsFaceUp())) + { + rc=false; + break; + } + } + } + + return rc; +} + diff --git a/plugins/qsolocards_plugin/SpiderBoard.h b/plugins/qsolocards_plugin/SpiderBoard.h new file mode 100644 index 000000000..bd0e32a8e --- /dev/null +++ b/plugins/qsolocards_plugin/SpiderBoard.h @@ -0,0 +1,101 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef SPIDERBOARD_H +#define SPIDERBOARD_H + +#include "GameBoard.h" +#include "CardStack.h" +#include "SpiderStack.h" +#include "SpiderHomeStack.h" + +#include + +class SpiderBoard : public GameBoard +{ + Q_OBJECT + + public: + enum GameType + { + FourSuits=4, + TwoSuits=2, + OneSuit=1 + }; + + static const QString GameTypeKeyStr; + + SpiderBoard(QWidget * pParent=NULL); + virtual ~SpiderBoard(); + + bool getHint(CardStack * & pSrcWidget, + unsigned int & srcStackIndex, + CardStack * & pDstWidget); + + inline bool hasDemo() const {return true;} + + virtual void newGame(); + + virtual void addGameMenuItems(QMenu & menu); + + virtual void loadSettings(const QSettings & settings); + virtual void saveSettings(QSettings & settings); + + inline bool isCheating() const {return m_cheat;} + + void setCheat(bool cheat); + + inline bool supportsScore() const{return true;} + + public slots: + virtual void slotDealNextCards(CardStack * pCardStackWidget=NULL,unsigned int index=0); + + // these slot catch the signals from the SpiderStacks that are started by + // a click on a card instead of a drag + virtual void slotSendSuitHome(SpiderStack *,const PlayingCardVector &,const CardMoveRecord &); + virtual void slotMoveCardsToDiffStack(SpiderStack *,const PlayingCardVector &,const CardMoveRecord &); + + + void slotSetFourSuits(); + void slotSetTwoSuits(); + void slotSetOneSuit(); + + protected: + void calcScore(); + + virtual void resizeEvent (QResizeEvent * event); + + bool runDemo(bool stopWhenNoMore=true); + + virtual void createStacks(); + + virtual bool isGameWon()const; + virtual bool isGameWonNotComplete()const; + + CardStack * m_pDeck; + std::vector m_homeVector; // we will have 8 items in this + //vector one for each suit (2 decks) + std::vector m_stackVector; // we will have 10 items in this vector + + bool m_cheat; + + + GameType m_gameType; +}; + +#endif // SPIDERBOARD_H diff --git a/plugins/qsolocards_plugin/SpiderHomeStack.cpp b/plugins/qsolocards_plugin/SpiderHomeStack.cpp new file mode 100644 index 000000000..5fb666688 --- /dev/null +++ b/plugins/qsolocards_plugin/SpiderHomeStack.cpp @@ -0,0 +1,70 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "SpiderHomeStack.h" + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +SpiderHomeStack::SpiderHomeStack() + :CardStack() +{ +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +SpiderHomeStack::~SpiderHomeStack() +{ +} + +///////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////// +bool SpiderHomeStack::canSendHome(const PlayingCardVector & cardVector) +{ + bool rc=false; + + if (PlayingCard::MaxCardIndex==cardVector.size() && + PlayingCard::King==cardVector[0].getIndex() && + PlayingCard::Ace==cardVector[cardVector.size()-1].getIndex()) + { + rc=true; + for(unsigned int i=1;iisEmpty()) + { + rc=SpiderHomeStack::canSendHome(newCards); + } + + return rc; +} diff --git a/plugins/qsolocards_plugin/SpiderHomeStack.h b/plugins/qsolocards_plugin/SpiderHomeStack.h new file mode 100644 index 000000000..108fb6314 --- /dev/null +++ b/plugins/qsolocards_plugin/SpiderHomeStack.h @@ -0,0 +1,46 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef SPIDERHOMESTACK_H +#define SPIDERHOMESTACK_H + +#include "CardStack.h" + +// When a suit is together from King to Ace it can be "sent home" or moved off the +// main board to a separate set stack. When all 8 sets of suits are "sent home" the +// game is won. +class SpiderHomeStack: public CardStack +{ + public: + SpiderHomeStack(); + ~SpiderHomeStack(); + + // this function just tests if the cardVector is complete + // King to Ace of the same suit + static bool canSendHome(const PlayingCardVector &); + + // for this type of stack the score will be 0 or 12 + // or one less than the number of cards in a suit. + // ie we have a sent home suit or nothing. + inline int score() const {return ((isEmpty())?0:PlayingCard::MaxCardIndex-1);} + + bool canAddCards(const PlayingCardVector &); + +}; + +#endif // SPIDERHOMESTACK_H diff --git a/plugins/qsolocards_plugin/SpiderStack.cpp b/plugins/qsolocards_plugin/SpiderStack.cpp new file mode 100644 index 000000000..5ff38576a --- /dev/null +++ b/plugins/qsolocards_plugin/SpiderStack.cpp @@ -0,0 +1,175 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "SpiderStack.h" +#include "SpiderHomeStack.h" + +/////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////// +SpiderStack::SpiderStack() + :VCardStack(), + m_cheat(false) +{ + this->setAutoTopCardUp(); + + + // connect a slot to get the signal when a movable card is clicked + this->connect(this,SIGNAL(movableCardsClicked(CardStack*,PlayingCardVector,CardMoveRecord)), + this,SLOT(slotMovableCardsClicked(CardStack*,PlayingCardVector,CardMoveRecord))); +} + +/////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////// +SpiderStack::~SpiderStack() +{ +} + +/////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////// +int SpiderStack::score() const +{ + const PlayingCardVector & cardVector=this->getCardVector(); + int score=0; + + for (unsigned int i=1;igetCardVector(); + + if (newCardVector.size()>0) + { + // if there are no cards in the stack then we will accept any cards + if (0==cardVector.size()) + { + rc=true; + } + else if (cardVector[cardVector.size()-1].isPrevCardIndex(newCardVector[0]) && + cardVector[cardVector.size()-1].isFaceUp()) + { + rc=true; + } + } + + return rc; +} + +/////////////////////////////////////////////////////////////////////////////////// +// similar to can Add cards. But in this case the +// suit of the last card in this stack is the same as +// the first suit of the cardVector +/////////////////////////////////////////////////////////////////////////////////// +bool SpiderStack::canAddCardsSameSuit(const PlayingCardVector & newCardVector) +{ + bool rc=false; + + if (this->canAddCards(newCardVector) && !this->isEmpty() && newCardVector.size()>0) + { + const PlayingCardVector & cardVector=this->getCardVector(); + + rc=cardVector[cardVector.size()-1].isSameSuit(newCardVector[0]); + } + + return rc; +} + +/////////////////////////////////////////////////////////////////////////////////// +// if a card is clicked on see if it needs to be sent home or can just be moved +// to another stack. +/////////////////////////////////////////////////////////////////////////////////// +void SpiderStack::slotMovableCardsClicked(CardStack * pCardStack, + const PlayingCardVector & moveCards, + const CardMoveRecord & moveRecord) +{ + bool isSentHome=false; + + Q_UNUSED(pCardStack); + + // first see if the item needs to be sent home + if (SpiderHomeStack::canSendHome(moveCards)) + { + emit sendSuitHome(this,moveCards,moveRecord); + isSentHome=true; + } + + // if this is not a case when the suit can be sent home + // Then we will just emit a signal to try to move the + // set of cards. + if (!isSentHome) + { + emit moveCardsToDiffStack(this,moveCards,moveRecord); + } +} + +/////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////// +bool SpiderStack::canMoveCard(unsigned int index) const +{ + if (m_cheat) + { + return true; + } + + bool rc=false; + const PlayingCardVector & cardVector=this->getCardVector(); + + // ok if we have cards in the stack and the index is valid + // see if we can move it. + if (cardVector.size()>0 && index. +*/ + +#ifndef SPIDERSTACK_H +#define SPIDERSTACK_H + +#include "VCardStack.h" + +// This is the stack of cards that are used for the main game play +// There are ten of these stacks. +class SpiderStack: public VCardStack +{ + Q_OBJECT + + public: + SpiderStack(); + ~SpiderStack(); + + inline bool isCheating() const{return m_cheat;} + + inline void setCheat(bool cheat=true){m_cheat=cheat;} + + int score() const; + + bool canAddCards(const PlayingCardVector &); + + // similar to can Add cards. But in this case the + // suit of the last card in this stack is the same as + // the first suit of the cardVector + bool canAddCardsSameSuit(const PlayingCardVector &); + + signals: + // signals that are emitted when a card that can be moved is clicked on + // the move record created will have the Remove and flip actions (if the flip of the + // card before the cards is necessary.) + void sendSuitHome(SpiderStack *,const PlayingCardVector &,const CardMoveRecord &); + void moveCardsToDiffStack(SpiderStack *,const PlayingCardVector &,const CardMoveRecord &); + + public slots: + void slotMovableCardsClicked(CardStack * pCardStack, + const PlayingCardVector &, + const CardMoveRecord &); + + + protected: + bool canMoveCard(unsigned int index) const; + + private: + bool m_cheat; +}; + +#endif // SPIDERSTACK_H diff --git a/plugins/qsolocards_plugin/SpideretteBoard.cpp b/plugins/qsolocards_plugin/SpideretteBoard.cpp new file mode 100644 index 000000000..3106dbbeb --- /dev/null +++ b/plugins/qsolocards_plugin/SpideretteBoard.cpp @@ -0,0 +1,182 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "SpideretteBoard.h" +#include "CardPixmaps.h" + +/////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////// +SpideretteBoard::SpideretteBoard() +{ + this->setGameName(QString(tr("Spiderette Solitaire")).trimmed()); + this->setGameId("Spiderette"); + + this->setHelpFile(":/help/SpideretteHelp.html"); +} + +/////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////// +SpideretteBoard::~SpideretteBoard() +{ +} + +/////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////// +void SpideretteBoard::newGame() +{ + // call the base class + GameBoard::newGame(); + + CardDeck deck; + unsigned int i; + + while(!deck.isEmpty()) + { + this->m_pDeck->addCard(deck.next()); + } + + + DealItemVector dealItemVector; + + + // Create the dealItemVector to direct the DealAnimation object on + // how to deal the cards. + for (i=0;im_stackVector.size();i++) + { + dealItemVector.push_back(DealItem(this->m_stackVector[i],m_pDeck)); + + unsigned int j; + + for (j=0;jsetPos(currPos); + + currPos.rx()+=GameBoard::LayoutSpacing*4 + cardSize.width()*4; + + + for (i=0;isetPos(currPos); + currPos.rx()+=cardSize.width()+GameBoard::LayoutSpacing; + } + + currPos.setY(GameBoard::LayoutSpacing*2+cardSize.height()); + currPos.setX(GameBoard::LayoutSpacing*2+cardSize.width()); + for (i=0;isetPos(currPos); + currPos.rx()+=cardSize.width()+GameBoard::LayoutSpacing; + } +} + +/////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////// +void SpideretteBoard::createStacks() +{ + setCardResizeAlg(8,ResizeByWidth); + + + unsigned int i; + + // first create the home widgets where the cards need to be eventually stacked to + // win the game. + for(i=0;i<4;i++) + { + this->m_homeVector.push_back(new SpiderHomeStack); + this->m_scene.addItem(m_homeVector[i]); + + // get signals when cards are added to the stack. So, we can add undo info and + // see when the game is over. + this->connect(this->m_homeVector[i],SIGNAL(cardsMovedByDragDrop(CardMoveRecord)), + this,SLOT(slotCardsMoved(CardMoveRecord))); + } + + // now create the 7 rows for the stacks. + for (i=0;i<7;i++) + { + this->m_stackVector.push_back(new SpiderStack); + this->m_scene.addItem(m_stackVector[i]); + + // get signals when cards are added to the stack. So, we can add undo info and + // see when the game is over. + this->connect(this->m_stackVector[i],SIGNAL(cardsMovedByDragDrop(CardMoveRecord)), + this,SLOT(slotCardsMoved(CardMoveRecord))); + this->connect(this->m_stackVector[i],SIGNAL(sendSuitHome(SpiderStack *,PlayingCardVector,CardMoveRecord)), + this,SLOT(slotSendSuitHome(SpiderStack*,PlayingCardVector,CardMoveRecord))); + this->connect(this->m_stackVector[i],SIGNAL(moveCardsToDiffStack(SpiderStack *,PlayingCardVector,CardMoveRecord)), + this,SLOT(slotMoveCardsToDiffStack(SpiderStack*,PlayingCardVector,CardMoveRecord))); + } + + this->m_pDeck=new CardStack; + this->m_scene.addItem(this->m_pDeck); + + // get signals when the deck is clicked on so we can deal the next set of cards + this->connect(this->m_pDeck,SIGNAL(cardClicked(CardStack*,uint)), + this,SLOT(slotDealNextCards(CardStack*,uint))); +} diff --git a/plugins/qsolocards_plugin/SpideretteBoard.h b/plugins/qsolocards_plugin/SpideretteBoard.h new file mode 100644 index 000000000..01be53147 --- /dev/null +++ b/plugins/qsolocards_plugin/SpideretteBoard.h @@ -0,0 +1,43 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef __SPIDERETTEBOARD_H__ +#define __SPIDERETTEBOARD_H__ + +#include "SpiderBoard.h" + +class SpideretteBoard:public SpiderBoard +{ + Q_OBJECT +public: + SpideretteBoard(); + virtual ~SpideretteBoard(); + + virtual void newGame(); + + virtual void addGameMenuItems(QMenu & menu); + + virtual void loadSettings(const QSettings & settings); + virtual void saveSettings(QSettings & settings); + +protected: + virtual void resizeEvent (QResizeEvent * event); + virtual void createStacks(); +}; + +#endif diff --git a/plugins/qsolocards_plugin/StackToStackAniMove.cpp b/plugins/qsolocards_plugin/StackToStackAniMove.cpp new file mode 100644 index 000000000..c00049f69 --- /dev/null +++ b/plugins/qsolocards_plugin/StackToStackAniMove.cpp @@ -0,0 +1,290 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "StackToStackAniMove.h" +#include "CardAnimationLock.h" + +#include + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +StackToStackAniMoveItem::StackToStackAniMoveItem(const CardMoveRecord & startMoveRecord,int duration) + :m_pSrc(NULL), + m_pDst(NULL), + m_pFlipStack(NULL), + m_flipIndex(-2), + m_srcTopCardIndex(-1), + m_cardVector(), + m_duration(duration), + m_moveRecord(startMoveRecord) +{ + CardMoveRecord moveRecord(startMoveRecord); + + while(!moveRecord.empty()) + { + CardMoveRecordItem currItem(moveRecord.back()); + CardStack * pStack=CardStack::getStackByName(currItem.stackName()); + const PlayingCardVector & cardVector=currItem.cardVector(); + + CardMoveRecordItem::MoveType moveType=currItem.moveType(); + + switch(moveType) + { + case CardMoveRecordItem::RemoveCards: + { + m_pSrc=pStack; + if (NULL!=m_pSrc) + { + m_srcTopCardIndex=m_pSrc->getCardVector().size()-cardVector.size(); + } + m_cardVector=cardVector; + } + break; + case CardMoveRecordItem::AddCards: + { + m_pDst=pStack; + } + break; + // for this case we are just going to flip the card over + case CardMoveRecordItem::FlipCard: + { + m_flipIndex=currItem.flipIndex(); + m_pFlipStack=pStack; + } + break; + }; + + moveRecord.pop_back(); + } +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +StackToStackAniMoveItem::StackToStackAniMoveItem(const StackToStackAniMoveItem & rh) + :m_pSrc(NULL), + m_pDst(NULL), + m_pFlipStack(NULL), + m_flipIndex(-1), + m_srcTopCardIndex(-1), + m_cardVector(), + m_duration(0), + m_moveRecord() +{ + *this=rh; +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +StackToStackAniMoveItem::StackToStackAniMoveItem() + :m_pSrc(NULL), + m_pDst(NULL), + m_pFlipStack(NULL), + m_flipIndex(-1), + m_srcTopCardIndex(-1), + m_cardVector(), + m_duration(0), + m_moveRecord() +{ +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +StackToStackAniMoveItem::~StackToStackAniMoveItem() +{ +} + +StackToStackAniMoveItem & StackToStackAniMoveItem::operator=(const StackToStackAniMoveItem & rh) +{ + m_pSrc=rh.m_pSrc; + m_pDst=rh.m_pDst; + m_pFlipStack=rh.m_pFlipStack; + m_flipIndex=rh.m_flipIndex; + m_srcTopCardIndex=rh.m_srcTopCardIndex; + m_cardVector=rh.m_cardVector; + m_duration=rh.m_duration; + m_moveRecord=rh.m_moveRecord; + + return *this; +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +StackToStackAniMove::StackToStackAniMove() + :m_pTimeLine(NULL), + m_flipDelayTimer(), + m_pItemAni(NULL), + m_pPixmapItem(NULL), + m_aniMoveItem(), + m_aniRunning(false) +{ + m_flipDelayTimer.setSingleShot(true); + m_flipDelayTimer.setInterval(250); + this->connect(&m_flipDelayTimer,SIGNAL(timeout()), + this,SLOT(slotWaitForFlipComplete())); +} + + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +StackToStackAniMove::~StackToStackAniMove() +{ + delete m_pTimeLine; + delete m_pItemAni; + delete m_pPixmapItem; +} + + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void StackToStackAniMove::moveCards(const CardMoveRecord & moveRecord,int duration) +{ + // if animation is off just process the move record as normal + if (!CardAnimationLock::getInst().animationsEnabled()) + { + CardStack::processCardMoveRecord(CardStack::RedoMove,moveRecord); + emit cardsMoved(moveRecord); + } + else + { + // first if we have an animation running stop it. + slotAniFinished(); + m_aniMoveItem=StackToStackAniMoveItem(moveRecord,duration); + CardAnimationLock::getInst().lock(); + runAnimation(); + } +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void StackToStackAniMove::stopAni() +{ + slotAniFinished(false); +} + + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void StackToStackAniMove::slotAniFinished(bool emitSignal) +{ + if (m_aniRunning) + { + m_pItemAni->timeLine()->stop(); + + // add the cards to the destination + m_aniMoveItem.dst()->addCards(m_aniMoveItem.getCardVector()); + + // now update the destination + m_aniMoveItem.dst()->updateStack(); + + // remove the animation object + m_aniMoveItem.dst()->scene()->removeItem(m_pPixmapItem); + + delete m_pPixmapItem; + m_pPixmapItem=NULL; + + + + // use the emit signal to know whether or not to disable the animation. + if (m_aniMoveItem.flipIndex()>-2) + { + m_aniMoveItem.flipStack()->flipCard(m_aniMoveItem.flipIndex(),emitSignal); + } + + CardAnimationLock::getInst().unlock(); + + m_aniRunning=false; + + if (emitSignal) + { + // emit a signal that the move is complete + emit cardsMoved(m_aniMoveItem.moveRecord()); + } + } +} + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void StackToStackAniMove::slotWaitForFlipComplete() +{ + this->runAnimation(); +} + + +////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////// +void StackToStackAniMove::runAnimation() +{ + m_aniRunning=true; + + // if the flip animation is running for the src or dst + // give it 1/2 a second to complete. + if (m_aniMoveItem.src()->isFlipAniRunning() || + m_aniMoveItem.dst()->isFlipAniRunning()) + { + m_flipDelayTimer.start(); + return; + } + + delete m_pTimeLine; + delete m_pItemAni; + delete m_pPixmapItem; + + + m_pTimeLine=new QTimeLine(m_aniMoveItem.duration()); + m_pItemAni=new QGraphicsItemAnimation; + m_pPixmapItem=new QGraphicsPixmapItem; + + QPixmap * pPixmap=m_aniMoveItem.src()->getStackPixmap(m_aniMoveItem.getCardVector()); + + if (pPixmap) + { + m_pPixmapItem->setPixmap(*pPixmap); + delete pPixmap; + } + + // set the z value to 2 so it will be on top of the + // stacks. + m_pPixmapItem->setZValue(2); + + // add the item to the scene and move it over the stack in the + // place of the cards we are going to move + m_aniMoveItem.src()->scene()->addItem(m_pPixmapItem); + m_pPixmapItem->setPos(m_aniMoveItem.src()->getGlobalCardPt(m_aniMoveItem.srcTopCardIndex())); + + + // setup the animation + m_pItemAni->setItem(m_pPixmapItem); + m_pItemAni->setTimeLine(m_pTimeLine); + + m_pItemAni->setPosAt (0, m_aniMoveItem.src()->getGlobalCardPt(m_aniMoveItem.srcTopCardIndex())); + m_pItemAni->setPosAt (1, m_aniMoveItem.dst()->getGlobalCardAddPt()); + + // connect up the slot so we will know when it is finished. + this->connect(m_pTimeLine,SIGNAL(finished()), + this,SLOT(slotAniFinished())); + + for (unsigned int i=0;iremoveTopCard(); + } + + // redraw the source stack and start the animation. + m_aniMoveItem.src()->updateStack(); + + m_pTimeLine->start(); +} diff --git a/plugins/qsolocards_plugin/StackToStackAniMove.h b/plugins/qsolocards_plugin/StackToStackAniMove.h new file mode 100644 index 000000000..3e6da6894 --- /dev/null +++ b/plugins/qsolocards_plugin/StackToStackAniMove.h @@ -0,0 +1,102 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef __STACKTOSTACKANIMOVE_H__ +#define __STACKTOSTACKANIMOVE_H__ + +#include "CardStack.h" +#include "CardMoveRecord.h" + +#include +#include +#include +#include +#include + +/* + StackToStackAniMove is just for moving one set of cards to another stack. Normal usage is + when a card in one stack is clicked on and then it is determined that this should result + in moving the card(s) to a different stack. (Auto)flipping + a card when the move is complete is also done if included in the moveRecord. +*/ + +class StackToStackAniMoveItem +{ +public: + StackToStackAniMoveItem(const CardMoveRecord & startMoveRecord,int duration); + StackToStackAniMoveItem(const StackToStackAniMoveItem & rh); + StackToStackAniMoveItem(); + + virtual ~StackToStackAniMoveItem(); + + inline CardStack * src() {return m_pSrc;} + inline CardStack * dst() {return m_pDst;} + inline CardStack * flipStack() {return m_pFlipStack;} + inline int flipIndex()const{return m_flipIndex;} + inline int srcTopCardIndex()const {return m_srcTopCardIndex;} + inline const PlayingCardVector & getCardVector() const{return m_cardVector;} + inline int duration()const{return m_duration;} + inline const CardMoveRecord & moveRecord(){return m_moveRecord;} + + StackToStackAniMoveItem & operator=(const StackToStackAniMoveItem & rh); + +private: + CardStack * m_pSrc; + CardStack * m_pDst; + CardStack * m_pFlipStack; + int m_flipIndex; + int m_srcTopCardIndex; + PlayingCardVector m_cardVector; + int m_duration; + CardMoveRecord m_moveRecord; +}; + + +class StackToStackAniMove:public QObject +{ + Q_OBJECT +public: + StackToStackAniMove(); + virtual ~StackToStackAniMove(); + + void moveCards(const CardMoveRecord & startMoveRecord,int duration=400); + void stopAni(); + +signals: + void cardsMoved(const CardMoveRecord & moveRecord); + +public slots: + void slotAniFinished(bool emitSignal=true); + void slotWaitForFlipComplete(); + +protected: + + void runAnimation(); + +private: + QTimeLine * m_pTimeLine; + QTimer m_flipDelayTimer; + QGraphicsItemAnimation * m_pItemAni; + QGraphicsPixmapItem * m_pPixmapItem; + StackToStackAniMoveItem m_aniMoveItem; + bool m_aniRunning; +}; + + + +#endif diff --git a/plugins/qsolocards_plugin/StackToStackFlipAni.cpp b/plugins/qsolocards_plugin/StackToStackFlipAni.cpp new file mode 100644 index 000000000..6ec4565d9 --- /dev/null +++ b/plugins/qsolocards_plugin/StackToStackFlipAni.cpp @@ -0,0 +1,334 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "StackToStackFlipAni.h" +#include "CardAnimationLock.h" +#include "CardPixmaps.h" + +#include +#include + +#include + +const qreal StackToStackFlipAni::ExposedPrecentShownCards=.18; +const qreal StackToStackFlipAni::ExposedPrecentHiddenCards=.02; + +/////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////// +StackToStackFlipAni::StackToStackFlipAni() + :m_pDst(NULL), + m_pSrc(NULL), + m_cardVector(), + m_firstCardToShow(0), + m_flipPtReached(false), + m_moveRecord(), + m_pTimeLine(NULL), + m_pItemAni(NULL), + m_pPixmapItem(NULL), + m_aniRunning(false) +{ +} + +/////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////// +StackToStackFlipAni::~StackToStackFlipAni() +{ +} + +/////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////// +void StackToStackFlipAni::moveCards(CardStack * pDst,CardStack * pSrc, + int numCards,int cardsShown, + int duration) +{ + // first if we have an animation running stop it. + this->stopAni(); + + // setup the next animation. + m_pDst=pDst; + m_pSrc=pSrc; + m_cardVector.clear(); + m_moveRecord.clear(); + m_flipPtReached=false; + + while( !m_pSrc->isEmpty() && numCards>0) + { + PlayingCard card(m_pSrc->removeTopCard(m_moveRecord)); + + m_cardVector.insert(m_cardVector.begin(),card); + numCards--; + } + + // by default we will show all cards + m_firstCardToShow=0; + + // if we are not showing all cards starting with index 0 + // then figure out the index of the first card that will + // be shown. + if (m_cardVector.size()>0 && cardsShown>=0 && + cardsShown<(int)m_cardVector.size()) + { + // ok if the value is 0 or 1. We will just show + // the last card. 0 doesn't make any sense if you + // are flipping cards. So, we will assume one for + // that case as well. + if (cardsShown<=1) + { + m_firstCardToShow=m_cardVector.size()-1; + } + else + { + m_firstCardToShow=m_cardVector.size()-cardsShown; + } + } + + + // if animation is off just immediately add the cards to the new + // stack. Call updateStack to redraw the stacks. And emit the + // signal that the cards have been moved. + if (!CardAnimationLock::getInst().animationsEnabled()) + { + this->flipCards(); + m_pSrc->updateStack(); + + m_pDst->addCards(m_cardVector,m_moveRecord); + m_pDst->updateStack(); + emit cardsMoved(m_moveRecord); + } + else + { + CardAnimationLock::getInst().lock(); + runAnimation(duration); + } + +} + +/////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////// +void StackToStackFlipAni::slotAniFinished(bool emitSignal) +{ + if (m_aniRunning) + { + m_aniRunning=false; + this->m_pTimeLine->stop(); + + m_pDst->addCards(m_cardVector,m_moveRecord); + m_pDst->updateStack(); + + // remove the animation object + m_pSrc->scene()->removeItem(m_pPixmapItem); + delete m_pPixmapItem; + m_pPixmapItem=NULL; + + CardAnimationLock::getInst().unlock(); + + if (emitSignal) + { + emit cardsMoved(m_moveRecord); + } + } +} + +/////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////// +void StackToStackFlipAni::slotAniProgress(qreal currProgress) +{ + if (currProgress>=.6 && !m_flipPtReached) + { + m_flipPtReached=true; + + this->flipCards(); + + QPixmap * pPixmap=this->getAniPixmap(); + + if (pPixmap) + { + m_pPixmapItem->setPixmap(*pPixmap); + delete pPixmap; + } + } +} + +/////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////// +void StackToStackFlipAni::runAnimation(int duration) +{ + m_aniRunning=true; + + delete m_pTimeLine; + delete m_pItemAni; + delete m_pPixmapItem; + + + m_pTimeLine=new QTimeLine(duration); + m_pItemAni=new QGraphicsItemAnimation; + m_pPixmapItem=new QGraphicsPixmapItem; + + + QPixmap * pPixmap=this->getAniPixmap(); + + if (pPixmap) + { + m_pPixmapItem->setPixmap(*pPixmap); + delete pPixmap; + } + + // set the z value to 2 so it will be on top of the + // stacks. + m_pPixmapItem->setZValue(2); + + // add the item to the scene and move it over the stack in the + // place of the cards we are going to move + m_pSrc->scene()->addItem(m_pPixmapItem); + m_pPixmapItem->setPos(m_pSrc->getGlobalLastCardPt()); + + + // setup the animation + m_pItemAni->setItem(m_pPixmapItem); + m_pItemAni->setTimeLine(m_pTimeLine); + + // set the start and end point + m_pItemAni->setPosAt (0, m_pSrc->getGlobalLastCardPt()); + m_pItemAni->setPosAt (1, m_pDst->getGlobalCardAddPt()); + + // set the scaling to give the flipping effect. + m_pItemAni->setScaleAt( 0, 1, 1 ); + m_pItemAni->setScaleAt( 0.6, 0, 1 ); + m_pItemAni->setScaleAt( 1, 1, 1 ); + + // connect up the slot so we will know when it is finished. + this->connect(m_pTimeLine,SIGNAL(finished()), + this,SLOT(slotAniFinished())); + + this->connect(m_pTimeLine,SIGNAL(valueChanged(qreal)), + this,SLOT(slotAniProgress(qreal))); + + // update the src stack behind the flip item we just added + m_pSrc->updateStack(); + + m_pTimeLine->start(); +} + +/////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////// +QPixmap * StackToStackFlipAni::getAniPixmap() +{ + QPixmap * pPixmap=NULL; + + if (m_cardVector.size()>0) + { + unsigned int i; + + pPixmap =new QPixmap(this->calcPixmapSize()); + // for linux the transparent fill must be done before + // we associate the pixmap with the painter + pPixmap->fill(Qt::transparent); + + QPainter painter(pPixmap); + + + QPoint pt(0,0); + + for (i=0;i=m_firstCardToShow && m_cardVector[index].isFaceUp()) + { + increment=CardPixmaps::getInst().getCardSize().width()*ExposedPrecentShownCards; + } + else + { + increment=CardPixmaps::getInst().getCardSize().width()*ExposedPrecentHiddenCards; + } + } + + return increment; +} + +/////////////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////////////// +void StackToStackFlipAni::flipCards() +{ + + if (m_cardVector.size()>0) + { + int i; + + PlayingCardVector flipVector; + + for(i=m_cardVector.size()-1;i>=0;i--) + { + m_cardVector[i].setFaceUp(!m_cardVector[i].isFaceUp()); + flipVector.push_back(m_cardVector[i]); + } + + m_cardVector.clear(); + m_cardVector=flipVector; + } +} diff --git a/plugins/qsolocards_plugin/StackToStackFlipAni.h b/plugins/qsolocards_plugin/StackToStackFlipAni.h new file mode 100644 index 000000000..f4065c894 --- /dev/null +++ b/plugins/qsolocards_plugin/StackToStackFlipAni.h @@ -0,0 +1,80 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef __STACKTOSTACKFLIPANI_H__ +#define __STACKTOSTACKFLIPANI_H__ + +#include "CardStack.h" +#include "CardMoveRecord.h" + +#include +#include +#include +#include +#include + +class StackToStackFlipAni: public QObject +{ + Q_OBJECT +public: + static const qreal ExposedPrecentShownCards; + static const qreal ExposedPrecentHiddenCards; + + StackToStackFlipAni(); + virtual ~StackToStackFlipAni(); + + inline bool isAniRunning() const{return m_aniRunning;} + + inline void stopAni(){if (m_aniRunning){slotAniFinished(false);m_aniRunning=false;}} + + void moveCards(CardStack * pDst,CardStack * pSrc, + int numCards=1,int cardsShown=-1, + int duration=500); + +signals: + void cardsMoved(const CardMoveRecord & moveRecord); + +public slots: + void slotAniFinished(bool emitSignal=true); + void slotAniProgress(qreal currProgress); + +protected: + virtual void runAnimation(int duration); + + virtual QPixmap * getAniPixmap(); + + QSize calcPixmapSize(); + int getOverlapIncrement(unsigned int index); + + void flipCards(); + +private: + CardStack * m_pDst; + CardStack * m_pSrc; + PlayingCardVector m_cardVector; + unsigned int m_firstCardToShow; // first index into m_cardVector to show + bool m_flipPtReached; + CardMoveRecord m_moveRecord; + + QTimeLine * m_pTimeLine; + QGraphicsItemAnimation * m_pItemAni; + QGraphicsPixmapItem * m_pPixmapItem; + bool m_aniRunning; +}; + +#endif diff --git a/plugins/qsolocards_plugin/VCardStack.cpp b/plugins/qsolocards_plugin/VCardStack.cpp new file mode 100644 index 000000000..3f4a21c6c --- /dev/null +++ b/plugins/qsolocards_plugin/VCardStack.cpp @@ -0,0 +1,333 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "VCardStack.h" +#include "CardPixmaps.h" +#include +#include + +#include + +const qreal VCardStack::ExposedPrecentFaceUp=.23; +const qreal VCardStack::ExposedPrecentFaceDown=.10; + +//////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////// +VCardStack::VCardStack() + :m_bRectVector(), + m_compressValue(CompressNormal), + m_percentScene(1) +{ +} + +//////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////// +VCardStack::~VCardStack() +{ +} + +//////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////// +void VCardStack::setStackBottom(qreal percentScene) +{ + if(percentScene>=0 && percentScene<=1) + { + m_percentScene=percentScene; + } + else + { + m_percentScene=1; + } +} + +//////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////// +QPointF VCardStack::getGlobalCardAddPt() const +{ + QPointF pt(0,0); + + const PlayingCardVector & cardVector=this->getCardVector(); + + // We are going to do this by the bounding rects and not by actual cards + // in the stacks. That way we can add something before doing animations + // and then update the display when the animation is complete + if (m_bRectVector.size()>0 && cardVector.size()>=m_bRectVector.size()) + { + pt=m_bRectVector[m_bRectVector.size()-1].topLeft(); + + pt.ry()+=getOverlapIncrement(cardVector[m_bRectVector.size()-1], + m_compressValue); + } + + return mapToScene(pt); +} + +//////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////// +QPointF VCardStack::getGlobalLastCardPt() const +{ + QPointF pt(0,0); + + const PlayingCardVector & cardVector=this->getCardVector(); + + // We are going to do this by the bounding rects and not by actual cards + // in the stacks. That way we can add something before doing animations + // and then update the display when the animation is complete + if (m_bRectVector.size()>0 && cardVector.size()>=m_bRectVector.size()) + { + pt=m_bRectVector[m_bRectVector.size()-1].topLeft(); + } + + return mapToScene(pt); +} + +//////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////// +QPointF VCardStack::getGlobalCardPt(int index) const +{ + QPointF pt(0,0); + + if (index>=0 && index<(int)m_bRectVector.size()) + { + pt=m_bRectVector[index].topLeft(); + } + + return mapToScene(pt); +} + +//////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////// +void VCardStack::updateStack() +{ + QSize size; + const PlayingCardVector & cardVector=this->getCardVector(); + + // the compress value decresses how much of cards are exposed. + // The preferred exposed value is normal. But we will decrease the + // values down to a quarter of the desired to make the stack fit on + // the screen. This function uses the m_precentScene value to determine + // the bottom point of the stack + for(m_compressValue=CompressNormal;m_compressValuescene()->sceneRect().bottom()*m_percentScene)>mapToScene(QPointF(0,size.height())).y()) + { + break; + } + } + + QPixmap * pPixmap=NULL; + + // draw the card and calc the bounding rectangles while we are at it. + if (this->isFlipAniRunning()) + { + PlayingCardVector newCardVector(cardVector); + + // the stack should have at least one card ie the one being flipped + // but make sure. + if (cardVector.size()>0) + { + newCardVector.pop_back(); + } + + // draw the card and calc the bounding rectangles while we are at it. + pPixmap=getStackPixmap(newCardVector,isHighlighted(), + hintHighlightIndex(),m_compressValue, + &m_bRectVector); + } + else + { + // draw the card and calc the bounding rectangles while we are at it. + pPixmap=getStackPixmap(cardVector,isHighlighted(), + hintHighlightIndex(),m_compressValue, + &m_bRectVector); + } + + if (NULL!=pPixmap) + { + this->setPixmap(*pPixmap); + delete pPixmap; + } +} + +//////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////// +QPixmap * VCardStack::getStackPixmap(const PlayingCardVector & cardVector, + bool highlighted, + int hintHighlightIndex) +{ + return getStackPixmap(cardVector,highlighted, + hintHighlightIndex,CompressNormal,NULL); +} + +//////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////// +bool VCardStack::getCardIndex(const QPointF & pos,unsigned int & index) +{ + bool rc=false; + + unsigned int i; + + for(i=0;im_bRectVector.size();i++) + { + if (this->m_bRectVector[i].contains(pos)) + { + index=i; + rc=true; + break; + } + } + + return rc; +} + + +//////////////////////////////////////////////////////////////////////////////////// +//////////////////////////////////////////////////////////////////////////////////// +void VCardStack::calcPixmapSize(const PlayingCardVector & cardVector, + QSize & size,qreal compressValue) +{ + unsigned int i; + + if (0==cardVector.size()) + { + size=CardPixmaps::getInst().getCardSize(); + } + else + { + unsigned int sizeY=0; + + for (i=0;iclear(); + } + + // first handle the case that there are no cards in the stack + if (0==cardVector.size()) + { + bool hl=(highlighted || HintHighlightNoCards==hintHighlightIndex); + pPixmap=new QPixmap(CardPixmaps::getInst().getCardNonePixmap(hl,this->showRedealCircle())); + } + else + { + unsigned int i; + QSize cardSize(CardPixmaps::getInst().getCardSize()); + QSize pixmapSize(0,0); + + this->calcPixmapSize(cardVector,pixmapSize,compressValue); + + pPixmap =new QPixmap(pixmapSize); + // for linux the transparent fill must be done before + // we associate the pixmap with the painter + pPixmap->fill(Qt::transparent); + + QPainter painter(pPixmap); + + + QPoint pt(0,0); + + for (i=0;i=0 && hintHighlightIndex<=(int)i) || + ((cardVector.size()-1==i) && highlighted)); + + if (cardVector[i].isFaceUp()) + { + painter.drawPixmap(pt,CardPixmaps::getInst().getCardPixmap(cardVector[i],hl)); + } + else + { + painter.drawPixmap(pt,CardPixmaps::getInst().getCardBackPixmap(hl)); + } + + unsigned int incrementValue=getOverlapIncrement(cardVector[i], + compressValue); + + if (pBRectVector) + { + // if it is the last card we just want the full size + // of the card. + if (cardVector.size()-1==i) + { + pBRectVector->push_back(QRectF(QPointF(0,pt.y()),cardSize)); + } + else + { + pBRectVector->push_back(QRectF(QPointF(0,pt.y()),QSize(cardSize.width(),incrementValue))); + } + } + + // increment the point that we are going to paint the + // card pixmap onto this pixmap + pt.ry()+=incrementValue; + + } + } + return pPixmap; +} diff --git a/plugins/qsolocards_plugin/VCardStack.h b/plugins/qsolocards_plugin/VCardStack.h new file mode 100644 index 000000000..c78a0f8aa --- /dev/null +++ b/plugins/qsolocards_plugin/VCardStack.h @@ -0,0 +1,88 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef VCARDSTACK_H +#define VCARDSTACK_H + +#include "CardStack.h" +#include +#include + +typedef std::vector CardBRectVect; + + +// this class will show cards stacked but all cards +// will be partly visible with a card on top of a card revealing +// a portion of the top of the card beneath it. +class VCardStack: public CardStack +{ + Q_OBJECT +public: + static const qreal ExposedPrecentFaceUp; // the precentage show for a face up card will be more than + // that for a card that is face down. Since, we want to be + // able to see the value of the card if it is face up. + static const qreal ExposedPrecentFaceDown; + + enum + { + CompressNormal=1, + CompressMax=4 + }; + + VCardStack(); + virtual ~VCardStack(); + + + // this function allows the caller to set the preportion of the screen that the + // stack can decend too. For example, 1 is the default which means to the bottom + // of the scene. To make the bottom 3/4 of the scene use .75 etc... 1 is the maximum + // value. + void setStackBottom(qreal percentScene); + qreal stackBottom() const{return m_percentScene;} + + // this function gets the point in the scene that a card would be added to this stack. + virtual QPointF getGlobalCardAddPt() const; + virtual QPointF getGlobalLastCardPt() const; + virtual QPointF getGlobalCardPt(int index) const; + + virtual void updateStack(); + + virtual QPixmap * getStackPixmap(const PlayingCardVector & cardVector, + bool highlighted=false, + int hintHighlightIndex=-1); +protected: + virtual bool getCardIndex(const QPointF & pos,unsigned int & index); + + void calcPixmapSize(const PlayingCardVector & cardVector, + QSize & size,qreal compressValue); + + virtual unsigned int getOverlapIncrement(const PlayingCard & card,qreal compressValue) const; + + virtual QPixmap * getStackPixmap(const PlayingCardVector & cardVector, + bool highlighted, + int hintHighlightIndex, + qreal compressValue, + CardBRectVect * pBRectVector); + +private: + CardBRectVect m_bRectVector; + + qreal m_compressValue; + qreal m_percentScene; +}; +#endif diff --git a/plugins/qsolocards_plugin/YukonBoard.cpp b/plugins/qsolocards_plugin/YukonBoard.cpp new file mode 100644 index 000000000..e2865e4e9 --- /dev/null +++ b/plugins/qsolocards_plugin/YukonBoard.cpp @@ -0,0 +1,488 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "YukonBoard.h" +#include "CardPixmaps.h" +#include + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +YukonBoard::YukonBoard() + :GameBoard(NULL,QString(tr("Yukon Solitaire")).trimmed(),QString("Yukon")), + m_pDeck(NULL), + m_homeVector(), + m_stackVector(), + m_cheat(false) +{ + this->setHelpFile(":/help/YukonHelp.html"); +} + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +YukonBoard::~YukonBoard() +{ +} + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +bool YukonBoard::getHint(CardStack * & pSrc, + unsigned int & srcStackIndex, + CardStack * & pDst) +{ + bool rc=false; + unsigned int i; + + // ok we will look for a move based on trying to move the first faceup + // card in a stack. The basic strategy for this game is to get all cards turned + // over. + if (!rc) + { + for (i=0;im_stackVector.size() && !rc;i++) + { + unsigned int j; + + for (j=0;jm_stackVector.size() && !rc;j++) + { + // can't move a stack to itself + if (i!=j) + { + PlayingCardVector addCardVector(this->m_stackVector[j]->getCardVector()); + unsigned int k=0; + while (!rc && addCardVector.size()>0) + { + // ok find the first card that is faceup. + if (!addCardVector[0].isFaceUp()) + { + addCardVector.erase(addCardVector.begin()); + } + // no need to do this if a king is already face up and the first card in the stack. + else if (!(PlayingCard::King==addCardVector[0].getIndex() && 0==k && + this->m_stackVector[i]->isEmpty()) && + this->m_stackVector[i]->canAddCards(addCardVector)) + { + pDst=this->m_stackVector[i]; + srcStackIndex=k; + pSrc=this->m_stackVector[j]; + + rc=true; + } + else + { + break; + } + k++; + } + } + } + } + } + + // ok let's see if we have an empty stack + // and a face up king. + if (!rc) + { + CardStack * pEmptyStack=NULL; + CardStack * pFaceUpKingStack=NULL; + unsigned int faceUpKingIndex=0; + + for (i=0;im_stackVector.size() && !rc;i++) + { + if (NULL==pEmptyStack && this->m_stackVector[i]->isEmpty()) + { + pEmptyStack=this->m_stackVector[i]; + } + + if (NULL==pFaceUpKingStack) + { + const PlayingCardVector cardVector=this->m_stackVector[i]->getCardVector(); + + unsigned int j; + + for(j=0;jm_homeVector.size() && !rc;i++) + { + unsigned int j; + + for (j=0;jm_stackVector.size() && !rc;j++) + { + const PlayingCardVector cardVector=this->m_stackVector[j]->getCardVector(); + + if (cardVector.size()>0) + { + PlayingCardVector addCardVector; + + addCardVector.push_back(cardVector[cardVector.size()-1]); + + if (this->m_homeVector[i]->canAddCards(addCardVector)) + { + pDst=this->m_homeVector[i]; + srcStackIndex=cardVector.size()-1; + pSrc=this->m_stackVector[j]; + + rc=true; + } + } + } + } + } + + // look at each stack and try to find the first available card that from another + // stack that can be moved to the stack. + if (!rc) + { + for (i=0;im_stackVector.size() && !rc;i++) + { + unsigned int j; + + for (j=0;jm_stackVector.size() && !rc;j++) + { + // can't move a stack to itself + if (i!=j) + { + PlayingCardVector addCardVector(this->m_stackVector[j]->getCardVector()); + unsigned int k=0; + while (!rc && addCardVector.size()>0) + { + // ok find the first card that is faceup. + if (!addCardVector[0].isFaceUp()) + { + addCardVector.erase(addCardVector.begin()); + } + else if (this->m_stackVector[i]->canAddCards(addCardVector)) + { + pDst=this->m_stackVector[i]; + srcStackIndex=k; + pSrc=this->m_stackVector[j]; + + rc=true; + } + else + { + addCardVector.erase(addCardVector.begin()); + } + k++; + } + } + } + } + } + + + + return rc; +} + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +void YukonBoard::newGame() +{ + // call the base class + GameBoard::newGame(); + + CardDeck deck; + unsigned int i; + + + while(!deck.isEmpty()) + { + this->m_pDeck->addCard(deck.next()); + } + + + DealItemVector dealItemVector; + + + // Create the dealItemVector to direct the DealAnimation object on + // how to deal the cards. + for (i=0;im_stackVector.size();i++) + { + dealItemVector.push_back(DealItem(this->m_stackVector[i],m_pDeck)); + + unsigned int j; + + for (j=0;j0) + { + for (j=0;j<4;j++) + { + dealItemVector[i].addCard(true); + } + } + } + + // ok now start the deal. We don't need a move record for this item. + m_dealAni.dealCards(dealItemVector,false); +} + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +void YukonBoard::addGameMenuItems(QMenu & menu) +{ + Q_UNUSED(menu); +} + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +void YukonBoard::loadSettings(const QSettings & settings) +{ + Q_UNUSED(settings); +} + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +void YukonBoard::saveSettings(QSettings & settings) +{ + Q_UNUSED(settings); +} + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +void YukonBoard::setCheat(bool cheat) +{ + this->m_cheat=cheat; + + for(unsigned int i=0;im_stackVector.size();i++) + { + m_stackVector[i]->setCheat(cheat); + } +} + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +void YukonBoard::slotStackCardsClicked(CardStack * pCardStack, + const PlayingCardVector & cardVector, + const CardMoveRecord & startMoveRecord) +{ + unsigned int i=0; + CardStack * pFoundStack=NULL; + + if (NULL==pCardStack) + { + return; + } + + // first see if the card can be added to the sent home stack + if (cardVector.size()==1) + { + for(i=0;im_homeVector.size();i++) + { + if (pCardStack!=this->m_homeVector[i] && + this->m_homeVector[i]->canAddCards(cardVector)) + { + pFoundStack=this->m_homeVector[i]; + break; + } + } + } + + // if we did not find a match look at the stacks. + if (NULL==pFoundStack) + { + for(i=0;im_stackVector.size();i++) + { + if (pCardStack!=this->m_stackVector[i] && + this->m_stackVector[i]->canAddCards(cardVector)) + { + pFoundStack=this->m_stackVector[i]; + break; + } + } + } + + if (pFoundStack) + { + CardMoveRecord moveRecord(startMoveRecord); + pFoundStack->addCards(cardVector,moveRecord,true); + + // perform the move of the cards and animate it if animations + // are enabled + m_sToSAniMove.moveCards(moveRecord); + } +} + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +void YukonBoard::calcScore() +{ + int score=0; + + for(unsigned int i=0;im_homeVector.size();i++) + { + score+=this->m_homeVector[i]->score(); + } + + emit scoreChanged(score,""); +} + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +void YukonBoard::resizeEvent (QResizeEvent * event) +{ + int i; + + this->setCardResizeAlg(8,ResizeByWidth); + + GameBoard::resizeEvent(event); + + QSize cardSize(CardPixmaps::getInst().getCardSize()); + + // ok let's see if it fits when we size things by width + // basically we just need to check if we have room to draw + // 4 cards vertically. If we don't have enough room we + // will try to draw by height. + if (cardSize.height()*4+GameBoard::LayoutSpacing*5>event->size().height()) + { + this->setCardResizeAlg(4,ResizeByHeight); + + GameBoard::resizeEvent(event); + + cardSize=CardPixmaps::getInst().getCardSize(); + } + + + + QPointF currPos(GameBoard::LayoutSpacing,GameBoard::LayoutSpacing); + + + for (i=0;i(m_homeVector.size());i++) + { + m_homeVector[i]->setPos(currPos); + currPos.ry()+=GameBoard::LayoutSpacing+cardSize.height(); + } + + currPos.setX(event->size().width()-GameBoard::LayoutSpacing-cardSize.width()); + currPos.setY(GameBoard::LayoutSpacing); + for (i=m_stackVector.size()-1;i>=0;i--) + { + m_stackVector[i]->setPos(currPos); + currPos.rx()-=cardSize.width()+GameBoard::LayoutSpacing; + } + + + currPos.setX(GameBoard::LayoutSpacing*4+cardSize.width()*4); + currPos.setY(event->size().height()-GameBoard::LayoutSpacing-cardSize.height()); + + m_pDeck->setPos(currPos); + +} + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +void YukonBoard::createStacks() +{ + unsigned int i; + + // first create the home widgets where the cards need to be eventually stacked to + // win the game. + for(i=0;i<4;i++) + { + this->m_homeVector.push_back(new FreeCellHome); + this->m_scene.addItem(m_homeVector[i]); + } + + // now create the 7 rows for the stacks. + for (i=0;i<7;i++) + { + this->m_stackVector.push_back(new KlondikeStack); + this->m_scene.addItem(m_stackVector[i]); + this->connect(this->m_stackVector[i],SIGNAL(cardsMovedByDragDrop(CardMoveRecord)), + this,SLOT(slotCardsMoved(CardMoveRecord))); + this->connect(this->m_stackVector[i],SIGNAL(movableCardsClicked(CardStack*,PlayingCardVector,CardMoveRecord)), + this,SLOT(slotStackCardsClicked(CardStack*,PlayingCardVector,CardMoveRecord))); + } + + this->m_pDeck=new FreeCellDeck; + this->m_scene.addItem(this->m_pDeck); + +} + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +bool YukonBoard::isGameWon()const +{ + bool rc=true; + + for (unsigned int i=0;im_homeVector.size();i++) + { + if (!this->m_homeVector[i]->isStackComplete()) + { + rc=false; + break; + } + } + + return rc; +} + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////////////////////////////////////////////////////// +bool YukonBoard::isGameWonNotComplete()const +{ + bool rc=true; + + for (unsigned int i=0;im_stackVector.size();i++) + { + if (!(this->m_stackVector[i]->cardsAscendingTopToBottom() && + this->m_stackVector[i]->allCardsFaceUp())) + { + rc=false; + break; + } + } + + return rc; +} diff --git a/plugins/qsolocards_plugin/YukonBoard.h b/plugins/qsolocards_plugin/YukonBoard.h new file mode 100644 index 000000000..64a38a740 --- /dev/null +++ b/plugins/qsolocards_plugin/YukonBoard.h @@ -0,0 +1,80 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef __YUKONBOARD_H__ +#define __YUKONBOARD_H__ + +#include "GameBoard.h" +#include "FreeCellHome.h" +#include "FreeCellDeck.h" +#include "KlondikeStack.h" + +#include + + +class YukonBoard : public GameBoard +{ + Q_OBJECT +public: + YukonBoard(); + ~YukonBoard(); + + bool getHint(CardStack * & pSrc, + unsigned int & srcStackIndex, + CardStack * & pDst); + + inline bool hasDemo() const {return true;} + + void newGame(); + + void addGameMenuItems(QMenu & menu); + + void loadSettings(const QSettings & settings); + void saveSettings(QSettings & settings); + + inline bool isCheating() const {return m_cheat;} + + void setCheat(bool cheat); + + inline bool supportsScore() const{return true;} + +public slots: + void slotStackCardsClicked(CardStack * pCardStack, + const PlayingCardVector & cardVector, + const CardMoveRecord &); + +protected: + void calcScore(); + + virtual void resizeEvent (QResizeEvent * event); + + virtual void createStacks(); + + bool isGameWon()const; + bool isGameWonNotComplete()const; + +private: + FreeCellDeck * m_pDeck; + + std::vector m_homeVector; // we will have 4 items in this vector one for each suit + std::vector m_stackVector; // we will have 7 items in this vector + + bool m_cheat; +}; + +#endif // YUKONBOARD_H diff --git a/plugins/qsolocards_plugin/help/._gpl3.html b/plugins/qsolocards_plugin/help/._gpl3.html new file mode 100644 index 000000000..864802133 Binary files /dev/null and b/plugins/qsolocards_plugin/help/._gpl3.html differ diff --git a/plugins/qsolocards_plugin/help/FreeCellHelp.html b/plugins/qsolocards_plugin/help/FreeCellHelp.html new file mode 100644 index 000000000..71d1499eb --- /dev/null +++ b/plugins/qsolocards_plugin/help/FreeCellHelp.html @@ -0,0 +1,62 @@ + + + + + + + + + + + + + + + +

Freecell +Solitaire

+

Written +by Steve Moore

+

Overview

+

Freecell +Solitaire is a solitaire game played with the standard 52 card deck. +The object is to arrange cards of the same suit from ace to king.

+

Rules

+

The +board is setup with eight stacks of cards, four “freecells”, and +four home stacks. The goal is to move all cards to the home stacks in +ascending order from ace to king of the same suit. Cards are placed +one at a time in order on the home stacks. The eight stacks of cards +are dealt with the first four stacks containing seven cards and the +last four contains size cards. All cards in the eight stacks are +dealt face up. Cards can be moved between the stacks by placing red +cards on black cards in descending order from king to ace. But only +one card can be moved to a stack or freecell at a time. A card can +also be played on the home stack, if it is an ace or the next card in +ascending order of a suit in one of the home stacks. Any card can be +placed in an empty freecell or an empty stack. Play will continue +until all moves are exhausted or until all cards are moved to the +home stacks and the game is won. +

+

Scoring

+

A +point is scored when a card is moved to one of the home stacks. A +total of 52 points can be scored, one for each card in the deck. The +current score is indicated in the status bar at the bottom of the +game window.

+

Game +Play

+

Cards +that are movable will be indicated when the mouse is over them with +the open hand icon. Cards with the open hand icon displayed over them +can be dragged and dropped to another stack or clicked to move them +to another stack. Hints of possible moves are available from the menu +select Control->Hint.

+ + \ No newline at end of file diff --git a/plugins/qsolocards_plugin/help/KlondikeHelp.html b/plugins/qsolocards_plugin/help/KlondikeHelp.html new file mode 100644 index 000000000..1da5ab701 --- /dev/null +++ b/plugins/qsolocards_plugin/help/KlondikeHelp.html @@ -0,0 +1,81 @@ + + + + + + + + + + + + + + + +

Klondike +Solitaire

+

Written +by Steve Moore

+

Overview

+

Klondike +Solitaire is a solitaire game played with the standard 52 card deck. +The variations of the game all deal with how many cards are flipped +at once from the deck, and how many times the deck of cards can be +cycled through. The variations are:

+
    +
  • Flip + one – one card is flipped over from the deck at a time, and the + deck can be recycled two times.

    +
  • Flip + three – three cards are flipped over from the deck at a time, and + the there is no limit on the number of times the deck can be + recycled. +

    +
  • No + redeals (flip one) – one card is flipped over from the deck at a + time, and the deck cannot be recycled.

    +
+

Rules

+

The +board is setup with seven stacks of cards, a deck of the remaining +cards, and four home stacks. The goal is to move all cards to the +home stacks in ascending order from ace to king of the same suit. +Cards are placed one at a time in order on the home stacks. The +seven stacks of cards are dealt with each stack containing one more +card than the previous stack. The first stack will contain one card +and the last of the seven will contain seven cards. All cards in the +seven stacks are face down accept the top card. Cards can be moved +between the stacks by placing red cards on black cards in descending +order from king to ace. When a card is moved of a stack with a face +down card being exposed it will be flipped over automatically. A +card can also be played on the home stack, if it is an ace or the +next card in ascending order of a suit in one of the home stacks. +Once moves are exhausted on the board the next set of cards can be +flipped over from the deck. The top card in the flipped over cards +from the deck can be played using the same rules described for the +stacks. Play will continue until all moves are exhausted or until +all cards are moved to the home stacks and the game is won. +

+

Scoring

+

A +point is scored when a card is moved to one of the home stacks. A +total of 52 points can be scored, one for each card in the deck. The +current score is indicated in the status bar at the bottom of the +game window.

+

Game +Play

+

Cards +that are movable will be indicated when the mouse is over them with +the open hand icon. Cards with the open hand icon displayed over them +can be dragged and dropped to another stack or clicked to move +them to another stack. Hints of possible moves are available from the +menu select Control->Hint.

+ + diff --git a/plugins/qsolocards_plugin/help/Spider3DeckHelp.html b/plugins/qsolocards_plugin/help/Spider3DeckHelp.html new file mode 100644 index 000000000..2b81dcb09 --- /dev/null +++ b/plugins/qsolocards_plugin/help/Spider3DeckHelp.html @@ -0,0 +1,70 @@ + + + + + + + + + + + + + + + +

Three +Deck Spider Solitaire

+

Written +by Steve Moore

+

Overview

+

Three +Deck Spider Solitaire is a variation of Spider Solitaire played with +156 cards or three full decks of playing cards. +

+

Rules

+

The +cards are dealt into six rows of six cards, and six rows of five +cards. All the cards are face down except the last card in each +stack. A card can be moved from one stack to another if it is the +next card in descending order with King being high and Ace being low +regardless of suit. But a stack of cards can only be moved if they +are in descending order and the same suit. Once moves are exhausted +twelve cards can be dealt one on top of each stack ( The last deal is +an exception cards are only added to the first six stacks. ). Cards +cannot be dealt if there is an empty stack.

+

The +object of the game is to get all twelve suits in descending order +from King to Ace. Once a suit is complete it can be sent home or +moved to one of the twelve empty slots at the top of the board. Once +all twelve suits are sent home the game is over.

+

Scoring

+

A +point is scored when cards in descending order of the same suit are +stacked on one another. So, the total number of points available is +144 or 12 for each suit. The score along with the number of deals +remaining are indicated in the status bar at the bottom of the game +window.

+

Game +Play

+

Cards +that are movable will be indicated when the mouse is over them with +the open hand icon. Cards with the open hand icon displayed over them +can be dragged and dropped to another stack or clicked to move them +to another stack ( For the click case the cards are moved to a +matching suit, non-matching suit, or an empty stack in that order. In +some cases it might be necessary to drag and drop the cards to move +them to the exact stack desired. ). When all moves are exhausted, the +next set of cards can be dealt on top of the current cards by +clicking on the deck in the upper left corner of the board. +

+

Hints +of possible moves are available from the menu select Control->Hint.

+ + \ No newline at end of file diff --git a/plugins/qsolocards_plugin/help/SpiderHelp.html b/plugins/qsolocards_plugin/help/SpiderHelp.html new file mode 100644 index 000000000..8733b68bb --- /dev/null +++ b/plugins/qsolocards_plugin/help/SpiderHelp.html @@ -0,0 +1,78 @@ + + + + + + + + + + + + + + + +

Spider +Solitaire

+

Written +by Steve Moore

+

Overview

+

Spider +Solitaire is a solitaire game played with 104 cards. It has three +different variations.

+
    +
  • Four + suits – two complete 52 card decks are used.

    +
  • Two + suits – four sets each of hearts and spades are used.

    +
  • One + suit – eight sets of spades are used.

    +
+

Rules

+

The +game is played the same regardless of the variation. The cards are +dealt into four rows of six cards, and six rows of five cards. All +the cards are face down except the last card in each stack. A card +can be moved from one stack to another if it is the next card in +descending order with King being high and Ace being low regardless of +suit. But a stack of cards can only be moved if they are in +descending order and the same suit. Once moves are exhausted ten +cards can be dealt one on top of each stack. Cards cannot be dealt if +there is an empty stack.

+

The +object of the game is to get all eight sets of suits ( There are +eight sets regardless of the variation. ) in descending order from +King to Ace. Once a suit is complete it can be sent home or moved to +one of the eight empty slots at the top of the board. Once all eight +suits are sent home the game is over.

+

Scoring

+

A +point is scored when cards in descending order of the same suit are +stacked on one another. So, the total number of points available is +96 or 12 for each suit. The score along with the number of deals +remaining are indicated in the status bar at the bottom of the game +window.

+

Game +Play

+

Cards +that are movable will be indicated when the mouse is over them with +the open hand icon. Cards with the open hand icon displayed over them +can be dragged and dropped to another stack or clicked to move them +to another stack ( For the click case the cards are moved to a +matching suit, non-matching suit, or an empty stack in that order. In +some cases it might be necessary to drag and drop the cards to move +them to the exact stack desired. ). When all moves are exhausted, the +next set of cards can be dealt on top of the current cards by +clicking on the deck in the upper left corner of the board. +

+

Hints +of possible moves are available from the menu select Control->Hint.

+ + \ No newline at end of file diff --git a/plugins/qsolocards_plugin/help/SpideretteHelp.html b/plugins/qsolocards_plugin/help/SpideretteHelp.html new file mode 100644 index 000000000..20f7d22bc --- /dev/null +++ b/plugins/qsolocards_plugin/help/SpideretteHelp.html @@ -0,0 +1,71 @@ + + + + + + + + + + + + + + + +

Spiderette +Solitaire

+

Written +by Steve Moore

+

Overview

+

Spiderette +Solitaire is a solitaire game played with a standard 52 card deck. +It is a variation of Spider Solitaire that is played with a board +layout similar to that of Klondike Solitaire.

+

Rules

+

The +cards are dealt into seven stacks. The number of cards increases by +one for each stack. The first stack contains one card and the last +contains seven. All the cards are face down except the last card in +each stack. A card can be moved from one stack to another if it is +the next card in descending order with King being high and Ace being +low regardless of suit. But a stack of cards can only be moved if +they are in descending order and the same suit. Once moves are +exhausted seven cards can be dealt one on top of each stack ( The +last deal is an exception cards are only added to the first three +stacks. ). Cards cannot be dealt if there is an empty stack.

+

The +object of the game is to get all four suits in descending order from +King to Ace. Once a suit is complete it can be sent home or moved to +one of the four empty slots at the top of the board. Once all fourxs +suits are sent home the game is over.

+

Scoring

+

A +point is scored when cards in descending order of the same suit are +stacked on one another. So, the total number of points available is +48 or 12 for each suit. The score along with the number of deals +remaining are indicated in the status bar at the bottom of the game +window.

+

Game +Play

+

Cards +that are movable will be indicated when the mouse is over them with +the open hand icon. Cards with the open hand icon displayed over them +can be dragged and dropped to another stack or clicked to move them +to another stack ( For the click case the cards are moved to a +matching suit, non-matching suit, or an empty stack in that order. In +some cases it might be necessary to drag and drop the cards to move +them to the exact stack desired. ). When all moves are exhausted, the +next set of cards can be dealt on top of the current cards by +clicking on the deck in the upper left corner of the board. +

+

Hints +of possible moves are available from the menu select Control->Hint.

+ + \ No newline at end of file diff --git a/plugins/qsolocards_plugin/help/YukonHelp.html b/plugins/qsolocards_plugin/help/YukonHelp.html new file mode 100644 index 000000000..f56597dbc --- /dev/null +++ b/plugins/qsolocards_plugin/help/YukonHelp.html @@ -0,0 +1,67 @@ + + + + + + + + + + + + + + + +

Yukon +Solitaire

+

Written +by Steve Moore

+

Overview

+

Yukon +Solitaire is a solitaire game played with the standard 52 card deck. +The object is to arrange cards of the same suit from ace to king.

+

Rules

+

The +board is setup with seven stacks of cards, and four home stacks. The +goal is to move all cards to the home stacks in ascending order from +ace to king of the same suit. Cards are placed one at a time in order +on the home stacks. The seven stacks of cards are dealt. The first +stack has just one face up card. The remaining have one ( second +stack ) increasing to six ( seventh stack ) cards face down and five +cards face up. Cards can be moved between the stacks by placing red +cards on black cards in ascending order ( You can move cards as deep +in the a stack as you wish. The red to black ascending relationship +only applies to the top card being moved and the last card in the +stack to which it is moved. ). When a card is moved of a stack with +a face down card being exposed it will be flipped over automatically. +A card can also be played on the home stack, if it is an ace or the +next card in ascending order of a suit in one of the home stacks. +Once moves are exhausted on the board the next set of cards can be +flipped over from the deck. The top card in the flipped over cards +from the deck can be played using the same rules described for the +stacks. Play will continue until all moves are exhausted or until all +cards are moved to the home stacks and the game is won. +

+

Scoring

+

A +point is scored when a card is moved to one of the home stacks. A +total of 52 points can be scored, one for each card in the deck. The +current score is indicated in the status bar at the bottom of the +game window.

+

Game +Play

+

Cards +that are movable will be indicated when the mouse is over them with +the open hand icon. Cards with the open hand icon displayed over them +can be dragged and dropped to another stack or clicked to move them +to another stack. Hints of possible moves are available from the menu +select Control->Hint.

+ + \ No newline at end of file diff --git a/plugins/qsolocards_plugin/help/gpl3.html b/plugins/qsolocards_plugin/help/gpl3.html new file mode 100644 index 000000000..d127cadf1 --- /dev/null +++ b/plugins/qsolocards_plugin/help/gpl3.html @@ -0,0 +1,692 @@ + + + + + + GNU General Public License - GNU Project - Free Software Foundation (FSF) + +

GNU GENERAL PUBLIC LICENSE

+

Version 3, 29 June 2007

+ +

Copyright © 2007 Free Software Foundation, Inc. <http://fsf.org/>

+ Everyone is permitted to copy and distribute verbatim copies + of this license document, but changing it is not allowed.

+ +

Preamble

+ +

The GNU General Public License is a free, copyleft license for +software and other kinds of works.

+ +

The licenses for most software and other practical works are designed +to take away your freedom to share and change the works. By contrast, +the GNU General Public License is intended to guarantee your freedom to +share and change all versions of a program--to make sure it remains free +software for all its users. We, the Free Software Foundation, use the +GNU General Public License for most of our software; it applies also to +any other work released this way by its authors. You can apply it to +your programs, too.

+ +

When we speak of free software, we are referring to freedom, not +price. Our General Public Licenses are designed to make sure that you +have the freedom to distribute copies of free software (and charge for +them if you wish), that you receive source code or can get it if you +want it, that you can change the software or use pieces of it in new +free programs, and that you know you can do these things.

+ +

To protect your rights, we need to prevent others from denying you +these rights or asking you to surrender the rights. Therefore, you have +certain responsibilities if you distribute copies of the software, or if +you modify it: responsibilities to respect the freedom of others.

+ +

For example, if you distribute copies of such a program, whether +gratis or for a fee, you must pass on to the recipients the same +freedoms that you received. You must make sure that they, too, receive +or can get the source code. And you must show them these terms so they +know their rights.

+ +

Developers that use the GNU GPL protect your rights with two steps: +(1) assert copyright on the software, and (2) offer you this License +giving you legal permission to copy, distribute and/or modify it.

+ +

For the developers' and authors' protection, the GPL clearly explains +that there is no warranty for this free software. For both users' and +authors' sake, the GPL requires that modified versions be marked as +changed, so that their problems will not be attributed erroneously to +authors of previous versions.

+ +

Some devices are designed to deny users access to install or run +modified versions of the software inside them, although the manufacturer +can do so. This is fundamentally incompatible with the aim of +protecting users' freedom to change the software. The systematic +pattern of such abuse occurs in the area of products for individuals to +use, which is precisely where it is most unacceptable. Therefore, we +have designed this version of the GPL to prohibit the practice for those +products. If such problems arise substantially in other domains, we +stand ready to extend this provision to those domains in future versions +of the GPL, as needed to protect the freedom of users.

+ +

Finally, every program is threatened constantly by software patents. +States should not allow patents to restrict development and use of +software on general-purpose computers, but in those that do, we wish to +avoid the special danger that patents applied to a free program could +make it effectively proprietary. To prevent this, the GPL assures that +patents cannot be used to render the program non-free.

+ +

The precise terms and conditions for copying, distribution and +modification follow.

+ +

TERMS AND CONDITIONS

+ +

0. Definitions.

+ +

“This License” refers to version 3 of the GNU General Public License.

+ +

“Copyright” also means copyright-like laws that apply to other kinds of +works, such as semiconductor masks.

+ +

“The Program” refers to any copyrightable work licensed under this +License. Each licensee is addressed as “you”. “Licensees” and +“recipients” may be individuals or organizations.

+ +

To “modify” a work means to copy from or adapt all or part of the work +in a fashion requiring copyright permission, other than the making of an +exact copy. The resulting work is called a “modified version” of the +earlier work or a work “based on” the earlier work.

+ +

A “covered work” means either the unmodified Program or a work based +on the Program.

+ +

To “propagate” a work means to do anything with it that, without +permission, would make you directly or secondarily liable for +infringement under applicable copyright law, except executing it on a +computer or modifying a private copy. Propagation includes copying, +distribution (with or without modification), making available to the +public, and in some countries other activities as well.

+ +

To “convey” a work means any kind of propagation that enables other +parties to make or receive copies. Mere interaction with a user through +a computer network, with no transfer of a copy, is not conveying.

+ +

An interactive user interface displays “Appropriate Legal Notices” +to the extent that it includes a convenient and prominently visible +feature that (1) displays an appropriate copyright notice, and (2) +tells the user that there is no warranty for the work (except to the +extent that warranties are provided), that licensees may convey the +work under this License, and how to view a copy of this License. If +the interface presents a list of user commands or options, such as a +menu, a prominent item in the list meets this criterion.

+ +

1. Source Code.

+ +

The “source code” for a work means the preferred form of the work +for making modifications to it. “Object code” means any non-source +form of a work.

+ +

A “Standard Interface” means an interface that either is an official +standard defined by a recognized standards body, or, in the case of +interfaces specified for a particular programming language, one that +is widely used among developers working in that language.

+ +

The “System Libraries” of an executable work include anything, other +than the work as a whole, that (a) is included in the normal form of +packaging a Major Component, but which is not part of that Major +Component, and (b) serves only to enable use of the work with that +Major Component, or to implement a Standard Interface for which an +implementation is available to the public in source code form. A +“Major Component”, in this context, means a major essential component +(kernel, window system, and so on) of the specific operating system +(if any) on which the executable work runs, or a compiler used to +produce the work, or an object code interpreter used to run it.

+ +

The “Corresponding Source” for a work in object code form means all +the source code needed to generate, install, and (for an executable +work) run the object code and to modify the work, including scripts to +control those activities. However, it does not include the work's +System Libraries, or general-purpose tools or generally available free +programs which are used unmodified in performing those activities but +which are not part of the work. For example, Corresponding Source +includes interface definition files associated with source files for +the work, and the source code for shared libraries and dynamically +linked subprograms that the work is specifically designed to require, +such as by intimate data communication or control flow between those +subprograms and other parts of the work.

+ +

The Corresponding Source need not include anything that users +can regenerate automatically from other parts of the Corresponding +Source.

+ +

The Corresponding Source for a work in source code form is that +same work.

+ +

2. Basic Permissions.

+ +

All rights granted under this License are granted for the term of +copyright on the Program, and are irrevocable provided the stated +conditions are met. This License explicitly affirms your unlimited +permission to run the unmodified Program. The output from running a +covered work is covered by this License only if the output, given its +content, constitutes a covered work. This License acknowledges your +rights of fair use or other equivalent, as provided by copyright law.

+ +

You may make, run and propagate covered works that you do not +convey, without conditions so long as your license otherwise remains +in force. You may convey covered works to others for the sole purpose +of having them make modifications exclusively for you, or provide you +with facilities for running those works, provided that you comply with +the terms of this License in conveying all material for which you do +not control copyright. Those thus making or running the covered works +for you must do so exclusively on your behalf, under your direction +and control, on terms that prohibit them from making any copies of +your copyrighted material outside their relationship with you.

+ +

Conveying under any other circumstances is permitted solely under +the conditions stated below. Sublicensing is not allowed; section 10 +makes it unnecessary.

+ +

3. Protecting Users' Legal Rights From Anti-Circumvention Law.

+ +

No covered work shall be deemed part of an effective technological +measure under any applicable law fulfilling obligations under article +11 of the WIPO copyright treaty adopted on 20 December 1996, or +similar laws prohibiting or restricting circumvention of such +measures.

+ +

When you convey a covered work, you waive any legal power to forbid +circumvention of technological measures to the extent such circumvention +is effected by exercising rights under this License with respect to +the covered work, and you disclaim any intention to limit operation or +modification of the work as a means of enforcing, against the work's +users, your or third parties' legal rights to forbid circumvention of +technological measures.

+ +

4. Conveying Verbatim Copies.

+ +

You may convey verbatim copies of the Program's source code as you +receive it, in any medium, provided that you conspicuously and +appropriately publish on each copy an appropriate copyright notice; +keep intact all notices stating that this License and any +non-permissive terms added in accord with section 7 apply to the code; +keep intact all notices of the absence of any warranty; and give all +recipients a copy of this License along with the Program.

+ +

You may charge any price or no price for each copy that you convey, +and you may offer support or warranty protection for a fee.

+ +

5. Conveying Modified Source Versions.

+ +

You may convey a work based on the Program, or the modifications to +produce it from the Program, in the form of source code under the +terms of section 4, provided that you also meet all of these conditions:

+ +
    +
  • a) The work must carry prominent notices stating that you modified + it, and giving a relevant date.
  • + +
  • b) The work must carry prominent notices stating that it is + released under this License and any conditions added under section + 7. This requirement modifies the requirement in section 4 to + “keep intact all notices”.
  • + +
  • c) You must license the entire work, as a whole, under this + License to anyone who comes into possession of a copy. This + License will therefore apply, along with any applicable section 7 + additional terms, to the whole of the work, and all its parts, + regardless of how they are packaged. This License gives no + permission to license the work in any other way, but it does not + invalidate such permission if you have separately received it.
  • + +
  • d) If the work has interactive user interfaces, each must display + Appropriate Legal Notices; however, if the Program has interactive + interfaces that do not display Appropriate Legal Notices, your + work need not make them do so.
  • +
+ +

A compilation of a covered work with other separate and independent +works, which are not by their nature extensions of the covered work, +and which are not combined with it such as to form a larger program, +in or on a volume of a storage or distribution medium, is called an +“aggregate” if the compilation and its resulting copyright are not +used to limit the access or legal rights of the compilation's users +beyond what the individual works permit. Inclusion of a covered work +in an aggregate does not cause this License to apply to the other +parts of the aggregate.

+ +

6. Conveying Non-Source Forms.

+ +

You may convey a covered work in object code form under the terms +of sections 4 and 5, provided that you also convey the +machine-readable Corresponding Source under the terms of this License, +in one of these ways:

+ +
    +
  • a) Convey the object code in, or embodied in, a physical product + (including a physical distribution medium), accompanied by the + Corresponding Source fixed on a durable physical medium + customarily used for software interchange.
  • + +
  • b) Convey the object code in, or embodied in, a physical product + (including a physical distribution medium), accompanied by a + written offer, valid for at least three years and valid for as + long as you offer spare parts or customer support for that product + model, to give anyone who possesses the object code either (1) a + copy of the Corresponding Source for all the software in the + product that is covered by this License, on a durable physical + medium customarily used for software interchange, for a price no + more than your reasonable cost of physically performing this + conveying of source, or (2) access to copy the + Corresponding Source from a network server at no charge.
  • + +
  • c) Convey individual copies of the object code with a copy of the + written offer to provide the Corresponding Source. This + alternative is allowed only occasionally and noncommercially, and + only if you received the object code with such an offer, in accord + with subsection 6b.
  • + +
  • d) Convey the object code by offering access from a designated + place (gratis or for a charge), and offer equivalent access to the + Corresponding Source in the same way through the same place at no + further charge. You need not require recipients to copy the + Corresponding Source along with the object code. If the place to + copy the object code is a network server, the Corresponding Source + may be on a different server (operated by you or a third party) + that supports equivalent copying facilities, provided you maintain + clear directions next to the object code saying where to find the + Corresponding Source. Regardless of what server hosts the + Corresponding Source, you remain obligated to ensure that it is + available for as long as needed to satisfy these requirements.
  • + +
  • e) Convey the object code using peer-to-peer transmission, provided + you inform other peers where the object code and Corresponding + Source of the work are being offered to the general public at no + charge under subsection 6d.
  • +
+ +

A separable portion of the object code, whose source code is excluded +from the Corresponding Source as a System Library, need not be +included in conveying the object code work.

+ +

A “User Product” is either (1) a “consumer product”, which means any +tangible personal property which is normally used for personal, family, +or household purposes, or (2) anything designed or sold for incorporation +into a dwelling. In determining whether a product is a consumer product, +doubtful cases shall be resolved in favor of coverage. For a particular +product received by a particular user, “normally used” refers to a +typical or common use of that class of product, regardless of the status +of the particular user or of the way in which the particular user +actually uses, or expects or is expected to use, the product. A product +is a consumer product regardless of whether the product has substantial +commercial, industrial or non-consumer uses, unless such uses represent +the only significant mode of use of the product.

+ +

“Installation Information” for a User Product means any methods, +procedures, authorization keys, or other information required to install +and execute modified versions of a covered work in that User Product from +a modified version of its Corresponding Source. The information must +suffice to ensure that the continued functioning of the modified object +code is in no case prevented or interfered with solely because +modification has been made.

+ +

If you convey an object code work under this section in, or with, or +specifically for use in, a User Product, and the conveying occurs as +part of a transaction in which the right of possession and use of the +User Product is transferred to the recipient in perpetuity or for a +fixed term (regardless of how the transaction is characterized), the +Corresponding Source conveyed under this section must be accompanied +by the Installation Information. But this requirement does not apply +if neither you nor any third party retains the ability to install +modified object code on the User Product (for example, the work has +been installed in ROM).

+ +

The requirement to provide Installation Information does not include a +requirement to continue to provide support service, warranty, or updates +for a work that has been modified or installed by the recipient, or for +the User Product in which it has been modified or installed. Access to a +network may be denied when the modification itself materially and +adversely affects the operation of the network or violates the rules and +protocols for communication across the network.

+ +

Corresponding Source conveyed, and Installation Information provided, +in accord with this section must be in a format that is publicly +documented (and with an implementation available to the public in +source code form), and must require no special password or key for +unpacking, reading or copying.

+ +

7. Additional Terms.

+ +

“Additional permissions” are terms that supplement the terms of this +License by making exceptions from one or more of its conditions. +Additional permissions that are applicable to the entire Program shall +be treated as though they were included in this License, to the extent +that they are valid under applicable law. If additional permissions +apply only to part of the Program, that part may be used separately +under those permissions, but the entire Program remains governed by +this License without regard to the additional permissions.

+ +

When you convey a copy of a covered work, you may at your option +remove any additional permissions from that copy, or from any part of +it. (Additional permissions may be written to require their own +removal in certain cases when you modify the work.) You may place +additional permissions on material, added by you to a covered work, +for which you have or can give appropriate copyright permission.

+ +

Notwithstanding any other provision of this License, for material you +add to a covered work, you may (if authorized by the copyright holders of +that material) supplement the terms of this License with terms:

+ +
    +
  • a) Disclaiming warranty or limiting liability differently from the + terms of sections 15 and 16 of this License; or
  • + +
  • b) Requiring preservation of specified reasonable legal notices or + author attributions in that material or in the Appropriate Legal + Notices displayed by works containing it; or
  • + +
  • c) Prohibiting misrepresentation of the origin of that material, or + requiring that modified versions of such material be marked in + reasonable ways as different from the original version; or
  • + +
  • d) Limiting the use for publicity purposes of names of licensors or + authors of the material; or
  • + +
  • e) Declining to grant rights under trademark law for use of some + trade names, trademarks, or service marks; or
  • + +
  • f) Requiring indemnification of licensors and authors of that + material by anyone who conveys the material (or modified versions of + it) with contractual assumptions of liability to the recipient, for + any liability that these contractual assumptions directly impose on + those licensors and authors.
  • +
+ +

All other non-permissive additional terms are considered “further +restrictions” within the meaning of section 10. If the Program as you +received it, or any part of it, contains a notice stating that it is +governed by this License along with a term that is a further +restriction, you may remove that term. If a license document contains +a further restriction but permits relicensing or conveying under this +License, you may add to a covered work material governed by the terms +of that license document, provided that the further restriction does +not survive such relicensing or conveying.

+ +

If you add terms to a covered work in accord with this section, you +must place, in the relevant source files, a statement of the +additional terms that apply to those files, or a notice indicating +where to find the applicable terms.

+ +

Additional terms, permissive or non-permissive, may be stated in the +form of a separately written license, or stated as exceptions; +the above requirements apply either way.

+ +

8. Termination.

+ +

You may not propagate or modify a covered work except as expressly +provided under this License. Any attempt otherwise to propagate or +modify it is void, and will automatically terminate your rights under +this License (including any patent licenses granted under the third +paragraph of section 11).

+ +

However, if you cease all violation of this License, then your +license from a particular copyright holder is reinstated (a) +provisionally, unless and until the copyright holder explicitly and +finally terminates your license, and (b) permanently, if the copyright +holder fails to notify you of the violation by some reasonable means +prior to 60 days after the cessation.

+ +

Moreover, your license from a particular copyright holder is +reinstated permanently if the copyright holder notifies you of the +violation by some reasonable means, this is the first time you have +received notice of violation of this License (for any work) from that +copyright holder, and you cure the violation prior to 30 days after +your receipt of the notice.

+ +

Termination of your rights under this section does not terminate the +licenses of parties who have received copies or rights from you under +this License. If your rights have been terminated and not permanently +reinstated, you do not qualify to receive new licenses for the same +material under section 10.

+ +

9. Acceptance Not Required for Having Copies.

+ +

You are not required to accept this License in order to receive or +run a copy of the Program. Ancillary propagation of a covered work +occurring solely as a consequence of using peer-to-peer transmission +to receive a copy likewise does not require acceptance. However, +nothing other than this License grants you permission to propagate or +modify any covered work. These actions infringe copyright if you do +not accept this License. Therefore, by modifying or propagating a +covered work, you indicate your acceptance of this License to do so.

+ +

10. Automatic Licensing of Downstream Recipients.

+ +

Each time you convey a covered work, the recipient automatically +receives a license from the original licensors, to run, modify and +propagate that work, subject to this License. You are not responsible +for enforcing compliance by third parties with this License.

+ +

An “entity transaction” is a transaction transferring control of an +organization, or substantially all assets of one, or subdividing an +organization, or merging organizations. If propagation of a covered +work results from an entity transaction, each party to that +transaction who receives a copy of the work also receives whatever +licenses to the work the party's predecessor in interest had or could +give under the previous paragraph, plus a right to possession of the +Corresponding Source of the work from the predecessor in interest, if +the predecessor has it or can get it with reasonable efforts.

+ +

You may not impose any further restrictions on the exercise of the +rights granted or affirmed under this License. For example, you may +not impose a license fee, royalty, or other charge for exercise of +rights granted under this License, and you may not initiate litigation +(including a cross-claim or counterclaim in a lawsuit) alleging that +any patent claim is infringed by making, using, selling, offering for +sale, or importing the Program or any portion of it.

+ +

11. Patents.

+ +

A “contributor” is a copyright holder who authorizes use under this +License of the Program or a work on which the Program is based. The +work thus licensed is called the contributor's “contributor version”.

+ +

A contributor's “essential patent claims” are all patent claims +owned or controlled by the contributor, whether already acquired or +hereafter acquired, that would be infringed by some manner, permitted +by this License, of making, using, or selling its contributor version, +but do not include claims that would be infringed only as a +consequence of further modification of the contributor version. For +purposes of this definition, “control” includes the right to grant +patent sublicenses in a manner consistent with the requirements of +this License.

+ +

Each contributor grants you a non-exclusive, worldwide, royalty-free +patent license under the contributor's essential patent claims, to +make, use, sell, offer for sale, import and otherwise run, modify and +propagate the contents of its contributor version.

+ +

In the following three paragraphs, a “patent license” is any express +agreement or commitment, however denominated, not to enforce a patent +(such as an express permission to practice a patent or covenant not to +sue for patent infringement). To “grant” such a patent license to a +party means to make such an agreement or commitment not to enforce a +patent against the party.

+ +

If you convey a covered work, knowingly relying on a patent license, +and the Corresponding Source of the work is not available for anyone +to copy, free of charge and under the terms of this License, through a +publicly available network server or other readily accessible means, +then you must either (1) cause the Corresponding Source to be so +available, or (2) arrange to deprive yourself of the benefit of the +patent license for this particular work, or (3) arrange, in a manner +consistent with the requirements of this License, to extend the patent +license to downstream recipients. “Knowingly relying” means you have +actual knowledge that, but for the patent license, your conveying the +covered work in a country, or your recipient's use of the covered work +in a country, would infringe one or more identifiable patents in that +country that you have reason to believe are valid.

+ +

If, pursuant to or in connection with a single transaction or +arrangement, you convey, or propagate by procuring conveyance of, a +covered work, and grant a patent license to some of the parties +receiving the covered work authorizing them to use, propagate, modify +or convey a specific copy of the covered work, then the patent license +you grant is automatically extended to all recipients of the covered +work and works based on it.

+ +

A patent license is “discriminatory” if it does not include within +the scope of its coverage, prohibits the exercise of, or is +conditioned on the non-exercise of one or more of the rights that are +specifically granted under this License. You may not convey a covered +work if you are a party to an arrangement with a third party that is +in the business of distributing software, under which you make payment +to the third party based on the extent of your activity of conveying +the work, and under which the third party grants, to any of the +parties who would receive the covered work from you, a discriminatory +patent license (a) in connection with copies of the covered work +conveyed by you (or copies made from those copies), or (b) primarily +for and in connection with specific products or compilations that +contain the covered work, unless you entered into that arrangement, +or that patent license was granted, prior to 28 March 2007.

+ +

Nothing in this License shall be construed as excluding or limiting +any implied license or other defenses to infringement that may +otherwise be available to you under applicable patent law.

+ +

12. No Surrender of Others' Freedom.

+ +

If conditions are imposed on you (whether by court order, agreement or +otherwise) that contradict the conditions of this License, they do not +excuse you from the conditions of this License. If you cannot convey a +covered work so as to satisfy simultaneously your obligations under this +License and any other pertinent obligations, then as a consequence you may +not convey it at all. For example, if you agree to terms that obligate you +to collect a royalty for further conveying from those to whom you convey +the Program, the only way you could satisfy both those terms and this +License would be to refrain entirely from conveying the Program.

+ +

13. Use with the GNU Affero General Public License.

+ +

Notwithstanding any other provision of this License, you have +permission to link or combine any covered work with a work licensed +under version 3 of the GNU Affero General Public License into a single +combined work, and to convey the resulting work. The terms of this +License will continue to apply to the part which is the covered work, +but the special requirements of the GNU Affero General Public License, +section 13, concerning interaction through a network will apply to the +combination as such.

+ +

14. Revised Versions of this License.

+ +

The Free Software Foundation may publish revised and/or new versions of +the GNU General Public License from time to time. Such new versions will +be similar in spirit to the present version, but may differ in detail to +address new problems or concerns.

+ +

Each version is given a distinguishing version number. If the +Program specifies that a certain numbered version of the GNU General +Public License “or any later version” applies to it, you have the +option of following the terms and conditions either of that numbered +version or of any later version published by the Free Software +Foundation. If the Program does not specify a version number of the +GNU General Public License, you may choose any version ever published +by the Free Software Foundation.

+ +

If the Program specifies that a proxy can decide which future +versions of the GNU General Public License can be used, that proxy's +public statement of acceptance of a version permanently authorizes you +to choose that version for the Program.

+ +

Later license versions may give you additional or different +permissions. However, no additional obligations are imposed on any +author or copyright holder as a result of your choosing to follow a +later version.

+ +

15. Disclaimer of Warranty.

+ +

THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY +APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT +HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM “AS IS” WITHOUT WARRANTY +OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, +THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR +PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM +IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF +ALL NECESSARY SERVICING, REPAIR OR CORRECTION.

+ +

16. Limitation of Liability.

+ +

IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING +WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS +THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY +GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE +USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF +DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD +PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), +EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF +SUCH DAMAGES.

+ +

17. Interpretation of Sections 15 and 16.

+ +

If the disclaimer of warranty and limitation of liability provided +above cannot be given local legal effect according to their terms, +reviewing courts shall apply local law that most closely approximates +an absolute waiver of all civil liability in connection with the +Program, unless a warranty or assumption of liability accompanies a +copy of the Program in return for a fee.

+ +

END OF TERMS AND CONDITIONS

+ +

How to Apply These Terms to Your New Programs

+ +

If you develop a new program, and you want it to be of the greatest +possible use to the public, the best way to achieve this is to make it +free software which everyone can redistribute and change under these terms.

+ +

To do so, attach the following notices to the program. It is safest +to attach them to the start of each source file to most effectively +state the exclusion of warranty; and each file should have at least +the “copyright” line and a pointer to where the full notice is found.

+ +
    <one line to give the program's name and a brief idea of what it does.>
+    Copyright (C) <year>  <name of author>
+
+    This program is free software: you can redistribute it and/or modify
+    it under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    This program is distributed in the hope that it will be useful,
+    but WITHOUT ANY WARRANTY; without even the implied warranty of
+    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+    GNU General Public License for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with this program.  If not, see <http://www.gnu.org/licenses/>.
+
+ +

Also add information on how to contact you by electronic and paper mail.

+ +

If the program does terminal interaction, make it output a short +notice like this when it starts in an interactive mode:

+ +
    <program>  Copyright (C) <year>  <name of author>
+    This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
+    This is free software, and you are welcome to redistribute it
+    under certain conditions; type `show c' for details.
+
+ +

The hypothetical commands `show w' and `show c' should show the appropriate +parts of the General Public License. Of course, your program's commands +might be different; for a GUI interface, you would use an “about box”.

+ +

You should also get your employer (if you work as a programmer) or school, +if any, to sign a “copyright disclaimer” for the program, if necessary. +For more information on this, and how to apply and follow the GNU GPL, see +<http://www.gnu.org/licenses/>.

+ +

The GNU General Public License does not permit incorporating your program +into proprietary programs. If your program is a subroutine library, you +may consider it more useful to permit linking proprietary applications with +the library. If this is what you want to do, use the GNU Lesser General +Public License instead of this License. But first, please read +<http://www.gnu.org/philosophy/why-not-lgpl.html>.

+ + + \ No newline at end of file diff --git a/plugins/qsolocards_plugin/images/anglo_bitmap.svg b/plugins/qsolocards_plugin/images/anglo_bitmap.svg new file mode 100644 index 000000000..e5cdb7fd5 --- /dev/null +++ b/plugins/qsolocards_plugin/images/anglo_bitmap.svg @@ -0,0 +1,10159 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/plugins/qsolocards_plugin/images/greenfelt.png b/plugins/qsolocards_plugin/images/greenfelt.png new file mode 100644 index 000000000..9bed0cb77 Binary files /dev/null and b/plugins/qsolocards_plugin/images/greenfelt.png differ diff --git a/plugins/qsolocards_plugin/images/sol128x128.png b/plugins/qsolocards_plugin/images/sol128x128.png new file mode 100644 index 000000000..6a759d693 Binary files /dev/null and b/plugins/qsolocards_plugin/images/sol128x128.png differ diff --git a/plugins/qsolocards_plugin/images/sol16x16.png b/plugins/qsolocards_plugin/images/sol16x16.png new file mode 100644 index 000000000..42bf709e0 Binary files /dev/null and b/plugins/qsolocards_plugin/images/sol16x16.png differ diff --git a/plugins/qsolocards_plugin/images/sol256x256.png b/plugins/qsolocards_plugin/images/sol256x256.png new file mode 100644 index 000000000..9125e38c6 Binary files /dev/null and b/plugins/qsolocards_plugin/images/sol256x256.png differ diff --git a/plugins/qsolocards_plugin/images/sol32x32.png b/plugins/qsolocards_plugin/images/sol32x32.png new file mode 100644 index 000000000..a145497dc Binary files /dev/null and b/plugins/qsolocards_plugin/images/sol32x32.png differ diff --git a/plugins/qsolocards_plugin/images/sol512x512.png b/plugins/qsolocards_plugin/images/sol512x512.png new file mode 100644 index 000000000..438fa5e0a Binary files /dev/null and b/plugins/qsolocards_plugin/images/sol512x512.png differ diff --git a/plugins/qsolocards_plugin/main.cpp b/plugins/qsolocards_plugin/main.cpp new file mode 100644 index 000000000..7746402b0 --- /dev/null +++ b/plugins/qsolocards_plugin/main.cpp @@ -0,0 +1,28 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include +#include "mainwindow.h" + +int main(int argc, char *argv[]) +{ + QApplication a(argc, argv); + MainWindow w; + w.show(); + return a.exec(); +} diff --git a/plugins/qsolocards_plugin/mainwindow.cpp b/plugins/qsolocards_plugin/mainwindow.cpp new file mode 100644 index 000000000..9456b26f4 --- /dev/null +++ b/plugins/qsolocards_plugin/mainwindow.cpp @@ -0,0 +1,653 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#include "mainwindow.h" + +#include +#include +#include +#include +#include +#include + +#include "CardAnimationLock.h" + +const unsigned int MainWindow::MaxWidth=780; +const unsigned int MainWindow::MaxHeight=900; +const QString MainWindow::SizeStr("size"); +const QString MainWindow::PtStr("point"); +const QString MainWindow::HelpStr("help"); +const QString MainWindow::GameIdStr("LastGame"); +const QString MainWindow::AnimationStr("EnableAnimations"); + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +MainWindow::MainWindow(QWidget *parent) + : QMainWindow(parent), + m_pGameBoard(NULL), + m_pMenuBar(NULL), + m_pGameOptionsMenu(NULL), + m_pHelpMenu(NULL), + m_settings("QSoloCards","QSoloCards"), + m_pNewGameAction(NULL), + m_pRestartAction(NULL), + m_pUndoAction(NULL), + m_pRedoAction(NULL), + m_pHintAction(NULL), + m_pAnimationAction(NULL), + m_pDemoAction(NULL), + m_pCheatAction(NULL), + m_pStatusBar(NULL), + m_pStatusBarLabel(NULL), + m_helpWindow(NULL), + m_aboutWindow(NULL), + m_gameMgr(), + m_firstShow(false) +{ + // make the window a nice size and make sure it is on the screen + QSize deskSize(QApplication::desktop()->size()); + + unsigned int width=MaxWidth<(unsigned int)deskSize.width()?MaxWidth:deskSize.width()-100; + unsigned int height=MaxHeight<(unsigned int)deskSize.height()?MaxHeight:deskSize.height()-100; + + int locX=(deskSize.width()-width)/2; + int locY=(deskSize.height()-height)/2; + + this->resize(m_settings.value(SizeStr, QSize(width, height)).toSize()); + this->move(m_settings.value(PtStr, QPoint(locX, locY)).toPoint()); + + // create the status bar we will use to show the score and game info. + this->m_pStatusBar=new QStatusBar; + this->m_pStatusBarLabel=new QLabel; + this->m_pStatusBar->addPermanentWidget(m_pStatusBarLabel); + this->setStatusBar(this->m_pStatusBar); + + // show the last game played or the default game if we don't have a last played. + // we need to create the board before adding the menus. This is done. So, the + // initial check state of the game selected will reflect the initial game. + int gameId=m_settings.value(GameIdStr, GameMgr::DefaultGame).toInt(); + GameBoard * pGameBoard=m_gameMgr.getGame((GameMgr::GameId)gameId); + + // add the menus for the window + this->addMenuItems(); + + // finally setup the board. + this->setupGameBoard(pGameBoard); +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +MainWindow::~MainWindow() +{ + // save the current settings for the game + this->m_settings.beginGroup(this->m_pGameBoard->gameSettingsId()); + this->m_pGameBoard->saveSettings(this->m_settings); + this->m_settings.endGroup(); + + // save the position of the game window + this->m_settings.setValue(SizeStr,this->size()); + this->m_settings.setValue(PtStr,this->pos()); + + // save the current game being played + this->m_settings.setValue(GameIdStr,this->m_gameMgr.getGameId()); + + // save if animation is enabled or not + this->m_settings.setValue(AnimationStr,this->m_pAnimationAction->isChecked()); +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotNewGame() +{ + if (NULL!=this->m_pGameBoard) + { + this->m_pGameBoard->newGame(); + } +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotRestartGame() +{ + if (NULL!=this->m_pGameBoard) + { + this->m_pGameBoard->restartGame(); + } +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotSelectGame(QAction * pAction) +{ + if (NULL!=pAction) + { + bool ok=false; + int gameId=pAction->data().toInt(&ok); + + // if we got the gameid and it is not the same as the current game + // set the game as the current. + if (ok && gameId!=this->m_gameMgr.getGameId()) + { + this->setupGameBoard(this->m_gameMgr.getGame((GameMgr::GameId)gameId)); + } + } +} + +void MainWindow::slotAnimation(bool checked) +{ + CardAnimationLock::getInst().enableAnimations(checked); + + if (this->m_pGameBoard->hasDemo() && checked) + { + this->m_pDemoAction->setEnabled(true); + } + else + { + this->m_pDemoAction->setEnabled(false); + } +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotCheat(bool checked) +{ + if (NULL!=this->m_pGameBoard) + { + this->m_pGameBoard->setCheat(checked); + } +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotUndo() +{ + if (NULL!=this->m_pGameBoard) + { + if (this->m_pGameBoard->canUndoMove()) + { + this->m_pGameBoard->undoMove(); + } + } +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotRedo() +{ + if (NULL!=this->m_pGameBoard) + { + if (this->m_pGameBoard->canRedoMove()) + { + this->m_pGameBoard->redoMove(); + } + } +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotHint() +{ + if (NULL!=this->m_pGameBoard) + { + this->m_pGameBoard->showHint(); + } +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotUndoAvail(bool avail) +{ + if (this->m_pUndoAction && !m_pDemoAction->isChecked()) + { + this->m_pRestartAction->setEnabled(avail); + + this->m_pUndoAction->setEnabled(avail); + } +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotRedoAvail(bool avail) +{ + if (this->m_pRedoAction) + { + this->m_pRedoAction->setEnabled(avail); + } +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotScoreChanged(int score,const QString & info) +{ + if (this->m_pStatusBar && !m_pDemoAction->isChecked()) + { + QString statusMsg(tr("%1 Score: %2").arg(info).arg(QString::number(score)).trimmed()); + + this->m_pStatusBarLabel->setText(statusMsg); + } +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotAbout() +{ + if (NULL==this->m_aboutWindow) + { + this->m_aboutWindow=new About(this); + connect(this->m_aboutWindow.data(),SIGNAL(showLink(QString)), + this,SLOT(slotShowHelp(QString))); + } + this->m_aboutWindow->show(); + this->m_aboutWindow->activateWindow(); +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotHelp() +{ + if (this->m_pGameBoard) + { + this->slotShowHelp(this->m_pGameBoard->helpFile()); + } +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotHelpClosed(int finishCode) +{ + Q_UNUSED(finishCode); + + this->m_settings.beginGroup(HelpStr); + this->m_settings.setValue(SizeStr,this->m_helpWindow->size()); + this->m_settings.setValue(PtStr,this->m_helpWindow->pos()); + this->m_settings.endGroup(); +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotShowHelp(const QString & helpFile) +{ + if (NULL==this->m_helpWindow) + { + this->m_helpWindow=new Help(this,helpFile); + this->m_settings.beginGroup(HelpStr); + this->m_helpWindow->resize(this->m_settings.value(SizeStr,QSize(640,480)).toSize()); + this->m_helpWindow->move(this->m_settings.value(PtStr,QPoint(200,200)).toPoint()); + this->m_settings.endGroup(); + this->connect(this->m_helpWindow,SIGNAL(finished(int)),this,SLOT(slotHelpClosed(int))); + this->m_helpWindow->show(); + } + else + { + this->m_helpWindow->setHelpFile(helpFile); + this->m_helpWindow->show(); + this->m_helpWindow->activateWindow(); + } +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotAnimationStarted() +{ + m_pRestartAction->setEnabled(false); + m_pDemoAction->setEnabled(false); +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotAnimationComplete() +{ + m_pRestartAction->setEnabled(true); + m_pDemoAction->setEnabled(true); +} + +///////////////////////////////////////////////////////////////////////////////////////////// +// this timeout is just to delay slightly calling newGame for a board. So, the +// animation will start with the QGraphicsScene visible and the board will already be +// completely drawn. +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotNewGameTimer() +{ + if (this->m_pGameBoard) + { + this->m_pMenuBar->setEnabled(true); + this->m_pGameBoard->newGame(); + } +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotDemoStarted() +{ + m_pNewGameAction->setEnabled(false); + m_pRestartAction->setEnabled(false); + m_pUndoAction->setEnabled(false); + m_pRedoAction->setEnabled(false); + m_pHintAction->setEnabled(false); + m_pAnimationAction->setEnabled(false); + m_pGameSelectMenu->setEnabled(false); + m_pGameOptionsMenu->setEnabled(false); + m_pCheatAction->setEnabled(false); + + m_pDemoAction->setChecked(true); +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotDemoStopped() +{ + m_pNewGameAction->setEnabled(true); + m_pRestartAction->setEnabled(true); + m_pHintAction->setEnabled(true); + m_pAnimationAction->setEnabled(true); + m_pGameSelectMenu->setEnabled(true); + m_pGameOptionsMenu->setEnabled(true); + m_pCheatAction->setEnabled(true); + + + if (this->m_pGameBoard->canUndoMove()) + { + m_pUndoAction->setEnabled(true); + } + + if (this->m_pGameBoard->canRedoMove()) + { + m_pRedoAction->setEnabled(true); + } + + m_pDemoAction->setChecked(false); + +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::slotDemoActionItem(bool checked) +{ + if (this->m_pGameBoard) + { + if (checked) + { + this->m_pGameBoard->startDemo(); + } + else + { + this->m_pGameBoard->stopDemo(); + } + } +} + +///////////////////////////////////////////////////////////////////////////////////////////// +// we are just using the showEvent to make sure that we don't start the animation of the dealing +// of cards for the game until the window has been shown. +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::showEvent(QShowEvent * pShowEvent) +{ + Q_UNUSED(pShowEvent); + if (!m_firstShow && NULL!=this->m_pGameBoard) + { + this->m_pGameBoard->newGame(); + + m_firstShow=true; + } +} + +///////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::addMenuItems() +{ + // create the menu for the app. + this->m_pMenuBar=new QMenuBar(this); + + // create a game menu + QMenu * pGameMenu=new QMenu(tr("Game").trimmed(),this->m_pMenuBar); + + m_pNewGameAction=new QAction(tr("New Game").trimmed(),pGameMenu); + m_pNewGameAction->setShortcuts(QKeySequence::New); + this->connect(m_pNewGameAction,SIGNAL(triggered()), + this,SLOT(slotNewGame())); + pGameMenu->addAction(m_pNewGameAction); + + this->m_pRestartAction=new QAction(tr("Restart Game").trimmed(),pGameMenu); + this->m_pRestartAction->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_R)); + this->connect(this->m_pRestartAction,SIGNAL(triggered()), + this,SLOT(slotRestartGame())); + + pGameMenu->addAction(this->m_pRestartAction); + + pGameMenu->addSeparator(); + + this->m_pGameSelectMenu=new QMenu(tr("Select Game").trimmed(),pGameMenu); + // add the available games to the menu. + this->m_gameMgr.buildGameListMenu(*this->m_pGameSelectMenu); + // connecting this one up a little different. Since, we are building + // a generic menu where we don't know what the contents are connect up + // to the menus triggered event. We can then get the action and from it's + // user data the id of the game selected. + this->connect(this->m_pGameSelectMenu,SIGNAL(triggered(QAction*)), + this,SLOT(slotSelectGame(QAction*))); + + pGameMenu->addMenu(this->m_pGameSelectMenu); + +#if !(defined Q_WS_MAC) + pGameMenu->addSeparator(); +#endif + + + QAction * pQuit=new QAction(tr("Quit").trimmed(),pGameMenu); + pQuit->setMenuRole(QAction::QuitRole); + pQuit->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_Q)); + this->connect(pQuit,SIGNAL(triggered()), + this,SLOT(close())); + pGameMenu->addAction(pQuit); + + this->m_pMenuBar->addMenu(pGameMenu); + + /////////////////////////////////////////////////////////////////////////// + // create a control menu + // for the cheat and undo menu items + /////////////////////////////////////////////////////////////////////////// + QMenu * pCtrlMenu=new QMenu(tr("Control").trimmed(),this->m_pMenuBar); + + m_pUndoAction=new QAction(tr("Undo").trimmed(),pCtrlMenu); + m_pUndoAction->setShortcuts(QKeySequence::Undo); + this->connect(m_pUndoAction,SIGNAL(triggered()), + this,SLOT(slotUndo())); + pCtrlMenu->addAction(m_pUndoAction); + + m_pRedoAction=new QAction(tr("Redo").trimmed(),pCtrlMenu); + m_pRedoAction->setShortcuts(QKeySequence::Redo); + this->connect(m_pRedoAction,SIGNAL(triggered()), + this,SLOT(slotRedo())); + pCtrlMenu->addAction(m_pRedoAction); + + m_pHintAction=new QAction(tr("Hint").trimmed(),pCtrlMenu); + m_pHintAction->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_H)); + this->connect(m_pHintAction,SIGNAL(triggered()), + this,SLOT(slotHint())); + pCtrlMenu->addAction(m_pHintAction); + + pCtrlMenu->addSeparator(); + + m_pAnimationAction=new QAction(tr("Animation").trimmed(),pCtrlMenu); + m_pAnimationAction->setCheckable(true); + this->connect(m_pAnimationAction,SIGNAL(triggered(bool)), + this,SLOT(slotAnimation(bool))); + pCtrlMenu->addAction(m_pAnimationAction); + + m_pAnimationAction->setChecked(m_settings.value(AnimationStr, true).toBool()); + + CardAnimationLock::getInst().enableAnimations(m_pAnimationAction->isChecked()); + + + m_pDemoAction=new QAction(tr("Demo").trimmed(),pCtrlMenu); + m_pDemoAction->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_D)); + m_pDemoAction->setCheckable(true); + this->connect(m_pDemoAction,SIGNAL(triggered(bool)), + this,SLOT(slotDemoActionItem(bool))); + pCtrlMenu->addAction(m_pDemoAction); + + + pCtrlMenu->addSeparator(); + + m_pCheatAction=new QAction(tr("Cheat").trimmed(),pCtrlMenu); + m_pCheatAction->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_C)); + m_pCheatAction->setCheckable(true); + this->connect(m_pCheatAction,SIGNAL(triggered(bool)), + this,SLOT(slotCheat(bool))); + pCtrlMenu->addAction(m_pCheatAction); + + + this->m_pMenuBar->addMenu(pCtrlMenu); + + + /////////////////////////////////////////////////////////////////////////// + // create a game options menu + // this menu will get the specific game option settings to add to the menu + // from the GameBoard class. We will not add it to the menu at this time. + // It will be added and/or removed when the game board is setup. It will + // only be added if it is needed. + /////////////////////////////////////////////////////////////////////////// + m_pGameOptionsMenu=new QMenu(tr("&Options").trimmed(),this->m_pMenuBar); + + //////////////////////////////////////////////////////////////////////////// + // add the help menu + //////////////////////////////////////////////////////////////////////////// + this->m_pHelpMenu=new QMenu(tr("&Help").trimmed(),this->m_pMenuBar); + + QAction * pHelp=new QAction(tr("Game Help").trimmed(),this->m_pHelpMenu); + pHelp->setShortcut(QKeySequence(Qt::Key_F1)); + this->connect(pHelp,SIGNAL(triggered()), + this,SLOT(slotHelp())); + this->m_pHelpMenu->addAction(pHelp); + +#if !(defined Q_WS_MAC) + this->m_pHelpMenu->addSeparator(); +#endif + + QAction * pAbout=new QAction(tr("&About").trimmed(),this->m_pHelpMenu); + pAbout->setMenuRole(QAction::AboutRole); + this->connect(pAbout,SIGNAL(triggered()), + this,SLOT(slotAbout())); + this->m_pHelpMenu->addAction(pAbout); + + this->m_pMenuBar->addMenu(this->m_pHelpMenu); + + + + this->setMenuBar(this->m_pMenuBar); + + // also go ahead and hook up the slots for the signals that animation is in progress + // now only used by the restart game menu item. Need the undo stack to be updated before + // we can restart a game. + connect(&CardAnimationLock::getInst(),SIGNAL(animationStarted()), + this,SLOT(slotAnimationStarted())); + + connect(&CardAnimationLock::getInst(),SIGNAL(animationComplete()), + this,SLOT(slotAnimationComplete())); +} + +///////////////////////////////////////////////////////////////////////////////////////////// +// Set a gameboard and hook up the menus, set the icon, etc... for the new board +// if there was a previous gameboard. When the QMainWindow::setCentralWidget function is called +// the old game board will be deleted by Qt. +///////////////////////////////////////////////////////////////////////////////////////////// +void MainWindow::setupGameBoard(GameBoard * pGameBoard) +{ + if (pGameBoard) + { + // save settings of the current game if we have one + if (NULL!=this->m_pGameBoard) + { + this->m_settings.beginGroup(this->m_pGameBoard->gameSettingsId()); + this->m_pGameBoard->saveSettings(this->m_settings); + this->m_settings.endGroup(); + } + + this->m_pGameBoard=pGameBoard; + + // connect the gameboards score changed signal to our slot so we + // can get score changes and display them. But first clear the + // current contents of the statusbar to get ride of old info if necessary. + this->m_pStatusBar->showMessage(""); + this->m_pStatusBarLabel->setText(""); + this->connect(this->m_pGameBoard,SIGNAL(scoreChanged(int,QString)), + this,SLOT(slotScoreChanged(int,QString))); + + this->m_settings.beginGroup(this->m_pGameBoard->gameSettingsId()); + this->m_pGameBoard->loadSettings(m_settings); + this->m_settings.endGroup(); + + + this->setCentralWidget(this->m_pGameBoard); + this->setWindowTitle(tr("QSoloCards: %1").arg(this->m_pGameBoard->gameName()).trimmed()); + + // connect up the game board to the menus + m_pUndoAction->setEnabled(this->m_pGameBoard->canUndoMove()); + m_pRedoAction->setEnabled(this->m_pGameBoard->canRedoMove()); + m_pRestartAction->setEnabled(this->m_pGameBoard->canUndoMove()); + + this->m_pMenuBar->removeAction(this->m_pGameOptionsMenu->menuAction()); + + this->m_pGameOptionsMenu->clear(); + this->m_pGameBoard->addGameMenuItems(*this->m_pGameOptionsMenu); + + if (!this->m_pGameOptionsMenu->isEmpty()) + { + this->m_pMenuBar->insertMenu(this->m_pHelpMenu->menuAction(),this->m_pGameOptionsMenu); + } + + // set the window icon for the game. + this->setWindowIcon(this->m_pGameBoard->getGamePixmap()); + + + /////////////////////////////////////////////////////////////////////////// + // connect up the slots so we will know when undo and redo actions are available + /////////////////////////////////////////////////////////////////////////// + this->connect(this->m_pGameBoard,SIGNAL(undoAvail(bool)), + this,SLOT(slotUndoAvail(bool))); + + this->connect(this->m_pGameBoard,SIGNAL(redoAvail(bool)), + this,SLOT(slotRedoAvail(bool))); + + if (this->isVisible()) + { + // disable the menus while we wait for the timer to pop. + this->m_pMenuBar->setEnabled(false); + QTimer::singleShot(100,this,SLOT(slotNewGameTimer())); + } + + this->m_pDemoAction->setChecked(false); + + if (this->m_pGameBoard->hasDemo() && CardAnimationLock::getInst().animationsEnabled()) + { + this->m_pDemoAction->setEnabled(true); + + this->connect(this->m_pGameBoard,SIGNAL(demoStarted()), + this,SLOT(slotDemoStarted())); + + this->connect(this->m_pGameBoard,SIGNAL(demoStopped()), + this,SLOT(slotDemoStopped())); + } + else + { + this->m_pDemoAction->setEnabled(false); + } + + } +} + diff --git a/plugins/qsolocards_plugin/mainwindow.h b/plugins/qsolocards_plugin/mainwindow.h new file mode 100644 index 000000000..9e4d874eb --- /dev/null +++ b/plugins/qsolocards_plugin/mainwindow.h @@ -0,0 +1,117 @@ +/* + QSoloCards is a collection of Solitaire card games written using Qt + Copyright (C) 2009 Steve Moore + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifndef MAINWINDOW_H +#define MAINWINDOW_H + +#include +#include +#include +#include +#include +#include +#include + +#include "GameBoard.h" +#include "Help.h" +#include "About.h" +#include "GameMgr.h" + +class MainWindow : public QMainWindow +{ + Q_OBJECT + +public: + static const unsigned int MaxWidth; + static const unsigned int MaxHeight; + static const QString SizeStr; + static const QString PtStr; + static const QString HelpStr; + static const QString GameIdStr; + static const QString AnimationStr; + + MainWindow(QWidget *parent = 0); + ~MainWindow(); + +public slots: + void slotNewGame(); + void slotRestartGame(); + void slotSelectGame(QAction *); + void slotAnimation(bool); + void slotCheat(bool); + void slotUndo(); + void slotRedo(); + void slotHint(); + + void slotUndoAvail(bool avail); + void slotRedoAvail(bool avail); + + void slotScoreChanged(int score,const QString &); + + void slotHelp(); + void slotAbout(); + + void slotHelpClosed(int); + + void slotShowHelp(const QString & helpFile); + + void slotAnimationStarted(); + void slotAnimationComplete(); + + void slotNewGameTimer(); + + void slotDemoStarted(); + void slotDemoStopped(); + + void slotDemoActionItem(bool); +protected: + void showEvent(QShowEvent * pShowEvent); + +private: + void addMenuItems(); + void setupGameBoard(GameBoard * pGameBoard); + + + + GameBoard * m_pGameBoard; + QMenuBar * m_pMenuBar; + QMenu * m_pGameSelectMenu; + QMenu * m_pGameOptionsMenu; + QMenu * m_pHelpMenu; + QSettings m_settings; + + QAction * m_pNewGameAction; + QAction * m_pRestartAction; + QAction * m_pUndoAction; + QAction * m_pRedoAction; + QAction * m_pHintAction; + QAction * m_pAnimationAction; + QAction * m_pDemoAction; + QAction * m_pCheatAction; + + QStatusBar * m_pStatusBar; + QLabel * m_pStatusBarLabel; + QPointer m_helpWindow; // use a QPointer so we don't have to worry about knowing if + // the help window has been deleted. The Window auto deletes + // when closes. + QPointer m_aboutWindow; + GameMgr m_gameMgr; + bool m_firstShow; +}; + +#endif // MAINWINDOW_H diff --git a/plugins/qsolocards_plugin/object_script.qsolocards_plugin.Debug b/plugins/qsolocards_plugin/object_script.qsolocards_plugin.Debug new file mode 100644 index 000000000..cbdb74bc8 --- /dev/null +++ b/plugins/qsolocards_plugin/object_script.qsolocards_plugin.Debug @@ -0,0 +1,64 @@ +INPUT( +./temp\obj\QSoloCardsPlugin.o +./temp\obj\main.o +./temp\obj\mainwindow.o +./temp\obj\PlayingCard.o +./temp\obj\CardDeck.o +./temp\obj\CardPixmaps.o +./temp\obj\CardStack.o +./temp\obj\DragCardStack.o +./temp\obj\VCardStack.o +./temp\obj\CardAnimationLock.o +./temp\obj\StackToStackAniMove.o +./temp\obj\DealAnimation.o +./temp\obj\FlipAnimation.o +./temp\obj\StackToStackFlipAni.o +./temp\obj\GameBoard.o +./temp\obj\CardMoveRecord.o +./temp\obj\About.o +./temp\obj\Help.o +./temp\obj\GameMgr.o +./temp\obj\SpiderBoard.o +./temp\obj\SpiderHomeStack.o +./temp\obj\SpiderStack.o +./temp\obj\KlondikeStack.o +./temp\obj\KlondikeFlipStack.o +./temp\obj\KlondikeHomeStack.o +./temp\obj\KlondikeBoard.o +./temp\obj\FreeCellBoard.o +./temp\obj\FreeCellDeck.o +./temp\obj\FreeCellStack.o +./temp\obj\FreeCellHome.o +./temp\obj\FreeCellFree.o +./temp\obj\Spider3DeckBoard.o +./temp\obj\SpideretteBoard.o +./temp\obj\YukonBoard.o +./temp\obj\moc_QSoloCardsPlugin.o +./temp\obj\moc_mainwindow.o +./temp\obj\moc_CardStack.o +./temp\obj\moc_DragCardStack.o +./temp\obj\moc_VCardStack.o +./temp\obj\moc_CardAnimationLock.o +./temp\obj\moc_StackToStackAniMove.o +./temp\obj\moc_DealAnimation.o +./temp\obj\moc_FlipAnimation.o +./temp\obj\moc_StackToStackFlipAni.o +./temp\obj\moc_GameBoard.o +./temp\obj\moc_About.o +./temp\obj\moc_Help.o +./temp\obj\moc_SpiderBoard.o +./temp\obj\moc_SpiderStack.o +./temp\obj\moc_KlondikeStack.o +./temp\obj\moc_KlondikeFlipStack.o +./temp\obj\moc_KlondikeHomeStack.o +./temp\obj\moc_KlondikeBoard.o +./temp\obj\moc_FreeCellBoard.o +./temp\obj\moc_FreeCellDeck.o +./temp\obj\moc_FreeCellStack.o +./temp\obj\moc_FreeCellHome.o +./temp\obj\moc_FreeCellFree.o +./temp\obj\moc_Spider3DeckBoard.o +./temp\obj\moc_SpideretteBoard.o +./temp\obj\moc_YukonBoard.o +./temp\obj\qrc_QSoloCards.o +); diff --git a/plugins/qsolocards_plugin/object_script.qsolocards_plugin.Release b/plugins/qsolocards_plugin/object_script.qsolocards_plugin.Release new file mode 100644 index 000000000..cbdb74bc8 --- /dev/null +++ b/plugins/qsolocards_plugin/object_script.qsolocards_plugin.Release @@ -0,0 +1,64 @@ +INPUT( +./temp\obj\QSoloCardsPlugin.o +./temp\obj\main.o +./temp\obj\mainwindow.o +./temp\obj\PlayingCard.o +./temp\obj\CardDeck.o +./temp\obj\CardPixmaps.o +./temp\obj\CardStack.o +./temp\obj\DragCardStack.o +./temp\obj\VCardStack.o +./temp\obj\CardAnimationLock.o +./temp\obj\StackToStackAniMove.o +./temp\obj\DealAnimation.o +./temp\obj\FlipAnimation.o +./temp\obj\StackToStackFlipAni.o +./temp\obj\GameBoard.o +./temp\obj\CardMoveRecord.o +./temp\obj\About.o +./temp\obj\Help.o +./temp\obj\GameMgr.o +./temp\obj\SpiderBoard.o +./temp\obj\SpiderHomeStack.o +./temp\obj\SpiderStack.o +./temp\obj\KlondikeStack.o +./temp\obj\KlondikeFlipStack.o +./temp\obj\KlondikeHomeStack.o +./temp\obj\KlondikeBoard.o +./temp\obj\FreeCellBoard.o +./temp\obj\FreeCellDeck.o +./temp\obj\FreeCellStack.o +./temp\obj\FreeCellHome.o +./temp\obj\FreeCellFree.o +./temp\obj\Spider3DeckBoard.o +./temp\obj\SpideretteBoard.o +./temp\obj\YukonBoard.o +./temp\obj\moc_QSoloCardsPlugin.o +./temp\obj\moc_mainwindow.o +./temp\obj\moc_CardStack.o +./temp\obj\moc_DragCardStack.o +./temp\obj\moc_VCardStack.o +./temp\obj\moc_CardAnimationLock.o +./temp\obj\moc_StackToStackAniMove.o +./temp\obj\moc_DealAnimation.o +./temp\obj\moc_FlipAnimation.o +./temp\obj\moc_StackToStackFlipAni.o +./temp\obj\moc_GameBoard.o +./temp\obj\moc_About.o +./temp\obj\moc_Help.o +./temp\obj\moc_SpiderBoard.o +./temp\obj\moc_SpiderStack.o +./temp\obj\moc_KlondikeStack.o +./temp\obj\moc_KlondikeFlipStack.o +./temp\obj\moc_KlondikeHomeStack.o +./temp\obj\moc_KlondikeBoard.o +./temp\obj\moc_FreeCellBoard.o +./temp\obj\moc_FreeCellDeck.o +./temp\obj\moc_FreeCellStack.o +./temp\obj\moc_FreeCellHome.o +./temp\obj\moc_FreeCellFree.o +./temp\obj\moc_Spider3DeckBoard.o +./temp\obj\moc_SpideretteBoard.o +./temp\obj\moc_YukonBoard.o +./temp\obj\qrc_QSoloCards.o +); diff --git a/plugins/qsolocards_plugin/qsolocards_plugin.pro b/plugins/qsolocards_plugin/qsolocards_plugin.pro new file mode 100644 index 000000000..86393617a --- /dev/null +++ b/plugins/qsolocards_plugin/qsolocards_plugin.pro @@ -0,0 +1,106 @@ +# ------------------------------------------------- +# Project created by QtCreator 2009-03-07T14:27:09 +# ------------------------------------------------- +#=== this part is common (similar) for all plugin projects ===================== +TEMPLATE = lib +CONFIG += plugin release + +# this is directory, where PluginInterface.h is located +INCLUDEPATH += ../ + +# and, the result (*.so or *.dll) should appear in this directory +DESTDIR = ../bin +OBJECTS_DIR = temp/obj +RCC_DIR = temp/qrc +UI_DIR = temp/ui +MOC_DIR = temp/moc + + +# the name of the result file; +TARGET = $$qtLibraryTarget(qsolocards_plugin) + +HEADERS += ../PluginInterface.h \ + QSoloCardsPlugin.h +SOURCES += QSoloCardsPlugin.cpp + +#=============================================================================== +SOURCES += main.cpp \ + mainwindow.cpp \ + PlayingCard.cpp \ + CardDeck.cpp \ + CardPixmaps.cpp \ + CardStack.cpp \ + DragCardStack.cpp \ + VCardStack.cpp \ + CardAnimationLock.cpp \ + StackToStackAniMove.cpp \ + DealAnimation.cpp \ + FlipAnimation.cpp \ + StackToStackFlipAni.cpp \ + GameBoard.cpp \ + CardMoveRecord.cpp \ + About.cpp \ + Help.cpp \ + GameMgr.cpp \ + SpiderBoard.cpp \ + SpiderHomeStack.cpp \ + SpiderStack.cpp \ + KlondikeStack.cpp \ + KlondikeFlipStack.cpp \ + KlondikeHomeStack.cpp \ + KlondikeBoard.cpp \ + FreeCellBoard.cpp \ + FreeCellDeck.cpp \ + FreeCellStack.cpp \ + FreeCellHome.cpp \ + FreeCellFree.cpp \ + Spider3DeckBoard.cpp \ + SpideretteBoard.cpp \ + YukonBoard.cpp +HEADERS += mainwindow.h \ + PlayingCard.h \ + CardDeck.h \ + CardPixmaps.h \ + CardStack.h \ + DragCardStack.h \ + VCardStack.h \ + CardAnimationLock.h \ + StackToStackAniMove.h \ + DealAnimation.h \ + FlipAnimation.h \ + StackToStackFlipAni.h \ + GameBoard.h \ + CardMoveRecord.h \ + About.h \ + Help.h \ + GameMgr.h \ + SpiderBoard.h \ + SpiderHomeStack.h \ + SpiderStack.h \ + KlondikeStack.h \ + KlondikeFlipStack.h \ + KlondikeHomeStack.h \ + KlondikeBoard.h \ + FreeCellBoard.h \ + FreeCellDeck.h \ + FreeCellStack.h \ + FreeCellHome.h \ + FreeCellFree.h \ + Spider3DeckBoard.h \ + SpideretteBoard.h \ + YukonBoard.h + +QT += svg +RESOURCES = QSoloCards.qrc + +mac:QMAKE_MAC_SDK=/Developer/SDKs/MacOSX10.4u.sdk +mac:CONFIG+=x86 ppc + +VER_MAJ = 0 +VER_MIN = 99 +VER_PAT = 1 +QMAKE_CXXFLAGS_DEBUG = -DVER_MAJ=$$VER_MAJ \ + -DVER_MIN=$$VER_MIN \ + -DVER_PAT=$$VER_PAT +QMAKE_CXXFLAGS_RELEASE = $$QMAKE_CXXFLAGS_DEBUG +mac:ICON = QSoloCards.icns