Communitygithub.com

anaydhawan/openvidstudio

Mejores prácticas para contenido, animación y efectos en Remotion.

¿Qué es openvidstudio?

Este skill proporciona una guía completa y detallada sobre las mejores prácticas para escribir markup de React en Remotion, el framework para crear videos programáticos. Está diseñado para ayudar a desarrolladores y agentes de IA a generar contenido, animaciones y efectos visuales de alta calidad que sean editables y predecibles en Remotion Studio. El skill cubre desde reglas generales de animación (usando `useCurrentFrame()` e `interpolate()` en lugar de CSS `transition` o `animation`), hasta el manejo de assets, componentes multimedia (`<Video>`, `<Audio>`, `<CanvasImage>`, `<AnimatedImage>`), y técnicas avanzadas como texto destacado, mapas, voz en off, transiciones, efectos visuales con CSS y shaders, contenido 3D con Three.js, y mucho más. También incluye referencias a otros skills para subtítulos, fuentes, animaciones Lottie, parámetros de composición, medición de DOM, detección de silencio y uso de FFmpeg. Es compatible con agentes como Claude Code, Cursor y Codex, y promueve el uso de `Interactive` para que los valores animados sean editables en el timeline del Studio.

Compatible con~Claude Code~Codex CLI~Cursor
npx skills add https://github.com/anaydhawan/openvidstudio/tree/HEAD/.agents/skills/remotion-markup

Preguntar en tu IA favorita

Abre un nuevo chat con esta habilidad de agente ya precargada.

Vista previa

Del README del skill

Documentación

Esta es una guía para escribir markup de React para Remotion. Si esto no es relevante, carga en su lugar las Mejores Prácticas de Remotion.

Preservar cambios del usuario

Los usuarios pueden hacer ediciones en el código fuera de la conversación.

Si detectas un cambio sorprendente hecho mientras tanto, no lo sobrescribas, asume que fue intencional o pide confirmación.

Reglas generales

Impulsa las animaciones usando useCurrentFrame() e interpolate(). Las transition o animation de CSS no se renderizarán correctamente, deben ser refactorizadas. Las clases de animación de Tailwind no se renderizarán correctamente, deben ser refactorizadas.

Usa Easing.bezier() y Easing.spring() para personalizar la temporización.

Estructura tu markup de acuerdo con las Mejores Prácticas de Interactividad de Remotion

import { useCurrentFrame, Easing, interpolate, Interactive } from "remotion";

export const FadeIn = () => {
  const frame = useCurrentFrame();

  return (
    <Interactive.Div
      name="Title"
      style={{
        opacity: interpolate(frame, [0, 2 * fps], [0, 1], {
          extrapolateRight: "clamp",
          extrapolateLeft: "clamp",
          easing: Easing.bezier(0.16, 1, 0.3, 1),
        }),
      }}
    >
      Hello World!
    </Interactive.Div>
  );
};

Mantén la llamada a interpolate() en línea dentro del prop style. Usa las propiedades CSS scale, translate, rotate en lugar de transform.

// 👍 Keyframes editables en línea y shorthands de transformación
style={{
  scale: interpolate(frame, [0, 100], [0, 1], {
    extrapolateLeft: 'clamp',
    extrapolateRight: 'clamp',
    easing: Easing.spring({damping: 200}),
    output: 'perceptual-scale' // Para animaciones de `scale`, usa "output: 'perceptual-scale'"
  }),
  translate: interpolate(frame, [0, 100], ["0px 0px", "100px 100px"], {
    extrapolateLeft: 'clamp',
    extrapolateRight: 'clamp',
    easing: Easing.spring({damping: 200}),
  }),
  rotate: interpolate(frame, [0, 100], ["20deg", "90deg"], {
    extrapolateLeft: 'clamp',
    extrapolateRight: 'clamp',
    easing: Easing.spring({damping: 200}),
  }),
}}

// 👎 Valores no en línea y cadenas transform se vuelven más difíciles de editar en Studio
const scale = interpolate(frame, [0, 100], [0, 1]);

style={{
  transform: `scale(${scale})`,
}}

Assets

Coloca los assets en la carpeta public/ en la raíz de tu proyecto. Usa staticFile() para referenciar archivos desde la carpeta public/.

Componentes multimedia

