Detectar y evitar problemas comunes de rendimiento y memoria en compilaciones de Unity WebGL

Rate this content
Bookmark

Esta sesión explora problemas comunes de rendimiento y memoria que surgen en las compilaciones WebGL producidas con el motor de juego Unity. Examine cómo identificar, solucionar y evitar trampas que pueden llevar a errores de falta de memoria. Aprenda a reducir la inestabilidad del juego y mejorar el rendimiento del juego en las compilaciones WebGL.

FAQ

Los problemas de memoria en compilaciones de Unity WebGL pueden surgir debido a la cantidad limitada de memoria asignada por el navegador, que varía según el dispositivo, sistema operativo, navegador utilizado y si es de 32 o 64 bits. Estos problemas pueden afectar la complejidad del contenido que se puede ejecutar y causar ralentización o bloqueos del juego.

En Unity WebGL, la gestión de la memoria puede mejorarse utilizando técnicas como los paquetes de activos, que permiten cargar y descargar activos a demanda, y el sistema de archivos de memoria virtual que desempaqueta los activos en tiempo de ejecución, evitando asignaciones extra por parte del navegador.

El montón de Unity es un bloque contiguo de memoria donde se almacenan todos los objetos en tiempo de ejecución en una compilación WebGL, incluyendo objetos nativos, activos cargados, escenas, shaders y archivos de animación. Gestionar adecuadamente el tamaño del montón es crucial para prevenir bloqueos del juego y optimizar el rendimiento.

Para reducir el uso de memoria en WebGL, se pueden adoptar estrategias como la utilización de paquetes de activos para manejar recursos frecuentes pero grandes, el uso de un sistema direccionable como alternativa a los paquetes de activos, y optimizar el código para minimizar las nuevas asignaciones de memoria como evitar la manipulación frecuente de cadenas.

La recolección de basura (GC) en WebGL se ejecuta una vez después de cada fotograma, ya que las limitaciones de JavaScript impiden pausar todos los hilos como en otras plataformas. Esta ejecución controlada ayuda a prevenir interrupciones inesperadas pero requiere que el código esté optimizado para reducir la frecuencia de la GC y mejorar el rendimiento.

Herramientas como Backtrace son útiles para depurar problemas de rendimiento y memoria en Unity WebGL. Permiten a los desarrolladores ver errores en tiempo real y analizar información del rendimiento del juego para identificar y solucionar problemas antes de que se intensifiquen.

Oz Syed
Oz Syed
10 min
07 Apr, 2022

Comments

Sign in or register to post your comment.

Video Summary and Transcription

La charla de hoy se centra en evitar problemas de rendimiento y memoria en las compilaciones de Unity WebGL. Se destaca la importancia de administrar la memoria y mantener pequeño el tamaño del montón. Técnicas como el uso de paquetes de activos o un sistema direccionable pueden ayudar a reducir el uso de la memoria. Se discuten las limitaciones de la recolección de basura en las compilaciones WebGL, junto con consejos para optimizar el código de Unity. Herramientas como Backtrace pueden ayudar en la depuración de problemas de memoria y rendimiento.

1. Introducción a las compilaciones de Unity WebGL

Short description:

Hoy, vamos a ver algunas de las formas en que podemos evitar problemas comunes de rendimiento y memoria que surgen en las compilaciones de Unity WebGL. La memoria es una restricción importante cuando se ejecuta una compilación de WebGL en un navegador. El montón de Unity es donde se almacenan todos los objetos en tiempo de ejecución, y es importante mantener el tamaño del montón lo más pequeño posible. Al construir una aplicación WebGL, Unity genera un archivo .data que contiene todos los activos y escenas requeridos. Para reducir el uso de memoria, puedes usar paquetes de activos o un sistema direccionable. La recolección de basura también es una consideración importante en las compilaciones de WebGL.

