0% encontró este documento útil (0 votos)
5 vistas

Html5 tutorial

HTML5 es un lenguaje de marcas que mejora el desarrollo de páginas web con nuevas capacidades en multimedia, rendimiento y semántica. Introduce elementos semánticos como article, section y nav, y mejora formularios y multimedia con nuevos tipos de input y elementos como audio y video. Además, HTML5 permite la creación de aplicaciones SPA, gestión de dispositivos y almacenamiento offline, y establece un único tipo de documento para simplificar su uso.
Derechos de autor
© © All Rights Reserved
Nos tomamos en serio los derechos de los contenidos. Si sospechas que se trata de tu contenido, reclámalo aquí.
Formatos disponibles
Descarga como PDF, TXT o lee en línea desde Scribd
0% encontró este documento útil (0 votos)
5 vistas

Html5 tutorial

HTML5 es un lenguaje de marcas que mejora el desarrollo de páginas web con nuevas capacidades en multimedia, rendimiento y semántica. Introduce elementos semánticos como article, section y nav, y mejora formularios y multimedia con nuevos tipos de input y elementos como audio y video. Además, HTML5 permite la creación de aplicaciones SPA, gestión de dispositivos y almacenamiento offline, y establece un único tipo de documento para simplificar su uso.
Derechos de autor
© © All Rights Reserved
Nos tomamos en serio los derechos de los contenidos. Si sospechas que se trata de tu contenido, reclámalo aquí.
Formatos disponibles
Descarga como PDF, TXT o lee en línea desde Scribd
Está en la página 1/ 84

Introducción HTML5

¿Qué es HTML5?
En esta introducción HTML5 vemos que HTML5 es un lenguaje de marcas que nos permite el
desarrollo de páginas web, al cual se le han añadido un conjunto de capacidades que nos
permiten explotar las capacidades de los dispositivos en temas de multimedia, rendimiento,
offline, interacción con el usuario,…

De esta manera HTML5 se compone de un núcleo de elementos del lenguaje y una serie de
APIs que nos permiten gestionar las nuevas capacidades.

Las mejoras en HTML5 respecto a las versiones previas de HTML van enfocadas a:

Semántica de los Documentos


Se incorporan nuevos elementos que nos permiten dotar de mayor semántica a los documentos.
Sobre todo a la hora de estructurar la información o los contenidos. Pasamos de un modelo
gobernado por las capas span y los bloques div donde la semántica se establecía con los
elementos CSS, a tener elementos específicos con su semántica.

Así, en HTML5 encontramos elementos como article, section, aside, header, footer,…

Mejora de formularios
Se han revisado los formularios proporcionando nuevos tipos de input así como incluyendo
nuevos elementos para los formularios como datalist para la gestión de listas, progress y
meter para las barras de progreso u output para las salidas de datos.
Además se proporciona una valiosísimo API de validación de formularios así como validaciones
explícitas en los propios campos.

Multimedia
Se incorporan nuevos elementos audio y video para poder gestionar de forma estándar los
codecs y formatos multimedia para poder incluir contenido multimedia en los documentos. Los
elementos audio y video incorporan unos potentes API para poder interactuar con sus
funcionalidades.

Gráficos y Efectos 2D/3D


Las limitaciones gráficas de HTML 4.01 eran muy grandes y no podíamos tener elementos
gráficos. En HTML5 se incluye el elemento canvas que nos permite crear gráficos 2D y 3D con
una gran interacción, llegando a la posibilidad de poder montar juegos gráficos sobre ellos.

Además se ha incluido el soporte de SVG dentro de los propios documentos HTML5.

Offline y Almacenamiento
La red ha pasado de ser dominada por agentes de usuario que eran navegadores conectados
constantemente a la red y de forma online a tener una amplia presencia y uso de dispositivos
móviles, los cuales tienen menor capacidad de procesamiento, tasa de conexión y que además
pueden estar offline.

Es por ello que HTML5 nos ayuda en primer lugar a saber si el navegador está online u offline. Y
además nos incluye una serie de capacidades de almacenamiento en la parte cliente como son
la WebStorage, la base de datos IndexedDB y la gestión de ficheros mediante el API File.

Rendimiento e Integración
HTML5 nos ofrece un conjunto de API que nos ayudan en la creación de aplicaciones SPA
(Single Page Application), para ello ha mejorado el objeto XMLHttpRequest generando el
Level 2.

Por otro ha creado los WebWorkers para que se puedan lanzar ejecuciones asíncronas desde
el navegador y así no afectar a la interacción directa con el usuario.

Otros apartados que se han trabajado para las aplicaciones SPA (Single Page Application) son
la integración del Historial API con las SPA, capacidades Fullscreen y la posibilidad de
controlar el drag&drop de elementos.

Conectividad
Las aplicaciones de cliente han pasado a un modelo de aplicaciones SPA (Single Page
Application) de una gran riqueza visual, pero las cuales recuperar los datos de servicios de
negocio externos.

Así, con HTML5, han surgido tecnologías como Websockets para establecer conexiones
permanentes con los servicios de negocio, Server-sent Events para poder publicar eventos
desde el servidor al cliente o WebRTC para poder crear webs que nos permitan una experiencia
real-time.

Gestión de Dispositivos
Como ya hemos comentado hemos pasado de ordenadores y su navegador a visualizar los
documentos web en dispositivos móviles que ofrecen muchas posibilidades y una manera
diferente de interacción por parte del usuario.

De esta manera con HTML5 podremos conocer la geolocalización del dispositivo, gestionar si
el dispositivo está en horizontal o vertical o accede a sus capacidades y conocer el estado
de la batería o poder utilizar la cámara.

Historia y Futuro de HTML 5


El 28 de octubre de 2014 se convertía en estándar la versión HTML5 dentro de la W3C. Ya
habían pasado unos años desde que el WHATWG (Web Hypertext Application Technology
Working Group) empezase a trabajar en la definición del estándar HTML5 liderados por Ian
Hickson.

El estándar HTML5 establece en su base dos puntos. El primero es que la especificación del
lenguaje debe de ser compatible con todo lo creado hasta el momento con HTML 4.01 y por otro
que hay que ir añadiendo de forma más dinámica nuevas funcionalidades a lenguaje que se
aprovechen de todos los avances tecnológicos.

Después de llegar a la publicación de HTML5 parecía que el trabajo de la W3C y el WHATWG


habían vuelto a confluir y teníamos un estándar con un futuro prometedor.

Si bien, desde el 2012, el trabajo realizado por la W3C y WHATWG se ha vuelto a separar en
dos vías.

Por un lado la W3C sigue trabajando en un modelo de versiones con una cadencia larga en el
tiempo, actualmente la versión HTML 5.2 es la recomendación estándar desde el
14/diciembre/2017 y está trabajando en HTML 5.3 que a 18/octubre/2018 está en “Working
Draft”.

Por otro la WHATWG trabaja en un modelo de estándar que está continuamente vivo y que se
conoce como HTML Living Standard.

Y ya existen algunas discrepancias en elementos y la compatibilidad que se deben de manejar.

Esperemos que en un futuro las aguas vuelvan a su cauce y tengamos de nuevo un estándar
único y ágil en la publicación de nuevas versiones.
Documento HTML5
Cuando hablamos del documento HTML5 lo primero que tenemos que saber que aunque hasta
HTML 4.01 habíamos tenido diferentes tipos de documentos, los cuales diferenciábamos por el
doctype del documento, en HTML5 solo se tiene un único tipo de documento el cual estará
determinado por la cabecera:

<!DOCTYPE html>

De esta manera el documento le está diciendo al navegador que es un documento de tipo


HTML5.

La siguiente cosa que haremos en un documento HTML5 será declarar el juego de caracteres
que utilizará. Para ello deberemos de utilizar un elemento meta mediante su atributo charset.

Así, para indicar que el juego de caracteres de un documento es utf-8 escribiremos lo siguiente
dentro del elemento head:

<head>
<meta charset="UTF-8">
</head>

HTML5 recomienda el uso del juego de caracteres estándar utf-8 y abandonar el uso de juegos
locales de caracteres utilizados en otras versiones como eran los ISO 8859-1.

El documento HTML5 base quedaría, uniendo todos los elementos que hemos explicado, de la
siguiente manera:

<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Titulo Documento</title>
</head>
<body>

<!-- Documento HTML5 -->

</body>
</html>

Ya puedes utilizar este documento HTML5 base para poder construir tus páginas web.
Semántica HTML5
La semántica HTML5 permite estructurar mucho mejor las páginas web definiendo las partes
que la componen de una forma mucho más entendible. Pero vamos a analizar primero como se
estructuraban las páginas en HTML 4 para entender el avance semántico que hemos tenido en
HTML5.

Análisis de la Semántica en HTML 4


Cuando se trabajaba con HTML 4 la estructura de un documento se conseguía mediante capas
div y elementos de cabecera h1 a h6. Dependiendo de la anidación que utilizásemos con las
cabeceras y capas, así se estructuraba nuestro documento.

Los elementos div se utilizaban para determinar las secciones y sub-secciones.

<div class="seccion">
<h1>Titulo Principal</h1>
Artículo principal del texto.
<div class="subseccion">
<h2>Subtítulo</h2>
Texto relacionado con el primer subtítulo del artículo.
</div>
</div>

Esto generaba una serie de problemas en HTML 4. El primero es que la semántica del
documento no depende de los elementos del documento HTML 4 sino del correcto uso de los
estilos CSS. Y hay que recordar que el uso de CSS solo debería de ser para dar estilo al
documento.

Otro problema era si queríamos unir varios documentos, es decir, componer un documento en
base a diferentes documentos HTML 4, ya que lo que estamos buscando es unir capas div
sobre otras capas div, además cada una podría tener títulos de cabecera de lo más variopintos
dando como resultado un documento con una estructura incorrecta.

La interpretación de los documentos en HTML 4 era totalmente lineal, y nos encontrábamos que
dentro de una sección podían aparecer partes no relativas a dicho contenido, normalmente
elementos como publicidad o información anexa.

EL último inconveniente es que aparecen otros elementos dentro del documento HTML 4 que no
son puro contenido, a lo cual también debemos de dar una estructura. Por ejemplo, áreas de
navegación, cabeceras, pies de página,…

Nuevo modelo semántico en HTML5


Para resolver los problemas derivados de la semántica en HTML 4 se crean un conjunto de
nuevos elementos en HTML 5: article, section, nav, aside, header y footer. Dando
nacimiento a la semántica HTML5.
Article
El elemento article nos permite definir una pieza independiente y auto-contenida dentro de
un documento HTML 5.

De esta manera podremos reutilizar los elementos article de múltiples formas.

Los elementos article suelen contener el contenido de un post, la entrada de un foro, un


artículo de un periódico,…

Section
Section es un elemento que representa una sección independiente dentro de un documento
HTML 5, la cual no puede ser representada por otro elemento semántico más específico como
podrían ser: nav, article, aside,…

Las secciones suelen tener incorporadas un elemento h1 a h6 que le sirve para indicar el título
de la sección.

Nav
El elemento nav o elemento de navegación define una sección que contiene enlaces de
navegación. Pueden existir tantos elementos nav como queramos dentro de un documento
HTML 5. Así es normal que encontremos un elemento nav para la navegación principal del sitio
web y otro que contenga una tabla de contenido del documento que estemos visualizando.

Los elementos nav no forman parte de la estructura general del documento, por lo cual no afecta
el sitio del documento donde vayan situados.

Aside
Aside o elemento de contenido asociado es un elemento que nos permite gestionar contenido
de forma independiente al contenido principal. El contenido dentro del elemento aside puede
estar relacionado o no con el contenido principal, pero nunca afectará a la estructura de la
sección que lo contiene. Se puede decir que es una relación indirecta.

El elemento aside suele utilizarse para contenido explicativo o bien para barras laterales.

Header
El elemento de cabecera header se utiliza normalmente para definir la cabecera de la página.
En la cabecera de la página solemos encontrar el título y logo de la página, un menú de
enlaces,….

El elemento header no es propietario del documento y es por ello que podemos definir
cabeceras mediante un elemento header dentro de los elementos article, section,aside y
nav.

No se creará ninguna sección cuando utilicemos el elemento header.


Footer
El elemento footer sirve para definir el pie de página de un documento. En los pie de página de
los documentos se suele incluir el copyright u otros elementos legales.

También podemos definir un pie de página dentro de los elementos article, section,aside y
nav.

No se creará ninguna sección cuando utilicemos el elemento footer.

Definir secciones en HTML 5


La primera sección dentro de un documento HTML 5 es el propio elemento body. Todo el
contenido dentro del elemento body es una sección.

Dentro del elemento body podremos encontrar otros elementos que definan secciones por si
mismo, las cuales se vayan anidando. Para ello encontramos elementos como article,
section,aside y nav.

Cada sección dentro de HTML 5 tiene su propia jerarquía de títulos de


cabecera. Es por ello que el primer título de cabecera de cada sección podrá
ser un h1.

<section>
<h1>Titulo principal</h1>
<section>
<h1>Subtítulo 1</h1>
<p>Contenido se la primera sección.</p>
</section>
<section>
<h1>Subtítulo 2</h1>
<p>Contenido se la segunda sección.</p>
</section>
<section>
<h1>Subtítulo 3</h1>
<p>Contenido se la tercera sección.</p>
</section>
<aside>
<p>Publicidad</p>
</aside>
</section>
<footer>
<p>Pie de Página de la web</p>
</footer>

La salida del documento HTML 5 será:


1. Título Principal
1. Subtítulo 1
2. Subtítulo 2
3. Subtítulo 3

El Validador de la W3C nos permite de una forma sencilla analizar el outline


de un documento HTML para ver la salida que genera y las secciones de las
que se compone.

Semántica y títulos de cabecera


A la hora de utilizar los títulos de cabecera h1 a h6 dentro de HTML 5 deberemos de saber que
el primer elemento que utilicemos en la sección será el que marque la cabecera de la sección,
independientemente del nivel de título de cabecera que tengamos.

Es decir, podemos tener una sección que empiece por h1 y otra que empiece igualmente por h1
o por h3 u otro nivel.

Así podríamos encontrarnos con el siguiente código semántico en HTML 5 :

<section>
<h1>Artículo principal</h1>
<p>Texto del artículo principal.</p>
<section>
<h2>Subsección</h2>
<p>Contenido secundario del artículo principal</p>
</section>
</section>
<section>
<h4>Artículo Secundario</h4>
<p>Contenido del artículo secundario.</p>
</section>

La salida del documento HTML 5 será:

1. Artículo Principal
1. Subsección
2. Artículo Secundario

Si bien es verdad que aunque esto esté permitido en HTML 5 es recomendable que cada una de
las secciones se empiece utilizando el título de cabecera h1.