Añade video y audio usando <Video> y <Audio> de @remotion/media. Añade imágenes usando el componente <CanvasImage>. Añade GIFs animados, APNG, WebP o imágenes AVIF usando <AnimatedImage>, usa @remotion/gif si no estás usando Chrome. Usa staticFile() para archivos en public/ o pasa una URL remota directamente:

import { Audio, Video } from "@remotion/media";
import { staticFile, CanvasImage, AnimatedImage } from "remotion";

export const MyComposition = () => {
  return (
    <>
      <Video src={staticFile("video.mp4")} style={{ opacity: 0.5 }} />
      <Audio src={staticFile("audio.mp3")} />
      <CanvasImage
        src={staticFile("logo.png")}
        style={{ width: 100, height: 100 }}
      />
      <Video src="https://remotion.media/video.mp4" />
      <AnimatedImage src={staticFile('nyancat.gif')} />
    </>
  );
};

Escena de ejemplo

import {
  AbsoluteFill,
  Easing,
  Interactive,
  interpolate,
  useCurrentFrame,
  useVideoConfig
} from "remotion";

export const Empty = () => {
  const {fps} = useVideoConfig();
  const frame = useCurrentFrame();

  return (
    <AbsoluteFill
      name="Scene"
      style={{
        display: 'flex',
        justifyContent: 'center',
        alignItems: 'center',
        backgroundColor: 'white'
      }}
    >
      <Interactive.Div
        name="Title"
        style={{
          opacity: interpolate(frame, [1 * fps, 2 * fps], [0, 1], {
            extrapolateRight: "clamp",
            extrapolateLeft: "clamp",
            easing: Easing.bezier(0.16, 1, 0.3, 1),
          }),
          fontSize: 88
        }}
      >
        Title
      </Interactive.Div>
      <Interactive.Div
        name="Subtitle"
        style={{
          opacity: interpolate(frame, [2 * fps, 3 * fps, 8 * fps, 10 * fps], [0, 1, 1, 0], {
            extrapolateRight: "clamp",
            extrapolateLeft: "clamp",
            easing: [Easing.bezier(0.16, 1, 0.3, 1), Easing.linear, Easing.bezier(0.16, 1, 0.3, 1)],
          }),
          fontSize: 32
        }}
      >
        Subtitle
      </Interactive.Div>
    </AbsoluteFill>
  );
}

Retraso, recorte

La mayoría de los componentes (<AbsoluteFill>, <Interactive.*> <Img>, <AnimatedImage>, <CanvasImage>, <HtmlInCanvas>, <Solid>, <Sequence> de remotion, <Video> y <Audio> de @remotion/media, <Gif>, y más) admiten las siguientes props:

from

<Img from={1 * fps} {/* ... */}/>
<Video from={1 * fps} {/* ... */}/>
<Interactive.Div from={1 * fps} {/* ... */}/>

Cuándo el elemento comienza a aparecer en la línea de tiempo.

durationInFrames

<Img durationInFrames={20 * fps} {/* ... */}/>
<Interactive.Div durationInFrames={20 * fps} {/* ... */}/>

Durante cuánto tiempo la capa se reproduce en la línea de tiempo. Para medios, pasa la duración natural del medio: <Video durationInFrames={29.322 * fps}/>

trimBefore

Útil para componentes cuyo reloj interno debe comenzar más tarde:

// Recorta los primeros 2 segundos del metraje
<Video trimBefore={2 * fps} {/* ... */} />

// `useCurrenFrame()` para hijos comienza en `10 * fps`
<Sequence trimBefore={10 * fps} {/* ... */} />

Fallback

Si un componente no admite estas props, envuélvelo en <Sequence> de remotion, que las tiene.

  • layout="absolute-fill" hace que Sequence se comporte como AbsoluteFill
  • layout="none" es el modo "sin cabeza", no se utiliza ningún elemento envolvente.

Mapas

Consulta Remotion Maps si deseas incluir mapas en el video.

Resaltados de texto y anotaciones

Consulta text-highlights.md para resaltados de texto (marcadores de resaltado), círculos, subrayados, tachados, texto tachado, recuadros.

Videos con múltiples escenas

Consulta multi-scene-video.md si planeas hacer un video con múltiples escenas consecutivas.

Voz en off

Consulta voiceover.md para agregar una voz en off generada por IA a las composiciones de Remotion usando ElevenLabs TTS.

Incrustar videos

Consulta embedding-videos.md para conocer en profundidad sobre incrustar videos: recorte, volumen, velocidad, bucle, tono.

Incrustar audio

