Controlling Lua Enhancements with Rules.txt

Prof. Garfield

Deity
Supporter
Joined
Mar 6, 2004
Messages
4,365
Location
Ontario
There has been a bit of a discussion today starting from this post in the main TOTPP thread. @techumseh asked for the ability to generalise the pikeman bonus to be added to the TOTPP. What he wants can already be achieved with Lua (especially thanks to the combat calculator work @Knighttime did), but the argument was made that having the feature directly in the rules will make it more accessible to scenario designers. I certainly agree that the current state of the Lua Scenario Template does not allow a new programmer to make combat changes.

I made a quick check today, and having extra "@" sections in the rules.txt doesn't appear to cause any problems in the game. (I haven't done much more than load a game with an extra section, but this idea would work with a separate file anyway.) I already have a module that can read the rules.txt file for the scenario, so why not just add extra sections to the rules.txt to control certain aspects of the game? This would be a very familiar way of controlling the game, but wouldn't require @TheNamelessOne 's attention.

I'm willing to program the features in if people want it, but I'm going to need experienced designers to determine what should be included and how to format it.
 
What kind of features could be added? I'm assuming your code could tell that commas indicate a new input is about to follow (like it the regular rules). It would be awesome if we could have @Units3 or whatever that has a row of new fields that we could utilize.

Some that are becoming pretty common or likely will be:

-cost to attack
-cost to move
-native transport that actually works
-land transporter (not sure if this is too complicated for this)
-aircraft carrier restricted (so easily no more use of a carrier for certain planes)

It would be awesome to have a simple reaction of some sort in rules. I really think this is one of those tools designers would use more if it were more accessible,especially now that player-controlled units "activate" on each tile. Not sure if it's doable with something like this or not but it's been on my mind since that update and I think it would be great for it to be more explored.
 
What kind of features could be added? I'm assuming your code could tell that commas indicate a new input is about to follow (like it the regular rules). It would be awesome if we could have @Units3 or whatever that has a row of new fields that we could utilize.

Basically, if something is achievable with Lua, and can be given adequate flexibility using a relatively small number of settings, it can be put into the extended rules. I suspect that in practice I will have functions that read the rules.txt file, and then build the corresponding tables in the settings files programmatically.

-cost to attack

That makes sense.

-cost to move

I haven't made an 'on move' execution point yet (I should ask TNO if he plans to do that, before leveraging the unit activation event), but once done, that is a good parameter.

-native transport that actually works

As long as the designer doesn't want native transport abilities to change as a result of events within the scenario, this could be read from the existing list in the rules. Perhaps there could be a "COSMICLUA" field that tells the game to do this.

-land transporter (not sure if this is too complicated for this)

As long as the "land transporter" requires storing units on a separate map, then I would consider it too complicated to include in the rules automatically. If not, then it is conceivable that a basic "just works" version could be automatically included, and specified from the rules.

-aircraft carrier restricted (so easily no more use of a carrier for certain planes)

Well, I just made a "navy" module dealing with planes that can use carriers. A simple version would be to have a single flag disabling carrier use. However, range 2+ carrier users will grant the carrier air protected status whenever attacked by a non carrier user. In the navy module, there is an option to make carriers always carry on certain players turns (so each side in a conflict can have its own carrier, if you want to deal with the situation that way). It is details like this which sometimes make it difficult to design settings that are both simple and universal, which is kind of required for a rules.txt interaction with Lua.

It would be awesome to have a simple reaction of some sort in rules. I really think this is one of those tools designers would use more if it were more accessible,especially now that player-controlled units "activate" on each tile. Not sure if it's doable with something like this or not but it's been on my mind since that update and I think it would be great for it to be more explored.

Reactions get very complicated very quickly. So complicated, in fact, that I don't have a generic settings file for them. I wonder if they might be obsolete with the ability of combat to end with both units alive. Most range 1 attacks in OTR, for example, could probably be redone with onInitiateCombat. However, if you want to propose a reaction paradigm that can be specified with 1 line of flags per unit, I'd be willing to implement it.

One thing I'd like to see is increased control over abilities of city improvements and wonders.

TOTPP doesn't give much control over city processing. We can change the food/shields/trade "harvested", but can't do much beyond that (like control tax/lux or sci multipliers from improvements, or how many citizens are content/happy). We can control things that happen outside the city processing, like defence bonuses or whether units automatically receive veteran status.
 
