Space Engineers

Space Engineers

[APck] AutoPillock Core 1.0
cheerkin  [developer] 12 Feb, 2024 @ 1:28pm
User guide
Terms
  • PB - programmable block.
  • APck - AutoPillock script, PB that runs AutoPillock script.
  • Command - a script argument. It can be several types - toggle, command, etc, but I would refer it as just command.
  • Boot Sequence - commands placed into APck PB CustomData. They are ran immediately on recompile/recycle.
  • Recycle - the result of running command:recycle on APck. Almost similar to recompile, it resets state, clears tasks, re-executes Boot Sequence.
  • Unit or Agent - a single logical instance of APckUnit that has its' own blocks, task queue, weapons, etc. In other words, its a minimal usable unit. One physical APck can run many Units via SubUnit feature.
  • SubUnit - a Unit that is not primary for a given APck instance. They are created dynamically by the main Unit and can be added any time as long as their required blocks exist on the grid.
  • Parent or TG.Parent - a unit that is the leader of TacticalGraph formation in which said unit happened to be.
  • Child or TG.Child or Subordinate - a TacticalGraph subordinate of said unit, in other words, unit that is suitable to formation task.
  • STQ, Saved Task Queue - permanently PB-stored task sequence that can be executed on demand.

For APck veterans, what is new in 1.0:
Many new conditions and shifters, check out these sections. Ram task is removed. Condition triggers are decoupled from WeapBot and can be associated with any task type, not only combat. New task creation attributes (FlyThrough, Circumnavigate, etc). Awareness setting is removed, now it is always global (TGP, apck designators and other sources are unified). TGP is released so it is now the preferred way of providing targeting data, used in conjunction with Target Query and multitargeting features.

For advanced targeting options refer to TGP page, it is outside of this guides' scope. For simple targeting, just rely on x-designators, there is no user input needed.

Intro

The APck can react to several things. The main way of influencing its' operation from a user point is running commands.

Boot Sequence

Commands can be placed into APck PB CustomData. They are ran immediately on recompile/recycle. A good way to getting familiar with APck is to look into CustomData of an existing build.
After you change Boot Sequence, you should recompile or recycle, if you want the new behavior immediately.
Commands can be 'commented out' by placing leading '//'. I often do that to not have typing commands when I want to alter behavior. I just comment out one line and uncomment alternative one.

The most obvious example:
//command:set-response:Attack command:set-response:FreeFire

Commands batching

You can issue many commands with one arg using this convention: [cmd1],[cmd2]...[cmdN]. As usual, this means direct argument pass, placing a line in Bood Sequence, using TreeMenuCommand, or making a toolbar action.

Commands routing

Any command can have filtering and routing prefix (first part when split by ':').
Example: bc<heavy bomber>:command:create-task:attack

Filtering prefix can be:
- tag, wrapped in (<>). It would try to match the Units' tag. Unit tag can be set in APck PB name wrapped in ([]). E.g. name: a-core [tag=heavy bomber-1]. If it gets command with <heavy bomber> prefix, it would match, but would not match <heavy bomber-5>
- index. A number wrapped in ([]), zero-based. This is used only for a Unit that has SubUnits or Subordinates to route a command to a index-based unit. E.g. 'su[0]:command:create-task:attack', 'w[3]:command:create-task:attack'

Routing prefix can be:

bc - pass command to everybody in antenna range, exept myself. Can use tag filter. To include this unit use command batch. E.g. '[command:cmd1],[bc:command:cmd1]'.
w - pass command to wingmen (subordinates). Can use index and tag filter.
su - pass command to SubUnit. Can use index and tag filter.
p - pass command to Parent. Can use tag.

Note that sub-units are not technically subordinates, but they would always be in the formation. In case they are doing the wingman task, they are joined with tier-1 subordinates. Thus w prefix does not work for them



Formations, subordination (TacticalGraph)

