Objectives

Objectives are conditions the player must complete to finish a quest. They are continuously checked while the quest is active. Objectives are different from Actions: objectives are things the player must do, actions are things that happen.

Objective Format

Each objective in a quest's objectives array follows this structure:

{
  "id": "unique_objective_id",
  "objectiveId": "kill",
  "args": ["validCode1", "validCode2", "5"],
  "onCompleteActions": [
    { "id": "notify", "args": ["Objective complete!"] }
  ]
}
  • id — A unique identifier for this objective instance within the quest.
  • objectiveId — The type of objective (e.g. kill, gather, walkdistance).
  • args — An array of string arguments specific to the objective type.
  • onCompleteActions — (Optional) Actions to execute when this objective is completed.

Mega Example: All Objective Types in One Quest

This is the most complex realistic example. It shows how to combine kill, gather, reach, check variable, land gate, sequence, and timer in a single quest:

{
  "id": "yourmod:epic-quest",
  "cooldown": -1,
  "perPlayer": true,
  "onAcceptedActions": [
    { "id": "playsound", "args": ["game:sounds/quest-accept", "0.8"] },
    { "id": "resetwalkdistance", "args": ["yourmod:epic-quest"] },
    { "id": "resettimer", "args": ["yourmod:epic-quest", "timer1"] }
  ],
  "killObjectives": [
    { "validCodes": ["wolf-*"], "demand": 5 }
  ],
  "gatherObjectives": [
    { "validCodes": ["game:herb-*"], "demand": 10 }
  ],
  "actionObjectives": [
    {
      "id": "walk_500m",
      "objectiveId": "walkdistance",
      "args": ["yourmod:epic-quest", "500", "0"]
    },
    {
      "id": "reach_temple",
      "objectiveId": "reachwaypoint",
      "args": ["5120,68,5340", "5"]
    },
    {
      "id": "check_blessing",
      "objectiveId": "checkvariable",
      "args": ["blessed", "==", "true"]
    },
    {
      "id": "enter_village",
      "objectiveId": "landgate",
      "args": ["derevnia", "enter_village", "Enter: ", "false"]
    },
    {
      "id": "do_steps_in_order",
      "objectiveId": "sequence",
      "args": [
        "yourmod:epic-quest",
        "seq1",
        "kill_5_wolves",
        "gather_10_herbs",
        "reach_temple"
      ]
    },
    {
      "id": "timer1",
      "objectiveId": "timer",
      "args": ["yourmod:epic-quest", "timer1", "300"]
    }
  ]
}

What each part does:

ObjectiveWhat the player must do
killKill 5 wolves
gatherCollect 10 herbs
walkdistanceWalk 500 meters total
reachwaypointReach the temple at 5120,68,5340 (radius 5)
checkvariableHave the blessed attribute set to true
landgateStand inside the derevnia land claim
sequenceComplete kill, then gather, then reach in that exact order
timerComplete everything within 300 seconds (5 minutes)

Objective-Level Actions

Each objective can fire its own onCompleteActions when it is finished. This is useful for updating the quest state or notifying the player:

{
  "id": "reach_north",
  "objectiveId": "reachwaypoint",
  "args": ["5200,70,5400", "10"],
  "onCompleteActions": [
    { "id": "playsound", "args": ["game:sounds/quest-step", "0.8"] },
    { "id": "notify", "args": ["yourmod:checkpoint-reached"] }
  ]
}

What happens:

  • When the player reaches the waypoint, a sound plays and a notification is sent.
  • This is independent of the quest's actionRewards — it fires immediately when the objective is done, not when the whole quest completes.

Complete Example

Here is a full quest that uses multiple objective types together. This is the pattern you copy when you want a quest with several steps:

