FPS drops overtime when running samples from Unity Render Streaming

Hello, I am using the receiver sample from Unity with the Webapp to receive a 360 video and display it on the skybox, however I am getting frames drops from using the Unity Render Streaming sample. This has been confirmed by isolating the WebApp and simply rendering a video from local disk into a skybox, even then the FPS still drops. This happens in the 3.0.1-preview Unity Render Streaming plugin version.

However, the lastest plugin version does not drop the FPS when I run the video locally, but code to receive the frames breaks.

Here is the code that works works perfectly but breaks on the lastest version:

using System;
using UnityEngine;
using UnityEngine.UI;

namespace Unity.RenderStreaming
{
    public class ReceiverSample : MonoBehaviour
    {
#pragma warning disable 0649
        [SerializeField] private Button startButton;
        [SerializeField] private Button stopButton;
        [SerializeField] private ReceiveVideoViewer receiveVideoViewer;
        [SerializeField] private SingleConnection connection;
        [SerializeField] private Material skyboxMaterial;
        [SerializeField] private Camera mainCamera;
        [SerializeField] private Canvas canvas;
#pragma warning restore 0649

        private string connectionId = "75189";
        private Texture currentTexture;
        private float deltaTime;

        void Awake()
        {
            // Load fallback image for testing
            Texture2D fallbackTexture = Resources.Load<Texture2D>("exemplo");
            if (fallbackTexture == null)
            {
                Debug.LogError("Fallback TestImage not found in Resources folder!");
            }

            // Skybox material setup
            if (skyboxMaterial == null)
            {
                skyboxMaterial = Resources.Load<Material>("360Material");
                if (skyboxMaterial == null)
                {
                    Debug.LogError("360Material not found in Resources folder!");
                }
                else
                {
                    Debug.Log("360Material successfully assigned.");
                    skyboxMaterial.SetTexture("_MainTex", fallbackTexture);
                    RenderSettings.skybox = skyboxMaterial;
                    DynamicGI.UpdateEnvironment(); // Refresh skybox lighting
                }
            }

            if (mainCamera == null)
            {
                mainCamera = Camera.main;
                if (mainCamera == null)
                {
                    Debug.LogError("Main camera not found!");
                }
                else
                {
                    Debug.Log("Main camera successfully assigned.");
                }
            }

            // Set up event to update skybox with received video texture
            if (receiveVideoViewer != null)
            {
                receiveVideoViewer.OnUpdateReceiveTexture += UpdateSkyboxTexture;
            }
            else
            {
                Debug.LogError("ReceiveVideoViewer is not assigned!");
            }
        }

        private void UpdateSkyboxTexture(Texture texture)
        {
            if (texture == null)
            {
                Debug.LogError("No texture received!");
                return;
            }

            // Check if the texture has changed to avoid redundant updates
            if (texture == currentTexture)
            {
                return; // No update needed
            }

            currentTexture = texture;
            Debug.Log($"Received new texture with dimensions: {texture.width}x{texture.height}");

            // Apply the new texture to the skybox material
            skyboxMaterial.SetTexture("_MainTex", texture);
            RenderSettings.skybox = skyboxMaterial;
            DynamicGI.UpdateEnvironment(); // Refresh skybox to apply new texture
            Debug.Log("Skybox material updated with video texture.");
        }

        void Start()
        {
            if (mainCamera != null)
            {
                // Set initial camera position for 360 video view
                mainCamera.transform.position = new Vector3(476f, 238f, -596f);
            }

            // Automatically start the video
            OnStart();
        }

        void Update()
        {
            // Calculate FPS
            deltaTime += (Time.deltaTime - deltaTime) * 0.1f;
        }

        void OnGUI()
        {
            // Display FPS counter in the top-left corner
            int width = Screen.width, height = Screen.height;

            GUIStyle style = new GUIStyle();

            Rect rect = new Rect(10, 10, width, height * 2 / 100);
            style.alignment = TextAnchor.UpperLeft;
            style.fontSize = height * 2 / 100;
            style.normal.textColor = Color.white;

            float fps = 1.0f / deltaTime;
            string text = $"FPS: {Mathf.Ceil(fps)}";
            GUI.Label(rect, text, style);
        }

        private void OnStart()
        {
            if (connection != null)
            {
                // Start the connection to receive the video stream
                connection.CreateConnection(connectionId);
                Debug.Log("Started connection to receive video.");
            }
            else
            {
                Debug.LogError("SingleConnection is not assigned!");
            }
        }

        private void OnStop()
        {
            if (connection != null)
            {
                // End the video connection
                connection.DeleteConnection(connectionId);
                connectionId = string.Empty;

                // Reset button visibility
                startButton?.gameObject.SetActive(true);
                stopButton?.gameObject.SetActive(false);
                Debug.Log("Stopped connection and cleaned up.");
            }
            else
            {
                Debug.LogError("SingleConnection is not assigned!");
            }
        }

        private void DeactivateCanvas()
        {
            if (canvas != null)
            {
                canvas.gameObject.SetActive(false);
            }
        }

        private void OnDestroy()
        {
            // Unsubscribe from texture update event
            if (receiveVideoViewer != null)
            {
                receiveVideoViewer.OnUpdateReceiveTexture -= UpdateSkyboxTexture;
            }
        }
    }
}

This is the error I get:

Assets\Samples\Unity Render Streaming\3.0.1-preview\Example\Gyro\GyroSample.cs(13,34):
error CS0246: The type or namespace name ‘VideoStreamReceiver’ could not be found
(are you missing a using directive or an assembly reference?)

Assets\Samples\Unity Render Streaming\3.0.1-preview\Example\Gyro\GyroSample.cs(14,34):
error CS0246: The type or namespace name ‘SignalingManager’ could not be found
(are you missing a using directive or an assembly reference?)

Assets\Samples\Unity Render Streaming\3.0.1-preview\Example\Gyro\GyroSample.cs(15,34):
error CS0246: The type or namespace name ‘SingleConnection’ could not be found
(are you missing a using directive or an assembly reference?)

Although the error is pointed out for the Gyro class, even if I remove the Gyro class, it will happen to any samples (eg. Receiver) In the Unity Render Streaming.

I’d like to know how to fix this…

  • What are the replacements for VideoStreamReceiver, SignalingManager, and SingleConnection in the latest version?
  • Are there migration guides or updated documentation for these changes?