Consulta audio.md para funciones avanzadas de audio como recorte, volumen, velocidad, tono.

Edición de video

Consulta video-editing.md para estructurar líneas de tiempo de video editables en Remotion Studio.

Recorte

Consulta cropping.md si necesitas recortar el rectángulo visible de un componente.

Transiciones

Consulta transitions.md para patrones de transición de escenas.

Efectos visuales y de píxeles

Al crear un efecto visual, considera si es factible usando CSS y HTML, o si se necesita un shader. Orden de preferencia:

  1. HTML + CSS regular u otras técnicas web
  2. Un efecto aplicado directamente al elemento (<Video>, <Img>), o envolviendo el contenido en <HtmlInCanvas>, que también acepta effects:
  • Un efecto listado en effects.md
  • Un createEffect() personalizado de effects.md cuando no haya un preset disponible.

Contenido 3D

Consulta ./3d.md para contenido 3D en Remotion usando Three.js y React Three Fiber.

Efectos de sonido

Cuando necesites usar efectos de sonido, carga el archivo ./sfx.md para más información.

Visualización de audio

Cuando necesites visualizar audio (barras de espectro, formas de onda, efectos reactivos a graves), carga el archivo ./audio-visualization.md para más información.

Mapas

Para mapas estáticos, rutas animadas y marcadores, explicadores geográficos, Mapbox, MapLibre, MapTiler, GeoJSON, o sobrevuelos geográficos 3D, carga Remotion Maps.

Subtítulos

Cuando trates con subtítulos o leyendas, carga el skill de Subtítulos de Remotion para más información.

Google Fonts

Es la forma recomendada de cargar fuentes en Remotion. Consulta google-fonts.md para saber cómo cargar Google Fonts.

Fuentes locales

Consulta local-fonts.md para saber cómo cargar fuentes locales.

GIFs

Consulta gifs.md para saber cómo mostrar GIFs sincronizados con la línea de tiempo de Remotion.

Imágenes avanzadas

Consulta images.md para dimensionar y posicionar imágenes, rutas de imágenes dinámicas y obtener dimensiones de imágenes.

Animaciones Lottie

Consulta lottie.md para incrustar animaciones Lottie en Remotion.

Temporización

Consulta timing.md para más técnicas de temporización para interpolate().

Videos parametrizados

Consulta parameters.md para hacer una composición parametrizable añadiendo un esquema Zod.

Medir nodos del DOM

Consulta measuring-dom-nodes.md para medir las dimensiones de elementos del DOM en Remotion.

Medir texto

Consulta measuring-text.md para medir dimensiones de texto, ajustar texto a contenedores y comprobar desbordamiento.

Usar FFmpeg

Para algunas operaciones de video, como recortar videos o detectar silencio, se debe usar FFmpeg. Carga el archivo ./ffmpeg.md para más información.

Detección de silencio

Cuando necesites detectar y recortar segmentos silenciosos de archivos de video o audio, carga el archivo ./silence-detection.md.

Duración dinámica, dimensiones y datos

Consulta calculate-metadata.md para establecer dinámicamente la duración de la composición, las dimensiones y las props.

Composiciones avanzadas

Consulta compositions.md para saber cómo definir imágenes fijas, carpetas, props por defecto y cómo anidar composiciones.

Secuenciación avanzada

Consulta sequencing.md para más patrones de secuenciación: retraso, recorte, limitar duración de elementos.

Instalar módulos

Usa npx remotion add para añadir nuevos paquetes con la versión correcta:

npx remotion add @remotion/media

Esto aplica para paquetes @remotion/*, mediabunny, @mediabunny/* y zod.

Vista previa del markup

npx remotion studio --no-open

Esto iniciará un proceso de larga duración e imprimirá la URL del servidor para la vista previa. Si el servidor ya está iniciado, imprimirá la URL. Puedes visitar una composición específica navegando a /[composition-id], por ejemplo http://localhost:3000/MapAnimation.

Opcional: comprobación de un solo fotograma

Puedes renderizar un solo fotograma con la CLI para verificar el diseño, los colores o la temporización. Omítelo para ediciones triviales, refactorizaciones puras, o cuando ya tengas suficiente confianza de Studio o renders anteriores.

npx remotion still [composition-id] --scale=0.25 --frame=30

A 30 fps, --frame=30 es la marca de un segundo (--frame está basado en cero).

Individual skills in this repo

This repo contains 1 individual skill — each has its own dedicated page.

Skills relacionados