- FEATURES_OVERVIEW.md: Complete summary of all system features - ANALYTICS.md: Analytics and reporting system documentation - ODOO_INTEGRATION.md: Odoo ERP integration guide - AB_TESTING.md: A/B testing system documentation - CONTENT_RECYCLING.md: Content recycling system docs - THREAD_SERIES.md: Thread series and scheduled posts - IMAGE_TEMPLATES.md: Visual template system documentation Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
8.1 KiB
8.1 KiB
Image Templates
Sistema de plantillas para generar imágenes dinámicas.
Descripción
Las plantillas de imagen permiten:
- Definir diseños reutilizables en HTML/CSS
- Insertar variables dinámicas
- Generar imágenes para diferentes plataformas
- Mantener consistencia visual
Modelo de Datos
ImageTemplate
ImageTemplate:
id: int
name: str
description: str
category: str # tip, producto, servicio, promocion, etc.
template_type: str # tip_card, product_card, quote, promo, announcement
# Plantilla
template_file: str # Ruta a archivo (opcional)
html_template: str # HTML inline
preview_url: str # URL de imagen preview
# Variables
variables: [str] # ["title", "content", "accent_color"]
# Configuración de diseño
design_config: JSON
# {
# "width": 1080,
# "height": 1080,
# "background_color": "#1a1a2e",
# "accent_color": "#d4a574",
# "font_family": "Inter"
# }
# Tamaños de salida
output_sizes: JSON
# {
# "instagram": {"width": 1080, "height": 1080},
# "x": {"width": 1200, "height": 675},
# "facebook": {"width": 1200, "height": 630}
# }
is_active: bool
API Endpoints
GET /api/templates/
Lista todas las plantillas.
Parámetros:
category: tip, producto, servicio, etc.template_type: tip_card, product_card, etc.active_only(bool, default=true)limit(int, default=50)
Respuesta:
{
"templates": [
{
"id": 1,
"name": "Tip Card Oscuro",
"description": "Tarjeta para tips con fondo oscuro",
"category": "tip",
"template_type": "tip_card",
"variables": ["title", "content", "emoji"],
"preview_url": "/uploads/previews/tip_card_dark.png"
}
],
"count": 10
}
GET /api/templates/{template_id}
Obtiene una plantilla con detalles completos.
Incluye full_html_template con el HTML completo.
POST /api/templates/
Crea una nueva plantilla.
Body:
{
"name": "Quote Card",
"description": "Tarjeta para frases motivacionales",
"category": "frase",
"template_type": "quote",
"html_template": "<div class='card'>...</div>",
"variables": ["quote", "author", "background_image"],
"design_config": {
"width": 1080,
"height": 1080,
"background_color": "#1a1a2e"
},
"output_sizes": {
"instagram": {"width": 1080, "height": 1080},
"x": {"width": 1200, "height": 675}
}
}
Validación:
- Requiere
html_templateotemplate_file
PUT /api/templates/{template_id}
Actualiza una plantilla.
DELETE /api/templates/{template_id}
Elimina una plantilla.
POST /api/templates/preview
Genera preview de una plantilla con variables.
Body:
{
"template_id": 1,
"variables": {
"title": "Tip del día",
"content": "Automatiza tus procesos con IA",
"emoji": "💡"
},
"output_size": {"width": 1080, "height": 1080}
}
O con HTML directo:
{
"html_template": "<div>{{title}}</div>",
"variables": {
"title": "Mi título"
}
}
Respuesta:
{
"rendered_html": "<div>Mi título</div>",
"output_size": {"width": 1080, "height": 1080},
"variables_used": ["title"]
}
GET /api/templates/categories/list
Lista categorías disponibles.
GET /api/templates/types/list
Lista tipos de plantilla disponibles.
Estructura HTML
Variables
Las variables se definen con doble llave: {{variable}}
<div class="card">
<span class="emoji">{{emoji}}</span>
<h1>{{title}}</h1>
<p>{{content}}</p>
</div>
Ejemplo Completo
<!DOCTYPE html>
<html>
<head>
<style>
* { margin: 0; padding: 0; box-sizing: border-box; }
body {
width: 1080px;
height: 1080px;
background: linear-gradient(135deg, #1a1a2e 0%, #16213e 100%);
font-family: 'Inter', sans-serif;
color: #ffffff;
display: flex;
align-items: center;
justify-content: center;
}
.card {
width: 900px;
padding: 60px;
background: rgba(255,255,255,0.05);
border-radius: 24px;
border: 1px solid rgba(212, 165, 116, 0.3);
}
.emoji {
font-size: 64px;
display: block;
margin-bottom: 24px;
}
h1 {
color: #d4a574;
font-size: 36px;
margin-bottom: 24px;
}
p {
font-size: 24px;
line-height: 1.6;
color: #e0e0e0;
}
.footer {
margin-top: 40px;
color: #888;
font-size: 18px;
}
</style>
</head>
<body>
<div class="card">
<span class="emoji">{{emoji}}</span>
<h1>{{title}}</h1>
<p>{{content}}</p>
<div class="footer">@{{username}} • Consultoría AS</div>
</div>
</body>
</html>
Categorías
| Categoría | Uso |
|---|---|
tip |
Tips tecnológicos |
producto |
Fichas de producto |
servicio |
Promoción de servicios |
promocion |
Ofertas y descuentos |
frase |
Frases motivacionales |
dato |
Datos curiosos |
anuncio |
Anuncios generales |
Tipos de Plantilla
| Tipo | Descripción |
|---|---|
tip_card |
Tarjeta de tip con emoji |
product_card |
Ficha de producto con imagen |
quote |
Frase con autor |
promo |
Promoción con precio |
announcement |
Anuncio destacado |
stats |
Estadísticas/números |
comparison |
Antes/después o A vs B |
Tamaños por Plataforma
| Plataforma | Ancho | Alto | Ratio |
|---|---|---|---|
| Instagram Post | 1080 | 1080 | 1:1 |
| Instagram Story | 1080 | 1920 | 9:16 |
| X (Twitter) | 1200 | 675 | 16:9 |
| 1200 | 630 | 1.91:1 | |
| 1200 | 627 | 1.91:1 | |
| Threads | 1080 | 1080 | 1:1 |
Ejemplo de Uso
from app.models.image_template import ImageTemplate
from app.core.database import SessionLocal
db = SessionLocal()
# Crear plantilla
template = ImageTemplate(
name="Tip Card Dark",
category="tip",
template_type="tip_card",
html_template="""
<div style="...">
<h1>{{title}}</h1>
<p>{{content}}</p>
</div>
""",
variables=["title", "content"],
design_config={
"width": 1080,
"height": 1080,
"background_color": "#1a1a2e"
}
)
db.add(template)
db.commit()
# Renderizar
html = template.html_template
html = html.replace("{{title}}", "Mi Título")
html = html.replace("{{content}}", "Mi contenido")
Generación de Imágenes
Para convertir HTML a imagen se recomienda:
Playwright (recomendado)
from playwright.async_api import async_playwright
async def html_to_image(html: str, width: int, height: int) -> bytes:
async with async_playwright() as p:
browser = await p.chromium.launch()
page = await browser.new_page(viewport={"width": width, "height": height})
await page.set_content(html)
screenshot = await page.screenshot(type="png")
await browser.close()
return screenshot
WeasyPrint (alternativa)
from weasyprint import HTML
def html_to_pdf(html: str) -> bytes:
return HTML(string=html).write_pdf()
Mejores Prácticas
- Fuentes web: Usa Google Fonts o incluye fuentes inline
- Colores consistentes: Define palette en design_config
- Responsive: Usa unidades relativas cuando sea posible
- Contraste: Asegura legibilidad texto/fondo
- Logo: Incluye branding en todas las plantillas
- Variables descriptivas:
{{product_name}}mejor que{{name}} - Fallbacks: Define valores por defecto para variables opcionales
Integración con Posts
# Al crear un post con imagen generada
post = Post(
content="Tip del día...",
image_template_id=template.id, # Referencia a la plantilla usada
image_url="/uploads/generated/tip_123.png"
)