众所周知,www.texture 在下载大纹理时会导致打嗝。
你应该尝试的事情:
1。使用WWW's LoadImageIntoTexture 函数将现有Texture2D 的内容替换为下载数据中的图像。如果问题仍然没有解决,请继续阅读。
WWW www = new WWW("file://" + filePath);
yield return www;
///////m_myTexture = www.texture; // Commenting this line removes frame out
www.LoadImageIntoTexture(m_myTexture);
2.使用www.textureNonReadable变量
使用www.textureNonReadable 代替www.texture 也可以加快加载时间。我经常看到这种情况发生。
3.使用函数Graphics.CopyTexture从一个纹理复制到另一个纹理。这应该很快。如果问题仍然没有解决,请继续阅读。
//Create new Empty texture with size that matches source info
m_myTexture = new Texture2D(www.texture.width, www.texture.height, www.texture.format, false);
Graphics.CopyTexture(www.texture, m_myTexture);
4.使用 Unity 的 UnityWebRequest API。这取代了 WWW 类。您必须拥有 Unity 5.2 及更高版本才能使用它。它具有GetTexture 功能,针对下载纹理进行了优化。
using (UnityWebRequest www = UnityWebRequest.GetTexture("http://www.my-server.com/image.png"))
{
yield return www.Send();
if (www.isError)
{
Debug.Log(www.error);
}
else
{
m_myTexture = DownloadHandlerTexture.GetContent(www);
}
}
如果以上三个选项都没有解决冻结问题,另一种解决方案是在带有GetPixel 和SetPixel 函数的协程函数中一个一个地复制像素。您添加一个计数器并设置您希望它等待的时间。随着时间的推移,它会间隔纹理复制。
5. 使用GetPixel 和SetPixel 函数逐一复制Texture2D 像素。示例代码包含来自 Nasa 的 8K 纹理,用于测试目的。复制Texture 时不会阻塞。如果是,请减小copyTextureAsync 函数中LOOP_TO_WAIT 变量的值。您还可以选择提供一个在复制Texture 完成后将调用的函数。
public Texture2D m_myTexture;
void Start()
{
//Application.runInBackground = true;
StartCoroutine(downloadTexture());
}
IEnumerator downloadTexture()
{
//http://visibleearth.nasa.gov/view.php?id=79793
//http://eoimages.gsfc.nasa.gov/images/imagerecords/79000/79793/city_lights_africa_8k.jpg
string url = "http://eoimages.gsfc.nasa.gov/images/imagerecords/79000/79793/city_lights_africa_8k.jpg";
//WWW www = new WWW("file://" + filePath);
WWW www = new WWW(url);
yield return www;
//m_myTexture = www.texture; // Commenting this line removes frame out
Debug.Log("Downloaded Texture. Now copying it");
//Copy Texture to m_myTexture WITHOUT callback function
//StartCoroutine(copyTextureAsync(www.texture));
//Copy Texture to m_myTexture WITH callback function
StartCoroutine(copyTextureAsync(www.texture, false, finishedCopying));
}
IEnumerator copyTextureAsync(Texture2D source, bool useMipMap = false, System.Action callBack = null)
{
const int LOOP_TO_WAIT = 400000; //Waits every 400,000 loop, Reduce this if still freezing
int loopCounter = 0;
int heightSize = source.height;
int widthSize = source.width;
//Create new Empty texture with size that matches source info
m_myTexture = new Texture2D(widthSize, heightSize, source.format, useMipMap);
for (int y = 0; y < heightSize; y++)
{
for (int x = 0; x < widthSize; x++)
{
//Get color/pixel at x,y pixel from source Texture
Color tempSourceColor = source.GetPixel(x, y);
//Set color/pixel at x,y pixel to destintaion Texture
m_myTexture.SetPixel(x, y, tempSourceColor);
loopCounter++;
if (loopCounter % LOOP_TO_WAIT == 0)
{
//Debug.Log("Copying");
yield return null; //Wait after every LOOP_TO_WAIT
}
}
}
//Apply changes to the Texture
m_myTexture.Apply();
//Let our optional callback function know that we've done copying Texture
if (callBack != null)
{
callBack.Invoke();
}
}
void finishedCopying()
{
Debug.Log("Finished Copying Texture");
//Do something else
}