Units can be orhanized into tree-like structure, where each unit can have only one parent, but a parent can have many children.
Connection is based on "rank" system and constrained by range. On start, after recycle or recompile, TacticalGraph listens to other units for a few seconds, and then chooses a unit that has [rank-1] and is closer than [D]. If successful, the unit marks that one as a Parent, and tells the Parent to mark him as a Child.
That means, if you recompile the Parent, the link with all subordinates is broken. If you recompile or add a new unit intended to be a Child, then the link would be set up as long as conditions are met. In other words, the link is child-initiated.
To set a rank, add [rank=X] in the APck PB CustomName.
To change [D], which is 500m by default, run command:set-value:tg-autolink-range:X (by this moment you should guess that it needs to be done on Child unit rather than formation leader).

Example:
Two big ships that have rank 10 and rank 50, five small ships with rank 11 and five with 51. After TG resolve, two big ships would have 5 suborditates each.
Two big ships that have rank 10, ten small ships with rank 11. After TG resolve, if all ships are within 500 range, one big ship would have all 10 subordinates. If they are spaced out (500+ m between groups), then they can link to their nearby parent big ship. With this approcah, it is possible to have big ships as children for a rank-9 ship.

This is not very convenient way for subordination deeper that 1 level. I have ideas to rework TacticalGraph, but for now it stays like this.




Captain module.

This is the module that handles tasks, target awareness and response. It gives move/aim assignment to Pilot module.

It has a few special properties that user can ineract with.

Response Kind - How to respond when aware of enemy. FreeFire - don't stop doing current task or sitting idle, but shoot enemy when it is in range, also use PMWs when available. Attack - immediately inject Attack task and actively engage.

Response Override - Command to execute instead of Attack task injection. By default, if Response Kind is Attack, the Cap injects Attack task. This is not suitable for certain builds like missiles. You can override it with appropriate command, usually placed in Boot Sequence. You can place {id} placeholder to have it replaced with current target id by the WeapBot. Example for missile: 'command:set-response-ovr:command:inject-task:ram:TargetId={id}'.

Timer triggers - you can add timer following naming convention: {task kind}.OnStart, {task kind}.OnComplete. Taks kind is the thing you see in the log along with id, like move-11, attack-2 or landing-69. You don't use the id, just the first part before '-'.
So, if you want to trigger a timer when you finish docking, you can add a timer 'Timer Whatever landing.OnComplete'.
For Ram task (missile behavior), there is a flexible proximity timer feature.
You can add timer tagged 'proximity100' to have it triggered 100m before impact, 'proximity511' - closer than 511, etc, and you can have as many of them as you can fit on the missile.

InferTask - you can create task by using current position. Supported tasks: move, dock, land. Add wait-for-signal tast beforehand, or this new task would be immediately completed. For dock, you need to be connected to connector. For land - resting with landing gear on the surface. The script would record matrices of gear/connector and create appropriate task. It can be later re-used from exec-queue, by repeat order, etc.

Default task - you can have permanently set default task to be added every time the task queue gets empty. This task auto-completes when Cap gets any other new task, and adds istelf back again as soon as all tasks are finished.

Saved Task Queue - permanently save current task buffer (task history starting from the last wait-for-signal) for later use. Typical case: you want to make shuttle to go between docks. Start by making a wait for signal task to stop the unit from immediate action (command:create-task:wait-for-signal). Then add up tasks however you want. You can fly the actual unit and use InferTask to create tasks. Then you add repeat command at the end using TaskExecute (command:create-task:exec:FollowUp=command;repeat). At this point you can store the queue (command:save-queue). After recompile or copying the unit you can use command:exec-queue any time, or have it placed in Boot Sequence.




Pilot module

It provides grid movement and rotation using own hardware or by delegating this task to external scripts like ThrustProvider.

The vanilla dampening should be off. By default, the Pilot dampens inertia, you can switch that using toggle:damp-when-idle.

It always cancels out gravity, so if you want 'zero-g flight' on planet you can turn dampening off with 'toggle:damp-when-idle:true'.

Sometimes you want the APck to stop touching thrust or gyro override, you can switch that using 'toggle:suppress-transition-control' and 'toggle:suppress-gyro-control'.

