• Home - See the latest news from Lone Wolf Development
  • Hero Lab® - Character management software for traditional role-playing games
  • Army Builder® - Point and click army construction for tabletop miniatures games
  • Realm Works™ - Streamlined RPG campaign management for players and GMs
  • Online Store - Buy Army Builder, Hero Lab and Card Vault here
  • Forums - Post your questions and comments about our products here
  • Technical Support - Having problems? Check here for solutions
  • Retailer Info - Important information for retailers, including free in-store licenses for all our products
  • More - Information about the company, other resources, and information on our discontinued products

–  Authoring Kit Support  –

Below you will find an assortment of topics specifically covering the Authoring Kit. If you are developing data files for Card Vault, this is a good place to start if you have questions. Additionally, the Card Vault forum is another great resource.

1.

Tips for users adding cards to an existing set of data files

 

If you are not the author of a given set of data files, it is likely that new updates of those files will be released at some point. Therefore, when adding cards to an existing set of data files, ALWAYS use separate ".dat" files to keep the new additions separate. If you don't, your additions will be overwritten by a new release. If you do, you can continue to use your additions with the new data files.

2.

When auto-numbering cards, always number each file separately.

 

Card ids must never change within Card Vault data files. That means that every time you generate new ids for cards, they must be exactly the same as the previous time you generated ids. Unfortunately, Windows provides no reliable ordering of files in a folder, so separate files will be randomly sequenced under different situations or on different computers. As a safeguard, we strongly recommend that you number the cards within each data file separately from all others files.

This can be achieved by assigning a unique prefix value for each separate file, with the generated unique id of each card being the combined prefix value and an incremental value for each card in the file. For example, you might assign the data files prefixes of "aa" and "bb". Then the cards in the first file would have the ids "aa001", "aa002", etc. Similarly, the cards in the second file would be numbered "bb001", "bb002", etc.

The problem with the above method is that you have to manually track which file is assigned which prefix and make sure it never changes. An even easier solution is to place the prefix into the file name. For example, you might name each file where the first 2-4 characters are the prefix to be used (e.g. "xxx_filename.dat" could indicate a prefix of "xxx"). You could even simply use the entire file name as the prefix, assuming you keep the file name short (the Magic data files use this technique).

3.

Use of the '$' special term vs. the '#' special term

 

When you are writing a rule with "card" scoping, you cannot use the '$' special term. The '$' symbol references the total number of cards in the DECK, so it serves no purpose within a "card" rule. When using "card" scope rules, the '#' symbol should be used to identify the total count of THAT specific card.

4.

When writing rules, use Stats to help debug and test them.

 

Why use stats to debug rules? Well, stats give you direct feedback about the values that are being used within rules. For example, if you've got a rule that is based on a particular tag expression, you can define each term of that expression as a separate stat. Then you can see the actual numbers for each of those terms within the stat display in CV.

Once you have the stats in place, you can add cards to the deck and watch the stats get calculated appropriately. If the stats don't look right, then you can check the tags on individual cards (via the right-click menu) to find out why the stats aren't tallying correctly. Once the stats look right, then you know the basic values used in the rules are correct. So now all you need to worry about is making sure the logic of the rule is correct, instead of also trying to determine whether the component elements of the rule are correct.

This technique makes it much easier to diagnose rules and get them working in CV.

5.

I need a rule to enforce that a sideboard must be 0 or 15 cards.

 

This one is pretty simple. Obviously, it's a deck rule, and the scope of the rule is whichever deck you've designated as the sideboard (e.g. "deck2"). To impose the sideboard rule, you can use the '$' term, which reports the total number of cards in the scope. So the rule should look like:
   ($ = 0) | ($ = 15)

6.

I need a rule that there can't be more than 5 duplicates of any one card in both in the sideboard an

 

