Codelab de funciones web

1. Introducción y configuración

Funciones web

Queremos cerrar la brecha de capacidades entre la Web y los anuncios nativos, y facilitar a los desarrolladores la creación de experiencias excelentes en la Web abierta. Creemos firmemente que cada desarrollador debería tener acceso a las funciones que necesita para crear una experiencia web excelente y estamos comprometidos con una Web más capaz.

Sin embargo, hay algunas capacidades, como el acceso al sistema de archivos y la detección de inactividad, que están disponibles para los anuncios nativos, pero no en la Web. Estas capacidades faltantes significan que algunos tipos de apps no se pueden publicar en la Web o son menos útiles.

Diseñaremos y desarrollaremos estas nuevas funciones de una manera abierta y transparente mediante los procesos estándares existentes de la plataforma web abierta y, al mismo tiempo, recibiremos comentarios anticipados de los desarrolladores y otros proveedores de navegadores a medida que iteramos en el diseño, a fin de garantizar un diseño interoperable.

Qué compilarás

En este codelab, probarás varias APIs web que son nuevas o que solo están disponibles detrás de una marca. Por lo tanto, este codelab se enfoca en las APIs y en los casos de uso que estas APIs desbloquean, más que en la compilación de un producto final específico.

Qué aprenderás

En este codelab, aprenderás la mecánica básica de varias APIs de última generación. Ten en cuenta que esta mecánica aún no es definitiva y apreciamos mucho tus comentarios sobre el flujo de desarrollo.

Requisitos

Como las APIs que se presentan en este codelab están a la vanguardia, los requisitos de cada API varían. Asegúrate de leer atentamente la información de compatibilidad al principio de cada sección.

Cómo abordar el codelab

El codelab no está diseñado para que se ejecute de manera secuencial. Cada sección representa una API independiente, así que no dudes en elegir lo que más te interesa.

2. API de Badging

El objetivo de la API de Badging es llevar la seguridad atención a lo que sucede en segundo plano. Para simplificar la demostración de este codelab, usemos la API para acercar la experiencia atención a algo que sucede en primer plano. Luego, puedes hacer la transferencia mental a lo que sucede en segundo plano.

Instala Airhorner

Para que esta API funcione, necesitas una AWP que esté instalada en la pantalla principal, por lo que el primer paso es instalar una AWP, como la infame y famosa airhorner.com. Presiona el botón Install ubicado en la esquina superior derecha o usa el menú de tres puntos para realizar la instalación de forma manual.

8b7fa8b3c94c6bdd.png

Aparecerá un mensaje de confirmación, haz clic en Instalar.

98e90422167ac786.png

Ahora tienes un nuevo ícono en el Dock de tu sistema operativo. Haz clic en él para iniciar la AWP. Tendrá su propia ventana de app y se ejecutará en modo independiente.

Cómo configurar una insignia

Ahora que tienes una AWP instalada, necesitarás algunos datos numéricos (las insignias solo pueden contener números) para que se muestren en ellas. Una cosa sencilla para contar en The Air Horner es, suspira, la cantidad de veces que se le emite una cuernos. En realidad, con la app Airhorner instalada, intenta hacer sonar la bocina y verifica la insignia. Cuenta uno cada vez que tocas la bocina.

b5e39de7a1775054.png

¿Cómo funciona? Básicamente, el código es el siguiente:

let hornCounter = 0;
const horn = document.querySelector('.horn');
horn.addEventListener('click', () => {
  navigator.setExperimentalAppBadge(++hornCounter);
});

Si tocas la bocina un par de veces y comprueba el ícono de la AWP, se actualizará cada vez. único. tiempo. suena la bocina. Así de fácil.

eed10c3ffe59999.png

Cómo borrar una insignia

El contador sube a 99 y, luego, vuelve a empezar. También puedes restablecerlo de forma manual. Abre la pestaña de la consola de Herramientas para desarrolladores, pega la siguiente línea y presiona Intro.