♪♪ Hola a todos. Mi nombre es Oz, y soy un evangelista de desarrollo de juegos en Backtrace Source Labs. Hoy, vamos a ver algunas de las formas en que podemos evitar problemas comunes de performance y memoria que surgen en las compilaciones de Unity WebGL. El primer punto que vamos a examinar es la gestión del performance. Y una restricción importante al ejecutar una compilación de WebGL en un navegador con buen performance es la memoria. Entonces, en términos de memoria, ¿cuáles son los problemas y cuáles son las consideraciones que debemos examinar?

Entonces, como sabes, la complejidad del contenido que puedes ejecutar está limitada por la memoria. La memoria es asignada por el navegador, y la cantidad de memoria que tiene disponible varía en función de varios factores, incluyendo el dispositivo que usas, el sistema operativo que usas, qué navegador usas, y si se ejecuta en un navegador de 32 bits o de 62 bits, y un par de otros factores. Entonces, para entender cómo la memoria impacta en el performance, es muy importante primero ver cómo se asigna la memoria en una compilación de Unity WebGL. Para esto, necesitamos echar un vistazo al montón de Unity. Entonces, ¿qué es el montón de Unity o un montón de memoria, como lo llama Unity? Básicamente, aquí es donde se almacenan todos los objetos en tiempo de ejecución, y estos podrían incluir objetos nativos, activos que se cargan, escenas, shaders, archivos de animation, así como otros objetos gestionados. Vale la pena mencionar que este montón es un bloque contiguo de memoria asignada. Hasta hace unos años, tenías que asignar el tamaño máximo del montón en la configuración de la compilación, pero ahora, Unity soporta la expansión del montón a demanda, dependiendo de las necesidades del juego, y es expandible hasta dos juegos. Sin embargo, la misma característica puede hacer que tu juego se bloquee, especialmente cuando el navegador falla al asignar un bloque contiguo de memoria, y es exactamente por eso que es muy importante mantener el tamaño del montón lo más pequeño posible.

Ahora, para entender cómo podemos mantener el tamaño del montón de memoria pequeño, primero tenemos que echar un vistazo a lo que Unity hace con todos los activos y los datos de la escena en un navegador, y qué sucede cuando construyes una aplicación WebGL en Unity. Entonces, cuando construyes una aplicación WebGL, lo que sucede es que Unity genera un archivo .data. Y esto es básicamente todos los activos y escenas en la aplicación que se requieren en el momento del lanzamiento, y todo eso se empaqueta en un archivo .data, incluyendo las escenas de Unity, texturas, modelos, precios de UI, activos de audio, shaders, y prácticamente todo lo demás que necesitas para que el juego funcione. Y básicamente Unity WebGL no tiene acceso a un sistema de archivos real, por lo que tiene que crear un sistema de archivos de memoria virtual, y el navegador luego desempaqueta el archivo .data en este sistema de archivos virtual particular. Y el navegador, mientras el juego está en ejecución, mantiene los data sin comprimir. Ahora imagina si tienes una escena compleja con todo tipo de activos, ¿verdad? Incluyendo modelos 3D, shaders, todo. Entonces puedes ver cómo posiblemente puede tener problemas de memoria y también ralentizar el rendimiento del juego. Entonces la pregunta que surge es, ¿qué puedes hacer para reducir la memoria? Bueno, hay algunas técnicas que puedes adoptar para reducir el uso de memoria. Y una forma, la más común, es usar paquetes de activos. Entonces podrías poner todos los activos más frecuentes, pero más grandes en un paquete de activos y cargarlo, descargarlo a demanda cuando quieras. También vale la pena mencionar que los paquetes de activos se descargan directamente en el montón de Unity y por lo tanto evitan la asignación extra realizada por un navegador. Si hay paquetes grandes, una técnica es posiblemente almacenar en caché los data y esto es básicamente una cosa adicional que te ayuda a evitar la descarga cada vez que realmente juegas el juego. Entonces el tercero es algo llamado sistema direccionable, que es una alternativa a los paquetes de activos. Y a veces se inicia como una versión mejor de los paquetes de activos. Sin embargo, tiene algunos de sus propios problemas, incluyendo el soporte de las compilaciones de WebGL de serie. Pero existen algunas soluciones para hacerlo funcionar. La próxima consideración importante con respecto a las compilaciones de WebGL es la recolección de basura o GC en resumen.

