I just played 3 long games and I was able to undo two fully and got an assert on the third one after more than 1000 actions... so I commit what I have:
- Modified undo to stop at "next phase" action - Added "muligan" and "force library shuffling" to the list of logged action - Fixed random logging - Fixed double logging of actions - Merged all the "next game" functions into a single one - Created a PlayerType type instead of using int - Moved the player loading code into the GameObserver and out of GameStateDuel to avoid having player references in both and simplify the initialization and termination. Tweeked a bit the humanplayer class to be able to do that. - Added a "load" menu available in testsuite mode, I use that to load problematique game. To use it, just copy-paste a game from the traces into Res/test/game/timetwister.txt. Game in traces starts by "rvalues:..." and ends by "[end]" - Added some untested and commented out code in GuiCombat to use the mouse/touch to setup the damage on the blockers - Broke the network game ... hoh well, I'll repair it when everything else works !! - various code cleanup and compilation fixes on Linux
This commit is contained in:
@@ -24,4 +24,4 @@ public:
|
||||
static string Process(const string& s);
|
||||
};
|
||||
|
||||
#endif
|
||||
#endif
|
||||
|
||||
@@ -44,7 +44,6 @@ public:
|
||||
void setMenuObject(Targetable * object, bool must = false);
|
||||
void setCustomMenuObject(Targetable * object, bool must = false,vector<MTGAbility*>abilities = vector<MTGAbility*>());
|
||||
void ButtonPressed(int controllerid, int controlid);
|
||||
void doMultipleChoice(int choice = -1);
|
||||
void ButtonPressedOnMultipleChoice(int choice = -1);
|
||||
void doReactTo(int menuIndex);
|
||||
TargetChooser * getCurrentTargetChooser();
|
||||
|
||||
@@ -207,7 +207,7 @@ public:
|
||||
DONT_INTERRUPT_ALL = 2,
|
||||
};
|
||||
Player * lastActionController;
|
||||
int setIsInterrupting(Player * player);
|
||||
int setIsInterrupting(Player * player, bool log = true);
|
||||
int count( int type = 0 , int state = 0 , int display = -1);
|
||||
Interruptible * getActionElementFromCard(MTGCardInstance * card);
|
||||
Interruptible * getPrevious(Interruptible * next, int type = 0, int state = 0 , int display = -1);
|
||||
@@ -217,7 +217,7 @@ public:
|
||||
void Fizzle(Interruptible * action);
|
||||
Interruptible * getAt(int id);
|
||||
void cancelInterruptOffer(int cancelMode = 1);
|
||||
void endOfInterruption();
|
||||
void endOfInterruption(bool log = true);
|
||||
Interruptible * getLatest(int state);
|
||||
Player * askIfWishesToInterrupt;
|
||||
int garbageCollect();
|
||||
|
||||
@@ -1655,8 +1655,8 @@ public:
|
||||
|
||||
void Update(float dt)
|
||||
{
|
||||
if(!nonstatic)
|
||||
return;
|
||||
if(!nonstatic)
|
||||
return;
|
||||
((MTGCardInstance *) target)->power -= wppt->power.getValue();
|
||||
((MTGCardInstance *) target)->addToToughness(-wppt->toughness.getValue());
|
||||
if(PT.size())
|
||||
@@ -1980,9 +1980,9 @@ public:
|
||||
void Update(float dt)
|
||||
{
|
||||
ListMaintainerAbility::Update(dt);
|
||||
if(!ability->oneShot)
|
||||
if(!ability->oneShot) {
|
||||
SorterFunction();
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
void findMatchingAmount()
|
||||
|
||||
@@ -24,19 +24,10 @@
|
||||
#ifdef NETWORK_SUPPORT
|
||||
#include "JNetwork.h"
|
||||
#endif //NETWORK_SUPPORT
|
||||
|
||||
#include "GameObserver.h"
|
||||
|
||||
class Rules;
|
||||
enum
|
||||
{
|
||||
PLAYER_TYPE_CPU = 0,
|
||||
PLAYER_TYPE_HUMAN = 1,
|
||||
PLAYER_TYPE_TESTSUITE = 2,
|
||||
PLAYER_TYPE_CPU_TEST = 3,
|
||||
#ifdef NETWORK_SUPPORT
|
||||
PLAYER_TYPE_REMOTE = 4
|
||||
#endif //NETWORK_SUPPORT
|
||||
};
|
||||
|
||||
|
||||
class MTGAllCards;
|
||||
class TransitionBase;
|
||||
@@ -88,7 +79,7 @@ public:
|
||||
static string currentMusicFile;
|
||||
static void playMusic(string filename = "", bool loop = true);
|
||||
static void stopMusic();
|
||||
static int players[2];
|
||||
static PlayerType players[2];
|
||||
|
||||
};
|
||||
|
||||
|
||||
@@ -20,6 +20,7 @@ struct CardGui;
|
||||
class Player;
|
||||
class TargetChooser;
|
||||
class Rules;
|
||||
class TestSuite;
|
||||
using namespace std;
|
||||
|
||||
class GameObserver{
|
||||
@@ -41,8 +42,9 @@ class GameObserver{
|
||||
void logAction(const string& s);
|
||||
bool processActions(bool undo);
|
||||
friend ostream& operator<<(ostream&, GameObserver&);
|
||||
bool load(const string& s, bool undo);
|
||||
bool mLoading;
|
||||
void nextGamePhase();
|
||||
void shuffleLibrary(Player* p);
|
||||
|
||||
public:
|
||||
int currentPlayerId;
|
||||
@@ -74,11 +76,15 @@ class GameObserver{
|
||||
const char * getCurrentGamePhaseName();
|
||||
const char * getNextGamePhaseName();
|
||||
void nextCombatStep();
|
||||
void userRequestNextGamePhase();
|
||||
void nextGamePhase();
|
||||
void userRequestNextGamePhase(bool allowInterrupt = true, bool log = true);
|
||||
void cleanupPhase();
|
||||
void nextPlayer();
|
||||
void setPlayers(vector<Player *> _players);
|
||||
|
||||
#ifdef TESTSUITE
|
||||
void loadTestSuitePlayer(int playerId, TestSuite* testSuite);
|
||||
#endif //TESTSUITE
|
||||
void loadPlayer(int playerId, PlayerType playerType = PLAYER_TYPE_HUMAN, int decknb=0, bool premadeDeck=false);
|
||||
Player * currentPlayer;
|
||||
Player * currentActionPlayer;
|
||||
Player * isInterrupting;
|
||||
@@ -111,8 +117,12 @@ class GameObserver{
|
||||
logAction(players[playerId], s);
|
||||
};
|
||||
void logAction(MTGCardInstance* card, MTGGameZone* zone, size_t index, int result);
|
||||
bool load(const string& s, bool undo = false);
|
||||
bool undo();
|
||||
bool isLoading(){ return mLoading; };
|
||||
void Mulligan(Player* player = NULL);
|
||||
Player* getPlayer(size_t index) { return players[index];};
|
||||
bool isStarted() { return (mLayers!=NULL);};
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
@@ -28,7 +28,6 @@ private:
|
||||
Credits * credits;
|
||||
int mGamePhase;
|
||||
Player * mCurrentPlayer;
|
||||
vector<Player *> mPlayers;
|
||||
GameObserver * game;
|
||||
DeckMenu * deckmenu;
|
||||
DeckMenu * opponentMenu;
|
||||
@@ -42,7 +41,6 @@ private:
|
||||
string musictrack;
|
||||
|
||||
bool MusicExist(string FileName);
|
||||
void loadPlayer(int playerId, int decknb = 0, bool isAI = false, bool isNetwork = false);
|
||||
void ConstructOpponentMenu(); //loads the opponentMenu if it doesn't exist
|
||||
void initScroller();
|
||||
void setGamePhase(int newGamePhase);
|
||||
@@ -79,9 +77,12 @@ public:
|
||||
MENUITEM_EVIL_TWIN = kEvilTwinMenuID,
|
||||
MENUITEM_MULLIGAN = -15,
|
||||
MENUITEM_UNDO = -16,
|
||||
#ifdef TESTSUITE
|
||||
MENUITEM_LOAD = -17,
|
||||
#endif
|
||||
#ifdef NETWORK_SUPPORT
|
||||
MENUITEM_REMOTE_CLIENT = -17,
|
||||
MENUITEM_REMOTE_SERVER = -18,
|
||||
MENUITEM_REMOTE_CLIENT = -18,
|
||||
MENUITEM_REMOTE_SERVER = -19,
|
||||
#endif
|
||||
MENUITEM_MORE_INFO = kInfoMenuID
|
||||
};
|
||||
|
||||
@@ -293,7 +293,7 @@ public:
|
||||
{
|
||||
counters = 0;
|
||||
}
|
||||
return MTGAbility::Update(dt);
|
||||
MTGAbility::Update(dt);
|
||||
}
|
||||
virtual int reactToClick(MTGCardInstance * card);
|
||||
virtual int isReactingToClick(MTGCardInstance * card, ManaCost * mana = NULL);
|
||||
|
||||
@@ -24,6 +24,17 @@ typedef enum
|
||||
#endif //NETWORK_SUPPORT
|
||||
} GameType;
|
||||
|
||||
typedef enum
|
||||
{
|
||||
PLAYER_TYPE_CPU = 0,
|
||||
PLAYER_TYPE_HUMAN = 1,
|
||||
PLAYER_TYPE_TESTSUITE = 2,
|
||||
PLAYER_TYPE_CPU_TEST = 3,
|
||||
#ifdef NETWORK_SUPPORT
|
||||
PLAYER_TYPE_REMOTE = 4
|
||||
#endif //NETWORK_SUPPORT
|
||||
} PlayerType;
|
||||
|
||||
class Constants
|
||||
{
|
||||
public:
|
||||
|
||||
@@ -120,85 +120,85 @@ class MTGGameZone {
|
||||
};
|
||||
|
||||
class MTGLibrary: public MTGGameZone {
|
||||
public:
|
||||
virtual ostream& toString(ostream&) const;
|
||||
const char * getName(){return "library";}
|
||||
public:
|
||||
virtual ostream& toString(ostream&) const;
|
||||
const char * getName(){return "library";}
|
||||
};
|
||||
|
||||
class MTGGraveyard: public MTGGameZone {
|
||||
public:
|
||||
virtual ostream& toString(ostream&) const;
|
||||
const char * getName(){return "graveyard";}
|
||||
public:
|
||||
virtual ostream& toString(ostream&) const;
|
||||
const char * getName(){return "graveyard";}
|
||||
};
|
||||
|
||||
class MTGHand: public MTGGameZone {
|
||||
public:
|
||||
virtual ostream& toString(ostream&) const;
|
||||
const char * getName(){return "hand";}
|
||||
public:
|
||||
virtual ostream& toString(ostream&) const;
|
||||
const char * getName(){return "hand";}
|
||||
};
|
||||
|
||||
class MTGRemovedFromGame: public MTGGameZone {
|
||||
public:
|
||||
virtual ostream& toString(ostream&) const;
|
||||
const char * getName(){return "exile";}
|
||||
public:
|
||||
virtual ostream& toString(ostream&) const;
|
||||
const char * getName(){return "exile";}
|
||||
};
|
||||
|
||||
class MTGStack: public MTGGameZone {
|
||||
public:
|
||||
virtual ostream& toString(ostream&) const;
|
||||
const char * getName(){return "stack";}
|
||||
public:
|
||||
virtual ostream& toString(ostream&) const;
|
||||
const char * getName(){return "stack";}
|
||||
};
|
||||
|
||||
class MTGInPlay: public MTGGameZone {
|
||||
public:
|
||||
void untapAll();
|
||||
MTGCardInstance * getNextAttacker(MTGCardInstance * previous);
|
||||
virtual ostream& toString(ostream&) const;
|
||||
const char * getName(){return "battlefield";}
|
||||
public:
|
||||
void untapAll();
|
||||
MTGCardInstance * getNextAttacker(MTGCardInstance * previous);
|
||||
virtual ostream& toString(ostream&) const;
|
||||
const char * getName(){return "battlefield";}
|
||||
};
|
||||
|
||||
|
||||
class MTGPlayerCards {
|
||||
protected:
|
||||
void init();
|
||||
protected:
|
||||
void init();
|
||||
|
||||
public:
|
||||
Player * owner;
|
||||
PlayRestrictions * playRestrictions;
|
||||
MTGLibrary * library;
|
||||
MTGGraveyard * graveyard;
|
||||
MTGHand * hand;
|
||||
MTGInPlay * inPlay;
|
||||
MTGInPlay * battlefield; //alias to inPlay
|
||||
MTGLibrary * library;
|
||||
MTGGraveyard * graveyard;
|
||||
MTGHand * hand;
|
||||
MTGInPlay * inPlay;
|
||||
MTGInPlay * battlefield; //alias to inPlay
|
||||
|
||||
MTGStack * stack;
|
||||
MTGRemovedFromGame * removedFromGame;
|
||||
MTGRemovedFromGame * exile; //alias to removedFromZone
|
||||
MTGGameZone * garbage;
|
||||
MTGGameZone * temp;
|
||||
MTGStack * stack;
|
||||
MTGRemovedFromGame * removedFromGame;
|
||||
MTGRemovedFromGame * exile; //alias to removedFromZone
|
||||
MTGGameZone * garbage;
|
||||
MTGGameZone * temp;
|
||||
|
||||
MTGPlayerCards();
|
||||
MTGPlayerCards(Player*, int * idList, int idListSize);
|
||||
MTGPlayerCards(MTGDeck * deck);
|
||||
~MTGPlayerCards();
|
||||
void initGame(int shuffle = 1, int draw = 1);
|
||||
void OptimizedHand(Player * who,int amount = 7,int lands = 3,int creatures = 0,int othercards = 4);
|
||||
void setOwner(Player * player);
|
||||
void discardRandom(MTGGameZone * from,MTGCardInstance * source);
|
||||
void drawFromLibrary();
|
||||
void showHand();
|
||||
void resetLibrary();
|
||||
void initDeck(MTGDeck * deck);
|
||||
void beforeBeginPhase();
|
||||
MTGCardInstance * putInGraveyard(MTGCardInstance * card);
|
||||
MTGCardInstance * putInExile(MTGCardInstance * card);
|
||||
MTGCardInstance * putInLibrary(MTGCardInstance * card);
|
||||
MTGCardInstance * putInHand(MTGCardInstance * card);
|
||||
MTGCardInstance * putInZone(MTGCardInstance * card, MTGGameZone * from, MTGGameZone * to);
|
||||
int isInPlay(MTGCardInstance * card);
|
||||
int isInGrave(MTGCardInstance * card);
|
||||
int isInZone(MTGCardInstance * card,MTGGameZone * zone);
|
||||
bool parseLine(const string& s);
|
||||
MTGPlayerCards();
|
||||
MTGPlayerCards(Player*, int * idList, int idListSize);
|
||||
MTGPlayerCards(MTGDeck * deck);
|
||||
~MTGPlayerCards();
|
||||
void initGame(int shuffle = 1, int draw = 1);
|
||||
void OptimizedHand(Player * who,int amount = 7,int lands = 3,int creatures = 0,int othercards = 4);
|
||||
void setOwner(Player * player);
|
||||
void discardRandom(MTGGameZone * from,MTGCardInstance * source);
|
||||
void drawFromLibrary();
|
||||
void showHand();
|
||||
void resetLibrary();
|
||||
void initDeck(MTGDeck * deck);
|
||||
void beforeBeginPhase();
|
||||
MTGCardInstance * putInGraveyard(MTGCardInstance * card);
|
||||
MTGCardInstance * putInExile(MTGCardInstance * card);
|
||||
MTGCardInstance * putInLibrary(MTGCardInstance * card);
|
||||
MTGCardInstance * putInHand(MTGCardInstance * card);
|
||||
MTGCardInstance * putInZone(MTGCardInstance * card, MTGGameZone * from, MTGGameZone * to);
|
||||
int isInPlay(MTGCardInstance * card);
|
||||
int isInGrave(MTGCardInstance * card);
|
||||
int isInZone(MTGCardInstance * card,MTGGameZone * zone);
|
||||
bool parseLine(const string& s);
|
||||
};
|
||||
|
||||
ostream& operator<<(ostream&, const MTGGameZone&);
|
||||
|
||||
@@ -101,8 +101,14 @@ public:
|
||||
|
||||
class HumanPlayer: public Player
|
||||
{
|
||||
protected:
|
||||
bool premade;
|
||||
public:
|
||||
HumanPlayer(GameObserver *observer, string deckFile, string deckFileSmall, MTGDeck * deck = NULL);
|
||||
HumanPlayer(GameObserver *observer, string deckFile, string deckFileSmall, bool premade = false, MTGDeck * deck = NULL);
|
||||
void End(){
|
||||
if(!premade && opponent())
|
||||
DeckStats::GetInstance()->saveStats(this, opponent(), observer);
|
||||
};
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
@@ -66,7 +66,7 @@ unsigned long hash_djb2(const char *str);
|
||||
void loadRandValues(string s);
|
||||
ostream& saveRandValues(ostream& out);
|
||||
int filesize(const char * filename);
|
||||
int WRand();
|
||||
int WRand(bool log = false);
|
||||
ptrdiff_t MRand (ptrdiff_t i);
|
||||
|
||||
#ifdef LINUX
|
||||
|
||||
Reference in New Issue
Block a user