examples ejemplos javascript html5 svg html5-canvas

javascript - ejemplos - svg html5 examples



HTML5 Canvas vs. SVG vs. div (8)

La respuesta corta:

SVG sería más fácil para usted, ya que la selección y el movimiento ya están incorporados. Los objetos SVG son objetos DOM, por lo que tienen controladores de "clic", etc.

Los DIV están bien, pero son torpes y tienen un rendimiento horrible al cargar en grandes cantidades.

Canvas tiene el mejor rendimiento, pero tiene que implementar usted mismo todos los conceptos de estado administrado (selección de objetos, etc.) o usar una biblioteca.

La respuesta larga:

HTML5 Canvas es simplemente una superficie de dibujo para un mapa de bits. Se configura para dibujar (diga con un color y grosor de línea), dibuje esa cosa, y luego el Lienzo no tiene conocimiento de esa cosa: no sabe dónde está ni qué es lo que acaba de dibujar, es sólo píxeles. Si desea dibujar rectángulos y hacer que se muevan o que puedan seleccionarse, debe codificar todo eso desde cero, incluido el código para recordar que los dibujó.

Por otro lado, SVG debe mantener referencias a cada objeto que representa. Cada elemento SVG / VML que creas es un elemento real en el DOM. De forma predeterminada, esto le permite realizar un seguimiento mucho mejor de los elementos que crea y facilita el manejo de cosas como los eventos del mouse de manera predeterminada, pero se ralentiza significativamente cuando hay una gran cantidad de objetos.

Esas referencias SVG DOM significan que algunos de los pasos para tratar con las cosas que dibuja se hacen por usted. Y SVG es más rápido cuando se procesan objetos realmente grandes , pero más lento cuando se procesan muchos objetos.

Un juego probablemente sería más rápido en Canvas. Un programa de mapa enorme probablemente sería más rápido en SVG. Si quiere usar Canvas, tengo algunos tutoriales sobre cómo poner en funcionamiento los objetos móviles here .

El lienzo sería mejor para las cosas más rápidas y la manipulación de mapas de bits pesados ​​(como la animación), pero tomará más código si quieres mucha interactividad.

He corrido un montón de números en el dibujo hecho en HTML DIV versus el dibujo hecho en lienzo. Podría hacer una gran publicación sobre los beneficios de cada uno, pero le daré algunos de los resultados relevantes de mis pruebas para que los tenga en cuenta para su aplicación específica:

Hice páginas de prueba Canvas y HTML DIV, ambas tenían "nodos" móviles. Los nodos de lienzo eran objetos que creé y seguí en Javascript. Los nodos HTML eran Divs movibles.

Agregué 100,000 nodos a cada una de mis dos pruebas. Se realizaron de manera muy diferente:

La pestaña de prueba HTML tardó una eternidad en cargarse (cronometrada en poco menos de 5 minutos, Chrome pidió que se eliminara la página la primera vez). El administrador de tareas de Chrome dice que la pestaña está ocupando 168MB. Toma un tiempo de CPU de 12-13% cuando lo estoy mirando, 0% cuando no estoy mirando.

La pestaña Lienzo cargada en un segundo y ocupa 30MB. También ocupa el 13% del tiempo de CPU todo el tiempo, independientemente de si uno lo está mirando o no. (Edición de 2013: En su mayoría han arreglado eso)

El arrastre en la página HTML es más suave, como lo espera el diseño, ya que la configuración actual consiste en volver a dibujar TODO cada 30 milisegundos en la prueba Canvas. Hay muchas optimizaciones para Canvas para esto. (La invalidación del lienzo es la más fácil, también las regiones de recorte, el redibujo selectivo, etc., solo depende de lo mucho que desee implementar)

No hay duda de que podría hacer que Canvas sea más rápido en la manipulación de objetos como los divs en esa simple prueba y, por supuesto, mucho más rápido en el tiempo de carga. Dibujar / cargar es más rápido en Canvas y también tiene mucho más espacio para optimizaciones (es decir, excluir cosas que están fuera de la pantalla es muy fácil).

Conclusión:

  • SVG es probablemente mejor para aplicaciones y aplicaciones con pocos elementos (¿menos de 1000? Depende realmente)
  • Canvas es mejor para miles de objetos y manipulación cuidadosa, pero se necesita mucho más código (o una biblioteca) para despegar.
  • Las Divs HTML son torpes y no se escalan, lo que hace que un círculo solo sea posible con esquinas redondeadas, lo que hace que las formas complejas sean posibles, pero involucra cientos de divs diminutos de pixel de ancho. La locura sobreviene.

¿Cuál es el mejor enfoque para crear elementos sobre la marcha y poder moverlos? Por ejemplo, digamos que quiero crear un rectángulo, círculo y polígono y luego seleccionar esos objetos y moverlos.

