Compare commits
96 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| ab34d0d366 | |||
| 963ab2840b | |||
| a25b010429 | |||
| 504160a740 | |||
| 5061f7c37f | |||
| 30f5a49988 | |||
| 2998e95a3b | |||
| ac29367ff8 | |||
| dbd7f82eab | |||
| 176b74489e | |||
| f940f8e303 | |||
| 2679213121 | |||
| 59c0cf467f | |||
| 5a2637856f | |||
| 26ecb199d3 | |||
| 62d42fb61f | |||
| 19c96e496b | |||
| e982ba50be | |||
| 27ad956034 | |||
| 8c6f694645 | |||
| 8ce85636d9 | |||
| 07683480b4 | |||
| 7d8fdbfd58 | |||
| 2a1cb03484 | |||
| baa90fb605 | |||
| 1b67b736df | |||
| e6514a8b33 | |||
| 636b07b350 | |||
| 4b5478530c | |||
| 4a721a7e18 | |||
| 2470629afd | |||
| ccdd16bbc7 | |||
| 9cf6e621ab | |||
| 94a97a3032 | |||
| f4ef7b9851 | |||
| c2be7dd025 | |||
| b51dfc7733 | |||
| 9999820a8f | |||
| 10bc8283ed | |||
| 66f3ba5a7b | |||
| 07f0175c5e | |||
| 7376ac382f | |||
| 3646219da4 | |||
| bfbc073593 | |||
| 307be96fd6 | |||
| 22f4f21619 | |||
| 1738e216d0 | |||
| 567650357f | |||
| 32de6ac124 | |||
| 60f3c87de1 | |||
| d9561118bc | |||
| 228e5342fb | |||
| 8574154071 | |||
| 80379ecde5 | |||
| 31b8ad248f | |||
| 2d02f97f7f | |||
| 6a37b5e461 | |||
| 38ed60bf63 | |||
| e664ecfaf5 | |||
| e2814c04f4 | |||
| 8c2836b0c2 | |||
| fcfab4c756 | |||
| ddd59c489a | |||
| db922a0e77 | |||
| 793c4d1d7d | |||
| 24eab33b6d | |||
| 4985323ad9 | |||
| 9fc551982b | |||
| 8ee67b5af8 | |||
| 78ad22479c | |||
| 2041aa45f0 | |||
| c8b0ce9669 | |||
| 11eb6de57e | |||
| c451234bd5 | |||
| b56862fcf8 | |||
| 21a6da91ca | |||
| 410108a005 | |||
| 51d5b166a6 | |||
| 1f77243881 | |||
| f63afb2dd6 | |||
| dbe1c6e2ae | |||
| 6a37425a38 | |||
| 02efa4745f | |||
| e78754bcd5 | |||
| 16dcf3cc5e | |||
| 03d168f972 | |||
| 6f6c8b0eb6 | |||
| fa14219e12 | |||
| 15cd86fad1 | |||
| 165eb699e8 | |||
| 33760f4066 | |||
| 656ab78cf5 | |||
| 541698f98e | |||
| 746a486e7a | |||
| 261a6e4780 | |||
| a683f5a2b7 |
+25
-33
@@ -1,34 +1,30 @@
|
|||||||
language: cpp
|
language: cpp
|
||||||
env:
|
|
||||||
global:
|
|
||||||
secure: "fJgWlCFbde96OSQNGKUmowGX+ERPeqP+n1EOMf1+FJzOU4DdkTLRAlV5+5qnEX9jB/3mWN6iPpmG1qEz/SdDG3KHxJYs4ZU/Lu485O24zZ/+GdYBNsrvhPD9ckPGEMLDa1foEVTDnW0Dlkz3BCFcszjhtXGUJv7v6Pj6LRk1Mg8="
|
|
||||||
matrix:
|
|
||||||
- BUILD_TYPE=PSP
|
|
||||||
- BUILD_TYPE=Android
|
|
||||||
- BUILD_TYPE=Qt
|
|
||||||
|
|
||||||
branches:
|
branches:
|
||||||
except:
|
except:
|
||||||
- latest-master
|
- latest-master
|
||||||
|
|
||||||
before_install:
|
before_install:
|
||||||
|
- export BUILD_PSP=YES
|
||||||
|
- export BUILD_ANDROID=YES
|
||||||
|
- export BUILD_Qt=YES
|
||||||
|
- export BUILD_MAC=YES
|
||||||
- sudo apt-get update -qq
|
- sudo apt-get update -qq
|
||||||
# Building for PSP here
|
# Building for PSP here
|
||||||
- if [ "$BUILD_TYPE" == "PSP" ]; then
|
- if [ "$BUILD_PSP" == "YES" ]; then
|
||||||
export PSPDEV="$TRAVIS_BUILD_DIR/opt/pspsdk" &&
|
export PSPDEV="$TRAVIS_BUILD_DIR/opt/pspsdk" &&
|
||||||
export PSPSDK="$PSPDEV/psp/sdk" &&
|
export PSPSDK="$PSPDEV/psp/sdk" &&
|
||||||
export PATH="$PATH:$PSPDEV/bin:$PSPSDK/bin" &&
|
export PATH="$PATH:$PSPDEV/bin:$PSPSDK/bin" &&
|
||||||
wget -O sdk.lzma http://sourceforge.net/projects/minpspw/files/SDK%20%2B%20devpak/pspsdk%200.11.2/minpspw_0.11.2-amd64.tar.lzma/download;
|
wget -O sdk.lzma http://sourceforge.net/projects/minpspw/files/SDK%20%2B%20devpak/pspsdk%200.11.2/minpspw_0.11.2-amd64.tar.lzma/download;
|
||||||
fi
|
fi
|
||||||
# Building for Android here
|
# Building for Android here
|
||||||
- if [ "$BUILD_TYPE" == "Android" ]; then
|
- if [ "$BUILD_ANDROID" == "YES" ]; then
|
||||||
export ANDROID="android-sdk-linux/tools/android" &&
|
export ANDROID="android-sdk-linux/tools/android" &&
|
||||||
if [ `uname -m` = x86_64 ]; then sudo apt-get install -qq --force-yes libgd2-xpm ia32-libs ia32-libs-multiarch jq; fi &&
|
if [ `uname -m` = x86_64 ]; then sudo apt-get install -qq --force-yes libgd2-xpm ia32-libs ia32-libs-multiarch jq; fi &&
|
||||||
wget http://dl.google.com/android/ndk/android-ndk-r9-linux-x86_64.tar.bz2 -nv &&
|
wget http://dl.google.com/android/ndk/android-ndk-r9-linux-x86_64.tar.bz2 -nv &&
|
||||||
wget http://dl.google.com/android/android-sdk_r23.0.2-linux.tgz -nv;
|
wget http://dl.google.com/android/android-sdk_r24.3.3-linux.tgz -nv;
|
||||||
fi
|
fi
|
||||||
# Building for Qt here
|
# Building for Qt here
|
||||||
- if [ "$BUILD_TYPE" == "Qt" ]; then
|
- if [ "$BUILD_Qt" == "YES" ]; then
|
||||||
sudo add-apt-repository --yes ppa:ubuntu-sdk-team/ppa &&
|
sudo add-apt-repository --yes ppa:ubuntu-sdk-team/ppa &&
|
||||||
sudo apt-get update -qq &&
|
sudo apt-get update -qq &&
|
||||||
sudo apt-get install -qq qt5-qmake qtbase5-dev qtdeclarative5-dev qttools5-dev qtmultimedia5-dev pulseaudio libpulse-dev &&
|
sudo apt-get install -qq qt5-qmake qtbase5-dev qtdeclarative5-dev qttools5-dev qtmultimedia5-dev pulseaudio libpulse-dev &&
|
||||||
@@ -36,33 +32,29 @@ before_install:
|
|||||||
fi
|
fi
|
||||||
|
|
||||||
install:
|
install:
|
||||||
# Building for PSP here
|
- if [ "$BUILD_PSP" == "YES" ]; then
|
||||||
- if [ "$BUILD_TYPE" == "PSP" ]; then
|
|
||||||
tar -x --xz -f sdk.lzma;
|
tar -x --xz -f sdk.lzma;
|
||||||
fi
|
fi
|
||||||
- if [ "$BUILD_TYPE" == "Android" ]; then
|
- if [ "$BUILD_ANDROID" == "YES" ]; then
|
||||||
tar --absolute-names -jxf android-ndk-r9-linux-x86_64.tar.bz2 &&
|
tar --absolute-names -jxf android-ndk-r9-linux-x86_64.tar.bz2 &&
|
||||||
tar -zxf android-sdk_r23.0.2-linux.tgz &&
|
tar -zxf android-sdk_r24.3.3-linux.tgz &&
|
||||||
$ANDROID list sdk --extended -a &&
|
$ANDROID list sdk --extended -a &&
|
||||||
echo yes | $ANDROID update sdk --filter tools,platform-tools,build-tools-21.1.1,android-10 --no-ui --force --no-https;
|
echo yes | $ANDROID update sdk -a -t tools,platform-tools,build-tools-22.0.1,android-10 --no-ui --force --no-https;
|
||||||
fi
|
fi
|
||||||
- sudo pip install pyjavaproperties
|
- sudo pip install pyjavaproperties
|
||||||
- sudo pip install github3.py
|
- sudo pip install github3.py
|
||||||
script: ./travis-script.sh
|
- sudo pip install cpp-coveralls
|
||||||
|
|
||||||
matrix:
|
env:
|
||||||
fast_finish: true
|
global:
|
||||||
|
- secure: "EBzr1+qjQsOhn0s+tcFmXR1jP9B0xiOSXuXbRXWZ1OEHNvp8+A5/pS84LYVFlaZqmxr5dApxvPtwhgLIUbQ3EPXm8LpC3KgSD4dS+9/QMbxhe5TK4oczgFRGcDTMJQZsCzhOh7hp3tbcbJg5Gp+VT7aFjFQSHDGwhzSJXsXwh/8="
|
||||||
|
- secure: "X5dTQfofqAutnXxmu11Ep2MQ5QYnMN8m0AITRtwymhEF2UclcOudI1+skPtuhAGbWQnSO+lhunV3cvMfw2/Ml3k/VDz6VdFSKFrzAu7ja1VLJfcxr7chi0s8q30pVBb66tGydjIBac3B+RQyqgmZQW1frbRrhC/kPFQ6wPWOJdQ="
|
||||||
|
- secure: "T97NUPnxCpVZ/c5HH0zfo0FO3DPSRMSmze58ubW5EUTZOjAMtEt+OFdsrNZvUTCugUj2M1agtonZbAbczpaAL+lgZcHDgXgWMkfO0pMnsWX1yyCNqMuE/iTMpJr/xsLQeyWlftWjJLsseQU45abZsd1XVmda/G+ZhrDLF1y55SA="
|
||||||
|
|
||||||
deploy:
|
script: "tools/travis-script.sh"
|
||||||
provider: releases
|
|
||||||
api-key:
|
after_success:
|
||||||
secure: "gzfDEihpfTmoO6CSjTNpHSlLTPtQUZUqTlmD91CQby6+znDsOy4xsqj10MNXe+l/3KYny1DtM48nxNKeVjsyeYg66TTzKsrgMVzt6Ah5CBhSXO99/TiaMJmSXmMO7GGfKDct190Dqej1gbR7AMd38DOYe2vpR0LX+Lf3gzDVLoU="
|
- coveralls -b . -e JGE/src -e JGE/include -i projects/mtg/include -i projects/mtg/src --gcov-options '\-lp'
|
||||||
file:
|
- python tools/upload-binaries.py -t $GH_TOKEN -s $TRAVIS_COMMIT -l core.zip -r Wagic-core.zip -b $TRAVIS_BRANCH
|
||||||
- ${TRAVIS_BUILD_DIR}/core.zip
|
- python tools/upload-binaries.py -t $GH_TOKEN -s $TRAVIS_COMMIT -l projects/mtg/Android/bin/Wagic-debug.apk -r Wagic-android.apk -b $TRAVIS_BRANCH
|
||||||
- ${TRAVIS_BUILD_DIR}/projects/mtg/Android/bin/Wagic-debug.apk
|
- python tools/upload-binaries.py -t $GH_TOKEN -s $TRAVIS_COMMIT -l projects/mtg/psprelease.zip -r Wagic-psp.zip -b $TRAVIS_BRANCH
|
||||||
- ${TRAVIS_BUILD_DIR}/projects/mtg/psprelease.zip
|
|
||||||
skip_cleanup: true
|
|
||||||
on:
|
|
||||||
repo: WagicProject/wagic
|
|
||||||
tags: false
|
|
||||||
branch: auto_releases
|
|
||||||
|
|||||||
@@ -0,0 +1,80 @@
|
|||||||
|
# Changelog
|
||||||
|
|
||||||
|
## [latest-master] (https://github.com/WagicProject/wagic/tree/latest-master)
|
||||||
|
#### 08/12/14
|
||||||
|
- *Merged pull-request:* Fix for guild_keywords Devotion, added some "Chroma" cards [\#606](https://github.com/WagicProject/wagic/pull/606) ([kevlahnota](https://github.com/kevlahnota))
|
||||||
|
|
||||||
|
- *Merged pull-request:* added guild keywords, added specific life cost [\#605](https://github.com/WagicProject/wagic/pull/605) ([kevlahnota](https://github.com/kevlahnota))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Buyback issue and a fix [\#604](https://github.com/WagicProject/wagic/pull/604) ([apollovy](https://github.com/apollovy))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Feature/ios update xcode5.1 [\#602](https://github.com/WagicProject/wagic/pull/602) ([mjnguyen](https://github.com/mjnguyen))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Remove dead code and fix circular initialization [\#601](https://github.com/WagicProject/wagic/pull/601) ([ZobyTwo](https://github.com/ZobyTwo))
|
||||||
|
|
||||||
|
- *Merged pull-request:* update android build tools version [\#600](https://github.com/WagicProject/wagic/pull/600) ([Rolzad73](https://github.com/Rolzad73))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Attempt to make android tools fetching for TravisCI explicit and futureproof [\#599](https://github.com/WagicProject/wagic/pull/599) ([Rolzad73](https://github.com/Rolzad73))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Damager keyword [\#598](https://github.com/WagicProject/wagic/pull/598) ([bjornsnoen](https://github.com/bjornsnoen))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Fix a rarity mistake and a grammatical error [\#596](https://github.com/WagicProject/wagic/pull/596) ([bjornsnoen](https://github.com/bjornsnoen))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Fix bug where the phase wheel got out of sync [\#588](https://github.com/WagicProject/wagic/pull/588) ([ZobyTwo](https://github.com/ZobyTwo))
|
||||||
|
|
||||||
|
- *Merged pull-request:* More easing [\#586](https://github.com/WagicProject/wagic/pull/586) ([ZobyTwo](https://github.com/ZobyTwo))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Added Avatar Tokens created by Ajani Goldmane. [\#585](https://github.com/WagicProject/wagic/pull/585) ([bjornsnoen](https://github.com/bjornsnoen))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Cleanup, usability fixes and source code documentation for DeckView.h and GridDeckView.h [\#583](https://github.com/WagicProject/wagic/pull/583) ([ZobyTwo](https://github.com/ZobyTwo))
|
||||||
|
|
||||||
|
- *Fixed bug:* Blight does not destroy at the end of turn but right now [\#592](https://github.com/WagicProject/wagic/issues/592)
|
||||||
|
|
||||||
|
- *Fixed bug:* game freezes on Android when the phone returns from "sleep mode" [\#544](https://github.com/WagicProject/wagic/issues/544)
|
||||||
|
|
||||||
|
- *Fixed bug:* Android port needs to be able to respond to attaching/detaching devices to it [\#522](https://github.com/WagicProject/wagic/issues/522)
|
||||||
|
|
||||||
|
## [alpha-195] (https://github.com/WagicProject/wagic/tree/alpha-195)
|
||||||
|
#### 07/12/13
|
||||||
|
- *Merged pull-request:* Reset positions and filters when reopening the editor [\#578](https://github.com/WagicProject/wagic/pull/578) ([ZobyTwo](https://github.com/ZobyTwo))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Deck viewer [\#577](https://github.com/WagicProject/wagic/pull/577) ([ZobyTwo](https://github.com/ZobyTwo))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Do not specify the system directory in JGE [\#576](https://github.com/WagicProject/wagic/pull/576) ([ZobyTwo](https://github.com/ZobyTwo))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Changed Travis build file to use Android API 10 and Android build tools 18.1.1 [\#575](https://github.com/WagicProject/wagic/pull/575) ([Rolzad73](https://github.com/Rolzad73))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Feature/play from grave [\#574](https://github.com/WagicProject/wagic/pull/574) ([pankdm](https://github.com/pankdm))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Fix Valgrind warnings appearing during the test suit. [\#573](https://github.com/WagicProject/wagic/pull/573) ([ZobyTwo](https://github.com/ZobyTwo))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Strings 2 [\#572](https://github.com/WagicProject/wagic/pull/572) ([ZobyTwo](https://github.com/ZobyTwo))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Android travis ci [\#570](https://github.com/WagicProject/wagic/pull/570) ([xawotihs](https://github.com/xawotihs))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Android NDK build fix [\#569](https://github.com/WagicProject/wagic/pull/569) ([Rolzad73](https://github.com/Rolzad73))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Add a few namespaces and fix header guards. [\#564](https://github.com/WagicProject/wagic/pull/564) ([ZobyTwo](https://github.com/ZobyTwo))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Updated deckmenu.cpp to properly render deck description and summary [\#562](https://github.com/WagicProject/wagic/pull/562) ([citiral](https://github.com/citiral))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Fix some valgrind memcheck warnings. However there remains one... [\#561](https://github.com/WagicProject/wagic/pull/561) ([ZobyTwo](https://github.com/ZobyTwo))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Remove some dead code [\#560](https://github.com/WagicProject/wagic/pull/560) ([ZobyTwo](https://github.com/ZobyTwo))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Show output only for failing tests [\#559](https://github.com/WagicProject/wagic/pull/559) ([pankdm](https://github.com/pankdm))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Defines/Typos [\#557](https://github.com/WagicProject/wagic/pull/557) ([ZobyTwo](https://github.com/ZobyTwo))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Simplify Damage::resolve a bit [\#556](https://github.com/WagicProject/wagic/pull/556) ([ZobyTwo](https://github.com/ZobyTwo))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Fix cranial plating [\#555](https://github.com/WagicProject/wagic/pull/555) ([pankdm](https://github.com/pankdm))
|
||||||
|
|
||||||
|
- *Merged pull-request:* Android cleanup [\#1](https://github.com/WagicProject/wagic/pull/1) ([Rolzad73](https://github.com/Rolzad73))
|
||||||
|
|
||||||
|
- *Fixed bug:* Iona and Nin don't work [\#527](https://github.com/WagicProject/wagic/issues/527)
|
||||||
|
|
||||||
|
- *Closed issue:* Less verbose output of tests at Travis [\#558](https://github.com/WagicProject/wagic/issues/558)
|
||||||
|
|
||||||
|
## [wagic-0.19.2] (https://github.com/WagicProject/wagic/tree/wagic-v0.19.2)
|
||||||
|
#### 28/10/13
|
||||||
@@ -248,7 +248,7 @@ void JFileSystem::clearZipCache()
|
|||||||
|
|
||||||
bool JFileSystem::AttachZipFile(const string &zipfile, char *password /* = NULL */)
|
bool JFileSystem::AttachZipFile(const string &zipfile, char *password /* = NULL */)
|
||||||
{
|
{
|
||||||
if (mZipAvailable && mZipFile != NULL)
|
if (mZipAvailable && mZipFile.is_open())
|
||||||
{
|
{
|
||||||
if (mZipFileName != zipfile)
|
if (mZipFileName != zipfile)
|
||||||
DetachZipFile(); // close the previous zip file
|
DetachZipFile(); // close the previous zip file
|
||||||
|
|||||||
+7
-3
@@ -67,7 +67,9 @@ void JMusic::seekAtTheBegining()
|
|||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////
|
||||||
JSample::JSample()
|
JSample::JSample()
|
||||||
#ifdef USE_PHONON
|
#ifdef QT_CONFIG
|
||||||
|
: effect(0)
|
||||||
|
#elif (defined USE_PHONON)
|
||||||
: mOutput(0), mMediaObject(0)
|
: mOutput(0), mMediaObject(0)
|
||||||
#endif
|
#endif
|
||||||
{
|
{
|
||||||
@@ -77,9 +79,11 @@ JSample::JSample()
|
|||||||
JSample::~JSample()
|
JSample::~JSample()
|
||||||
{
|
{
|
||||||
#if (defined QT_CONFIG) && (!defined USE_PHONON)
|
#if (defined QT_CONFIG) && (!defined USE_PHONON)
|
||||||
if(effect)
|
if(effect) {
|
||||||
delete effect;
|
delete effect;
|
||||||
#elif USE_PHONON
|
effect = 0;
|
||||||
|
}
|
||||||
|
#elif (defined USE_PHONON)
|
||||||
if(mOutput)
|
if(mOutput)
|
||||||
delete mOutput;
|
delete mOutput;
|
||||||
if(mMediaObject)
|
if(mMediaObject)
|
||||||
|
|||||||
@@ -3,7 +3,7 @@
|
|||||||
|
|
||||||
[](https://travis-ci.org/WagicProject/wagic)
|
[](https://travis-ci.org/WagicProject/wagic)
|
||||||
[](https://ci.appveyor.com/project/xawotihs/wagic/branch/master)
|
[](https://ci.appveyor.com/project/xawotihs/wagic/branch/master)
|
||||||
|
[](https://coveralls.io/r/WagicProject/wagic?branch=master)
|
||||||
|
|
||||||
## Description
|
## Description
|
||||||
|
|
||||||
|
|||||||
+9
-1
@@ -4,6 +4,14 @@
|
|||||||
# - All section names are case-sensitive.
|
# - All section names are case-sensitive.
|
||||||
# - Section names should be unique on each level.
|
# - Section names should be unique on each level.
|
||||||
|
|
||||||
|
# branches to build
|
||||||
|
branches:
|
||||||
|
# blacklist
|
||||||
|
except:
|
||||||
|
- travis_mac_osx
|
||||||
|
# Do not build on tags (GitHub only)
|
||||||
|
skip_tags: true
|
||||||
|
|
||||||
#---------------------------------#
|
#---------------------------------#
|
||||||
# environment configuration #
|
# environment configuration #
|
||||||
#---------------------------------#
|
#---------------------------------#
|
||||||
@@ -61,7 +69,7 @@ after_deploy:
|
|||||||
|
|
||||||
# to run your custom scripts instead of provider deployments
|
# to run your custom scripts instead of provider deployments
|
||||||
deploy_script:
|
deploy_script:
|
||||||
- "C:/Python27/python.exe upload-binaries.py -t %GH_TOKEN% -s %APPVEYOR_REPO_COMMIT% -l projects/mtg/bin/Wagic-windows.zip -r Wagic-windows.zip -b %APPVEYOR_REPO_BRANCH%"
|
- "C:/Python27/python.exe tools/upload-binaries.py -t %GH_TOKEN% -s %APPVEYOR_REPO_COMMIT% -l projects/mtg/bin/Wagic-windows.zip -r Wagic-windows.zip -b %APPVEYOR_REPO_BRANCH%"
|
||||||
|
|
||||||
# to disable deployment
|
# to disable deployment
|
||||||
#deploy: off
|
#deploy: off
|
||||||
|
|||||||
@@ -0,0 +1,20 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||||
|
<plist version="1.0">
|
||||||
|
<dict>
|
||||||
|
<key>NSPrincipalClass</key>
|
||||||
|
<string>NSApplication</string>
|
||||||
|
<key>CFBundlePackageType</key>
|
||||||
|
<string>APPL</string>
|
||||||
|
<key>CFBundleGetInfoString</key>
|
||||||
|
<string>Created by Qt/QMake</string>
|
||||||
|
<key>CFBundleSignature</key>
|
||||||
|
<string>????</string>
|
||||||
|
<key>CFBundleExecutable</key>
|
||||||
|
<string>wagic.launcher</string>
|
||||||
|
<key>CFBundleIdentifier</key>
|
||||||
|
<string>wagic.wagic</string>
|
||||||
|
<key>NOTE</key>
|
||||||
|
<string>This file was generated by Qt/QMake.</string>
|
||||||
|
</dict>
|
||||||
|
</plist>
|
||||||
Binary file not shown.
Executable
+5
@@ -0,0 +1,5 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
cd ${0%/*/*}/Resources
|
||||||
|
#cd ../Resources
|
||||||
|
exec ../MacOS/wagic -platformpluginpath ../PlugIns >> ../logs/out.log 2> ../logs/err.log
|
||||||
@@ -86,7 +86,7 @@ all: $(DEFAULT_RULE)
|
|||||||
|
|
||||||
endif
|
endif
|
||||||
|
|
||||||
CFLAGS := -Wall -W -Werror -Wno-unused $(CFLAGS)
|
CFLAGS := -Wall -W -Wno-unused $(CFLAGS)
|
||||||
CXXFLAGS += $(CFLAGS)
|
CXXFLAGS += $(CFLAGS)
|
||||||
# -fno-exceptions
|
# -fno-exceptions
|
||||||
|
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,21 @@
|
|||||||
|
<PACK name="Dragons of Tarkir" type="Booster" pool="all set:DTK;" price="700">
|
||||||
|
<slot copies="1">
|
||||||
|
<random_card>rarity:mythic;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
</slot>
|
||||||
|
<slot copies="3">
|
||||||
|
<random_card>rarity:uncommon;</random_card>
|
||||||
|
</slot>
|
||||||
|
<slot copies="1">
|
||||||
|
<random_card>rarity:special;</random_card>
|
||||||
|
</slot>
|
||||||
|
<slot copies="10">
|
||||||
|
<random_card>rarity:common;</random_card>
|
||||||
|
</slot>
|
||||||
|
</PACK>
|
||||||
@@ -0,0 +1,934 @@
|
|||||||
|
[meta]
|
||||||
|
author=Wagic Team
|
||||||
|
year=2015
|
||||||
|
[/meta]
|
||||||
|
[card]
|
||||||
|
primitive=Abzan Advantage
|
||||||
|
id=391781
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Abzan Beastmaster
|
||||||
|
id=391782
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Abzan Kin-Guard
|
||||||
|
id=391783
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Abzan Runemark
|
||||||
|
id=391784
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Abzan Skycaptain
|
||||||
|
id=391785
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Ainok Guide
|
||||||
|
id=391786
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Alesha, Who Smiles at Death
|
||||||
|
id=391787
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Alesha's Vanguard
|
||||||
|
id=391788
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Ambush Krotiq
|
||||||
|
id=391789
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Ancestral Vengeance
|
||||||
|
id=391790
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Arashin Cleric
|
||||||
|
id=391791
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Arashin War Beast
|
||||||
|
id=391792
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Arcbond
|
||||||
|
id=391793
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Archers of Qarsi
|
||||||
|
id=391794
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Archfiend of Depravity
|
||||||
|
id=391795
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Atarka, World Render
|
||||||
|
id=391796
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Aven Skirmisher
|
||||||
|
id=391797
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Aven Surveyor
|
||||||
|
id=391798
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Bathe in Dragonfire
|
||||||
|
id=391799
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Battle Brawler
|
||||||
|
id=391800
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Battlefront Krushok
|
||||||
|
id=391801
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Bloodfell Caves
|
||||||
|
id=391802
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Bloodfire Enforcers
|
||||||
|
id=391803
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Blossoming Sands
|
||||||
|
id=391804
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Break Through the Line
|
||||||
|
id=391805
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Brutal Hordechief
|
||||||
|
id=391806
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Cached Defenses
|
||||||
|
id=391807
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Channel Harm
|
||||||
|
id=391808
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Citadel Siege
|
||||||
|
id=391809
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Cloudform
|
||||||
|
id=391810
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Collateral Damage
|
||||||
|
id=391811
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Crucible of the Spirit Dragon
|
||||||
|
id=391812
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Crux of Fate
|
||||||
|
id=391813
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Cunning Strike
|
||||||
|
id=391814
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Daghatar the Adamant
|
||||||
|
id=391815
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Dark Deal
|
||||||
|
id=391816
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Defiant Ogre
|
||||||
|
id=391817
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Destructor Dragon
|
||||||
|
id=391818
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Diplomacy of the Wastes
|
||||||
|
id=391819
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Dismal Backwater
|
||||||
|
id=391820
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Douse in Gloom
|
||||||
|
id=391821
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Dragon Bell Monk
|
||||||
|
id=391822
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Dragonrage
|
||||||
|
id=391823
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Dragonscale General
|
||||||
|
id=391824
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Dromoka, the Eternal
|
||||||
|
id=391825
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Elite Scaleguard
|
||||||
|
id=391826
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Enhanced Awareness
|
||||||
|
id=391827
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Ethereal Ambush
|
||||||
|
id=391828
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Fascination
|
||||||
|
id=391829
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Fearsome Awakening
|
||||||
|
id=391830
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Feral Krushok
|
||||||
|
id=391831
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Fierce Invocation
|
||||||
|
id=391832
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Flamerush Rider
|
||||||
|
id=391833
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Flamewake Phoenix
|
||||||
|
id=391834
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Forest
|
||||||
|
id=391836
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Formless Nurturing
|
||||||
|
id=391837
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Friendly Fire
|
||||||
|
id=391838
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Frontier Mastodon
|
||||||
|
id=391839
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Frontier Siege
|
||||||
|
id=391840
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Frost Walker
|
||||||
|
id=391841
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Fruit of the First Tree
|
||||||
|
id=391842
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Ghastly Conscription
|
||||||
|
id=391843
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Goblin Boom Keg
|
||||||
|
id=391844
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Goblin Heelcutter
|
||||||
|
id=391845
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Gore Swine
|
||||||
|
id=391846
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Grave Strength
|
||||||
|
id=391847
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Great-Horn Krushok
|
||||||
|
id=391848
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Grim Contest
|
||||||
|
id=391849
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Gurmag Angler
|
||||||
|
id=391850
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Harsh Sustenance
|
||||||
|
id=391851
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Hero's Blade
|
||||||
|
id=391852
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Hewed Stone Retainers
|
||||||
|
id=391853
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Honor's Reward
|
||||||
|
id=391854
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Hooded Assassin
|
||||||
|
id=391855
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Humble Defector
|
||||||
|
id=391856
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Hungering Yeti
|
||||||
|
id=391857
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Hunt the Weak
|
||||||
|
id=391858
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Island
|
||||||
|
id=391859
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Jeskai Barricade
|
||||||
|
id=391861
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Jeskai Infiltrator
|
||||||
|
id=391862
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Jeskai Runemark
|
||||||
|
id=391863
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Jeskai Sage
|
||||||
|
id=391864
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Jungle Hollow
|
||||||
|
id=391865
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Kolaghan, the Storm's Fury
|
||||||
|
id=391866
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Lightform
|
||||||
|
id=391867
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Lightning Shrieker
|
||||||
|
id=391868
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Lotus Path Djinn
|
||||||
|
id=391869
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Lotus-Eye Mystics
|
||||||
|
id=391870
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Map the Wastes
|
||||||
|
id=391871
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Marang River Prowler
|
||||||
|
id=391872
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Mardu Runemark
|
||||||
|
id=391873
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Mardu Scout
|
||||||
|
id=391874
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Mardu Shadowspear
|
||||||
|
id=391875
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Mardu Strike Leader
|
||||||
|
id=391876
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Mardu Woe-Reaper
|
||||||
|
id=391877
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Mastery of the Unseen
|
||||||
|
id=391878
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Merciless Executioner
|
||||||
|
id=391879
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Mindscour Dragon
|
||||||
|
id=391880
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Mistfire Adept
|
||||||
|
id=391881
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Mob Rule
|
||||||
|
id=391882
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Monastery Mentor
|
||||||
|
id=391883
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Monk Token
|
||||||
|
id=-391883
|
||||||
|
rarity=T
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Monastery Siege
|
||||||
|
id=391884
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Mountain
|
||||||
|
id=391885
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Neutralizing Blast
|
||||||
|
id=391887
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Noxious Dragon
|
||||||
|
id=391888
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Ojutai, Soul of Winter
|
||||||
|
id=391889
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Orc Sureshot
|
||||||
|
id=391890
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Outpost Siege
|
||||||
|
id=391891
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Palace Siege
|
||||||
|
id=391892
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Pilgrim of the Fires
|
||||||
|
id=391893
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Plains
|
||||||
|
id=391895
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Pressure Point
|
||||||
|
id=391896
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Pyrotechnics
|
||||||
|
id=391897
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Qarsi High Priest
|
||||||
|
id=391898
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Rageform
|
||||||
|
id=391899
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Rakshasa's Disdain
|
||||||
|
id=391900
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Rally the Ancestors
|
||||||
|
id=391901
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Reach of Shadows
|
||||||
|
id=391902
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Reality Shift
|
||||||
|
id=391903
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Refocus
|
||||||
|
id=391904
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Renowned Weaponsmith
|
||||||
|
id=391905
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Return to the Earth
|
||||||
|
id=391906
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Rite of Undoing
|
||||||
|
id=391907
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Rugged Highlands
|
||||||
|
id=391908
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Ruthless Instincts
|
||||||
|
id=391909
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Sage-Eye Avengers
|
||||||
|
id=391911
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Sage's Reverie
|
||||||
|
id=391910
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Sandblast
|
||||||
|
id=391912
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Sandsteppe Mastodon
|
||||||
|
id=391913
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Sandsteppe Outcast
|
||||||
|
id=391914
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Scoured Barrens
|
||||||
|
id=391915
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Scroll of the Masters
|
||||||
|
id=391916
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Shaman of the Great Hunt
|
||||||
|
id=391917
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Shamanic Revelation
|
||||||
|
id=391918
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Shifting Loyalties
|
||||||
|
id=391919
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Shockmaw Dragon
|
||||||
|
id=391920
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Shu Yun, the Silent Tempest
|
||||||
|
id=391921
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Sibsig Host
|
||||||
|
id=391922
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Sibsig Muckdraggers
|
||||||
|
id=391923
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Silumgar, the Drifting Death
|
||||||
|
id=391924
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Smoldering Efreet
|
||||||
|
id=391925
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Soul Summons
|
||||||
|
id=391926
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Soulfire Grand Master
|
||||||
|
id=391927
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Soulflayer
|
||||||
|
id=391928
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Sudden Reclamation
|
||||||
|
id=391929
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Sultai Emissary
|
||||||
|
id=391930
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Sultai Runemark
|
||||||
|
id=391931
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Sultai Skullkeeper
|
||||||
|
id=391932
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Supplant Form
|
||||||
|
id=391933
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Swamp
|
||||||
|
id=391934
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Swiftwater Cliffs
|
||||||
|
id=391936
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Tasigur, the Golden Fang
|
||||||
|
id=391937
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Tasigur's Cruelty
|
||||||
|
id=391938
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Temporal Trespass
|
||||||
|
id=391939
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Temur Battle Rage
|
||||||
|
id=391940
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Temur Runemark
|
||||||
|
id=391941
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Temur Sabertooth
|
||||||
|
id=391942
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Temur War Shaman
|
||||||
|
id=391943
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Thornwood Falls
|
||||||
|
id=391944
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Torrent Elemental
|
||||||
|
id=391945
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Tranquil Cove
|
||||||
|
id=391946
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Typhoid Rats
|
||||||
|
id=391947
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Ugin, the Spirit Dragon
|
||||||
|
id=391948
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Ugin's Construct
|
||||||
|
id=391949
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Valorous Stance
|
||||||
|
id=391950
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Vaultbreaker
|
||||||
|
id=391951
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Wandering Champion
|
||||||
|
id=391952
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=War Flare
|
||||||
|
id=391953
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Warden of the First Tree
|
||||||
|
id=391954
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Wardscale Dragon
|
||||||
|
id=391955
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Whisk Away
|
||||||
|
id=391956
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Whisperer of the Wilds
|
||||||
|
id=391957
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Whisperwood Elemental
|
||||||
|
id=391958
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Wild Slash
|
||||||
|
id=391959
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Wildcall
|
||||||
|
id=391960
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Will of the Naga
|
||||||
|
id=391961
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Winds of Qal Sisma
|
||||||
|
id=391962
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Wind-Scarred Crag
|
||||||
|
id=391963
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Write into Being
|
||||||
|
id=391964
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Yasova Dragonclaw
|
||||||
|
id=391965
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Forest
|
||||||
|
id=391835
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Island
|
||||||
|
id=391860
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Mountain
|
||||||
|
id=391886
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Plains
|
||||||
|
id=391894
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Swamp
|
||||||
|
id=391935
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
@@ -0,0 +1,21 @@
|
|||||||
|
<PACK name="Fate Reforged" type="Booster" pool="all set:FRF;" price="700">
|
||||||
|
<slot copies="1">
|
||||||
|
<random_card>rarity:mythic;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
</slot>
|
||||||
|
<slot copies="3">
|
||||||
|
<random_card>rarity:uncommon;</random_card>
|
||||||
|
</slot>
|
||||||
|
<slot copies="1">
|
||||||
|
<random_card>rarity:special;</random_card>
|
||||||
|
</slot>
|
||||||
|
<slot copies="10">
|
||||||
|
<random_card>rarity:common;</random_card>
|
||||||
|
</slot>
|
||||||
|
</PACK>
|
||||||
@@ -0,0 +1,830 @@
|
|||||||
|
[meta]
|
||||||
|
author=Wagic Team
|
||||||
|
year=2014
|
||||||
|
block=Theros
|
||||||
|
[/meta]
|
||||||
|
[card]
|
||||||
|
primitive=Aegis of the Gods
|
||||||
|
id=380364
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Aerial Formation
|
||||||
|
id=380365
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Agent of Erebos
|
||||||
|
id=380366
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Ajani, Mentor of Heroes
|
||||||
|
id=380367
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Ajani's Presence
|
||||||
|
id=380368
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Akroan Line Breaker
|
||||||
|
id=380369
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Akroan Mastiff
|
||||||
|
id=380370
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Armament of Nyx
|
||||||
|
id=380371
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Armory of Iroas
|
||||||
|
id=380372
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Aspect of Gorgon
|
||||||
|
id=380373
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Athreos, God of Passage
|
||||||
|
id=380374
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Banishing Light
|
||||||
|
id=380375
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Bassara Tower Archer
|
||||||
|
id=380376
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Battlefield Thaumaturge
|
||||||
|
id=380377
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Bearer of the Heavens
|
||||||
|
id=380378
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Bladetusk Boar
|
||||||
|
id=380379
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Blinding Flare
|
||||||
|
id=380380
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Bloodcrazed Hoplite
|
||||||
|
id=380381
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Brain Maggot
|
||||||
|
id=380382
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Cast into Darkness
|
||||||
|
id=380383
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Chariot of Victory
|
||||||
|
id=380384
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Cloaked Siren
|
||||||
|
id=380385
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Colossal Heroics
|
||||||
|
id=380386
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Consign to Dust
|
||||||
|
id=380387
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Countermand
|
||||||
|
id=380388
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Cruel Feeding
|
||||||
|
id=380389
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Crystalline Nautilus
|
||||||
|
id=380390
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Cyclops of Eternal Fury
|
||||||
|
id=380391
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Dakra Mystic
|
||||||
|
id=380392
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Daring Thief
|
||||||
|
id=380393
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Dawnbringer Charioteers
|
||||||
|
id=380394
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Deicide
|
||||||
|
id=380395
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Desecration Plague
|
||||||
|
id=380396
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Deserter's Quarters
|
||||||
|
id=380397
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Desperate Stand
|
||||||
|
id=380398
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Dictate of Erebos
|
||||||
|
id=380399
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Dictate of Heliod
|
||||||
|
id=380400
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Dictate of Karametra
|
||||||
|
id=380401
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Dictate of Kruphix
|
||||||
|
id=380402
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Dictate of the Twin Gods
|
||||||
|
id=380403
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Disciple of Deceit
|
||||||
|
id=380404
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Doomwake Giant
|
||||||
|
id=380405
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Dreadbringer Lampads
|
||||||
|
id=380406
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Eagle of the Watch
|
||||||
|
id=380407
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Eidolon of Blossoms
|
||||||
|
id=380408
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Eidolon of Rhetoric
|
||||||
|
id=380409
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Eidolon of the Great Revel
|
||||||
|
id=380410
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Extinguish All Hope
|
||||||
|
id=380411
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Feast of Dreams
|
||||||
|
id=380412
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Felhide Petrifier
|
||||||
|
id=380413
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Flamespeaker's Will
|
||||||
|
id=380414
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Fleetfeather Cockatrice
|
||||||
|
id=380415
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Flurry of Horns
|
||||||
|
id=380416
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Font of Fertility
|
||||||
|
id=380417
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Font of Fortunes
|
||||||
|
id=380418
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Font of Ire
|
||||||
|
id=380419
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Font of Return
|
||||||
|
id=380420
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Font of Vigor
|
||||||
|
id=380421
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Forgeborn Oreads
|
||||||
|
id=380422
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Gluttonous Cyclops
|
||||||
|
id=380423
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Gnarled Scarhide
|
||||||
|
id=380424
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Godhunter Octopus
|
||||||
|
id=380425
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Godsend
|
||||||
|
id=380426
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Golden Hind
|
||||||
|
id=380427
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Goldenhide Ox
|
||||||
|
id=380428
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Gold-Forged Sentinel
|
||||||
|
id=380429
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Grim Guardian
|
||||||
|
id=380430
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Hall of Triumph
|
||||||
|
id=380431
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Harness by Force
|
||||||
|
id=380432
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Harvestguard Alseids
|
||||||
|
id=380433
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Heroes' Bane
|
||||||
|
id=380434
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Hour of Need
|
||||||
|
id=380435
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Hubris
|
||||||
|
id=380436
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Humbler of Mortals
|
||||||
|
id=380437
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Hydra Broodmaster
|
||||||
|
id=380438
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Hypnotic Siren
|
||||||
|
id=380439
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Interpret the Signs
|
||||||
|
id=380440
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Iroas, God of Victory
|
||||||
|
id=380441
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Keranos, God of Storms
|
||||||
|
id=380442
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=King Macar, the Gold-Cursed
|
||||||
|
id=380443
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Kiora's Dismissal
|
||||||
|
id=380444
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Knowledge and Power
|
||||||
|
id=380445
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Kruphix, God of Horizons
|
||||||
|
id=380446
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Kruphix's Insight
|
||||||
|
id=380447
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Lagonna-Band Trailblazer
|
||||||
|
id=380448
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Launch the Fleet
|
||||||
|
id=380449
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Leonin Iconoclast
|
||||||
|
id=380450
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Lightning Diadem
|
||||||
|
id=380451
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Magma Spray
|
||||||
|
id=380452
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Mana Confluence
|
||||||
|
id=380453
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Market Festival
|
||||||
|
id=380454
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Master of the Feast
|
||||||
|
id=380455
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Mogis's Warhound
|
||||||
|
id=380456
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Mortal Obstinacy
|
||||||
|
id=380457
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Nature's Panoply
|
||||||
|
id=380458
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Nessian Game Warden
|
||||||
|
id=380459
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Nightmarish End
|
||||||
|
id=380460
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Nyx Infusion
|
||||||
|
id=380461
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Nyx Weaver
|
||||||
|
id=380462
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Nyx-Fleece Ram
|
||||||
|
id=380463
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Oakheart Dryads
|
||||||
|
id=380464
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Oppressive Rays
|
||||||
|
id=380465
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Oreskos Swiftclaw
|
||||||
|
id=380466
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Pensive Minotaur
|
||||||
|
id=380467
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Phalanx Formation
|
||||||
|
id=380468
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Pharika, God of Affliction
|
||||||
|
id=380469
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Pharika's Chosen
|
||||||
|
id=380470
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Pheres-Band Thunderhoof
|
||||||
|
id=380471
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Pheres-Band Warchief
|
||||||
|
id=380472
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Pin to the Earth
|
||||||
|
id=380473
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Polymorphous Rush
|
||||||
|
id=380474
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Prophetic Flamespeaker
|
||||||
|
id=380475
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Pull from the Deep
|
||||||
|
id=380476
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Quarry Colossus
|
||||||
|
id=380477
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Ravenous Leucrocota
|
||||||
|
id=380478
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Renowned Weaver
|
||||||
|
id=380479
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Reprisal
|
||||||
|
id=380480
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Returned Reveler
|
||||||
|
id=380481
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Revel of the Fallen God
|
||||||
|
id=380482
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Reviving Melody
|
||||||
|
id=380483
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Riddle of Lightning
|
||||||
|
id=380484
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Riptide Chimera
|
||||||
|
id=380485
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Rise of Eagles
|
||||||
|
id=380486
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Ritual of the Returned
|
||||||
|
id=380487
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Rollick of Abandon
|
||||||
|
id=380488
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Rotted Hulk
|
||||||
|
id=380489
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Rouse the Mob
|
||||||
|
id=380490
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Sage of Hours
|
||||||
|
id=380491
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Satyr Grovedancer
|
||||||
|
id=380492
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Satyr Hoplite
|
||||||
|
id=380493
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Scourge of Fleets
|
||||||
|
id=380494
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Setessan Tactics
|
||||||
|
id=380495
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Sightless Brawler
|
||||||
|
id=380496
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Sigiled Skink
|
||||||
|
id=380497
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Sigiled Starfish
|
||||||
|
id=380498
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Silence the Believers
|
||||||
|
id=380499
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Skybind
|
||||||
|
id=380500
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Skyspear Cavalry
|
||||||
|
id=380501
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Solidarity of Heroes
|
||||||
|
id=380502
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Spawn of Thraxes
|
||||||
|
id=380503
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Spirespine
|
||||||
|
id=380504
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Spite of Mogis
|
||||||
|
id=380505
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Spiteful Blow
|
||||||
|
id=380506
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Squelching Leeches
|
||||||
|
id=380507
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Starfall
|
||||||
|
id=380508
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Stonewise Fortifier
|
||||||
|
id=380509
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Stormchaser Chimera
|
||||||
|
id=380510
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Strength from the Fallen
|
||||||
|
id=380511
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Supply-Line Cranes
|
||||||
|
id=380512
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Swarmborn Giant
|
||||||
|
id=380513
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Temple of Epiphany
|
||||||
|
id=380514
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Temple of Malady
|
||||||
|
id=380515
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Tethmos High Priest
|
||||||
|
id=380516
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Thassa's Devourer
|
||||||
|
id=380517
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Thassa's Ire
|
||||||
|
id=380518
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Thoughtrender Lamia
|
||||||
|
id=380519
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Tormented Thoughts
|
||||||
|
id=380520
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Triton Cavalry
|
||||||
|
id=380521
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Triton Shorestalker
|
||||||
|
id=380522
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Twinflame
|
||||||
|
id=380523
|
||||||
|
rarity=R
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Underworld Coinsmith
|
||||||
|
id=380524
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=War-Wing Siren
|
||||||
|
id=380525
|
||||||
|
rarity=C
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Whitewater Naiads
|
||||||
|
id=380526
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Wildfire Cerberus
|
||||||
|
id=380527
|
||||||
|
rarity=U
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
|
primitive=Worst Fears
|
||||||
|
id=380528
|
||||||
|
rarity=M
|
||||||
|
[/card]
|
||||||
@@ -0,0 +1,21 @@
|
|||||||
|
<PACK name="Journey Into Nyx" type="Booster" pool="all set:JOU;" price="700">
|
||||||
|
<slot copies="1">
|
||||||
|
<random_card>rarity:mythic;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
</slot>
|
||||||
|
<slot copies="3">
|
||||||
|
<random_card>rarity:uncommon;</random_card>
|
||||||
|
</slot>
|
||||||
|
<slot copies="1">
|
||||||
|
<random_card>rarity:special;</random_card>
|
||||||
|
</slot>
|
||||||
|
<slot copies="10">
|
||||||
|
<random_card>rarity:common;</random_card>
|
||||||
|
</slot>
|
||||||
|
</PACK>
|
||||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,21 @@
|
|||||||
|
<PACK name="Khans of Tarkir" type="Booster" pool="all set:KTK;" price="700">
|
||||||
|
<slot copies="1">
|
||||||
|
<random_card>rarity:mythic;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
<random_card>rarity:rare;</random_card>
|
||||||
|
</slot>
|
||||||
|
<slot copies="3">
|
||||||
|
<random_card>rarity:uncommon;</random_card>
|
||||||
|
</slot>
|
||||||
|
<slot copies="1">
|
||||||
|
<random_card>rarity:special;</random_card>
|
||||||
|
</slot>
|
||||||
|
<slot copies="10">
|
||||||
|
<random_card>rarity:common;</random_card>
|
||||||
|
</slot>
|
||||||
|
</PACK>
|
||||||
@@ -1513,8 +1513,3 @@ primitive=Zephyr Net
|
|||||||
id=142357
|
id=142357
|
||||||
rarity=C
|
rarity=C
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
|
||||||
primitive=Avatar Token
|
|
||||||
id=-140233
|
|
||||||
rarity=T
|
|
||||||
[/card]
|
|
||||||
|
|||||||
@@ -11,7 +11,7 @@ rarity=C
|
|||||||
[card]
|
[card]
|
||||||
primitive=Accorder's Shield
|
primitive=Accorder's Shield
|
||||||
id=370581
|
id=370581
|
||||||
rarity=C
|
rarity=U
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Accursed Spirit
|
primitive=Accursed Spirit
|
||||||
@@ -31,7 +31,7 @@ rarity=C
|
|||||||
[card]
|
[card]
|
||||||
primitive=Air Servant
|
primitive=Air Servant
|
||||||
id=370688
|
id=370688
|
||||||
rarity=C
|
rarity=U
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Ajani, Caller of the Pride
|
primitive=Ajani, Caller of the Pride
|
||||||
@@ -121,7 +121,7 @@ rarity=C
|
|||||||
[card]
|
[card]
|
||||||
primitive=Blur Sliver
|
primitive=Blur Sliver
|
||||||
id=370593
|
id=370593
|
||||||
rarity=U
|
rarity=C
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Bogbrew Witch
|
primitive=Bogbrew Witch
|
||||||
@@ -156,7 +156,7 @@ rarity=C
|
|||||||
[card]
|
[card]
|
||||||
primitive=Bubbling Cauldron
|
primitive=Bubbling Cauldron
|
||||||
id=370661
|
id=370661
|
||||||
rarity=R
|
rarity=U
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Burning Earth
|
primitive=Burning Earth
|
||||||
@@ -261,7 +261,7 @@ rarity=R
|
|||||||
[card]
|
[card]
|
||||||
primitive=Darksteel Forge
|
primitive=Darksteel Forge
|
||||||
id=370734
|
id=370734
|
||||||
rarity=R
|
rarity=M
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Darksteel Ingot
|
primitive=Darksteel Ingot
|
||||||
@@ -326,7 +326,7 @@ rarity=R
|
|||||||
[card]
|
[card]
|
||||||
primitive=Doom Blade
|
primitive=Doom Blade
|
||||||
id=370609
|
id=370609
|
||||||
rarity=C
|
rarity=U
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Door of Destinies
|
primitive=Door of Destinies
|
||||||
@@ -339,6 +339,11 @@ id=370660
|
|||||||
rarity=U
|
rarity=U
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
|
primitive=Dragon Egg Dragon
|
||||||
|
id=-370660
|
||||||
|
rarity=T
|
||||||
|
[/card]
|
||||||
|
[card]
|
||||||
primitive=Dragon Hatchling
|
primitive=Dragon Hatchling
|
||||||
id=370717
|
id=370717
|
||||||
rarity=C
|
rarity=C
|
||||||
@@ -431,7 +436,7 @@ rarity=C
|
|||||||
[card]
|
[card]
|
||||||
primitive=Fortify
|
primitive=Fortify
|
||||||
id=370712
|
id=370712
|
||||||
rarity=U
|
rarity=C
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Frost Breath
|
primitive=Frost Breath
|
||||||
@@ -581,7 +586,7 @@ rarity=R
|
|||||||
[card]
|
[card]
|
||||||
primitive=Kalonian Hydra
|
primitive=Kalonian Hydra
|
||||||
id=370766
|
id=370766
|
||||||
rarity=R
|
rarity=M
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Kalonian Tusker
|
primitive=Kalonian Tusker
|
||||||
@@ -591,7 +596,7 @@ rarity=U
|
|||||||
[card]
|
[card]
|
||||||
primitive=Lava Axe
|
primitive=Lava Axe
|
||||||
id=370595
|
id=370595
|
||||||
rarity=
|
rarity=C
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Lay of the Land
|
primitive=Lay of the Land
|
||||||
@@ -619,8 +624,8 @@ id=370740
|
|||||||
rarity=R
|
rarity=R
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Zombie Token
|
primitive=Liliana's Reaver Zombie
|
||||||
id=-339967
|
id=-370740
|
||||||
rarity=T
|
rarity=T
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
@@ -736,7 +741,7 @@ rarity=R
|
|||||||
[card]
|
[card]
|
||||||
primitive=Nightwing Shade
|
primitive=Nightwing Shade
|
||||||
id=370705
|
id=370705
|
||||||
rarity=U
|
rarity=C
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Oath of the Ancient Wood
|
primitive=Oath of the Ancient Wood
|
||||||
@@ -831,7 +836,7 @@ rarity=R
|
|||||||
[card]
|
[card]
|
||||||
primitive=Quag Sickness
|
primitive=Quag Sickness
|
||||||
id=370714
|
id=370714
|
||||||
rarity=U
|
rarity=C
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Quicken
|
primitive=Quicken
|
||||||
@@ -846,7 +851,7 @@ rarity=C
|
|||||||
[card]
|
[card]
|
||||||
primitive=Ratchet Bomb
|
primitive=Ratchet Bomb
|
||||||
id=370623
|
id=370623
|
||||||
rarity=C
|
rarity=R
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Regathan Firecat
|
primitive=Regathan Firecat
|
||||||
@@ -896,7 +901,7 @@ rarity=R
|
|||||||
[card]
|
[card]
|
||||||
primitive=Scourge of Valkas
|
primitive=Scourge of Valkas
|
||||||
id=370584
|
id=370584
|
||||||
rarity=R
|
rarity=M
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Scroll Thief
|
primitive=Scroll Thief
|
||||||
@@ -951,7 +956,7 @@ rarity=M
|
|||||||
[card]
|
[card]
|
||||||
primitive=Shimmering Grotto
|
primitive=Shimmering Grotto
|
||||||
id=370631
|
id=370631
|
||||||
rarity=C
|
rarity=U
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Shivan Dragon
|
primitive=Shivan Dragon
|
||||||
@@ -1031,6 +1036,7 @@ rarity=U
|
|||||||
[card]
|
[card]
|
||||||
primitive=Staff of the Mind Magus
|
primitive=Staff of the Mind Magus
|
||||||
id=370676
|
id=370676
|
||||||
|
rarity=U
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Staff of the Wild Magus
|
primitive=Staff of the Wild Magus
|
||||||
@@ -1105,7 +1111,7 @@ rarity=R
|
|||||||
[card]
|
[card]
|
||||||
primitive=Thunder Strike
|
primitive=Thunder Strike
|
||||||
id=370607
|
id=370607
|
||||||
rarity=U
|
rarity=C
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Tidebinder Mage
|
primitive=Tidebinder Mage
|
||||||
@@ -1115,7 +1121,7 @@ rarity=R
|
|||||||
[card]
|
[card]
|
||||||
primitive=Time Ebb
|
primitive=Time Ebb
|
||||||
id=370641
|
id=370641
|
||||||
rarity=R
|
rarity=C
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Tome Scour
|
primitive=Tome Scour
|
||||||
@@ -1215,7 +1221,7 @@ rarity=R
|
|||||||
[card]
|
[card]
|
||||||
primitive=Windreader Sphinx
|
primitive=Windreader Sphinx
|
||||||
id=370810
|
id=370810
|
||||||
rarity=U
|
rarity=M
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Windstorm
|
primitive=Windstorm
|
||||||
@@ -1243,8 +1249,8 @@ id=370619
|
|||||||
rarity=R
|
rarity=R
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
primitive=Zombie Token
|
primitive=Xathrid Necromancer Zombie
|
||||||
id=-339968
|
id=-370619
|
||||||
rarity=T
|
rarity=T
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
|
|||||||
@@ -86,17 +86,6 @@ mana={5}{U}
|
|||||||
type=Sorcery
|
type=Sorcery
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
name=Gravecrawler
|
|
||||||
abilities=cantblock
|
|
||||||
autograveyard=aslongas(zombie|myBattlefield) {B}:name(cast from graveyard) activate name(cast from graveyard) castcard(normal) assorcery
|
|
||||||
text=Gravecrawler can't block. -- You may cast Gravecrawler from your graveyard as long as you control a Zombie.
|
|
||||||
mana={B}
|
|
||||||
type=Creature
|
|
||||||
subtype=Zombie
|
|
||||||
power=2
|
|
||||||
toughness=1
|
|
||||||
[/card]
|
|
||||||
[card]
|
|
||||||
name=Ivy Seer
|
name=Ivy Seer
|
||||||
auto={2}{G}{T}:foreach(*[green]|myhand) 1/1 target(creature)
|
auto={2}{G}{T}:foreach(*[green]|myhand) 1/1 target(creature)
|
||||||
text={2}{G}, {T}: Reveal any number of green cards in your hand. Target creature gets +X/+X until end of turn, where X is the number of cards revealed this way.
|
text={2}{G}, {T}: Reveal any number of green cards in your hand. Target creature gets +X/+X until end of turn, where X is the number of cards revealed this way.
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@@ -4149,15 +4149,6 @@ mana={U}{U}
|
|||||||
type=Sorcery
|
type=Sorcery
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
name=Draining Whelk
|
|
||||||
text=Flash (You may cast this spell any time you could cast an instant.) -- Flying -- When Draining Whelk enters the battlefield, counter target spell. Put X +1/+1 counters on Draining Whelk, where X is that spell's converted mana cost.
|
|
||||||
mana={4}{U}{U}
|
|
||||||
type=Creature
|
|
||||||
subtype=Illusion
|
|
||||||
power=1
|
|
||||||
toughness=1
|
|
||||||
[/card]
|
|
||||||
[card]
|
|
||||||
name=Drake Umbra
|
name=Drake Umbra
|
||||||
mana={4}{U}
|
mana={4}{U}
|
||||||
type=Enchantment
|
type=Enchantment
|
||||||
@@ -7045,16 +7036,6 @@ mana={2}{G}
|
|||||||
type=Enchantment
|
type=Enchantment
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
name=Heartlash Cinder
|
|
||||||
abilities=haste
|
|
||||||
text=Haste -- Chroma - When Heartlash Cinder enters the battlefield, it gets +X/+0 until end of turn, where X is the number of red mana symbols in the mana costs of permanents you control.
|
|
||||||
mana={1}{R}
|
|
||||||
type=Creature
|
|
||||||
subtype=Elemental Warrior
|
|
||||||
power=1
|
|
||||||
toughness=1
|
|
||||||
[/card]
|
|
||||||
[card]
|
|
||||||
name=Heartstone
|
name=Heartstone
|
||||||
text=Activated abilities of creatures cost {1} less to activate. This effect can't reduce the amount of mana an ability costs to activate to less than one mana.
|
text=Activated abilities of creatures cost {1} less to activate. This effect can't reduce the amount of mana an ability costs to activate to less than one mana.
|
||||||
mana={3}
|
mana={3}
|
||||||
@@ -7686,12 +7667,6 @@ type=Instant
|
|||||||
text=As an additional cost to cast Induce Despair, reveal a creature card from your hand. Target creature gets -X/-X until end of turn, where X is the revealed card's converted mana cost.
|
text=As an additional cost to cast Induce Despair, reveal a creature card from your hand. Target creature gets -X/-X until end of turn, where X is the revealed card's converted mana cost.
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
name=Induce Paranoia
|
|
||||||
text=Counter target spell. If {B} was spent to cast Induce Paranoia, that spell's controller puts the top X cards of his or her library into his or her graveyard, where X is the spell's converted mana cost.
|
|
||||||
mana={2}{U}{U}
|
|
||||||
type=Instant
|
|
||||||
[/card]
|
|
||||||
[card]
|
|
||||||
name=Inescapable Brute
|
name=Inescapable Brute
|
||||||
text=Wither (This deals damage to creatures in the form of -1/-1 counters.) -- Inescapable Brute must be blocked if able.
|
text=Wither (This deals damage to creatures in the form of -1/-1 counters.) -- Inescapable Brute must be blocked if able.
|
||||||
mana={5}{R}
|
mana={5}{R}
|
||||||
@@ -11490,15 +11465,6 @@ mana={X}{R}
|
|||||||
type=Instant
|
type=Instant
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
name=Outrage Shaman
|
|
||||||
text=Chroma - When Outrage Shaman enters the battlefield, it deals damage to target creature equal to the number of red mana symbols in the mana costs of permanents you control.
|
|
||||||
mana={3}{R}{R}
|
|
||||||
type=Creature
|
|
||||||
subtype=Goblin Shaman
|
|
||||||
power=2
|
|
||||||
toughness=2
|
|
||||||
[/card]
|
|
||||||
[card]
|
|
||||||
name=Outrider en-Kor
|
name=Outrider en-Kor
|
||||||
text=Flanking (Whenever a creature without flanking blocks this creature, the blocking creature gets -1/-1 until end of turn.) -- {0}: The next 1 damage that would be dealt to Outrider en-Kor this turn is dealt to target creature you control instead.
|
text=Flanking (Whenever a creature without flanking blocks this creature, the blocking creature gets -1/-1 until end of turn.) -- {0}: The next 1 damage that would be dealt to Outrider en-Kor this turn is dealt to target creature you control instead.
|
||||||
mana={2}{W}
|
mana={2}{W}
|
||||||
@@ -12350,15 +12316,6 @@ power=2
|
|||||||
toughness=2
|
toughness=2
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
name=Primalcrux
|
|
||||||
text=Trample -- Chroma - Primalcrux's power and toughness are each equal to the number of green mana symbols in the mana costs of permanents you control.
|
|
||||||
mana={G}{G}{G}{G}{G}{G}
|
|
||||||
type=Creature
|
|
||||||
subtype=Elemental
|
|
||||||
power=*
|
|
||||||
toughness=*
|
|
||||||
[/card]
|
|
||||||
[card]
|
|
||||||
name=Primitive Etchings
|
name=Primitive Etchings
|
||||||
text=Reveal the first card you draw each turn. Whenever you reveal a creature card this way, draw a card.
|
text=Reveal the first card you draw each turn. Whenever you reveal a creature card this way, draw a card.
|
||||||
mana={2}{G}{G}
|
mana={2}{G}{G}
|
||||||
@@ -12905,13 +12862,6 @@ mana={R}{R}
|
|||||||
type=Enchantment
|
type=Enchantment
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
name=Ral Zarek
|
|
||||||
text=+1: Tap target permanent, then untap another target permanent. -- -2: Ral Zarek deals 3 damage to target creature or player. -- -7: Flip five coins. Take an extra turn after this one for each coin that comes up heads.
|
|
||||||
mana={2}{U}{R}
|
|
||||||
type=Planeswalker
|
|
||||||
subtype=Ral
|
|
||||||
[/card]
|
|
||||||
[card]
|
|
||||||
name=Raiding Party
|
name=Raiding Party
|
||||||
text=Raiding Party can't be the target of white spells or abilities from white sources. -- Sacrifice an Orc: Each player may tap any number of untapped white creatures he or she controls. For each creature tapped this way, that player chooses up to two Plains. Then destroy all Plains that weren't chosen this way by any player.
|
text=Raiding Party can't be the target of white spells or abilities from white sources. -- Sacrifice an Orc: Each player may tap any number of untapped white creatures he or she controls. For each creature tapped this way, that player chooses up to two Plains. Then destroy all Plains that weren't chosen this way by any player.
|
||||||
mana={2}{R}
|
mana={2}{R}
|
||||||
@@ -14541,12 +14491,6 @@ mana={W}
|
|||||||
type=Enchantment
|
type=Enchantment
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
name=Serum Powder
|
|
||||||
text={T}: Add {1} to your mana pool. -- Any time you could mulligan and Serum Powder is in your hand, you may exile all the cards from your hand, then draw that many cards. (You can do this in addition to taking mulligans.)
|
|
||||||
mana={3}
|
|
||||||
type=Artifact
|
|
||||||
[/card]
|
|
||||||
[card]
|
|
||||||
name=Serum Visions
|
name=Serum Visions
|
||||||
text=Draw a card. -- Scry 2. (To scry 2, look at the top two cards of your library, then put any number of them on the bottom of your library and the rest on top in any order.)
|
text=Draw a card. -- Scry 2. (To scry 2, look at the top two cards of your library, then put any number of them on the bottom of your library and the rest on top in any order.)
|
||||||
mana={U}
|
mana={U}
|
||||||
@@ -15830,15 +15774,6 @@ text={T}: Add {1} to your mana pool. -- {4}, {T}: Put a 0/1 white Goat creature
|
|||||||
type=Land
|
type=Land
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
name=Springjack Shepherd
|
|
||||||
text=Chroma - When Springjack Shepherd enters the battlefield, put a 0/1 white Goat creature token onto the battlefield for each white mana symbol in the mana costs of permanents you control.
|
|
||||||
mana={3}{W}
|
|
||||||
type=Creature
|
|
||||||
subtype=Kithkin Wizard
|
|
||||||
power=1
|
|
||||||
toughness=2
|
|
||||||
[/card]
|
|
||||||
[card]
|
|
||||||
name=Sprout Swarm
|
name=Sprout Swarm
|
||||||
text=Convoke (Each creature you tap while casting this spell reduces its total cost by {1} or by one mana of that creature's color.) -- Buyback {3} (You may pay an additional {3} as you cast this spell. If you do, put this card into your hand as it resolves.) -- Put a 1/1 green Saproling creature token onto the battlefield.
|
text=Convoke (Each creature you tap while casting this spell reduces its total cost by {1} or by one mana of that creature's color.) -- Buyback {3} (You may pay an additional {3} as you cast this spell. If you do, put this card into your hand as it resolves.) -- Put a 1/1 green Saproling creature token onto the battlefield.
|
||||||
mana={1}{G}
|
mana={1}{G}
|
||||||
@@ -17631,15 +17566,6 @@ toughness=2
|
|||||||
text=Auras attached to permanents you control have totem armor. (If an enchanted permanent you control would be destroyed, instead remove all damage from it and destroy an Aura attached to it.)
|
text=Auras attached to permanents you control have totem armor. (If an enchanted permanent you control would be destroyed, instead remove all damage from it and destroy an Aura attached to it.)
|
||||||
[/card]
|
[/card]
|
||||||
[card]
|
[card]
|
||||||
name=Umbra Stalker
|
|
||||||
text=Chroma - Umbra Stalker's power and toughness are each equal to the number of black mana symbols in the mana costs of cards in your graveyard.
|
|
||||||
mana={4}{B}{B}{B}
|
|
||||||
type=Creature
|
|
||||||
subtype=Elemental
|
|
||||||
power=*
|
|
||||||
toughness=*
|
|
||||||
[/card]
|
|
||||||
[card]
|
|
||||||
name=Unblinking Bleb
|
name=Unblinking Bleb
|
||||||
text=Morph {2}{U} (You may cast this face down as a 2/2 creature for {3}. Turn it face up any time for its morph cost.) -- Whenever Unblinking Bleb or another permanent is turned face up, you may scry 2. (To scry 2, look at the top two cards of your library, then put any number of them on the bottom of your library and the rest on top in any order.)
|
text=Morph {2}{U} (You may cast this face down as a 2/2 creature for {3}. Turn it face up any time for its morph cost.) -- Whenever Unblinking Bleb or another permanent is turned face up, you may scry 2. (To scry 2, look at the top two cards of your library, then put any number of them on the bottom of your library and the rest on top in any order.)
|
||||||
mana={3}{U}
|
mana={3}{U}
|
||||||
|
|||||||
@@ -345,6 +345,7 @@ foratog.txt
|
|||||||
force_of_nature.txt
|
force_of_nature.txt
|
||||||
force_of_nature2.txt
|
force_of_nature2.txt
|
||||||
force_of_nature3.txt
|
force_of_nature3.txt
|
||||||
|
formidable.txt
|
||||||
fountain_of_youth.txt
|
fountain_of_youth.txt
|
||||||
Frogmite.txt
|
Frogmite.txt
|
||||||
fungus_sliver.txt
|
fungus_sliver.txt
|
||||||
@@ -661,6 +662,8 @@ tidal_warrior_i649.txt
|
|||||||
tidal_warrior_i652.txt
|
tidal_warrior_i652.txt
|
||||||
Timely_Reinforcements.txt
|
Timely_Reinforcements.txt
|
||||||
titanic_ultimatum.txt
|
titanic_ultimatum.txt
|
||||||
|
tokenizer.txt
|
||||||
|
tokenizer2.txt
|
||||||
torture.txt
|
torture.txt
|
||||||
tranquil_domain.txt
|
tranquil_domain.txt
|
||||||
turn_to_slag.txt
|
turn_to_slag.txt
|
||||||
@@ -714,4 +717,5 @@ momir/overcost.txt
|
|||||||
#AI Tests
|
#AI Tests
|
||||||
########################
|
########################
|
||||||
ai/goblin_artillery.txt
|
ai/goblin_artillery.txt
|
||||||
ai/proliferate_simple.txt
|
#I don’t understand why this test works, and it breaks the redo, so I deactivate it.
|
||||||
|
#ai/proliferate_simple.txt
|
||||||
|
|||||||
@@ -0,0 +1,33 @@
|
|||||||
|
#Testing Atarka Beastbreaker,Stampeding Elk Herd -- Formidable
|
||||||
|
#Atarka Beastbreaker will become 6/6, and then attacks along with Stampeding Elk Herd, trample effect will trigger
|
||||||
|
#then p2 will block with Steel Wall, p2 must have 13 life...
|
||||||
|
[INIT]
|
||||||
|
COMBATATTACKERS
|
||||||
|
[PLAYER1]
|
||||||
|
inplay:Atarka Beastbreaker,Krosan Tusker,Stampeding Elk Herd
|
||||||
|
manapool:{4}{G}
|
||||||
|
[PLAYER2]
|
||||||
|
inplay:Steel Wall
|
||||||
|
life:20
|
||||||
|
[DO]
|
||||||
|
Atarka Beastbreaker
|
||||||
|
choice 1
|
||||||
|
Atarka Beastbreaker
|
||||||
|
Stampeding Elk Herd
|
||||||
|
next
|
||||||
|
Steel Wall
|
||||||
|
#blockers
|
||||||
|
next
|
||||||
|
#combatdamage 2
|
||||||
|
next
|
||||||
|
next
|
||||||
|
#endofcombat 2
|
||||||
|
[ASSERT]
|
||||||
|
COMBATEND
|
||||||
|
[PLAYER1]
|
||||||
|
inplay:Atarka Beastbreaker,Krosan Tusker,Stampeding Elk Herd
|
||||||
|
manapool:{0}
|
||||||
|
[PLAYER2]
|
||||||
|
graveyard:Steel Wall
|
||||||
|
life:13
|
||||||
|
[END]
|
||||||
@@ -0,0 +1,29 @@
|
|||||||
|
# Testing Tokenizer - Parallel Lives (ISD) 249662
|
||||||
|
# Dragon Fodder (ALA) 174936
|
||||||
|
# text=Put two 1/1 red Goblin creature tokens into play.
|
||||||
|
# Tokens must be 2.. since there are no tokenizer.
|
||||||
|
[INIT]
|
||||||
|
FIRSTMAIN
|
||||||
|
[PLAYER1]
|
||||||
|
hand:174936
|
||||||
|
manapool:{R}{1}
|
||||||
|
inplay:249662
|
||||||
|
[PLAYER2]
|
||||||
|
hand:Demystify
|
||||||
|
manapool:{W}
|
||||||
|
[DO]
|
||||||
|
174936
|
||||||
|
no
|
||||||
|
yes
|
||||||
|
Demystify
|
||||||
|
249662
|
||||||
|
endinterruption
|
||||||
|
[ASSERT]
|
||||||
|
FIRSTMAIN
|
||||||
|
[PLAYER1]
|
||||||
|
graveyard:249662,174936
|
||||||
|
inplay:-174936,-174936
|
||||||
|
[PLAYER2]
|
||||||
|
graveyard:Demystify
|
||||||
|
life:20
|
||||||
|
[END]
|
||||||
@@ -0,0 +1,27 @@
|
|||||||
|
# Testing Tokenizer - Parallel Lives (ISD) 249662
|
||||||
|
# Dragon Fodder (ALA) 174936
|
||||||
|
# text=Put two 1/1 red Goblin creature tokens into play.
|
||||||
|
# Tokens must be 8.. since there are two tokenizer... original value
|
||||||
|
# is 2 with first tokenizer it will become 4, with the second tokenizer
|
||||||
|
# the value will be 8...
|
||||||
|
[INIT]
|
||||||
|
FIRSTMAIN
|
||||||
|
[PLAYER1]
|
||||||
|
hand:174936
|
||||||
|
manapool:{R}{1}
|
||||||
|
inplay:249662,249662
|
||||||
|
[PLAYER2]
|
||||||
|
inplay:plains
|
||||||
|
hand:Demystify
|
||||||
|
[DO]
|
||||||
|
174936
|
||||||
|
[ASSERT]
|
||||||
|
FIRSTMAIN
|
||||||
|
[PLAYER1]
|
||||||
|
graveyard:174936
|
||||||
|
inplay:249662,249662,-174936,-174936,-174936,-174936,-174936,-174936,-174936,-174936
|
||||||
|
[PLAYER2]
|
||||||
|
hand:Demystify
|
||||||
|
inplay:plains
|
||||||
|
life:20
|
||||||
|
[END]
|
||||||
@@ -12,6 +12,8 @@ using std::vector;
|
|||||||
class ManaCost;
|
class ManaCost;
|
||||||
class MTGAbility;
|
class MTGAbility;
|
||||||
|
|
||||||
|
namespace AI {
|
||||||
|
|
||||||
class AIHint
|
class AIHint
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
@@ -66,4 +68,6 @@ public:
|
|||||||
~AIHints();
|
~AIHints();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -3,6 +3,8 @@
|
|||||||
|
|
||||||
#include "AIPlayerBaka.h"
|
#include "AIPlayerBaka.h"
|
||||||
|
|
||||||
|
namespace AI {
|
||||||
|
|
||||||
class AIMomirPlayer: public AIPlayerBaka
|
class AIMomirPlayer: public AIPlayerBaka
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
@@ -14,4 +16,6 @@ public:
|
|||||||
MTGAbility * getMomirAbility();
|
MTGAbility * getMomirAbility();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -18,20 +18,44 @@
|
|||||||
#include "Player.h"
|
#include "Player.h"
|
||||||
#include "config.h"
|
#include "config.h"
|
||||||
|
|
||||||
|
#include <vector>
|
||||||
#include <queue>
|
#include <queue>
|
||||||
using std::queue;
|
using std::queue;
|
||||||
|
using std::vector;
|
||||||
|
|
||||||
|
|
||||||
|
namespace AI {
|
||||||
|
|
||||||
class AIStats;
|
class AIStats;
|
||||||
class AIPlayer;
|
class AIPlayer;
|
||||||
|
|
||||||
|
|
||||||
|
class Action
|
||||||
|
{
|
||||||
|
protected:
|
||||||
|
GameObserver* m_pObserver;
|
||||||
|
bool parseLine(const string& s);
|
||||||
|
|
||||||
|
public:
|
||||||
|
Action(GameObserver* g, const string& s) : m_pObserver(g)
|
||||||
|
{
|
||||||
|
parseLine(s);
|
||||||
|
};
|
||||||
|
|
||||||
|
friend ostream& operator<<(ostream&, const Action&);
|
||||||
|
friend istream& operator>>(istream&, Action&);
|
||||||
|
};
|
||||||
|
|
||||||
class AIAction
|
class AIAction
|
||||||
{
|
{
|
||||||
|
protected:
|
||||||
|
int clickMultiAct(vector<Targetable*>&actionTargets);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
AIPlayer * owner;
|
AIPlayer * owner;
|
||||||
MTGAbility * ability;
|
MTGAbility * ability;
|
||||||
NestedAbility * nability;
|
|
||||||
Player * player;
|
Player * player;
|
||||||
int id;
|
// int id;
|
||||||
MTGCardInstance * click;
|
MTGCardInstance * click;
|
||||||
MTGCardInstance * target; // TODO Improve
|
MTGCardInstance * target; // TODO Improve
|
||||||
vector<Targetable*>mAbilityTargets;
|
vector<Targetable*>mAbilityTargets;
|
||||||
@@ -60,7 +84,10 @@ public:
|
|||||||
{
|
{
|
||||||
};
|
};
|
||||||
int Act();
|
int Act();
|
||||||
int clickMultiAct(vector<Targetable*>&actionTargets);
|
ostream& logSimpleAct(ostream& out, MTGCardInstance* click) const;
|
||||||
|
ostream& logMultiAct(ostream& out, const vector<Targetable *> &actionTargets) const;
|
||||||
|
|
||||||
|
friend ostream& operator<<(ostream& out, const AIAction& a);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
@@ -77,8 +104,20 @@ protected:
|
|||||||
int clickMultiTarget(TargetChooser * tc,vector<Targetable*>&potentialTargets);
|
int clickMultiTarget(TargetChooser * tc,vector<Targetable*>&potentialTargets);
|
||||||
int clickSingleTarget(TargetChooser * tc,vector<Targetable*>&potentialTargets, MTGCardInstance * Choosencard = NULL);
|
int clickSingleTarget(TargetChooser * tc,vector<Targetable*>&potentialTargets, MTGCardInstance * Choosencard = NULL);
|
||||||
RandomGenerator randomGenerator;
|
RandomGenerator randomGenerator;
|
||||||
|
virtual bool canFirstStrikeKill(MTGCardInstance * card, MTGCardInstance *ennemy);
|
||||||
|
virtual bool canPlay(MTGCardInstance * card);
|
||||||
|
virtual int getCreaturesInfo(Player * player, int neededInfo = INFO_NBCREATURES , int untapMode = 0, int canAttack = 0);
|
||||||
|
|
||||||
|
virtual int createAbilityPotentialsActions(MTGAbility * a, MTGCardInstance * c, vector<AIAction>& actions);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
enum {
|
||||||
|
INFO_NBCREATURES,
|
||||||
|
INFO_CREATURESPOWER,
|
||||||
|
INFO_CREATURESRANK,
|
||||||
|
INFO_CREATURESTOUGHNESS,
|
||||||
|
INFO_CREATURESATTACKINGPOWER
|
||||||
|
};
|
||||||
|
|
||||||
//These variables are used by TestSuite and Rules.cpp... TODO change that?
|
//These variables are used by TestSuite and Rules.cpp... TODO change that?
|
||||||
int agressivity;
|
int agressivity;
|
||||||
@@ -89,7 +128,7 @@ public:
|
|||||||
virtual int receiveEvent(WEvent * event);
|
virtual int receiveEvent(WEvent * event);
|
||||||
virtual void Render();
|
virtual void Render();
|
||||||
|
|
||||||
AIPlayer(GameObserver *observer, string deckFile, string deckFileSmall, MTGDeck * deck = NULL);
|
AIPlayer(GameObserver *observer, string deckFile, string deckFileSmall, string avatarFile, MTGDeck * deck = NULL);
|
||||||
virtual ~AIPlayer();
|
virtual ~AIPlayer();
|
||||||
|
|
||||||
virtual int chooseTarget(TargetChooser * tc = NULL, Player * forceTarget = NULL, MTGCardInstance * Chosencard = NULL, bool checkonly = false) = 0;
|
virtual int chooseTarget(TargetChooser * tc = NULL, Player * forceTarget = NULL, MTGCardInstance * Chosencard = NULL, bool checkonly = false) = 0;
|
||||||
@@ -116,5 +155,6 @@ class AIPlayerFactory{
|
|||||||
#endif
|
#endif
|
||||||
};
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -4,6 +4,8 @@
|
|||||||
#include "AIPlayer.h"
|
#include "AIPlayer.h"
|
||||||
#include "AllAbilities.h"
|
#include "AllAbilities.h"
|
||||||
|
|
||||||
|
namespace AI {
|
||||||
|
|
||||||
class AIStats;
|
class AIStats;
|
||||||
class AIHints;
|
class AIHints;
|
||||||
class AIHint;
|
class AIHint;
|
||||||
@@ -57,7 +59,7 @@ public:
|
|||||||
OrderedAIAction* a2Ptr = const_cast<OrderedAIAction*>(&a2);
|
OrderedAIAction* a2Ptr = const_cast<OrderedAIAction*>(&a2);
|
||||||
int e1 = a1Ptr->getEfficiency();
|
int e1 = a1Ptr->getEfficiency();
|
||||||
int e2 = a2Ptr->getEfficiency();
|
int e2 = a2Ptr->getEfficiency();
|
||||||
if (e1 == e2) return a1Ptr->id < a2Ptr->id;
|
// if (e1 == e2) return a1Ptr->id < a2Ptr->id;
|
||||||
return (e1 > e2);
|
return (e1 > e2);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
@@ -72,7 +74,7 @@ class AIPlayerBaka: public AIPlayer{
|
|||||||
virtual int interruptIfICan();
|
virtual int interruptIfICan();
|
||||||
virtual int chooseAttackers();
|
virtual int chooseAttackers();
|
||||||
virtual int chooseBlockers();
|
virtual int chooseBlockers();
|
||||||
virtual int canFirstStrikeKill(MTGCardInstance * card, MTGCardInstance *ennemy);
|
virtual bool canFirstStrikeKill(MTGCardInstance * card, MTGCardInstance *ennemy);
|
||||||
virtual int effectBadOrGood(MTGCardInstance * card, int mode = MODE_PUTINTOPLAY, TargetChooser * tc = NULL);
|
virtual int effectBadOrGood(MTGCardInstance * card, int mode = MODE_PUTINTOPLAY, TargetChooser * tc = NULL);
|
||||||
|
|
||||||
|
|
||||||
@@ -105,19 +107,10 @@ class AIPlayerBaka: public AIPlayer{
|
|||||||
virtual int getEfficiency(OrderedAIAction * action);
|
virtual int getEfficiency(OrderedAIAction * action);
|
||||||
virtual int getEfficiency(MTGAbility * ability);
|
virtual int getEfficiency(MTGAbility * ability);
|
||||||
virtual bool payTheManaCost(ManaCost * cost, MTGCardInstance * card = NULL,vector<MTGAbility*> gotPayment = vector<MTGAbility*>());
|
virtual bool payTheManaCost(ManaCost * cost, MTGCardInstance * card = NULL,vector<MTGAbility*> gotPayment = vector<MTGAbility*>());
|
||||||
virtual int getCreaturesInfo(Player * player, int neededInfo = INFO_NBCREATURES , int untapMode = 0, int canAttack = 0);
|
|
||||||
virtual ManaCost * getPotentialMana(MTGCardInstance * card = NULL);
|
virtual ManaCost * getPotentialMana(MTGCardInstance * card = NULL);
|
||||||
virtual int selectAbility();
|
virtual int selectAbility();
|
||||||
|
|
||||||
public:
|
public:
|
||||||
enum {
|
|
||||||
INFO_NBCREATURES,
|
|
||||||
INFO_CREATURESPOWER,
|
|
||||||
INFO_CREATURESRANK,
|
|
||||||
INFO_CREATURESTOUGHNESS,
|
|
||||||
INFO_CREATURESATTACKINGPOWER
|
|
||||||
};
|
|
||||||
|
|
||||||
vector<MTGAbility*>gotPayments;
|
vector<MTGAbility*>gotPayments;
|
||||||
|
|
||||||
AIPlayerBaka(GameObserver *observer, string deckFile, string deckfileSmall, string avatarFile, MTGDeck * deck = NULL);
|
AIPlayerBaka(GameObserver *observer, string deckFile, string deckfileSmall, string avatarFile, MTGDeck * deck = NULL);
|
||||||
@@ -137,4 +130,5 @@ class AIPlayerBaka: public AIPlayer{
|
|||||||
virtual int createAbilityTargets(MTGAbility * a, MTGCardInstance * c, RankingContainer& ranking);
|
virtual int createAbilityTargets(MTGAbility * a, MTGCardInstance * c, RankingContainer& ranking);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -11,6 +11,8 @@ class AIStats;
|
|||||||
class AIHints;
|
class AIHints;
|
||||||
|
|
||||||
|
|
||||||
|
namespace AI {
|
||||||
|
|
||||||
class AIPlayerBakaB: public AIPlayerBaka{
|
class AIPlayerBakaB: public AIPlayerBaka{
|
||||||
protected:
|
protected:
|
||||||
int orderBlockers();
|
int orderBlockers();
|
||||||
@@ -18,7 +20,7 @@ protected:
|
|||||||
int interruptIfICan();
|
int interruptIfICan();
|
||||||
int chooseAttackers();
|
int chooseAttackers();
|
||||||
int chooseBlockers();
|
int chooseBlockers();
|
||||||
int canFirstStrikeKill(MTGCardInstance * card, MTGCardInstance *ennemy);
|
bool canFirstStrikeKill(MTGCardInstance * card, MTGCardInstance *ennemy);
|
||||||
int effectBadOrGood(MTGCardInstance * card, int mode = MODE_PUTINTOPLAY, TargetChooser * tc = NULL);
|
int effectBadOrGood(MTGCardInstance * card, int mode = MODE_PUTINTOPLAY, TargetChooser * tc = NULL);
|
||||||
|
|
||||||
|
|
||||||
@@ -61,6 +63,8 @@ protected:
|
|||||||
int createAbilityTargets(MTGAbility * a, MTGCardInstance * c, RankingContainer& ranking);
|
int createAbilityTargets(MTGAbility * a, MTGCardInstance * c, RankingContainer& ranking);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -0,0 +1,34 @@
|
|||||||
|
/*
|
||||||
|
* Wagic, The Homebrew ?! is licensed under the BSD license
|
||||||
|
* See LICENSE in the Folder's root
|
||||||
|
* http://wololo.net/wagic/
|
||||||
|
|
||||||
|
AIPlayerMinMax is the MinMax implementation of the AIPlayer interface
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _IAPLAYER_MINMAX_H
|
||||||
|
#define _IAPLAYER_MINMAX_H
|
||||||
|
|
||||||
|
#include "AIPlayer.h"
|
||||||
|
#include "config.h"
|
||||||
|
|
||||||
|
namespace AI {
|
||||||
|
|
||||||
|
class AIPlayerMinMax: public AIPlayer{
|
||||||
|
|
||||||
|
protected:
|
||||||
|
void LookAround();
|
||||||
|
|
||||||
|
public:
|
||||||
|
AIPlayerMinMax(GameObserver *observer, string deckFile, string deckFileSmall, string avatarFile, MTGDeck * deck = NULL);
|
||||||
|
virtual ~AIPlayerMinMax();
|
||||||
|
|
||||||
|
virtual int chooseTarget(TargetChooser * tc = NULL, Player * forceTarget = NULL, MTGCardInstance * Chosencard = NULL, bool checkonly = false) = 0;
|
||||||
|
virtual int affectCombatDamages(CombatStep) = 0;
|
||||||
|
virtual int Act(float dt) = 0;
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
@@ -18,6 +18,8 @@ class MTGCard;
|
|||||||
class Damage;
|
class Damage;
|
||||||
class WEvent;
|
class WEvent;
|
||||||
|
|
||||||
|
namespace AI {
|
||||||
|
|
||||||
class AIStat
|
class AIStat
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
@@ -49,4 +51,6 @@ public:
|
|||||||
void Render();
|
void Render();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -204,7 +204,6 @@ protected:
|
|||||||
JQuadPtr pspIcons[8];
|
JQuadPtr pspIcons[8];
|
||||||
InterruptDecision interruptDecision[2];
|
InterruptDecision interruptDecision[2];
|
||||||
float timer;
|
float timer;
|
||||||
int currentState;
|
|
||||||
ActionStackMode mode;
|
ActionStackMode mode;
|
||||||
int checked;
|
int checked;
|
||||||
ATutorialMessage* currentTutorial;
|
ATutorialMessage* currentTutorial;
|
||||||
@@ -224,7 +223,7 @@ public:
|
|||||||
int getNextIndex(Interruptible * previous, int type = 0, int state = 0 , int display = -1);
|
int getNextIndex(Interruptible * previous, int type = 0, int state = 0 , int display = -1);
|
||||||
void Fizzle(Interruptible * action, FizzleMode fizzleMode = PUT_IN_GRAVEARD);
|
void Fizzle(Interruptible * action, FizzleMode fizzleMode = PUT_IN_GRAVEARD);
|
||||||
Interruptible * getAt(int id);
|
Interruptible * getAt(int id);
|
||||||
void cancelInterruptOffer(InterruptDecision cancelMode = DONT_INTERRUPT, bool log = true);
|
void cancelInterruptOffer(Player* p = 0, InterruptDecision cancelMode = DONT_INTERRUPT, bool log = true);
|
||||||
void endOfInterruption(bool log = true);
|
void endOfInterruption(bool log = true);
|
||||||
Interruptible * getLatest(int state);
|
Interruptible * getLatest(int state);
|
||||||
Player * askIfWishesToInterrupt;
|
Player * askIfWishesToInterrupt;
|
||||||
@@ -251,7 +250,9 @@ public:
|
|||||||
#endif
|
#endif
|
||||||
void setCurrentTutorial(ATutorialMessage* message) {currentTutorial = message;};
|
void setCurrentTutorial(ATutorialMessage* message) {currentTutorial = message;};
|
||||||
ATutorialMessage* getCurrentTutorial() {return currentTutorial;};
|
ATutorialMessage* getCurrentTutorial() {return currentTutorial;};
|
||||||
bool isCalm() {return interruptDecision[0] == NOT_DECIDED && interruptDecision[1] == NOT_DECIDED;};
|
bool isNotUndecided() {
|
||||||
|
return (interruptDecision[0] == NOT_DECIDED && interruptDecision[1] == NOT_DECIDED);
|
||||||
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -183,10 +183,10 @@ private:
|
|||||||
for (int k = 0; k < 4; k++)
|
for (int k = 0; k < 4; k++)
|
||||||
{
|
{
|
||||||
MTGGameZone * zone = dzones[k];
|
MTGGameZone * zone = dzones[k];
|
||||||
if (dtc->targetsZone(zone, card))
|
if (dtc->targetsZone(zone, card)&&dp == card->controller())
|
||||||
{
|
{
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 2);
|
intValue += zone->countDevotion(dtc, 2);
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 5);
|
intValue += zone->countDevotion(dtc, 5);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -203,10 +203,10 @@ private:
|
|||||||
for (int k = 0; k < 4; k++)
|
for (int k = 0; k < 4; k++)
|
||||||
{
|
{
|
||||||
MTGGameZone * zone = dzones[k];
|
MTGGameZone * zone = dzones[k];
|
||||||
if (dtc->targetsZone(zone, card))
|
if (dtc->targetsZone(zone, card)&&dp == card->controller())
|
||||||
{
|
{
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 3);
|
intValue += zone->countDevotion(dtc, 3);
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 5);
|
intValue += zone->countDevotion(dtc, 5);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -223,10 +223,10 @@ private:
|
|||||||
for (int k = 0; k < 4; k++)
|
for (int k = 0; k < 4; k++)
|
||||||
{
|
{
|
||||||
MTGGameZone * zone = dzones[k];
|
MTGGameZone * zone = dzones[k];
|
||||||
if (dtc->targetsZone(zone, card))
|
if (dtc->targetsZone(zone, card)&&dp == card->controller())
|
||||||
{
|
{
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 2);
|
intValue += zone->countDevotion(dtc, 2);
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 4);
|
intValue += zone->countDevotion(dtc, 4);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -243,10 +243,10 @@ private:
|
|||||||
for (int k = 0; k < 4; k++)
|
for (int k = 0; k < 4; k++)
|
||||||
{
|
{
|
||||||
MTGGameZone * zone = dzones[k];
|
MTGGameZone * zone = dzones[k];
|
||||||
if (dtc->targetsZone(zone, card))
|
if (dtc->targetsZone(zone, card)&&dp == card->controller())
|
||||||
{
|
{
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 1);
|
intValue += zone->countDevotion(dtc, 1);
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 4);
|
intValue += zone->countDevotion(dtc, 4);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -263,10 +263,10 @@ private:
|
|||||||
for (int k = 0; k < 4; k++)
|
for (int k = 0; k < 4; k++)
|
||||||
{
|
{
|
||||||
MTGGameZone * zone = dzones[k];
|
MTGGameZone * zone = dzones[k];
|
||||||
if (dtc->targetsZone(zone, card))
|
if (dtc->targetsZone(zone, card)&&dp == card->controller())
|
||||||
{
|
{
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 1);
|
intValue += zone->countDevotion(dtc, 1);
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 3);
|
intValue += zone->countDevotion(dtc, 3);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -283,10 +283,10 @@ private:
|
|||||||
for (int k = 0; k < 4; k++)
|
for (int k = 0; k < 4; k++)
|
||||||
{
|
{
|
||||||
MTGGameZone * zone = dzones[k];
|
MTGGameZone * zone = dzones[k];
|
||||||
if (dtc->targetsZone(zone, card))
|
if (dtc->targetsZone(zone, card)&&dp == card->controller())
|
||||||
{
|
{
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 2);
|
intValue += zone->countDevotion(dtc, 2);
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 3);
|
intValue += zone->countDevotion(dtc, 3);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -303,10 +303,10 @@ private:
|
|||||||
for (int k = 0; k < 4; k++)
|
for (int k = 0; k < 4; k++)
|
||||||
{
|
{
|
||||||
MTGGameZone * zone = dzones[k];
|
MTGGameZone * zone = dzones[k];
|
||||||
if (dtc->targetsZone(zone, card))
|
if (dtc->targetsZone(zone, card)&&dp == card->controller())
|
||||||
{
|
{
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 4);
|
intValue += zone->countDevotion(dtc, 4);
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 5);
|
intValue += zone->countDevotion(dtc, 5);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -323,10 +323,10 @@ private:
|
|||||||
for (int k = 0; k < 4; k++)
|
for (int k = 0; k < 4; k++)
|
||||||
{
|
{
|
||||||
MTGGameZone * zone = dzones[k];
|
MTGGameZone * zone = dzones[k];
|
||||||
if (dtc->targetsZone(zone, card))
|
if (dtc->targetsZone(zone, card)&&dp == card->controller())
|
||||||
{
|
{
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 3);
|
intValue += zone->countDevotion(dtc, 3);
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 4);
|
intValue += zone->countDevotion(dtc, 4);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -343,10 +343,10 @@ private:
|
|||||||
for (int k = 0; k < 4; k++)
|
for (int k = 0; k < 4; k++)
|
||||||
{
|
{
|
||||||
MTGGameZone * zone = dzones[k];
|
MTGGameZone * zone = dzones[k];
|
||||||
if (dtc->targetsZone(zone, card))
|
if (dtc->targetsZone(zone, card)&&dp == card->controller())
|
||||||
{
|
{
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 1);
|
intValue += zone->countDevotion(dtc, 1);
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 5);
|
intValue += zone->countDevotion(dtc, 5);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -363,10 +363,10 @@ private:
|
|||||||
for (int k = 0; k < 4; k++)
|
for (int k = 0; k < 4; k++)
|
||||||
{
|
{
|
||||||
MTGGameZone * zone = dzones[k];
|
MTGGameZone * zone = dzones[k];
|
||||||
if (dtc->targetsZone(zone, card))
|
if (dtc->targetsZone(zone, card)&&dp == card->controller())
|
||||||
{
|
{
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 1);
|
intValue += zone->countDevotion(dtc, 1);
|
||||||
intValue += zone->countTotalManaSymbols(dtc, 2);
|
intValue += zone->countDevotion(dtc, 2);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -635,6 +635,17 @@ private:
|
|||||||
{
|
{
|
||||||
intValue = target->controller()->opponent()->game->hand->nb_cards;
|
intValue = target->controller()->opponent()->game->hand->nb_cards;
|
||||||
}
|
}
|
||||||
|
else if (s == "powertotalinplay")//Count Total Power of Creatures you control... Formidable
|
||||||
|
{
|
||||||
|
intValue = 0;
|
||||||
|
for (int j = card->controller()->game->inPlay->nb_cards - 1; j >= 0; --j)
|
||||||
|
{
|
||||||
|
if (card->controller()->game->inPlay->cards[j]->hasType(Subtypes::TYPE_CREATURE))
|
||||||
|
{
|
||||||
|
intValue += card->controller()->game->inPlay->cards[j]->power;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
intValue = atoi(s.c_str());
|
intValue = atoi(s.c_str());
|
||||||
@@ -3129,7 +3140,7 @@ public:
|
|||||||
SAFE_DELETE(NewPow);
|
SAFE_DELETE(NewPow);
|
||||||
SAFE_DELETE(NewTou);
|
SAFE_DELETE(NewTou);
|
||||||
}
|
}
|
||||||
for (int i = 0; i < multiplier->getValue(); ++i)
|
for (int i = 0; i < Tokenizer(); ++i)
|
||||||
{
|
{
|
||||||
//MTGCardInstance * myToken;
|
//MTGCardInstance * myToken;
|
||||||
if (tokenId)
|
if (tokenId)
|
||||||
@@ -3188,6 +3199,23 @@ public:
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int Tokenizer()//tokenizer
|
||||||
|
{
|
||||||
|
int tokenize = 1;
|
||||||
|
if (source->controller()->game->battlefield->hasAbility(Constants::TOKENIZER))
|
||||||
|
{
|
||||||
|
int nbcards = source->controller()->game->battlefield->nb_cards;
|
||||||
|
for (int j = 0; j < nbcards; j++)
|
||||||
|
{
|
||||||
|
if (source->controller()->game->battlefield->cards[j]->has(Constants::TOKENIZER))
|
||||||
|
tokenize *= 2;
|
||||||
|
}
|
||||||
|
return multiplier->getValue()*tokenize;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
return multiplier->getValue();
|
||||||
|
}
|
||||||
|
|
||||||
void setTokenOwner()
|
void setTokenOwner()
|
||||||
{
|
{
|
||||||
switch(who)
|
switch(who)
|
||||||
@@ -5529,6 +5557,17 @@ public:
|
|||||||
AAShuffle * clone() const;
|
AAShuffle * clone() const;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
//Mulligan
|
||||||
|
class AAMulligan: public ActivatedAbilityTP
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
AAMulligan(GameObserver* observer, int _id, MTGCardInstance * card, Targetable * _target, ManaCost * _cost = NULL, int who =
|
||||||
|
TargetChooser::UNSET);
|
||||||
|
int resolve();
|
||||||
|
const string getMenuText();
|
||||||
|
AAMulligan * clone() const;
|
||||||
|
};
|
||||||
|
|
||||||
//Remove Mana From ManaPool
|
//Remove Mana From ManaPool
|
||||||
class AARemoveMana: public ActivatedAbilityTP
|
class AARemoveMana: public ActivatedAbilityTP
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -52,7 +52,6 @@ class GameObserver{
|
|||||||
string startupGameSerialized;
|
string startupGameSerialized;
|
||||||
bool parseLine(const string& s);
|
bool parseLine(const string& s);
|
||||||
virtual void logAction(const string& s);
|
virtual void logAction(const string& s);
|
||||||
bool processAction(const string& s);
|
|
||||||
bool processActions(bool undo
|
bool processActions(bool undo
|
||||||
#ifdef TESTSUITE
|
#ifdef TESTSUITE
|
||||||
, TestSuiteGame* testgame
|
, TestSuiteGame* testgame
|
||||||
@@ -69,6 +68,7 @@ class GameObserver{
|
|||||||
);
|
);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
bool processAction(const string& s);
|
||||||
int currentPlayerId;
|
int currentPlayerId;
|
||||||
CombatStep combatStep;
|
CombatStep combatStep;
|
||||||
int turn;
|
int turn;
|
||||||
@@ -78,7 +78,7 @@ class GameObserver{
|
|||||||
vector<list<Phase*> >gameTurn;
|
vector<list<Phase*> >gameTurn;
|
||||||
int cancelCurrentAction();
|
int cancelCurrentAction();
|
||||||
ExtraCosts * mExtraPayment;
|
ExtraCosts * mExtraPayment;
|
||||||
int oldGamePhase;
|
GamePhase oldGamePhase;
|
||||||
TargetChooser * targetChooser;
|
TargetChooser * targetChooser;
|
||||||
DuelLayers * mLayers;
|
DuelLayers * mLayers;
|
||||||
ReplacementEffects *replacementEffects;
|
ReplacementEffects *replacementEffects;
|
||||||
@@ -111,6 +111,7 @@ class GameObserver{
|
|||||||
void loadPlayer(int playerId, PlayerType playerType = PLAYER_TYPE_HUMAN, int decknb=0, bool premadeDeck=false);
|
void loadPlayer(int playerId, PlayerType playerType = PLAYER_TYPE_HUMAN, int decknb=0, bool premadeDeck=false);
|
||||||
virtual void loadPlayer(int playerId, Player* player);
|
virtual void loadPlayer(int playerId, Player* player);
|
||||||
|
|
||||||
|
int getPlayerId(Player* player) {if(player == players[0]) return 1; else if(player == players[1]) return 2; else return 0;};
|
||||||
Player * currentPlayer;
|
Player * currentPlayer;
|
||||||
Player * currentActionPlayer;
|
Player * currentActionPlayer;
|
||||||
Player * isInterrupting;
|
Player * isInterrupting;
|
||||||
@@ -138,6 +139,7 @@ class GameObserver{
|
|||||||
int receiveEvent(WEvent * event);
|
int receiveEvent(WEvent * event);
|
||||||
bool connectRule;
|
bool connectRule;
|
||||||
|
|
||||||
|
void logActionMomir(MTGCardInstance * card_to_discard, int cardId);
|
||||||
void logAction(Player* player, const string& s="");
|
void logAction(Player* player, const string& s="");
|
||||||
void logAction(int playerId, const string& s="") {
|
void logAction(int playerId, const string& s="") {
|
||||||
logAction(players[playerId], s);
|
logAction(players[playerId], s);
|
||||||
@@ -151,6 +153,7 @@ class GameObserver{
|
|||||||
bool undo();
|
bool undo();
|
||||||
bool isLoading(){ return mLoading; };
|
bool isLoading(){ return mLoading; };
|
||||||
void Mulligan(Player* player = NULL);
|
void Mulligan(Player* player = NULL);
|
||||||
|
void serumMulligan(Player* player = NULL);
|
||||||
Player* getPlayer(size_t index) { return players[index];};
|
Player* getPlayer(size_t index) { return players[index];};
|
||||||
bool isStarted() { return (mLayers!=NULL);};
|
bool isStarted() { return (mLayers!=NULL);};
|
||||||
RandomGenerator* getRandomGenerator() { return &randomGenerator; };
|
RandomGenerator* getRandomGenerator() { return &randomGenerator; };
|
||||||
|
|||||||
@@ -219,7 +219,8 @@ class Constants
|
|||||||
LURE = 101,
|
LURE = 101,
|
||||||
NOLEGEND = 102,
|
NOLEGEND = 102,
|
||||||
CANPLAYFROMGRAVEYARD = 103,
|
CANPLAYFROMGRAVEYARD = 103,
|
||||||
NB_BASIC_ABILITIES = 104,
|
TOKENIZER = 104,
|
||||||
|
NB_BASIC_ABILITIES = 105,
|
||||||
|
|
||||||
|
|
||||||
RARITY_S = 'S', //Special Rarity
|
RARITY_S = 'S', //Special Rarity
|
||||||
|
|||||||
@@ -98,6 +98,7 @@ class MTGGameZone {
|
|||||||
unsigned int countByType(const string &value);
|
unsigned int countByType(const string &value);
|
||||||
unsigned int countByCanTarget(TargetChooser * tc);
|
unsigned int countByCanTarget(TargetChooser * tc);
|
||||||
unsigned int countTotalManaSymbols(TargetChooser * tc, int color);
|
unsigned int countTotalManaSymbols(TargetChooser * tc, int color);
|
||||||
|
unsigned int countDevotion(TargetChooser * tc, int color); //devotion for gods
|
||||||
MTGCardInstance * findByName(string name);
|
MTGCardInstance * findByName(string name);
|
||||||
|
|
||||||
//returns true if one of the cards in the zone has the ability
|
//returns true if one of the cards in the zone has the ability
|
||||||
|
|||||||
@@ -99,6 +99,7 @@ public:
|
|||||||
string toString();
|
string toString();
|
||||||
int getCost(int color);
|
int getCost(int color);
|
||||||
int getManaSymbols(int color);
|
int getManaSymbols(int color);
|
||||||
|
int getManaSymbolsHybridMerged(int color);
|
||||||
|
|
||||||
//Returns NULL if i is greater than nbhybrids
|
//Returns NULL if i is greater than nbhybrids
|
||||||
ManaCostHybrid * getHybridCost(unsigned int i);
|
ManaCostHybrid * getHybridCost(unsigned int i);
|
||||||
|
|||||||
@@ -19,6 +19,7 @@ public:
|
|||||||
string toString();
|
string toString();
|
||||||
int getConvertedCost();
|
int getConvertedCost();
|
||||||
int getManaSymbols(int color);
|
int getManaSymbols(int color);
|
||||||
|
int getManaSymbolsHybridMerged(int color);
|
||||||
|
|
||||||
friend std::ostream& operator<<(std::ostream& out, ManaCostHybrid& m);
|
friend std::ostream& operator<<(std::ostream& out, ManaCostHybrid& m);
|
||||||
friend std::ostream& operator<<(std::ostream& out, ManaCostHybrid* m);
|
friend std::ostream& operator<<(std::ostream& out, ManaCostHybrid* m);
|
||||||
|
|||||||
@@ -68,6 +68,7 @@ public:
|
|||||||
MTGInPlay * inPlay();
|
MTGInPlay * inPlay();
|
||||||
ManaPool * getManaPool();
|
ManaPool * getManaPool();
|
||||||
void takeMulligan();
|
void takeMulligan();
|
||||||
|
void serumMulligan();
|
||||||
ManaCost * doesntEmpty;
|
ManaCost * doesntEmpty;
|
||||||
ManaCost * poolDoesntEmpty;
|
ManaCost * poolDoesntEmpty;
|
||||||
void cleanupPhase();
|
void cleanupPhase();
|
||||||
|
|||||||
@@ -114,7 +114,7 @@ public:
|
|||||||
int run();
|
int run();
|
||||||
};
|
};
|
||||||
|
|
||||||
class TestSuiteAI:public AIPlayerBaka
|
class TestSuiteAI:public AI::AIPlayerBaka
|
||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
MTGCardInstance * getCard(string action);
|
MTGCardInstance * getCard(string action);
|
||||||
|
|||||||
@@ -234,7 +234,7 @@ public:
|
|||||||
WCFilterSet(string arg);
|
WCFilterSet(string arg);
|
||||||
bool isMatch(MTGCard *c)
|
bool isMatch(MTGCard *c)
|
||||||
{
|
{
|
||||||
return (setid == MTGSets::ALL_SETS || c->setId == setid);
|
return (setid == MTGSets::ALL_SETS || c->setId == setid) && (c->getRarity() != Constants::RARITY_T); //removes viewing of card tokens. tokens will not display on spoiler and should not affect gameplay :)
|
||||||
}
|
}
|
||||||
;
|
;
|
||||||
string getCode();
|
string getCode();
|
||||||
|
|||||||
@@ -7,6 +7,8 @@
|
|||||||
|
|
||||||
#include <sstream>
|
#include <sstream>
|
||||||
|
|
||||||
|
namespace AI {
|
||||||
|
|
||||||
AIHint::AIHint(string _line)
|
AIHint::AIHint(string _line)
|
||||||
{
|
{
|
||||||
string line = _line;
|
string line = _line;
|
||||||
@@ -582,3 +584,5 @@ AIAction * AIHints::suggestAbility(ManaCost * potentialMana)
|
|||||||
}
|
}
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
};
|
||||||
|
|||||||
@@ -6,6 +6,8 @@
|
|||||||
#include "AIStats.h"
|
#include "AIStats.h"
|
||||||
#include "AllAbilities.h"
|
#include "AllAbilities.h"
|
||||||
|
|
||||||
|
namespace AI {
|
||||||
|
|
||||||
AIMomirPlayer::AIMomirPlayer(GameObserver *observer, string file, string fileSmall, string avatarFile, MTGDeck * deck) :
|
AIMomirPlayer::AIMomirPlayer(GameObserver *observer, string file, string fileSmall, string avatarFile, MTGDeck * deck) :
|
||||||
AIPlayerBaka(observer, file, fileSmall, avatarFile, deck)
|
AIPlayerBaka(observer, file, fileSmall, avatarFile, deck)
|
||||||
{
|
{
|
||||||
@@ -128,3 +130,4 @@ int AIMomirPlayer::computeActions()
|
|||||||
return AIPlayerBaka::computeActions();
|
return AIPlayerBaka::computeActions();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
};
|
||||||
|
|||||||
@@ -13,11 +13,36 @@
|
|||||||
#include "AIPlayerBakaB.h"
|
#include "AIPlayerBakaB.h"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
namespace AI {
|
||||||
|
|
||||||
|
|
||||||
|
bool Action::parseLine(const string& s)
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
ostream& operator<<(ostream& out, const Action&)
|
||||||
|
{
|
||||||
|
return out;
|
||||||
|
}
|
||||||
|
|
||||||
|
istream& operator>>(istream& in, Action& a)
|
||||||
|
{
|
||||||
|
string s;
|
||||||
|
|
||||||
|
while(std::getline(in, s))
|
||||||
|
{
|
||||||
|
if(!a.parseLine(s))
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return in;
|
||||||
|
}
|
||||||
|
|
||||||
int AIPlayer::totalAIDecks = -1;
|
int AIPlayer::totalAIDecks = -1;
|
||||||
|
|
||||||
const char * const MTG_LAND_TEXTS[] = { "artifact", "forest", "island", "mountain", "swamp", "plains", "other lands" };
|
|
||||||
|
|
||||||
AIAction::AIAction(AIPlayer * owner, MTGCardInstance * c, MTGCardInstance * t)
|
AIAction::AIAction(AIPlayer * owner, MTGCardInstance * c, MTGCardInstance * t)
|
||||||
: owner(owner), ability(NULL), player(NULL), click(c), target(t)
|
: owner(owner), ability(NULL), player(NULL), click(c), target(t)
|
||||||
{
|
{
|
||||||
@@ -42,6 +67,51 @@ AIAction::AIAction(AIPlayer * owner, MTGCardInstance * c, MTGCardInstance * t)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ostream& operator<<(ostream& out, const AIAction& a)
|
||||||
|
{
|
||||||
|
do {
|
||||||
|
if (a.player && !a.playerAbilityTarget)
|
||||||
|
{
|
||||||
|
out << "p" + (a.owner->getObserver()->getPlayerId(a.player) + 1) << endl;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (a.ability)
|
||||||
|
{
|
||||||
|
a.logSimpleAct(out, a.click);
|
||||||
|
// we're ignoring ability and we shouldn't
|
||||||
|
if (a.target && !a.mAbilityTargets.size())
|
||||||
|
{
|
||||||
|
a.logSimpleAct(out, a.target);
|
||||||
|
// sounds broken if target is a player ... or not, it's the following case
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
else if(a.playerAbilityTarget && !a.mAbilityTargets.size())
|
||||||
|
{
|
||||||
|
out << "p" + (a.owner->getObserver()->getPlayerId((Player*)a.playerAbilityTarget) + 1) << endl;
|
||||||
|
// with this log we're losing what player clicked on who ... which is bad.
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if(a.mAbilityTargets.size())
|
||||||
|
{
|
||||||
|
a.logMultiAct(out, a.mAbilityTargets);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if(a.mAbilityTargets.size())
|
||||||
|
{
|
||||||
|
a.logMultiAct(out, a.mAbilityTargets);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
else if (a.click)
|
||||||
|
{ //Shouldn't be used, really...
|
||||||
|
assert(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
} while(0);
|
||||||
|
|
||||||
|
return out;
|
||||||
|
}
|
||||||
|
|
||||||
int AIAction::Act()
|
int AIAction::Act()
|
||||||
{
|
{
|
||||||
GameObserver * g = owner->getObserver();
|
GameObserver * g = owner->getObserver();
|
||||||
@@ -82,6 +152,46 @@ int AIAction::Act()
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ostream& AIAction::logSimpleAct(ostream& out, MTGCardInstance* click) const
|
||||||
|
{
|
||||||
|
string currentPlayer = "p" + (owner->getObserver()->getPlayerId(owner) + 1);
|
||||||
|
out << currentPlayer << click->currentZone->getName() << "[" << click->currentZone->getIndex(click) << "]" << endl;
|
||||||
|
return out;
|
||||||
|
}
|
||||||
|
|
||||||
|
ostream& AIAction::logMultiAct(ostream& out, const vector<Targetable*>& actionTargets) const
|
||||||
|
{
|
||||||
|
GameObserver * g = owner->getObserver();
|
||||||
|
TargetChooser * tc = g->getCurrentTargetChooser();
|
||||||
|
do {
|
||||||
|
if(!tc) break;
|
||||||
|
vector<Targetable*>::const_iterator ite = actionTargets.begin();
|
||||||
|
while(ite != actionTargets.end())
|
||||||
|
{
|
||||||
|
MTGCardInstance * card = ((MTGCardInstance *) (*ite));
|
||||||
|
if(card == (MTGCardInstance*)tc->source)//click source first.
|
||||||
|
{
|
||||||
|
logSimpleAct(out, card);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
++ite;
|
||||||
|
}
|
||||||
|
|
||||||
|
// this is just wrong, but at least it should compile
|
||||||
|
for(int k = 0 ;k < int(actionTargets.size()) && k < tc->maxtargets; k++)
|
||||||
|
{
|
||||||
|
if (MTGCardInstance * card = dynamic_cast<MTGCardInstance *>(actionTargets[k]))
|
||||||
|
{
|
||||||
|
if(k+1 == int(actionTargets.size()))
|
||||||
|
tc->done = true;
|
||||||
|
logSimpleAct(out, card);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
tc->attemptsToFill++;
|
||||||
|
} while (0);
|
||||||
|
return out;
|
||||||
|
}
|
||||||
|
|
||||||
int AIAction::clickMultiAct(vector<Targetable*>& actionTargets)
|
int AIAction::clickMultiAct(vector<Targetable*>& actionTargets)
|
||||||
{
|
{
|
||||||
GameObserver * g = owner->getObserver();
|
GameObserver * g = owner->getObserver();
|
||||||
@@ -116,7 +226,7 @@ int AIAction::clickMultiAct(vector<Targetable*>& actionTargets)
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
AIPlayer::AIPlayer(GameObserver *observer, string file, string fileSmall, MTGDeck * deck) :
|
AIPlayer::AIPlayer(GameObserver *observer, string file, string fileSmall, string avatarFile, MTGDeck * deck) :
|
||||||
Player(observer, file, fileSmall, deck)
|
Player(observer, file, fileSmall, deck)
|
||||||
{
|
{
|
||||||
agressivity = 50;
|
agressivity = 50;
|
||||||
@@ -124,6 +234,33 @@ AIPlayer::AIPlayer(GameObserver *observer, string file, string fileSmall, MTGDec
|
|||||||
playMode = Player::MODE_AI;
|
playMode = Player::MODE_AI;
|
||||||
mFastTimerMode = false;
|
mFastTimerMode = false;
|
||||||
|
|
||||||
|
if(avatarFile != "")
|
||||||
|
{
|
||||||
|
if(!loadAvatar(avatarFile, "bakaAvatar"))
|
||||||
|
{
|
||||||
|
avatarFile = "baka.jpg";
|
||||||
|
loadAvatar(avatarFile, "bakaAvatar");
|
||||||
|
}
|
||||||
|
mAvatarName = avatarFile;
|
||||||
|
}
|
||||||
|
else //load a random avatar.
|
||||||
|
{
|
||||||
|
avatarFile = "avatar";
|
||||||
|
char buffer[3];
|
||||||
|
sprintf(buffer, "%i", int(observer->getRandomGenerator()->random()%100));
|
||||||
|
avatarFile.append(buffer);
|
||||||
|
avatarFile.append(".jpg");
|
||||||
|
if(!loadAvatar(avatarFile, "bakaAvatar"))
|
||||||
|
{
|
||||||
|
avatarFile = "baka.jpg";
|
||||||
|
loadAvatar(avatarFile, "bakaAvatar");
|
||||||
|
}
|
||||||
|
mAvatarName = avatarFile;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (fileSmall == "ai_baka_eviltwin")
|
||||||
|
mAvatar->SetHFlip(true);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
AIPlayer::~AIPlayer()
|
AIPlayer::~AIPlayer()
|
||||||
@@ -372,3 +509,151 @@ void AIPlayer::invalidateTotalAIDecks()
|
|||||||
totalAIDecks = -1;
|
totalAIDecks = -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool AIPlayer::canFirstStrikeKill(MTGCardInstance * card, MTGCardInstance *ennemy)
|
||||||
|
{
|
||||||
|
if (ennemy->has(Constants::FIRSTSTRIKE) || ennemy->has(Constants::DOUBLESTRIKE))
|
||||||
|
return false;
|
||||||
|
if (!(card->has(Constants::FIRSTSTRIKE) || card->has(Constants::DOUBLESTRIKE)))
|
||||||
|
return false;
|
||||||
|
if (!(card->power >= ennemy->toughness))
|
||||||
|
return false;
|
||||||
|
if (!(card->power >= ennemy->toughness + 1) && ennemy->has(Constants::FLANKING))
|
||||||
|
return false;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool AIPlayer::canPlay(MTGCardInstance * card)
|
||||||
|
{
|
||||||
|
if (card->hasType(Subtypes::TYPE_LAND))
|
||||||
|
{
|
||||||
|
if (game->playRestrictions->canPutIntoZone(card, game->inPlay) == PlayRestriction::CANT_PLAY)
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (game->playRestrictions->canPutIntoZone(card, game->stack) == PlayRestriction::CANT_PLAY)
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (!manaPool->canAfford(card->getManaCost()))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
int AIPlayer::getCreaturesInfo(Player * player, int neededInfo, int untapMode, int canAttack)
|
||||||
|
{
|
||||||
|
int result = 0;
|
||||||
|
CardDescriptor cd;
|
||||||
|
cd.init();
|
||||||
|
cd.setType("Creature");
|
||||||
|
cd.unsecureSetTapped(untapMode);
|
||||||
|
MTGCardInstance * card = NULL;
|
||||||
|
while ((card = cd.nextmatch(player->game->inPlay, card)))
|
||||||
|
{
|
||||||
|
if (!canAttack || card->canAttack())
|
||||||
|
{
|
||||||
|
if (neededInfo == INFO_NBCREATURES)
|
||||||
|
{
|
||||||
|
result++;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
result += card->power;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
int AIPlayer::createAbilityPotentialsActions(MTGAbility * a, MTGCardInstance * c, vector<AIAction>& actions)
|
||||||
|
{
|
||||||
|
if (!a->getActionTc())
|
||||||
|
{
|
||||||
|
AIAction aiAction(this, a, c, NULL);
|
||||||
|
actions.push_back(aiAction);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
vector<Targetable*>potentialTargets;
|
||||||
|
for (int i = 0; i < 2; i++)
|
||||||
|
{
|
||||||
|
Player * p = observer->players[i];
|
||||||
|
MTGGameZone * playerZones[] = { p->game->graveyard, p->game->library, p->game->hand, p->game->inPlay,p->game->stack };
|
||||||
|
// try player first
|
||||||
|
if(a->getActionTc()->canTarget((Targetable*)p))
|
||||||
|
{
|
||||||
|
if(a->getActionTc()->maxtargets == 1)
|
||||||
|
{
|
||||||
|
AIAction aiAction(this, a, p, c);
|
||||||
|
actions.push_back(aiAction);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
potentialTargets.push_back(p);
|
||||||
|
}
|
||||||
|
for (int j = 0; j < 5; j++)
|
||||||
|
{
|
||||||
|
MTGGameZone * zone = playerZones[j];
|
||||||
|
for (int k = 0; k < zone->nb_cards; k++)
|
||||||
|
{
|
||||||
|
MTGCardInstance * t = zone->cards[k];
|
||||||
|
if (a->getActionTc()->canTarget(t))
|
||||||
|
{
|
||||||
|
if(a->getActionTc()->maxtargets == 1)
|
||||||
|
{
|
||||||
|
AIAction aiAction(this, a, c, t);
|
||||||
|
actions.push_back(aiAction);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
potentialTargets.push_back(t);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
vector<Targetable*>realTargets;
|
||||||
|
if(a->getActionTc()->maxtargets != 1)
|
||||||
|
{
|
||||||
|
if(a->getActionTc()->getNbTargets() && a->getActionTc()->attemptsToFill > 4)
|
||||||
|
{
|
||||||
|
a->getActionTc()->done = true;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
while(potentialTargets.size())
|
||||||
|
{
|
||||||
|
AIAction * check = NULL;
|
||||||
|
|
||||||
|
Player * pTargeting = 0;
|
||||||
|
MTGCardInstance * cTargeting = dynamic_cast<MTGCardInstance*>(potentialTargets[0]);
|
||||||
|
if(cTargeting)
|
||||||
|
{
|
||||||
|
check = NEW AIAction(this, a,c,cTargeting);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
pTargeting = dynamic_cast<Player*>(potentialTargets[0]);
|
||||||
|
if(pTargeting)
|
||||||
|
check = NEW AIAction(this, a,pTargeting,c);
|
||||||
|
}
|
||||||
|
|
||||||
|
if(check && pTargeting)
|
||||||
|
{
|
||||||
|
AIAction aiAction(this, a,pTargeting,c);
|
||||||
|
actions.push_back(aiAction);
|
||||||
|
}
|
||||||
|
if(check)
|
||||||
|
realTargets.push_back(potentialTargets[0]);
|
||||||
|
potentialTargets.erase(potentialTargets.begin());
|
||||||
|
SAFE_DELETE(check);
|
||||||
|
}
|
||||||
|
if(!realTargets.size() || (int(realTargets.size()) < a->getActionTc()->maxtargets && a->getActionTc()->targetMin))
|
||||||
|
return 0;
|
||||||
|
AIAction aiAction(this, a, c,realTargets);
|
||||||
|
aiAction.target = dynamic_cast<MTGCardInstance*>(realTargets[0]);
|
||||||
|
aiAction.playerAbilityTarget = dynamic_cast<Player*>(realTargets[0]);
|
||||||
|
actions.push_back(aiAction);
|
||||||
|
}
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|||||||
@@ -14,6 +14,7 @@
|
|||||||
// AIAction
|
// AIAction
|
||||||
//
|
//
|
||||||
|
|
||||||
|
namespace AI {
|
||||||
|
|
||||||
Player * OrderedAIAction::getPlayerTarget()
|
Player * OrderedAIAction::getPlayerTarget()
|
||||||
{
|
{
|
||||||
@@ -2192,36 +2193,6 @@ int AIPlayerBaka::computeActions()
|
|||||||
return 1;
|
return 1;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
//
|
|
||||||
// Combat //
|
|
||||||
//
|
|
||||||
|
|
||||||
int AIPlayerBaka::getCreaturesInfo(Player * player, int neededInfo, int untapMode, int canAttack)
|
|
||||||
{
|
|
||||||
int result = 0;
|
|
||||||
CardDescriptor cd;
|
|
||||||
cd.init();
|
|
||||||
cd.setType("Creature");
|
|
||||||
cd.unsecureSetTapped(untapMode);
|
|
||||||
MTGCardInstance * card = NULL;
|
|
||||||
while ((card = cd.nextmatch(player->game->inPlay, card)))
|
|
||||||
{
|
|
||||||
if (!canAttack || card->canAttack())
|
|
||||||
{
|
|
||||||
if (neededInfo == INFO_NBCREATURES)
|
|
||||||
{
|
|
||||||
result++;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
result += card->power;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
int AIPlayerBaka::chooseAttackers()
|
int AIPlayerBaka::chooseAttackers()
|
||||||
{
|
{
|
||||||
//Attack with all creatures
|
//Attack with all creatures
|
||||||
@@ -2268,19 +2239,12 @@ int AIPlayerBaka::chooseAttackers()
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Can I first strike my oponent and get away with murder ? */
|
/* Can I first strike my oponent and get away with murder ? */
|
||||||
int AIPlayerBaka::canFirstStrikeKill(MTGCardInstance * card, MTGCardInstance *ennemy)
|
bool AIPlayerBaka::canFirstStrikeKill(MTGCardInstance * card, MTGCardInstance *ennemy)
|
||||||
{
|
{
|
||||||
if(hints && hints->HintSaysAlwaysBlock(observer,ennemy))
|
if(hints && hints->HintSaysAlwaysBlock(observer,ennemy))
|
||||||
return 1;
|
return true;
|
||||||
if (ennemy->has(Constants::FIRSTSTRIKE) || ennemy->has(Constants::DOUBLESTRIKE))
|
|
||||||
return 0;
|
return AIPlayer::canFirstStrikeKill(card, ennemy);
|
||||||
if (!(card->has(Constants::FIRSTSTRIKE) || card->has(Constants::DOUBLESTRIKE)))
|
|
||||||
return 0;
|
|
||||||
if (!(card->power >= ennemy->toughness))
|
|
||||||
return 0;
|
|
||||||
if (!(card->power >= ennemy->toughness + 1) && ennemy->has(Constants::FLANKING))
|
|
||||||
return 0;
|
|
||||||
return 1;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int AIPlayerBaka::chooseBlockers()
|
int AIPlayerBaka::chooseBlockers()
|
||||||
@@ -2464,7 +2428,7 @@ int AIPlayerBaka::receiveEvent(WEvent * event)
|
|||||||
|
|
||||||
|
|
||||||
AIPlayerBaka::AIPlayerBaka(GameObserver *observer, string file, string fileSmall, string avatarFile, MTGDeck * deck) :
|
AIPlayerBaka::AIPlayerBaka(GameObserver *observer, string file, string fileSmall, string avatarFile, MTGDeck * deck) :
|
||||||
AIPlayer(observer, file, fileSmall, deck)
|
AIPlayer(observer, file, fileSmall, avatarFile, deck)
|
||||||
{
|
{
|
||||||
|
|
||||||
nextCardToPlay = NULL;
|
nextCardToPlay = NULL;
|
||||||
@@ -2480,34 +2444,6 @@ AIPlayerBaka::AIPlayerBaka(GameObserver *observer, string file, string fileSmall
|
|||||||
hints->add(mDeck->meta_AIHints[i]);
|
hints->add(mDeck->meta_AIHints[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
if(avatarFile != "")
|
|
||||||
{
|
|
||||||
if(!loadAvatar(avatarFile, "bakaAvatar"))
|
|
||||||
{
|
|
||||||
avatarFile = "baka.jpg";
|
|
||||||
loadAvatar(avatarFile, "bakaAvatar");
|
|
||||||
}
|
|
||||||
mAvatarName = avatarFile;
|
|
||||||
}
|
|
||||||
else //load a random avatar.
|
|
||||||
{
|
|
||||||
avatarFile = "avatar";
|
|
||||||
char buffer[3];
|
|
||||||
sprintf(buffer, "%i", int(observer->getRandomGenerator()->random()%100));
|
|
||||||
avatarFile.append(buffer);
|
|
||||||
avatarFile.append(".jpg");
|
|
||||||
if(!loadAvatar(avatarFile, "bakaAvatar"))
|
|
||||||
{
|
|
||||||
avatarFile = "baka.jpg";
|
|
||||||
loadAvatar(avatarFile, "bakaAvatar");
|
|
||||||
}
|
|
||||||
mAvatarName = avatarFile;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (fileSmall == "ai_baka_eviltwin")
|
|
||||||
mAvatar->SetHFlip(true);
|
|
||||||
|
|
||||||
initTimer();
|
initTimer();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -2598,3 +2534,5 @@ AIPlayerBaka::~AIPlayerBaka() {
|
|||||||
}
|
}
|
||||||
SAFE_DELETE(hints);
|
SAFE_DELETE(hints);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|||||||
@@ -14,6 +14,7 @@
|
|||||||
// Abilities/Target Selection
|
// Abilities/Target Selection
|
||||||
//
|
//
|
||||||
|
|
||||||
|
namespace AI {
|
||||||
|
|
||||||
MTGCardInstance * AIPlayerBakaB::chooseCard(TargetChooser * tc, MTGCardInstance * source, int random)
|
MTGCardInstance * AIPlayerBakaB::chooseCard(TargetChooser * tc, MTGCardInstance * source, int random)
|
||||||
{
|
{
|
||||||
@@ -117,7 +118,7 @@ int AIPlayerBakaB::chooseAttackers()
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Can I first strike my oponent and get away with murder ? */
|
/* Can I first strike my oponent and get away with murder ? */
|
||||||
int AIPlayerBakaB::canFirstStrikeKill(MTGCardInstance * card, MTGCardInstance *ennemy)
|
bool AIPlayerBakaB::canFirstStrikeKill(MTGCardInstance * card, MTGCardInstance *ennemy)
|
||||||
{
|
{
|
||||||
return AIPlayerBaka::canFirstStrikeKill(card, ennemy);
|
return AIPlayerBaka::canFirstStrikeKill(card, ennemy);
|
||||||
}
|
}
|
||||||
@@ -180,7 +181,7 @@ AIPlayerBakaB::~AIPlayerBakaB() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,78 @@
|
|||||||
|
#include "PrecompiledHeader.h"
|
||||||
|
|
||||||
|
#include "AIPlayerMinMax.h"
|
||||||
|
#include "CardDescriptor.h"
|
||||||
|
#include "AIStats.h"
|
||||||
|
#include "AllAbilities.h"
|
||||||
|
#include "ExtraCost.h"
|
||||||
|
#include "GuiCombat.h"
|
||||||
|
#include "AIHints.h"
|
||||||
|
#include "ManaCostHybrid.h"
|
||||||
|
#include "MTGRules.h"
|
||||||
|
|
||||||
|
namespace AI {
|
||||||
|
|
||||||
|
//
|
||||||
|
// Abilities/Target Selection
|
||||||
|
//
|
||||||
|
|
||||||
|
AIPlayerMinMax::AIPlayerMinMax(GameObserver *observer, string deckFile, string deckFileSmall, string avatarFile, MTGDeck * deck) :
|
||||||
|
AIPlayer(observer, deckFile, deckFileSmall, avatarFile, deck)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
int AIPlayerMinMax::Act(float dt)
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
};
|
||||||
|
|
||||||
|
AIPlayerMinMax::~AIPlayerMinMax()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void AIPlayerMinMax::LookAround()
|
||||||
|
{
|
||||||
|
vector<MTGCardInstance*>::iterator ite;
|
||||||
|
vector<AIAction> potentialActions;
|
||||||
|
|
||||||
|
// look for something useable (including mana)
|
||||||
|
for (size_t i = 1; i < observer->mLayers->actionLayer()->mObjects.size(); i++)
|
||||||
|
{
|
||||||
|
MTGAbility * a = ((MTGAbility *) observer->mLayers->actionLayer()->mObjects[i]);
|
||||||
|
//Make sure we can use the ability
|
||||||
|
for (int j = 0; j < game->inPlay->nb_cards; j++)
|
||||||
|
{
|
||||||
|
MTGCardInstance * card = game->inPlay->cards[j];
|
||||||
|
if (a->isReactingToClick(card, 0))
|
||||||
|
{
|
||||||
|
createAbilityPotentialsActions(a, card, potentialActions);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// look for something playable
|
||||||
|
for(ite = game->hand->cards.begin(); ite != game->hand->cards.end(); ite++)
|
||||||
|
{
|
||||||
|
if(canPlay(*ite))
|
||||||
|
{
|
||||||
|
AIAction a(this, (*ite));
|
||||||
|
potentialActions.push_back(a);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
stringstream stream;
|
||||||
|
stream << *observer;
|
||||||
|
vector<AIAction>::const_iterator it;
|
||||||
|
for(it = potentialActions.begin(); it != potentialActions.end(); it++)
|
||||||
|
{
|
||||||
|
stringstream theCommand;
|
||||||
|
theCommand << (*it);
|
||||||
|
|
||||||
|
GameObserver g;
|
||||||
|
g.load(stream.str());
|
||||||
|
g.processAction(theCommand.str());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@@ -6,6 +6,9 @@
|
|||||||
#include "MTGCardInstance.h"
|
#include "MTGCardInstance.h"
|
||||||
#include "WEvent.h"
|
#include "WEvent.h"
|
||||||
#include "AllAbilities.h"
|
#include "AllAbilities.h"
|
||||||
|
|
||||||
|
namespace AI {
|
||||||
|
|
||||||
//TODO:better comments this is too cryptic to work on by anyone but original coder.
|
//TODO:better comments this is too cryptic to work on by anyone but original coder.
|
||||||
bool compare_aistats(AIStat * first, AIStat * second)
|
bool compare_aistats(AIStat * first, AIStat * second)
|
||||||
{
|
{
|
||||||
@@ -217,3 +220,5 @@ void AIStats::Render()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|||||||
@@ -608,7 +608,7 @@ int ActionStack::setIsInterrupting(Player * player, bool log)
|
|||||||
|
|
||||||
if (!gModRules.game.canInterrupt())
|
if (!gModRules.game.canInterrupt())
|
||||||
{
|
{
|
||||||
cancelInterruptOffer(DONT_INTERRUPT, log);
|
cancelInterruptOffer(0, DONT_INTERRUPT, log);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -622,9 +622,18 @@ int ActionStack::setIsInterrupting(Player * player, bool log)
|
|||||||
|
|
||||||
int playerId = (player == observer->players[1]) ? 1 : 0;
|
int playerId = (player == observer->players[1]) ? 1 : 0;
|
||||||
interruptDecision[playerId] = INTERRUPT;
|
interruptDecision[playerId] = INTERRUPT;
|
||||||
|
|
||||||
|
Interruptible* latest = getLatest(NOT_RESOLVED);
|
||||||
|
stringstream stream;
|
||||||
|
|
||||||
|
if(latest)
|
||||||
|
stream << "yes " << " " << latest->getDisplayName();
|
||||||
|
else
|
||||||
|
stream << "yes";
|
||||||
|
|
||||||
observer->isInterrupting = player;
|
observer->isInterrupting = player;
|
||||||
if(log)
|
if(log)
|
||||||
observer->logAction(player, "yes");
|
observer->logAction(player, stream.str());
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -672,7 +681,6 @@ ActionStack::ActionStack(GameObserver* game)
|
|||||||
interruptDecision[i] = NOT_DECIDED;
|
interruptDecision[i] = NOT_DECIDED;
|
||||||
askIfWishesToInterrupt = NULL;
|
askIfWishesToInterrupt = NULL;
|
||||||
timer = -1;
|
timer = -1;
|
||||||
currentState = -1;
|
|
||||||
mode = ACTIONSTACK_STANDARD;
|
mode = ACTIONSTACK_STANDARD;
|
||||||
checked = 0;
|
checked = 0;
|
||||||
lastActionController = NULL;
|
lastActionController = NULL;
|
||||||
@@ -873,8 +881,6 @@ void ActionStack::Update(float dt)
|
|||||||
//modal = 0;
|
//modal = 0;
|
||||||
|
|
||||||
TargetChooser * tc = observer->getCurrentTargetChooser();
|
TargetChooser * tc = observer->getCurrentTargetChooser();
|
||||||
int newState = observer->getCurrentGamePhase();
|
|
||||||
currentState = newState;
|
|
||||||
if (!tc)
|
if (!tc)
|
||||||
checked = 0;
|
checked = 0;
|
||||||
|
|
||||||
@@ -992,18 +998,33 @@ void ActionStack::Update(float dt)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void ActionStack::cancelInterruptOffer(InterruptDecision cancelMode, bool log)
|
void ActionStack::cancelInterruptOffer(Player* p, InterruptDecision cancelMode, bool log)
|
||||||
{
|
{
|
||||||
int playerId = (observer->isInterrupting == observer->players[1]) ? 1 : 0;
|
assert(observer->isInterrupting!=0);
|
||||||
|
int playerId;
|
||||||
|
if(p) {
|
||||||
|
playerId = observer->getPlayerId(p)-1;
|
||||||
|
} else {
|
||||||
|
if(observer->isInterrupting == observer->players[1]) {
|
||||||
|
playerId = 1;
|
||||||
|
} else {
|
||||||
|
playerId = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if(log) {
|
||||||
|
stringstream stream;
|
||||||
|
Interruptible* latest = getLatest(NOT_RESOLVED);
|
||||||
|
if(latest)
|
||||||
|
stream << "no " << cancelMode << " " << latest->getDisplayName();
|
||||||
|
else
|
||||||
|
stream << "no " << cancelMode;
|
||||||
|
observer->logAction(playerId, stream.str());
|
||||||
|
}
|
||||||
interruptDecision[playerId] = cancelMode;
|
interruptDecision[playerId] = cancelMode;
|
||||||
askIfWishesToInterrupt = NULL;
|
askIfWishesToInterrupt = NULL;
|
||||||
observer->isInterrupting = NULL;
|
observer->isInterrupting = NULL;
|
||||||
timer = -1;
|
timer = -1;
|
||||||
if(log) {
|
|
||||||
stringstream stream;
|
|
||||||
stream << "no " << cancelMode;
|
|
||||||
observer->logAction(playerId, stream.str());
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void ActionStack::endOfInterruption(bool log)
|
void ActionStack::endOfInterruption(bool log)
|
||||||
@@ -1059,7 +1080,7 @@ bool ActionStack::CheckUserInput(JButton inputKey)
|
|||||||
}
|
}
|
||||||
else if ((JGE_BTN_PRI == key))
|
else if ((JGE_BTN_PRI == key))
|
||||||
{
|
{
|
||||||
cancelInterruptOffer(DONT_INTERRUPT_ALL);
|
cancelInterruptOffer(0, DONT_INTERRUPT_ALL);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
|
|||||||
@@ -1359,6 +1359,13 @@ int AAFizzler::resolve()
|
|||||||
sCard = sTarget->source;
|
sCard = sTarget->source;
|
||||||
if (!sCard || !sTarget || sCard->has(Constants::NOFIZZLE))
|
if (!sCard || !sTarget || sCard->has(Constants::NOFIZZLE))
|
||||||
return 0;
|
return 0;
|
||||||
|
if (source->alias == 111057 && sTarget)//Draining Whelk
|
||||||
|
{
|
||||||
|
for (int j = sTarget->cost->getConvertedCost(); j > 0; j--)
|
||||||
|
{
|
||||||
|
source->counters->addCounter(1,1);
|
||||||
|
}
|
||||||
|
}
|
||||||
stack->Fizzle(sTarget, fizzleMode);
|
stack->Fizzle(sTarget, fizzleMode);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
@@ -2482,6 +2489,19 @@ int AACloner::resolve()
|
|||||||
|
|
||||||
Player * targetPlayer = who == 1 ? source->controller()->opponent() : source->controller();
|
Player * targetPlayer = who == 1 ? source->controller()->opponent() : source->controller();
|
||||||
|
|
||||||
|
int tokenize = 1;//tokenizer support for cloning
|
||||||
|
if (targetPlayer->game->battlefield->hasAbility(Constants::TOKENIZER))
|
||||||
|
{
|
||||||
|
int nbcards = targetPlayer->game->battlefield->nb_cards;
|
||||||
|
for (int j = 0; j < nbcards; j++)
|
||||||
|
{
|
||||||
|
if (targetPlayer->game->battlefield->cards[j]->has(Constants::TOKENIZER))
|
||||||
|
tokenize *= 2;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (int i = 0; i < tokenize; ++i)
|
||||||
|
{
|
||||||
MTGCardInstance * myClone = NEW MTGCardInstance(clone, targetPlayer->game);
|
MTGCardInstance * myClone = NEW MTGCardInstance(clone, targetPlayer->game);
|
||||||
targetPlayer->game->temp->addCard(myClone);
|
targetPlayer->game->temp->addCard(myClone);
|
||||||
|
|
||||||
@@ -2511,6 +2531,7 @@ int AACloner::resolve()
|
|||||||
spell->source->addType(*it);
|
spell->source->addType(*it);
|
||||||
}
|
}
|
||||||
delete spell;
|
delete spell;
|
||||||
|
}
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -2941,6 +2962,32 @@ AAShuffle * AAShuffle::clone() const
|
|||||||
return NEW AAShuffle(*this);
|
return NEW AAShuffle(*this);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Mulligan
|
||||||
|
AAMulligan::AAMulligan(GameObserver* observer, int _id, MTGCardInstance * card, Targetable * _target, ManaCost * _cost, int who) :
|
||||||
|
ActivatedAbilityTP(observer, _id, card, _target, _cost, who)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
int AAMulligan::resolve()
|
||||||
|
{
|
||||||
|
Player * player = getPlayerFromTarget(getTarget());
|
||||||
|
if (player)
|
||||||
|
{
|
||||||
|
player->serumMulligan();
|
||||||
|
}
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
const string AAMulligan::getMenuText()
|
||||||
|
{
|
||||||
|
return "Mulligan";
|
||||||
|
}
|
||||||
|
|
||||||
|
AAMulligan * AAMulligan::clone() const
|
||||||
|
{
|
||||||
|
return NEW AAMulligan(*this);
|
||||||
|
}
|
||||||
|
|
||||||
// Remove Mana From ManaPool
|
// Remove Mana From ManaPool
|
||||||
AARemoveMana::AARemoveMana(GameObserver* observer, int _id, MTGCardInstance * card, Targetable * _target, string manaDesc, int who) :
|
AARemoveMana::AARemoveMana(GameObserver* observer, int _id, MTGCardInstance * card, Targetable * _target, string manaDesc, int who) :
|
||||||
ActivatedAbilityTP(observer, _id, card, _target, NULL, who)
|
ActivatedAbilityTP(observer, _id, card, _target, NULL, who)
|
||||||
@@ -3503,7 +3550,7 @@ int MenuAbility::processAbility()
|
|||||||
mClone->resolve();
|
mClone->resolve();
|
||||||
SAFE_DELETE(mClone);
|
SAFE_DELETE(mClone);
|
||||||
if (source->controller() == game->isInterrupting)
|
if (source->controller() == game->isInterrupting)
|
||||||
game->mLayers->stackLayer()->cancelInterruptOffer(ActionStack::DONT_INTERRUPT, false);
|
game->mLayers->stackLayer()->cancelInterruptOffer(0, ActionStack::DONT_INTERRUPT, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
processed = true;
|
processed = true;
|
||||||
@@ -3540,7 +3587,7 @@ int MenuAbility::reactToChoiceClick(Targetable * object,int choice,int control)
|
|||||||
if(!mClone)
|
if(!mClone)
|
||||||
{
|
{
|
||||||
if (source->controller() == game->isInterrupting)
|
if (source->controller() == game->isInterrupting)
|
||||||
game->mLayers->stackLayer()->cancelInterruptOffer(ActionStack::DONT_INTERRUPT, false);
|
game->mLayers->stackLayer()->cancelInterruptOffer(0, ActionStack::DONT_INTERRUPT, false);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
mClone->target = abilities[choice]->target;
|
mClone->target = abilities[choice]->target;
|
||||||
|
|||||||
@@ -625,7 +625,7 @@ int Credits::isDifficultyUnlocked(DeckStats * stats)
|
|||||||
{
|
{
|
||||||
if (options[Options::DIFFICULTY_MODE_UNLOCKED].number)
|
if (options[Options::DIFFICULTY_MODE_UNLOCKED].number)
|
||||||
return 0;
|
return 0;
|
||||||
int nbAIDecks = AIPlayer::getTotalAIDecks();
|
int nbAIDecks = AI::AIPlayer::getTotalAIDecks();
|
||||||
|
|
||||||
int wins = 0;
|
int wins = 0;
|
||||||
|
|
||||||
@@ -743,7 +743,7 @@ int Credits::IsMoreAIDecksUnlocked(DeckStats * stats) {
|
|||||||
// the number of currently unlocked decks in order to go through.
|
// the number of currently unlocked decks in order to go through.
|
||||||
if (stats->nbGames() < currentlyUnlocked * 1.2) return 0;
|
if (stats->nbGames() < currentlyUnlocked * 1.2) return 0;
|
||||||
|
|
||||||
if (AIPlayer::getTotalAIDecks() > currentlyUnlocked)
|
if (AI::AIPlayer::getTotalAIDecks() > currentlyUnlocked)
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|||||||
@@ -295,8 +295,8 @@ void GameObserver::userRequestNextGamePhase(bool allowInterrupt, bool log)
|
|||||||
{
|
{
|
||||||
if(log) {
|
if(log) {
|
||||||
stringstream stream;
|
stringstream stream;
|
||||||
stream << "next " << allowInterrupt << " " <<mCurrentGamePhase;
|
stream << "next " << allowInterrupt;
|
||||||
logAction(currentPlayer, stream.str());
|
logAction(currentPlayer/*currentActionPlayer*/, stream.str());
|
||||||
}
|
}
|
||||||
|
|
||||||
if(getCurrentTargetChooser() && getCurrentTargetChooser()->maxtargets == 1000)
|
if(getCurrentTargetChooser() && getCurrentTargetChooser()->maxtargets == 1000)
|
||||||
@@ -1497,6 +1497,7 @@ ostream& operator<<(ostream& out, const GameObserver& g)
|
|||||||
out << "player=" << g.currentPlayerId + 1 << endl;
|
out << "player=" << g.currentPlayerId + 1 << endl;
|
||||||
if(g.mCurrentGamePhase != MTG_PHASE_INVALID)
|
if(g.mCurrentGamePhase != MTG_PHASE_INVALID)
|
||||||
out << "phase=" << g.phaseRing->phaseName(g.mCurrentGamePhase) << endl;
|
out << "phase=" << g.phaseRing->phaseName(g.mCurrentGamePhase) << endl;
|
||||||
|
out << "gameType=" << g.gameType() << endl;
|
||||||
out << "[player1]" << endl;
|
out << "[player1]" << endl;
|
||||||
out << *(g.players[0]) << endl;
|
out << *(g.players[0]) << endl;
|
||||||
out << "[player2]" << endl;
|
out << "[player2]" << endl;
|
||||||
@@ -1570,8 +1571,13 @@ bool GameObserver::load(const string& ss, bool undo, int controlledPlayerIndex
|
|||||||
if (s[s.size() - 1] == '\r') s.erase(s.size() - 1); //Handle DOS files
|
if (s[s.size() - 1] == '\r') s.erase(s.size() - 1); //Handle DOS files
|
||||||
if (!s.size()) continue;
|
if (!s.size()) continue;
|
||||||
if (s[0] == '#') continue;
|
if (s[0] == '#') continue;
|
||||||
std::transform(s.begin(), s.end(), s.begin(), ::tolower);
|
|
||||||
if (s.find("seed ") == 0)
|
if (s.find("gameType:") == 0)
|
||||||
|
{
|
||||||
|
mGameType = (GameType)atoi(s.substr(9).c_str());
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if (s.find("seed:") == 0)
|
||||||
{
|
{
|
||||||
mSeed = atoi(s.substr(5).c_str());
|
mSeed = atoi(s.substr(5).c_str());
|
||||||
randomGenerator.setSeed(mSeed);
|
randomGenerator.setSeed(mSeed);
|
||||||
@@ -1660,6 +1666,25 @@ bool GameObserver::load(const string& ss, bool undo, int controlledPlayerIndex
|
|||||||
if(testgame)
|
if(testgame)
|
||||||
testgame->initGame();
|
testgame->initGame();
|
||||||
#endif //TESTSUITE
|
#endif //TESTSUITE
|
||||||
|
switch(mGameType) {
|
||||||
|
case GAME_TYPE_MOMIR:
|
||||||
|
{
|
||||||
|
addObserver(NEW MTGMomirRule(this, -1, MTGCollection()));
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case GAME_TYPE_STONEHEWER:
|
||||||
|
{
|
||||||
|
addObserver(NEW MTGStoneHewerRule(this, -1,MTGCollection()));
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case GAME_TYPE_HERMIT:
|
||||||
|
{
|
||||||
|
addObserver(NEW MTGHermitRule(this, -1));
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
processActions(undo
|
processActions(undo
|
||||||
#ifdef TESTSUITE
|
#ifdef TESTSUITE
|
||||||
@@ -1669,7 +1694,7 @@ bool GameObserver::load(const string& ss, bool undo, int controlledPlayerIndex
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
logAction(s);
|
actionsList.push_back(s);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@@ -1699,19 +1724,28 @@ bool GameObserver::processAction(const string& s)
|
|||||||
size_t size = s.find("]")-begin;
|
size_t size = s.find("]")-begin;
|
||||||
size_t index = atoi(s.substr(begin, size).c_str());
|
size_t index = atoi(s.substr(begin, size).c_str());
|
||||||
dumpAssert(index < zone->cards.size());
|
dumpAssert(index < zone->cards.size());
|
||||||
|
if(s.find(" -momir- ") != string::npos) {
|
||||||
|
int cardId = atoi(s.substr(s.find(" -momir- ") + 9).c_str());
|
||||||
|
MTGMomirRule * a = ((MTGMomirRule *) mLayers->actionLayer()->getAbility(MTGAbility::MOMIR));
|
||||||
|
a->reactToClick(zone->cards[index], cardId);
|
||||||
|
mLayers->actionLayer()->stuffHappened = 1;
|
||||||
|
}
|
||||||
|
else
|
||||||
cardClick(zone->cards[index], zone->cards[index]);
|
cardClick(zone->cards[index], zone->cards[index]);
|
||||||
} else if (s.find("stack") != string::npos) {
|
} else if (s.find("stack") != string::npos) {
|
||||||
size_t begin = s.find("[")+1;
|
size_t begin = s.find("[")+1;
|
||||||
size_t size = s.find("]")-begin;
|
size_t size = s.find("]")-begin;
|
||||||
size_t index = atoi(s.substr(begin, size).c_str());
|
size_t index = atoi(s.substr(begin, size).c_str());
|
||||||
stackObjectClicked((Interruptible*)mLayers->stackLayer()->getByIndex(index));
|
stackObjectClicked((Interruptible*)mLayers->stackLayer()->getByIndex(index));
|
||||||
} else if (s.find("yes") != string::npos) {
|
} else if (s.find(".yes") != string::npos) {
|
||||||
mLayers->stackLayer()->setIsInterrupting(p);
|
mLayers->stackLayer()->setIsInterrupting(p);
|
||||||
} else if (s.find("no") != string::npos) {
|
} else if (s.find(".no") != string::npos) {
|
||||||
mLayers->stackLayer()->cancelInterruptOffer();
|
mLayers->stackLayer()->cancelInterruptOffer(p);
|
||||||
} else if (s.find("endinterruption") != string::npos) {
|
} else if (s.find("endinterruption") != string::npos) {
|
||||||
mLayers->stackLayer()->endOfInterruption();
|
mLayers->stackLayer()->endOfInterruption();
|
||||||
} else if (s.find("next") != string::npos) {
|
} else if (s.find(".next") != string::npos) {
|
||||||
|
// currentPlayer = p;
|
||||||
|
// currentActionPlayer = p;
|
||||||
userRequestNextGamePhase();
|
userRequestNextGamePhase();
|
||||||
} else if (s.find("combatok") != string::npos) {
|
} else if (s.find("combatok") != string::npos) {
|
||||||
mLayers->combatLayer()->clickOK();
|
mLayers->combatLayer()->clickOK();
|
||||||
@@ -1720,14 +1754,14 @@ bool GameObserver::processAction(const string& s)
|
|||||||
} else if (s.find("choice") != string::npos) {
|
} else if (s.find("choice") != string::npos) {
|
||||||
int choice = atoi(s.substr(s.find("choice ") + 7).c_str());
|
int choice = atoi(s.substr(s.find("choice ") + 7).c_str());
|
||||||
mLayers->actionLayer()->doReactTo(choice);
|
mLayers->actionLayer()->doReactTo(choice);
|
||||||
} else if (s == "p1" || s == "p2") {
|
|
||||||
cardClick(NULL, p);
|
|
||||||
} else if(s.find("mulligan") != string::npos) {
|
} else if(s.find("mulligan") != string::npos) {
|
||||||
Mulligan(p);
|
Mulligan(p);
|
||||||
} else if(s.find("shufflelib") != string::npos) {
|
} else if(s.find("shufflelib") != string::npos) {
|
||||||
// This should probably be differently and be automatically part of the ability triggered
|
// This should probably be differently and be automatically part of the ability triggered
|
||||||
// that would allow the AI to use it as well.
|
// that would allow the AI to use it as well.
|
||||||
shuffleLibrary(p);
|
shuffleLibrary(p);
|
||||||
|
} else if (s.find("p1") || s.find("p2")) {
|
||||||
|
cardClick(NULL, p);
|
||||||
} else {
|
} else {
|
||||||
DebugTrace("no clue about: " + s);
|
DebugTrace("no clue about: " + s);
|
||||||
}
|
}
|
||||||
@@ -1771,21 +1805,29 @@ bool GameObserver::processActions(bool undo
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
for(loadingite = loadingList.begin(); loadingite != loadingList.end(); loadingite++, cmdIndex++)
|
for(loadingite = loadingList.begin(); loadingite != loadingList.end(); /*loadingite++,*/ cmdIndex++)
|
||||||
{
|
{
|
||||||
processAction(*loadingite);
|
Interruptible* lastInterruption;
|
||||||
|
Player* lastInterruptingPlayer;
|
||||||
|
|
||||||
size_t nb = actionsList.size();
|
do
|
||||||
|
|
||||||
for (int i = 0; i<6; i++)
|
|
||||||
{
|
{
|
||||||
|
lastInterruption = mLayers->stackLayer()->getLatest(NOT_RESOLVED);
|
||||||
|
lastInterruptingPlayer = isInterrupting;
|
||||||
// let's fake an update
|
// let's fake an update
|
||||||
GameObserver::Update(counter);
|
GameObserver::Update(counter);
|
||||||
counter += 1.000f;
|
counter += 1.000f;
|
||||||
}
|
}
|
||||||
dumpAssert(actionsList.back() == *loadingite);
|
while(
|
||||||
dumpAssert(nb == actionsList.size());
|
(lastInterruption != mLayers->stackLayer()->getLatest(NOT_RESOLVED)
|
||||||
dumpAssert(cmdIndex == (actionsList.size()-1));
|
&& mLayers->stackLayer()->isNotUndecided())
|
||||||
|
||lastInterruptingPlayer != isInterrupting);
|
||||||
|
// one again just to be sure
|
||||||
|
GameObserver::Update(counter);
|
||||||
|
counter += 1.000f;
|
||||||
|
|
||||||
|
string s = *loadingite;
|
||||||
|
processAction(s);
|
||||||
}
|
}
|
||||||
|
|
||||||
mLoading = false;
|
mLoading = false;
|
||||||
@@ -1814,14 +1856,42 @@ void GameObserver::logAction(MTGCardInstance* card, MTGGameZone* zone, size_t in
|
|||||||
logAction(stream.str());
|
logAction(stream.str());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void GameObserver::logActionMomir(MTGCardInstance * card, int cardId)
|
||||||
|
{
|
||||||
|
stringstream stream;
|
||||||
|
|
||||||
|
stream << "p" << ((card->controller()==players[0])?"1.":"2.")
|
||||||
|
<< card->currentZone->getName()<< "[" << card->currentZone->getIndex(card) << "] "
|
||||||
|
<< " -momir- " << cardId << " " << card->getLCName();
|
||||||
|
|
||||||
|
logAction(stream.str());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void GameObserver::logAction(const string& s)
|
void GameObserver::logAction(const string& s)
|
||||||
{
|
{
|
||||||
|
stringstream stream;
|
||||||
|
stream << s;
|
||||||
|
stream << " " << getCurrentGamePhaseName();
|
||||||
|
// << mLayers->stackLayer()->interruptDecision[0]
|
||||||
|
// << mLayers->stackLayer()->interruptDecision[1];
|
||||||
|
if(s.find("shufflelib") == string::npos &&
|
||||||
|
s.find("next") == string::npos &&
|
||||||
|
s.find(".no") == string::npos &&
|
||||||
|
s.find(".yes") == string::npos
|
||||||
|
) {
|
||||||
|
// shufflelib replay might be desynchronized
|
||||||
|
stream << " cp " << getPlayerId(currentPlayer) << ", ii " << getPlayerId(isInterrupting) << ", cap " << getPlayerId(currentActionPlayer);
|
||||||
|
}
|
||||||
|
|
||||||
if(mLoading)
|
if(mLoading)
|
||||||
{
|
{
|
||||||
string toCheck = *loadingite;
|
string toCheck = *loadingite;
|
||||||
dumpAssert(toCheck == s);
|
string vs = stream.str();
|
||||||
|
dumpAssert(toCheck == vs);
|
||||||
|
loadingite++;
|
||||||
}
|
}
|
||||||
actionsList.push_back(s);
|
actionsList.push_back(stream.str());
|
||||||
};
|
};
|
||||||
|
|
||||||
bool GameObserver::undo()
|
bool GameObserver::undo()
|
||||||
@@ -1839,6 +1909,13 @@ void GameObserver::Mulligan(Player* player)
|
|||||||
player->takeMulligan();
|
player->takeMulligan();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void GameObserver::serumMulligan(Player* player)
|
||||||
|
{
|
||||||
|
if(!player) player = currentPlayer;
|
||||||
|
logAction(player, "mulligan serum powder");
|
||||||
|
player->serumMulligan();
|
||||||
|
}
|
||||||
|
|
||||||
Player* GameObserver::createPlayer(const string& playerMode
|
Player* GameObserver::createPlayer(const string& playerMode
|
||||||
#ifdef TESTSUITE
|
#ifdef TESTSUITE
|
||||||
, TestSuiteGame* testgame
|
, TestSuiteGame* testgame
|
||||||
@@ -1851,7 +1928,7 @@ Player* GameObserver::createPlayer(const string& playerMode
|
|||||||
switch(aMode)
|
switch(aMode)
|
||||||
{
|
{
|
||||||
case Player::MODE_AI:
|
case Player::MODE_AI:
|
||||||
AIPlayerFactory playerCreator;
|
AI::AIPlayerFactory playerCreator;
|
||||||
if(players.size())
|
if(players.size())
|
||||||
pPlayer = playerCreator.createAIPlayer(this, MTGCollection(), players[0]);
|
pPlayer = playerCreator.createAIPlayer(this, MTGCollection(), players[0]);
|
||||||
else
|
else
|
||||||
@@ -1924,7 +2001,7 @@ void GameObserver::loadPlayer(int playerId, PlayerType playerType, int decknb, b
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{ //AI Player, chooses deck
|
{ //AI Player, chooses deck
|
||||||
AIPlayerFactory playerCreator;
|
AI::AIPlayerFactory playerCreator;
|
||||||
Player * opponent = NULL;
|
Player * opponent = NULL;
|
||||||
if (playerId == 1) opponent = players[0];
|
if (playerId == 1) opponent = players[0];
|
||||||
|
|
||||||
@@ -1934,7 +2011,7 @@ void GameObserver::loadPlayer(int playerId, PlayerType playerType, int decknb, b
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
//Random deck
|
//Random deck
|
||||||
AIPlayerFactory playerCreator;
|
AI::AIPlayerFactory playerCreator;
|
||||||
Player * opponent = NULL;
|
Player * opponent = NULL;
|
||||||
|
|
||||||
// Reset the random logging.
|
// Reset the random logging.
|
||||||
@@ -1951,7 +2028,7 @@ void GameObserver::loadPlayer(int playerId, PlayerType playerType, int decknb, b
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (playerType == PLAYER_TYPE_CPU_TEST)
|
if (playerType == PLAYER_TYPE_CPU_TEST)
|
||||||
((AIPlayer *) players[playerId])->setFastTimerMode();
|
((AI::AIPlayer *) players[playerId])->setFastTimerMode();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -263,7 +263,7 @@ void GameStateDeckViewer::saveDeck()
|
|||||||
void GameStateDeckViewer::saveAsAIDeck(string deckName)
|
void GameStateDeckViewer::saveAsAIDeck(string deckName)
|
||||||
{
|
{
|
||||||
|
|
||||||
int deckId = AIPlayer::getTotalAIDecks() + 1;
|
int deckId = AI::AIPlayer::getTotalAIDecks() + 1;
|
||||||
|
|
||||||
std::ostringstream oss;
|
std::ostringstream oss;
|
||||||
oss << "deck" <<deckId;
|
oss << "deck" <<deckId;
|
||||||
@@ -278,7 +278,7 @@ void GameStateDeckViewer::saveAsAIDeck(string deckName)
|
|||||||
filepath.append(aiDeckName).append(".txt");
|
filepath.append(aiDeckName).append(".txt");
|
||||||
DebugTrace("saving AI deck " << filepath);
|
DebugTrace("saving AI deck " << filepath);
|
||||||
myDeck->save(filepath, true, deckName, deckDesc);
|
myDeck->save(filepath, true, deckName, deckDesc);
|
||||||
AIPlayer::invalidateTotalAIDecks(); //We added one AI deck, so we need to invalidate the count cache
|
AI::AIPlayer::invalidateTotalAIDecks(); //We added one AI deck, so we need to invalidate the count cache
|
||||||
}
|
}
|
||||||
|
|
||||||
void GameStateDeckViewer::sellCard()
|
void GameStateDeckViewer::sellCard()
|
||||||
|
|||||||
@@ -1734,8 +1734,8 @@ void GameStateDuel::setAISpeed()
|
|||||||
{
|
{
|
||||||
if (mParent->players[i] == PLAYER_TYPE_CPU)
|
if (mParent->players[i] == PLAYER_TYPE_CPU)
|
||||||
{
|
{
|
||||||
if(dynamic_cast<AIPlayer*>(game->players[i]))
|
if(dynamic_cast<AI::AIPlayer*>(game->players[i]))
|
||||||
((AIPlayer *)game->players[i])->setFastTimerMode(tournament->getFastTimerMode());
|
((AI::AIPlayer *)game->players[i])->setFastTimerMode(tournament->getFastTimerMode());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -254,7 +254,7 @@ int GameStateMenu::gamePercentComplete() {
|
|||||||
|
|
||||||
//unlocked AI decks
|
//unlocked AI decks
|
||||||
int currentlyUnlocked = options[Options::AIDECKS_UNLOCKED].number;
|
int currentlyUnlocked = options[Options::AIDECKS_UNLOCKED].number;
|
||||||
int totalAIDecks = AIPlayer::getTotalAIDecks();
|
int totalAIDecks = AI::AIPlayer::getTotalAIDecks();
|
||||||
int reallyUnlocked = MIN(currentlyUnlocked, totalAIDecks);
|
int reallyUnlocked = MIN(currentlyUnlocked, totalAIDecks);
|
||||||
total+= totalAIDecks / 10;
|
total+= totalAIDecks / 10;
|
||||||
done+= reallyUnlocked / 10;
|
done+= reallyUnlocked / 10;
|
||||||
|
|||||||
@@ -236,8 +236,8 @@ void GameStateOptions::Render()
|
|||||||
"Nakano, Niegen, Kaioshin, Psyringe, r1c47, Superhiro,",
|
"Nakano, Niegen, Kaioshin, Psyringe, r1c47, Superhiro,",
|
||||||
"Szei, Thanatos02, Whismer, Wololo",
|
"Szei, Thanatos02, Whismer, Wololo",
|
||||||
"",
|
"",
|
||||||
"Thanks also go to Dr.Watson, Orine, Raphael, Sakya, Tyranid",
|
"Thanks also go to Dr.Watson, KF1, Orine, Raphael, Sakya,",
|
||||||
"for their help.",
|
"Tacoghandi, Tyranid for their help.",
|
||||||
"",
|
"",
|
||||||
"Thanks to everyone who contributes code/content on the forums!",
|
"Thanks to everyone who contributes code/content on the forums!",
|
||||||
"",
|
"",
|
||||||
|
|||||||
@@ -727,7 +727,7 @@ int GuiCombat::receiveEventMinus(WEvent* e)
|
|||||||
DAMAGE: step = event->step;
|
DAMAGE: step = event->step;
|
||||||
if (!observer->currentPlayer->displayStack())
|
if (!observer->currentPlayer->displayStack())
|
||||||
{
|
{
|
||||||
((AIPlayer *) observer->currentPlayer)->affectCombatDamages(step);
|
((AI::AIPlayer *) observer->currentPlayer)->affectCombatDamages(step);
|
||||||
observer->userRequestNextGamePhase(false, false);
|
observer->userRequestNextGamePhase(false, false);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2532,6 +2532,16 @@ MTGAbility * AbilityFactory::parseMagicLine(string s, int id, Spell * spell, MTG
|
|||||||
return a;
|
return a;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//Serum Powder
|
||||||
|
found = s.find("serumpowder");
|
||||||
|
if (found != string::npos)
|
||||||
|
{
|
||||||
|
Targetable * t = spell? spell->getNextTarget() : NULL;
|
||||||
|
MTGAbility * a = NEW AAMulligan(observer, id, card, t, NULL, who);
|
||||||
|
a->oneShot = 1;
|
||||||
|
return a;
|
||||||
|
}
|
||||||
|
|
||||||
//Remove Mana from ManaPool
|
//Remove Mana from ManaPool
|
||||||
vector<string> splitRemove = parseBetween(s, "removemana(", ")");
|
vector<string> splitRemove = parseBetween(s, "removemana(", ")");
|
||||||
if (splitRemove.size())
|
if (splitRemove.size())
|
||||||
|
|||||||
@@ -132,7 +132,8 @@ const char* Constants::MTGBasicAbilities[] = {
|
|||||||
"soulbond",
|
"soulbond",
|
||||||
"lure",
|
"lure",
|
||||||
"nolegend",
|
"nolegend",
|
||||||
"canplayfromgraveyard"
|
"canplayfromgraveyard",
|
||||||
|
"tokenizer"//parallel lives
|
||||||
};
|
};
|
||||||
|
|
||||||
map<string,int> Constants::MTGBasicAbilitiesMap;
|
map<string,int> Constants::MTGBasicAbilitiesMap;
|
||||||
|
|||||||
@@ -580,6 +580,24 @@ unsigned int MTGGameZone::countTotalManaSymbols(TargetChooser * tc, int color)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unsigned int MTGGameZone::countDevotion(TargetChooser * tc, int color)
|
||||||
|
{
|
||||||
|
if (!tc) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
// we don't care if cards have protection.
|
||||||
|
bool withoutProtections = true;
|
||||||
|
int result = 0;
|
||||||
|
for (int i = 0; i < nb_cards; i++)
|
||||||
|
{
|
||||||
|
if (tc->canTarget(cards[i], withoutProtections))
|
||||||
|
{
|
||||||
|
result += cards[i]->getManaCost()->getManaSymbolsHybridMerged(color);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
MTGCardInstance * MTGGameZone::findByName(string name)
|
MTGCardInstance * MTGGameZone::findByName(string name)
|
||||||
{
|
{
|
||||||
for (int i = 0; i < (nb_cards); i++)
|
for (int i = 0; i < (nb_cards); i++)
|
||||||
|
|||||||
@@ -1724,6 +1724,9 @@ int MTGMomirRule::reactToClick(MTGCardInstance * card_to_discard, int cardId)
|
|||||||
{
|
{
|
||||||
if (!isReactingToClick(card_to_discard))
|
if (!isReactingToClick(card_to_discard))
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
|
game->logActionMomir(card_to_discard, cardId);
|
||||||
|
|
||||||
Player * player = game->currentlyActing();
|
Player * player = game->currentlyActing();
|
||||||
ManaCost * cost = player->getManaPool();
|
ManaCost * cost = player->getManaPool();
|
||||||
player->getManaPool()->pay(cost);
|
player->getManaPool()->pay(cost);
|
||||||
|
|||||||
@@ -618,6 +618,27 @@ int ManaCost::getManaSymbols(int color)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int ManaCost::getManaSymbolsHybridMerged(int color)
|
||||||
|
{
|
||||||
|
int result = cost[color];
|
||||||
|
for (size_t i = 0; i < hybrids.size(); ++i)
|
||||||
|
{
|
||||||
|
result = hybrids[i].getManaSymbolsHybridMerged(color);//removed +
|
||||||
|
}
|
||||||
|
if (extraCosts && extraCosts->costs.size())
|
||||||
|
{
|
||||||
|
for (size_t i = 0; i < extraCosts->costs.size(); ++i)
|
||||||
|
{
|
||||||
|
LifeorManaCost * phyrexianMana = dynamic_cast<LifeorManaCost*>(extraCosts->costs[i]);
|
||||||
|
if (phyrexianMana)
|
||||||
|
{
|
||||||
|
result += phyrexianMana->getManaCost()->getManaSymbolsHybridMerged(color);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
int ManaCost::parseManaSymbol(char symbol)
|
int ManaCost::parseManaSymbol(char symbol)
|
||||||
{
|
{
|
||||||
switch (symbol)
|
switch (symbol)
|
||||||
|
|||||||
@@ -58,6 +58,14 @@ int ManaCostHybrid::getManaSymbols(int color)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int ManaCostHybrid::getManaSymbolsHybridMerged(int color)
|
||||||
|
{
|
||||||
|
// we assume that color1 and color2 are different
|
||||||
|
if (color1 == color) return value1;
|
||||||
|
if (color2 == color) return value2;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
int ManaCostHybrid::hasColor(int color)
|
int ManaCostHybrid::hasColor(int color)
|
||||||
{
|
{
|
||||||
if (((color1 == color) && value1) || ((color2 == color) && value2))
|
if (((color1 == color) && value1) || ((color2 == color) && value2))
|
||||||
|
|||||||
@@ -217,6 +217,22 @@ void Player::takeMulligan()
|
|||||||
//Draw hand with 1 less card penalty //almhum
|
//Draw hand with 1 less card penalty //almhum
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Player::serumMulligan()
|
||||||
|
{
|
||||||
|
MTGPlayerCards * currentPlayerZones = game;
|
||||||
|
int cardsinhand = currentPlayerZones->hand->nb_cards;
|
||||||
|
for (int i = 0; i < cardsinhand; i++) //Exile
|
||||||
|
currentPlayerZones->putInZone(currentPlayerZones->hand->cards[0],
|
||||||
|
currentPlayerZones->hand,
|
||||||
|
currentPlayerZones->exile);
|
||||||
|
|
||||||
|
currentPlayerZones->library->shuffle(); //Shuffle
|
||||||
|
|
||||||
|
for (int i = 0; i < (cardsinhand); i++)
|
||||||
|
game->drawFromLibrary();
|
||||||
|
//Draw hand no penalty
|
||||||
|
}
|
||||||
|
|
||||||
//Cleanup phase at the end of a turn
|
//Cleanup phase at the end of a turn
|
||||||
void Player::cleanupPhase()
|
void Player::cleanupPhase()
|
||||||
{
|
{
|
||||||
@@ -385,18 +401,30 @@ bool Player::operator<(Player& aPlayer)
|
|||||||
if(isDead() && !aPlayer.isDead())
|
if(isDead() && !aPlayer.isDead())
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
|
// if this opponent is not dead and aPlayer opponent is dead then this < aPlayer
|
||||||
|
if(!opponent()->isDead() && aPlayer.opponent()->isDead())
|
||||||
|
return true;
|
||||||
|
|
||||||
// heuristics for min-max
|
// heuristics for min-max
|
||||||
|
|
||||||
// if this is more poisoined than aPlayer then this < aPlayer
|
// if this is more poisoined than aPlayer then this < aPlayer
|
||||||
if(poisonCount > aPlayer.poisonCount)
|
if((poisonCount - opponent()->poisonCount) > (aPlayer.poisonCount - aPlayer.opponent()->poisonCount))
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
// if this has less life than aPlayer then this < aPlayer
|
// if this has less life than aPlayer then this < aPlayer
|
||||||
if(life < aPlayer.life)
|
if((life - opponent()->life) < (aPlayer.life - aPlayer.opponent()->life))
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
// if this has less parmanents in game that aPlayer then this < aPlayer
|
// if this has less permanents in game that aPlayer then this < aPlayer
|
||||||
if(game->battlefield->cards.size() < aPlayer.game->battlefield->cards.size())
|
if(((int)game->battlefield->cards.size() - (int)opponent()->game->battlefield->cards.size()) < ((int)aPlayer.game->battlefield->cards.size() - (int)aPlayer.opponent()->game->battlefield->cards.size()))
|
||||||
|
return true;
|
||||||
|
|
||||||
|
// if this has less cards in hand that aPlayer then this < aPlayer
|
||||||
|
if(((int)game->hand->cards.size() - (int)opponent()->game->hand->cards.size()) < ((int)aPlayer.game->hand->cards.size() - (int)aPlayer.opponent()->game->hand->cards.size()))
|
||||||
|
return true;
|
||||||
|
|
||||||
|
// if this has less mana than aPlayer then this < aPlayer
|
||||||
|
if(aPlayer.manaPool->canAfford(manaPool))
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
|
|||||||
@@ -184,8 +184,8 @@ void Rules::addExtraRules(GameObserver* g)
|
|||||||
else if (p->isAI() && (p->playMode == Player::MODE_AI && p->opponent()->playMode== Player::MODE_AI))
|
else if (p->isAI() && (p->playMode == Player::MODE_AI && p->opponent()->playMode== Player::MODE_AI))
|
||||||
{
|
{
|
||||||
handsize = ((AADrawer *)a)->getNumCards();
|
handsize = ((AADrawer *)a)->getNumCards();
|
||||||
((AIPlayer *) p)->forceBestAbilityUse = true;
|
((AI::AIPlayer *) p)->forceBestAbilityUse = true;
|
||||||
((AIPlayer *) p)->agressivity += 100;
|
((AI::AIPlayer *) p)->agressivity += 100;
|
||||||
hand->OptimizedHand(p,handsize, 3, 1, 3);
|
hand->OptimizedHand(p,handsize, 3, 1, 3);
|
||||||
}
|
}
|
||||||
else if (!p->isAI() && !Optimizedhandcheat)
|
else if (!p->isAI() && !Optimizedhandcheat)
|
||||||
@@ -203,8 +203,8 @@ void Rules::addExtraRules(GameObserver* g)
|
|||||||
handsize = ((AADrawer *)a)->getNumCards();
|
handsize = ((AADrawer *)a)->getNumCards();
|
||||||
if(difficultyRating == EASY)
|
if(difficultyRating == EASY)
|
||||||
{
|
{
|
||||||
((AIPlayer *) p)->forceBestAbilityUse = true;
|
((AI::AIPlayer *) p)->forceBestAbilityUse = true;
|
||||||
((AIPlayer *) p)->agressivity += 100;
|
((AI::AIPlayer *) p)->agressivity += 100;
|
||||||
hand->OptimizedHand(p,handsize, 3, 1, 3);//easy decks get a major boost, open hand is 2lands,1 creature under 3 mana,3spells under 3 mana.
|
hand->OptimizedHand(p,handsize, 3, 1, 3);//easy decks get a major boost, open hand is 2lands,1 creature under 3 mana,3spells under 3 mana.
|
||||||
}
|
}
|
||||||
else if (difficultyRating == NORMAL)
|
else if (difficultyRating == NORMAL)
|
||||||
@@ -266,7 +266,7 @@ Player * Rules::loadPlayerMomir(GameObserver* observer, int isAI)
|
|||||||
if (!isAI) // Human Player
|
if (!isAI) // Human Player
|
||||||
player = NEW HumanPlayer(observer, options.profileFile("momir.txt", "", true).c_str(), deckFileSmall, false, tempDeck);
|
player = NEW HumanPlayer(observer, options.profileFile("momir.txt", "", true).c_str(), deckFileSmall, false, tempDeck);
|
||||||
else
|
else
|
||||||
player = NEW AIMomirPlayer(observer, options.profileFile("momir.txt", "", true).c_str(), deckFileSmall, empty, tempDeck);
|
player = NEW AI::AIMomirPlayer(observer, options.profileFile("momir.txt", "", true).c_str(), deckFileSmall, empty, tempDeck);
|
||||||
|
|
||||||
return player;
|
return player;
|
||||||
}
|
}
|
||||||
@@ -300,7 +300,7 @@ Player * Rules::loadPlayerRandom(GameObserver* observer, int isAI, int mode)
|
|||||||
if (!isAI) // Human Player
|
if (!isAI) // Human Player
|
||||||
player = NEW HumanPlayer(observer, deckFile, deckFileSmall, false, tempDeck);
|
player = NEW HumanPlayer(observer, deckFile, deckFileSmall, false, tempDeck);
|
||||||
else
|
else
|
||||||
player = NEW AIPlayerBaka(observer, deckFile, deckFileSmall, "", tempDeck);
|
player = NEW AI::AIPlayerBaka(observer, deckFile, deckFileSmall, "", tempDeck);
|
||||||
|
|
||||||
return player;
|
return player;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -311,7 +311,7 @@ void StoryDuel::init()
|
|||||||
|
|
||||||
sprintf(deckFile, "%s/opponent_deck.txt", folder);
|
sprintf(deckFile, "%s/opponent_deck.txt", folder);
|
||||||
sprintf(deckFileSmall, "campaign_ennemy_%s_%s", mParent->folder.c_str(), pageId.c_str());
|
sprintf(deckFileSmall, "campaign_ennemy_%s_%s", mParent->folder.c_str(), pageId.c_str());
|
||||||
game->loadPlayer(1, NEW AIPlayerBaka(game, deckFile, deckFileSmall, "baka.jpg"));
|
game->loadPlayer(1, NEW AI::AIPlayerBaka(game, deckFile, deckFileSmall, "baka.jpg"));
|
||||||
|
|
||||||
string rulesFile = folder;
|
string rulesFile = folder;
|
||||||
rulesFile.append("/rules.txt");
|
rulesFile.append("/rules.txt");
|
||||||
|
|||||||
@@ -620,7 +620,7 @@ string TaskWinAgainst::getShortDesc()
|
|||||||
|
|
||||||
bool TaskWinAgainst::isDone(GameObserver* observer, GameApp *)
|
bool TaskWinAgainst::isDone(GameObserver* observer, GameApp *)
|
||||||
{
|
{
|
||||||
AIPlayerBaka * baka = (AIPlayerBaka*) observer->players[1];
|
AI::AIPlayerBaka * baka = (AI::AIPlayerBaka*) observer->players[1];
|
||||||
return ((baka) && (!observer->players[0]->isAI()) && (observer->players[1]->isAI()) && (observer->didWin(observer->players[0])) // Human player wins
|
return ((baka) && (!observer->players[0]->isAI()) && (observer->players[1]->isAI()) && (observer->didWin(observer->players[0])) // Human player wins
|
||||||
&& (baka->deckId == opponent));
|
&& (baka->deckId == opponent));
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -576,7 +576,7 @@ int TestSuite::loadNext()
|
|||||||
#elif defined(IOS)
|
#elif defined(IOS)
|
||||||
thread_count = 6;
|
thread_count = 6;
|
||||||
#else
|
#else
|
||||||
thread_count = 4;
|
thread_count = 2;
|
||||||
#endif
|
#endif
|
||||||
for(size_t i = 0; i < (thread_count-1); i++)
|
for(size_t i = 0; i < (thread_count-1); i++)
|
||||||
mWorkerThread.push_back(new boost::thread(ThreadProc, this));
|
mWorkerThread.push_back(new boost::thread(ThreadProc, this));
|
||||||
@@ -603,6 +603,7 @@ void TestSuite::ThreadProc(void* inParam)
|
|||||||
float counter = 1.0f;
|
float counter = 1.0f;
|
||||||
while(instance->mProcessing && (filename = instance->getNextFile()) != "")
|
while(instance->mProcessing && (filename = instance->getNextFile()) != "")
|
||||||
{
|
{
|
||||||
|
DebugTrace("Checking " + filename);
|
||||||
TestSuiteGame theGame(instance, filename);
|
TestSuiteGame theGame(instance, filename);
|
||||||
if(theGame.isOK)
|
if(theGame.isOK)
|
||||||
{
|
{
|
||||||
@@ -612,6 +613,14 @@ void TestSuite::ThreadProc(void* inParam)
|
|||||||
theGame.observer->startGame(theGame.gameType, /*instance->mRules*/Rules::getRulesByFilename("testsuite.txt"));
|
theGame.observer->startGame(theGame.gameType, /*instance->mRules*/Rules::getRulesByFilename("testsuite.txt"));
|
||||||
theGame.initGame();
|
theGame.initGame();
|
||||||
|
|
||||||
|
while(!theGame.observer->didWin())
|
||||||
|
theGame.observer->Update(counter++);
|
||||||
|
|
||||||
|
// rewind and redo thanks to the action logging
|
||||||
|
stringstream stream;
|
||||||
|
stream << (*theGame.observer);
|
||||||
|
theGame.observer->load(stream.str(), false, 0, &theGame);
|
||||||
|
|
||||||
while(!theGame.observer->didWin())
|
while(!theGame.observer->didWin())
|
||||||
theGame.observer->Update(counter++);
|
theGame.observer->Update(counter++);
|
||||||
}
|
}
|
||||||
@@ -846,7 +855,7 @@ void TestSuiteGame::initGame()
|
|||||||
|
|
||||||
for (int i = 0; i < 2; i++)
|
for (int i = 0; i < 2; i++)
|
||||||
{
|
{
|
||||||
AIPlayerBaka * p = (AIPlayerBaka *) (observer->players[i]);
|
AI::AIPlayerBaka * p = (AI::AIPlayerBaka *) (observer->players[i]);
|
||||||
p->forceBestAbilityUse = forceAbility;
|
p->forceBestAbilityUse = forceAbility;
|
||||||
p->life = initState.players[i]->life;
|
p->life = initState.players[i]->life;
|
||||||
p->poisonCount = initState.players[i]->poisonCount;
|
p->poisonCount = initState.players[i]->poisonCount;
|
||||||
|
|||||||
@@ -310,6 +310,7 @@
|
|||||||
<ClCompile Include="src\AIPlayer.cpp" />
|
<ClCompile Include="src\AIPlayer.cpp" />
|
||||||
<ClCompile Include="src\AIPlayerBaka.cpp" />
|
<ClCompile Include="src\AIPlayerBaka.cpp" />
|
||||||
<ClCompile Include="src\AIPlayerBakaB.cpp" />
|
<ClCompile Include="src\AIPlayerBakaB.cpp" />
|
||||||
|
<ClCompile Include="src\AIPlayerMinMax.cpp" />
|
||||||
<ClCompile Include="src\AIStats.cpp" />
|
<ClCompile Include="src\AIStats.cpp" />
|
||||||
<ClCompile Include="src\AllAbilities.cpp" />
|
<ClCompile Include="src\AllAbilities.cpp" />
|
||||||
<ClCompile Include="src\CardDescriptor.cpp" />
|
<ClCompile Include="src\CardDescriptor.cpp" />
|
||||||
@@ -468,6 +469,7 @@
|
|||||||
<ClInclude Include="include\AIPlayer.h" />
|
<ClInclude Include="include\AIPlayer.h" />
|
||||||
<ClInclude Include="include\AIPlayerBaka.h" />
|
<ClInclude Include="include\AIPlayerBaka.h" />
|
||||||
<ClInclude Include="include\AIPlayerBakaB.h" />
|
<ClInclude Include="include\AIPlayerBakaB.h" />
|
||||||
|
<ClInclude Include="include\AIPlayerMinMax.h" />
|
||||||
<ClInclude Include="include\AIStats.h" />
|
<ClInclude Include="include\AIStats.h" />
|
||||||
<ClInclude Include="include\AllAbilities.h" />
|
<ClInclude Include="include\AllAbilities.h" />
|
||||||
<ClInclude Include="include\CacheEngine.h" />
|
<ClInclude Include="include\CacheEngine.h" />
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
<?xml version="1.0" encoding="utf-8"?>
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<ClCompile Include="src\ActionElement.cpp">
|
<ClCompile Include="src\ActionElement.cpp">
|
||||||
@@ -331,6 +331,9 @@
|
|||||||
<ClCompile Include="src\NetworkPlayer.cpp">
|
<ClCompile Include="src\NetworkPlayer.cpp">
|
||||||
<Filter>src</Filter>
|
<Filter>src</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
|
<ClCompile Include="src\AIPlayerMinMax.cpp">
|
||||||
|
<Filter>src</Filter>
|
||||||
|
</ClCompile>
|
||||||
<ClCompile Include="src\CarouselDeckView.cpp">
|
<ClCompile Include="src\CarouselDeckView.cpp">
|
||||||
<Filter>src</Filter>
|
<Filter>src</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
@@ -687,6 +690,9 @@
|
|||||||
<ClInclude Include="include\NetworkPlayer.h">
|
<ClInclude Include="include\NetworkPlayer.h">
|
||||||
<Filter>inc</Filter>
|
<Filter>inc</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
|
<ClInclude Include="include\AIPlayerMinMax.h">
|
||||||
|
<Filter>inc</Filter>
|
||||||
|
</ClInclude>
|
||||||
<ClInclude Include="include\CarouselDeckView.h">
|
<ClInclude Include="include\CarouselDeckView.h">
|
||||||
<Filter>inc</Filter>
|
<Filter>inc</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
|
|||||||
@@ -12,6 +12,10 @@ CONFIG(console, graphics|console){
|
|||||||
CONFIG += console
|
CONFIG += console
|
||||||
CONFIG -= app_bundle
|
CONFIG -= app_bundle
|
||||||
DEFINES += TESTSUITE
|
DEFINES += TESTSUITE
|
||||||
|
|
||||||
|
QMAKE_CXXFLAGS += -g -fprofile-arcs -ftest-coverage
|
||||||
|
QMAKE_LDFLAGS += -g -fprofile-arcs -ftest-coverage
|
||||||
|
LIBS += -lgcov
|
||||||
}
|
}
|
||||||
else:CONFIG(graphics, graphics|console){
|
else:CONFIG(graphics, graphics|console){
|
||||||
folder_01.source = qml/QmlWagic
|
folder_01.source = qml/QmlWagic
|
||||||
@@ -19,13 +23,8 @@ else:CONFIG(graphics, graphics|console){
|
|||||||
DEPLOYMENTFOLDERS = folder_01
|
DEPLOYMENTFOLDERS = folder_01
|
||||||
QT += core gui opengl network multimedia
|
QT += core gui opengl network multimedia
|
||||||
QT -= declarative quick qml
|
QT -= declarative quick qml
|
||||||
#maemo5:DEFINES += QT_WIDGET
|
|
||||||
DEFINES += QT_WIDGET
|
DEFINES += QT_WIDGET
|
||||||
unix:!symbian:INCLUDEPATH += /usr/include/GL
|
unix:!symbian:INCLUDEPATH += /usr/include/GL
|
||||||
|
|
||||||
# Please do not modify the following two lines. Required for deployment.
|
|
||||||
# !maemo5:include(qml/qmlapplicationviewer/qmlapplicationviewer.pri)
|
|
||||||
# !maemo5:qtcAddDeployment()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#!android:!symbian:QT += phonon
|
#!android:!symbian:QT += phonon
|
||||||
@@ -134,6 +133,28 @@ maemo5: {
|
|||||||
USERDIR = /sdcard/Wagic/Res
|
USERDIR = /sdcard/Wagic/Res
|
||||||
DEFINES += RESDIR=\\\"$$RESDIR\\\"
|
DEFINES += RESDIR=\\\"$$RESDIR\\\"
|
||||||
DEFINES += USERDIR=\\\"$$USERDIR\\\"
|
DEFINES += USERDIR=\\\"$$USERDIR\\\"
|
||||||
|
} else:macx {
|
||||||
|
# Copy the custom Info.plist to the app bundle
|
||||||
|
QMAKE_INFO_PLIST = MacOS/Info.plist
|
||||||
|
# Icon is mandatory for submission
|
||||||
|
ICON = MacOS/wagic.icns
|
||||||
|
|
||||||
|
#Move resource file
|
||||||
|
res.commands = cd $$_PRO_FILE_PWD_/bin/Res; python createResourceZip.py;
|
||||||
|
res.depends = all
|
||||||
|
QMAKE_EXTRA_TARGETS += res
|
||||||
|
|
||||||
|
# Create a dmg file
|
||||||
|
dmg.commands = mkdir wagic.app/Contents/logs; mkdir wagic.app/Contents/Resources/Res; mv $$_PRO_FILE_PWD_/bin/Res/core*.zip wagic.app/Contents/Resources/Res; cp $$_PRO_FILE_PWD_/MacOS/wagic.launcher wagic.app/Contents/MacOS; $$dirname(QMAKE_QMAKE)/macdeployqt wagic.app -dmg
|
||||||
|
dmg.depends = res
|
||||||
|
QMAKE_EXTRA_TARGETS += dmg
|
||||||
|
|
||||||
|
QMAKE_MACOSX_DEPLOYMENT_TARGET = 10.9
|
||||||
|
QMAKE_MAC_SDK = macosx
|
||||||
|
|
||||||
|
# Only Intel binaries are accepted so force this
|
||||||
|
CONFIG += x86
|
||||||
|
|
||||||
} else:unix {
|
} else:unix {
|
||||||
# Variables
|
# Variables
|
||||||
BINDIR = /usr/bin
|
BINDIR = /usr/bin
|
||||||
|
|||||||
@@ -59,6 +59,7 @@ SOURCES += \
|
|||||||
src/AIMomirPlayer.cpp\
|
src/AIMomirPlayer.cpp\
|
||||||
src/AIPlayer.cpp\
|
src/AIPlayer.cpp\
|
||||||
src/AIPlayerBaka.cpp\
|
src/AIPlayerBaka.cpp\
|
||||||
|
src/AIPlayerMinMax.cpp\
|
||||||
src/AIStats.cpp\
|
src/AIStats.cpp\
|
||||||
src/AllAbilities.cpp\
|
src/AllAbilities.cpp\
|
||||||
src/CardDescriptor.cpp\
|
src/CardDescriptor.cpp\
|
||||||
@@ -177,6 +178,7 @@ HEADERS += \
|
|||||||
include/AIHints.h\
|
include/AIHints.h\
|
||||||
include/AIPlayerBaka.h\
|
include/AIPlayerBaka.h\
|
||||||
include/AIPlayerBakaB.h\
|
include/AIPlayerBakaB.h\
|
||||||
|
include/AIPlayerMinMax.h\
|
||||||
include/DeckEditorMenu.h\
|
include/DeckEditorMenu.h\
|
||||||
include/WResourceManagerImpl.h\
|
include/WResourceManagerImpl.h\
|
||||||
include/DeckMenu.h\
|
include/DeckMenu.h\
|
||||||
|
|||||||
Executable
+37
@@ -0,0 +1,37 @@
|
|||||||
|
#!/bin/sh -e
|
||||||
|
|
||||||
|
## New of branch to use
|
||||||
|
TRAVIS_MAC_BRANCH=travis_mac_osx
|
||||||
|
|
||||||
|
## Only cross-compile on Mac the master branch
|
||||||
|
test "$TRAVIS_BRANCH" != "master" && exit 0
|
||||||
|
|
||||||
|
## Configure Git to use OAuth token
|
||||||
|
git config credential.helper "store --file=.git/credentials"
|
||||||
|
echo "https://${GH_TOKEN}:@github.com" > .git/credentials
|
||||||
|
git config --global user.name $GH_USER
|
||||||
|
git config --global user.email $GH_EMAIL
|
||||||
|
git remote set-url origin "https://${GH_TOKEN}@github.com/WagicProject/wagic.git"
|
||||||
|
|
||||||
|
## Delete remote Travis-Mac branch (if any)
|
||||||
|
echo git branches = `git branch -r`
|
||||||
|
#export REMOTE=$(git branch -r | grep "origin/$TRAVIS_MAC_BRANCH")
|
||||||
|
#if [ "$REMOTE" = "origin/$TRAVIS_MAC_BRANCH" ]; then
|
||||||
|
# echo "Removing old $TRAVIS_MAC_BRANCH branch"
|
||||||
|
# # Delete remote branch
|
||||||
|
# git branch -r -D "origin/$TRAVIS_MAC_BRANCH"
|
||||||
|
# Push (delete) remote branch on temote server (e.g. github)
|
||||||
|
git push origin --delete "$TRAVIS_MAC_BRANCH"
|
||||||
|
#else
|
||||||
|
# echo "$REMOTE : No $TRAVIS_MAC_BRANCH to remove"
|
||||||
|
#fi
|
||||||
|
|
||||||
|
## Create a new branch
|
||||||
|
git checkout -q -b "$TRAVIS_MAC_BRANCH" "$TRAVIS_BRANCH"
|
||||||
|
|
||||||
|
## Write a new Travis-CI configuration file
|
||||||
|
cp tools/macos.travis.yml .travis.yml
|
||||||
|
git add .travis.yml
|
||||||
|
git commit -m "Auto-Updated Travis-CI configuration for Mac"
|
||||||
|
## Push new branch to remote server
|
||||||
|
git push -q origin $TRAVIS_MAC_BRANCH:$TRAVIS_MAC_BRANCH 2> /dev/null > /dev/null
|
||||||
@@ -0,0 +1,15 @@
|
|||||||
|
language: objective-c
|
||||||
|
before_install:
|
||||||
|
- brew update
|
||||||
|
- brew install qt5
|
||||||
|
- sudo pip install pyjavaproperties
|
||||||
|
- sudo pip install github3.py
|
||||||
|
|
||||||
|
env:
|
||||||
|
global:
|
||||||
|
secure: "EBzr1+qjQsOhn0s+tcFmXR1jP9B0xiOSXuXbRXWZ1OEHNvp8+A5/pS84LYVFlaZqmxr5dApxvPtwhgLIUbQ3EPXm8LpC3KgSD4dS+9/QMbxhe5TK4oczgFRGcDTMJQZsCzhOh7hp3tbcbJg5Gp+VT7aFjFQSHDGwhzSJXsXwh/8="
|
||||||
|
script:
|
||||||
|
- /usr/local/opt/qt5/bin/qmake projects/mtg/wagic-qt.pro CONFIG+=graphics
|
||||||
|
- make -j 4 dmg
|
||||||
|
after_success:
|
||||||
|
- python tools/upload-binaries.py -t $GH_TOKEN -s $TRAVIS_COMMIT -l wagic.dmg -r Wagic-macosx.dmg -b $TRAVIS_BRANCH
|
||||||
Executable
+87
@@ -0,0 +1,87 @@
|
|||||||
|
#!/bin/sh -e
|
||||||
|
|
||||||
|
# let's dump some info to debug a bit
|
||||||
|
echo ls = `ls`
|
||||||
|
echo pwd = `pwd`
|
||||||
|
# computing potential release name
|
||||||
|
echo TRAVIS_PULL_REQUEST = $TRAVIS_PULL_REQUEST
|
||||||
|
echo TRAVIS_BRANCH = $TRAVIS_BRANCH
|
||||||
|
|
||||||
|
if [ "$TRAVIS_PULL_REQUEST" = "false" ]; then
|
||||||
|
if [ "$TRAVIS_BRANCH" = "alphas" ]; then
|
||||||
|
export RELEASE_NAME="alpha-${TRAVIS_BUILD_NUMBER}"
|
||||||
|
else if [ "$TRAVIS_BRANCH" = "master" ]; then
|
||||||
|
export RELEASE_NAME="latest-master"
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo RELEASE_NAME = $RELEASE_NAME
|
||||||
|
|
||||||
|
|
||||||
|
# updating versions with the TRAVIS build numbers
|
||||||
|
cd projects/mtg/
|
||||||
|
ant update > error.txt
|
||||||
|
cd ../..
|
||||||
|
|
||||||
|
# we create resource package
|
||||||
|
cd projects/mtg/bin/Res
|
||||||
|
python createResourceZip.py
|
||||||
|
# if we let the zip here, Wagic will use it in the testsuite
|
||||||
|
# and we'll get 51 failed test cases
|
||||||
|
mv core_*.zip ../../../../core.zip
|
||||||
|
cd ../../../..
|
||||||
|
|
||||||
|
# we're building a PSP binary here
|
||||||
|
if [ "$BUILD_PSP" = "YES" ]; then
|
||||||
|
echo PSPDEV = $PSPDEV
|
||||||
|
echo psp-config = `psp-config --psp-prefix`
|
||||||
|
cd JGE
|
||||||
|
make -j 4
|
||||||
|
cd ..
|
||||||
|
cd projects/mtg
|
||||||
|
mkdir objs
|
||||||
|
make -j 4
|
||||||
|
mkdir WTH
|
||||||
|
mkdir WTH/Res
|
||||||
|
mv EBOOT.PBP WTH/
|
||||||
|
mv ../../JGE/exceptionHandler/prx/exception.prx WTH/
|
||||||
|
cp ../../core.zip WTH/Res
|
||||||
|
cd WTH/Res
|
||||||
|
unzip core.zip
|
||||||
|
rm core.zip
|
||||||
|
cd ..
|
||||||
|
chmod -R 775 Res
|
||||||
|
cd ..
|
||||||
|
zip psprelease.zip -r WTH/
|
||||||
|
cd ../..
|
||||||
|
fi
|
||||||
|
|
||||||
|
# we're building an Android binary here
|
||||||
|
if [ "$BUILD_ANDROID" = "YES" ]; then
|
||||||
|
android-ndk-r9/ndk-build -C projects/mtg/Android -j4
|
||||||
|
$ANDROID list targets
|
||||||
|
$ANDROID update project -t 1 -p projects/mtg/Android
|
||||||
|
ant debug -f projects/mtg/Android/build.xml
|
||||||
|
fi
|
||||||
|
|
||||||
|
# we're building a Qt version with GUI here
|
||||||
|
if [ "$BUILD_Qt" = "YES" ]; then
|
||||||
|
mkdir qt-gui-build
|
||||||
|
cd qt-gui-build
|
||||||
|
$QMAKE ../projects/mtg/wagic-qt.pro CONFIG+=release CONFIG+=graphics
|
||||||
|
make -j 4
|
||||||
|
cd ..
|
||||||
|
# let's try an Intel linux binary in debug text-mode-only
|
||||||
|
$QMAKE projects/mtg/wagic-qt.pro CONFIG+=console CONFIG+=debug DEFINES+=CAPTURE_STDERR
|
||||||
|
make -j 4
|
||||||
|
# Now we run the testsuite (Res needs to be in the working directory)
|
||||||
|
cd projects/mtg
|
||||||
|
../../wagic
|
||||||
|
cd ../..
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Let's launch de Mac cross-compilation
|
||||||
|
if [ "$BUILD_MAC" = "YES" ]; then
|
||||||
|
./tools/build-macos-script.sh
|
||||||
|
fi
|
||||||
@@ -49,7 +49,7 @@ def main():
|
|||||||
|
|
||||||
(options, args) = parser.parse_args()
|
(options, args) = parser.parse_args()
|
||||||
|
|
||||||
if (options.token and options.sha and options.local and options.remote and options.branch == 'master'):
|
if (options.token and options.sha and options.local and options.remote and (options.branch == 'master' or options.branch == 'travis_mac_osx')):
|
||||||
gh = login(token = options.token)
|
gh = login(token = options.token)
|
||||||
else:
|
else:
|
||||||
parser.print_help()
|
parser.print_help()
|
||||||
@@ -59,8 +59,9 @@ def main():
|
|||||||
r = checkRelease(repository, options.remote)
|
r = checkRelease(repository, options.remote)
|
||||||
filename = options.remote
|
filename = options.remote
|
||||||
with open(options.local, 'rb') as fd:
|
with open(options.local, 'rb') as fd:
|
||||||
r.upload_asset('application/zip', filename , fd)
|
asset = r.upload_asset('application/zip', filename , fd)
|
||||||
|
s = 'File ' + options.local + ' has been uploaded as ' + asset.name + '.'
|
||||||
|
print s
|
||||||
|
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
main()
|
main()
|
||||||
@@ -1,106 +0,0 @@
|
|||||||
#!/bin/sh -ex
|
|
||||||
|
|
||||||
# let's dump some info to debug a bit
|
|
||||||
echo ls = `ls`
|
|
||||||
echo pwd = `pwd`
|
|
||||||
# computing potential release name
|
|
||||||
echo TRAVIS_PULL_REQUEST = $TRAVIS_PULL_REQUEST
|
|
||||||
echo TRAVIS_BRANCH = $TRAVIS_BRANCH
|
|
||||||
|
|
||||||
if [ "$TRAVIS_PULL_REQUEST" = "false" ]; then
|
|
||||||
if [ "$TRAVIS_BRANCH" = "alphas" ]; then
|
|
||||||
export RELEASE_NAME="alpha-${TRAVIS_BUILD_NUMBER}"
|
|
||||||
else if [ "$TRAVIS_BRANCH" = "master" ]; then
|
|
||||||
export RELEASE_NAME="latest-master"
|
|
||||||
fi
|
|
||||||
fi
|
|
||||||
fi
|
|
||||||
|
|
||||||
echo RELEASE_NAME = $RELEASE_NAME
|
|
||||||
|
|
||||||
|
|
||||||
# updating versions with the TRAVIS build numbers
|
|
||||||
cd projects/mtg/
|
|
||||||
ant update > error.txt
|
|
||||||
cd ../..
|
|
||||||
|
|
||||||
# we create resource package
|
|
||||||
cd projects/mtg/bin/Res
|
|
||||||
python createResourceZip.py
|
|
||||||
# if we let the zip here, Wagic will use it in the testsuite
|
|
||||||
# and we'll get 51 failed test cases
|
|
||||||
mv core_*.zip ../../../../core.zip
|
|
||||||
cd ../../../..
|
|
||||||
|
|
||||||
# we're building a PSP binary here
|
|
||||||
if [ "$BUILD_TYPE" = "PSP" ]; then
|
|
||||||
# let's dump some info to debug a bit
|
|
||||||
echo PSPDEV = $PSPDEV
|
|
||||||
echo psp-config = `psp-config --psp-prefix`
|
|
||||||
cd JGE
|
|
||||||
make -j 4
|
|
||||||
cd ..
|
|
||||||
cd projects/mtg
|
|
||||||
mkdir objs
|
|
||||||
make -j 4
|
|
||||||
mkdir WTH
|
|
||||||
mkdir WTH/Res
|
|
||||||
mv EBOOT.PBP WTH/
|
|
||||||
mv ../../JGE/exceptionHandler/prx/exception.prx WTH/
|
|
||||||
cp ../../core.zip WTH/Res
|
|
||||||
cd WTH/Res
|
|
||||||
unzip core.zip
|
|
||||||
rm core.zip
|
|
||||||
cd ..
|
|
||||||
chmod -R 775 Res
|
|
||||||
cd ..
|
|
||||||
zip psprelease.zip -r WTH/
|
|
||||||
cd ../..
|
|
||||||
fi
|
|
||||||
|
|
||||||
# we're building an Android binary here
|
|
||||||
if [ "$BUILD_TYPE" = "Android" ]; then
|
|
||||||
android-ndk-r9/ndk-build -C projects/mtg/Android -j4
|
|
||||||
$ANDROID list targets
|
|
||||||
$ANDROID update project -t 1 -p projects/mtg/Android
|
|
||||||
ant debug -f projects/mtg/Android/build.xml
|
|
||||||
fi
|
|
||||||
|
|
||||||
if [ "$BUILD_TYPE" = "Qt" ]; then
|
|
||||||
# we're building a Qt version with GUI here
|
|
||||||
mkdir qt-gui-build
|
|
||||||
cd qt-gui-build
|
|
||||||
$QMAKE ../projects/mtg/wagic-qt.pro CONFIG+=release CONFIG+=graphics
|
|
||||||
make -j 4
|
|
||||||
cd ..
|
|
||||||
# let's try an Intel linux binary in debug text-mode-only
|
|
||||||
$QMAKE projects/mtg/wagic-qt.pro CONFIG+=console CONFIG+=debug DEFINES+=CAPTURE_STDERR
|
|
||||||
make -j 4
|
|
||||||
|
|
||||||
# we're cross-compiling a Qt Windows version here,
|
|
||||||
# PATH is only set here to prevent colision
|
|
||||||
|
|
||||||
# export PATH="$PATH:/opt/mingw32/bin"
|
|
||||||
# mkdir build
|
|
||||||
# cd build
|
|
||||||
# mkdir win-cross
|
|
||||||
# cd win-cross
|
|
||||||
# /opt/mingw32/bin/qmake ../../projects/mtg/wagic-qt.pro CONFIG+=release CONFIG+=graphics
|
|
||||||
# make -j 4
|
|
||||||
# cd release
|
|
||||||
# cp ../../../projects/mtg/bin/fmod.dll .
|
|
||||||
# cp /opt/mingw32/bin/QtCore4.dll .
|
|
||||||
# cp /opt/mingw32/bin/QtGui4.dll .
|
|
||||||
# cp /opt/mingw32/bin/QtNetwork4.dll .
|
|
||||||
# cp /opt/mingw32/bin/QtOpenGL4.dll .
|
|
||||||
# cp ../../../projects/mtg/bin/zlib1.dll .
|
|
||||||
# cp /opt/mingw32/bin/libpng15-15.dll .
|
|
||||||
# cd ..
|
|
||||||
# zip win-cross.zip -r release/
|
|
||||||
# cd ../..
|
|
||||||
|
|
||||||
# Now we run the testsuite (Res needs to be in the working directory)
|
|
||||||
cd projects/mtg
|
|
||||||
../../wagic
|
|
||||||
cd ../..
|
|
||||||
fi
|
|
||||||
@@ -1,99 +0,0 @@
|
|||||||
if [ "$TRAVIS_PULL_REQUEST" == "false" ]; then
|
|
||||||
if [ "$TRAVIS_BRANCH" == "alphas" ]; then
|
|
||||||
echo -e "Creating a release\n"
|
|
||||||
curl -X POST -H "Authorization: token ${GH_TOKEN}" \
|
|
||||||
-d '{"tag_name": "alpha-'${TRAVIS_BUILD_NUMBER}'", "target_commitish": "master", "name": "Alpha release number '${TRAVIS_BUILD_NUMBER}'", "body": "Automatic alpha release generated by Travis CI", "draft": false, "prerelease": true}' "https://api.github.com/repos/WagicProject/wagic/releases" > json.txt
|
|
||||||
IDDI=`cat json.txt | jq '.id'`
|
|
||||||
|
|
||||||
echo -e "Uploading Core resources\n"
|
|
||||||
curl -X POST -H "Authorization: token ${GH_TOKEN}" \
|
|
||||||
-H "Accept: application/vnd.github.manifold-preview" \
|
|
||||||
-H "Content-Type: application/zip" \
|
|
||||||
--data-binary @core.zip \
|
|
||||||
"https://uploads.github.com/repos/WagicProject/wagic/releases/${IDDI}/assets?name=Wagic-core.zip"
|
|
||||||
|
|
||||||
echo -e "Uploading android package\n"
|
|
||||||
curl -X POST -H "Authorization: token ${GH_TOKEN}" \
|
|
||||||
-H "Accept: application/vnd.github.manifold-preview" \
|
|
||||||
-H "Content-Type: application/zip" \
|
|
||||||
--data-binary @projects/mtg/Android/bin/Wagic-debug.apk \
|
|
||||||
"https://uploads.github.com/repos/WagicProject/wagic/releases/${IDDI}/assets?name=Wagic-android.apk"
|
|
||||||
|
|
||||||
echo -e "Uploading PSP package\n"
|
|
||||||
curl -X POST -H "Authorization: token ${GH_TOKEN}" \
|
|
||||||
-H "Accept: application/vnd.github.manifold-preview" \
|
|
||||||
-H "Content-Type: application/zip" \
|
|
||||||
--data-binary @projects/mtg/psprelease.zip \
|
|
||||||
"https://uploads.github.com/repos/WagicProject/wagic/releases/${IDDI}/assets?name=Wagic-psp.zip"
|
|
||||||
|
|
||||||
# echo -e "Uploading Windows package\n"
|
|
||||||
# curl -X POST -H "Authorization: token ${GH_TOKEN}" \
|
|
||||||
# -H "Accept: application/vnd.github.manifold-preview" \
|
|
||||||
# -H "Content-Type: application/zip" \
|
|
||||||
# --data-binary @build/win-cross/win-cross.zip \
|
|
||||||
# "https://uploads.github.com/repos/WagicProject/wagic/releases/${IDDI}/assets?name=Wagic-windows.zip"
|
|
||||||
|
|
||||||
echo -e "Done uploading\n"
|
|
||||||
fi
|
|
||||||
fi
|
|
||||||
|
|
||||||
if [ "$TRAVIS_PULL_REQUEST" == "false" ]; then
|
|
||||||
if [ "$TRAVIS_BRANCH" == "master" ]; then
|
|
||||||
|
|
||||||
# get info about all releases
|
|
||||||
echo -e "Getting info about previous releases"
|
|
||||||
curl -X GET -H "Authorization: token ${GH_TOKEN}" \
|
|
||||||
"https://api.github.com/repos/WagicProject/wagic/releases" > json.txt
|
|
||||||
|
|
||||||
# extract info only about only "latest-release" tag
|
|
||||||
cat json.txt |jq 'map(select (.tag_name == "latest-master"))' > latest.txt
|
|
||||||
|
|
||||||
# get id of release
|
|
||||||
ID_TO_DELETE=`cat latest.txt |jq '.[0].id'`
|
|
||||||
|
|
||||||
# delete previous release
|
|
||||||
echo -e "Deleting release number ${ID_TO_DELETE}"
|
|
||||||
curl -X DELETE -H "Authorization: token ${GH_TOKEN}" \
|
|
||||||
"https://api.github.com/repos/WagicProject/wagic/releases/${ID_TO_DELETE}"
|
|
||||||
|
|
||||||
# delete previous tag
|
|
||||||
curl -X DELETE -H "Authorization: token ${GH_TOKEN}" \
|
|
||||||
"https://api.github.com/repos/WagicProject/wagic/git/refs/tags/latest-master"
|
|
||||||
|
|
||||||
|
|
||||||
echo -e "Creating a release\n"
|
|
||||||
curl -X POST -H "Authorization: token ${GH_TOKEN}" \
|
|
||||||
-d '{"tag_name": "latest-master", "target_commitish": "master", "name": "master-'${TRAVIS_BUILD_NUMBER}'", "body": "Automatic release based on latest commit to master branch generated by Travis CI", "draft": false, "prerelease": true}' "https://api.github.com/repos/WagicProject/wagic/releases" > json.txt
|
|
||||||
IDDI=`cat json.txt | jq '.id'`
|
|
||||||
|
|
||||||
echo -e "Uploading Core resources\n"
|
|
||||||
curl -X POST -H "Authorization: token ${GH_TOKEN}" \
|
|
||||||
-H "Accept: application/vnd.github.manifold-preview" \
|
|
||||||
-H "Content-Type: application/zip" \
|
|
||||||
--data-binary @core.zip \
|
|
||||||
"https://uploads.github.com/repos/WagicProject/wagic/releases/${IDDI}/assets?name=Wagic-core.zip"
|
|
||||||
|
|
||||||
echo -e "Uploading android package\n"
|
|
||||||
curl -X POST -H "Authorization: token ${GH_TOKEN}" \
|
|
||||||
-H "Accept: application/vnd.github.manifold-preview" \
|
|
||||||
-H "Content-Type: application/zip" \
|
|
||||||
--data-binary @projects/mtg/Android/bin/Wagic-debug.apk \
|
|
||||||
"https://uploads.github.com/repos/WagicProject/wagic/releases/${IDDI}/assets?name=Wagic-android.apk"
|
|
||||||
|
|
||||||
echo -e "Uploading PSP package\n"
|
|
||||||
curl -X POST -H "Authorization: token ${GH_TOKEN}" \
|
|
||||||
-H "Accept: application/vnd.github.manifold-preview" \
|
|
||||||
-H "Content-Type: application/zip" \
|
|
||||||
--data-binary @projects/mtg/psprelease.zip \
|
|
||||||
"https://uploads.github.com/repos/WagicProject/wagic/releases/${IDDI}/assets?name=Wagic-psp.zip"
|
|
||||||
|
|
||||||
# echo -e "Uploading Windows package\n"
|
|
||||||
# curl -X POST -H "Authorization: token ${GH_TOKEN}" \
|
|
||||||
# -H "Accept: application/vnd.github.manifold-preview" \
|
|
||||||
# -H "Content-Type: application/zip" \
|
|
||||||
# --data-binary @build/win-cross/win-cross.zip \
|
|
||||||
# "https://uploads.github.com/repos/WagicProject/wagic/releases/${IDDI}/assets?name=Wagic-windows.zip"
|
|
||||||
|
|
||||||
echo -e "Done uploading\n"
|
|
||||||
fi
|
|
||||||
fi
|
|
||||||
Reference in New Issue
Block a user