Ejemplo robusto de widget embebible con aislamiento de estilos usando Shadow DOM y propiedades CSS personalizadas para integración dinámica y hardware.
/*
Widget embebible con Shadow DOM y propiedades CSS personalizadas
- Aislamiento completo de estilos
- Personalización mediante variables CSS
- Integración con Arduino LED RGB (pines 9,10,11)
- Dependencias Node.js y LitElement opcional
*/
/* Definición CSS global para fallback y documentación de variables */
:root {
--widget-bg-color: #222222;
--widget-text-color: #eeeeee;
--widget-accent-color: #ff4081;
--widget-font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
--widget-padding: 1rem;
--widget-border-radius: 0.5rem;
}
/* Definición del Web Component */
class IsolatedWidget extends HTMLElement {
constructor() {
super();
// Creación de Shadow DOM en modo abierto para acceso desde scripts externos
this.attachShadow({ mode: 'open' });
// Plantilla HTML y CSS aislados
this.shadowRoot.innerHTML = `
<style>
/* Reset y base del widget */
:host {
display: block;
background-color: var(--widget-bg-color, #222);
color: var(--widget-text-color, #eee);
font-family: var(--widget-font-family, sans-serif);
padding: var(--widget-padding, 1rem);
border-radius: var(--widget-border-radius, 0.5rem);
box-shadow: 0 0 10px rgba(0,0,0,0.5);
max-width: 320px;
user-select: none;
}
h2 {
margin-top: 0;
color: var(--widget-accent-color, #ff4081);
font-weight: 700;
font-size: 1.5rem;
}
p {
font-size: 1rem;
line-height: 1.4;
margin-bottom: 1rem;
}
button {
background-color: var(--widget-accent-color, #ff4081);
border: none;
color: white;
padding: 0.5rem 1rem;
border-radius: 0.3rem;
cursor: pointer;
font-size: 1rem;
transition: background-color 0.3s ease;
}
button:hover {
background-color: #e73370;
}
/* LED RGB simulado con div coloreado */
.led-rgb {
width: 40px;
height: 40px;
border-radius: 50%;
background-color: var(--widget-accent-color, #ff4081);
margin: 1rem auto 0 auto;
box-shadow: 0 0 10px var(--widget-accent-color, #ff4081);
transition: background-color 0.5s ease, box-shadow 0.5s ease;
}
</style>
<h2>Widget Aislado</h2>
<p>Este widget utiliza Shadow DOM para aislar estilos y propiedades CSS personalizadas para personalización dinámica.</p>
<button id="changeColorBtn">Cambiar Color LED</button>
<div class="led-rgb" id="led"></div>
`;
// Estado interno para el color del LED
this.colors = ['#ff4081', '#40ff81', '#4081ff', '#ffff40', '#ff8040'];
this.currentColorIndex = 0;
// Referencias DOM
this.ledElement = this.shadowRoot.getElementById('led');
this.button = this.shadowRoot.getElementById('changeColorBtn');
// Vincular evento click
this.button.addEventListener('click', () => this.changeLedColor());
}
// Método para cambiar el color del LED y actualizar la propiedad CSS personalizada
changeLedColor() {
this.currentColorIndex = (this.currentColorIndex + 1) % this.colors.length;
const newColor = this.colors[this.currentColorIndex];
// Actualizar el color del LED simulado
this.ledElement.style.backgroundColor = newColor;
this.ledElement.style.boxShadow = `0 0 10px ${newColor}`;
// Actualizar la variable CSS personalizada en :host
this.style.setProperty('--widget-accent-color', newColor);
// Integración Arduino: enviar señal vía serial o protocolo personalizado (no implementado aquí)
// Ejemplo: enviar color RGB para cambiar LED hardware
// serialPort.write(convertHexToRGB(newColor));
}
}
// Registro del elemento personalizado
customElements.define('isolated-widget', IsolatedWidget);
/*
Configuración Arduino (comentarios):
- LED RGB conectado a pines PWM 9 (rojo), 10 (verde), 11 (azul)
- Alimentación 5V y GND común
- Control de color mediante PWM analogWrite
- Comunicación serial posible con widget para sincronización de color
*/
/*
Ejemplo de cableado Arduino:
+5V ---------------------> Ánodo común LED RGB
Pin 9 (PWM) ------------> Cátodo rojo LED
Pin 10 (PWM) -----------> Cátodo verde LED
Pin 11 (PWM) -----------> Cátodo azul LED
GND ---------------------> GND común
*/
/*
Dependencias de software:
- Node.js >=14 para compilación y desarrollo
- LitElement (opcional) para simplificar Web Component
- Herramientas de compilación: Rollup o Webpack para empaquetar y minificar
- Servidor con CORS habilitado para embedding cross-origin
*/
/*
Ejemplo HTML para embedding:
<script type="module" src="path/to/isolated-widget.js"></script>
<isolated-widget style="--widget-bg-color:#111; --widget-text-color:#ddd;
--widget-accent-color:#00ffcc;"></isolated-widget>
*/html
<!DOCTYPE html>
<html lang="es">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Ejemplo Widget Aislado con Shadow DOM</title>
</head>
<body>
<!-- Uso del widget personalizado -->
<isolated-widget style="--widget-bg-color:#111; --widget-text-color:#ddd; --widget-accent-color:#00ffcc;"></isolated-widget>
<script type="module">
/*
Widget embebible con Shadow DOM y propiedades CSS personalizadas
- Aislamiento completo de estilos
- Personalización mediante variables CSS
- Integración con Arduino LED RGB (pines 9,10,11)
- Dependencias Node.js y LitElement opcional
*/
/* Definición CSS global para fallback y documentación de variables */
:root {
--widget-bg-color: #222222;
--widget-text-color: #eeeeee;
--widget-accent-color: #ff4081;
--widget-font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
--widget-padding: 1rem;
--widget-border-radius: 0.5rem;
}
/* Definición del Web Component */
class IsolatedWidget extends HTMLElement {
constructor() {
super();
// Creación de Shadow DOM en modo abierto para acceso desde scripts externos
this.attachShadow({ mode: 'open' });
// Plantilla HTML y CSS aislados
this.shadowRoot.innerHTML = `
<style>
/* Reset y base del widget */
:host {
display: block;
background-color: var(--widget-bg-color, #222);
color: var(--widget-text-color, #eee);
font-family: var(--widget-font-family, sans-serif);
padding: var(--widget-padding, 1rem);
border-radius: var(--widget-border-radius, 0.5rem);
box-shadow: 0 0 10px rgba(0,0,0,0.5);
max-width: 320px;
user-select: none;
}
h2 {
margin-top: 0;
color: var(--widget-accent-color, #ff4081);
font-weight: 700;
font-size: 1.5rem;
}
p {
font-size: 1rem;
line-height: 1.4;
margin-bottom: 1rem;
}
button {
background-color: var(--widget-accent-color, #ff4081);
border: none;
color: white;
padding: 0.5rem 1rem;
border-radius: 0.3rem;
cursor: pointer;
font-size: 1rem;
transition: background-color 0.3s ease;
}
button:hover {
background-color: #e73370;
}
/* LED RGB simulado con div coloreado */
.led-rgb {
width: 40px;
height: 40px;
border-radius: 50%;
background-color: var(--widget-accent-color, #ff4081);
margin: 1rem auto 0 auto;
box-shadow: 0 0 10px var(--widget-accent-color, #ff4081);
transition: background-color 0.5s ease, box-shadow 0.5s ease;
}
</style>
<h2>Widget Aislado</h2>
<p>Este widget utiliza Shadow DOM para aislar estilos y propiedades CSS personalizadas para personalización dinámica.</p>
<button id="changeColorBtn">Cambiar Color LED</button>
<div class="led-rgb" id="led"></div>
`;
// Estado interno para el color del LED
this.colors = ['#ff4081', '#40ff81', '#4081ff', '#ffff40', '#ff8040'];
this.currentColorIndex = 0;
// Referencias DOM
this.ledElement = this.shadowRoot.getElementById('led');
this.button = this.shadowRoot.getElementById('changeColorBtn');
// Vincular evento click
this.button.addEventListener('click', () => this.changeLedColor());
}
// Método para cambiar el color del LED y actualizar la propiedad CSS personalizada
changeLedColor() {
this.currentColorIndex = (this.currentColorIndex + 1) % this.colors.length;
const newColor = this.colors[this.currentColorIndex];
// Actualizar el color del LED simulado
this.ledElement.style.backgroundColor = newColor;
this.ledElement.style.boxShadow = `0 0 10px ${newColor}`;
// Actualizar la variable CSS personalizada en :host
this.style.setProperty('--widget-accent-color', newColor);
// Integración Arduino: enviar señal vía serial o protocolo personalizado (no implementado aquí)
// Ejemplo: enviar color RGB para cambiar LED hardware
// serialPort.write(convertHexToRGB(newColor));
}
}
// Registro del elemento personalizado
customElements.define('isolated-widget', IsolatedWidget);
</script>
</body>
</html>Widget Web Component basado en Shadow DOM para aislamiento completo de estilos
Uso de propiedades CSS personalizadas para personalización dinámica del tema (colores, espacios, fuentes)
Configuración Arduino: cableado para LED RGB conectado a pines PWM 9 (rojo), 10 (verde), 11 (azul)
Configuración Arduino: alimentación 5V y masa común con el microcontrolador
Software: dependencia en Node.js >=14 para compilación con herramientas como Rollup o Webpack
Software: dependencia en LitElement o similar para simplificar la creación de Web Components (opcional)
Configuración de compilación: scripts npm para empaquetar y minificar CSS y JS
Configuración de hosting: CORS habilitado para embedding cross-origin
Configuración HTML de embedding: uso de <script type='module'> para importar el componente
Configuración CSS global: definición de propiedades CSS personalizadas por defecto para fallback