The function and usage of synergy in Unity

Posted by bad76 on Wed, 09 Feb 2022 14:14:49 +0100

Coroutine can be regarded as a function whose return value is ienumeror, but it needs to be used with StartCoroutine.

A coroutine is not multithreaded. All tasks are completed on the main thread. It is an asynchronous multitask processing method.

The advantage of coroutine is that it can execute a part by frame like update in a function, or execute a part after a few seconds.

For example, implement a timer:

Common implementation methods are as follows:

This method has two disadvantages. It needs to be judged and executed once in each frame, which wastes resources.
Creating many variables actually changes only one number.

Compare the methods of using collaborative process:

yield return new WaitForSeconds will be called again in a second to execute the rest.

Two functions for terminating a coroutine, stopCoroutine and stopAllCoroutine.

yield return null is equivalent to the execution of the rest of the next frame.

The examples in the official tutorial are introduced below:

public class CoroutinesExample : MonoBehaviour
{
    public float smoothing = 1f;
    public Transform target;


    void Start ()
    {
        StartCoroutine(MyCoroutine(target));
    }


    IEnumerator MyCoroutine (Transform target)
    {
        while(Vector3.Distance(transform.position, target.position) > 0.05f)
        {
            transform.position = Vector3.Lerp(transform.position, target.position, smoothing * Time.deltaTime);

            yield return null;
        }

        print("Reached the target.");

        yield return new WaitForSeconds(3f);

        print("MyCoroutine is now finished.");
    }

After the coroutine starts executing, it will continue to execute the operation in the loop every time null is returned in the loop, and then until the loop ends. After the loop ends, it will execute print"Reached the target.", Then execute yield return new WaitForSeconds(3f);, Until 3 seconds later, return to this function again, and then execute print("MyCoroutine is now finished.");.

An example of using CO process is analyzed and implemented:
For example, click a position on the screen, and then the object will move to that position:

public class PropertiesAndCoroutines : MonoBehaviour
{
    public float smoothing = 7f;
    public Vector3 Target
    {
        get { return target; }
        set//This part of the function will be executed when the target is set
        {
            target = value;

            StopCoroutine("Movement");
            StartCoroutine("Movement", target);
        }
    }


    private Vector3 target;


    IEnumerator Movement (Vector3 target)
    {
        while(Vector3.Distance(transform.position, target) > 0.05f)
        {
            transform.position = Vector3.Lerp(transform.position, target, smoothing * Time.deltaTime);

            yield return null;
        }
    }

Using the method of CO process can realize that objects do not have to poll every frame in update, which can improve efficiency.

Click the function of setting position:
ClickSetPosition

public class ClickSetPosition : MonoBehaviour
{
    public PropertiesAndCoroutines coroutineScript;


    void OnMouseDown ()
    {
        Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);
        RaycastHit hit;

        Physics.Raycast(ray, out hit);

        if(hit.collider.gameObject == gameObject)
        {
            Vector3 newTarget = hit.point + new Vector3(0, 0.5f, 0);
            coroutineScript.Target = newTarget;
        }
    }
}

Add the function of ScreenPointToRay:

Camera.ScreenPointToRay
describe
Returns the light from the camera through the screen point.

The generated light is located in world space, starting from the near plane of the camera and passing through the (x,y) pixel coordinates of the position on the screen (ignoring position.z).

Screen space is defined in pixels. The lower left corner of the screen is (0,0), and the upper right corner is (pixelWidth -1,pixelHeight -1).

	Camera cam;

    void Start()
    {
        cam = GetComponent<Camera>();
    }

    void Update()
    {
        Ray ray = cam.ScreenPointToRay(new Vector3(200, 200, 0));
        Debug.DrawRay(ray.origin, ray.direction * 10, Color.yellow);
    }

Physics. The function of raycast is to release rays. For example, it can provide the starting point, distance and direction of emission, and then send rays
If we want to get some collision related information, we can declare a rayCastHit variable, which is used to store some collision related information:

        RaycastHit hit;


You can obtain a lot of required information and output the ray information to the ray information variable. Use the following statement:

      RaycastHit hit;
      Physics.Raycast(ray, out hit);

Topics: Unity