APck can have different thruster set-ups. The most common is '3dThrust' - when you have at least one thruster in each direction, or at least 3 grav gens, in other words, when the grid can move in any direction without having to rotate. Then it can have single thrust set-up that heavily limits the number of compatible tasks, it is mostly used for compact missiles. In this set-up the Pilot ignores Aim behaviors and rotates to fulfill movement assignment. And finally, it can have ThrustDelegation, when APck assumes that external script has all means of moving the grid. In this mode it passes move assignment to external script (move point, target velocity, own velocity, speed limit, etc). In this mode Cap can work in 'hybrid-mode' (toggle:vtol-hybrid) when the external script passes back the Force vector it applied, so the Pilot would still use its' thrusters tp assist.




WeapBot module

WeapBot aims and uses weapons and controls desiged combat distance based on installed weapons and setting.

Settings

1. PMW_FF_REACTION_R - top of the code. Changes the distance for threat reaction when an agent has PMWs like sub-units or dumb-units (default is 2500).

2. Set-values and toggles. See script argument reference for more info on those settings:

wb-range-override
wb-precision-override
wb-model-cycle-timeout
ripple-increment-interval
torpedo-fuse-offset
wb-snipe-range

Combat range

If there is a designator turret, then short-range distance is set to 550/700m, depending on grid size.
If there are player-made weapons (sub-unit, dumb-unit), then long-range is set to PMW_FF_REACTION_R.

Otherwise, short/long range is chosen from a weapon with the shortest/longest range available.

If wb-snipe-range toggle is set to true, then resulting combat range would be the long-range value minus 50m.
Otherwise, CR would be the short-range value minus 50m.

Finally, if the wb-range-override is set to non-zero value, CR would be set to that value, no matter what weapons/turrets/PMWs are available.

WeaponFaces

Weapons are organized into WeaponFaces, one per grid direction, so up to 6 is possible. E.g. you can have guns pointing forward and left, so there would be two WeaponFaces.
WeaponFace contains 1+ WeaponGroups, they represent different types of weapons. WeapBot switches weapon groups automatically, based on weapon cooldown rate. It wouldn't switch faces on its' own yet, so you need to tell it explicitly to do so:
command:wb-cycle-face

You can pass index as a parameter. I.e. if you have 2 weapon faces, set the default (usually forward-looking) by "command:wb-cycle-face:0", second by "command:wb-cycle-face:1", etc.

You can automate it using conditional commands.

Condition checks & triggers

You can add a Condition to be tested during specific task.

Format: command:add-condition:{task-kind aka type}:{interval?}:{cooldown?}:{check1}&{check2?}&{checkN?}:{command|toggle}:{the rest is usual command tail}

! This section was moved to Engineer guide to make this guide less scary.



Tasks

Additional terms
  • Task - an assignment to do something in a certain way
  • Task Queue - a sequence of Tasks to be executed one by one
  • Kind - task type
  • Attribute - named value that overrides or defines certain aspect of a Task
  • Position - world coordinates of a point, similar to GPS, usually defining a target for a Task
  • OnStart - event that triggers when a Task is initialized and actually started (not created or added)
  • OnComplete - event that triggers when a Task is completed and removed

General format
'command:create-task:{kind}:{attribute-pairs?}:{p.X:p.Y:p.Z?}'

As usual, command parts are separated with ':'.

Task kinds part (required)

orbit
wait
wait-for-signal
exec
cruise-fw
move
move-rel
jab
attack
follow
wingman
dock
maintenance
cargo
land

Attributes (optional part)

Comma-delimeted key-value pairs. If any value contains ':', it should be escaped (replaced) with ';'.

Example:
command:create-task:attack:Name=slowpoke,TargetId=100500,SpeedLimit=10
Here, we have two attributes set. Attributes part is 'Name=slowpoke,TargetId=100500,SpeedLimit=10'.

TargetId attribute is a special one - if you don't supply it for a task that needs it, then the code would use Captains' TargetId (see above).