navigator.setExperimentalAppBadge(0);

Como alternativa, también puedes deshacerte de la insignia borrando la insignia de forma explícita, como se muestra en el siguiente fragmento. El ícono de la AWP debería volver a verse al principio, claro y sin insignia.

navigator.clearExperimentalAppBadge();

33eafb314a3a9f30.png

Comentarios

¿Qué te pareció esta API? Responde esta encuesta brevemente para ayudarnos:

¿El uso de esta API fue intuitivo?

No

¿Pudiste ejecutar el ejemplo?

No .

¿Tienes algo que decir? ¿Faltaban funciones? Envía comentarios rápidos en esta encuesta. ¡Gracias!

3. API de Native File System

La API de Native File System permite que los desarrolladores compilen aplicaciones web poderosas que interactúan con los archivos en el dispositivo local del usuario. Después de que un usuario otorga acceso a una app web, esta API permite que las apps web lean o guarden cambios directamente en archivos y carpetas del dispositivo del usuario.

Cómo leer un archivo

La frase "Hello, World" de la API del sistema de archivos nativos es leer un archivo local y obtener su contenido. Crea un archivo .txt sin formato y, luego, ingresa texto. Luego, navega a cualquier sitio seguro (es decir, un sitio entregado a través de HTTPS), como example.com, y abre la consola de Herramientas para desarrolladores. Pega el siguiente fragmento de código en la consola. Debido a que la API de Native File System requiere un gesto del usuario, adjuntamos un controlador de doble clic en el documento. Más adelante, necesitaremos el controlador del archivo, así que solo lo haremos una variable global.

document.ondblclick = async () => {
  window.handle = await window.chooseFileSystemEntries();
  const file = await handle.getFile();
  document.body.textContent = await file.text();
};

c02679081eb4d538.png

Cuando haces doble clic en cualquier parte de la página example.com, aparece un selector de archivos.

d98962600d62d149.png

Selecciona el archivo .txt que creaste antes. El contenido del archivo reemplazará el contenido real de body de example.com.

eace3d15bd4f8192.png

Cómo guardar un archivo

A continuación, queremos hacer algunos cambios. Por lo tanto, hagamos que body se pueda editar pegando el siguiente fragmento de código. Ahora, puedes editar el texto como si el navegador fuera un editor de texto.

document.body.contentEditable = true;

ca32797417449343.png

Ahora, queremos volver a escribir estos cambios en el archivo original. Por lo tanto, necesitamos un escritor en el controlador del archivo, que podemos obtener pegando el siguiente fragmento en la consola. Nuevamente, necesitamos un gesto del usuario, así que esta vez esperamos un clic en el documento principal.

document.onclick = async () => {
  const writer = await handle.createWriter();
  await writer.truncate(0);
  await writer.write(0, document.body.textContent);
  await writer.close();
};

d2729a8f76f43073.png

Cuando hagas clic (no doble clic) en el documento, aparecerá un mensaje de permiso. Cuando otorgues permiso, el contenido del archivo será el que hayas editado antes en body. Para verificar los cambios, abre el archivo en otro editor (o vuelve a iniciar el proceso haciendo doble clic en el documento y abriéndolo de nuevo).

2eccf61fe4a46109.png

202263abdedae737.png

¡Felicitaciones! Acabas de crear el editor de texto más pequeño del mundo, [citation needed].

Comentarios

¿Qué te pareció esta API? Responde esta encuesta brevemente para ayudarnos:

¿El uso de esta API fue intuitivo?

No

¿Pudiste ejecutar el ejemplo?

No .

¿Tienes algo que decir? ¿Faltaban funciones? Envía comentarios rápidos en esta encuesta. ¡Gracias!

4. API de Shape Detection

