Enemies (Rabbits)
Relevant source files
The following files were used as context for generating this wiki page:
Rabbits are a primary enemy type in Farm Siege. They spawn periodically from the sides of the screen and attempt to reach and destroy the player's plants. The rabbit system is managed through a combination of a data model (RabbitData), a state management store (MovablesStore), a rendering component (Rabbit), and a top-level overlay (Rabbits) that orchestrates their behavior each game tick.
Players can defend against rabbits by shooting them. A successful hit removes the rabbit from the game, awards points, and triggers visual effects. If a rabbit reaches a plant, it will stop moving and begin to "eat" it, eventually removing the plant from the grid. The game's difficulty scales by increasing the game speed, which in turn affects how frequently rabbits spawn.
Configuration
Rabbit behavior is defined by a set of values in src/values.json. These settings control spawning frequency, movement speed, and scoring.
| Parameter | Value | Description |
|---|---|---|
spawning.min | 8000 | Minimum time (ms) between rabbit spawn waves. |
spawning.max | 20000 | Maximum time (ms) between rabbit spawn waves. |
grace.min | 10000 | Minimum grace period (ms) before the first rabbit wave spawns. |
grace.max | 15000 | Maximum grace period (ms) before the first rabbit wave spawns. |
amount.min | 4 | Minimum number of rabbits per wave. |
amount.max | 7 | Maximum number of rabbits per wave. |
speed | 0.2 | The base movement speed of rabbits (pixels per millisecond). |
timeToClear | 1000 | Time (ms) a rabbit takes to eat a plant after reaching it. |
scores.rabbit | 5 | Points awarded for shooting a rabbit. |
Sources: src/values.json:2-15, 53-56
Data Model: RabbitData
The state of each individual rabbit is encapsulated in the RabbitData class. This class holds all information related to a rabbit's position, movement, and state.
Sources: src/store/models/RabbitData.ts
Class Diagram
This diagram shows the structure of the RabbitData class, including its properties and methods for managing a rabbit's state.
Sources: src/store/models/RabbitData.ts:7-86
Properties and Methods
| Property | Type | Description |
|---|---|---|
_x | number | The current x-coordinate of the rabbit. |
_y | number | The current y-coordinate of the rabbit. |
_direction | Directions | The direction the rabbit is moving (Left or Right). |
_targetX | number | The x-coordinate the rabbit is moving towards (typically a plant). |
_timeLeft | number | A timer used for the duration of eating a plant. Initialized to timeToClear. |
targetReached | boolean | A getter that returns true if the rabbit's x equals targetX. |
| Method | Description |
|---|---|
move(amount) | Updates the rabbit's x-coordinate. If it overshoots the target, it snaps to the targetX. |
reduceTimeLeft(amount) | Decrements the _timeLeft timer, ensuring it doesn't go below zero. |
resetTimer() | Resets _timeLeft to the configured timeToClear value. |
detectHit(bullets) | Checks if the rabbit's coordinates are within a 50px radius of any bullet in the provided array. Returns true if hit. |
Sources: src/store/models/RabbitData.ts:7-86
State Management: MovablesStore
The MovablesStore is the central hub for managing all "movable" entities, including rabbits. It handles their entire lifecycle from spawning to removal.
Sources: src/store/MovablesStore.ts
Spawning Logic
Rabbits are spawned in waves. The process begins after an initial grace period and then repeats at random intervals.
- A timer is initiated in
start()with a random duration betweengrace.minandgrace.max. - When the timer fires,
spawnRabbits()is called. - A random number of rabbits (
amount.mintoamount.max) is determined. - Each rabbit is assigned to a unique, random row (0-7).
- A single direction (
LeftorRight) is chosen for the entire wave. RabbitDatainstances are created off-screen with a random offset and added to therabbitsarray in the store's state.- A new timer is set for the next spawn wave, with a duration between
spawning.minandspawning.max, adjusted by thespeedMultiplier.
This flowchart illustrates the rabbit spawning process within the MovablesStore.
Game Tick Update Cycle
On every game tick, the Rabbits overlay orchestrates a series of updates via the MovablesStore.
This sequence diagram shows the interactions for updating rabbit state during a single game tick.
Key Methods in the Update Cycle
setRabbitTargets(callback): This method iterates through all active rabbits. For each one, it executes a callback function provided by theRabbitsoverlay. This callback scans theGridStorecontent to find the column of the first plant in the rabbit's path, which becomes the rabbit'stargetX. If no plant is found, a target is set off-screen.
Sources: src/store/MovablesStore.ts:88-105, src/overlays/Rabbits.ts:25-61updateRabbits(timeDifference): Moves each rabbit closer to itstargetXbased on its speed and thetimeDifference. It also filters out rabbits that have moved completely off-screen.
Sources: src/store/MovablesStore.ts:47-86detectHit(bullets, callback): This method is called when the player fires their gun. It filters therabbitsarray, removing any rabbit that returnstruefrom its owndetectHitmethod. For each removed rabbit, a callback is executed to add score and trigger visual effects.
Sources: src/store/MovablesStore.ts:153-171, src/CharacterContainer.ts:182-190stillRabbits: A getter that returns an array of rabbits that have reached their target (targetReachedis true). TheRabbitsoverlay uses this to handle plant-eating logic. When a still rabbit'stimeLeftreaches 0, the plant at its location is removed from theGridStore.
Sources: src/store/MovablesStore.ts:173-175, src/overlays/Rabbits.ts:74-81
Rendering
Rabbits are rendered on the canvas through a hierarchy of components. The Rabbits overlay is responsible for rendering all rabbits managed by the MovablesStore.
Component Hierarchy
Rabbit Component
The Rabbit component is a visual representation of a single rabbit. It doesn't contain any state itself but instead displays a sprite based on the props it receives.
| Prop | Type | Description |
|---|---|---|
direction | Directions | Determines whether to use the left- or right-facing sprite. |
moving | boolean | Determines whether to render the AnimatedSprite or the static Sprite. |
The component contains two child components: an AnimatedSprite for a moving rabbit and a Sprite for a still (eating) rabbit. A show condition on each child ensures only one is visible at a time based on the moving prop.
Sources: src/components/animals/Rabbit.ts:17-71
Rabbits Overlay
The Rabbits overlay acts as the bridge between the MovablesStore data and the visual Rabbit components. It uses a Repeating logical component to iterate over the movablesStore.content.rabbits array. For each RabbitData object in the array, it renders a Rabbit component, passing the direction and moving status (data.x !== data.targetX) as props.
Sources: src/overlays/Rabbits.ts:84-101
Summary
The rabbit enemy system is a core gameplay mechanic designed to pressure the player. Rabbits are managed by the MovablesStore, which controls their spawning, movement, and removal. Their behavior is driven by configuration in values.json and their state is tracked in RabbitData objects. The Rabbits overlay and Rabbit component work together to render them on screen and orchestrate their interactions with the game world, such as finding plants in the GridStore and being hit by bullets from the CharacterStore.