下载文件之前从 http 请求获取文件/AssetBundle 大小

siu*_*ala 5 c# unity-game-engine

问题:

我想在完成下载文件之前获取 assetBundle 的大小。我可以向用户显示剩余时间。在Unity2018.2中,我们可以获取让我乘以进度的文件大小下载文件大小吗?或者还有其他方法来计算剩余时间

我知道WWW.responseHeaders包含该信息,但似乎需要完成下载。

这是我目前的代码。

    using (WWW downloadPackageWWW = new WWW(pkg.url))
    {
        while (!downloadPackageWWW.isDone)
        {
            print("progress: " + downloadPackageWWW.progress * 100 + "%");    
            yield return null;
        }

        if (downloadPackageWWW.error != null)
            print("WWW download had an error:" + downloadPackageWWW.error);
        if (downloadPackageWWW.responseHeaders.Count > 0) 
            print(pkg.fileName + ": " + downloadPackageWWW.responseHeaders["Content-Length"]+" byte");

        byte[] bytes = downloadPackageWWW.bytes;
        File.WriteAllBytes(pkgPath, bytes);

    }
Run Code Online (Sandbox Code Playgroud)

--

更新:

为了获得剩余时间,我提出了一个理想的方法,通过Time.deltaTime来计算,并且我们不需要知道总文件大小和下载速度。

float lastProgress = 0;
while (!www.isDone)
{  
     float deltaProgress = www.progress - lastProgress;
     float progressPerSec = deltaProgress / Time.deltaTime;
     float remaingTime = (1 - www.progress) / progressPerSec;
     print("Remaining: " + remaingTime + " sec"); 
     lastProgress = www.progress;
     yield return null;
}
Run Code Online (Sandbox Code Playgroud)

Pro*_*mer 5

您应该使用 Unity 的UnityWebRequestAPI 来向我们发出请求。在您当前的 Unity 版本中,WWWAPI 现在是在底层实现的UnityWebRequest,但它仍然缺乏许多功能。

您可以通过两种方式获取文件的大小,而无需下载或等待文件完成下载:

1.HEAD通过提出请求UnityWebRequest.Head。然后您可以使用UnityWebRequest.GetResponseHeader("Content-Length")来获取数据的大小。

IEnumerator GetFileSize(string url, Action<long> resut)
{
    UnityWebRequest uwr = UnityWebRequest.Head(url);
    yield return uwr.SendWebRequest();
    string size = uwr.GetResponseHeader("Content-Length");

    if (uwr.isNetworkError || uwr.isHttpError)
    {
        Debug.Log("Error While Getting Length: " + uwr.error);
        if (resut != null)
            resut(-1);
    }
    else
    {
        if (resut != null)
            resut(Convert.ToInt64(size));
    }
}
Run Code Online (Sandbox Code Playgroud)

用法

void Start()
{
    string url = "http://ipv4.download.thinkbroadband.com/5MB.zip";
    StartCoroutine(GetFileSize(url,
    (size) =>
    {
        Debug.Log("File Size: " + size);
    }));
}
Run Code Online (Sandbox Code Playgroud)

2 . 另一种选择是使用UnityWebRequestwithDownloadHandlerScript然后覆盖该void ReceiveContentLength(int contentLength)函数。调用该SendWebRequest函数后,该ReceiveContentLength函数应在参数中为您提供下载大小contentLength。然后您应该中止该UnityWebRequest请求。下面是一个关于如何使用 的示例DownloadHandlerScript

我会选择第一个解决方案,因为它更简单、更容易并且需要更少的资源来工作。