Difference between revisions of "Oolite JavaScript Reference: Condition scripts"

From Elite Wiki
(Initial documentation of condition scripts)
 
(Updating BB links)
 
(14 intermediate revisions by 5 users not shown)
Line 1: Line 1:
'''NOTE: This page documents a feature planned for Oolite 1.77, which is potentially subject to significant change before then.'''
+
== Condition scripts ==
 +
Condition scripts are used to set conditions on the appearance of ships and equipment beyond the basics possible in [[shipdata.plist]], [[shipyard.plist]], [[shiplibrary.plist]] and [[equipment.plist]]. They have a similar purpose to the "conditions" parameters in those plists, which use the legacy scripting engine, but have the full flexibility of the Javascript scripting engine. If both "conditions" and a condition script are specified for the same item, they will both be tested (but you should never need to do this).
  
=Condition scripts=
+
Conditions scripts may define any or all of the following methods. There is a single instance of each condition script regardless of how many ships and equipment items use it, so variables may be shared between calls in <code>this._property</code>
Condition scripts are used to set conditions on the appearance of ships and equipment beyond the basics possible in [[shipdata.plist]], [[shipyard.plist]] and [[equipment.plist]]. They supersede the "conditions" parameters in those plists, which use the legacy scripting engine.
 
  
Conditions scripts may define any or all of the following functions. There is a single instance of each condition script regardless of how many ships and equipment items use it, so variables may be shared between calls in <code>this._property</code>
+
In 1.81 the scripts are extended slightly to modify ''how'' things may appear as well as whether they may appear.
  
==allowAwardEquipment==
+
=== allowAwardEquipment ===
 
{{oolite-method-added|1.77}}
 
{{oolite-method-added|1.77}}
  