2. Gestión de Memoria y Depuración en Unity WebGL

Short description:

GC en Unity WebGL se ejecuta una vez después de cada fotograma debido a las limitaciones en JavaScript. Manipular cadenas puede causar problemas de rendimiento y de memoria. Ejemplos incluyen la actualización de un texto de temporizador de cuenta regresiva y el uso de enlarged para un bucle. Para optimizar el código de Unity, use StringBuilder para la manipulación de cadenas, cache las matrices antes de iterar y use CompareTag en lugar de comparar cadenas. Herramientas como Backtrace pueden ayudar a depurar problemas de memoria y rendimiento. Si tienes preguntas sobre WebGL o Unity, no dudes en ponerte en contacto.

Entonces, típicamente lo que hace GC es localizar y recoger la memoria no utilizada y luego reasignarla al montón de Unity. En otras plataformas, cuando se ejecuta GC, todos los hilos en ejecución se pausan para dar tiempo para que GC revise la pila. Esto no es posible en WebGL debido a las limitaciones en JavaScript. Entonces, lo que hace Unity aquí es simplemente ejecutarlo una vez después de cada fotograma porque la condición para que GC se ejecute en WebGL es que la pila tiene que estar vacía y esto solo sucede después de que se renderiza cada fotograma.

Ahora veremos algunos ejemplos de code que aumentan GC y reducen el performance y cómo podemos realmente escribir un mejor code. Entonces, en el primer ejemplo que tengo aquí, puedes ver cómo la manipulación de una cadena es una causa principal de problema de performance y a veces también puede causar que una aplicación se quede sin memoria. Y la razón principal por la que esto sucede es porque cualquier manipulación de cadena hace que Unity cree una nueva cadena cada vez y esto puede sumar rápidamente. Por ejemplo, si el code fuera parte del bucle de actualización. Este ejemplo que puedes ver aquí es donde tienes un temporizador de cuenta regresiva mostrando en un UI y el texto del temporizador de cuenta regresiva se está actualizando continuamente en el bucle de actualización al agregar el prefijo de cuenta regresiva con el valor de cuenta regresiva. Y cada vez que haces eso, está creando una nueva cadena que puede sumar rápidamente y no es bueno para la memoria. A la derecha, puedes ver cómo este code se está reescribiendo en un mejor code donde separamos la etiqueta y el valor y por lo tanto evitamos la manipulación de la cadena por completo. Aquí hay otro ejemplo de manipulación de cadena. Si se está utilizando enlarged para un bucle. Ya sabes, en una compilación no-WebGL, esto podría funcionar tan bien como podría ser porque el recolector de basura estará involucrado pero no tanto en una compilación de WebGL porque en una compilación de WebGL no tiene la oportunidad de involucrarse hasta el final del fotograma y por lo tanto es probable que se quede sin memoria y se bloquee. Aquí tengo algunos otros ejemplos donde puedes optimizar el code de Unity para reducir la asignación de memoria y reducir la necesidad de recolección de basura frecuente. Entonces, cuando usas cadenas, por ejemplo, si necesitas manipular y pegar cadena, usa StringBuilder en lugar de Plus. Si estás usando funciones de Unity donde la función devolvería una matriz y tienes que hacer algunas manipulaciones de matriz o iterar a través de una matriz, deberías almacenarla en caché antes de usarla en un bucle for. Para comparaciones como comparar un nombre o etiqueta, no muchos de nosotros sabemos que estos accesorios en realidad devuelven una nueva cadena cada vez, por lo que es mejor usar, por ejemplo, para comparar con una etiqueta, usa la función CompareTag. Y por último, pero no menos importante, en el caso de las coroutines, una cosa común que tendemos a hacer como programadores es usar una línea que devuelve new WaitForSeconds o WaitUntil o WaitWhile. Así que en su lugar, almacénalo en caché y úsalo, especialmente si lo estás usando en un bucle for.

