我正在统一开发一个应用程序,它将显示数据库中项目的名称和图像。我使用预制件来显示名称和图像,但是我不知道如何通过URL(链接)数组在预制件中显示图像。
我做了预制
newObj.transform.GetChild(2).GetComponent<Image>().sprite = GetItems.getItems.itemsimage[i];
统一显示图像,但我不知道如何显示
public void PopulateItems(int categoryBtnClick)
{
GameObject newObj;
for (int i = 0; i < GetItems.getItems.itemsData.Length-1; i++)
{
int cat_id = int.Parse(GetItems.getItems.category_id[i]);
if (cat_id == categoryBtnClick) //cat_id and categoryBtnClick contains id of item
{
newObj = (GameObject)Instantiate(itemScrollviewPrefab, transform);
newObj.transform.GetChild(0).GetComponent<Text>().text =GetItems.getItems.itemsName[i];
newObj.transform.GetChild(1).GetComponent<Text>().text = GetItems.getItems.itemsId[i];
if (GetItems.getItems.itemsModel[i] != null)
{
newObj.transform.GetChild(2).GetComponent<Image>().sprite =GetItems.getItems.itemsimage[i] ; //itemsimage[i] contains link of image
}
newObj.transform.GetChild(3).GetComponent<Text>().text = GetItems.getItems.itemsPrice[i];
newObj.transform.GetChild(4).GetComponent<Text>().text = GetItems.getItems.itemsDescription[i];
newObj.transform.parent = itemContentParent.transform;
}
}
}
我希望每次循环在该索引上运行图像都会统一打印
答案 0 :(得分:0)
RawImage
没有sprite
,但是需要Texture
。
您不能简单地传递URL。您必须download the texture,然后将结果应用于rawImage.texture
。来自文档的示例:
using UnityEngine;
using System.Collections;
using UnityEngine.Networking;
public class MyBehaviour : MonoBehaviour
{
void Start()
{
StartCoroutine(GetTexture());
}
IEnumerator GetTexture()
{
UnityWebRequest www = UnityWebRequestTexture.GetTexture("http://www.my-server.com/image.png");
yield return www.SendWebRequest();
if(www.isNetworkError || www.isHttpError)
{
Debug.Log(www.error);
}
else
{
Texture myTexture = ((DownloadHandlerTexture)www.downloadHandler).texture;
}
}
}
下载是异步进行的,因此在下载所有图像之前可能会生成预制件...取决于您如何处理此问题(例如,同时显示加载动画或占位符)-我假设您要实例化马上。
您只需将回调添加到download方法即可在成功或失败时执行任何方法:
IEnumerator GetTexture(string url, Action<Texture> successCallback, = null, Action<string> errorCallback = null)
{
UnityWebRequest www = UnityWebRequestTexture.GetTexture(url);
yield return www.SendWebRequest();
if(www.isNetworkError || www.isHttpError)
{
errorCallback?.Invoke(www.error);
}
else
{
successCallback?.Invoke(((DownloadHandlerTexture)www.downloadHandler).texture);
}
}
,然后在代码中添加回调,例如使用lambda expressions,应在成功或错误时执行:
// ...
if (GetItems.getItems.itemsModel[i] != null)
{
// optional here add a loading or default texture
// to be displayed until texture is downloaded e.g.
newObj.transform.GetChild(2).GetComponent<RawImage>().texture = someDefaultTexture;
// start the download
StartCoroutine(GetTexture(
// The url
GetItems.getItems.itemsimage[i],
// executed on success
(s) =>
{
OnSuccess(newObj.transform.GetChild(2).GetComponent<RawImage>(), s);
},
// optional for visualizing download errors
(e) =>
{
OnError(e);
}
));
}
// ...
最后实现回调,例如:
// callback for success download
private void OnSuccess(RawImage rawImage, Texture texture)
{
rawImage.texture = texture;
}
// callback for download error
private void OnError(RawImage rawImage, string error)
{
rawImage.Texture = someErrorTexture;
Debug.Log(error, this);
}
关于下载的纹理的一个警告(因为我最近也犯了这个错误):
通常未使用/未引用的纹理会被垃圾收集/删除,因此设备的内存不会被填满... 但是显然,通过UnityWebRequest
创建的纹理甚至不会被破坏如果他们没有任何参考资料了。
这可能会导致内存泄漏,导致下载的纹理填充设备的内存!
因此,当您不再需要任何下载的纹理时,请确保积极销毁它们,例如通过添加类似
的脚本public class CleanUpTexture : MonoBehaviour
{
private RawImage rawImage;
private void Awake()
{
rawImage = GetComponent<RawImage>();
}
private void OnDestroy()
{
if(!rawImage || rawImage.texture == null) return;
Destroy(rawImage.texture);
}
}
RawImage
组件旁边的那个纹理是否应该与对象一起被破坏。
这当然假设您永远不会将相同的纹理分配给其他任何东西。并且还假设您永远不会为该对象分配不同的纹理(因为1.您会松散对下载的纹理的引用,并且2.可能会破坏您本来不是想要的纹理)