La API de Shape Detection proporciona acceso a detectores de formas acelerados (p.ej., para rostros humanos) y funciona en imágenes estáticas o feeds de imágenes en vivo. Los sistemas operativos tienen detectores de funciones de alto rendimiento y altamente optimizados, como FaceDetector de Android. La API de Shape Detection abre estas implementaciones nativas y las expone a través de un conjunto de interfaces de JavaScript.

Actualmente, las funciones compatibles son la detección de rostro a través de la interfaz FaceDetector, la detección de códigos de barras a través de la interfaz BarcodeDetector y la detección de texto (reconocimiento óptico de caracteres) a través de la interfaz TextDetector.

Detección de rostro

Una característica fascinante de la API de Shape Detection es la detección de rostros. Para probarlo, necesitamos una página con rostros. Esta página con el rostro del autor es un buen comienzo. Se verá como en la siguiente captura de pantalla. En un navegador compatible, se reconocerán el cuadro de límite del rostro y los puntos de referencia del rostro.

Para ver qué tan poco código se requería para que esto sucediera, remezcla o edita el proyecto de Glitch, especialmente el archivo script.js.

f4aa7b77a0a1d1f5.png

Si quieres ser completamente dinámico y no solo trabajar con el rostro del autor, ve a esta página de resultados de la Búsqueda de Google llena de rostros en una pestaña privada o en el modo de invitado. En esa página, abre las Herramientas para desarrolladores de Chrome. Para ello, haz clic con el botón derecho en cualquier lugar y, luego, selecciona Inspeccionar. Luego, en la pestaña Consola, pega el fragmento que aparece a continuación. El código destacará los rostros detectados con un cuadro rojo semitransparente.

document.querySelectorAll('img[alt]:not([alt=""])').forEach(async (img) => {
  try {
    const faces = await new FaceDetector().detect(img);
    faces.forEach(face => {
      const div = document.createElement('div');
      const box = face.boundingBox;
      const computedStyle = getComputedStyle(img);
      const [top, right, bottom, left] = [
        computedStyle.marginTop,
        computedStyle.marginRight,
        computedStyle.marginBottom,
        computedStyle.marginLeft
      ].map(m => parseInt(m, 10));
      const scaleX = img.width / img.naturalWidth;
      const scaleY = img.height / img.naturalHeight;
      div.style.backgroundColor = 'rgba(255, 0, 0, 0.5)';
      div.style.position = 'absolute';
      div.style.top = `${scaleY * box.top + top}px`;
      div.style.left = `${scaleX * box.left + left}px`;
      div.style.width = `${scaleX * box.width}px`;
      div.style.height = `${scaleY * box.height}px`;
      img.before(div);
    });
  } catch(e) {
    console.error(e);
  }
});

Notarás que hay algunos mensajes de DOMException y que no se procesan todas las imágenes. Esto se debe a que las imágenes de la mitad superior de la página se intercalan como URI de datos y, por lo tanto, es posible acceder a ellas, mientras que las imágenes de la mitad inferior de la página provienen de un dominio diferente que no está configurado para admitir CORS. No debemos preocuparnos por esta demostración.

Detección de puntos de referencia faciales

Además de los rostros, en sí, macOS también admite la detección de puntos de referencia faciales. Para probar la detección de puntos de referencia faciales, pega el siguiente fragmento en la consola. Recordatorio: La alineación de los puntos de referencia no es perfecta debido a crbug.com/914348, pero puedes ver hacia dónde se dirige esto y lo potente que puede ser esta función.