This needs to be a card scoping rule, since it applies to a single card at a time. However, since it has to span multiple decks, the proper scope needs to be "span". Since the limit applies to the count of each card, you can use the '#' special term for card rules to obtain that count. Therefore, verifying that you don't have more than 5 of a particular card across all decks would look like:
   (# <= 5)

7.

There are certain cards that can only be played in conjunction with certain others. I need a rule to enforce this.

 

Here's the specific problem. There are multiple decks for this game, and there are certain cards in those decks which can only be played by specific character(s). I need a rule that will verify that the proper character is present whenever any cards restricted to that character are in the deck.

The first step is to put the pieces into place that are required. After that, we'll look at the rule that is needed. This example will use a single character as an example, and the method can be easily extrapolated to other characters.

  1. Start with a tag group named "character" and create a tag for each character. For this example, let's use the name "Fred". So define the tag group and a tag of "Fred" within it.
  2. Assign the "character.Fred" tag to the Fred character card.
  3. Define another tag group named "ischar" and create a tag for each character. We'll use this to identify which cards require which characters. So define the tag group and add a tag of "Fred" within it.
  4. Assign the "ischar.Fred" tag to all cards that require the Fred character to be in the deck.

Everything is in place that we need. Now let's look at the rule you need to write...

  1. The rule needs to span multiple cards, so you have to write a rule with deck scoping.
  2. Since you need to verify that the character card is present for any
    cards requiring the character, you'll have to write a separate rule for each character - i.e. one rule to check for Fred, another for George, etc.
  3. Since we have a separate rule for each character, the rule needs to be declared valid if there are no cards requiring that character. This is done with the term "card:ischar.Fred = 0". So we'll start each rule with a first term of "card:ischar.Fred = 0" and use an OR ('|') to combine it with the rest of the rule. This way, the rest of the rule will be ignored if there are no cards requiring Fred.
  4. If our rule gets past the first term, then we know there is at least one card that requires our character. So the next part is to verify the character is present. This done with the term "card:character.Fred > 0".
  5. Putting it all together, our rule is given below. This rule verifies that we have at least one Fred card when there are any cards present that require Fred.
      (card:ischar.Fred = 0) | (card:character.Fred > 0)
  6. Verifying separately that a card is doesn't have any character requirements is unnecessary with the above rule. If a card has no character requirements, it will satisfy the first term of each rule and be declared valid for each rule.
  7. The last factor to address is the actual scope of the deck rule. Since you have two play decks, you either have to assign the rule a scope of "all" OR you have to define the rule twice, with each instance of the rule applying to a separate deck. However, given your description of things, you should be fine with simply using a single rule with "all" scope.

Now that everything is figured out, the complete rule entry within the data file will look something like this:
<rule id="isFred" scope="all"
  message="One or more cards require Fred" summary="Fred needed">
<![CDATA[
  (card:ischar.Fred = 0) | (card:character.Fred < 0)
]]>
</rule>

8.

Designing a rule to deny including some cards with other cards

 

Here is the problem put forth by a user:
I am contemplating how to set up a tag structure so that I can try and handle mechanics like "Will not join Scorpion Clan". I have a tag group "deckis" that has the tag value "Scorpion". I have a tag group "restricts" that has a value "NoScorp". How can I create a rule that will complain if a card with restricts.NoScorp is put into a deck with deckis.Scorpion? Or should I set up some other mechanic?
The answer:
You should be able to write a deck rule that looks something like the following:
sum:deckis.Scorpion * 999 * sum:restricts.NoScorp <= sum:restricts.NoScorp
The above rule totals up the number of Scorpion-only cards and compares it to the number of cards that preclude Scorpion. The reason for the "* 999" is to ensure that a single Scorpion-only card will cause the rule to fail for any number of no-Scorpion cards. The reason for the "* sum:restricts.NoScorp" is a bit more insidius. What if there are NO no-Scorpion cards in the deck? Then the rule will always fail because a single Scorpion card will be greater than zero. So how to fix it? Multiply by the number of no-Scorpion cards on the left. This way, if there are no no-Scorpion cards, you'll get "0 <= 0" and the rule succeeds. Since we just want a big number on the left, a non-zero value for NoScorp just makes our number bigger, and we get the proper desired result.

9.

For my skin, the transparent regions of my scrollbar mask are showing up black.

 

This is correct behavior. The scroller itself is a separate child window and not a region of the containing window. Consequently, a transparent region of the scroll BAR will simply show the solid background color assigned to the scroller. Black is the default background color for the scroller window, so that's what shows through.