RenderTexture 到 Texture2D 非常慢
RenderTexture to Texture2D is very slowly
我们在 Unity3D 上开发了一个应用程序,它将从屏幕上获取图像并将其传输到 Texture2D。
我们在普通(弱)设备上的性能有困难。
代码如下。我们截屏,然后读取像素 (ReadPixels) - 问题出现了,应用程序运行速度非常慢。
我们尝试从相机获取纹理,但它不起作用,因为我们的扫描仪与 Kudan 并行工作,反过来它会阻止对相机的访问。然后我们尝试限制要扫描的屏幕区域(通过扫描一个小 window,但不是全屏)——但性能没有明显提高。
有人能帮忙吗?
这是我们的代码:
IEnumerator DecodeScreen()
{
yield return new WaitForEndOfFrame();
RenderTexture RT = new RenderTexture(Screen.width, Screen.height,24);
Texture2D screen = new Texture2D(RT.width, RT.height, TextureFormat.RGB24, false, false);
screen.ReadPixels(new Rect(0, 0, RT.width, RT.height), 0, 0);
screen.Apply();
Debug.Log(resultText.text);
GetComponent().targetTexture = null;
Destroy(RT);
}
有几种方法可以改进此代码或将 RenderTexture
转换为 Texture2D
的可选方法。
1。将 WaitForEndOfFrame
声明为函数外部的变量,这样您就不必在每次调用该函数时都这样做。
2。您每次调用该函数时都会创建一个新的 Texture2D
。在 Start
函数中执行一次,然后重新使用它。如果 RenderTexture
宽度或高度发生变化,您可以自由调整纹理大小。
3。您每次调用该函数时也会创建新的 RenderTexture
。
使用 RenderTexture.GetTemporary
获得临时 RenderTexture
速度更快。使用完毕后,您可以RenderTexture.ReleaseTemporary
释放它。
Texture2D screen = null;
WaitForEndOfFrame frameEndWait = new WaitForEndOfFrame();
void Start()
{
screen = new Texture2D(Screen.width, Screen.height, TextureFormat.RGB24, false, false);
}
IEnumerator DecodeScreen()
{
yield return frameEndWait;
RenderTexture RT = RenderTexture.GetTemporary(Screen.width, Screen.height, 24);
//Resize only when Texture2D is null or when its size changes
if (screen == null || screen.width != RT.width || screen.height != RT.height)
{
screen.Resize(RT.width, RT.height, TextureFormat.RGB24, false);
//screen = new Texture2D(Screen.width, Screen.height, TextureFormat.RGB24, false, false);
}
screen.ReadPixels(new Rect(0, 0, RT.width, RT.height), 0, 0);
screen.Apply();
RenderTexture.ReleaseTemporary(RT);
}
您还有其他选择:
使用 C++ 原生插件:
发送RenderTexture.GetNativeTexturePtr()
to a native side of your C++ then create a OpenGL texture from that and load it from C# with pointer using the Texture2D.CreateExternalTexture
function and keep updating it with the Texture2D.UpdateExternalTexture
函数。
最快的方法是放弃 RenderTexture
。使用 OpenGL glReadPixels
函数从 C++ 端截取屏幕截图,然后使用指针将图像发送到 Unity 并使用 Texture2D.CreateExternalTexture
function and keep updating it with the Texture2D.UpdateExternalTexture
function. You can modify the mouse pixel code from my 加载它并使其执行此操作。
如果不需要纹理的系统内存版本,或者 AsyncGPUReadback.Request 需要,请使用 CopyTexture()。
我们在 Unity3D 上开发了一个应用程序,它将从屏幕上获取图像并将其传输到 Texture2D。
我们在普通(弱)设备上的性能有困难。
代码如下。我们截屏,然后读取像素 (ReadPixels) - 问题出现了,应用程序运行速度非常慢。
我们尝试从相机获取纹理,但它不起作用,因为我们的扫描仪与 Kudan 并行工作,反过来它会阻止对相机的访问。然后我们尝试限制要扫描的屏幕区域(通过扫描一个小 window,但不是全屏)——但性能没有明显提高。
有人能帮忙吗?
这是我们的代码:
IEnumerator DecodeScreen()
{
yield return new WaitForEndOfFrame();
RenderTexture RT = new RenderTexture(Screen.width, Screen.height,24);
Texture2D screen = new Texture2D(RT.width, RT.height, TextureFormat.RGB24, false, false);
screen.ReadPixels(new Rect(0, 0, RT.width, RT.height), 0, 0);
screen.Apply();
Debug.Log(resultText.text);
GetComponent().targetTexture = null;
Destroy(RT);
}
有几种方法可以改进此代码或将 RenderTexture
转换为 Texture2D
的可选方法。
1。将 WaitForEndOfFrame
声明为函数外部的变量,这样您就不必在每次调用该函数时都这样做。
2。您每次调用该函数时都会创建一个新的 Texture2D
。在 Start
函数中执行一次,然后重新使用它。如果 RenderTexture
宽度或高度发生变化,您可以自由调整纹理大小。
3。您每次调用该函数时也会创建新的 RenderTexture
。
使用 RenderTexture.GetTemporary
获得临时 RenderTexture
速度更快。使用完毕后,您可以RenderTexture.ReleaseTemporary
释放它。
Texture2D screen = null;
WaitForEndOfFrame frameEndWait = new WaitForEndOfFrame();
void Start()
{
screen = new Texture2D(Screen.width, Screen.height, TextureFormat.RGB24, false, false);
}
IEnumerator DecodeScreen()
{
yield return frameEndWait;
RenderTexture RT = RenderTexture.GetTemporary(Screen.width, Screen.height, 24);
//Resize only when Texture2D is null or when its size changes
if (screen == null || screen.width != RT.width || screen.height != RT.height)
{
screen.Resize(RT.width, RT.height, TextureFormat.RGB24, false);
//screen = new Texture2D(Screen.width, Screen.height, TextureFormat.RGB24, false, false);
}
screen.ReadPixels(new Rect(0, 0, RT.width, RT.height), 0, 0);
screen.Apply();
RenderTexture.ReleaseTemporary(RT);
}
您还有其他选择:
使用 C++ 原生插件:
发送RenderTexture.GetNativeTexturePtr()
to a native side of your C++ then create a OpenGL texture from that and load it from C# with pointer using the Texture2D.CreateExternalTexture
function and keep updating it with the Texture2D.UpdateExternalTexture
函数。
最快的方法是放弃 RenderTexture
。使用 OpenGL glReadPixels
函数从 C++ 端截取屏幕截图,然后使用指针将图像发送到 Unity 并使用 Texture2D.CreateExternalTexture
function and keep updating it with the Texture2D.UpdateExternalTexture
function. You can modify the mouse pixel code from my
如果不需要纹理的系统内存版本,或者 AsyncGPUReadback.Request 需要,请使用 CopyTexture()。