document.querySelectorAll('img[alt]:not([alt=""])').forEach(async (img) => {
  try {
    const faces = await new FaceDetector().detect(img);
    faces.forEach(face => {
      const div = document.createElement('div');
      const box = face.boundingBox;
      const computedStyle = getComputedStyle(img);
      const [top, right, bottom, left] = [
        computedStyle.marginTop,
        computedStyle.marginRight,
        computedStyle.marginBottom,
        computedStyle.marginLeft
      ].map(m => parseInt(m, 10));
      const scaleX = img.width / img.naturalWidth;
      const scaleY = img.height / img.naturalHeight;
      div.style.backgroundColor = 'rgba(255, 0, 0, 0.5)';
      div.style.position = 'absolute';
      div.style.top = `${scaleY * box.top + top}px`;
      div.style.left = `${scaleX * box.left + left}px`;
      div.style.width = `${scaleX * box.width}px`;
      div.style.height = `${scaleY * box.height}px`;
      img.before(div);

      const landmarkSVG = document.createElementNS('http://www.w3.org/2000/svg', 'svg');
      landmarkSVG.style.position = 'absolute';
      landmarkSVG.classList.add('landmarks');
      landmarkSVG.setAttribute('viewBox', `0 0 ${img.width} ${img.height}`);
      landmarkSVG.style.width = `${img.width}px`;
      landmarkSVG.style.height = `${img.height}px`;
      face.landmarks.map((landmark) => {                    
        landmarkSVG.innerHTML += `<polygon class="landmark-${landmark.type}" points="${
        landmark.locations.map((point) => {          
          return `${scaleX * point.x},${scaleY * point.y} `;
        }).join(' ')
      }" /></svg>`;          
      });
      div.before(landmarkSVG);
    });
  } catch(e) {
    console.error(e);
  }
});

Detección de códigos de barras

La segunda función de la API de Shape Detection es la detección de códigos de barras. Al igual que antes, necesitamos una página con códigos de barras, como esta. Cuando lo abras en un navegador, verás los distintos códigos QR descifrados. Haz un remix o edita el proyecto de Glitch, especialmente el archivo script.js, para ver cómo se hace.

7778003ff472389b.png

Si quieres algo más dinámico, podemos volver a usar la Búsqueda de imágenes de Google. Esta vez, ve a esta página de resultados de la Búsqueda de Google en el navegador en una pestaña privada o en el modo de invitado. Ahora, pega el siguiente fragmento en la pestaña de la consola de Herramientas para desarrolladores de Chrome. Después de un momento breve, los códigos de barras reconocidos se anotarán con el valor sin procesar y el tipo de código de barras.

document.querySelectorAll('img[alt]:not([alt=""])').forEach(async (img) => {
  try {
    const barcodes = await new BarcodeDetector().detect(img);
    barcodes.forEach(barcode => {
      const div = document.createElement('div');
      const box = barcode.boundingBox;
      const computedStyle = getComputedStyle(img);
      const [top, right, bottom, left] = [
        computedStyle.marginTop,
        computedStyle.marginRight,
        computedStyle.marginBottom,
        computedStyle.marginLeft
      ].map(m => parseInt(m, 10));
      const scaleX = img.width / img.naturalWidth;
      const scaleY = img.height / img.naturalHeight;
      div.style.backgroundColor = 'rgba(255, 255, 255, 0.75)';
      div.style.position = 'absolute';
      div.style.top = `${scaleY * box.top + top}px`;
      div.style.left = `${scaleX * box.left - left}px`;
      div.style.width = `${scaleX * box.width}px`;
      div.style.height = `${scaleY * box.height}px`;
      div.style.color = 'black';
      div.style.fontSize = '14px';      
      div.textContent = `${barcode.rawValue}`;
      img.before(div);
    });
  } catch(e) {
    console.error(e);
  }
});

Detección de texto

La última función de la API de Shape Detection es la detección de texto. A esta altura, ya sabes cómo funciona: necesitamos una página con imágenes que contengan texto, como esta con resultados de escaneo de Google Libros. En los navegadores compatibles, verás el texto reconocido y un cuadro delimitador dibujado alrededor de los pasajes de texto. Haz un remix o edita el proyecto de Glitch, especialmente el archivo script.js, para ver cómo se hace.

ec2be17d1e4d01ba.png

