Wayback Machinekoobas.hobune.stream
May JUN Jul
Previous capture 14 Next capture
2021 2022 2023
2 captures
12 Jun 22 - 14 Jun 22
sparklines
Close Help
  • Products
  • Solutions
  • Made with Unity
  • Learning
  • Support & Services
  • Community
  • Asset Store
  • Get Unity

UNITY ACCOUNT

You need a Unity Account to shop in the Online and Asset Stores, participate in the Unity Community and manage your license portfolio. Login Create account
  • Blog
  • Forums
  • Answers
  • Evangelists
  • User Groups
  • Beta Program
  • Advisory Panel

Navigation

  • Home
  • Products
  • Solutions
  • Made with Unity
  • Learning
  • Support & Services
  • Community
    • Blog
    • Forums
    • Answers
    • Evangelists
    • User Groups
    • Beta Program
    • Advisory Panel

Unity account

You need a Unity Account to shop in the Online and Asset Stores, participate in the Unity Community and manage your license portfolio. Login Create account

Language

  • Chinese
  • Spanish
  • Japanese
  • Korean
  • Portuguese
  • Ask a question
  • Spaces
    • Default
    • Help Room
    • META
    • Moderators
    • Topics
    • Questions
    • Users
    • Badges
  • Home /
avatar image
0
Question by MarrMooMoo · Oct 30, 2017 at 06:05 PM · randomobject movement

How to make object move from one random point to another continuously?

Student new to coding so sorry if my code doesn't make much sense! In my set up I currently have a giant cube that has this script(JS) attached to it:

 public var prefab: Transform;
 
 function Update () {
     if(Input.GetMouseButtonDown(0)){
         Instantiate(prefab, new Vector3(0, 0, 3), Quaternion.identity);
     }
 }

So when clicked a sphere is spawned and dropped onto a plane below. When spawned I want these spheres to move to a random coordinate along the plane, then once it gets there to move to another random point. Here is what I have:

 var speed: float;
 var arrived: boolean;
 var randX: float;
 var randZ: float;
 var newPosition;
 
 function Start(){
     arrived = false;
     randX = Random.Range(-5, 5);
     randZ = Random.Range(-5, 5);
     newPosition = new Vector3(randX, -1.504, randZ);
 }
 
 function Update () {
     if(!arrived) {
         transform.position = Vector3.Lerp(transform.position, newPosition, Time.deltaTime * speed);
         if(GameObject.Find('SpawnedObj').transform.position.x == randX) {
             arrived = true;
             randX = Random.Range(-5, 5);
             randZ = Random.Range(-5, 5);
             newPosition = new Vector3(randX, -1.504, randZ);
         };
     };
     else if(arrived){
         // WaitForSeconds(1);
         arrived = false;
     };
 }

As you can probably tell when I run this the sphere moves to the initial random coordinate, but then doesn't move after that. How can I fix this? Also I want to have it so that when it reaches the coordinate it waits a few seconds before moving to the next, but I don't know how to do that. I dabbled with WaitForSeconds, but if thats the right way to go I don't think I used it correctly. Any kind of help would be greatly appreciated!

UPDATE:

So as I was messing around with it some more on my own I changed the GameObject.Find('SpawnedObj').transform.position.x to just transform.position.x and then changed speed from 1 to 50. What I noticed is it would then move from point to point, but at seemingly random intervals. When speed is changed back to 1 it will not move from its initial random point. I have no idea why this is. Help in any form will still be appreciated!

Comment
Add comment
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users

1 Reply

· Add your reply
  • Sort: 
avatar image
2
Best Answer

Answer by Legend_Bacon · Oct 30, 2017 at 07:25 PM

Hello there,

To preface this, I don't code in JS, so hopefully you'll be able to use my C# for your stuff. While you could in theory achieve what you want within an update loop, I would strongly recommend using a coroutine for this. More info HERE.

The "WaitForSeconds", as far as I know, works best when used in coroutines, but won't work if you just stick it in an update.

Basically, drag this script onto your sphere and it should work:

 using System.Collections;
 using UnityEngine;
 
 public class testScript : MonoBehaviour
 {
     private float movementDuration = 2.0f;
     private float waitBeforeMoving = 2.0f;
     private bool hasArrived = false;
 
     private void Update()
     {
         if(!hasArrived)
         {
             hasArrived = true;
             float randX = Random.Range(-5.0f, 5.0f);
             float randZ = Random.Range(-5.0f, 5.0f);
             StartCoroutine(MoveToPoint(new Vector3(randX, -1.504f, randZ)));
         }
     }
 
     private IEnumerator MoveToPoint(Vector3 targetPos)
     {
         float timer = 0.0f;
         Vector3 startPos = transform.position;
 
         while (timer < movementDuration)
         {
             timer += Time.deltaTime;
             float t = timer / movementDuration;
             t = t * t * t * (t * (6f * t - 15f) + 10f);
             transform.position = Vector3.Lerp(startPos, targetPos, t);
 
             yield return null;
         }
 
         yield return new WaitForSeconds(waitBeforeMoving);
         hasArrived = false;
     }
 }

If you want or need more info on cool ways to Lerp stuff, THIS is a great read.

I hope this helps!

~LegendBacon

Comment
Add comment · Show 5 · Share
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users
avatar image MarrMooMoo · Oct 30, 2017 at 07:29 PM 0
Share

