2
\$\begingroup\$

Unity scripts need access to components they will be using, my solution here guarantees that a script will have a valid reference to a component it needs, but is this solution overkill, or hard to discern intention from?

Note: null coalescence operators would be cleaner but cannot be used for unity objects or components for terrible reasons.

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

[RequireComponent(typeof(Rigidbody))]  // disallows deletion of component from editor
public class CubeControll : MonoBehaviour
{
    [SerializeField, HideInInspector]
    private Rigidbody rigidbody;

    private void OnValidate()
    {
        rigidbody = GetComponent<Rigidbody>() != null ? // if has component attached
            GetComponent<Rigidbody>() :  // assign referance
            gameObject.AddComponent<Rigidbody>(); // else add new component
    }

    // start, update etc
}

This is a common situation, are there any general best practices to doing this?

\$\endgroup\$
5
  • \$\begingroup\$ is there any reason for not using the constructor to validate the rigidbody ? so this way you can make it readonly. \$\endgroup\$
    – iSR5
    Aug 13, 2020 at 5:24
  • \$\begingroup\$ @Heslacher, yes this is my real code... why do you say that? both branches of the ?: operator return a Rigidbody... i'm not really sure what you mean? \$\endgroup\$
    – Jay
    Aug 13, 2020 at 10:00
  • \$\begingroup\$ @iSR5, are you familiar with Unity? This class inherits from monobehavior, you should never create a constructor for monobehavior derived objects \$\endgroup\$
    – Jay
    Aug 13, 2020 at 10:07
  • 1
    \$\begingroup\$ @Jake unfortunately no, that's why I asked you. But it's clear now. \$\endgroup\$
    – iSR5
    Aug 13, 2020 at 12:02
  • \$\begingroup\$ Oh, you're right. sorry i don't know how that happened. I've corrected my code \$\endgroup\$
    – Jay
    Aug 13, 2020 at 12:28

1 Answer 1

1
\$\begingroup\$

Right now you are calling GetComponent<T>() twice if the first call return a value != null.

Well, I would do this in a very simple way.

private void OnValidate()
{
    rigidbody = GetComponent<Rigidbody>();
    if (rigidbody != null) { return; }
 
    rigidbody = gameObject.AddComponent<Rigidbody>();
}
\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.