AI Elements Persona vs un personaje de Rive a medida
Por el equipo de Charmotion · Actualizado el

AI Elements Persona es un componente de React de Vercel que renderiza un visual de IA animado con Rive WebGL2. Tiene cinco estados (idle, listening, thinking, speaking, asleep) y seis variantes, con Obsidian como predeterminada. Su documentación no explica cómo cargar tu propio .riv, así que una mascota de marca implica escribir un pequeño componente de Rive con los mismos nombres de estado.
Puntos clave
- Los estados de Persona son idle, listening, thinking, speaking y asleep; sus variantes son Obsidian, Mana, Opal, Halo, Glint y Command.
- Las props documentadas son
state,variant,classNamey callbacks de ciclo de vida. - Los archivos .riv personalizados no están documentados, así que trata Persona como un conjunto de visuales abstractos, no como un cargador de personajes.
- Un wrapper que acepte la misma prop
statete permite cambiar Persona por un personaje de marca sin tocar la lógica del chat.
¿Ya tienes un personaje o logo? Mira tu personaje en pantallas reales de una app: pantallas de splash, onboarding, carga y estado vacío. Es gratis, funciona en tu navegador y no sube nada.
¿Qué hace el componente Persona de AI Elements?
AI Elements es la biblioteca de componentes de React de Vercel para interfaces de IA, pensada para usarse junto con el AI SDK. Persona es su pieza de avatar. La documentación lo describe como un componente que "muestra un visual de IA animado que responde a distintos estados de la conversación" (AI Elements: Persona).
Internamente renderiza con Rive sobre WebGL2, así que los cambios de estado se mezclan en lugar de saltar entre clips. También resuelve un detalle de React que suele romper los componentes WebGL hechos a mano: la documentación menciona una protección integrada que retrasa un fotograma la inicialización de WebGL2, de modo que no se crea ningún contexto durante el montaje descartable de desarrollo de Strict Mode.
Como otros componentes de AI Elements, Persona se agrega a tu proyecto como código fuente en lugar de instalarse como un paquete opaco:
npx ai-elements@latest add persona
"use client";
import { Persona } from "@/components/ai-elements/persona";
export function AssistantVisual({ state }: { state: "idle" | "listening" | "thinking" | "speaking" | "asleep" }) {
return <Persona state={state} className="size-24" />;
}
Como usa APIs del navegador, renderízalo desde un client component en el App Router de Next.js. Si omites variant, obtienes el aspecto Obsidian predeterminado.
¿Qué estados y variantes admite?
Según su documentación, Persona admite cinco estados de conversación y seis variantes visuales (AI Elements: Persona):
| Prop | Valores | Notas |
|---|---|---|
state | idle, listening, thinking, speaking, asleep | Contrólalo desde el estado de tu chat o de voz |
variant | Obsidian (predeterminada), Mana, Opal, Halo, Glint, Command | Estilos visuales abstractos |
className | Clases CSS | Tamaño y ubicación |
| Callbacks de ciclo de vida | onLoad, onReady, onPlay, onPause, onStop, onLoadError | Estados de carga y respaldo ante errores |
Los cinco estados se corresponden con cómo se comportan los asistentes y coinciden con las convenciones de la mayoría de las guías de avatares: escuchar mientras el usuario habla, pensar mientras el modelo trabaja, hablar mientras responde y dormir cuando la sesión está inactiva.
Lo que no está en la lista es igual de útil saberlo. No hay reacciones puntuales como éxito o error, ni un estado "loading" distinto de thinking. Si tu producto necesita celebrar una tarea completada o señalar un fallo de forma visual, tendrás que mostrarlo en otra parte de la interfaz.
El mapeo desde el AI SDK es breve. Con useChat, submitted pasa a thinking, streaming pasa a speaking y todo lo demás a idle (referencia de useChat):
const personaState = status === "submitted" ? "thinking" : status === "streaming" ? "speaking" : "idle";¿Puedo usar mi propio personaje en Persona?
No de ninguna forma documentada. La documentación de Persona enumera las props anteriores y las seis variantes integradas; no explica cómo pasar tu propio archivo .riv ni cómo agregar una variante (AI Elements: Persona). A octubre de 2026, trata Persona como un conjunto de visuales abstractos listos para usar.
Como el componente se copia en tu código, puedes leer cómo carga sus archivos de Rive y qué valores les asigna. En principio es posible editarlo para que apunte a otro archivo, pero no está documentado, tu archivo tendría que exponer exactamente los inputs o propiedades que controla el componente, y actualizar el componente más adelante sobrescribiría tus cambios.
La opción más limpia es un componente propio muy pequeño que acepte la misma prop state. Tu lógica de chat sigue produciendo "idle" | "listening" | "thinking" | "speaking" | "asleep", y en el momento de renderizar eliges si eso va a Persona o a tu personaje. El runtime de React de Rive maneja el archivo con unas pocas líneas, como muestra la siguiente sección; consulta Rive en React y Next.js para los detalles de configuración.
¿Cómo se mapean los estados de Persona a un personaje con 10 estados de ánimo?
Un personaje con estados de ánimo numerados cubre los cinco estados de Persona y deja espacio para reacciones. Con la distribución de diez estados de ánimo que se usa en otras partes de estas guías, el mapeo es directo:
| Estado de Persona | Estado de ánimo | Valor |
|---|---|---|
| idle | idle | 0 |
| listening | listening | 6 |
| thinking | thinking | 3 |
| speaking | talking | 7 |
| asleep | sleeping | 8 |
"use client";
import { useEffect } from "react";
import { useRive, useViewModelInstanceNumber } from "@rive-app/react-webgl2";
export type PersonaState = "idle" | "listening" | "thinking" | "speaking" | "asleep";
const MOOD: Record<PersonaState, number> = { idle: 0, listening: 6, thinking: 3, speaking: 7, asleep: 8 };
export function CharacterPersona({ state, className }: { state: PersonaState; className?: string }) {
const { rive, RiveComponent } = useRive({
src: "/character.riv",
stateMachine: "CharacterViewModelMachine",
autoplay: true,
autoBind: true,
});
const { setValue: setMood } = useViewModelInstanceNumber("mood", rive?.viewModelInstance);
useEffect(() => {
setMood(MOOD[state]);
}, [state, setMood]);
return (
<div aria-hidden="true" className={className}>
<RiveComponent />
</div>
);
}
Los hooks vienen de la API de Data Binding de Rive para React (Data Binding de Rive en React). Como las props coinciden, cambiar entre <Persona state={s} /> y <CharacterPersona state={s} /> es un cambio de una línea. Después puedes agregar las reacciones que le faltan a Persona con useViewModelInstanceTrigger("success", ...).
¿Cómo manejo la carga y los errores con Persona o con un personaje personalizado?
Ambas opciones descargan un runtime de Rive y un archivo .riv antes de que aparezca nada, así que planifica los primeros momentos y los posibles fallos. Persona expone callbacks de ciclo de vida para esto, como onLoad, onReady y onLoadError (AI Elements: Persona). Un componente personalizado obtiene la misma información de useRive: la instancia rive sigue siendo null hasta que el archivo termina de cargar.
- Reserva el espacio. Dale al wrapper un tamaño fijo para que el diseño del chat no salte cuando aparezca el canvas.
- Muestra primero una imagen fija. Una imagen estática de la pose en reposo detrás del canvas evita una caja vacía en conexiones lentas.
- Recurre a un respaldo discreto. Si la carga falla, conserva la imagen fija y sigue adelante. El asistente tiene que funcionar sin su avatar.
- Mantén el estado en texto. Tanto si el visual es una esfera como una mascota, una etiqueta como "Pensando" le dice a todos lo que pasa, incluidos los usuarios de lectores de pantalla.
Para pausar fuera de pantalla, el movimiento reducido y los remontajes del canvas, las reglas son idénticas en ambos casos; consulta animación de avatares de IA accesible y rápida.
¿Cuándo conviene más una mascota de marca que una esfera abstracta?
Ninguna es mejor en general. Transmiten cosas distintas.
| Persona (visual abstracto) | Personaje personalizado | |
|---|---|---|
| Tiempo de configuración | Minutos | Trabajo de diseño y animación, o un set generado |
| Reconocimiento de marca | Aspecto compartido por muchas apps | Solo tuyo |
| Estados | Cinco, fijos | Los que tenga el archivo |
| Reacciones (éxito, error) | No incluido | Posibles con triggers |
| Expectativa que genera | "Esto es un sistema" | "Esta es la personalidad de nuestro producto" |
Elige Persona cuando estés prototipando, cuando el asistente sea una utilidad dentro de una herramienta más grande o cuando quieras la sensación neutra y ambiental de una esfera. Elige un personaje cuando el asistente sea el producto, cuando ya tengas una mascota de marca o un logo que la gente reconoce, o cuando necesites reacciones más allá de los cinco estados, como celebrar una reserva completada.
La diferencia de costo se ha reducido. Charmotion convierte un personaje o logo existente en un set de 17 animaciones en pocos minutos, con los diez moods de arriba y seis triggers en un solo .riv (planes de pago, desde $20/mes), además de exportaciones en MP4, GIF y WebM/MOV transparente para los lugares a los que no llega un canvas. Elijas lo que elijas, mantén la lógica de estados separada de la parte visual, como en el wrapper de arriba, para que la decisión siga siendo reversible.