Para probarlo de forma dinámica, ve a esta página de resultados de la Búsqueda en una pestaña privada o en modo de invitado. Ahora, pega el siguiente fragmento en la pestaña de la consola de Herramientas para desarrolladores de Chrome. Con un poco de espera, se reconocerá parte del texto.

document.querySelectorAll('img[alt]:not([alt=""])').forEach(async (img) => {
  try {
    const texts = await new TextDetector().detect(img);
    texts.forEach(text => {
      const div = document.createElement('div');
      const box = text.boundingBox;
      const computedStyle = getComputedStyle(img);
      const [top, right, bottom, left] = [
        computedStyle.marginTop,
        computedStyle.marginRight,
        computedStyle.marginBottom,
        computedStyle.marginLeft
      ].map(m => parseInt(m, 10));
      const scaleX = img.width / img.naturalWidth;
      const scaleY = img.height / img.naturalHeight;
      div.style.backgroundColor = 'rgba(255, 255, 255, 0.75)';
      div.style.position = 'absolute';
      div.style.top = `${scaleY * box.top + top}px`;
      div.style.left = `${scaleX * box.left - left}px`;
      div.style.width = `${scaleX * box.width}px`;
      div.style.height = `${scaleY * box.height}px`;
      div.style.color = 'black';
      div.style.fontSize = '14px';      
      div.innerHTML = text.rawValue;
      img.before(div);
    });
  } catch(e) {
    console.error(e);
  }
});

Comentarios

¿Qué te pareció esta API? Responde esta encuesta brevemente para ayudarnos:

¿El uso de esta API fue intuitivo?

No

¿Pudiste ejecutar el ejemplo?

No .

¿Tienes algo que decir? ¿Faltaban funciones? Envía comentarios rápidos en esta encuesta. ¡Gracias!

5. API de Web Share Target

La API de Web Share Target permite que las apps web instaladas se registren en el sistema operativo subyacente como un objetivo de uso compartido para recibir contenido compartido de la API de Web Share o de eventos del sistema, como el botón para compartir a nivel del sistema operativo.

Cómo instalar una AWP para compartir

Como primer paso, necesitas una AWP con la que puedas compartir contenido. Esta vez, Airhorner (por suerte) no hará el trabajo, pero la app de demostración de Web Share Target te ayudará. Instala la app en la pantalla principal del dispositivo.

925df16a12638bb2.png

Cómo compartir algo con la AWP

A continuación, necesitas algo para compartir, como una foto de Google Fotos. Usa el botón Compartir y selecciona la AWP del libro de recortes como objetivo de uso compartido.

7216e8bb1be6d6db.png

Cuando presiones el ícono de la aplicación, llegarás directamente a la AWP del libro de recortes y la foto aparecerá allí.

9016985cb4bb48fe.png

¿Cómo funciona? Para averiguarlo, explora el manifiesto de la aplicación web de la AWP de Scrapbook. La configuración para que la API de Web Share Target funcione se encuentra en la propiedad "share_target" del manifiesto que, en su campo "action", apunta a una URL decorada con parámetros como se indica en "params".

Luego, el lado del uso compartido propaga esta plantilla de URL según corresponda (ya sea facilitada por una acción de compartir o controlada de manera programática por el desarrollador con la API de Web Share), para que el lado receptor pueda extraer los parámetros y realizar alguna acción con ellos, como mostrarlos.

{
  "action": "/_share-target",
  "enctype": "multipart/form-data",
  "method": "POST",
  "params": {
    "files": [{
      "name": "media",
      "accept": ["audio/*", "image/*", "video/*"]
    }]
  }
}

Comentarios

¿Qué te pareció esta API? Responde esta encuesta brevemente para ayudarnos:

¿El uso de esta API fue intuitivo?

No

¿Pudiste ejecutar el ejemplo?

No .

¿Tienes algo que decir? ¿Faltaban funciones? Envía comentarios rápidos en esta encuesta. ¡Gracias!