Secciones Implícitas
Para mantener compatibilidad con el procesamiento de documentos HTML 4, dentro de HTML 5
existen las secciones implícitas.

Y es que el uso de los elementos de títulos de cabecera dentro de una sección generarán una
subsección, aunque no hayamos utilizado otro elemento para definir una nueva sección.

Es decir, que en el siguiente código HTML 5 tendremos dos secciones, aunque solo hayamos
utilizado un elemento section.

<section>
<h1>Artículo principal</h1>
<p>Texto del artículo principal.</p>
<h2>Subsección</h2>
<p>Contenido secundario del artículo principal</p>
</section>

El uso del elemento h2 acabará generando una subsección de forma implícita. Por lo tanto la
salida del documento será:

1. Artículo principal
1. Subsección

En el caso de que el elemento a utilizar sea del mismo nivel que el de la sección actual, lo que
hará será crear una nueva sección.

De esta manera vemos que dentro del elemento section hay el uso de dos elementos h1. El
segundo hará que se genere una nueva sección.

<section>
<h1>Título 1</h1>
<p>Texto del artículo.</p>
<h1>Título 2</h1>
<p>Texto del artículo.</p>
</section>

La salida del documento será:

1. Título 1
2. Título 2

Elementos con su propia estructura


Hay un conjunto de elementos dentro de HTML 5 los cuales tienen su propia estructura y que no
afectan a la estructura de la sección que los alberga. Estos son: blockquote, details,
fieldset, figure y td.

Así podríamos encontrarnos una referencia utilizando un elemento blockquote dentro de una
sección.

<section>
<h1>Artículo principal</h1>
<p>Texto del artículo principal.</p>
<blockquote>
<h1>Título a Remarcar</h1>
<p>Contenido a remarcar.</p>
</blockquote>
<section>
<h2>Subsección</h2>
<p>Contenido secundario del artículo principal</p>
</section>
</section>

Dicho elemento blockquote no afecta para nada a la estructura, la cual seguirá siendo:

1. Artículo Principal
1. Subsección

Address: Autor de un artículo


El elemento address ya existía desde HTML 4. Este elemento nos sirve para incluir información
de contacto. Si bien en HTML 5 se ha extendido su uso para poder establecer el contacto de las
diferentes secciones del documento.

Como un documento puede contener secciones de diferentes autores podremos definir tantos
elementos address como necesitemos.

Para definir secciones de diferentes autores deberemos de utilizar el elemento article y el


contacto asociado mediante el elemento address será aquel que esté más cercano al elemento
article.

Formularios HTML5
Si hay un punto sobre el que se ha incrementado más su funcionalidad de HTML 4.01 a HTML5
ese es los formularios. Y es que se ha mantenido la misma filosofía de desarrollo, pero se ha
dotado de nuevas funcionalidades a los formularios pasando a tener unos formularios con
muchas más posibilidades

Elementos Input
El elemento principal de un formulario es el elemento de entrada de datos o input. Es por ello
que dicho elemento en HTML5 ha incluido varias novedades.

Por un lado el elemento input ha incluido nuevos atributos: placeholder, autocomplete y


autofocus que permiten de forma sencilla el ponerle información contextual, hacerle un foco y
autocompletar su contendio.

Por otro se han añadido más tipos de campos de entrada como son: search, email, url, tel,
range, number, datetime-local, week, month, time y color. Lo cual nos proporciona más
capacidades para obtener datos y sobre todo obtener datos de calidad, ya que ciertas de estas
especializaciones llevan asociadas validaciones que nos aseguran que el dato es correcto. Por
ejemplo, los campos de tipo email validan que el contenido corresponda con un email.

Puedes leer en detalle más información sobre las novedades de los elementos Input en HTML5

Elemento DataList
Hasta ahora cuando manejábamos una lista de elementos en HTML nos teníamos que ajustar al
uso del elemento select, mediante el cual podíamos ofrecer al usuario una lista de selección
simple o múltiple.

En HTML5 aparece el elemento datalist. La idea del elemento datalist es la de poder


crear una lista de elementos de forma independiente a los campos de entrada, de la misma
forma que se creaban los elementos select para, de forma separada, asociarla a un elemento
inputde formulario que lo necesite.

Esto nos ofrece muchas posibilidades pensando en que estos datos, en ciertas ocasiones, se
podrían cargar de forma ásincrona y así pueden modificarse dependiendo de la situación.

Lee más sobre el uso del elemento DataList

Barras de Progreso
Otro nuevo elemento, o mejor dicho, nuevos elementos, son las barras de progreso. Y es que en
este caso tenemos dos tipos de barras de progreso: progress y meter.

En el caso de la barra de progreso progress encontramos un elemento sencillo dónde con


un valor y un máximo se puede renderizar una barra de progreso.

El elemento meter nos ofrece más posibilidades ya que nos permite definir una barra de
progreso en tramos y además indicarle cual es el valor óptimo de la barra de progreso
para que el navegador sepa como renderizarla y asociarla un color: verde, rojo o amarillo.

Aprende a trabajar con las barras de progreso.


Elemento Output
Si ya teníamos el elemento input para las entradas de datos, los formularios HTML5 han
incluido el elemento ouput para la salidas de datos o cálculos. Es decir, si tenemos cálculos
internos dentro del formulario, los cuales haya que enviar o no, se podrán mostrar sobre un
elemento output.

Puedes leer más sobre lo sencillo que es utilizar el elemento output.

Validaciones
Posiblemente la mayor mejora que hayan sufrido los formularios HTML5 es que ahora incluyen
validaciones de forma implícita, además de un API de Validación de Formularios con el que,
mediante el uso de Javascript, podemos realizar nuestras propias validaciones personalizadas.

En el caso de las validaciones implícitas, estas van en los nuevos tipos de elementos input, así
se validará que los emails y urls tienen un formato correcto o que cuando insertamos un número
este realmente es un número.

Otros controles que se añaden son el control de los campos obligatorios o los límites sobre
mínimo y máximo de los valores que se aceptan.

El caso más potente es el uso de patrones, ya que nos permitirá de forma implícita realizar una
validación de un campo asociado a un patrón definido en Javascript y con lo que podemos
realizar casi cualquier tipo de validación.

Y si con todo esto no es suficiente, el API de Validación de Formlarios nos permite comprobar
si hay validaciones correctas y personalizar mensajes.

No esperes más y aprende a realizar validaciones de formularios con HTML5.

Elementos Input
Nuevos Atributos
En HTML5 aparecen un conjunto de atributos nuevos para los elementos input que nos
permiten manipular mejor los formularios. Estos son: placeholder, autocomplete y autofocus

Placeholder
Hasta HTML5 la forma que existía de dar información contextual sobre el contenido que había
que insertar en un campo de formulario era mediante el elemento label.

En HTML5 aparece el atributo placeholder, el cual permite poner información sobre lo que hay
que insertar dentro del elemento input dentro del mismo elemento.

<input type="text" name="nombre" id="nombre" placeholder="Nombre"/>

Como podemos ver el texto del placeholder queda difuminado dentro del elemento input.

Autocomplete
Mediante el atributo autocomplete permitiremos al agente de usuario (navegador) que pueda
apoyarse en información introducida en otros formularios en el pasado para intentar completar el
contenido de un campo ofreciendo alternativas de texto.

Algunos navegadores permiten tener datos preconfigurados para poder autocompletar el


contenido del formulario.

<input type="text" name="nombre" id="nombre" autocomplete="name">


<input type="text" name="url" id="url" autocomplete="off">
<input type="text" name="direccion" id="direccion"
autocomplete="street-address">

Los valores que pueden tener pueden ser on y off. O bien valores que indiquen la semántica
del campo para que se pueda autocompletar, estos pueden ser: name, country, sex, street,
username, organization,… puedes consultar más valores para el atributo autocomplete

Autofocus
Hasta HTML5 el control del foco de los elementos input de un formulario debía de ser
ejecutado mediante código Javascript. Pero ahora ya contamos con un atributo que nos permite
indicar cual de los elementos input de un formulario empieza a tener el foco del mismo.

Solo uno de los elementos input puede tener el atributo autofocus.

Bastará con añadir el atributo autofocus sobre uno de los elementos input para que este
obtenga el foco cuando se cargue la página.

<input type="text" name="url" id="url" autofocus>

Nuevos tipos Input


Una de las cosas que nos encontramos en HTML5 son nuevos tipos de elemento de entrada de
datos en los formularios. Lo que viene a ser el atributo type del elemento input.

Hasta HTML 4.01 podíamos definir un elemento input como: text, radio, checkbox, password,
file, hidden y submit.

Recordamos que la estructura de un elemento input es:

<input type="tipo" id="identificador" size="tamaño" name="nombre"


value="texto por defecto"/>

Ahora contamos con nuevos tipos de elementos input como son: search, email, url, tel, range,
number, date y color.

Input Search
El tipo search de los elementos input nos sirven para definir campos de entrada para
búsquedas. Es decir, si añadimos un buscador dentro de nuestra web, el campo sobre el cual el
usuario podrá introducir el texto de la búsqueda será de tipo search.

<input type="search" id="busqueda" name="q"/>

Vemos que simplemente hemos especificado el valor search dentro del atributo type del
elemento input. Al contrario que lo que sucede en otros tipos de elementos input en el caso
de las búsquedas no hay una visualización específica dentro de los diferentes navegadores.

Input Email
Uno de los datos de contacto más solicitados en Internet es, obviamente, el email. Hasta la
versión de HTML5 cuando estamos creando un formulario y queremos que un campo fuese de
tipo email lo que hacíamos era declararlo de tipo texto y crearnos unos códigos javascript de
validación de emails.

Con la aparición del tipo email, deberemos de marcar el elemento input como un elemento del
tipo email.

<input type="email" id="email" name="email"/>

A partir de este momento el navegador será el que realice las comprobaciones de que el
dato introducido sea un email. Bien es cierto que, de momento, las validaciones de los
navegadores son mínimas y no van más allá del formato del email en cuanto a tener una @ o
que después del punto exista un dominio, sea el que fuese.

Visualmente, en Google Chrome tenemos el siguiente efecto visual en la validación de un email:

De igual manera las opciones que nos ofrece del texto a rellenar serán emails y no cualquier
otro tipo de texto. Al menos textos que cuadren con la expresión regular del email.

