Thursday, December 3, 2009

Shock and Royal Assassin – Part 2

Today I'm going to examine how Firemox encodes Shock and Royal Assassin. Firemox allows you to play against other people on the Internet with rules enforcement. Firemox uses Java and currently has 6,041 cards.

Firemox uses XML to represent cards which is much better than using Java itself. On the plus side XML is usually shorter than Java and allows non-programmers to help. Using an "in-between" language like XML allows the programmer greater freedom when changing the code. For example, the damage code could be changed for all of the cards simultaneously because the damage code for each card is generated "on the fly" from the XML.

On the negative side, it hard to create XML code or any "do it yourself" language that is very flexible. The Firemox XML code below has a "colors" property which simply states the color of the card. Usually a card's color is determined by its mana cost but there are a few cards like Transguild Courier that are the exception.

I would hate to have to create an XML schema for Magic cards because it would be a very hard task. It would literally take weeks if not months. I'm sure that many hours of work was spent creating Firemox's XML language.

p.s. When I use the phrase "in-between" or "do it yourself" language, I'm talking about a problem domain language that only applies to a specific problem, like controlling a robot.

Firemox - Royal Assassin
<card> 
<rules-author-comment>By fabdouglas</rules-author-comment>

<init>
<registers>
<register index="colorless" value="1"/>
<register index="black" value="2"/>
<register index="power" value="1"/>
<register index="toughness" value="1"/>
</registers>

<colors>black</colors>
<idcards>creature </idcards>
<properties>assassin</properties>
</init>

<abilities>
<ability ref="cast-spell"/>
<activated-ability playable="instant" name="" zone="play">
<cost>
<action ref="T"/>
<action ref="target-creature">
<test>
<in-zone zone="playANDtapped"/>
</test>
</action>
</cost>

<effects>
<action ref="destroy"/>
</effects>
</activated-ability>
</abilities>


Firemox - Shock
<card>
<rules-author-comment>riclas</rules-author-comment>

<init>
<registers>
<register index='red' value='1'/>
</registers>
<colors>red </colors>
<idcards>instant </idcards>
</init>

<abilities>
<activated-ability playable='this' name='' zone='hand'>
<cost>
<pay-mana value='manacost'/>
<action ref='target-dealtable'/>
</cost>

<effects>
<assign-damage value='2' type='damage-normal'/>
<action ref='finish-spell'/>
</effects>
</activated-ability>
</abilities>

</card>

Monday, November 30, 2009

Shock and Royal Assassin – Part 1

When I first started working on Forge, I could only find two other Magic programs Firemox and Magma. Now there are programs such as Incantus, MagicWars, and Wagic which were inspired by this blog. (On a side note Incantus, MagicWars, and Firemox are like Magic Online and let you play against other people on the Internet with rules enforcement. Wagic and Magma let you play against the computer.)

All of these Magic programs, including my own (Forge), encode cards differently. Today I’m going to show how Forge and Wagic encode two familiar cards: Shock and Royal Assassin. Forge takes the direct route and shoehorns cards into Java while Wagic uses its own scripting language which is very short and concise.

Of the five programs mentioned I believe that Forge’s cards are the longest and Wagic’s are the shortest. Having short cards is a big advantage since it means less code is required for each card and hopefully less debugging. In Forge if you wanted to change the damage code, you would have to update each card that dealt damage, while Wagic would only have to tweak the damage code that is used for all the cards, which is a big improvement.

(This is a contrived example but it is generally true. Cards in Forge always a global static method to deal damage, so the damage code could be updated easily but other aspects of cards such as targeting do not always use a global static method.)

On a side note, usually Forge’s cards are very long but I forgot about the scripting code that people like Rob Cashwalker has been writing. (Since Forge is an open source project, letting other people do some of the “hard stuff” is truly wonderful.) Forge’s Shock is only 5 lines, which is great, and probably wins the title of “shortest Shock code”. So in reality some of Forge’s cards are very long like Royal Assassin and some of the cards are very short like Shock.

Wagic – Royal Assassin
[card]
text={T}: Destroy target tapped creature.
id=129708
auto={T}:destroy target(creature[tapped])
name=Royal Assassin
rarity=R
type=Creature
mana={1}{B}{B}
power=1
subtype=Human Assassin
toughness=1
[/card]

Wagic – Shock
[card]
text=Shock deals 2 damage to target creature or player.
target=creature,player
auto=Damage:2
id=129732
name=Shock
rarity=C
type=Instant
mana={R}
[/card]
Forge - Shock
Shock
R
Instant
no text
spDamageCP:2