{
  "id": "yourmod:multi-step-quest",
  "cooldown": -1,
  "perPlayer": true,
  "onAcceptedActions": [
    { "id": "playsound", "args": ["game:sounds/quest-accept", "0.8"] }
  ],
  "killObjectives": [
    { "validCodes": ["wolf-male", "wolf-female"], "demand": 3 }
  ],
  "gatherObjectives": [
    { "validCodes": ["game:herb-*"], "demand": 5 }
  ],
  "actionObjectives": [
    {
      "id": "reach_temple",
      "objectiveId": "reachwaypoint",
      "args": ["5120,68,5340", "5"]
    },
    {
      "id": "check_blessing",
      "objectiveId": "checkvariable",
      "args": ["blessed", "==", "true"]
    }
  ]
}

How the objectives work together:

  • killObjectives — the player must kill 3 wolves.
  • gatherObjectives — the player must collect 5 herbs.
  • reachwaypoint — the player must reach the temple at 5120,68,5340 (radius 5 blocks).
  • checkvariable — the player must have the attribute blessed set to true (usually set by a dialogue action).

All four must be completed before the quest becomes completable.


Quest with a Gate

A gate is an objective that must be satisfied before the quest can be completed, even if all other objectives are done. The most common gate is landgate — requiring the player to be inside a specific land claim.

{
  "id": "yourmod:gate-example",
  "cooldown": -1,
  "perPlayer": true,
  "onAcceptedActions": [
    { "id": "playsound", "args": ["game:sounds/quest-accept", "0.8"] }
  ],
  "gatherObjectives": [
    { "validCodes": ["game:ingot-*"], "demand": 3 }
  ],
  "actionObjectives": [
    {
      "id": "must_be_in_town",
      "objectiveId": "landgate",
      "args": ["town", "must_be_in_town", "Return to town: ", "false"]
    }
  ]
}

What happens:

  • The player collects 3 ingots anywhere.
  • The quest cannot be completed until the player walks back into the town land claim.
  • The HUD shows: Return to town: must_be_in_town

Gates and Sequences

Some objectives are designed to block progress until other conditions are met.

Sequence + Land Gate Combined

This example shows how to force the player to complete objectives in order, and then return to a safe zone:

{
  "id": "yourmod:patrol-quest",
  "cooldown": -1,
  "perPlayer": true,
  "actionObjectives": [
    {
      "id": "patrol_steps",
      "objectiveId": "sequence",
      "args": [
        "yourmod:patrol-quest",
        "patrol1",
        "reach_north",
        "reach_east",
        "reach_south",
        "return_base"
      ]
    },
    {
      "id": "reach_north",
      "objectiveId": "reachwaypoint",
      "args": ["5200,70,5400", "10"]
    },
    {
      "id": "reach_east",
      "objectiveId": "reachwaypoint",
      "args": ["5300,70,5400", "10"]
    },
    {
      "id": "reach_south",
      "objectiveId": "reachwaypoint",
      "args": ["5300,70,5300", "10"]
    },
    {
      "id": "return_base",
      "objectiveId": "landgate",
      "args": ["base", "return_base", "Return to base: ", "false"]
    }
  ]
}

How it works:

  • sequence forces the player to visit the 4 waypoints in order.
  • The last step (return_base) is a landgate — the player must enter the base land claim.
  • The quest cannot be completed until all 4 sequence steps are done and the player is inside base.

Sequence

Forces objectives to be completed in order. The next objective only becomes active after the previous one is done:

{
  "id": "quest_01",
  "objectiveId": "sequence",
  "args": [
    "myquest",
    "seq1",
    "step1_kill",
    "step2_gather",
    "step3_reach"
  ]
}
  • step1_kill must be completed first
  • Then step2_gather becomes active
  • Then step3_reach becomes active

💡 Sequence works with any objective type. The objective IDs in args can be killObjectives, gatherObjectives, or actionObjectives — the sequence controller finds them by their id field.

Land Gate

Blocks a quest until the player is standing inside a specific land claim:

{
  "id": "gate_village",
  "objectiveId": "landgate",
  "args": ["derevnia", "enter_village", "Enter: ", "false"]
}
  • args[0] — the land claim name
  • args[1] — the objective ID this gate is blocking
  • args[2] — HUD prefix (e.g. Enter: )
  • args[3] — hide the prefix (true/false)

Kill Objectives

