So I’m creating a mode in my game, it’s like a survival. You gotta keep killing the enemies as they come. And the longer your there the faster they enemy’s are instantiated. Timer is also there to see how long you can survive for. The problem I’m facing is to make the enemy shoot. What I did is
First - Set it’s destination to the target
Second - What I wanted is that when anyone (player) comes near the sphere collider I’ve placed on the enemy. It’ll stop. Both the target and enemy’s collider’s are set to trigger but when I did this
It didn’t detect anyone which hit the collider, and kept moving until it has reached the target
What I want is when the enemy comes near the player, it stops, and shoots. I could just check both their distance. But I’m still curious that why doesn’t the trigger work?
Another question about target, currently It’s just a cube with the player tag. What I wanna know is what types of ways can a enemy be assigned in the code, without physically assigning it in the inspector?
All help will be appreciated. Thanks!
EDIT - I also did Debug.Log(other.name); And nothing is written in the console. meaning collision isn’t detected
Well coupla ways: first you gotta meet all the requirements (at least one non-kinematic rigidbody, collider correct, etc.), but you also have to move it there properly, eg, NOT by setting transform.position. You need to move it with .MovePosition() on the Rigidbody to ensure it gets collision checks.
I like using Resources.Load() to get stuff for a given level, since it’s super-simple.
But I also often create a ScriptableObject collection of “things you need for this level,” so for instance here’s one for a monster maze generation game I’m working on:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
[CreateAssetMenu]
public class MonsterMaze3DSkin : ScriptableObject
{
[Header( "The Base Level (huge-size floor and ceiling)")]
public GameObject BaseLevelPrefab;
[Header( "Outer Walls:")]
public GameObject WallsOuterPerimeter;
[Header( "Main Walls:")]
public GameObject WallsInnerCommon;
public GameObject FloorInnerCommon;
public GameObject CeilingInnerCommon;
[Header( "Near Exits:")]
public GameObject WallsNearExit;
public GameObject FloorNearExit;
public GameObject CeilingNearExit;
[Header( "Corner Post where necessary")]
public GameObject CornerPostPrefab;
[Header( "The exit structure and particle system.")]
public GameObject ExitPrefab;
}
So this lets me make dungeons look different over time, by swapping out the above skin, having one for each level in the maze. It’s kinda like how Diablo 1 skinned four dungeons. I have a LOT of games that use patterns like this so I can use the same code to make a lot of content.
Also in that vein, here’s a more generic thing I use a lot, such as "give me a random or shuffled rock from a collection of rocks called RocksForThirdMoonFromTheSun):
What do you mean by .MovePosition() on the RB. I’m not sure where you want me to use that, and what for. Because all I’m doing is setting the agent destination to the target. Am I getting you correctly?
Thats exactly what I needed, I’ll read the docs and try using that
That looks PRETTY NICE. Thats a really cool way to do it
I also had another question. I was making a shoot coroutine, realised making a method would be better. Problem isanimator.SetFloat() is not working in the method. Works perfectly fine in the coroutine, but my not in the method?? Is there a reason for this?
Huh… never thought of that… I am going to speculate that when the navmesh agent moves, it bypasses physics as well, but there might be googling you can do. There might be a setting on the agent though?
Both NavMesh and Physics keep their own notions of where you are in space and then use various approaches to sync it with the transform.position. Same goes for rotation.
I’ll check all the settings on the agent to see what could be preventing this and I’ll check those docs out as well
But the float I’m calling is that same in the coroutine, works in the coroutine but not in the method. I don’t think I’m using it correctly, question still remains why does it work in the coroutine but not in the method?
It HAS to be being called either more or less often. Animator doesn’t care where you call it from, as long as it is main thread (which is everything in standard script land, coros and otherwise).
Ohh jeez, now it doesn’t. But another surprising part is the same script which wasn’t working in the coro before, is now working perfectly fine. I’m actually confused
Well the first thing is to drop it in a blank scene, press play and then get jiggy with the parameters right there in the animator window… does the animation do what you expect when you twiddle that float??
Often it is just one busted animation or state or transition, you fix it, off you go.
Also, I don’t think it’s busted or anything because just for now, I’m using the same animator controller for my player and enemy AI. My player’s shoot anim works fine as well. Same thing doesn’t work for the AI. That doesn’t make sense either.
Alright, anim’s aside and to going back to topic. So far agent goes to the target, and when at a certain range, it stops. Problem is now, If I move around it won’t follow, it’ll get to the place where I was instantiated, then keeps shooting there. Won’t follow even if I move around. I thought maybe because I called enemy.isStopped = true In a method, though when I made a simple script.
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.AI;
public class test : MonoBehaviour
{
public NavMeshAgent agent;
public GameObject target;
void Start()
{
agent = this.GetComponent<NavMeshAgent>();
}
// Update is called once per frame
void Update()
{
agent.SetDestination(target.transform.position);
}
}
It only went to the targets first position, where it was instantiated, when the target moves around. It doesn’t. I tried the same with agent.destination but doesn’t work? Is this a bug? Because as far as I know, that script above should make it follow the player in play mode, and all tutorials do the same thing
Seems like it should. Print the position that you’re giving to SetDestination()!
Also, what happens if you move that SetDestination out of Update and into a coroutine that loops forever and only calls it once per second? My theory is that the pathing might be constantly trying to repath and never finishes because you’re telling the destination every frame, even if it might be the same. Not sure how smart the navmesh agents are that way… they may just keep recalculating again and again and never go.
The positions given are the positions of where the object is instantiated.
I did make a method for it but didn’t work either. I’ll try it in the coro
All I know is that they do follow the agent, I think it might be some problem in the scene. One thing is when I click play, and view the target in the scene tab. It says ‘Static’ on it. And doesn’t allow me to move it around either
Hey Kurt, so I’ve tried it in a coro. But the same thing happened. I’ve also been very curious for 2 things, one it just should work no reason why, then when I saw the static object in the scene which is the target. I thought that might be the reason. I created a new project. And used the test script above, 2 things changed, one it followed, it wherever, and two. Target wasn’t displayed static in the scene. So maybe the object being static in the scene is the problem. But I don’t understand why because I did the same with cubes, and they were displayed static in the scene but got nothing on them? Do you think this is the problem or something else?
EDIT: After going through this even more, I’ve found out that the enemy is only having problem following the player, I used other object’s, and in play mode moved them around. The agent did follow them and when they left it range, it followed it again. just not for the player? Why, I can’t really find any reason