Reactions get very complicated very quickly. So complicated, in fact, that I don't have a generic settings file for them. I wonder if they might be obsolete with the ability of combat to end with both units alive. Most range 1 attacks in OTR, for example, could probably be redone with onInitiateCombat. However, if you want to propose a reaction paradigm that can be specified with 1 line of flags per unit, I'd be willing to implement it.

I was thinking about this a little earlier and how to make it easy. In essence I think that a "simple" reaction would check this for each unit. Let's pretend it's a SAM site:

Unit: SAM Battery
First let's define where it Can react from:
Can React WHILE on Map 0
Can React WHILE on Map 1
Can React WHILE on Map 2
Can React WHILE on Map 3
Next let's define where it can react to:
Can React to Unit on Map 0?
Can React to Unit on Map 1?
Can React to Unit on Map 2?
Can React to Unit on map 3?
Next let's define WHAT it can react to:
Can React to Domain 0?
Can React to Domain 1?
Can Reaction to Domain 2?
Let's Carve Out if there is a ROLE it won't react to (to give greater flexibility - maybe bombers only react to fighters that come near them, but not other bombers, for example).
Will React to Role 0
Will React to Role 1
Will React to Role 2
Will React to Role 3
Will React to Role 4
Will React to Role 5
Will React to Role 6
Will React to Role 7
Distance it can react (in tiles)
Times it can react per turn
Can Take Damage While Reaction? Yes, No, 1/2 (if no, then it simply deals damage, if yes, then the other unit can strike back, if 1/2 (which might be "flag 2", then units that defend against it might have a penalty).

I was thinking it might be "simple" to just have it use its ordinary attack, defense, hitpower, firepower, and flags (such as x2 vs. air) to compute the actual damage.

This is 22 "flags" I suppose which wouldn't be ridiculous in my mind: 0000000000000000000000

So maybe a SAM site that I wanted to only hit Air Units on maps 0 and 1 with the attack or air superiority flag at a distance of 3 tiles 2 times with impunity would look like this (not reversed):

1000110001010010000320

Would something like this work?
 
Last edited:
Just as an aside, perhaps if you were building this, one of the "core" values you could have for every other units in @Units3 or whathave you would be "Ignores Reactions" - so in this same SAM battery example, I could have a wild weasel unit that is capable of ignoring the defenses.

Edit and as one more aside - we have "sees two spaces." What about "Sees how many spaces" and it can be input from 1-9?
 
This is 22 "flags" I suppose which wouldn't be ridiculous in my mind: 0000000000000000000000

So maybe a SAM site that I wanted to only hit Air Units on maps 0 and 1 with the attack or air superiority flag at a distance of 3 tiles 2 times with impunity would look like this (not reversed):

1000110001010010000320

Would something like this work?

Seems reasonable to me. (I'd split the flags into smaller groups with commas, but that sort of detail can be worked out later.)

Would this be a reaction to combat, firing a projectile, or just coming into range?

Edit and as one more aside - we have "sees two spaces." What about "Sees how many spaces" and it can be input from 1-9?

I hadn't thought about that, but I think we now have all the tools to extend sight radius with Lua, although that would involve using an "on move into tile" execution point, which I haven't implemented yet.
 
I wonder if they might be obsolete with the ability of combat to end with both units alive.

Would this be a reaction to combat, firing a projectile, or just coming into range?

The reason we used them in OTR probably doesn't exist anymore given this, but I do think there's a wide range of situations they're useful for. I'd actually argue that they are all the more enticing now that onActivate works per tile for everyone. The reason being, the AI can "use" it flawlessly if we just go with a "coming into range" trigger. We couldn't (or maybe we could some other way, but not as easily certainly) do that before when we needed a different trigger, like a key press, that the AI would never know to use. The AI knows how to approach units, and also knows how to move its own units out into the world on defensible terrain. In my mind the onActivate makes this much more useful for single player games.

I guess one thing I didn't add in for the flags would be "chance". You'd probably want some random element to it. I think we could still use flags though and just keep it as simple as 0 = 100% chance, 1 = 10% chance, 2 = 20% chance, etc. That way it's still just one flag, and also allows for "better" units to have a "better" chance of having the reaction.
 
Hey hey, you sillies crafters, don't forget @techumseh initial wish which is way simplier yet leaves questions :

-How to organize groups (unlimited integers on tech groups fashion ?)
-How to organize group relations (something similar to the transporters one with a strength factor ?)

:)
 
Last edited:
Here's a sample specification for modifying combat groups.
Code:
;       Custom Combat Modifiers
; A) Unit Name: No direct effect, but if the unit name doesn't match
;       the name for the unit with the same ID, a warning is printed
;       in the console
; B) Group Membership mask:     0: not in group;    1: in group
;       00000001    Group 0
;       00000010    Group 1
;       00000100    Group 2
;       00001000    Group 3
;       00010000    Group 4
;       00100000    Group 5
;       01000000    Group 6
;       10000000    Group 7
; C) Percentage Increment:      Determines how much the modifier masks change with
;                               each increase.  25 means the increment is 25%
; D) Attack Modifier mask:      0: Can't attack group, 1-9: multiply attack power by percentage increment 
;                               when attacking that group.  That is, if the increment is 25,
;                               1: 25% power, 2: 50% power, 3: 75% power, 4: 100%, 5: 125%
;                               *: attack with normal power against group
; E) Defense Modifier mask:     0-9: multiply defender power by the percentage increment
;                               when defending against attacks from that group.
;                               That is, if the increment is 33.
;                               1: 33% of normal, 2: 66% of normal, 3: 99% normal, 4: 132% normal, etc
;                               *: defend at normal value against group
;   A               B       C       D           E
Settlers,       00000001,   25, ********,   ******5* ;
Engineers,      00000001,   50, ********,   ******3* ;
Warriors,       00000000,   40, ******03,   ******** ;
Phalanx,        00000010,   50, ********,   ******** ;