Track creature kills by entity code. The player must kill a certain number of matching entities.

{
  "id": "kill_wolves",
  "objectiveId": "kill",
  "args": ["wolf-male", "wolf-female", "5"]
}
  • args[0..n-1] — ` One or more entity codes to match (supports wildcard *`).
  • args[n] — `` The number of kills required (last element in args).

Gather Objectives

Track item collection. The player must have a certain number of matching items in their inventory.

{
  "id": "gather_flax",
  "objectiveId": "gather",
  "args": ["flaxfibers", "10"]
}
  • args[0..n-1] — ` One or more item/block codes to match (supports wildcard *`).
  • args[n] — `` The number of items required (last element in args).

Action Objectives

Action objectives cover a wide range of specialized conditions beyond simple kill/gather tracking. Each uses a unique objectiveId and its own argument format.

walkdistance

Requires the player to walk a certain distance in meters while the quest is active.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Distance in meters the player must walk (required).
  • args[2] — `` Tracking slot index (optional, default 0).

💡 Use the resetwalkdistance action to reset the distance counter if the quest is restarted or the objective needs to be re-tracked.

randomkill

Assigns a random kill target from a predefined slot. The target entity is selected randomly when the quest starts.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` The random kill slot identifier (required).

checkvariable

Checks a player attribute (variable) against a value using a comparison operator. Completes when the condition is true.

  • args[0] — `` The attribute/variable name to check (required).
  • args[1] — ` Comparison operator (required). Valid operators: =, ==, >, >=,
  • args[2] — `` The value to compare against (required).
  • args[3] — `` Action string to execute on completion (optional).

timeofday

Completes when the in-game time matches the specified mode. Useful for quests that require waiting for day or night.

  • args[0] — ` Time mode (required). Values: day, night, or startHour,endHour (e.g. 6,18` for daytime hours).

interactat

Completes when the player interacts (right-clicks) at one of the specified coordinates.

  • args[0] — ` First coordinate in x,y,z` format (required).
  • args[1..n] — `` Additional coordinates (optional). Any one match completes the objective.

interactcount

Counts the number of interactions at specified coordinates. Completes when the player has interacted the required number of times.

  • args[0..n-1] — ` Coordinates in x,y,z` format (required).
  • args[n] — `` Localization key for the HUD display text (last element).

plantflowers

Checks if a certain number of flowers are planted nearby the player.

  • args[0] — `` Number of flowers required nearby (required).

hasattribute

Checks if the player has a specific attribute set to a specific value. Completes when the attribute matches.

  • args[0] — `` The attribute key name (required).
  • args[1] — `` The expected value (required).

reachwaypoint

Completes when the player reaches a specific coordinate within a given radius.

  • args[0] — `` Target coordinate (required).
  • args[1] — ` Detection radius in blocks (optional, default 2`).

hasitem

Checks if the player currently has a certain number of items in their inventory.

  • args[0] — ` Item code to match, supports wildcard *` (required).
  • args[1] — `` Number of items required (required).

wearing

Checks if the player is wearing a specific item in their equipment slots.

  • args[0] — ` Item code to match, supports wildcard *` (required).
  • args[1] — `` Specific equipment slot index to check (optional, checks all slots if omitted).

interactwithentity

