Referencia para desarrolladores de <oim-player>
<oim-player> es un Web Component premium y agnóstico al framework que gestiona el renderizado de alto rendimiento de Object Interactive Media (tanto imágenes .oim como vídeos interactivos .ovm) con inyección multilingüe en tiempo real en la capa dinámica.
Características
- Aislamiento con Shadow DOM: El encapsulado total de estilos evita que las hojas de estilo de la página contenedora se filtren o interfieran con las capas del player y su interactividad.
- Tokens CSS dinámicos: Personalizaciones sencillas de estilo para controles y vistas mediante propiedades CSS personalizadas (
--oim-*). - Optimización para dispositivos de gama baja: Suspende automáticamente el renderizado y los cálculos de layout de los vídeos en pausa para reducir a cero los ciclos de CPU.
- Lazy loading nativo: Integra
IntersectionObserverpara diferir las peticiones de red y el renderizado hasta que el player entra en el viewport. - Arquitectura de motor unificada: Alterna dinámicamente entre motores de renderizado (
ImageEngineoVideoEngine) leyendo las firmas de la cabecera binaria del archivo. - Escalado dinámico de aspect ratio: Incluye un calculador de dimensiones de precisión y
ResizeObserverpara adaptar dinámicamente el tamaño del canvas al contenedor anfitrión. - Fuentes empaquetadas en el binario: Carga localmente las tipografías incrustadas dentro del propio archivo
.oimantes de levantar el telón, garantizando cero peticiones externas de fuentes y cero cambios visuales de layout.
Instalación y uso básico
Incluye el script en tu documento HTML y declara la etiqueta personalizada:
<!-- Import the Web Component bundle -->
<script src="https://cdn.oim.media/oim-player.js"></script>
<!-- Declare the player in the DOM -->
<oim-player
src="hero.oim"
lang="en"
fit="contain"
align="center">
</oim-player>Atributos y API
| Atributo | Tipo | Por defecto | Descripción |
|---|---|---|---|
src | string | "" | URL del archivo de imagen .oim o de vídeo .ovm de destino. |
lang | string | "en" | Código de idioma activo para mostrar el contenido localizado de los slots. |
fit | "contain" | "cover" | "contain" | Controla el modo de ajuste de contención del canvas interactivo. |
align | "center" | "top" | "bottom" | "center" | Alineación vertical del viewport interactivo. |
allow-lottie | boolean | true | Permite o restringe la carga de animaciones vectoriales Lottie JSON. |
disable-animations | boolean | según mode | Desactiva todas las animaciones visuales (loops, hovers, Lottie) por accesibilidad (respeta prefers-reduced-motion). |
mode | "image" | "full" | "image" | Preajuste de las dos banderas de capacidad. image es una imagen quieta con su idioma; full se mueve y responde. Un atributo explicito manda sobre el preajuste. |
disable-actions | boolean | según mode | Suspende las acciones de clic y hover declaradas en el archivo. prefers-reduced-motion NO lo activa: es una preferencia vestibular sobre el movimiento, no una renuncia a poder interactuar. |
auto-rotate-lang | number | "false" | "false" | Intervalo en ms para cambiar automáticamente entre los idiomas disponibles. |
placeholder | string | ninguno | Miniatura que se muestra hasta que el player pinta. Solo se usan URL http:, https:, blob: y data:image/. |
activate-on | "visible" | "hover" | "manual" | "visible" | hover mueve el archivo solo bajo el puntero (en táctil se comporta como visible); manual lo deja a play() y pause(). |
palette | string | la del archivo | Nombre de una de las paletas del archivo. Los nombres desconocidos se ignoran. |
show-slots | boolean | true | false dibuja solo la imagen base. |
Funcionalidades avanzadas
Desactivar animaciones (disable-animations)
Si está activado, o si el sistema operativo del usuario prefiere movimiento reducido (prefers-reduced-motion: reduce), el player:
- Detiene todos los loops de keyframes CSS y los efectos de hover.
- Carga los archivos Lottie con
loop: false,autoplay: false, y los pausa en el frame 0.
Rotación automática de idiomas (auto-rotate-lang)
Rota dinámicamente entre todas las traducciones disponibles en los metadatos:
<!-- Cycle through languages every 4 seconds (4000ms) -->
<oim-player src="product.oim" auto-rotate-lang="4000"></oim-player>El ciclo se pausa automáticamente cuando el vídeo está en pausa (modo OVM) y se reanuda al reproducirse.
Métodos de la API de JavaScript
Puedes controlar el custom element de forma programática mediante JavaScript:
const player = document.querySelector('oim-player');
// Change language dynamically
player.setLang('es');
// Adjust zoom level (1.0 to 4.0)
player.setZoom(1.8);
// Play / Pause (OVM video engine only, toggles language rotation)
player.play();
player.pause();
// Seek to timestamp (OVM video engine only)
player.seek(12.5); // time in secondsPersonalización de estilos (variables CSS)
Personaliza los botones visuales, las tipografías y los fondos ajustando las variables CSS en el contexto del componente:
oim-player {
/* System Colors */
--oim-bg: #050505;
--oim-primary: #f59e0b;
--oim-primary-hover: #fbbf24;
--oim-red: #ef4444;
/* User Interface & Controls */
--oim-control-bg: rgba(0, 0, 0, 0.75);
--oim-control-border: rgba(255, 255, 255, 0.15);
--oim-control-text: #f0f0f0;
--oim-control-hover-bg: rgba(255, 255, 255, 0.2);
--oim-control-text-hover: #000000;
/* Border Radii and Speeds */
--oim-transition-duration: 0.2s;
--oim-border-radius: 20px;
}API de montaje imperativo
Para entornos SPA dinámicos, utiliza el método estático OimPlayer.mount() para instanciar un player sobre cualquier elemento contenedor del DOM:
import 'oim-player.js';
OimPlayer.mount('player-container-id', 'promo.ovm', {
allowZoom: false,
showLanguageSelector: true,
showSlots: true,
fit: 'contain',
align: 'center'
});Eventos personalizados de ciclo de vida
El componente emite eventos personalizados estándar de HTML para comunicar los estados del motor y de la carga:
oim:loaded
Se emite cuando los metadatos se han descifrado, validado y montado correctamente.
player.addEventListener('oim:loaded', (e) => {
const { type, metadata } = e.detail;
console.log(`OIM ${type} engine loaded successfully. Metadata:`, metadata);
});oim:action
Se emite cuando se ejecuta una accion declarada en un slot. El archivo no puede provocar nada por su cuenta: no declara handler, ni URL, ni destino fuera de si mismo. Solo se anuncia, y solo sirve si la pagina escucha. preventDefault() suprime el efecto local.
player.addEventListener('oim:action', (e) => {
const { slot, name, trigger, targets, types } = e.detail;
// Si quieres que un clic navegue, decide la PAGINA — con su propia URL.
if (name === 'Comprar') window.location.href = '/producto/42';
});types puede incluir play (contrato 1.22.0). Las capas que se muestran u ocultan se mueven como dice su style.reveal; con disable-animations o prefers-reduced-motion: reduce aparecen y desaparecen al instante y play no hace nada. pause() congela también un revelado o un play en curso, y play() lo reanuda.
Motor de escalado dinámico
Para evitar que los layouts interactivos se estiren o pixelen, .oim-player-viewport calcula sus coordenadas a partir de la resolución original del asset.
- Ajuste Contain (
fit="contain"): Mide el espacio del contenedor padre y escala el viewport para encajar perfectamente sin recortes ni distorsión. - Ajuste Cover (
fit="cover"): Escala el viewport para cubrir por completo el área del contenedor, recortando los márgenes que sobresalen. - Observador de redimensionado: Escucha con un
ResizeObserverlos cambios de tamaño de la ventana y las modificaciones de layout del padre, recalibrando dinámicamente las escalas.
Integraciones avanzadas y diagnóstico
Estilo premium de scrollbar
Consigue temas oscuros de alta fidelidad sin las barras de scroll nativas del navegador usando selectores CSS de WebKit:
/* Custom fine scrollbar */
.custom-scrollbar::-webkit-scrollbar {
width: 6px;
height: 6px;
}
.custom-scrollbar::-webkit-scrollbar-track {
background: rgba(255, 255, 255, 0.01);
border-radius: 8px;
}
.custom-scrollbar::-webkit-scrollbar-thumb {
background: rgba(255, 255, 255, 0.1);
border-radius: 8px;
transition: background 0.2s;
}
.custom-scrollbar::-webkit-scrollbar-thumb:hover {
background: rgba(245, 158, 11, 0.4);
}Resaltado de sintaxis JSON de alta fidelidad
Renderiza de forma programática las salidas de metadatos extraídos mediante sustituciones con regex:
function syntaxHighlightJson(json) {
if (!json) return '';
let str = typeof json !== 'string' ? JSON.stringify(json, null, 2) : json;
str = str.replace(/&/g, '&').replace(/</g, '<').replace(/>/g, '>');
return str.replace(/("(\\u[a-zA-Z0-9]{4}|\\[^u]|[^\\"])*"(\s*:)?|\b(true|false|null)\b|-?\d+(?:\.\d*)?(?:[eE][+-]?\d+)?)/g, function (match) {
let style = 'color: #38bdf8;'; // numbers
if (/^"/.test(match)) {
if (/:$/.test(match)) {
style = 'color: #fbbf24; font-weight: 600;'; // keys
} else {
style = 'color: #34d399;'; // strings
}
} else if (/true|false/.test(match)) {
style = 'color: #c084fc; font-weight: bold;'; // booleans
} else if (/null/.test(match)) {
style = 'color: #71717a; font-style: italic;'; // nulls
}
return `<span style="${style}">${match}</span>`;
});
}Integración personalizada sin Web Components (modo Headless / Core)
Si deseas integrar OIM en tu propio visor personalizado o en una aplicación de terceros, no es obligatorio usar la etiqueta HTML <oim-player>. El ecosistema está diseñado bajo un principio modular que permite decodificar y renderizar los archivos de forma independiente:
Opción A: decodificación pura con @oim-media/core (sin HTML)
Para extraer los metadatos de un archivo OIM y renderizarlos con tus propios componentes personalizados (por ejemplo, en React, Vue, Svelte o un Canvas 2D):
import { extractOIM } from '@oim-media/core';
// 1. Fetch the .oim or .png file
const response = await fetch('image.oim');
const blob = await response.blob();
// 2. Extract metadata and the clean image (Layer −1)
const { image, metadata } = await extractOIM(blob);
// 'image' is an OIM-free PNG Blob ready to be placed in a standard <img>.
// 'metadata' is the OIM JSON containing slots and interactions.
console.log("OIM Metadata:", metadata);Opción B: inicialización programática con ImageEngine
Si quieres que el motor de OIM se encargue de la inyección de slots en el DOM, pero prefieres controlar la instancia de forma programática en JavaScript (sin Web Components):
import { ImageEngine } from '@oim-media/player-oim/engines';
const myContainer = document.getElementById('my-viewer-container');
// Instantiate the engine on the container
const engine = new ImageEngine(myContainer, {
disableAnimations: false,
allowZoom: true
});
// Load the interactive file
await engine.load('image.oim');