# Question What is the best way to implement a movement for a 2.5D enemy?

Discussion in 'Scripting' started by LazyGhost15, Dec 3, 2023.

1. ### LazyGhost15

Joined:
Feb 12, 2022
Posts:
108
I have a 2D spider in a 3D world and I want it to chase the player, but if he is too far away from his spawn point he goes back to his territory to wonder. But I don't know how should I add the movement system

Joined:
Aug 1, 2021
Posts:
594
In development, you need to split your problem in smaller tasks and do one after another. In your case:

2. Create and attach a C# script to your spider (let's call it SpiderMovement.cs)

Your spider has 2 states, "Chase the player", and "Return to territory", so you need 2 more steps + 1 shared step between the 2 "Get distance to player". We continue our steps list by adding those new 3 steps:

3. Get distance to player: A simple
``Vector3.Distance(spider.transform.position, player.transform.position)``
is enough.

4. Chase the player: If the distance (we got from step 3) is smaller or equals to chaseDistance (to be defined by you), we move the spider towards the player with a particular speed (again defined by you). A simple
``spider.transform.position = Vector3.MoveTowards(spider.transform.position, player.transform.position, speed * time.deltaTime)``
is enough.

5. Return to territory: If the distance (we got from step 3) is bigger than chaseDistance, we move the spider back towards its territory (could be an empty GameObject you add to the scene). We do the same as step 4, but move the spider towards its territory rather than the player.

Let's translate steps 3-5 into code:
Code (CSharp):
1. public class SpiderMovement : MonoBehaviour
2. {
3.     // Assign it from the Editor by drag-drop
4.     public GameObject player;
5.
6.     // Assign it from the Editor by drag-drop
7.     public GameObject territory;
8.
9.     public float speed = 1.0f;
10.
11.     public float chaseDistance = 10.0f;
12.
13.     // Combining steps 3-5
14.     private void Update()
15.     {
16.         float distanceToPlayer = GetDistanceToPlayer();
17.
18.         if (distanceToPlayer <= chaseDistance)
19.         {
20.             ChasePlayer();
21.         }
22.         else
23.         {
24.             ReturnToTerritory();
25.         }
26.     }
27.
28.     // Step 3
29.     private float GetDistanceToPlayer()
30.     {
31.         // this means "this spider"
32.         return Vector3.Distance(player.transform.position, this.transform.position);
33.     }
34.
35.     // Step 4
36.     private void ChasePlayer()
37.     {
38.         this.transform.position = Vector3.MoveTowards(this.transform.position, player.transform.position, speed * time.deltaTime);
39.     }
40.
41.     // Step 5
42.     private void ReturnToTerritory()
43.     {
44.         this.transform.position = Vector3.MoveTowards(this.transform.position, territory.transform.position, speed * time.deltaTime);
45.     }
46. }
As further improvement to your code, and since ChasePlayer() and ReturnToTerritory() do the same thing (except the spider destination), we can create a method MoveSpiderTowards() where we pass a GameObject as a destination:
Code (CSharp):
1. private void MoveSpiderTowards(GameObject destination)
2. {
3.     this.transform.position = Vector3.MoveTowards(this.transform.position, destination.transform.position, speed * time.deltaTime);
4. }
Then in our update, we get rid of ChasePlayer() and ReturnToTerritory() completely, and simply do:
Code (CSharp):
1. private void Update()
2. {
3.     float distanceToPlayer = GetDistanceToPlayer();
4.
5.     if (distanceToPlayer <= chaseDistance)
6.     {
7.         MoveSpiderTowards(player);
8.     }
9.     else
10.     {
11.         MoveSpiderTowards(territory);
12.     }
13. }
We can add more states, for example Attack, by adding a new condition that checks if the distance to the player is less than an attackRange float and trigger an Attack() method.

Last edited: Dec 3, 2023
LazyGhost15 likes this.