Mientras hablamos de las formas en que la memoria puede ser gestionada en algunas situaciones y cómo podemos reducir el uso de memoria, hay algunas situaciones inesperadas que pueden hacer que las aplicaciones se queden sin memoria o incluso hacer que las aplicaciones se bloqueen, así que aquí es donde las herramientas que pueden ayudar a debugging estos problemas entran en juego. Así que una de esas herramientas es Backtrace, que uso en las aplicaciones y juegos que hago para cualquier plataforma. Y por supuesto, WebGL no es una excepción. Así que cuando lo integro, puedo ver errores en tiempo real y en el panel de control y me ayuda a solucionar problemas de performance y de falta de memoria. Cosas como las que vemos hoy, estas pueden ser realmente utilizadas y luego esa información puede ser recogida para solucionar problemas futuros antes de que se salgan de control.

Eso es prácticamente el final de la masterclass. Si tienes alguna pregunta sobre WebGL o Unity, no dudes en ponerte en contacto conmigo. Mis datos de contacto están en esta diapositiva. Gracias por sintonizar. ♪♪♪

Check out more articles and videos

We constantly think of articles and videos that might spark Git people interest / skill us up or help building a stellar career

Una Guía del Comportamiento de Renderizado de React
React Advanced Conference 2022React Advanced Conference 2022
25 min
Una Guía del Comportamiento de Renderizado de React
Top Content
React es una biblioteca para "renderizar" UI a partir de componentes, pero muchos usuarios se encuentran confundidos acerca de cómo funciona realmente el renderizado de React. ¿Qué significan términos como "renderizado", "reconciliación", "Fibers", y "committing"? ¿Cuándo ocurren los renderizados? ¿Cómo afecta el Contexto al renderizado, y cómo las bibliotecas como Redux causan actualizaciones? En esta charla, aclararemos la confusión y proporcionaremos una base sólida para entender cuándo, por qué, y cómo React renderiza. Veremos: - Qué es realmente el "renderizado" - Cómo React encola los renderizados y el comportamiento de renderizado estándar - Cómo se utilizan las claves y los tipos de componentes en el renderizado - Técnicas para optimizar el rendimiento del renderizado - Cómo el uso del contexto afecta al comportamiento del renderizado - Cómo las bibliotecas externas se integran en el renderizado de React
Acelerando tu aplicación React con menos JavaScript
React Summit 2023React Summit 2023
32 min
Acelerando tu aplicación React con menos JavaScript
Top Content
¿Demasiado JavaScript te está agobiando? Los nuevos marcos que prometen no usar JavaScript parecen interesantes, pero tienes una aplicación React existente que mantener. ¿Qué tal si Qwik React es tu respuesta para un inicio de aplicaciones más rápido y una mejor experiencia de usuario? Qwik React te permite convertir fácilmente tu aplicación React en una colección de islas, que pueden ser renderizadas en el servidor y rehidratadas con retraso, e incluso en algunos casos, se puede omitir la rehidratación por completo. Y todo esto de manera incremental sin una reescritura.
Concurrencia en React, Explicada
React Summit 2023React Summit 2023
23 min
Concurrencia en React, Explicada
Top Content
¡React 18! ¡Funciones concurrentes! Tal vez ya hayas probado las nuevas APIs como useTransition, o tal vez solo hayas oído hablar de ellas. Pero, ¿sabes cómo React 18 logra las mejoras de rendimiento que trae consigo? En esta charla, echemos un vistazo bajo el capó de las características de rendimiento de React 18: - Cómo React 18 reduce el tiempo que tu página permanece congelada (también conocido como TBT) - Qué sucede exactamente en el hilo principal cuando ejecutas useTransition() - Cuál es la trampa con las mejoras (¡no hay torta gratis!), y por qué Vue.js y Preact se negaron rotundamente a lanzar algo similar
El Futuro de las Herramientas de Rendimiento
JSNation 2022JSNation 2022
21 min
El Futuro de las Herramientas de Rendimiento
Top Content
Nuestra comprensión del rendimiento y la experiencia del usuario ha evolucionado mucho a lo largo de los años. Las herramientas de desarrollo web necesitan evolucionar de manera similar para asegurarse de que sean centradas en el usuario, accionables y contextuales donde se refiere a las experiencias modernas. En esta charla, Addy te guiará a través de cómo Chrome y otros han estado pensando en este problema y qué actualizaciones han estado haciendo a las herramientas de rendimiento para reducir la fricción para construir grandes experiencias en la web.
Optimización de juegos HTML5: 10 años de aprendizaje
JS GameDev Summit 2022JS GameDev Summit 2022
33 min
Optimización de juegos HTML5: 10 años de aprendizaje
Top Content
El motor de juegos de código abierto PlayCanvas está construido específicamente para el navegador, incorporando 10 años de aprendizaje sobre optimización. En esta charla, descubrirás la salsa secreta que permite a PlayCanvas generar juegos con tiempos de carga increíblemente rápidos y tasas de fotogramas sólidas como una roca.
Construyendo Experimentos Divertidos con WebXR & Babylon.js
JS GameDev Summit 2022JS GameDev Summit 2022
33 min
Construyendo Experimentos Divertidos con WebXR & Babylon.js
Top Content
Durante esta sesión, veremos un par de demostraciones de lo que puedes hacer usando WebXR, con Babylon.js. Desde experimentos de audio en VR, hasta juegos casuales en VR en una máquina de arcade hasta un uso más serio para crear nuevas formas de colaboración usando AR o VR, deberías tener una comprensión bastante buena de lo que puedes hacer hoy.
Consulta también el artículo para ver el contenido completo, incluyendo ejemplos de código: artículo. 