Forge – Royal Assassin
if(cardName.equals("Royal Assassin"))
{
final Ability_Tap ability = new Ability_Tap(card)
{

public boolean canPlayAI()
{
CardList human =
CardFactoryUtil.AI_getHumanCreature(card, true);
human = human.filter(new CardListFilter()
{
public boolean addCard(Card c)
{return c.isTapped();}
});

CardListUtil.sortAttack(human);
CardListUtil.sortFlying(human);

if(0 < human.size())
setTargetCard(human.get(0));

return 0 < human.size();
}
public void resolve()
{
Card c = getTargetCard();

if(AllZone.GameAction.isCardInPlay(c) &&
c.isTapped() && CardFactoryUtil.canTarget(card, c) )
{
AllZone.GameAction.destroy(c);
}
}//resolve()
};//SpellAbility

Input target = new Input()
{
public void showMessage()
{
AllZone.Display.showMessage("Select
target tapped creature to destroy");
ButtonUtil.enableOnlyCancel();
}
public void selectButtonCancel() {stop();}
public void selectCard(Card c, PlayerZone zone)
{
if(!CardFactoryUtil.canTarget(card, c)){
AllZone.Display.showMessage(
"Cannot target this card (Shroud? Protection?).");
}
else if(c.isCreature() &&
zone.is(Constant.Zone.Play) && c.isTapped())
{
//tap ability
card.tap();

ability.setTargetCard(c);
AllZone.Stack.add(ability);
stop();
}
}//selectCard()
};//Input

card.addSpellAbility(ability);
ability.setDescription("tap: Destroy target
tapped creature.");
ability.setBeforePayMana(target);
}

Friday, November 27, 2009

Forge is the new official name

The name "MTG Forge" appears to attract Wizard's lawyers like flies to Aunt's Mays apple pie. Having the initials "mtg" seems to be the reason for the cease and desist letter about my original Sourceforge.net site. The name "Forge" sounds a little weird and empty to me but it is good enough. (And everybody by now should know that I am a firm believer in “good enough”.) The official name of this project is "Forge" and my official nickname is "mtgrares".

I tried calling myself forge but it is a little bit confusing having the same name for both a person and a project.

Wednesday, November 25, 2009

Forge's Architecture

The architecture for a computer program is very important since everything else in that program relies on it. Computer architecture is very similar to constructing a physical building. The program's architecture is the concrete foundation that you build on. If the foundation is cracked or broken, then you have a BIG problem. (I hope you understand that a program's architecture is very important even though you cannot see it.)

Forge's architecture restricts which cards are supported. Some cards cannot be added because the architecture isn't flexible enough. Cards like planeswalkers aren't really supported but were added by using elaborate hacks. The same thing applies to cards like Hypnotic Specter and Glorious Anthem. Even activated abilities that tap a card like Royal Assassin have to be "hacked" a little.

All of these "little hacks" add up and causes something later that "should work", not to work. Protection was a major update that required all of the targeting code for all of the cards to be changed. I didn't think about protection when I was creating Forge so all of the cards have to be changed one at a time in order to support protection.

Dennis, Rob, Zerker and others from the forums have donated weeks of their time toward Forge. And although I created Forge, these are the guys that keep it going.

Monday, November 23, 2009

Forge Is Not a One Man Project

Sorry for the long title but I couldn't think of a shorter one. The title is trying to say that many people have contributed to Forge. One person improved the card download and added a cool looking progress bar. Another person compiled a list of cards that could be added to "cards.txt". Someone else coded a few new cards.

This is article is also a big THANK YOU for everyone that has contributed to Forge. Forge really is a group project.

To view a complete list of people and their contributions, see the forum here. Below is a summary.

DennisBergkamp - is currently the lead developer and has the unpleasant job of making sure that everything doesn't fall apart. (Everything will fall apart, it is just a matter of when.) This is the guy that rewrote all of Forge's targeting code in order to support protection.

Rob Cashwalker - has transformed cards.txt from a simple file into keyword madness. He spearheaded the movement to add more and more "keywords" like drawing card and dealing damage to cards.txt. One of his earliest contributions was landwalk.

Thanks to Slightlymagic.net and Huggybaby for providing Forge with its very own forum.

Silly Freak created the "resizable game option" which allows Forge to be resized. He also wrote the "central error code" that shows the nice reports as well as divided up Forge's files into convenient directories.

Zerker has done a great job adding the mana pool and other cards.
Nantuko84 gave me the code that shows the card pictures in play as well as added several cards and added filters to the deck editor.

Mr. Chaos was one of my first, exuberant fans that sent me more than enough error reports.

Apthaven helped to spread the word of Forge far and wide as well as posting bug reports.

Chris. H. has done a fantastic job of keeping up all of the rarities for all of the cards in Forge. He is also responsible for playtesting the quest decks and determining the difficultly of a deck. Currently the decks are only divided up into three categories: easy, medium and hard, but three more "wizard" categories are going to be added soon which should make questing more difficult.

The hard thing is that once you start listing people you inevitably leave someone out, so let me say sorry in advance.

All of these people have helped make Forge the superb program that it is today. (These people also deal with all of Forge's inherent problems that I created. Reading someone else's code is like trying to follow a complicated math problem.)

Friday, November 20, 2009

DCMA Google Notice

I just received a e-mail notification from Google, the owner's of blogspot.com, that one of my posts contained an illegal link. The link was obviously to MTG Forge. I presume that this blog won't be shut down but who really knows.

I'll just post updates on Mediafire.com for awhile. This isn't a great way of doing things because MTG Forge will probably be removed from mediafire.com also.

(This is directed toward Wizards of the Coast. I enjoy Magic and I also understand that you own Magic and can do whatever you want to do with it. I also understand that you have been burnt by other computer programs such as Apprentice and Magic Workstation which makes money off of your work.

MTG Forge has about 2,000 cards and is a casual player's dream. Some of these cards are on your restricted list and will never be printed again like Tithe, Sapphire Mox, Timetwister and Wheel of Fortune. Other cards are out-of-print powerhouses like Flamtongue Kavu and Kiki-Jiki, Mirror Breaker. MTG Forge has a few cards that are in Standard such as Wrath of God, planeswalkers, Lightning Bolt and a variety of creatures with a few "vanilla" abilities.

You are not loosing money when people download this program. I officially want to wave the white flag of peace and would enjoy talking to you on the phone. Anyone from a wizards e-mail address can contact me at (mtgrares yahoo com) and I will give you my phone number.)

Improving Min-Max and Alpha-Beta on Wikipedia

Min-max and alpha-beta are both mentioned on Wikipedia but they have horrible, unusable pseudo-code. The book “Algorithms in a Nutshell” has GREAT pseudo-code so I posted it in both of the discussion sections. (I was too afraid of making the changes myself in the main Wikipedia entry.) Below are links for min-max and alpha-beta pseudo-code.

Min-Max
Alpha-Beta