Usually attributes are specific to a certain task kind, but there are also uniform ones (which means they can be included in any task creation command):
Name - task name override;
Ticks - time limit, counting from actual task start (not creation), in ticks. There are 60 ticks in a second, for a default script update rate;
SpeedLimit - max speed, in m/s;
Proximity - override for a distance at which waypoint is considered reached;
FlyThrough - override to force a fly-through behavior (not caring about stopping path, moving through target point at max speed). Important for missile-type agents;
Circumnavigate - override planetary circumnavigation behavior (go around the planet instead of straight to waypoint/target).

Position coordinates (optional, 3 parts)

Certain tasks require position. It can be set as 3 trailing parts (X, Y, Z). It is similar to keen GPS, so you can get three numbers manually, or by using RTS command script.
Example:
command:create-task:attack:Name=attack static point:234234:100789:123
Three parts after attribute-pairs part define the position (X:Y:Z). If you don't supply it for a task that requires it, then the code would use the position from StaticPos (see Captain module above). E.g. if you set StaticPos by raycasting, then you can just 'command:create-task:attack' to have an agent attack that StaticPos.

It's important to remember that task is not necessarily started at the moment it was created using create-task command.

Task kinds

"orbit"
Summary: Creates APckTaskMove with orbit behavior.
Attributes: R - orbit radius, default is 500.
Center point is assumed to be R meters front (at the moment of task creation, not OnStart).
Tip: if you want to queue orbit task, you might want to use Exec kind of task to inject orbit task "in place", so the APck would orbit the actual area (example below).

"wait"
Summary: holds position until signal or until set ticks limit is reached.
Attributes: TickLimit (60 means one second of simulation time).

"wait-for-signal"
Same as above, but also clears task queue buffer (for queue saving purposes).

"exec"
Summary: executes arbitrary command (.OnComplete).
Attributes: FollowUp - full command text, but with ':' replaced by ';' (to not interfere with the wrapping command itself).

Example for 'command:create-task:orbit:R=1000'
command:create-task:exec:FollowUp=command;create-task;orbit;R=1000

Example for repeat command (looping current task buffer starting from the last wait-for-signal task)
command:create-task:exec:FollowUp=command;repeat

"cruise-fw"
Summary: creates infinite task for moving forward, maintaining altitude in case of planet (i.e. can be used for stable planet orbit).

Direction is not fixed at task creation - if you rotate an agent, or it changes direction due to combat interrupt, then it would continue that way.

Remember that you can use TickLimit and SpeedLimit attributes when needed.

NEW: R param optionally defines minimum safety altitude (elevation above surface). By default an agent won't react to terrain unless you specify this value.

NEW: You can use rc-distance to raycast trigger when there is terran obstacle, and take custom measures like move-rel command to move higher/sideways/etc.

"move"
Summary: moves to a Position.

FlyThrough attribute (see above) sets if an agent should break or just rush through a Position point. It takes effect only for tasks to be created, not existing ones. Setting it to false may be useful for missiles, so they won't lose speed during intermediate waypoints when attacking.

"move-rel"
Summary: same as above, but Position is treated like a vector relative to an agent at the moment of task start (not creation).
Use remap attribute (RemapNG=true) within the task if you want it to work with axis defined by gravity and forward (X, Y, Z are normally Left, Up and Backward of the "forward-gyro", in case of remap the Up would be inverted gravity, and move-rel:0:1000:0 would mean a point 1000m directly above in gravity, no matter how the agent is oriented at the moment of task start).
This task is useful when you want an agent to move forward for a certain amount of time (e.g. missile leaving a silo), or if you want a 1t unit gain altitude based on conditions.

X is a left-right axis, Y is top-down, Z is forward-backward.

Example for moving 1000m forward
command:create-task:move-rel:0:0:1000

"jab"
Summary: inertial torpedo strike using own acceleration to launch (dumb-unit or sub-unit).
Attributes: TargetId.

If id is not supplied, it is treated as untargeted jab using current forward direction. TargetId should be id of datalink enemy target.

Ram task was removed

See CustomData sequence examples on missile usage in v.1.0+: Boot Sequence examples

"attack"
Summary: force attack using fixed weapons, test combat conditions, etc, with evasion movement behavior. Similar to threat response, but for specific target or Position.
Attributes: TargetId.

