0

我使用 UnityWebRequest 加载图像。

这是代码。

            UnityWebRequest uwr;
            StartCoroutine(LoadImageCorroutine());
            IEnumerator LoadImageCorroutine()
            {
                using (uwr = UnityWebRequestTexture.GetTexture(@"file:///C://UnityTests/Filerepository/Items/3faju5ozafrz.png"))
                {
                    yield return uwr.SendWebRequest();
                    rawImage.texture = DownloadHandlerTexture.GetContent(uwr);

                    //Debug.Log(i.ToString());
                }
                uwr.Dispose();
                StopCoroutine(LoadImageCorroutine());
            }

我进行了一些性能测试,并注意到每次调用协程时内存使用率都会上升,之后并没有下降。

考虑到 CPU 负载随着时间的推移而下降,协程似乎要么正确停止,要么至少处于空闲状态。

如何摆脱 UnityWebRequest 加载到我的内存中的任何内容?

4

1 回答 1

2

我自己之前已经遇到过这个问题。您可以通过使用分析器 ( CTRL + 7)来查看发生了什么并进行内存快照

  • 点击内存模块
  • 在底部从“简单”切换到“详细”
  • 点击Take Sample
  • 结帐“资产”→“Texture2D”

在运行您的例程之前和之后。

SPOILER:您会看到,在每次运行下载例程后,内存中都会多出一个纹理资源,该资源永远不会被破坏。

问题是任何Texture下载的 viaUnityWebRequestTexture.GetTexture不会被 GC 收集,即使它不再被引用!因此,协程的每次运行都会在您的记忆中增加一个纹理实例。


为了解决这个问题,一旦你知道你真的想要破坏纹理,你必须“手动”这样做:

IEnumerator LoadImageCorroutine()
{
    using (var uwr = UnityWebRequestTexture.GetTexture(@"file:///C://UnityTests/Filerepository/Items/3faju5ozafrz.png"))
    {
        yield return uwr.SendWebRequest();

        // I would always check for errors first
        if(uwr.isHttpError || uwr.isNetworkError)
        {
            Debug.LogError($"Could not load texture do to {uwr.responseCode} - \"{uwr.error}\"", this);
            yield break;
        }

        // Destroy the current texture instance
        if(rawImage.texture) 
        {
            Destroy(rawImage.texture);
        }
     
        rawImage.texture = DownloadHandlerTexture.GetContent(uwr);

        //Debug.Log(i.ToString());
    } 

    // since you are using "using" there is no need to call Dispose() manually

    // This is anyway the end of your coroutine .. you do not want to call
    // StopCoroutine(LoadImageCorroutine()) here
}
于 2020-05-19T07:08:01.527 回答