Diego Dozal Magnani
Diego Dozal Magnani

Reputation: 3

Access a VideoPlayer of another scene to use VideoPlayer.Prepare()

I'm learning Unity and I have to improve the transition between a sequence of scenes which each has a GameObject called VideoManager and each of those has a VideoPlayer. I have thought use VideoPlayer.Prepare() to pre-load the next VideoPlayer of the next scene but I have found that acces to GameObject from another scene It's realy hard.

I have been searching for possibles solutions and I'm currently trying one, let me explain.

  1. Create a script VPGlobalManager with two attributes:
[SerializeField] public List<VideoPlayer> _secuence;
[SerializeField] public int _indexCurrentVP;

I want that the list _secuence continue through the life of the app, and the _indexCurrentVP is the pointer to which the current active scene can acces to know which video .Prepare() (in general for each scene I only want Prepare the next VideoPlayer of the next scene). Finally I'm thinking in append this script to a GameObject and use DontDestroyOnLoad like this post https://gamedev.stackexchange.com/questions/110958/what-is-the-proper-way-to-handle-data-between-scenes or use a static classwith those two attributes.

  1. Now, this is the big issue : I haven't found a method to fill the list _sequence, because I have to acces to a GameObject from a current scene to a scene that hasn't been loaded in order to add a reference to the next VideoPlayer (which is in the next scene) and then Prepare() it. I don't know have to do this, I have searched for a way to do it but the big problem is that the VideoPlayers are in differents scenes and I can change that. I want to achieve something like have a script called VPOptimized and add it to each VideoManager with the next content
public class VPOptimize : MonoBehaviour
{
    VPManager _vpManager;

    private void Awake()
    {
        var _vp = transform.GetComponent<VideoPlayer>() as VideoPlayer;
        if (_vp != null)
        {
            _vpManager.instance._secuence.Add(_vp); 
        }
    }
}

But unfortunately, Awake method only triggers in the active scene, so I can add all the VideoPlayers to my list . And that's all, if any of you can give feedback or advice to improve my solution or maybe find another I will be grateful.

Nice day :)

**Help me Obi Wan Strange Kenobi, you are my only hope **

Upvotes: 0

Views: 127

Answers (1)

NPatch
NPatch

Reputation: 159

This is expected. Unity does not support multi scene references (i.e. reference a gameobject and/or component of one scene in another) out of the box. What DontDestroyOnLoad does is make sure some scripts last the full lifetime of the application and are not lost during scene load/unload, but it's not gonna help you populate that list of videoplayer references beforehand.

The usual way is to load a scene and use sth like FindObjectOfType or one of its variations to find a reference to a component in one of the currently loaded scenes and cache it.

The other way would be to put all videos in a ScriptableObject which is an asset and can be referenced in all scenes and when a scene is loaded, get the video to play from the ScriptableObject and Prepare it.

As mentioned here,

Awake is called either when an active GameObject that contains the script is initialized when a Scene loads, or when a...

So you should be able to call Prepare on the video selected, provided you know how each scene can find the video to play from the ScriptableObject. Some good material for this can be found here:

  1. Game architecture with ScriptableObjects | Open Projects Devlog
  2. Unite Austin 2017 - Game Architecture with Scriptable Objects

Upvotes: 0

Related Questions