-
Notifications
You must be signed in to change notification settings - Fork 0
Ranged Combat and Ammo
A PlayerMob carrying a bow or crossbow uses it at range and switches to melee up close — and it fires
only while it carries ammo it can actually use, spending one round per shot. Out of ammo, it grabs nearby loose
ammo or falls back to melee. Armed ranged mobs also acquire targets from farther out than melee mobs do, with
the distance multiplier configurable. All behaviour is tunable from config/playermob.properties.
Added in v0.58.0. Earlier versions fired bows and crossbows with unlimited ammo and never consumed arrows. The attack-acquisition range bonus was added in the same release.
An aggressive mob's attack-acquisition radius (how far away it will decide to fight) is normally determined
by its traits — friendliness and fightFlight — via DispositionResolver. When a mob has a ranged weapon
and carries ammo for it, that radius is multiplied so it opens fire from further away than a melee mob would.
Two config multipliers drive this (both live in playermob.properties):
| Multiplier | Default | Effect |
|---|---|---|
attackRangeMultiplier |
1.0 |
Global scale on the trait-based attack radius for all aggressive PlayerMobs. 1.0 = unchanged. |
rangedAttackRangeMultiplier |
2.0 |
Extra scale applied on top only when the mob holds a ranged weapon with ammo. Default ×2. |
Effective ranged reach = attackRangeMultiplier × rangedAttackRangeMultiplier — so with defaults, a
ranged-armed mob engages at twice the distance a melee mob of identical traits would.
- Only FIGHT acquisition is widened. FLEE range, WATCH range, and GREET are unaffected — a timid mob with a bow still only bolts at its normal close-range threshold, not sooner.
-
Respects
requireArrows. IfrequireArrows=false(unlimited ammo), a ranged-armed mob always gets the bonus. IfrequireArrows=true(the default), it only gets the bonus while it actually carries matching ammo. -
Clamped to
[0, 64]. Setting either multiplier to0fully disables proactive distance-attack (the mob still retaliates when hurt). Values above 64 are clamped.
# Default: all mobs unchanged, ranged mobs engage at 2× the trait distance
attackRangeMultiplier=1.0
rangedAttackRangeMultiplier=2.0
# Server wants aggressive snipers — all mobs 1.5×, ranged 4× (= 6× overall for ranged)
attackRangeMultiplier=1.5
rangedAttackRangeMultiplier=4.0
# Disable the ranged bonus entirely, keep melee unchanged
rangedAttackRangeMultiplier=1.0Note: Acquisition range is also capped by the mob's
FOLLOW_RANGEattribute and line-of-sight — no matter how large the multiplier, the mob can't see through walls or beyond its attribute cap.
In combat the mob keeps a "best of each category" weapon toolkit and picks per range, every tick:
-
Beyond
rangedEngageDistance(default 8 blocks) → draw the best ranged weapon (and it has ammo for it). -
Within
meleeEngageDistance(default 4 blocks) → draw the best melee weapon. - In between → a hysteresis band: keep the current combat weapon so it doesn't flicker at the boundary.
A crossbow charges, fires, then reloads between shots (the vanilla pillager cycle); a bow draws, strafes,
and looses. This is driven by WeaponAwareAttackGoal — see AI Goals.
By default (requireArrows=true) a ranged weapon fires only while the mob carries ammo that weapon accepts,
and consumes one round per shot from its 8-slot backpack:
| Weapon | Accepts |
|---|---|
| Bow | Arrows (plain, tipped, or spectral) |
| Crossbow | Arrows or firework rockets |
The round is consumed the instant the shot fires. Tipped and spectral arrows fire as their own type, and a crossbow loaded with a firework rocket shoots the firework.
When a ranged-armed mob runs out of ammo, in priority order:
-
Fetch nearby ammo. If the enemy isn't too close (farther than ~6 blocks) and a dropped round the weapon
accepts is within ~10 blocks, the mob walks over, grabs it, and resumes firing. This is
SeekAmmoGoal. - Fall back to melee. Otherwise — enemy on top of it, or nothing nearby to grab — it draws its best melee weapon (or bashes with the ranged weapon if it owns no melee) and closes in.
A PlayerMob also picks up ammo it walks over: arrows for any mob, and firework rockets too if it owns a crossbow to fire them with. So a wild crossbow mob restocks from dropped fireworks; a bow-only mob ignores them.
This is no-code — use commands or the spawn egg. For example:
# Summon a PlayerMob a few blocks away
/summon playermob:player_mob ~ ~ ~3
# Give it a crossbow in the main hand
/item replace entity @e[type=playermob:player_mob,limit=1] weapon.mainhand with minecraft:crossbow
# Give it a stack of arrows (slot index into the 8-slot backpack)
/item replace entity @e[type=playermob:player_mob,limit=1] container.0 with minecraft:arrow 64
# ...or firework rockets for a crossbow
/item replace entity @e[type=playermob:player_mob,limit=1] container.1 with minecraft:firework_rocket 16You can also drop arrows or fireworks on the ground near the mob and let it pick them up. See
Spawning and NBT for the full /summon, spawn-egg, and NBT reference (equipment, skin, personality).
Edit config/playermob.properties (created on first run, in the server/world config directory). It's read
once at startup, so a file edit needs a restart — to change ammo behaviour live, use the command below.
| Key | Default | Effect |
|---|---|---|
attackRangeMultiplier |
1.0 |
Global scale on the trait-based attack-acquisition distance for all aggressive PlayerMobs. 1.0 = unchanged. Clamped to [0, 64]. |
rangedAttackRangeMultiplier |
2.0 |
Extra scale applied on top of attackRangeMultiplier when a mob holds a ranged weapon with ammo. Default ×2, so ranged mobs engage at twice the usual trait distance. Clamped to [0, 64]. |
requireArrows |
true |
true = ranged weapons consume inventory ammo and can't fire when empty. false = global unlimited ammo (vanilla behaviour — never consumes, always fires). |
seekArrowsWhenEmpty |
true |
When true, an out-of-ammo mob fetches nearby loose ammo (if the enemy isn't too close) before falling back to melee. false = always melee when empty. No effect when requireArrows=false. |
rangedEngageDistance |
8.0 |
Blocks beyond which the mob prefers a ranged weapon. |
meleeEngageDistance |
4.0 |
Blocks within which the mob draws melee. Must be > 0 and < rangedEngageDistance; an invalid pair resets both to 8.0 / 4.0. |
# Consume inventory ammo (the default)
requireArrows=true
seekArrowsWhenEmpty=true
# Snipe from farther out, only melee at point-blank
rangedEngageDistance=12.0
meleeEngageDistance=3.0Toggle global unlimited ammo live, op level 2 (gamemasters). Like the other /playermob toggles, this is a
session override — it takes effect immediately but is not written back to the config file (a restart
reverts to requireArrows).
| Command | Effect |
|---|---|
/playermob unlimitedammo |
Report whether unlimited ammo is on. |
/playermob unlimitedammo on |
Unlimited ammo — ranged weapons never run out (sets requireArrows=false). |
/playermob unlimitedammo off |
Inventory ammo — ranged weapons consume their backpack ammo (sets requireArrows=true). |
- Save-compatible. Ammo lives in the existing backpack — no new save data, so old worlds load unchanged.
- Only crossbows take fireworks, matching vanilla. A bow with only fireworks in its pack can't fire and melees.
- Fireworks are hoarded only by crossbow owners. A mob that owns no crossbow won't pick up firework rockets as ammo.
- Unlimited-ammo mode still respects the range switch — it just never consumes or runs dry.
- Mid-combat ammo fetch is for loose ground items, not chests. A mob will still loot ammo from chests through its normal raiding goals (see AI Goals) when it isn't fighting.
-
AI Goals —
WeaponAwareAttackGoal(the range switch) andSeekAmmoGoal(the fetch). -
Entity API Reference —
hasRangedAmmo,consumeAmmoForShot,getProjectile, and theRangedAmmopolicy. - Spawning and NBT — give a mob a weapon, ammo, skin, and personality.
- README — player-facing overview.
Getting started
In-game commands
No-code (datapacks)
Java API
Patterns