Entiendo que HTML5 proporciona tres elementos que pueden hacer esto posible: svg , canvas y div . Para lo que quiero hacer, ¿cuál de esos elementos proporcionará el mejor rendimiento?

Para comparar estos enfoques, estaba pensando en crear tres páginas web visualmente idénticas, cada una con un encabezado, pie de página, widget y contenido de texto. El widget en la primera página se crearía completamente con el elemento canvas , el segundo completamente con el elemento svg y el tercero con el elemento div simple, HTML y CSS.


Conocer las diferencias entre SVG y Canvas sería útil para seleccionar el correcto.

Lona

  • Resolución dependiente
  • No hay soporte para manejadores de eventos.
  • Capacidades de representación de texto pobres
  • Puede guardar la imagen resultante como .png o .jpg
  • Muy adecuado para juegos de gráficos intensivos

SVG

  • Resolución independiente
  • Soporte para manejadores de eventos.
  • Ideal para aplicaciones con grandes áreas de renderizado (Google Maps)
  • Representación lenta si es compleja (cualquier cosa que use mucho el DOM será lenta)
  • No es adecuado para la aplicación de juegos

Estoy de acuerdo con las conclusiones de Simon Sarris:

He comparado alguna visualización en Protovis (SVG) con Processingjs (Canvas) que muestra> 2000 puntos y processingjs es mucho más rápida que protovis.

El manejo de eventos con SVG es mucho más fácil porque puede adjuntarlos a los objetos. En Canvas debe hacerlo manualmente (verifique la posición del mouse, etc.) pero para una interacción simple no debería ser difícil.

También está la biblioteca dojo.gfx del kit de herramientas de dojo. Proporciona una capa de abstracción y puede especificar el renderizador (SVG, Canvas, Silverlight). Esa podría ser también una opción viable, aunque no sé cuánta sobrecarga agrega la capa de abstracción adicional, pero hace que sea más fácil codificar interacciones y animaciones y es agnóstico con el procesador.

Aquí hay algunos puntos de referencia interesantes:


Mientras busco en Google, encuentro una buena explicación sobre el uso y la compresión de SVG y Canvas en http://teropa.info/blog/2016/12/12/graphics-in-angular-2.html

Espero eso ayude:

  • SVG, al igual que HTML, utiliza la representación retenida : cuando queremos dibujar un rectángulo en la pantalla, usamos de forma declarativa un elemento en nuestro DOM. El navegador dibujará un rectángulo, pero también creará un objeto SVGRectElement en memoria que representa el rectángulo. Este objeto es algo que se adhiere para que lo manipulemos, se conserva. Podemos asignarle diferentes posiciones y tamaños a lo largo del tiempo. También podemos adjuntar oyentes de eventos para hacerlo interactivo.
  • El lienzo utiliza la representación inmediata : cuando dibujamos un rectángulo , el navegador muestra de inmediato un rectángulo en la pantalla, pero nunca habrá ningún "objeto rectangular" que lo represente. Solo hay un montón de píxeles en el búfer de lienzo. No podemos mover el rectángulo. Solo podemos dibujar otro rectángulo. No podemos responder a clics u otros eventos en el rectángulo. Solo podemos responder a eventos en todo el lienzo .

Así que el lienzo es una API más restrictiva y de bajo nivel que SVG. Pero hay un lado negativo en eso, que es que con Canvas puede hacer más con la misma cantidad de recursos. Debido a que el navegador no tiene que crear y mantener el gráfico de objetos en memoria de todas las cosas que hemos dibujado, necesita menos recursos de memoria y computación para dibujar la misma escena visual. Si tiene una visualización muy grande y compleja para dibujar, Canvas puede ser su boleto.


Para agregar a esto, he estado haciendo una aplicación de diagrama, y ​​inicialmente comencé con lienzo. El diagrama consta de muchos nodos, y pueden ser bastante grandes. El usuario puede arrastrar elementos en el diagrama alrededor.

Lo que encontré fue que en mi Mac, para imágenes muy grandes, SVG es superior. Tengo una MacBook Pro 2013 13 "Retina, y funciona bastante bien con el violín de abajo. La imagen es de 6000x6000 píxeles y tiene 1000 objetos. Una construcción similar en un lienzo era imposible de animar para mí cuando el usuario estaba arrastrando objetos en el diagrama.

En las pantallas modernas, también debe tener en cuenta las diferentes resoluciones, y aquí SVG le ofrece todo esto de forma gratuita.

Fiddle: http://jsfiddle.net/knutsi/PUcr8/16/

Pantalla completa: http://jsfiddle.net/knutsi/PUcr8/16/embedded/result/

