Generally speaking, you would never directly access game objects from a different scene. A somewhat better approach would be to create an object or script that persists across scenes, and have the objects in the scene derive some of their settings from that object or script.
Object.DontDestroyOnLoad is your friend here. If you call this function, and pass the object you want to persist as the argument, that object will persist across scene changes. It will continue to exist for as long as your game is running, no matter what scene you are playing.
Another option would be to use static variables in some of your component scripts. Static variables exist for the class they are defined in. If you change them, they will change for every instance of that class. I generally wouldn’t use them just for the access advantage, as that isn’t their primary purpose. But for items that only have a single instance they could actually be quite useful.
All Components tah need to be referenced from another scene was inherit from IDBehaviour.
ID Behaviour has the only filed public GuidId (Guidis custom serializable class with 2 Int32 fields and overriden equality operator), and Awake function that adds link to component to static
private class IDBehaviour : MonoBehaviour
{
private static Dictionary<Guid, IDBehaviour> _objectsByIds;
public static Dictionary<Guid, IDBehaviour> ObjectsDict
{
get
{
return _objectsByIds;
}
}
[SerializeFiled]
private Guid _id;
private void Awake ( )
{
_objectsByIds.Add( _id, this );
}
}
In another scene i have components with filed like this:
[SerializeField, ObjectID(typeof(SomeType))]
private Guid _someObjId;
public SomeType SomeObj
{
get
{
return (SomeType)IDBehaviour.ObjectsDict[_someObjId];
}
}
And also I have wrote custom PropertyDrawer for ObjectID attribute so the link can be done through drag’n’drop.