This method is called when the game engine needs to know whether a particular ship can have equipment fitted. This may be because the player is looking at possible upgrades at a station, or from a call to [[Oolite_JavaScript_Reference:_Ship#canAwardEquipment|ship.canAwardEquipment]] or [[Oolite_JavaScript_Reference:_Ship#canAwardEquipment|ship.awardEquipment]], or for other similar reasons. The equipment key and a reference to the ship entity are passed as parameters. If the method does not exist, or returns a value other than <code>false</code>, then the equipment may be added or offered for sale (subject to other conditions, of course)
+
In order for this method to be called, the <code>condition_script</code> property of an equipment item (as declared in the [[Equipment.plist]] file) must be specified, it must declare the name of the Javascript file where the method exists, and the method must exist in the referenced JavaScript file. The method will only be called for the equipment items which reference the condition script.
  
  this.allowAwardEquipment = function(eqKey, ship)
+
This method is called when the game engine needs to know whether a particular ship can have equipment fitted. In other words, it is asking whether to allow equipment to be awarded to a ship. This may be because the player is looking at possible upgrades at a station (on the F3 Equip Ship screen), or from a call to [[Oolite_JavaScript_Reference:_Ship#canAwardEquipment|ship.canAwardEquipment]] or [[Oolite_JavaScript_Reference:_Ship#canAwardEquipment|ship.awardEquipment]], or for other similar reasons. The equipment key and a reference to the ship entity are passed as parameters. You would use this method to control if, and under what conditions, a piece of equipment is offered for purchase and installation. Returning a value of <code>true</code> would indicate that the equipment can be installed; returning a value of <code>false</code> indicates the equipment can't be installed and so it won't appear on the F3 Equip Ship screen, and any of the JavaScript methods to add the equipment item would fail. If the method does not exist, or returns a value other than <code>false</code>, then a value of <code>true</code> is assumed and the equipment may be added or offered for sale (subject to other conditions, of course, like TL constraints)
 +
 
 +
<code>context</code> will be one of:
 +
* <code>"newShip"</code> - equipment for a ship in a station shipyard (F3 F3)
 +
* <code>"npc"</code> - awarding equipment to NPC on ship setup
 +
* <code>"purchase"</code> - equipment for purchase on the F3 screen
 +
* <code>"scripted"</code> - equipment added by JS or legacy scripts
 +
(Context can in theory also be <code>"loading"</code>, <code>"damage"</code> or <code>"portable"</code>, but if you see one of these, it's a bug)
 +
 
 +
  this.allowAwardEquipment = function(eqKey, ship, context)
 
  {
 
  {
 
   // your code here
 
   // your code here
Line 17: Line 26:
 
  }
 
  }
  
==allowOfferShip==
+
The standard condition script for the core game equipment allows equipment to be barred using the <code>"oolite-barred-equipment"</code> key in <code>script_info</code>. If this key contains an array of equipment keys, then those items of equipment will not be sold at this station. In 1.79 and later, this <code>script_info</code> key may be applied to any ship, preventing those items being installed onto the ship. For example:
 +
 
 +
script_info = {
 +
  "oolite-barred-equipment" = ("EQ_WEAPON_MILITARY_LASER");
 +
}
 +
 
 +
On a station, this would prevent it selling military lasers. On a ship in 1.79 or later, this would also stop the ship fitting military lasers.
 +
 
 +
If you want to allow your equipment to be barred in the same way, you can either set the <code>condition_script</code> property to use the standart <code>"oolite-conditions.js"</code> script, or add the following snippet to the <code>allowAwardEquipment</code> of your condition script:
 +
// OXP hook to allow stations to forbid specific equipment
 +
if(context == "purchase" && player.ship.dockedStation && player.ship.dockedStation.scriptInfo["oolite-barred-equipment"])
 +
{
 +
  if (player.ship.dockedStation.scriptInfo["oolite-barred-equipment"].indexOf(equipment) != -1)
 +
  {
 +
    return false;
 +
  };
 +
 +
// OXP hook to allow ships to forbid specific "available to all" equipment
 +
if(ship.scriptInfo && ship.scriptInfo["oolite-barred-equipment"] && ship.scriptInfo["oolite-barred-equipment"].indexOf(equipment) != -1)
 +
{
 +
  return false;
 +
};
 +
 
 +
=== allowOfferShip ===
 
{{oolite-method-added|1.77}}
 
{{oolite-method-added|1.77}}
  
Line 28: Line 60:
 
  }
 
  }
  
==allowSpawnShip==
+
=== allowShowLibraryShip ===
 +
{{oolite-method-added|1.81}}
 +
 
 +
This method is called when the ship library is being shown in-game (rather than on the start screen) and determines whether the ship appears on the list for the player to view. If the method does not exist or returns a value which cannot be interpreted as a boolean, it will be assumed to have returned <code>true</code>.
 +
 
 +
this.allowShowLibraryShip = function(shipKey)
 +
{
 +
  // your code here
 +
  return bool;
 +
}
 +
 
 +
=== allowSpawnShip ===
 
{{oolite-method-added|1.77}}
 
{{oolite-method-added|1.77}}
  
Line 38: Line 81:
 
   return bool;
 
   return bool;
 
  }
 
  }
 +
 +
=== updateEquipmentPrice ===
 +
{{oolite-method-added|1.81}}
 +
 +
This method is called when the game engine needs to know the price of fitting equipment covered by this condition script. The method takes an equipment key and the current price as parameters, and must return a non-negative number for the actual price of the equipment.
 +
 +
this.updateEquipmentPrice = function(equipmentKey, currentPrice)
 +
{
 +
  // your code here
 +
  return newPrice;
 +
}
 +
 +
This method is called before [[Shipdata.plist#equipment_price_factor|equipment_price_factor]] is considered.
 +
  
  
 +
== Links ==
 +
There is an extended bulletin board discussion with a couple of examples [https://bb.oolite.space/viewtopic.php?p=286037#p286037 here] (2022).
  
 
[[Category:Oolite JavaScript Reference]]
 
[[Category:Oolite JavaScript Reference]]

Latest revision as of 02:18, 29 February 2024

Condition scripts

Condition scripts are used to set conditions on the appearance of ships and equipment beyond the basics possible in shipdata.plist, shipyard.plist, shiplibrary.plist and equipment.plist. They have a similar purpose to the "conditions" parameters in those plists, which use the legacy scripting engine, but have the full flexibility of the Javascript scripting engine. If both "conditions" and a condition script are specified for the same item, they will both be tested (but you should never need to do this).

Conditions scripts may define any or all of the following methods. There is a single instance of each condition script regardless of how many ships and equipment items use it, so variables may be shared between calls in this._property

In 1.81 the scripts are extended slightly to modify how things may appear as well as whether they may appear.

allowAwardEquipment

This method was added in Oolite test release 1.77.

In order for this method to be called, the condition_script property of an equipment item (as declared in the Equipment.plist file) must be specified, it must declare the name of the Javascript file where the method exists, and the method must exist in the referenced JavaScript file. The method will only be called for the equipment items which reference the condition script.

This method is called when the game engine needs to know whether a particular ship can have equipment fitted. In other words, it is asking whether to allow equipment to be awarded to a ship. This may be because the player is looking at possible upgrades at a station (on the F3 Equip Ship screen), or from a call to ship.canAwardEquipment or ship.awardEquipment, or for other similar reasons. The equipment key and a reference to the ship entity are passed as parameters. You would use this method to control if, and under what conditions, a piece of equipment is offered for purchase and installation. Returning a value of true would indicate that the equipment can be installed; returning a value of false indicates the equipment can't be installed and so it won't appear on the F3 Equip Ship screen, and any of the JavaScript methods to add the equipment item would fail. If the method does not exist, or returns a value other than false, then a value of true is assumed and the equipment may be added or offered for sale (subject to other conditions, of course, like TL constraints)

context will be one of:

  • "newShip" - equipment for a ship in a station shipyard (F3 F3)
  • "npc" - awarding equipment to NPC on ship setup
  • "purchase" - equipment for purchase on the F3 screen
  • "scripted" - equipment added by JS or legacy scripts

(Context can in theory also be "loading", "damage" or "portable", but if you see one of these, it's a bug)

this.allowAwardEquipment = function(eqKey, ship, context)
{
  // your code here
  return bool;
}

The standard condition script for the core game equipment allows equipment to be barred using the "oolite-barred-equipment" key in script_info. If this key contains an array of equipment keys, then those items of equipment will not be sold at this station. In 1.79 and later, this script_info key may be applied to any ship, preventing those items being installed onto the ship. For example:

script_info = {
  "oolite-barred-equipment" = ("EQ_WEAPON_MILITARY_LASER");
}

On a station, this would prevent it selling military lasers. On a ship in 1.79 or later, this would also stop the ship fitting military lasers.

If you want to allow your equipment to be barred in the same way, you can either set the condition_script property to use the standart "oolite-conditions.js" script, or add the following snippet to the allowAwardEquipment of your condition script:

// OXP hook to allow stations to forbid specific equipment
if(context == "purchase" && player.ship.dockedStation && player.ship.dockedStation.scriptInfo["oolite-barred-equipment"])
{
  if (player.ship.dockedStation.scriptInfo["oolite-barred-equipment"].indexOf(equipment) != -1)
  {
    return false;
  };

// OXP hook to allow ships to forbid specific "available to all" equipment
if(ship.scriptInfo && ship.scriptInfo["oolite-barred-equipment"] && ship.scriptInfo["oolite-barred-equipment"].indexOf(equipment) != -1)
{
  return false;
};

allowOfferShip

This method was added in Oolite test release 1.77.

This method is called when the game engine is considering adding a ship managed by this condition script to a shipyard. If the method does not exist, or returns a value other than false, then the ship may appear for sale (or it may not, for a variety of other reasons). The ship key from shipyard.plist is passed as a parameter.

this.allowOfferShip = function(shipKey)
{
  // your code here
  return bool;
}

allowShowLibraryShip

This method was added in Oolite test release 1.81.

This method is called when the ship library is being shown in-game (rather than on the start screen) and determines whether the ship appears on the list for the player to view. If the method does not exist or returns a value which cannot be interpreted as a boolean, it will be assumed to have returned true.

this.allowShowLibraryShip = function(shipKey)
{
  // your code here
  return bool;
}

allowSpawnShip

This method was added in Oolite test release 1.77.

This method is called when the game engine is considering spawning a ship managed by this condition script. If the method does not exist, or returns a value other than false, then the ship may be spawned (or it may not, if another ship with the appropriate role is selected instead). The ship key from shipdata.plist is passed as a parameter.

this.allowSpawnShip = function(shipKey)
{
  // your code here
  return bool;
}

updateEquipmentPrice

This method was added in Oolite test release 1.81.

This method is called when the game engine needs to know the price of fitting equipment covered by this condition script. The method takes an equipment key and the current price as parameters, and must return a non-negative number for the actual price of the equipment.

this.updateEquipmentPrice = function(equipmentKey, currentPrice)
{
  // your code here
  return newPrice;
}

This method is called before equipment_price_factor is considered.


Links

There is an extended bulletin board discussion with a couple of examples here (2022).