Workshops on related topic

Masterclass de Depuración de Rendimiento de React
React Summit 2023React Summit 2023
170 min
Masterclass de Depuración de Rendimiento de React
Top Content
Featured WorkshopFree
Ivan Akulov
Ivan Akulov
Los primeros intentos de Ivan en la depuración de rendimiento fueron caóticos. Vería una interacción lenta, intentaría una optimización aleatoria, vería que no ayudaba, y seguiría intentando otras optimizaciones hasta que encontraba la correcta (o se rendía).
En aquel entonces, Ivan no sabía cómo usar bien las herramientas de rendimiento. Haría una grabación en Chrome DevTools o React Profiler, la examinaría, intentaría hacer clic en cosas aleatorias, y luego la cerraría frustrado unos minutos después. Ahora, Ivan sabe exactamente dónde y qué buscar. Y en esta masterclass, Ivan te enseñará eso también.
Así es como va a funcionar. Tomaremos una aplicación lenta → la depuraremos (usando herramientas como Chrome DevTools, React Profiler, y why-did-you-render) → identificaremos el cuello de botella → y luego repetiremos, varias veces más. No hablaremos de las soluciones (en el 90% de los casos, es simplemente el viejo y regular useMemo() o memo()). Pero hablaremos de todo lo que viene antes - y aprenderemos a analizar cualquier problema de rendimiento de React, paso a paso.
(Nota: Esta masterclass es más adecuada para ingenieros que ya están familiarizados con cómo funcionan useMemo() y memo() - pero quieren mejorar en el uso de las herramientas de rendimiento alrededor de React. Además, estaremos cubriendo el rendimiento de la interacción, no la velocidad de carga, por lo que no escucharás una palabra sobre Lighthouse 🤐)
Crea un Juego Con PlayCanvas en 2 Horas
JSNation 2023JSNation 2023
116 min
Crea un Juego Con PlayCanvas en 2 Horas
Top Content
Featured WorkshopFree
Steven Yau
Steven Yau
En esta masterclass, construiremos un juego utilizando el motor WebGL de PlayCanvas desde el principio hasta el final. Desde el desarrollo hasta la publicación, cubriremos las características más cruciales como la escritura de scripts, la creación de UI y mucho más.
Tabla de contenido:- Introducción- Introducción a PlayCanvas- Lo que vamos a construir- Agregando un modelo de personaje y animación- Haciendo que el personaje se mueva con scripts- 'Falsa' carrera- Agregando obstáculos- Detectando colisiones- Agregando un contador de puntuación- Fin del juego y reinicio- ¡Resumen!- Preguntas
Nivel de la masterclassSe recomienda familiaridad con los motores de juegos y los aspectos del desarrollo de juegos, pero no es obligatorio.
Construyendo aplicaciones web que iluminan Internet con QwikCity
JSNation 2023JSNation 2023
170 min
Construyendo aplicaciones web que iluminan Internet con QwikCity
Featured WorkshopFree
Miško Hevery
Miško Hevery
Construir aplicaciones web instantáneas a gran escala ha sido elusivo. Los sitios del mundo real necesitan seguimiento, análisis y interfaces y interacciones de usuario complejas. Siempre comenzamos con las mejores intenciones pero terminamos con un sitio menos que ideal.
QwikCity es un nuevo meta-framework que te permite construir aplicaciones a gran escala con un rendimiento de inicio constante. Veremos cómo construir una aplicación QwikCity y qué la hace única. El masterclass te mostrará cómo configurar un proyecto QwikCity. Cómo funciona el enrutamiento con el diseño. La aplicación de demostración obtendrá datos y los presentará al usuario en un formulario editable. Y finalmente, cómo se puede utilizar la autenticación. Todas las partes básicas para cualquier aplicación a gran escala.
En el camino, también veremos qué hace que Qwik sea único y cómo la capacidad de reanudación permite un rendimiento de inicio constante sin importar la complejidad de la aplicación.
Cómo crear arte generativo increíble con código JavaScript simple
JS GameDev Summit 2022JS GameDev Summit 2022
165 min
Cómo crear arte generativo increíble con código JavaScript simple
Top Content
WorkshopFree
Frank Force
Frank Force
En lugar de dibujar manualmente cada imagen como en el arte tradicional, los artistas generativos escriben programas que son capaces de producir una variedad de resultados. En esta masterclass aprenderás cómo crear arte generativo increíble usando solo un navegador web y un editor de texto. Comenzando con conceptos básicos y avanzando hacia la teoría avanzada, cubriremos todo lo que necesitas saber.
Next.js 13: Estrategias de Obtención de Datos
React Day Berlin 2022React Day Berlin 2022
53 min
Next.js 13: Estrategias de Obtención de Datos
Top Content
WorkshopFree
Alice De Mauro
Alice De Mauro
- Introducción- Prerrequisitos para la masterclass- Estrategias de obtención: fundamentos- Estrategias de obtención – práctica: API de obtención, caché (estática VS dinámica), revalidar, suspense (obtención de datos en paralelo)- Prueba tu construcción y sírvela en Vercel- Futuro: Componentes de servidor VS Componentes de cliente- Huevo de pascua de la masterclass (no relacionado con el tema, destacando la accesibilidad)- Conclusión
PlayCanvas de principio a fin: la versión rápida
JS GameDev Summit 2022JS GameDev Summit 2022
121 min
PlayCanvas de principio a fin: la versión rápida
Top Content
WorkshopFree
João Ruschel
João Ruschel
En esta masterclass, construiremos un juego completo utilizando el motor PlayCanvas mientras aprendemos las mejores prácticas para la gestión de proyectos. Desde el desarrollo hasta la publicación, cubriremos las características más cruciales como la gestión de activos, scripting, audio, depuración, y mucho más.