Read the documentation and predict how the four units interact in combat. If it is different from my explanation, let me know, since then the documentation isn't clear

Spoiler Read documentation first :

Settlers and engineers are part of "group 0", and phalanx is part of "group 1".
Settlers defend against group 1 units at 125%, and engineers defend at 150%. In all other combat, these units have their normal attack or defense stat.
Warriors can't attack group 1 (the attack will be cancelled before the first round), and attack group 0 at 120%. All other combat situations are done at normal strength.


Any thoughts?
 
Looks really really great prof, and the related commantaries are excellent too !

Little question there, thinking too much is better than not enough :
Is it an issue to double the number of groups ? 8 may limit them sometimes, while 16 gives quite some more room ?
@CurtSibling , @techumseh ,* what are your opinions on that matter ? Is 8 unit groups (+the hardcoded pixers one) definitly enough (which would free prof from my nagging there :D ) ?

*I'm not forgetting you @JPetroski , and your opinion is welcome too. Just, you're kind of a veteran coder now already using it in lua ;)
 
"Kind of veteran?" @JPetroski is a full coder arch-mage at this point!

More like this at this stage.

upload_2022-3-10_7-15-12.png
 
Is it an issue to double the number of groups ? 8 may limit them sometimes, while 16 gives quite some more room ?

There was no particular reason for choosing 8 groups other than brevity. I was planning on making the code handle an arbitrary number of groups, and having some parameter specify how many to expect. With a bit of reflection, I'm inclined to say that if you need more than 16 extra combat modifiers, it might be time to ask someone to code in the actual combat system that you want, or to reflect on whether that system is too complicated.
 
Prof's new navy settings might already cover this....But...
I think having a section on what air units can use a carrier flagged unit would be of great use.
And (perhaps) also what sort of units can get on board a naval transport...Having this in a elegant
"@" section in rules would be huge...:)
 
Looks really really great prof, and the related commantaries are excellent too !

Little question there, thinking too much is better than not enough :
Is it an issue to double the number of groups ? 8 may limit them sometimes, while 16 gives quite some more room ?
@CurtSibling , @techumseh ,* what are your opinions on that matter ? Is 8 unit groups (+the hardcoded pixers one) definitly enough (which would free prof from my nagging there :D ) ?

*I'm not forgetting you @JPetroski , and your opinion is welcome too. Just, you're kind of a veteran coder now already using it in lua ;)

8 seems plenty. But as Bill Gates said, "64K should be enough for anybody".
 
Top Bottom