Tracks interactions with a specific entity. Completes after the required number of interactions.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` The entity code or ID to interact with (required).
  • args[2] — `` Number of interactions required (required).

inland

Completes when the player is standing inside a specific land claim area.

  • args[0] — `` The name of the land claim to check (required).

landgate

A progress gate tied to a land claim. Used to block quest progression until the player has completed objectives within a claimed area.

  • args[0] — `` The land claim name (required).
  • args[1] — `` The objective to gate behind (optional).
  • args[2] — `` Display prefix for the HUD (optional).
  • args[3] — ` Whether to hide the prefix (true/false`, optional).

killnear

Tracks kills near a specific coordinate. Only kills within the radius count toward completion.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Unique objective identifier (required).
  • args[2] — `` Center coordinate (required).
  • args[3] — `` Detection radius in blocks (required).
  • args[4] — ` Entity code to match, supports wildcard * (optional, default *` matches all).
  • args[5] — `` Number of kills required (required).

killactiontarget

Requires the player to kill a target that was marked by a previous action (e.g. a spawned boss or marked entity).

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Unique objective identifier (required).
  • args[2] — `` The target identifier set by the marking action (required).
  • args[3] — `` Number of kills required (required).

sequence

Defines an ordered sequence of objectives that must be completed in order. The next objective only activates after the previous one is done.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Unique identifier for this sequence (required).
  • args[2..n] — `` Ordered list of objective IDs to complete in sequence (required).

temporalstorm

Requires the player to survive a number of temporal storms while the quest is active.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Unique objective identifier (required).
  • args[2] — `` Number of storms to survive (required).

Experimental Objectives

⚠️ These objectives are experimental and may change or be removed in future versions. Use them with caution in production quest packs.

Timed Challenge Example

Combine timer with other objectives to create a time-limited challenge:

{
  "id": "yourmod:timed-hunt",
  "cooldown": 24,
  "perPlayer": true,
  "onAcceptedActions": [
    { "id": "playsound", "args": ["game:sounds/quest-accept", "0.8"] },
    { "id": "resettimer", "args": ["yourmod:timed-hunt", "timer1"] }
  ],
  "killObjectives": [
    { "validCodes": ["bear-male"], "demand": 1 }
  ],
  "actionObjectives": [
    {
      "id": "timer1",
      "objectiveId": "timer",
      "args": ["yourmod:timed-hunt", "timer1", "120"]
    },
    {
      "id": "reach_cave",
      "objectiveId": "reachwaypoint",
      "args": ["5000,60,5000", "5"]
    }
  ]
}

What the player must do:

  • Kill 1 bear.
  • Reach the cave at 5000,60,5000.
  • Do it all within 120 seconds (2 minutes).

If the timer expires before both objectives are done, the quest fails (or resets depending on your quest logic).

killwithweapon

Tracks kills made with a specific weapon type.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Unique objective identifier (required).
  • args[2] — ` Weapon item code, supports wildcard *` (required).
  • args[3] — `` Number of kills required (required).

harvestcrop

Tracks crop harvesting.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Unique objective identifier (required).
  • args[2] — ` Crop block code, supports wildcard *` (required).
  • args[3] — `` Number of crops to harvest (required).

mineblock

Tracks block mining/breaking.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Unique objective identifier (required).
  • args[2] — ` Block code, supports wildcard *` (required).
  • args[3] — `` Number of blocks to mine (required).

placeblock

Tracks block placement.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Unique objective identifier (required).
  • args[2] — ` Block code, supports wildcard *` (required).
  • args[3] — `` Number of blocks to place (required).

fishcatch

Tracks fish caught.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Unique objective identifier (required).
  • args[2] — ` Fish item code, supports wildcard *` (required).
  • args[3] — `` Number of fish to catch (required).

timer

A time-limit gate. The objective completes (or fails) after the specified number of seconds. Useful for timed challenges.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Unique objective identifier (required).
  • args[2] — `` Time limit in seconds (required).

💡 Use the resettimer action to reset the timer if the quest is restarted or the objective needs to be re-tracked.

craftitem

Tracks items crafted on the crafting grid.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Unique objective identifier (required).
  • args[2] — ` Item code, supports wildcard *` (required).
  • args[3] — `` Number of items to craft (required).

smeltitem

Tracks items smelted in a furnace or similar device.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Unique objective identifier (required).
  • args[2] — ` Item code, supports wildcard *` (required).
  • args[3] — `` Number of items to smelt (required).

Escort Quest Example

> ⚠️ EXPERIMENTAL — Requires EscortObjectiveEnabled: true in config.

A complete escort quest with a merchant:

{
  "id": "yourmod:escort-merchant",
  "cooldown": -1,
  "perPlayer": true,
  "onAcceptedActions": [
    { "id": "playsound", "args": ["game:sounds/quest-accept", "0.8"] },
    { "id": "spawnentity", "args": ["npc-merchant", "5200,70,5400", "merchant1"] }
  ],
  "actionObjectives": [
    {
      "id": "escort_merchant",
      "objectiveId": "escort",
      "args": [
        "yourmod:escort-merchant",
        "escort1",
        "npc-merchant",
        "waypoint",
        "5300",
        "70",
        "5500",
        "5",
        "failondeath=true",
        "maxleashbreaks=5",
        "timelimit=300",
        "leashrange=25",
        "warndistance=20"
      ]
    }
  ]
}

What happens:

  • A merchant NPC spawns at 5200,70,5400.
  • The player must escort the merchant to 5300,70,5500.
  • The player must stay within 25 blocks (leashrange).
  • The merchant must survive (failondeath=true).
  • The player has 5 minutes (timelimit=300).
  • If the player gets too far 5 times (maxleashbreaks=5), the quest fails.

escort

> ⚠️ EXPERIMENTAL — Requires EscortObjectiveEnabled: true in config.

Escort a target entity. Two modes: proximity (stay near for N seconds) and waypoint (escort to destination).

Proximity Mode

Player must stay near a target entity for N seconds total. Leaving range pauses progress.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Unique objective identifier (required).
  • args[2] — ` Entity code to escort, supports wildcard *` (required).
  • args[3] — `` Total seconds to stay near the entity (required).
  • args[4+] — `` Optional key=value options (see below).
{
  "id": "escort_merchant",
  "objectiveId": "escort",
  "args": ["myquest", "escort1", "npc-merchant", "60", "failondeath=true", "maxleashbreaks=3"]
}

Waypoint Mode

Entity moves toward a destination. Player must stay near until arrival.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Unique objective identifier (required).
  • args[2] — ` Entity code to escort, supports wildcard *` (required).
  • args[3] — ` Literal string "waypoint"` to activate this mode (required).
  • args[4] — `` Destination X coordinate (required).
  • args[5] — `` Destination Y coordinate (required).
  • args[6] — `` Destination Z coordinate (required).
  • args[7] — `` Arrival radius in blocks (optional, default 5).
  • args[8+] — `` Optional key=value options (see below).
{
  "id": "escort_refugee",
  "objectiveId": "escort",
  "args": ["myquest", "escort1", "npc-refugee", "waypoint", "5120", "68", "5340", "5",
           "failondeath=true", "ambushchance=0.05", "ambushentity=game:wolf-male", "ambushcount=3"]
}

Options

Append as key=value strings after the main arguments:

OptionDefaultDescription
failondeathtrueFail if escort target dies
maxleashbreaks3Max times player can be too far. -1 = unlimited
timelimit0Time limit in seconds. 0 = no limit
leashrange20.0Distance at which leash breaks
warndistance15.0Distance for warning message
speedmult1.0NPC movement speed (waypoint mode)
ambushchance0.0Chance (0-1) per tick of enemy ambush
ambushentity—Entity code to spawn during ambushes
ambushcount2Enemies per ambush

Failure Conditions

The escort fails if:

  • Leash broken — Player too far too many times (maxleashbreaks)
  • Target died — Escort entity killed (if failondeath=true)
  • Time expired — Time limit reached (if timelimit set)

💡 Waypoint mode uses simple direct movement. For complex pathfinding, configure the entity's AI tasks and use proximity mode instead.

defendpoint

Tracks waves survived at a defend point. Completes when N waves are cleared.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Unique objective identifier (required).
  • args[2] — `` Number of waves to survive (required).

💡 Requires external system to signal wave completion via DefendPointObjective.TryIncrement.

timedkill

Kill N entities within a time limit. Timer starts on first kill, resets if time expires before reaching the target.

  • args[0] — `` The quest this objective belongs to (required).
  • args[1] — `` Unique objective identifier (required).
  • args[2] — ` Entity code, supports wildcard *` (required).
  • args[3] — `` Number of kills required within the time window (required).
  • args[4] — `` Time limit in seconds (required).

Press ESC to close