var wiggle_factor = 0.0; nodes = []; // create svg: var svg = document.createElementNS("http://www.w3.org/2000/svg", "svg"); svg.setAttribute(''style'', ''border: 1px solid black''); svg.setAttribute(''width'', ''6000''); svg.setAttribute(''height'', ''6000''); svg.setAttributeNS("http://www.w3.org/2000/xmlns/", "xmlns:xlink", "http://www.w3.org/1999/xlink"); document.body.appendChild(svg); function makeNode(wiggle) { var node = document.createElementNS("http://www.w3.org/2000/svg", "g"); var node_x = (Math.random() * 6000); var node_y = (Math.random() * 6000); node.setAttribute("transform", "translate(" + node_x + ", " + node_y +")"); // circle: var circ = document.createElementNS("http://www.w3.org/2000/svg", "circle"); circ.setAttribute( "id","cir") circ.setAttribute( "cx", 0 + "px") circ.setAttribute( "cy", 0 + "px") circ.setAttribute( "r","100px"); circ.setAttribute(''fill'', ''red''); circ.setAttribute(''pointer-events'', ''inherit'') // text: var text = document.createElementNS("http://www.w3.org/2000/svg", "text"); text.textContent = "This is a test! ÅÆØ"; node.appendChild(circ); node.appendChild(text); node.x = node_x; node.y = node_y; if(wiggle) nodes.push(node) return node; } // populate with 100 nodes: for(var i = 0; i < 1000; i++) { var node = makeNode(true); svg.appendChild(node); } // make one mapped to mouse: var bnode = makeNode(false); svg.appendChild(bnode); document.body.onmousemove=function(event){ bnode.setAttribute("transform","translate(" + (event.clientX + window.pageXOffset) + ", " + (event.clientY + window.pageYOffset) +")"); }; setInterval(function() { wiggle_factor += 1/60; nodes.forEach(function(node) { node.setAttribute("transform", "translate(" + (Math.sin(wiggle_factor) * 200 + node.x) + ", " + (Math.sin(wiggle_factor) * 200 + node.y) + ")"); }) },1000/60);


Para sus propósitos, recomiendo usar SVG, ya que obtiene eventos DOM, como el manejo del mouse, incluido el arrastrar y soltar, incluido, no tiene que implementar su propio redibujo y no tiene que realizar un seguimiento del estado de tus objetos Usa Canvas cuando tengas que manipular imágenes de mapa de bits y usa un div regular cuando quieras manipular cosas creadas en HTML. En cuanto al rendimiento, verás que los navegadores modernos ahora están acelerando los tres, pero ese lienzo ha recibido la mayor atención hasta el momento. Por otro lado, la forma en que escribes tu javascript es fundamental para obtener el máximo rendimiento con el lienzo, por lo que todavía recomiendo usar SVG.


Sólo mis 2 centavos con respecto a la opción de divs.

Famous / Infamous y SamsaraJS (y posiblemente otros) usan divs no anidados absolutamente posicionados (con contenido HTML / CSS no trivial), combinados con matrix2d / matrix3d ​​para posicionamiento y transformaciones 2D / 3D, y logran un 60FPS estable en hardware móvil moderado , por lo que yo argumentaría que divs es una opción lenta.

Hay un montón de grabaciones de pantalla en Youtube y en otros lugares, de cosas 2D / 3D de alto rendimiento que se ejecutan en el navegador con todo como elemento DOM en el que se puede inspeccionar el elemento , a 60FPS (mezclado con WebGL para ciertos efectos, pero no para el parte principal de la prestación).


Si bien todavía hay algo de verdad en la mayoría de las respuestas anteriores, creo que merecen una actualización:

A lo largo de los años, el rendimiento de SVG ha mejorado mucho y ahora hay transiciones y animaciones CSS aceleradas por hardware para SVG que no dependen en absoluto del rendimiento de JavaScript. Por supuesto, el rendimiento de JavaScript también ha mejorado y, con él, el rendimiento de Canvas, pero no tanto como SVG ha mejorado. También hay un "chico nuevo" en el bloque que está disponible en casi todos los navegadores hoy en día y es WebGL . Para usar las mismas palabras que Simon usó anteriormente: supera a Canvas y SVG sin esfuerzo. Sin embargo, esto no significa que deba ser la tecnología de referencia, ya que es una bestia con la que trabajar y es solo más rápido en casos de uso muy específicos.

En mi humilde opinión para la mayoría de los casos de uso hoy en día, SVG ofrece la mejor relación rendimiento / facilidad de uso. Las visualizaciones deben ser realmente complejas (con respecto al número de elementos) y realmente simples al mismo tiempo (por elemento) para que Canvas y aún más para que WebGL brille realmente.

En esta respuesta a una pregunta similar , ofrezco más detalles, por qué creo que la combinación de las tres tecnologías a veces es la mejor opción que tiene.