Thanks for the reply, and thanks for the reads! I'll fiddle around with this in JS when I get home from class and let you know how it works/if I have any issues. I'm definitely gonna learn C# after this week, seems to be more support for it.

avatar image Legend_Bacon MarrMooMoo · Oct 30, 2017 at 07:31 PM 0
Share

I would recommend switching to C# yes, as Unity is dropping JS soon anyways. Best of luck!

~LegendBacon

avatar image MarrMooMoo · Oct 30, 2017 at 07:55 PM 0
Share

Works like a charm! Only thing I'm wondering is what to do when there are many of them and they collide, as it seems to throw it all off. Perhaps an if statement where if they come in contact with each other it kills and restarts the code? Do you think that will work?

avatar image Legend_Bacon MarrMooMoo · Oct 31, 2017 at 09:07 AM 1
Share

Hello there,

A fair point here, I didn't consider collisions. In that case, if you need to stop the coroutine immediately, you can always assign it to a variable and stop that:

 using System.Collections;
 using System.Collections.Generic;
 using UnityEngine;
 
 public class TestScript : $$anonymous$$onoBehaviour
 {
     private float movementDuration = 2.0f;
     private float waitBefore$$anonymous$$oving = 2.0f;
     private bool hasArrived = false;
     private Coroutine moveCoroutine = null;
 
     private void Update()
     {
         if (!hasArrived)
         {
             hasArrived = true;
             float randX = Random.Range(-5.0f, 5.0f);
             float randZ = Random.Range(-5.0f, 5.0f);
             moveCoroutine = StartCoroutine($$anonymous$$oveToPoint(new Vector3(randX, -1.504f, randZ)));
         }
         if (Input.Get$$anonymous$$ouseButtonDown(0))
             Stop$$anonymous$$ovement();
     }
 
     private IEnumerator $$anonymous$$oveToPoint(Vector3 targetPos)
     {
         float timer = 0.0f;
         Vector3 startPos = transform.position;
 
         while (timer < movementDuration)
         {
             timer += Time.deltaTime;
             float t = timer / movementDuration;
             t = t * t * t * (t * (6f * t - 15f) + 10f);
             transform.position = Vector3.Lerp(startPos, targetPos, t);
 
             yield return null;
         }
 
         yield return new WaitForSeconds(waitBefore$$anonymous$$oving);
         hasArrived = false;
     }
 
     private void Stop$$anonymous$$ovement()
     {
         if (moveCoroutine != null)
             StopCoroutine(moveCoroutine);
     }
 
     public void OnCollisionEnter(Collision collision)
     {
         if(collision.gameObject.CompareTag("sphereTag"))
             Stop$$anonymous$$ovement();
     }
 }
 

You can assign a coroutine to a variable by doing myCoroutineVariable = StartCoroutine($$anonymous$$yCoroutine());. Then, whenever you want to stop the coroutine, you can call StopCoroutine(myCoroutineVariable).

In this script, I do it on mouse input or when the sphere collides with an object that has the tag "sphereTag". Note that it immediately stop the coroutine, which means the "hasArrived" doesn't get set back to false.

If you need more info about collision events, I encourage you to take a look at THIS handy tutorial right here.

Hope that helps! ~LegendBacon

avatar image Meliass · Jul 04, 2019 at 09:52 PM 0
Share

Hi I know this is a pretty old post. $$anonymous$$ay I ask, what if I do not want the sphere to move indefinitely ie, stops after 3 random movement? Should I use a while loop ? If so which part of the code should i add the while loop in? :( thank you @Legend_Bacon

Your answer

Hint: You can notify a user about this post by typing @username

Up to 2 attachments (including images) can be used with a maximum of 524.3 kB each and 1.0 MB total.

Follow this Question

Answers Answers and Comments

78 People are following this question.

avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image

Related Questions

Create number of enemies when one is deid 1 Answer

¿how to take all values from an array without order? 2 Answers

Using arrays to randomly select an object 0 Answers

Random Range Seems... Unrandom 1 Answer

Random object placement. 1 Answer


Enterprise
Social Q&A

Social
Subscribe on YouTube social-youtube Follow on LinkedIn social-linkedin Follow on Twitter social-twitter Follow on Facebook social-facebook Follow on Instagram social-instagram

Footer

  • Purchase
    • Products
    • Subscription
    • Asset Store
    • Unity Gear
    • Resellers
  • Education
    • Students
    • Educators
    • Certification
    • Learn
    • Center of Excellence
  • Download
    • Unity
    • Beta Program
  • Unity Labs
    • Labs
    • Publications
  • Resources
    • Learn platform
    • Community
    • Documentation
    • Unity QA
    • FAQ
    • Services Status
    • Connect
  • About Unity
    • About Us
    • Blog
    • Events
    • Careers
    • Contact
    • Press
    • Partners
    • Affiliates
    • Security
Copyright © 2020 Unity Technologies
  • Legal
  • Privacy Policy
  • Cookies
  • Do Not Sell My Personal Information
  • Cookies Settings
"Unity", Unity logos, and other Unity trademarks are trademarks or registered trademarks of Unity Technologies or its affiliates in the U.S. and elsewhere (more info here). Other names or brands are trademarks of their respective owners.
  • Anonymous
  • Sign in
  • Create
  • Ask a question
  • Spaces
  • Default
  • Help Room
  • META
  • Moderators
  • Explore
  • Topics
  • Questions
  • Users
  • Badges