- Home /
How do I randomize the movement & rotation of a 2D game object, such that it automatically moves in the direction it faces and not walk diagonally ?
I'm spawning them from a game object that ping pongs, so on spawn, they should start moving randomly.
Answer by coolbird22 · Mar 31, 2014 at 08:06 PM
I worked on the code some more but was still not able to piece it. With some help from Maximilian from PushyPixels here is the code that works the best for me. Very simple and precise.
Here is the code for your use:
using UnityEngine;
using System.Collections;
public class RandomMovement : MonoBehaviour {
public float rotationSpeed;
public float movementSpeed;
public float rotationTime;
void Start()
{
Invoke("ChangeRotation",rotationTime);
}
void ChangeRotation()
{
if(Random.value > 0.5f)
{
rotationSpeed = -rotationSpeed;
}
Invoke("ChangeRotation",rotationTime);
}
void Update() {
transform.Rotate (new Vector3 (0, 0, rotationSpeed * Time.deltaTime));
transform.position += transform.up*movementSpeed*Time.deltaTime;
}
}
Answer by corriedotdev · Mar 25, 2014 at 09:22 AM
Have a look at something like randomizing the x movement of the 2d sprite. http://docs.unity3d.com/Documentation/ScriptReference/Random.Range.html
That docmentation should basically answer your question. Just put in the area threshold that you want the object to spawn in. And of you go ;o
I've already managed to instantiate them in my scene. What I need them to do is have random movement.
Answer by Fappp · Mar 25, 2014 at 09:36 AM
In short, you need a combination of Transform.LookAt and Transform.Translate
That said, AI is something difficult and needs to be tailored to specific situations. Can you give me your current code for the things that should move?
Updated with scripts!
Okay it's alot, but here we go: Create a plane sized 20,0.1,20 > set it's position to 10,0,10 Create a box and call it "Ai Node" attach this script to the Ai Node:
var worldSize : int = 20;
var oldPos : Vector 3 = aiNode.position;
function Start(){
InvokeRepeating("NodeMove",0,0.1);
}
function NodeMove(){
transform.position.x = Random.Range(0,worldSize);
transform.position.y = 0.55;
transform.position.z = Random.Range(0,worldSize);
}
then create a box sized 0.1,0.1,0.1 and call it randomAi. Attach this script:
// villager AI FB Projecten || Fabian Broekhuizen
var target : Vector3;
var targetSet : boolean;
var position : Vector3;
var distance : float;
var aiNode : Transform;
var moving : boolean;
var wandering : boolean;
var arrived : boolean;
Start(){
InvokeRepeating("OffTrack",0,2)
}
function Awake(){
wandering = true;
}
function Update(){
aiNode = GameObject.Find("Ai Node").transform;
distance = Vector3.Distance(target, position);
position = transform.position;
transform.position.y = 0.1;
if (moving){
transform.Translate(Vector3.forward / 10 * Time.deltaTime);
targetRotation = Quaternion.LookRotation (target - transform.position);
transform.rotation = Quaternion.Lerp (transform.rotation, targetRotation, 1);
}
if (distance < 1 ){
arrived = true;
targetSet = false;
}
if (wandering && !targetSet){
target = aiNode.position;
targetSet = true;
moving = true;
}
}
function OffTrack(){
oldPos = aiNode.position;
targetSet = false;
wander = false;
target = transform.position + Random.insideUnitSphere * 5;
yield WaitForSeconds(1);
wander = true;
target = oldPos;
targetSet = true;
}
Updated with request
Oh! I never knew about Transform.LookAt. I'll try looking into it. As for the current code, there is nothing I have for the AI. I have 2 spawner gameobjects that keep spawning these enemy gameobjects at random intervals, and after being spawned, they just stay where they spawned and this is where I need to create a script to be attached to the enemy gameobjects. Thanks for replying.
I guess I'll need some help on that after all. I tried putting a dummy game object in the scene and make the enemy objects look at it and move towards it but it just wouldn't work. And I ended up deleting the code. Any help is appreciated.
Big thanks for offering your own code to help out !
Oddly enough, I'm getting errors in the Console for both the scripts. For the first script, it says:
Assets/Scripts/Random.js(8,35): BCE0019: 'Range' is not a member of 'Random'.
Assets/Scripts/Random.js(10,35): BCE0019: 'Range' is not a member of 'Random'.
For the second script, it says:
Assets/Scripts/Crowd.js(26,8): BCE0005: $$anonymous$$ identifier: 'targetRotation'.
Assets/Scripts/Crowd.js(27,66): BCE0005: $$anonymous$$ identifier: 'targetRotation'.
Also, I'm using a 2D environment so I'll have to modify the world up axis Y to world up axis Z. Just infor$$anonymous$$g.
EDIT: I had the name of my script file as Random.js which was causing the error for the 1st script. Editing the same removed the error though I'm still stuck on the second scripts' error.
EDIT: I added 'var' before the beginning of both the sentences. This eli$$anonymous$$ated both the errors in the second script but there is a new error in the Console that says - Assets/Scripts/Crowd.js(27,21): BCE0043: Unexpected token: ..
EDIT: I removed ther 'var' from that line and the scripts started working. The Ai Node object started randomly teleporting throughthe environment and the randomAi object started moving but only towards the first ever position that the Ai Node object had spawned. So, it wasn't changing its' LookAt direction on every update that it should be doing. Quite an interesting script indeed. I'd love to sift through it soon. Thanks yet again for sharing !
You are very welcome! I never worked with the 2D function in Unity so are completely clueless!
The behaviour is correct, it should pick the new ainode transform a.k.a target when the distance < 1. This combined with the fast warping ainode ensures all spawned ai's will move to another location every time.
Glad I could help out.
Aha! Tweaking the distance < 1 made it work a lot better as it kept changing the direction a lot more spontaneously. Though the motion itself is not exactly the way I had hoped it would be. Currently, it travels in a straight line until the distance < 1 and then,changes the direction to a new location set by the Ai Node. Is there a way to keep the object move in a continuously curved path where it can steer in a range of say -30 degrees to +30 degrees, or something along those lines ? This is primarily for the movement to look more organic and less robotic as in the currently posted script. Also, big thanks to you Fappp, for all your help as I'm sure there will be a lot many who would find this very useful. It shall not take too much of an effort to convert this so it moves in only 2 axes for a 2D game.