If Position/StaticPos is set, then it would ignore TargetId. TargetId should be id of datalink enemy target.

"follow"
Summary: infinite task for maintaining relative position, given a friendly APck id, or just following sensor-detected player.
Attributes: TargetId.

TargetId should be id of friendly APck grid. If no TargetId is provided, tries to use sensor block named 'sensor-apck'.
The relative position is captured at the moment of task initialization (OnStart).

"wingman"
Summary: infinite task for following TG.Parent, using assigned formation position.

"dock"
Summary: docking to a friendly APck grid or to known connector position/normal.
Attributes: TargetId, AimNormal.

TargetId should be id of friendly APck grid. If no TargetId is provided, it tries to use Position and AimNormal attribute.
AimNormal attribute is 3-part vector that matches known static connector direction. It is used to match static connector orientation, and Position is used to reach said connector.
Both values are better created using InferTask feature (see above). Then you can store inferred task, or see PB log to get the task string.

NEW: "maintenance"
By default created for agents which are docked to a connector at the moment of initialization. Switches battery charge mode, fuel tanks stockpile, turns overrides and dampeners off (Inert mode). This task brohibits combat response (agents won't scramble to fight nearby targets). Use it after docking task (command:request-docking, etc) to retain this behavior after you used agents and they are re-docked back to the carrier (othewise they would undock and attack without your explicit permission). Alternatively, change response setting (command:set-response) to Ignore.

"cargo"
Summary: tries to store/retreive cargo to match specified order.
Attributes: [varying]

Desired item amount is set in a way similar to attribute-pairs. Key is item tag (Ore, Iron, Ingot, etc), value is amount.
An agent would attempt to exchange cargo until it has amounts matching the order.
An agent won't proceed with next tasks until all desired item amount entries are satisfied. Cargo items which do not match are ignored.

Example for loading 2000 units of ore combined
command:create-task:cargo:Ore=2000

Example for unloading all ore and steel plates
command:create-task:cargo:Name=unload,Ore=0,SteelPlate=0

To make cargo shuttle, create a queue like 'move-dock-cargo-move-move-dock-cargo-exec(repeat command)'. Move command requests undock so as long as cargo task condition is satisfied, an agent would proceed to the next task. See 'Saved Task Queue' above for more info.

"land"
Summary: lands to surface (planet, asteroid, ship, etc) using a reference landing gear.
Attributes: AimNormal.

The task requires to have at least one known landing gear or mag plate. Overwise, the task won't do anything.

Position is optional(3 trailing command parts as usual). AimNormal attribute is optionally supplied to match the surface.
Both values are better created using InferTask feature (see above). Then you can store inferred task, or see PB log to get the task string.

If no vectors are provided, and the unit is near planet, the code would attempt to land using gravity to align, and altitude data (below remote controller) to deduce the surface point.
Last edited by cheerkin; 4 Apr @ 7:46am
< >
Showing 1-5 of 5 comments
Staticnoizz 23 Dec, 2024 @ 12:26am 
is there somewhere i can go to get a bit more help? ive been pouring over several pages of this and im still having trouble sorting this all out.
Staticnoizz 24 Dec, 2024 @ 12:59pm 
sorry to bother you again but this link only leads to some kind of blank server. "you find yourself in a strange place. You don't have access to any text channels, or there are none on this server" the rest of the page is blacked out and does not say a server name. would you be able to send me an invite link to that server?
cheerkin  [developer] 24 Dec, 2024 @ 6:09pm 
Hmm, alright, does this link work for you?
https://discord.gg/bV5GpZpV

You don't need to "apply" for restricted channel, you can ask about my scripts in space-engineers-game or questions-and-requests channels. There are people who are experienced and glad to help.
cheerkin  [developer] 4 Apr @ 7:43am 
Doc updates:
- StaticPos and TargetId properties are removed from the Captain module.
- note about sub-units prefixing in the commands routing section
- clarifications for the "land" task
< >
Showing 1-5 of 5 comments
Per page: 1530 50