6. API de Wake Lock

Para evitar que se agote la batería, la mayoría de los dispositivos se suspenden rápidamente cuando están inactivos. Aunque esto es correcto la mayor parte del tiempo, algunas aplicaciones necesitan mantener la pantalla o el dispositivo activo para completar su trabajo. La API de Wake Lock proporciona una manera de evitar que el dispositivo se atenúe y bloquee la pantalla, o que se suspenda. Esta función habilita nuevas experiencias que, hasta ahora, requerían una app nativa.

Configura un protector de pantalla

Para probar la API de Wake Lock, primero debes asegurarte de que el dispositivo se suspenda. Por lo tanto, en el panel de preferencias de tu sistema operativo, activa el protector de pantalla que prefieras y asegúrate de que se inicie después de 1 minuto. Para asegurarte de que funcione, deja el dispositivo solo durante ese tiempo (por supuesto, es doloroso). Las siguientes capturas de pantalla muestran macOS, pero puedes probar esto en tu dispositivo móvil Android o en cualquier plataforma de escritorio compatible.

6f345e8c2b6c22c.png

Cómo establecer un bloqueo de activación de pantalla

Ahora que sabes que el protector de pantalla funciona, usarás un bloqueo de activación de tipo "screen" para evitar que haga su trabajo. Ve a la app de demo de Wake Lock y haz clic en Activate .

screen Casilla de verificación Wake Lock.

12ed15dd94f51d4d.png

A partir de ese momento, se activará un bloqueo de activación. Si tienes la paciencia necesaria para dejar el dispositivo intacto durante un minuto, verás que el protector de pantalla no se inició.

¿Cómo funciona? Para descubrirlo, ve al proyecto Glitch para la app de demostración de Wake Lock y consulta script.js. La esencia del código se encuentra en el siguiente fragmento. Abre una nueva pestaña (o usa cualquier pestaña que tengas abierta) y pega el siguiente código en una consola de Herramientas para desarrolladores de Chrome. Cuando hagas clic en la ventana, deberías ver un bloqueo de activación activo durante exactamente 10 segundos (consulta los registros de la consola) y el protector de pantalla no debería iniciarse.

if ('wakeLock' in navigator && 'request' in navigator.wakeLock) {  
  let wakeLock = null;
  
  const requestWakeLock = async () => {
    try {
      wakeLock = await navigator.wakeLock.request('screen');
      wakeLock.addEventListener('release', () => {        
        console.log('Wake Lock was released');                    
      });
      console.log('Wake Lock is active');      
    } catch (e) {      
      console.error(`${e.name}, ${e.message}`);
    } 
  };

  requestWakeLock();
  window.setTimeout(() => {
    wakeLock.release();
  }, 10 * 1000);
}

621c2654d06a7cce.png

Comentarios

¿Qué te pareció esta API? Responde esta encuesta brevemente para ayudarnos:

¿El uso de esta API fue intuitivo?

No

¿Pudiste ejecutar el ejemplo?

No .

¿Tienes algo que decir? ¿Faltaban funciones? Envía comentarios rápidos en esta encuesta. ¡Gracias!

7. API de Contact Picker

Una API que nos entusiasma mucho es la API del selector de contactos. Permite que una aplicación web acceda a los contactos desde el administrador de contactos nativo del dispositivo para que la aplicación web tenga acceso a los datos de tus contactos. de correo electrónico y números de teléfono. Puedes especificar si quieres solo uno o varios contactos y si quieres todos los campos o solo un subconjunto de nombres, direcciones de correo electrónico y números de teléfono.

Consideraciones de privacidad

Una vez que se abre el selector, puedes elegir los contactos que deseas compartir. Notarás que no existe la opción y eso es deliberado: queremos que compartir sea una decisión consciente. Del mismo modo, el acceso no es continuo, sino que se trata de una decisión única.

Cómo acceder a los contactos