Input URL
El comportamiento del tipo url es parecido al del tipo email. La única diferencia es que en este
caso se valida que el contenido insertado coincida con una URL. Es decir, tenga su
protocolo especificado (http://), el servidor, el dominio,… con lo cual evitaremos el tener que
utilizar, como sucedía anteriormente, validadores de URL.

<input type="url" id="website" name="website">

Si utilizamos un tipo url dentro de un elemento input y no insertamos un texto con forma de
URL, el navegador nos mostrará lo siguiente:

Input Tel
El tipo tel nos servirá para indicar que el campo es un número de teléfono. Dada la gran
cantidad de formatos de números de telfóno que hay en el mundo, no se realizará ninguna
validación de formato sobre el campo.

Si bien, la semántica que damos indicando que irá un número te teléfono hace que los campos
de tipo tel para algunos dispositivos móviles muestre un teclado numérico.

Podremos insertar un campo que gestione un número de teléfono mediante el tipo tel de la
siguiente forma:

<input type="tel" id="telefono" name="telefono">

Input Number
Los elementos input de tipo number nos van a valer para poder introducir números. Para crear
un elemento input de tipo number simplemente tendremos que crear la siguiente estructura:

<input type="number" id="numero" name="numero">

A este tipo de elementos le podemos especificar un par de atributos más. Por un lado podemos
fijar cual es el número mínimo y máximo que se puede insertar. Esto lo haremos mediante los
atributos min y max.

<input type="number" id="numero" name="numero" min="valor_minimo"


max="valor_maximo">

Por otro podemos indicar el valor de incremento o decremento de los números. Es decir, si
queremos que solo se incremente de dos en dos, o de tres en tres,… Esto lo conseguimos
mediante el atributo step.

<input type="number" id="numero" name="numero" step="incremento">

De esta manera podríamos tener el siguiente código fuente:

<form action="#" method="get">


<label for="anio">¿Cuál es tu año par favorito del siglo XXI?</label>
<input type="number" id="anio" name="anio" min="2000" max="2018"
step="2"/>
<input type="submit" value="Buscar"/>
</form>
Vemos que el valor mínimo es 2000 y el máximo 2018 y que solo podemos incrementar o
decrementar de 2 en 2, ya que preguntamos por años pares.

Los campos input de tipo number nos forzarán a que el valor introducido sea un número y
además que esté dentro del rango marcado por los atributos min y max.

Input Range
Otra forma de elegir un valor numérico es mediante un slider. Para poder poner estas barras de
selección tenemos el tipos range dentro de los elementos input.

<input type="range" id="numero" name="numero">

Los elementos input de tipo range aceptan los mismos parámetros que los elementos number.
Así que podremos añadir los atributos min, max y step.

<input type="range" id="numero" name="numero" min="valor_minimo"


max="valor_maximo" step="incremento">

De esta manera el mismo ejemplo anterior relativo a los años, pero con un slider quedaría de la
siguiente forma:

<form action="#" method="get">


<label for="anio">¿Cuál es tu año par favorito del siglo
XXI?</label><br/>
<input type="range" id="anio" name="anio" min="2000" max="2018"
step="2"/>
<input type="submit" value="Enviar"/>
</form>

Como se puede ver es idéntico.


Uno de los problemas que nos econtramos con los sliders es que no tienen una representación
visual del valor que estamos marcando. Es por ello que deberemos de utilizar algún código en
Javascript para poder mostrarlo.

Así el mismo ejemplo, pero visualizand el año quedaría de la siguiente forma:

<form action="#" method="get">


<label for="anio">¿Cuál es tu año par favorito del siglo
XXI?</label><br/>
<input type="range" id="anio" name="anio" min="2000" max="2018"
step="2"/>
<span id="salida"></span><br/>
<input type="submit" value="Enviar"/>
</form>

Y tendríamos que añadir el siguiente código Javascript:

var anio = document.getElementById("anio");


var salida = document.getElementById("salida");

salida.textContent = anio.value;

anio.oninput = function() {
salida.textContent = anio.value;
}

Este código Javascript simplemente vuelca el valor del elemento input sobre un elemento
span.

Input Datetime
Otra de las opciones que han incoporado los elementos de texto input en los formularios
HTML5 es el manejo de fechas. Para ello contamos con 4 tipos de elementos input, que son:
datetime-local, month, time y week.

Input Datetime-local
Este tipo de elemento nos permite escoger una fecha y hora, sin especificar la zona horaria en la
que se encuentra. El valor del tipo input será datetime-local.

<input type="datetime-local" id="fechahora" name="fechahora"/>

La representación visual de un tipo datetime-local será:


Input Month
En este caso se creará un selector de meses del año. El valor del tipo input para los meses en
month.

<input type="month" id="mes" name="mes"/>

La representción visual para los campos de texto de tipo mes es:

Input Time
Para poder indicar una hora en formato horas y minutos (hh:mm) disponemos del tipo time para
los elementos de texto de un formualario. La estructura para un elemento input de tipo time
es:

<input type="time" id="hora" name="hora"/>


Y su representación visual:

Podemos comprobar que se le da el formato *hh:mm** dentro de la caja de texto.

Input Week
El último elemento para el manejo de fechas es el tipo week. En este caso el elemento week nos
permite seleccionar una semana dentro del año.

<input type="week" id="semana" name="semana"/>

Vemos que la representación visual cambia y nos muestra las semanas del año dentro del
calendario.

Input Color
Si lo que queremos es que un usuario nos indique un color de una paleta de colores utilizaremos
el elemento input con un tipo color.

<input type="color" name="colorfavorito" value="#ff0000">

Mediante el atributo value podemos indicar en formato RGB un color que será el que muestre la
paleta por defecto.

De esta manera, en el navegador, podremos ver algo parecido a lo siguiente:


Input File
En HTML 4.01 ya existía un campo de texto input en que podíamos subir ficheros. Este era el
tipo file. En HTML5 sigue existiendo dicho campo, si bien se ha añadido una serie de atributos
adicionales para su manejo.

La estructura de un tipo file es la siguiente:

<input id="ficheros" type="file" name="file" id="file"><br/>

Uno de los atributos específicos del tipo file que ya existía era el filtrado de tipos de ficheros a
aceptar. Esto lo indicamos con el atributo accept el cual recibirá una extensión de fichero o un
mime-type de los ficheros que aceptamos subir separados por comas.

Si queremos hacerlo por extesiones:

<input id="ficheros" type="file" name="file" id="file"


accept=".jpg,.gif,.png"><br/>

O por mimetypes:

<input id="ficheros" type="file" name="file" id="file"


accept="image/*,audio/*"><br/>
En el caso de que queramos subir más de un fichero deberemos de recurrir al atributo
multiple.

<input id="ficheros" type="file" name="file" id="file" accept="image/*"


multiple><br/>

Por último nos encontramos con el atributo capture el cual nos sirve para indicar que el origen
del fichero podrá ser la cámara o micrófono del dispositivo. Los valores del atributo capture
pueden ser user para la cámara frontal o enviroment para la cámara trasea.

<input id="ficheros" type="file" name="file" id="file" accept="image/*"


capture="user"><br/>

DataList
Una de las mejoras que aparece en los formularios HTML5 es la posibilidad de incluir opciones
de selección mediante un nuevo elemento denominado datalist.

La idea es que mediante el elemento datalist podamos definir una lista de valores. Esta
lista de valores será posteriormente asociada a otro elemento del formulario mediant el atributo
list.

La estructura del elemento datalist es la siguiente:

<datalist id="miLista">
<option>Opción 1</option>
<option>Opción 2</option>
<option>Opción 3</option>
<option>Opción 4</option>
...
<option>Opción N</option>
</datalist>

Vemos que cana uno de los datos de la lista se define mediante un elemento de tipo option.

La lista la asociaremos a los elementos de tipo input con el valor dado en el id sobre el
atributo list.

<input type="text" name="lista" id="lista" list="miLista">


Al asociar un DataList a un elemento de tipo input conseguiremos el efecto
de autocompletado. Es decir, el navegador irá dando opciones de
completado al usuario atendiendo a los elementos que haya en el DataList.

De esta manera podríamos definir una lista de ciudades:

<datalist id="ciudades">
<option>Ávila</option>
<option>Burgos</option>
<option>León</option>
<option>Palencia</option>
<option>Salamanca</option>
<option>Segovia</option>
<option>Soria</option>
<option>Valladolid</option>
<option>Zamora</option>
</datalist>

Y posteriomente asociadala a un campo de texto:

<input type="text" name="castillaleon" id="castillaleon" list="ciudades">

DataList con texto y valor


Ya hemos visto el uso básico de un DataList ahora vamos a ver cómo podemos hacer algo más
avanzado. En este caso vamos a vr cómo podemos crear una lista de elementos dónde haya
dos partes, por un lado el texto que inserta o elige el usuario y por otro el valor que tiene dicho
elemento.

Para poder hacer esto, dentro de los elementos option deberemos de utilizar los atrobutos
value para poder dar el valor y label para darle la etiqueta de texto que se mostrará.

<datalist id="miLista">
<option label="Texto 1" value="Valor 1"></option>
<option label="Texto 2" value="Valor 2"></option>
<option label="Texto 3" value="Valor 3"></option>
...
<option label="Texto N" value="Valor N"></option>
</datalist>
Podemos utilizar los campos de texto y valor de un DataList de la siguiente forma:

<datalist id="listaurls">
<option value="http://lineadecodigo.com" label="Línea de Código">
<option value="http://www.manualweb.net" label="Manual Web">
<option value="http://www.dudasprogramacion.com" label="Dudas de
Programación">
<option value="http://www.w3api.com" label="W3Api">
</datalist>
<input type="url" id="misurl" list="listaurls" />

Compatibilidad del elemento DataList


El elemento datalist es relativamente nuevo y puede darse el caso de que nos encontremos
con un navegador -sobre todo los antiguos- que no soporte dicho elemento. En este caso
podemos apoyarnos en el elemento select que ya da de por sí una lista de opciones.

Así podemos combinar el uso de los elemento datalist y select de la siguiente forma:

<datalist id="miLista">
<label for="elemento">Selecciona un elemento de la lista:</label>
<select id="elementos" name="elementos">
<option>Opción 1</option>
<option>Opción 2</option>
<option>Opción 3</option>
<option>Opción 4</option>
...
<option>Opción N</option>
</select>
</datalist>

Los navegadores que den soporte al elemento datalist directamente ignorarán el elemento
select y no lo pintarán.

Siguiendo esta estructura podríamos tener el siguiente código de compatibilidad:

<label for="misurl">Dinos tu URL:</label>


<input type="url" id="misurl" list="listaurls" />
<datalist id="listaurls">
<label for="elemento">O eligela de la siguiente lista:</label>
<select id="elementos" name="elementos">
<option value="http://lineadecodigo.com" label="Línea de Código">
<option value="http://www.manualweb.net" label="Manual Web">
<option value="http://www.dudasprogramacion.com" label="Dudas de
Programación">
<option value="http://www.w3api.com" label="W3Api">
</select>
</datalist>
Barras de Progreso
En los formularios de HTMl5 encontramos un par de elementos que nos permiten definir una
barra de progreso. Las barras de progreso nos permiten notificar al usuario el grado de avance
que existe en alguna acción determinada.

Los dos elementos que tenemos en HTMl5 para poder construir una barra de progreso son:
progress y meter.

Progress
El elemento progress nos permite especificar el grado de avance atendiendo a un valor mínimo
y un valor máximo. Para ello cuenta con el atributo max que indicar el valor máximo de progreso
y el atributo value que indica el valor actual del progreso.

<progress max="valor_maximo" value="valor_actual"></progress>

El contenido del elemento progress nos sirve para trabajar la compatibilidad, ya que si el
navegador no sabe pintar un elemento progress, pintará lo que haya dentro de él y a la inversa,
si el navegador sabe pintar el elemento progress, solo pintará dicho elemento.

Podemos crear una barra de progreso con un avance del 25% de la siguiente forma

<progress max="100" value="25">25/100</progress>

Meter
En el caso del elemento meter podremos crear barras de progreso delimitadas por un valor
mínimo y un valor máximo, para ello utilizaremos los valores min y max respectivamente.

<meter min="valor_minimo" max="valor_maximo"></meter>

Además las barra de progreso meter establece otros dos valores de referencia dentro de la
barra. Estos son el valor de inferior y superior, los cuales representa mediante los atributos low
y high.

<meter min="valor_minimo" max="valor_maximo" low="valor_inferior"


high="valor_superior"></meter>
Esto permite que podamos dividir a la barra en tres secciones:

● Inferior, la que va entre min y low.


● Intermedia, la que va entre low y high.
● Alta, la que va entre high y max.

Ahora un quinto valor entra en juego, es el valor que se denomina óptimo. Este valor se
identifica mediante el atributo optimum. Dependiendo del valor que demos al atributo optimum, y
en conjunto con las secciones de la barra, obtendremos una semántica u otra.

● Si el valor de optimum se encuentra en la sección inferior, consideraremos que las


sección inferior es la óptima, que la sección intermedia representa la media y que la
sección alta es la peor sección.
● Si el valor de optimum se encuentra en la sección intermedia se considerará la sección
intermedia como la óptima, mientras que las secciones inferior y alta serán consideradas
la media.
● Y si el valor de optimum se encuentra en la sección alta, se considerará la sección alta
como la óptima, se sección intermedia como la media y la sección inferior como la peor.

<meter min="valor_minimo" max="valor_maximo" low="valor_inferior"


high="valor_superior" optimum="valor_optimo"></meter>

El último atributo que tenemos es el que representa el valor de la barra. Este será el atributo
value.

Es importante saber que dependiendo del valor que tenga nuestro atributo value, combinado
con la sección de la barra en la que se encuentra y el tipo de valor óptimo obtendremos una
representación gráfica en un color u otro.

<meter min="valor_minimo" max="valor_maximo" low="valor_inferior"


high="valor_superior" optimum="valor_optimo" value="valor"></meter>

● Cuando el valor está en una sección óptima se representará en verde.


● Si el valor está en una sección media se representará en amarillo
● Y si el valor está en la sección mala se representará en rojo.
Aunque pueda parecer un poco lioso el uso de meter y sus colores, podríamos resumirlo que si
queremos que la barra sea en rojo, amarillo o verde, como un progreso de valor, lo único que
hay que hacer es que el valor óptimo esté entre los valores high y max.

Así, podremos pintar una barra con un valor de progreso 80/100 como avance óptimo de la
siguiente forma:

<meter min="0" max="100" value="80" low="25" high="75"


optimum="90">80/100</meter>

Elemento Output
Uno de los elementos nuevos que tenemos dentro de los formularios, a parte de los DataList y
las Barras de Progreso, es el elemento output.

El elemento output nos va a servir para mostrar resultados de cálculos dentro de un formulario.
Y es que muchas veces los formularios son utilizados para calcular subtotales o totales de
elementos y es, en estos casos, dónde el elemento output entra en acción.

La estructura del elemento output es la siguiente:

<output for="valores" form="id-formulario" name="nombre"></output>

Atributos Output
Como podemos observar su estructua es muy sencilla y cuenta con tres atributos principales:
for, form y name.

El atributo for nos va a servir para identificar el conjunto de elementos que contribuyen al
resultado mostrado en el elemento output. Estos identificadores deberán de aparecer
separados por espacios.

De esta forma, si tenemos dos campos de entrada e1 y e2 que contribuyen con el resultado,
indicaríamos su dependencia de la siguiente forma:

<input type="number" id="e1"/>

<input type="number" id="e2"/>

<output for="e1 e2"></output>

El atributo form nos sirve para identificar al formulario del cual depende el elemento output por
lo que su valor será el id de dicho formulario.
<form id="myform" action="#">

<input type="number" id="e1"/>

<input type="number" id="e2"/>

<output for="e1 e2" form="myform"></output>

</form>

El atributo form es importante ya que nos permite poner el elemento output en cualquier parte
del documento, si necesidad de estar dentro del formulario.

<form id="myform" action="#">

<input type="number" id="e1"/>

<input type="number" id="e2"/>

</form>

<h2>Resultado</h2>

<output for="e1 e2" form="myform"></output>

En el caso de que no indiquemos el valor del id del formulario del que depende, se le asignará
el id del formulario del que forme parte.

El último atributo es name, mediante este atributo simplemente estamos dando un nombre al
elemento para que pueda ser enviado desde el formulario como un dato más. Es exactamente el
mismo mecanismo que el atributo name de los elementos input.

<form id="myform" action="#">

<input type="number" id="e1"/>

<input type="number" id="e2"/>

<output for="e1 e2" form="myform" name="resultado"></output>

</form>
Calculos en Output
Aunque el nombre del elemento output pueda dar a entender que el cálculo de los elementos
que asociamos mediante el atributo for es automático, la realidad es que no es así.

Es decir, que si queremos realizar cálculos que se muestren en el elemento output deberemos
de recurrir al lenguaje Javascript.

No es que haya que ser un experto en el lenguaje Javascript. Por ejemplo podemos utilizar el
evento oninput del formulario para asociar el cálculo.

<form oninput="resultado.value=parseInt(a.value)+parseInt(b.value)">

<input type="range" name="b" value="50" /> +

<input type="number" name="a" value="10" /> =

<output name="resultado">60</output>

</form>

En este caso vemos como le hemos asociado la suma de dos elementos del formulario al
elemento ouput en el evento oninput. El valor de los campos del formulario input y output se
refleja en el atributo value.

resultado.value=parseInt(a.value)+parseInt(b.value)
Validación formularios
Cuando estamos introduciendo datos en un formulario puede suceder que el usuario inserte un
dato que no es correcto, ya sea por el formato del dato, por el valor del dato,… Es por ello que
deberemos de realizar validaciones a los formularios que creemos.

Algunas de las validaciones típicas que nos encontraremos serán: “No puedes dejar el campo
en blanco”, “La longitud debe de ser mayor de 8”, “El valor introducido no es un email”,…

Además las validaciones permiten que el valor del dato que se va a enviar al servidor ya tenga
cierta calidad, por lo que reducirá la posibilidad de fallo de validación en el servidor y por lo tanto
reduzca las llamadas que hagamos a nuestros servicios de datos (o negocio).

Recuerda que hacer validaciones en la parte del cliente no implica el dejar de


hacerlas en el lado del servidor.

Dentro de HTML5 encontramos dos formas de hacer validaciones de formulario:

● Validaciones propias del HTML5, son las que nos ofrece el propio lenguaje, son
validaciones básicas que no podremos personalizar, pero que nos serán de gran ayuda.
● Validaciones utilizando Javascript, nos permite utilizar la potencia del lenguaje
Javascript junto con un API de Validación para personalizar al máximo nuestras
validaciones de formularios.

Validaciones HTML5
Atributo Required
El primer atributo que nos vamos a encontrar dentro de un formulario es el atributo required.
Mediante el atributo required podremos indicar que el campo sobre el que se aplica es
obligatorio.

<input type="text" name="nombre" id="nombre" required/>

Si intentamos procesar el formulario y el campo que hemos marcado como required sigue
vacío, el navegador nos mostrará un mensaje de error.
Expresiones Regulares
Otra posibilidad es validar el contenido utilizando una expresión regular. Si queremos definir una
expresión regular deberemos de utilizar el atributo pattern. El atributo pattern recibirá una
expresión regular Javascript.

<input type="text" name="nombre" id="nombre" pattern="patron"/>

Algunas de estas exprexiones regulares son:

● a — Que aparezca la letra ‘a’.


● abc — Que aparezca la letra ‘a’, seguida de la ‘b’ y seguida de la ‘c’.
● a* — El carácter aparece 0 o muchas veces.
● a+ — El carácter aparece 1 o muchas veces.
● [^a] — Cualquier carácter que no sea una ‘a’
● a|b — El carácter es uno u otro.
● [a-z] — Cualquier carácter de la ‘a’ a la ‘z’.
● [0-9 — Cualquier número.
● a{5} — El carácter aparece 5 veces.
● a{5,8} — El carácter aparece de 5 a 8 veces.
● \w — Cualquier carácter alfanumérico (letras, números y subrayado).
● \d — Cualquier dígito.

Y lógicamente puedes combinarlas todas como quieras.

Así por ejemplo podríamos indicar que elija entre “Madrid” y “Barcelona”.

<input type="text" name="ciudad" id="ciudad" pattern="Madrid|Barcelona"/>

O que el usuario pueda meter las letras, números y subrayados que quiera, pero al menos uno,
de la siguiente forma:

<input type="text" name="texto" id="texto" pattern="[\w]+"/>

O que el número contenga 5 dígitos:

<input type="number" name="numero" id="numero" pattern="\d{5}"/>

Si quieres, puedes leer más sobre expresiones regulares en Javascript.

En el caso de que el valor introducido en el usuario no corresponda con el patrón, el navegador


nos mostrará un mensaje de error.
Podemos utilizar el atributo title para poder dar más información al usuario cuando se muestre
el error.

<input type="text" name="nombre" id="nombre" pattern="[\w]+" title="Letras,


números o subrayados"/>

Veremos que lo que se muestra por pantalla incluye la información adicional.

Limitar Tamaños
Si queremos limitar el tamaño de un campo input o de un textarea, ya sea limitándolo a tener
un número mínimo o un número máximo de caracteres, podemos recurrir a los atributos
minlength y maxlength.

<input type="text" id="nombre" minlength="numero" maxlength="numero"/>

Por ejemplo, imagina que quieres una contraseña que tenga, al menos, 8 caracteres:

<input type="password" name="pwd" id="pwd" minlength="8" required/>

Si no insertamos el número suficiente de caracteres, el navegador nos avisará del número de


caracteres que nos falta.
En el caso de que el campo sea de tipo number, los propios atributos min y max establecen este
tipo de validación.

Validaciones Javascript
Ya hemos visto como HTML5 nos permite de forma sencilla realizar validaciones de datos. Si
bien estas se nos pueden quedar cortas a la hora de realizar validaciones o de personalizar los
mensajes de error asociados al formulario.

Es por ello que HTML5 dispone de un API de Validación de Formularios el cual nos ofrece un
conjunto de propiedades y métodos para realizar nuestras validaciones personalizadas.

Propiedades:

● validationMessage
● validity
● willValidate

Métodos:

● checkValidity()
● HTMLFormElement.reportValidity()
● setCustomValidity(message)

Interface ValidityState
El interface ValiditySate describe el estado de validación de un elemento. De esta manera
sobre este estado podremos ver si hay un problema de rango .rangeOverflow o si el valor del
campo es demasiado largo .tooLong o si el tipo de dato introducido no es correcto
.typeMismatch o …

Dentro del API de Validación de Formularios es el objeto validity el que implementa dicho
interface. Este objeto está asociado a los campos de un formulario.

// Accedemos a un elemento input de tipo email

var email = document.getElementById("mail");

if (email.validity.typeMismatch) {

console.log("Hay un error en el formato introducido!!!")

}
validationMessage
Una vez que sabemos cómo acceder al objeto validity que contiene el estado de validación
de un campo de formulario. Pero si lo que queremos saber es qué mensaje va a mostrar el
navegador, deberemos de acceder a la propiedad validationMessage.

// Accedemos a un elemento input de tipo email

var email = document.getElementById("mail");

if (email.validity.typeMismatch) {

console.log(email.validationMessage); // Mensaje por defecto

willValidate
Si queremos saber si el elemento del formulario va a ser evaluado en el envío, lo que
deberemos de hacer es consultar la propiedad willValidate. La cual devolerá true si el
campo se validará en el envío o false si no se le va a hacer una validación.

checkValidity
El método checkValidity() nos permite comprobar si el elemento tiene problemas de
validación. Devuelve true en el caso de que el elemento no tenga problemas de validación y
false si el elemento tiene problemas de validación.

// Accedemos a un elemento input de tipo email

var email = document.getElementById("mail");

if (!email.checkValidity())

if (email.validity.typeMismatch) {

console.log("Hay un error en el formato introducido!!!")

}
reportValidity
En este caso el método reportValidity realiza una comprobación de la validación a nivel
del elemento de formulario. Es por eso que su sintaxis en
HTMLFormElement.reportValidity(). Es decir, comprueba si todos los elementos que hay en
un formulario pasan la validación de formato o hay campos con error.

var webform = document.getElementById("webform");

webform.onchange = function(event) {

if (webform.reportValidity()){

console.log("Todos los campos del formulario están validados


correctamente.");

} else {

console.log("Hay campos del formulario con problemas de validación.");

setCustomValidity
El último método que vemos es el más interesante, ya que mediante setCustomValidity
vamos a poder personalizar el mensaje de error que se le muestra al usuario cuando el
formulario contiene errores de validación.

El método setCustomValidity recibe como parámetro el mensaje que queremos


personalizar y es aplicado sobre el elemento que estamos validando y por lo tanto adaptamos
el mensaje a dicho tipo de elemento.

var email = document.getElementById("mail");

email.addEventListener("input", function (event) {

if (email.validity.typeMismatch) {

email.setCustomValidity("Cuidado, el campo es de tipo email!!!");

} else {

email.setCustomValidity("");

});
Aquí podemos ver que lanzamos el cambio de mensaje cada vez que se produce una
modificación sobre el campo input. Si bien podemos hacerlo en cualquier momento.

Deshabilitar Validaciones
Ya hemos visto cómo aprovecharnos al máximo de las validaciones automáticas de HTML5 y de
cómo podemos personalizarlas mediante el API de Validaciones de Formularios. Si bien
puede darse el caso de que no nos interese que estas validaciones se ejecuten. En este caso
podemos deshabilitar las validaciones del formulario mediante el atributo novalidate a nivel de
formulario.

<form action="#" novalidate>

<label for="nombre">¿Cómo te llamas?:</label>

<input type="text" name="nombre" id="nombre" required/>

<input type="submit" value="Enviar">

</form>

El atributo novalidate dentro del elemento form deshabilitara todos los controles del
formulario.
Vídeo en HTML5
Introducción al vídeo en HTML5
Con los aumentos de los anchos de vanda el uso del vídeo en la web cada vez se extiende más
y hoy en día es el contenido más consumido en las páignas web.

Atrás quedaron los días en los que no existían estándares para poder reproducir vídeos por
Internet y en los cuales tecnologías como Flash o Silverlight disponian de este privilegio. Si
bien acarreaban otros problemas de portabilidad, seguridad y al fin y al cabo poca integración
con los estándares HTML y CSS.

A partir de HTML5 se estándariza el uso del vídeo mediante el elemento video del lenguaje. De
igual manera aparecn un conjunto de APIs que nos permiten interactuar con el contenido que
muestra el vídeo.

Si queremos incluir un vídeo en nuestra página HTML5 simplemente tendremos que escribir lo
siguiente:

<video src="mivideo.webm" controls>

<p>Su navegador no soporta vídeos HTML5.</p>

</video>

Dentro del código tenemos que conocer el significado de sus dos atributos. Por un lado el
atributo src nos sirve para indicar el nombre del fichero que contiene el vídeo que queremos
reproducir.

Mientras que por el otro el atributo controls permite que se muestre un panel de control de
reprodución del vídeo, para que se pueda iniciar, parar, adelantar, cambiar el sonido,…

Atributos del vídeo


Para poder manipular el vídeo, la forma en la que se muestra,… el elemento video de HTML5
nos ofrece diferentes atributos. Revisemos para que sirven.

Fichero del vídeo


Para poder indicar dónde está el fichero que contiene el vídeo deberemos de utilizar el atributo
src. Este atributo recibirá como valor el nombre del fichero.

<video src="mivideo.webm" controls>

<p>Su navegador no soporta vídeos HTML5.</p>

</video>
Ancho y alto del vídeo
Aunque como todo elemento HTML podemos modificar la apariencia mediante el lenguaje CSS,
el elemento vídeo nos ofrece los atributos widht y height para poder definir el ancho y alto del
vídeo respetivamente.

<video src="mivideo.webm" width="600" height="400" controls>

<p>Su navegador no soporta vídeos HTML5.</p>

</video>

Inicio automático del vídeo


Si queremos que el vídeo se inicie de forma automática una vez que se carge el documento
HTML5 deberemos de utilizar el atributo autoplay.

<video src="mivideo.webm" autoplay controls>

<p>Su navegador no soporta vídeos HTML5.</p>

</video>

Vídeo en bucle
En el caso de que queramos que el vídeo se reproduzca en bulce una y otra vez usaremos el
atributo loop.

<video src="mivideo.webm" autoplay loop>

<p>Su navegador no soporta vídeos HTML5.</p>

</video>
Vídeo sin sonido
Otra opción es que el vídeo se ejecute sin sonido. Esto lo conseguimos apoyándonos en el
atributo muted.

<video src="mivideo.webm" autoplay muted>

<p>Su navegador no soporta vídeos HTML5.</p>

</video>

Cartel del vídeo


Antes de que se inicie el vídeo podemos poner una imagen de muestra (o cartel). Para ello
vamos a utilizar el atributo poster. El atributo poster recibirá una URL con el nombre del
fichero que queremos utilizar como cartel del vídeo.

<video src="mivideo.webm" controls poster="mivideo.png">

<p>Su navegador no soporta vídeos HTML5.</p>

</video>

Si hemos utilizado el atributo autoplay no se verá el cartel del vídeo.

Precargar el vídeo
Los vídeos suelen ser ficheros que tienen un tamño considerable y es por ello que el tiempo de
descarga en la web suele ser superior que al contenido textual o gráfico. Es por ello que se
puede dar el caso de que se haya cargado el contenido de un documento, pero no el vídeo que
incluye.

Para paliar este tema del tamaño podemos precargar el vídeo. En este caso vamos a utilizar el
atributo preload, el cual puede tener tres valores:

● ‘none’, no hace buffering del vídeo.


● ‘auto’, hace buffering del vídeo.
● ‘metadata’, hace buffering, pero solo de la metainformación del vídeo.

<video src="mivideo.webm" controls preload="auto">

<p>Su navegador no soporta vídeos HTML5.</p>

</video>
Formatos de Vídeo
Cada uno de los navegadores es capaz de rederizar un formato de vídeo diferente.

Contenedores de formato
Formatos como mp3, mp4 o WebM son conocidos como contenedores de formato, ya que
contienen diferentes partes que permiten que se componga un vídeo o canción.

WebM
El contenedor WebM utiliza formatos Ogg Vorbis para el audio y VP8/VP9 para el vídeo.

MPEG 4
El contenedor MP4 utiliza formato de audio mp3 o aac y un formato de vídeo H.264.

Ogg
El contenedor Ogg utiliza formatos Ogg Vorbis para el audio y Ogg Theora para el vídeo.

Chrome Firefox Internet Explorer Opera Safari

WebM 6.0 4.0 9.0 10.60 3.1

MPEG 4 x x

Ogg x x

Estos contenedores de formato lo que hacen es comprimir el vídeo y audio en ficheros


manejables.

Los navegadores utilizan los codecs para poder descomprimir el contenido de los contenedores
y poder reproducir el vídeo y audio. Si el navegador no tiene un codec que soporte el formato,
no se podrá reproducir el vídeo y/o audio.

Múltiples orígenes y formatos del vídeo


Esta situación que nos obliga a tener diferentes contenedores de formato atendiendo al
navegador hace que nuestros documentos HTML5 tengan que permitir cargar varios ficheros en
varios formatos.

Esto lo coseguimos mediante el elemento source. El elemento source es un elemento anidado


al elemento video y nos sirve para enlazar diferentes ficheros de vídeo en formatos diferentes.

La estructura del elemento source es la siguiente:


<video controls>

<source src="mivideo.mp4" type="video/mp4"/>

<source src="mivideo.webm" type="video/webm"/>

<p>Su navegador no soporta vídeos HTML5.</p>

</video>

A la hora de renderizar el vídeo, el navegador irá recorriendo los diferentes formatos hasta que
encuentre uno que pueda reproducir.

Media Formats en HTML5


Media Formats
Los elementos video y audio sirven para reproducir ficheros de audio y de vídeo de forma
estándar y sin la necesidad de utilizar plugins de reproducción.

Los formatos de video y audio consisten en un contenedor dentro del cual encontramos los
streams de datos a repoducir.

El contenedor puede albergar ficheros de video, audio, datos y subtítulos. Junto con el vídeo y el
audio nos encontramos los codecs.

Un codec es un algoritmo de compresión que nos ayuda a descomprimir y comprimir los ficheros
de media.

Cada navegador tiene capacidad para reproducir un tipo u otro de formatos de media. Algunos
de estos formatos son estándares y otros son propietarios.

https://developer.mozilla.org/en-US/docs/Web/HTML/Supported_media_formats

Formatos
WebM
El formato WebM es una versión restringida del formato de contenedor Matroska. El cual utiliza
el codec de vídeo VP8 o VP9 y el codec de audio Vorbis o Opus.

Los mime types para el formato WebM son:

● video/webm, para los ficheros de vídeo (y audio) de WebM.


● audio/webm, para los ficheros de audio de WebM.
Ogg Theora Vorbis
Es un contenedor de media Ogg, el cual contiene un codec de vídeo Theora y un codec de
audio Vorbis. Este contenedor está soportado por Firefox, Chrome y Opera. En algunos casos
dentro de Safari (fuera de iOS).

El formato WebM tiene mayor compresión que otros formatos como Ogg y es por ello que es
preferido por los desarrolladores. Si bien se suele utilizar Ogg para navegegadores antiguos que
no soportan WebM.

Los media types para un contenedor Ogg son:

● audio/ogg, para ficheros de audio.


● video/ogg, para ficheros de vídeo (y posiblemente audio).
● application/ogg, se utiliza en el caso de que no se sepa el contenido del contenedor Ogg.

Ogg Opus
En este caso tenemos el contenedor Ogg utilizando el codec de audio Opus.

El media type para el contenedor Ogg Opus es *audio/ogg; codecs=opus**.

Ogg FLAC
Es un contenedor Ogg que utiliza un codec de audio FLAC.

MP4 H.264 (AAC o MP3)


El contenedor MP4 está formato por un codec de vídeo H.264 y un codec de audio AAC.

Este formato es soportado por Internet Explorer, Safari y Chrome.

Podemos encontar el contenedor MP4 con un codec de audio MP3. Si bien en este caso este
codec solo es soportado por Internet Explorer y Chrome.

Los formatos *mpeg** están patentados y no tienen licencias gratuitas para su distribución.

MP4 FLAC
Es un contenedor MP4 pero que tiene un codec de audio FLAC.

Contenedores de Audio
MP3
Es un formato de audio. Su media type es audio/mpeg. Necesita de un decoder mp3 para que
pueda ser reproducido.
WAVE PCM
El formato de contenedor Wave tiene el codec de audio PCM. Es el conocido como wave codec
1. Las extensiones de estos ficheros son .wav.

Los mime types reconocidos para el formato wave son:

● audio/wave
● audio/wav
● audio/x-wav
● audio/x-pn-wav

FLAC
El contenedor de formato FLAC está compuesto por el codec de audio FLAC. Suelen tener la
extensión .flac.

Los mime types para el formato FLAC son:

● audio/flac
● audio/x-flac

Compatibilidad Codecs
Como hemos visto la compatibilidad de los codec varia dependiendo del navegador. Es por ello
que puedes comprobar la compatibilidad de un determinado codec con un navegador en
Supported Media Formats de MDN.

Canvas HTML5
En HTML 4.01 la gestión de contenidos visuales se limitaba a las imágenes y a los mapas de
imágenes mediante los elementos img y map respectivamente. Estos elementos nos daban la
capacidad de añadir objetos gráficos que enriquecian el aspecto de nuestra web.

Si bien una de las grandes limitaciones de las imágenes en HTML 4.01 era que el contenido de
estas imágenes era estático (en algunos casos animado si usábamos un GIF). No se podía
realizar ninguna interacción entre el usuario y los elementos que componían la imagen.

En HTML5 encontramos el elemento canvas, el cual viene a subsanar estas deficiencias. La


idea del elemento canvas es que este sea como un lienzo. En el lienzo podremos desde cargar
una imagen a interactuar con él de forma dinámica.

El elemento canvas no fue uno de los elementos que apareció nuevo en la especificación, si no
que era un elemento que ideó Apple y que implementó Safari. Lo que hizo el grupo de trabajo
de HTML5 fue el incorporarlo a la especificiación. Una situación parecida a la vivida por el
elemento XMLHttpRequest ideado por Microsoft y postriormente estandarizado.
Cierto es que siempre quedará en el aire el por qué se tomo esta decisión en vez de apostar por
algo más acceible y existente como era la tecnología SVG.

Elemento Canvas
Para crear un elemento canvas en nuestra página utilizaremos el elemento canvas. El código
para crear este elemento será algo parecido a:

<canvas id="micanvas" height="200" width="400"></canvas>

El contenido del elemento canvas será el que se cargue cuando el navegador no soporta dicho
elemento. De esta forma podemos utilizarlo para sacar un texto informativo sobre el no soporte
de este elemento:

<canvas id="micanvas" height="200" width="400">

Su navegador no soporta el elemento Canvas. Le recomendamos que se


actualice a una versión más moderna.

</canvas>

O bien una imagen que sea lo más cercana posible al contenido de nuestro canvas.

<canvas id="micanvas" height="200" width="400">

<img src="imagenAlternativa.png" />

</canvas>

Si no insertamos nada dentro del canvas, lo que veremos será un espacio en blanco con el
tamaño que le hayamos indicado al canvas. Si no le indicamos un tamaño, por defecto, el
canvas se pintará en 300x150.

Manipular un Canvas
Para manipular el elemento canvas vamos a tener que tirar de Javascript. De esta forma lo
primero será el obtener una referencia al elemento canvas. En concreto recuperaremos su
contexto mediante el método .getContext(). Este método se ejecuta directamente sobre el
elemento canvas es por ello que lo primero que haremos será acceder al elemento con un
getElementById().

var canvas = document.getElementById("micanvas");


var context = canvas.getContext("2D");

El contexto que recuperamos es el 2D. Ya que es el único contexto disponible en los elementos
canvas a día de hoy. Si bien los navegadores web ya están trabajando para ofrecer un contexto
3D basado en WebGL.

Además el méteodo getContext() nos va a servir para poder comprobar si el navegador


soporta al elemento canvas o no.

var canvas = document.getElementById("micanvas");

if (canvas.getContext) {

var context = canvas.getContext("2D");

Una vez que tenemos el contexto del elemento canvas podemos empezar a interactuar con él.
Añadirendo colores, imágenes, líneas, elementos gráficos, degradados,…

Dibujar Figuras
Para poder insertar figuras dentro del canvas deberemos de conocer cómo funciona el sistema
de coordenadas. Y es que para posicionar a un elemento en el canvas tendremos la esquina
superior izquierda como la relativa a la posición (0,0) y la esquina inferior derecha como la
posición (ancho,alto), dónde los valores de ancho y alto corresponden al tamaño que le
hayamos dado al lienzo.

Rectángulos
Para poder añadir un rectángulo al canvas disponemos de tres métodos: fillRect,
strokeRect y clearRect. Estos métodos los vamos a ejecutar sobre el contexto del canvas.

El método fillRect nos sirve para crear un rectángulo relleno. La sintaxis del método
fillRect es la siguiente:

void ctx.fillRect(x, y, width, height);


Dónde x e y son las coordenadas de la esquina superior izquierda del rectángulo dentro del
canvas, mientras que con width y height indicamos el ancho y alto del rectángulo
respectivamente.

Si no indicamos nada, el relleno del rectángulo será el color establecido por defecto, es decir, el
negro.

Con el método strokeRect generaremos un rectángulo que solo tenga la línea exterior. La
sintáxis del método strokeRect es:

void ctx.strokeRect(x, y, width, height);

Los parámetros son los mismos que utilizábamos con el método fillRect.

El último método que gestiona rectángulos en HTML5 es clearRect. El método clearRect


genera un rectángulo que sea transparente sobre la zona del rectángulo.

void ctx.clearRect(x, y, width, height);

Al igual que los dos anteriores métodos, los parámetros son las coordenadas de origen x e y así
como el ancho o width y alto height.

De esta manera podemos tener un rectángulo que tenga internamente otro transparente,
utiliznado los métodos fillRect y clearRect de la siguiente forma:

if (canvas.getContext) {

var ctx = canvas.getContext('2d');

ctx.fillStyle = 'green';

ctx.fillRect(10, 10, 200, 100);

ctx.clearRect(30, 30, 160, 60);

Paths
A parte de los rectángulos tenemos otra figura que nos permite dibujar objetos dentro de un
canvas es el path. Un path es una secuencia de puntos los cuales van unidos por líneas o
curvas. Los path pueden ser abiertos o cerrados, siendo en este segundo caso el último punto
coincidente con el primero.

Para hacernos una idea es como si estuviésemos pintando con un lapiz sobre un lienzo. Lo
primero es mover el lapíz a un punto y desde ese punto trazar una línea o curva hasta otro punto
y así sucesivamente.
Para crear un path deberemos de invocar al método beginPath sobre el contexto del canvas.

void ctx.beginPath();

Una vez que hemos creado el path podemos realizar una serie de operaciones, por ejemplo
podemos movernos y crear una línea de la siguiente forma:

ctx.beginPath();

ctx.moveTo(75, 50);

ctx.lineTo(100, 75);

Es importante que cuando realizamos operaciones en el path del canvas para que estas se
visualicen, es decir, se reflejen en el canvas deberemos de llamar al método stroke o fill.

Por un lado el método stroke lo que hace es dibujar las líneas que hayamos trazado
incluyéndolas en el canvas.

void ctx.stroke();

void ctx.stroke(path);

Por el otro el método fill lo que hace es rellenar el área que hemos delimitado mediante las
líneas. Asumiendo que el último punto equivale al punto desde el que empezamos el subpath.
Hay que tener en cuenta que cada vez que movemos el puntero creamos un nuevo subpath.

void ctx.fill([fillRule]);

void ctx.fill(path [, fillRule]);

Así, nuestro ejemplo para tener un path incluiría lo siguiente:

ctx.beginPath();

ctx.moveTo(75, 50);

ctx.lineTo(100, 75);

ctx.fill();
Para poder finalizar la gestión de un path tenemos el método closePath. Este método añade
una línea desde la posición en la que nos encontremos hasta la posición inicial del path. El
utilizar el método closePath no evita el que tengamos que forzar el pintado con fill o stroke.

void ctx.closePath();

En el caso de que utilicemos el método fill no será necesario que


invoquemos al método closePath ya que el propio método fill traza una
línea hasta el origen del subpath.

Mover el puntero
Para mover el puntero en el canvas dentro de un path tenemos el método moveTo.

void ctx.moveTo(x, y);

Los parámetros x e y representan las coordenadas (x,y) del canvas a la cual queremos mover el
cursor. Hay que tener en cuenta que cada vez que movamos el puntero crearemos un nuevo
sub-path con un nuevo punto de origen.

Por ejemplo podemos mover el puntero para crear dos líneas paralelas de la siguiente forma:

ctx.beginPath();

ctx.moveTo(10,10);

ctx.lineTo(10,100);

ctx.moveTo(20,10);

ctx.lineTo(20,100);

ctx.stroke();

Dibujar Líneas
Para poder dibuajar líneas dentro de un canvas en HTML5 vamos a utilizar el método lineTo.
La sintaxis del método lineTo es:

ctx.lineTo(x, y);
Dónde las propiedades x e y representan la posición (x,y) del punto final de la línea. El punto de
origen será el punto dónde esté el puntero del path dentro del canvas.

Es decir, que si ejecutamos el siguiente código:

ctx.moveTo(10,10);

ctx.lineto(10,100);

Nos pintará una línea desde el punto (10,10) a el punto (10,100).

Dibujar un arco
Para poder dibujar un arco dentro de un canvas tenemos dos métodos arc y arcTo. Veamos su
sintaxis en detalle.

arc(x, y, radius, startAngle, endAngle, anticlockwise)

En el caso de arc deberemos de indicar el centro del arco mediante los parámetros x e y. Lo
siguiente es especificar el radio que va a tener el arco mediante el parámetro radius.

Lo siguiente será indicar lel ángulo en el que empezamos startAngle en radianes y luego el
ángulo sobre el que acabamos endAngle en radianes.

Recuerda que si quieres trabajar en grados, un grado es igual a π/180


radianes

El último parámetro, anticlockwise indica si el arco se traza en la dirección de las agujas del
reloj que será un valor false (valor por defecto) o si queremos que sea como las agujas del
reloj, lo cual será un valor de true.

De esta forma podemos dibujar un círculo entero si escribimos lo siguiente:

ctx.arc(100,100,50,0,2 * Math.PI);

ctx.stroke();

El segundo método es arcTo y su sintaxis sería:

void ctx.arcTo(x1, y1, x2, y2, radius);


En este caso se realiza un arco atendiendo a dos puntos de control, el primer punto de control
es el demarcado por los parámetros x1 e y1 y el segundo es el demarcado por x2 e y2. Lo
siguiente que hay que indicar es el radio del arco mediante el parámetro radius. Que así dicho
suena bastante complicado de entender.

La idea de dibujar un arco mediante dos líneas tangenciales, para ello necesitaremos un primer
punto para poder hacer las dos líneas. Este le conseguimos moviendo el puntero.

void ctx.moveTo(x0,y0);

void ctx.arcTo(x1, y1, x2, y2, radius);

Con el primer punto ya tendremos las dos líneas tangenciales. El arco se dibujará desde el
punto inicial hasta el punto dónde el cículo de rádio radius toca con las líneas tangenciales y
hasta el segundo punto dónde el círculo toca con la otra línea tangencial.

La imagen lo explica mucho mejor:

Y, ¿por qué? esta complicación a la hora de dibujar arcos. La idea de este método arcTo es
para poder redondear las esquinas de los rectángulos, tal y cómo vemos en el siguiente
diagrama:
Dibujar una curva Bézier
Otra de las capacidades que tenemos en un path es la de poder crear una curva de Bézier para
ello disponemos de los métodos quadraticCurveTo y bezierCurveTo.

En el caso de quadraticCurveTo la sintaxis será:

void ctx.quadraticCurveTo(cpx, cpy, x, y);

Crea una curva de Bézier utilizando un punto de control, demarcado por los parámetros cpx y
cpy y el punto final demarcado por x e y. Hay que tener en cuenta que el punto de inicio será
aquél en el que esté el puntero dentro del canvas. Por lo que normalmente encontraremos algo
así como:

void ctx.moveTo(x1,y1);

void ctx.quadraticCurveTo(cpx, cpy, x2, y2);

El efecto de la curva de Bézier que genera el método quadraticCurveTo sería algo parecido
a:

Para el método bezierCurveTo tenemos la siguiente sintaxis:

void ctx.bezierCurveTo(cp1x, cp1y, cp2x, cp2y, x, y);

En este caso crea una curva de Bézier atendiendo a dos puntos de control, el primer punto de
control sería cp1x y cp1y, mientras que el segundo punto de control es cp2x y cp2y y un punto
de fin marcado con los parámtros x e y.
Visualmente obtendríamos algo como:

Rectángulos
A parte de la figura que podemos dibujar de un rectángulo con el canvas también contamos con
la posibilidad de añadir al path la figura de un rectángulo. Y para ello tenemos el método rect.
La sintaxis del método rect es:

void ctx.rect(x, y, width, height);

Este método nos dibujará un rectángulo que empiece en la posición x e y y que tenga un ancho
y alto definido con los parámetros width y height respectivamente.

Podemos crear un rectángulo de 200x100 de la siguiente manera:

if (canvas.getContext) {

var ctx = canvas.getContext('2d');

ctx.rect(10,10,200,100);

ctx.fill();

Al contratario que otros métodos del path con rect no necesitamos realizar
un moveTo al prinicipio ya que lo hace el propio método.

Objeto Path
Uno de los objetos que podemos manejar en el canvas es el objeto Path2D. Este objeto lo que
nos permite es almacenar un path y la secuencia de comandos que lleve asociada, para poder
repetirlo lass veces que necesitemos.

Podemos construir un objeto Path2D de varias formas:


new Path2D();

new Path2D(path);

new Path2D(d);

Podemos copiar el path de uno existente y pasarlo como parámetro path. O bien puede ser un
path SVG definido por una cadena.

Definimos un path que almacene los comandos:

let path1 = new Path2D();

path1.rect(10, 10, 100,100);

Este Path lo que tiene es dibujar un rectángulo mediante el método rect. Ahora lo que podemos
es crear un nuevo path a partir de este path existente:

let path2 = new Path2D(path1);

Ahora podemos añadir más comandos al path:

path2.moveTo(220, 60);

path2.arc(170, 60, 50, 0, 2 * Math.PI);

Para volcar un path a un canvas lo que haremos será utilizar un método stroke o fill que
reciba ese path como parámetro.

ctx.stroke(path2);

Path2D SVG
También podemos crear un path con un objeto Path2D que reciba como parámetro un path svg.
Un ejemplo de path SVG sería:

"M 10 10 h 80 v 80 h -80 Z"


Que lo que viene a decir es: “ves al punto 10,10 (M 10 10), desplázate horizontalmente al 80
(h80), desplázate verticalmente al 80 (v 80), desplázate horizontalmente hacía la izquierda -80
puntos (h -80) y traza hacía el inicio”.

Así crearíamos nuestro path SVG de la siguiente forma:

// Cuadrado

var pathsvg = new Path2D('M10 10 h 80 v 80 h -80 Z');

ctx.fill(pathsvg);

// triangulo

var pathsvg2 = new Path2D('M100 10 l 80 80 h -80 Z');

ctx.fill(pathsvg2);

Estilos y Colores en el Canvas


Hasta ahora hemos visto cómo podíamos crear nuestras figuras y paths dentro del canvas para
que se visualicen. Algo hemos visto a la hora de darle estilos y colores ya que hemos visto que
podíamos crear solo el contorno con el método stroke o rellenarlo con el método fill. Pero
veamos algo más en detalle cómo darle estilo y color a nuestros diseños en el canvas.

Colores
Hay dos propiedades que tenemos que controlar para poder dar los colores a los elementos de
un canvas, estas son: fillStyle y strokeStyle las cuales darán el color al relleno de las
figuras y al borde de las figuras respectivamente.

Para asignarle un color a una de estas propiedades haremos lo siguiente:

ctx.fillStyle = color;

ctx.strokeStyle = color;

Dónde el color puede ser tres cosas diferentes:

● Color RGB, en este caso podremos expresar el color mediante un nombre ‘red’, el
código RGB #ff0000 o mediante la función rgb, que para un color rojo sería
rgb(255,0,0);.
● Objeto Gradiente, para mostrar un degradado de colores.
● Patrón,

Así, podríamos rellenar un círculo de color rojo de la siguiente forma:


ctx.beginPath();

ctx.arc(100,100,50,0,2*Math.PI);

ctx.fillStyle = 'red';

ctx.fill();

O tener un triángulo con un borde que sea verde:

ctx.beginPath();

ctx.moveTo(50, 50);

ctx.lineTo(100, 100);

ctx.lineTo(50, 100);

ctx.lineTo(50, 50);

ctx.strokeStyle = 'green';

ctx.stroke();

En el caso de hacer un fill hay que recordar que el último trazo genera una
línea hasta el origen del path. En el caso de utilizar stroke esto no sucede,
por lo que hay que generar el último movimiento de línea .lineTo(50, 50)

Transparencias
A la hora de manipular un Canvas podemos hacer que haya rellenos que sean transparentes (o
traslúcidos). Para ello podemos utilizar la propiedad globalAlpha o indicar el alpha en la
función rgba() cuando asignemos un color.

El en caso de que manipulemos la propiedad globalAlpha utilizaremos el siguiente código:

ctx.globalAlpha = valor;

El valor de la transparencia va desde 0.0 a 1.0 en decimales. Dónde 0.0 es totalmente


transparente y 1.0 es totalmente opaco.

La idea de utilizar la propiedad globalAlpha es cuando vas a utilizar la transparencia para


mútiples figuras. De esta manera podemos crear un rectángulo que sea transparente de la
siguiente forma:
ctx.fillStyle = 'red';

ctx.globalAlpha = 0.5;

ctx.fillRect(80, 80, 200, 100);

La otra forma de crear una transparencia es establecer la transparencia en el valor del color
RGB. Para ello utilizamos el cuatro parámetro de la función rgba() cuando demos el color
mediante fillStyle o strokeStyle.

La función rgba() tiene la siguiente sintaxis:

rgba(rojo,verde,azul,transparencia);

Así, podemos volver a crear nuestro mismo rectángulo transparente de la siguiente forma:

ctx.fillStyle = 'rgba(255,0,0,0.5)';

ctx.fillRect(80, 80, 200, 100);

Estilos de Líneas
A las líneas que hemos dibujado en nuestro path también las podemos dar estilo.

Ancho Línea
Lo más básico que podemos hacer con una línea es establecer el ancho de la línea. Por defecto
el ancho de la lína es de 1.0.

Para poder modificar el ancho de la línea contamos con la propiedad lineWidth. La sintaxis de
esta propiedad es la siguiente:

ctx.lineWidth = tamaño;

Así podemos dibujar una línea modificando su tamaño de la siguiente forma:

ctx.lineWidth = 8;

ctx.moveTo(10,10);

ctx.lineTo(10, 100);

ctx.stroke();
Fin de Línea
Otra parte visual que podemos modificar de una línea es su final, es decir la forma que tendrán
los extremos. Para ello tenemos la propiedad lineCap. La sintaxis de la propiedad lineCap es:

ctx.lineCap = butt|round|square;

Los valores que puede tener la propiedad lineCap son: butt, round y square.

● butt, el borde es cuadrado con el tamaño de la línea.


● round, el borde de la línea es redondeado.
● square, se añade un pequeño cuadro al final de la línea, adicional a ella, con el mismo
ancho que tiene la línea.

De esta forma el código para tener una línea con los finales redondeados sería el siguiente:

ctx.lineCap = 'round';

ctx.lineWidth = 20;

ctx.moveTo(50,50);

ctx.lineTo(50,150);

ctx.stroke();

Unión de Líneas
Cuando estamos dibujando un conjunto de líneas (o arcos o curvas) tendremos un conjunto de
uniones entre ellos. Dentro de los canvas de HTML5 podemos definir el estilo a darle a esta
unión de líneas.

Para ello disponemos de la propiedad lineJoin. La sintaxis de la propiedad lineJoin es:

ctx.lineJoin = round|bevel|miter;

Los posibles valores que tiene la propiedad lineJoin son: round, bevel y miter.

● round, redondea las uniones entre las líneas. Para ello utiliza un arco de radio igual al
ancho de la línea.
● bevel, las líneas son recortadas de forma rectangular entre los diferentes segmentos,
como si fuese un bisel.
● miter, se extiende el límite de la línea para conectarla con el siguiente segmento, es el
valor por defecto de unión entre líneas.
● Si queremos ver cómo quedaría nuestra unión de líneas redondeadas podemos utilizar
el siguiente código:

ctx.lineWidth = 20;

ctx.lineJoin = 'round';

ctx.moveTo(50,50);

ctx.lineTo(100,150);

ctx.lineTo(150,50);

ctx.lineTo(200,150);

ctx.lineTo(250,50);

ctx.stroke();

En el caso de haber utilizado el valor miter disponemos de la propiedad miterLimit para


limitar cuánto se alargará el límite de la línea para unirlo con el siguiente segmento.

En el caso de que las líneas superen el valor establecido la unión cambiará de miter a un tipo
bevel.

Podemos establecer el miterLimit con el siguiente código:

ctx.miterLimit = valor;

Líneas punteadas
Podemos hacer que las líneas que creemos en el canvas sean a guiones. Para ello tenemos el
método setLineDash() y la propiedad lineDashOffset.

Mediante el método setLineDash() podemos establecer el tamaño de las líneas y el tamaño


de los espacios en modo patrón que se irá aplicando a toda la línea.

setLineDash([tamaño_linea1,tamaño_espacio1, tamaño_linea2,
tamaño_espacio2,..., tamaño_lineaN,tamaño_espacioN]);

De esta manera podemos definir un rectángulo que tenga líneas de un tamaño 4 y espacios de
un tamaño 2 de la siguiente forma:
var canvas = document.getElementById('lienzo');

if (canvas.getContext) {

var ctx = canvas.getContext('2d');

ctx.setLineDash([4,2]);

ctx.strokeStyle = 'green';

ctx.strokeRect(10, 10, 200, 100);

Por otro lado podemos indicar el desplazamiento desde el inicio de la línea en el cual queremos
aplicar el patrón de línea punteadas. Para esto tenemos la propiedad lineDashOffset. Si por
ejemplo queremos que haya un desplazamiento de 5 posiciones para que se empiece a aplicar
el patrón escribiremos lo siguiente:

ctx.lineDashOffset = 5;

Gradientes
Hasta ahora hemos visto cómo aplicar colores de relleno de las figuras mediante colores sólidos,
o bien utilizar el atributo globalAlpha para aplicar transparencias. Otra opción que tenemos
para los rellenos son los gradientes.

Un gradiente es una transición de color desde un color origen a un color destino. O bien la
transición de un color de inicio, a un segundo colo, de aquí a un tercer color,…

Los gradientes pueden ser gradientes lineales, es decir que se ejecutan en la dirección de una
línea o pueden ser gradientes radiales, en este caso se aplica la transición de color de forma
circular.

Gradiente Lineal
Para crear un gradiente lineal utilizamos el método .createLinearGradient(). La sintaxis del
método .createLinearGradient() es la siguiente:

CanvasGradient ctx.createLinearGradient(x0, y0, x1, y1);

Dónde las coordenadas x0 e y0 nos sirven para indicar el inicio del gradiente y x1 e y1 nos
sirven para indicar el final del gradiente.

Por ejemplo podemos crear un gradiente que vaya en diagonal desde la posición (0,0) a la
posición (150,150) de la siguiente forma:
var lineargradient = ctx.createLinearGradient(0, 0, 150, 150);

Lo que nos devuelve el método .createLinearGradient() es un objeto CanvasGradient.


Este objeto se lo podremos aplicar como valor a las propiedades fillStyle y strokeStyle
que lo utilizarán como color para poder rellenar los objetos que correspondan.

Podemos aplicar el gradiente lineal de la siguiente forma, para un fillStyle:

ctx.fillStyle = lineargradient;

Pero, ¿qué colores se utilizan el el gradiente? Para poder indicar los colores tenemos el método
.addColorStop(). La sintaxis del método .addColorStop() es la siguiente:

void gradient.addColorStop(offset, color);

Podremos añadir tantos colores al gradiente como deseemos. Si bien los colores deben de estar
situados en el offset. El valor del offset va de 0 a 1. Con el parámetro color indicaremos el
color que se aplique en el gradiente.

Entonces, si queremos que el gradiente empiece en un color blanco y acabe en un color verde
podemos codificar lo siguiente:

lineargradient.addColorStop(0, 'white');

lineargradient.addColorStop(1, 'green');

En el caso de que queramos tres colores, dónde a los dos anteriores se pase por un color rojo
entre medias, tendremos lo siguiente:

lineargradient.addColorStop(0, 'white');

lineargradient.addColorStop(.5, 'red');

lineargradient.addColorStop(1, 'green');

El código completo para aplicar nuestro gradiente lineal sería:


var ctx = canvas.getContext('2d');

var lineargradient = ctx.createLinearGradient(0, 100, 150, 100);

lineargradient.addColorStop(0, 'white');

lineargradient.addColorStop(1, 'green');

ctx.fillStyle = lineargradient;

ctx.fillRect(10, 10, 160, 100);

En este caso hemos rellenado al figura de un rectángulo mediante el gradiente.

Gradiente Radial
Para los gradientes radiales tenemos el método .createRadialGradient(). La sintaxis del
método .createRadialGradient() es:

CanvasGradient ctx.createRadialGradient(x0, y0, r0, x1, y1, r1);

En este caso el origen del gradiente se indica mediante una posión x0 e y0, pero con un radio
especificado con r0. El final del gradiente lo especificamos mediante el punto x1 e y1 y su radio
r1.

Aunque estemos trabajando con círculos, el gradiente radial lo podemos aplicar a cualquier
figura.

El método .addColorStop() funciona de igual manera para el gradiente radial. Así podremos
tener el siguiente ejemplo para crear un gradiente radial:

var rg1 = ctx.createRadialGradient(45, 45, 10, 52, 50, 30);

rg1.addColorStop(0, '#A7D30C');

rg1.addColorStop(0.9, '#019F62');

rg1.addColorStop(1, 'rgba(1, 159, 98, 0)');

ctx.fillStyle = rg1;

ctx.fillRect(0, 0, 300, 300);


Patrones
Una de las cosas que podemos hacer con la imágenes dentro de un canvas es crear patrones.
Es decir, repetir la imagen tantas veces como queramos. Para ello tenemos el método
.createPattern().

La sintaxis del método .createPattern() es la siguiente:

CanvasPattern ctx.createPattern(image, repetition);

El parámtro image recibirá una referencia a un origen de imagen que se encuentre dentro del
documento HTML5. Esta imagen puede ser una imagen normal, un canvas, un vídeo, una
imagen svg,…

Para cargar una imagen podemos utilizar la clase Image que representa a un objeto HTML5 de
imagen. Dicha imagen recibe una URI en su propiedad srccon el path en el que esta la imagen.

var imagen = new Image();

imagen.src = 'imagen.jpg';

Es importante saber que cuando cargamos una imagen, esta no se carga automáticamente para
que podamos utilizarla. Es por ello que nos debemos de apoyar en el evento onload de la
imagen para poder utilizarla.

img.onload = function() {

// Manipulamos la imagen

};

El segundo parámetro del método .createPattern() es repetition, el cual nos sirve para
indicar el modelo de repetición del patrón. Los modelos que existen son:

● repeat, el patrón se repite en todas las direcciones, tanto en el eje x, como en el eje y.
● repeat-x, el patrón solo se repite en el eje horizontal x.
● repeat-y, el patrón solo se repite en el eje vertical y.
● no-repeat, la imagen solo se utiliza una vez.

El patrón nos devuelve un objeto CanvasPattern, el cual se puede aplicar a las propiedades
fillStyle o strokeStyle.

El código completo para poder crear un patrón de imagenes nos quedaría de la siguiente forma:
var ctx = canvas.getContext('2d');

var img = new Image();

img.src = 'patron.jpg';

img.onload = function() {

var pattern = ctx.createPattern(img, 'repeat');

ctx.fillStyle = pattern;

ctx.fillRect(0, 0, 300, 300);

};

Sombras
Otro de los efectos que podemos realizar sobre los elementos de un canvas es generarles una
sombra. Para poder dar sombras a un elemento disponemos de 4 propiedades sobre el contexto
del canvas:

● shadowOffsetX, recibe un valor numérico en formato float que será la distancia desde
el elemento en horizontal dónde se posicionará la sombra.
● shadowOffsetY, recibe un valor numérico en formato float que será la distancia desde
el elemento en vertical dónde se posicionará la sombra.
● shadowBlur, nos sirve para indicar el efecto borroso sobre la sombra. Los valores van
desde el 0, que es el valor por defecto.
● shadowColor, indica el color que le queremos dar a la sombra. El color se puede
asignar mediante el nombre del color, el formato RGB o la función rgb().
Texto en Canvas
En HTML5 tenemos dos métodos para insertar un texto en canvas. Estos métodos son:
.fillText() y strokeText().

CanvasRenderingContext2D.fillText(text, x, y [, maxWidth]);
CanvasRenderingContext2D.strokeText(text, x, y [, maxWidth]);

En el caso de fillText nos inserta un texto definido en el parámetro text dentro de la posición
x,y, al cual podemos limitar el ancho del texto mediante el parámetro opcional maxWidth. El
método fillText nos insertará un texto relleno.

El funcionamiento de strokeText es el mismo que fillText, pero con la diferencia que del
texto que inserta solo representa el borde.

De esta manera podemos insertar una cadena de texto de la siguiente forma:

if (canvas.getContext) {
var ctx = canvas.getContext('2d');
ctx.fillText("Esto es texto en un Canvas",10,10);
}

Estilo del Texto


A la hora de insertar texto en el canvas podemos dar un estilo del texto de tal manera que
seleccionemos la fuente, alineación y dirección del mismo.

Para poder dar estilo del texto disponemos de una serie de propiedades:

Fuente
Mediante la propiedad font podemos especificar esl estilo de la fuente que estamos utilizando.
Dentro del estilo podemos indicar el tamaño y tipo de letra.

La sintaxis de la propiedad font es:

ctx.font = value;
El valor que se le pasa a la propiedad font es el de una cadena igual a la cadena que le
pasamos en CSS. La cadena se puede representar así:
"estilo tamaño fuente"

Por ejemplo podríamos tener la siguiente fuente:

ctx.font = "bold 50px serif";

Alineación Texto
También podemos selecionar la alineación del texto mediante la propiedad textAlign. La
sintaxis de la propiedad textAlign es la siguiente:

ctx.textAlign = "left" || "right" || "center" || "start" || "end";

Los valores que puede tener son:

● left, alineado a la izquierda.


● right, alineado a la derecha.
● center, texto centrado.
● start, el texto se alinea según el “locale” desde el principio. Es decir, si el texto se
escribe de izquierda a derecha, se alinea a la izquierda. Si el texto se escribe de derecha
a izquierda se alinea a la derecha. Es el valor por defecto.
● end, el texto se alinea al final de la línea atendiendo al “locale”. Si el texto se escribe de
izquierda a derecha se alinea a la derecha, y si el texto se escribe de derecha a
izquierda se alinea a la izquierda.

Podemos dejar un texto alineado a la derecha de la siguiente forma:

ctx.font = '24px serif';


ctx.textAlign = 'right';
ctx.fillText("Esto es texto alineado a la derecha",400,50);

Al utilizar la posición el el método filltext(), esta será el inicio para el alineado a la derecha.
Línea base del texto
Para establecer la línea base del texto tenemos la propiedad textBaseline. En este caso la
sintaxis será:

ctx.textBaseline = "top" || "hanging" || "middle" || "alphabetic" ||


"ideographic" || "bottom";

Los valores que puede tomar la propiedad textBaseline son:

● top,
● hanging,
● middle,
● alphabetic,
● ideographic,
● bottom,
Modo Offline
Aunque a los inicios todo agente de usuario que estuviese en Internet se suponía que iba a estar
constantemente conectado a la red, el paso del tiempo nos ha demostrado que en ciertas
circustancias el agente de usuario estará desconectado y por lo tanto en modo offline.

La idea es que aunque el agente de usuario esté offline consigamos darle una misma
experiencia de usuario que en online o al menos que afecte lo menos posible. Por ejemplo, si el
usuario está realizando acciones, estas pueden ser encoladas para ser tratadas posteriormente
o podemos recurrir a elementos que estén almacenados en el cliente para poder dar una
respuesta.

Es por ello que en HTML5 aparece la capacidad de detectar si el usuario está online u offline
para gestionar las expectativas del mismo.

Así tenemos un API en HTML5 que nos indica cuando un usuario pasa a estar offline y cuando
el usuario vuelve a estar online.

Propiedad onLine
La propiedad que indica si el usuario está online u offline es navigator.onLine dónde
devolverá true si el usuario está online y false si el usuario está offline.

Así que simplemente tendremos que consultar el valor de la propiedad:

if (navigator.onLine) {
console.log("El usuario está online");
}
else
{
console.log("El usuario está offline");
}

Eventos Offline
Cómo el usuario puede cambiar de estado, es decir, en cualquier momento de tiempo y por
múltiples circustancias el usuario puede pasar de estar online a estar offline y viceversa. Bien
porque haya perdido la conexión, por que el usuario lo fuerce,…

Para estas situaciones en HTML5 disponemos de dos eventos sobre el elemento window. Estos
son el evento online cuando el usuario pass a estar online y offline cuando el usuario pasa
a estar offline.

Así que deberemos de controlar dichos eventos para poder gestionar de forma correcta el modo
offline. Para ello nos valemos del método addEventListener y así gestionar dichos eventos.
window.addEventListener("online", function(event){
console.log(event.type);
console.log("El usuario pasa a esta online");
},false);

window.addEventListener("offline", function(e){
console.log(event.type);
console.log("El usuario pasa a esta offline");
},false);

WebStorage
El API WebStorage nos permite almacenar elementos clave/valor de una forma sencilla en la
memoria del navegador y que estos elementos estén disponibles a lo largo de la sesión de un
usuario. Esto nos evita la necesidad de utilizar cookies.

Tenemos dos tipos de almacenamiento en los navegadores:

● sessionStorage
● localStorage

sessionStorage
Mantiene un área de almacenamiento para cada uno de los sites mientras dure la sesión del
navegador. Es decir, mientras el navegador permanezca abierto. El objeto que lo maneja es
window.sessionStorage.

localStorage
Funciona igual que el sessionStorage pero con la diferencia de que los datos persisten incluso
después de cerrar el navegador. El objeto que lo maneja es window.localStorage.

Objeto Storage
Cuando invocamos a cualquiera de los dos tipos de almacenamiento lo que se crea es un objeto
Storage. Sobre el objeto Storage es dónde podremos almacenar, recuperar o borrar los
elementos de la caché.

Con el objeto Storage podemos hacer múltiples operaciones que vemos a continuación:

Tamaño de la Storage
Si queremos saber cuál es el tamaño del almacenamiento, es decir, cuántos valores hay
almacenados, lo que tenemos es que trabaja con la variable .length. Esta variable nos
devuelve un número con el tamaño.

console.log("Tamaño Storage:" + localStorage.length);

Añadir un elemento al Storage


Para añadir un elemento al Storage utilizamos el método setItem(). El método setItem()
recibe dos parámetros, por un lado el nombre de la clave y por otro al valor que queremos
asociar a la clave.

localStorage.setItem('clave','valor');

De esta forma podemos crear algunas claves:

localStorage.setItem('color','rojo');
localStorage.setItem('ancho',12);

Recuperar un elemento al Storage


Una vez que tengamos claves en nuestra Storage podremos recuperar sus valores mediante el
nombre de la clave utilizando el método getItem.

localStorage.getItem('clave');
Así, si queremos recuperar las claves almacenadas anteriormente podemos hacerlo de la
siguiente forma:

console.log(localStorage.getItem('color'));
console.log(localStorage.getItem('ancho'));

Eliminar un elemento al Storage


Todo elemento almacenado en la Storage puede ser eliminado de la misma utilizando el
método removeItem recibiendo el nombre de la clave como parámetro.

localStorage.removeItem('clave');

Vamos a eliminar la variable ‘color’ que habíamos creado anteriomente de la siguiente manera:

localStorage.removeItem('color');

Vaciar la Storage
Si queremos ser más drásticos y lo que queremos es eliminar todo el contenido de la Storage
recurriremos al método clear. El método clear elimina todo el contenido que exista en la
Storage.

localStorage.clear();

Claves de los elementos de la Storage


Si desconocemos los nombres de las claves que se han insertado en la Storage lo que
haremos será recurrir al método key() que nos devuelve el nombre de la clave de la posición
pasada como parámetro.

localStorage.key(numero);

Podemos recuperar la clave que está en la segunda posición de la siguiente forma:


localStorage.key(1);

O podemos recuperar todas las claves y valores:


for (var x=0; x<localStorage.length;x++) {
console.log(localStorage.key(x) + "=" +
localStorage.getItem(localStorage.key(x)));
}

El funcionamiento con sessionStorage es exactamente el mismo ya que de


igual manera utiliza un objeto Storage. Así que puedes cambiar el valor
localStorage por sessionStorage y funciona igual.

StorageEvent
Cuando se produce un cambio en la Storage tenemos la capacidad de avisar a otros
documentos del dominio mediante el StorageEvent. Este evento es lanzado cada vez que hay
un cambio en el Storage y es gestionado por otros documentos diferentes a dónde se produce
el cambio.

Podemos controlar el evento StorageEvent de la siguiente forma:

window.addEventListener('storage', function(e){
...
}, false);

Los atributos que recibiremos en el evento y a los que tendremos acceso son:

key
Es una cadena con el nombre de la clave del Storage que ha cambiado.

newValue
Es una cadena con el valor nuevo que se le ha asignado a la clave.

oldValue
Es una cadena con el valor original que tenía la clave.

url
Es una URI con la localización del documento que ha efectuado el cambio.

storageArea
El un objeto DOM que representa el valor que ha sido modificado.

De esta manera podemos capturar toda la informacion de un StorageEvent de la siguiente


forma:

window.addEventListener('storage', function(e){
console.log(e.key);
console.log(e.oldValue);
console.log(e.newValue);
console.log(e.url);
console.log(JSON.stringify(e.storageArea));
}, false);
Introducción a IndexedDB
IndexedDB es un API de bajo nivel para poder almacenar datos estructurados en la parte del
cliente. Estos datos pueden ser también ficheros o blobs. IndexedDB utiliza índices para poder
realizar búsquedas de alto rendimiento.

Aunque existen otros mecanismos de almacenamiento en el cliente, como pueden ser las
Cookies o la API WebStorage estos presentan unas limitaciones de tamaño, unos 4kb en las
Cookies y hasta los 10Mb en la API WebStorage. Sin embargo la base de datos IndexedDB
nos permite almacenar cantidades mayores de datos, llegando en algunas implementaciones a
los 250Mb.

Características de IndexedDB
Las principales características que definen a IndexedDB son:

Almacena pares clave/valor


IndexedDB es un almacén de objetos, es decir que podemos almacenar cualquier tipo de objeto
dentro de la base de datos. Si bien cada objeto tiene asociada una clave que lo identificará de
una forma única. A dicha clave va asociado el valor que es el objeto en sí.

Es Asíncrona
Para no penalizar el rendimiento del cliente, la base de datos IndexedDB funciona de forma
asíncrona. Esto nos permite almacenar grandes cantidades de datos sin que estemos
penalizando a la respuesta de renderizado del navegador. Cuando veamos el API de
IndexedDB veremos que las respuestas de sus métodos son asíncronas. Si bien podemos
encontrar algunas implementaciones de IndexedDB utilizando promesas.

Soporta Transacciones
Las operaciones que realicemos sobre IndexedDB se realizan mediante transacciones
(incluidas las lecturas). Es decir, podremos deshacer ciertas operaciones en el caso de que se
produzca un fallo dentro de la transacción.

Restricción de Dominio
Una base de datos IndexedDB solo pertenece a un dominio, es por ello que solo podremos
acceder al contenido de la información que alberga cuando lo operemos desde el dominio al que
corresponde. De esta manera mantenemos la seguridad de los datos almacenados.

Gran Capacidad de Almacenamiento


Ya hemos visto que IndexedDB viene a paliar los límites de almacenamiento que aparecen en
las Cookies o en la API WebStorage, llegando a poder almacenar hasta 250Mb.
Soporte Almacenamiento Binario
Dentro de IndexedDB podemos almacenar contenido binario como un ArrayBuffer de objetos u
objetos Blob.

Conceptos Básicos
Cuando vayamos a manejar una base de datos IndexedDB debemos de manejar una serie de
conceptos u elementos básicos de la misma:

● Base de Datos: IDBDatabase


● Almacén de Objetos: IDBObjectStore
● Índices: IDBIndex
● Transacciones: IDBTransaction
● Consultas: IDBRequest
● Punteros o Cursores: IDBCursor
● Rango de Clave: IDBKeyRange

Base de Datos: IDBDatabase


La base de datos se representa mediante un objeto IDBDatabase. Por cada dominio podremos
crear tantas bases de datos como queramos.

La base de datos se identifica por un nombre de base de datos y una versión. Solo puede existir
una única versión a la vez. Es por ello que si queremos cambiar de versión deberemos de
realizar una migración de los datos de la versión actual.

Almacén de Objetos: IDBObjectStore


El almacén de objetos, representado por el objeto IDBObjectStore es el conjunto de datos
relativos a un concepto. Sería similar a una tabla dentro de una base de datos relacional.

Dentro del almacén de objetos encontraremos los datos. Cada uno de los datos es un registro.
Lo que caracteriza a cada registro es que tiene una clave asociada.

Índices: IDBIndex
Los índices nos permiten optimizar las búsquedas dentro de IndexedDB. La base de datos se
mantendrá ordenada por los índices que definamos. El objeto IDBIndex nos ayuda a definir los
índices.

Es importante definir los índices mediante IDBIndex ya que será necesario para poder realizar
búsquedas con filtros.

Transacciones: IDBTransaction
Como hemos comentado el acceso de lectura y escritura sobre la base de datos se hace
mediante transacciones. El objeto que representa una transacción es IDBTransaction. La
transacción nos ofrecerá métodos error, abort y complete para poder gestionar el resultado
de la transacción.

Consultas: IDBRequest
Las consultas que realicemos sobre la base de datos IndexedDB las vamos a gestionar
mediante un objeto IDBRequest. Tendremos un evento onsuccess que nos avisará cuando la
consulta haya sido satisfactoria.

Punteros o Cursores: IDBCursor


En el caso de que la consulta sobre la base de datos IndexedDB devuelva un conjunto múltiples
de datos deberemos de manejar un cursor (o puntero) para poder recorrer el conjunto de objetos
devueltos como respuesta. El objeto que nos ayuda a manejar los cursores es IDBCursor.

Rango de Clave: IDBKeyRange


Si queremos gestionar un subconjuto de los elementos almacenados deberemos de apoyarnos
en los índices, en concreto en el elemento IDBKeyRange. El elemento IDBKeyRange nos ayuda
a establecer filtros sobre los datos para que el contenido devuelto solo corresponda a un rango.

API Fullscreen
El API Fullscreen nos permite que un elemento del DOM (y sus descendientes) puedan ser
representados a pantalla completa. Lo que permite es visualizar la página eliminando cualquier
elemento del navegador (menús, pestañas,…). Con ello podremos poner desde el propio
documento a pantalla completa, elementos de vídeo, imágenes,…

Métodos Fullscreen API


Lo primero que tenemos que conocer son los métodos que nos permite manejar el API
Fullscreen. Los métodos que nos permiten visualizar un elemento a pantalla completa son:

● Document.exitFullscreen()
● Element.requestFullscreen()

requestFullscreen()
Solicita al agente de usuario (que normalmente será el navegador) el poder visualizar un
elemento a pantalla completa. El método Element.requestFullscreen devolverá una
promesa o Promise que será resuelta una vez que se activa el modo pantalla completa.

exitFullscreen()
Solicita al agente de usuario el salir del modo de visualización a pantalla completa para volver a
una visualización normal. El método Document.exitFullscreen devolverá una promesa o
Promise que será resuelta una vez que el modo pantalla completa se ha deshabilitado.

Poner el documento a pantalla completa


Una vez que conocemos los métodos que nos permiten manejar la pantalla completa del API
Fullscreen vamos a ver cómo podemos poner un documento y un elemento a pantalla
completa.

Lo que vamos a crear es una función sobre la que apoyarnos y lanzar la pantalla compelta:

function getFullscreen(element){
if(element.requestFullscreen) {
element.requestFullscreen();
} else if(element.mozRequestFullScreen) {
element.mozRequestFullScreen();
} else if(element.webkitRequestFullscreen) {
element.webkitRequestFullscreen();
} else if(element.msRequestFullscreen) {
element.msRequestFullscreen();
}
}

Vemos que lo primero que hacemos es comprobar si el elemento sobre el que queremos poner
la pantalla completa soporta esta capacidad. Esta información nos la da la propiedd
requestFullscreen. En el caso de que si que se soporte nos valdrá con invocar al método
requestFullscreen sobre el elemento. En ste caso nos apoyamos en los hacks de los
diferentes navegadores.

Ahora simplemente tendremos que llamar a nuestro método getFullscreen pasándole el


elemento que representa el documento completo document.documentElement.

getFullscreen(document.documentElement);

Elemento en pantalla completa


Ahora que hemos visto cómo poner el documento a pantalla completa, vamos a pasar a realizar
la misma acción con un elemento. En este caso nos vamos a apoyar en un elemento vídeo para
enseñar cómo podemos poner un elemento en pantalla completa. Lo primero que haremos será
crear el elemento vídeo en nuestra página:
<video id="mivideo" src="ejemplo-video.ogv" controls>
Tu navegador no soporta el elemento <code>video</code>.
</video>

Lo siguiente que haremos será invocar al método getFullscreen que hemos definido. Pero en
este caso llamaremos al elemento vídeo. Para poder obtener el elemento vídeo tendremos que
utilizar el método getElementById.

getFullscreen(document.getElementById("mivideo"));

Salir de la pantalla completa


Para poder codificar el salir de una pantalla completa debería de bastar con utilizar el método
exitFullscreen, pero hay que tener en cuenta los diferentes navegadores. Es por ello que es
buena idea tener un método que valide los diferentes métodos.

function exitFullscreen() {
if(document.exitFullscreen) {
document.exitFullscreen();
} else if(document.mozCancelFullScreen) {
document.mozCancelFullScreen();
} else if(document.webkitExitFullscreen) {
document.webkitExitFullscreen();
}
}

Una vez que tengamos este método simplemente tendremos que invocarlo para salir de la
pantalla completa.

exitFullscreen();

Propiedades Fullscreen API


Para poder manejar el API Fullscreen disponemos de dos propiedades:

● DocumentOrShadowRoot.fullscreenElement
● Document.fullscreenEnabled
fullscreenElement
La propiedad fullscreenElement nos indica qué elemento del DOM o del “shadow DOM” está
siendo mostrado en pantalla completa.

fullscreenEnabled
Mediante la propiedad fullscreenEnabled nos indica si podemos activar el modo de pantalla
completa, lo cual nos devolvería el valor true o por si el contrario no está disponible el modo de
pantalla completa. En este segundo caso el valor de la propiedad será false.

Saber si la pantalla completa está activa


Jugando con las propiedades fullscreenEnabled y fullscreenElement podemos comprobar
si tenemos al agente de usuario mostrándose en pantalla completa y además podemos saber
qué elemento es el que se está mostrando a pantalla completa.

var fullscreenElement = document.fullscreenElement ||


document.mozFullScreenElement || document.webkitFullscreenElement;
var fullscreenEnabled = document.fullscreenEnabled ||
document.mozFullScreenEnabled || document.webkitFullscreenEnabled;

console.log('enabled:' + fullscreenEnabled);
console.log('element:' + fullscreenElement);

De igual manera que en los casos anteriores tenemos que apoyarnos en los hacks que tienen
los diferentes navegadores para poder evaluar el contenido de las propiedades.

Eventos Fullscreen API


Junto a las propiedades y método del Fullscreen API tendremos la gestión de eventos. Esta
gestión de eventos nos ayudará a saber cuando ha existido un cambio hacía o desde la pantalla
completa o bien cuándo se ha producido un error en la gestión de la pantalla completa.

Los eventos que podemos manejar son:

● Document.onfullscreenchange
● Document.onfullscreenerror
● Element.onfullscreenchange
● Element.onfullscreenerror

Podemos ver que los eventos pueden ser aplicados a un elemento en completo o a todo el
documento. Todo dependiendo sobre qué estemos gestionando la pantalla completa.

onfullscreenchange
Un evento es enviado bien a un documento (o Document) o a un elemento (Element),
dependiendo de lo que estemos intentando mostrar a pantalla completa, ya sea un elemento en
concreto o tdoda la página o documento.

onfullscreenerror
Un evento de error es enviado al docunento o elemento que intentó mostrarse en pantalla
completa o salir de ella.

Controlar el paso a pantalla completa


Ya hemos visto como podemos ayudar al usuario a poner un documento o elementos a pantalla
completa. Pero, ¿qué sucede si es el propio usuario el que pone el agente de usuario a pantalla
completa?. ¿Cómo podemos aprovecharnos de saber que está visualizando el contenido de esa
forma?

En este caso lo que tenemos que hacer es controlar el evento onfullscreenchange. Para ello
vamos a registrar un listener que lo controle.

document.addEventListener("fullscreenchange",cambioPantalla,false);
document.addEventListener("webkitfullscreenchange",cambioPantalla,false);
document.addEventListener("mozfullscreenchange",cambioPantalla,false);
document.addEventListener("MSFullscreenchange",cambioPantalla,false);

Hemos puesto todos los hacks del evento onfullscreenchange y les hemos enviado a la
función cambioPantalla.

function cambioPantalla(event){
console.log("Cambio en Pantalla Completa " + Date.now());
}

Diccionarios Fullscreen API


El API Fullscreenc cuenta con un diccionario FullscreenOptions. Este diccionario se le puede
enviar al método Element.requestFullscreen para especificar propiedades adicionales.

Soporte Multi-Navegador del Fullscreen API


En este artículo hemos visto como manejar los métodos que define el estándar del API
Fullscreen, si bien el soporte puede variar por cada uno de los navegadores web y es por ello
que tendremos que apoyarnos en el hack de cada navegador.

De est forma tendrás que tener en cuenta los siguientes:


● .mozRequestFullScreen()
● .webkitRequestFullscreen()
● .msRequestFullscreen();

Más ejemplos del API Fullscreen


Puedes revisar más artículos sobre el Fullscreen API en Línea de Código.

History API
Aunque ya llevaba tiempo el objeto history dentro del DOM de los documentos HTML, la
llegada de HTML5 refuerza su uso y le incluye nuevos métodos para poder manipularlo.

Pero vayamos viendo poco a poco qué es el History API y como podemos manipular el historial
de navegación mediante el objeto history.

Operaciones Básicas History API


Lo primero que tenemos que saber es que el historial de navegación es una lista de páginas
sobre la que nos podemos mover. Esta lista está compuesta por las últimas páginas web que
hayamos visitado.

Por lo tanto, podemos movernos por ella hacia delante, hacía atrás o a un punto en concreto.
Siempre teniendo en cuenta que partiremos en la última posición de la lista.

Moverse por el historial


Si querermos movernos por el History API de forma sencilla vamos a tener dos métodos:
back() y forward().

Mediante el método back() vamos a movernos hacía atrás en el historial. Bastará con escribir:

window.history.back();

Para poder ir a la última página que visitó el usuario con el navegador. Es el mismo efecto que si
el usuario pulsase sobre el botón de atrás.

En el caso de que queramos ir adelante en el hitorial deberemos de utilizar forward(). En este


caso deberemos de escribir:

window.history.forward();
Para poder ir a la siguiente página que visitó el usuario. Es el mismo efecto que si el usuario
pulsase sobre el botón de adelante en el navegador.

Ir a una posición concreta del historial


Si no queremos hacer movimiento lineales sobre el historial podemos hacer un movimiento a un
punto en concreto del historial. En este caso deberemos de apoyarnos en el método go(). El
método go() recibe como parámetro la posicines sobre las que nos queremos mover. Es decir,
si el número es positivo nos moveremos tantas posiciones adelante como indique el método y si
es negativo nos moveremos tantas posiciones atrás como indique el número (en positivo) del
método.

La sintaxis del método go() es:

window.history.go(numero);

Así podemos movernos dos posiciones adelante de la actual:

window.history.go(2);

O, por ejemplo, movernos tres posiciones hacía atrás de la posición actual:

window.history.go(-3);

De esta forma hay una similitu de métodos entre:

window.history.go(1); // window.history.forward();
window.history.go(-1); // window.history.back();

Número de elementos del historial


Una cosa importante a la hora de movernos por el historial mediante el History API es saber
cuántos elementos hay almacenados en el historial. Esto lo obtendremos mediante la propiedad
.length:

window.history.length;
Gestionar Estados History API
Cuando se pensó inicialmente el objeto history se trabajaba con la hipótesis de que cada
nueva navegación, y por lo tanto carga de página, iba a suponer un nuevo estado dentro del
historial. Pero con la aparición de las técnicas AJAX (Asynchronous Javascript and XML)
llegaron las cargas parciales de las páginas o las modificaciones de los elementos del DOM
para proporcionar una experiencia más rica de visualización al usuario.

Es decir, el usuario estaba navegando, pero su historial de navgeación no cambiaba. Por lo cual,
si el usuario, habituado a manipular los botones del navegador, realizaba alguna navegación,
alteraba por completo la navegación de la aplicación que usaba patrones AJAX.

Es por ello que en HTML5 se incrementan las funcionalidades del History API y se añade la
gestión de estados. De esta forma, cuando se produce una navegación dentro de una aplicación
AJAX podemos introducir un nuevo estado dentro del historial y así paliar los efectos colaterales
que se producen al navegar por el historial.

Estas capacidades de gestión de estados en el History API junto con la gestión de los anclas o
hash (#) en la URL de la página, permitía que se hiciera una gestión de navegación en
aplicaciones AJAX satisfactoria.

Si queremos saber información del estado en el que se encuentra el historial nos bastará con
escribir:

console.log(JSON.stringify(history.state));

Modificar entradas en el historial


Si queremos modificar los estados dentro del History API tenemos dos métodos: pushState()
para incluir un nuevo estado y replaceState() para reemplazar un estado ya existente.

pushState()
El método que nos permite añadir un nuevo estado es pushState(). La estructura de
pushState() es la siguiente:

history.pushState(objeto_estado, titulo, url);

Dónde objeto_estado es un objeto Javascript que representa la información del estado que
queremos guardar. Cuando navegemos hacía este estado, el evento que gestiona un cambio en
el historial disponibilizará esta información. Así en este objeto deberemos de guardar todo
aquello que necesitemos para poder recuperar mediante técnicas AJAX la representación visual
asociada al estado.
Algunos navegadores tiene la limitación de 640Kb de serialización de los objetos que
deberemos de tener en cuenta.

El atributo titulo representa el título asociado al estado. Y por último, el atributo URL es la url
que se insertará en el hsitorial de navegación, por lo tanto debe de existir dicha URL y puede
expresarse de forma relativa o absoluta. Es importante saber que el navegador no cargará la
URL cuando ejecutemos un pushState().

Así, podemos crear un nuevo estado con el History API de la siguiente forma:

history.pushState({ pagina: "1" }, "Título 1", "state.html#p1");

Vemos que tenemos un objeto Javascript en el que solo hemos guardado una propiedad, pero
sobre el que podríamos guardar toda la información que se necesite:

{ pagina: "1" }

replaceState()
Otro método que tenemos para modificar los estados del historial es replaceState().
Mediante el método replaceState() podremos modificar la información asociada al estado
actual que tengamos en el historial.

La estructura del método replaceState() es:

history.replaceState(objeto_estado, título, URL);

Dónde objeto_estado es el nuevo estado a aplicar, título el nuevo título a aplicar y url la nueva
URL.

Así, podríamos cambiar el estado actual ejecutando el método replaceState() de la siguiente


forma:

history.replaceState({ pagina: "2" }, "Título 2", "state.html#p2");

Gestionar eventos sobre el historial


Lo último que tenemos que saber en la gestión de estados dentro del History API es que
cuando el usuario navega por el historial, ya sea mediante los métodos bakc(), forward(),
go() o con los botones del navegador, se genera un evento onpopstate.

Controlando el evento onpopstate podremos realizar las acciones sobre el estado en el que
está el navegador. Ya que dicho evento llevará asociado el estado como valor.

Podemos controlar el evento onpopstate de la siguiente forma:


window.onpopstate = function(event) {};

Así si, por ejemplo, queremos volvar el contenido del estado que se ha quedado al navegar
escribiremos lo siguiente:

window.onpopstate = function(event) {
console.log(JSON.stringify(event.state));
};

También podría gustarte