This document describes API changes for 1.7 Beta 1.

Items

<GetDisplayAttributes> event

This event can be used to programmatically set display attributes on an item. The event should return a list of display attributes. For example:

<GetDisplayAttributes>
   (list "blessed" "rusted")
</GetDisplayAttributes>

The above code will cause the item to display those two attributes. By default, the attributes are considered neutral; you may use a labelType to specify advantages (shown in blue) or disadvantages (shown in red):

<GetDisplayAttributes>
   (list
      { label:"blessed"   labelType:'advantage }
      { label:"rusted"    labelType:'disadvantage }
      )
</GetDisplayAttributes>

Armor

Using Armor Items

Two new parameters have been added for armor that can be used: asArmorSet="true" and completeArmorOnly="true". For example:

<ItemType ...
   ...
   <Invoke 
         asArmorSet="true"
         installedOnly="true"
         >
      ...
   </Invoke>
</ItemType>

When applied to armor, the above will show a single entry for the armor item regardless of the number of segments installed. For example, if there are three of the above armor segments installed, we only show a single entry in the Use Menu.

When invoked, only one of the armor segments will be called, and it is up to the code in <Invoke> to deal with other armor segments (including them or not as appropriate).

Note also that installedOnly="true" is required if you want to use the armor only when installed. Otherwise, you'll get the Use Menu when installed and uninstalled.

The completeArmorOnly="true" parameter requires that all armor segments be of the same type.

New Properties

API 31 adds the following new properties to armor items:

  • 'completeSet: Returns True if this armor segment is part of a complete set. That is, if all segments on the ship are of the same type. This property only works with objGetItemProperty.
  • 'primeSegment: Returns True is this segment is the first segment of a set of armor of the same type. This is particularly useful when handling an <OnUpdate> or <OnAIUpdate> for an armor type. In some cases you may want to handle the update only once for all segments. In that case, you can check for this property and only proceed if the result is True. This property works even if not all segments are of the same type, and even if there is only one segment of each type. This property only works with objGetItemProperty.

Weapons

Variants

API 30 introduced the concept of scalable weapons. A scalable weapon is a single item type which can be altered at runtime by setting some property (in this case, the level of the item).

API 31 generalizes this into the concept of variants. A single weapon can optionally define a set of variants and select a given variant at runtime. The syntax for defining a variant is identical to that for defining missiles, but with different tag names:

<ItemType unid="..."
   ...
   >
   <Weapon
      ...
      >
      <Variants type="charges">
         <Variant
            type=    "missile"
            damage=  "kinetic:1d6"
            ...
            />
         <Variant
            type=    "missile"
            damage=  "blast:1d6"
            ...
            />
         ...
      </Variants>
   </Weapon>
</ItemType>

The example above defines multiple variants of a single weapon. The type= parameter (in the <Variants> element) controls how the variant is selected. The following types are supported:

  • type="charges": The active variant is selected by setting the charges value for the item (e.g., (itmSetProperty theItem 'charges ...)). The first variant is selected with charges = 0, the second with charges = 1, etc.
  • type="levels": The variant is selected by setting the item's level. The starting level and the maximum level must still be set in the item type (as with scalable items). The first variant is selected by setting the item to the lowest level. Note that this allows far more control over the properties of a weapon at a given level. The prior method for defining scalable weapons is still fully supported, as it allows for automatic definition of levels.
  • type="missiles": For full generality, we support this type, which is equivalent to the original method for defining missiles. When this type is used the weapon is automatically designated as a launcher. Switching between variants is done with the missile select key.

Extensions

Starting in API 31, the extends= parameter on an extension can refer to a library. This allows an extension to not have to specify every adventure by UNID. For example, the HD extension extends the Human Space library, which means it will be included in any adventure that directly includes Human Space.

Any adventures using API 26 and above will need to include the Human Space library in order to get the HD extension and the Soundtrack extension. [This should already be the case, since API 26 requires explicit includes of Human Space if the adventure uses it.]

Pre-API 26 adventures will use the compatibility library, which triggers inclusion of the HD and Soundtrack extensions.

Sovereigns

Sovereigns now keep track of how many of their ships/stations have been killed by the player. For stations, we only count major stations, which either have the populated or the score attribute.

You can retrieve these values as type properties:

(typGetProperty someSovereign 'shipsDestroyedByPlayer)
(typGetProperty someSovereign 'stationsDestroyedByPlayer)

We also compute a threat level for the player based on how many ships/stations they've killed. Threat level can be one of the following values:

4 = Existential threat. More than 10 stations destroyed.
3 = Major threat. More than 5 stations destroyed
    or more than 15 ships destroyed.
2 = Raider threat. At least one station destroyed.
1 = Piracy threat. More than 5 ships destroyed.
0 = No threat.

You may access this value with the 'playerThreatLevel property.

Eventually we'll use this system to implement some smarter behavior for sovereigns.

For now, this is only in one place. If the player is a major threat or above, then friendly stations will instantly blacklist on any attack. For example, if the player has destroyed more than 15 Commonwealth ships, then hitting a Commonwealth station (even by accident) will blacklist the player.

Miscellaneous

  • All ship classes now generate a default <PlayerSetting> definition if none if provided. This allows any ship to be a player ship (can switch to it using plyChangeShip).
  • <Sound> resources are now treated like other design types; they override correctly.
  • <OnUpdate> is called every 30 ticks for every object type (including missions). No need to register for events.
  • <GetDockScreen> is now called when determining whether the player can dock with an object. Previously, if a station did not have a defined dock screen, but did provide one in <GetDockScreen>, the player could not dock.
  • The core engine defines svNeutral, which is a neutral sovereign friendly with everyone (except destructive chaos). All planets, stars, asteroids, as well as wrecks and stargates are now svNeutral instead of svIndependent (the latter was only friendly with constructive alignments).
  • If a <StationType> does not specify a sovereign, it defaults to svNeutral.
  • Added 'waitForThreat order. This waits either until the timer runs out, or until something threatens the ship (same as gateOnThreat) and then goes on to the next order.
  • Added 'target and 'source properties for missiles (which can be set).
  • <OnSystemWeaponFire> now defines aShotObj as the object pointer for the actual shot.
  • <OnSystemWeaponFire> gets called for repeated shots. aFireRepeat is set to the ordinal number of the repeated shot (where 0 = original shot).
  • Added (sysGetLightIntensity pos), which returns a light level from 0-100. It will return 100 within 15 light seconds of a star and 0 beyond the star's maximum light radius. The intensity decreases linearly (not inverse-square).
  • rpgInstallDevicePrep now honors <Trade> limits even if totalPrice is specified. See: https://ministry.kronosaur.com/record.hexm?id=58343.

TLisp

This section describes changes to TLisp in API 31:

  • (itmFireEvent item event [data]): Triggers the given event.
  • (objFireItemInvoke obj item): Programmatically uses the given item.
  • The sort function can sort structs by any field. E.g., (sort myListOfStructs 'ascending 'fieldA) will sort the list of structs by fieldA.
  • Vector functions now optionally accept floating-point values.
  • Options for (sysGetRandomLocation) now accepts objType, which is the type of station to place (helpful for handling exclusion regions).
  • (scrRemoveAction) no longer throws an error for non-existent action IDs. Instead, it just returns Nil. This allows you to call it to remove actions that may or may not be there, without having to check first.
  • Added 'ascended property for objects, which returns True if the object is ascended.
  • (objGetObjByID ...) now works on ascended objects.

VFX

Ray

  • Added style="whiptail", which is an oscillating sine wave.
  • Added animate="cycle", which works with whiptail to animate through a sine wave cycle.
nms 29 Oct 2016:

I'm all for improving the functionality of labels, but it would be even better if we could specify the background color. See:
Request: Better ItemAttribute label functionality
Military and Illegal tags should be unique colors