Acceder a los contactos es una tarea sencilla. Antes de que se abra el selector, puedes especificar los campos que desees (las opciones name, email y telephone) y si deseas acceder a varios o solo a un contacto. Puedes probar esta API en un dispositivo Android si abres la aplicación de demostración. La sección relevante del código fuente es básicamente el siguiente fragmento:

getContactsButton.addEventListener('click', async () => {
  const contacts = await navigator.contacts.select(
      ['name', 'email'],
      {multiple: true});
  if (!contacts.length) {
    // No contacts were selected, or picker couldn't be opened.
    return;
  }
  console.log(contacts);
});

de94db2dfb7c67af.png

8. API de Async Clipboard

Cómo copiar y pegar texto

Hasta ahora, no había forma de copiar y pegar de manera programática las imágenes en el portapapeles del sistema. Recientemente, agregamos compatibilidad con imágenes a la API de Async Clipboard,

para copiar y pegar imágenes. Lo nuevo es que también puedes escribir imágenes en el portapapeles. La API del portapapeles asíncrono permitía copiar y pegar texto durante un tiempo. Puedes copiar texto en el portapapeles llamando a navigator.clipboard.writeText() y, luego, pegar ese texto llamando a navigator.clipboard.readText().

Copia y pega imágenes

Ahora también puedes escribir imágenes en el portapapeles. Para que esto funcione, necesitas los datos de la imagen como un BLOB que, luego, pasas al constructor del elemento del portapapeles. Por último, puedes copiar este elemento del portapapeles llamando a navigator.clipboard.write().

// Copy: Writing image to the clipboard
try {
  const imgURL = 'https://developers.google.com/web/updates/images/generic/file.png';
  const data = await fetch(imgURL);
  const blob = await data.blob();
  await navigator.clipboard.write([
    new ClipboardItem(Object.defineProperty({}, blob.type, {
      value: blob,
      enumerable: true
    }))
  ]);
  console.log('Image copied.');
} catch(e) {
  console.error(e, e.message);
}

Pegar la imagen desde el portapapeles se ve bastante complicado, pero, en realidad, solo consiste en recuperar el BLOB del elemento del portapapeles. Como puede haber varios, debes hacer un bucle entre ellos hasta que tengas el que te interesa. Por motivos de seguridad, en este momento, esto se limita a las imágenes PNG, pero es posible que en el futuro se admitan más formatos de imagen.

async function getClipboardContents() {
  try {
    const clipboardItems = await navigator.clipboard.read();
    for (const clipboardItem of clipboardItems) {
      try {
        for (const type of clipboardItem.types) {
          const blob = await clipboardItem.getType(type);
          console.log(URL.createObjectURL(blob));
        }
      } catch (e) {
        console.error(e, e.message);
      }
    }
  } catch (e) {
    console.error(e, e.message);
  }
}

Puedes ver esta API en acción en una app de demostración. Los fragmentos relevantes de su código fuente están incorporados arriba. Se pueden copiar imágenes al portapapeles sin permiso, pero debes otorgar acceso para pegarlas desde el portapapeles.

99f6dbf35ff4f393.png

Después de otorgar el acceso, puedes leer la imagen desde el portapapeles y pegarla en la aplicación:

ace5945f4aca70ff.png

9. ¡Lo lograste!

¡Felicitaciones! Llegaste al final del codelab. Una vez más, este es un recordatorio de que la mayoría de las APIs aún se encuentran en proceso de cambio y se están trabajando activamente en ellas. Por lo tanto, el equipo valora mucho tus comentarios, ya que la interacción con personas como nos ayudará a implementar estas APIs correctamente.

También te recomendamos que consultes con frecuencia nuestra página de destino Funciones. Lo mantendremos actualizado y tiene acceso a todos los artículos detallados sobre las APIs en las que trabajamos. ¡Sigue bailando!

Tomás y todo el equipo de Funciones 🐡