Preguntas frecuentes
¿Qué estados admite el componente Persona de AI Elements?
Persona admite cinco estados: idle, listening, thinking, speaking y asleep. Se renderiza con Rive sobre WebGL2 y viene en seis variantes: Obsidian (la predeterminada), Mana, Opal, Halo, Glint y Command. Las props documentadas son state, variant, className y callbacks del ciclo de vida como onLoad y onLoadError.
¿Puedo cargar un archivo .riv personalizado en Persona?
La documentación de Persona no describe cómo cargar tu propio .riv ni cómo agregar variantes. Como el código fuente del componente se copia en tu proyecto, editarlo es técnicamente posible, pero no está documentado. Un pequeño componente de Rive que acepte la misma prop state es la forma más mantenible de usar un personaje de marca.
¿Persona funciona con React Strict Mode?
Sí. Su documentación describe una protección integrada que retrasa un fotograma la inicialización de WebGL2, así que no se crea ningún contexto durante el montaje descartable de desarrollo de Strict Mode. Si escribes tu propio avatar de Rive, mantén useRive y RiveComponent en un único componente estable para evitar problemas de remontaje.
Respuestas rápidas de esta guía
Fuentes
- Persona component, Vercel AI Elements
- useChat reference, AI SDK by Vercel
- React runtime: Data binding, Rive
- React runtime: Best practices, Rive