Communitygithub.com

caceresfjulian/motion-figure

Constrói figuras que se movem ou respondem ao leitor, em três níveis: animações SMIL e widgets de controle deslizante dentro de lições, figuras interativas de mecanismos que mostram as partes nomeadas de um sistema real com um veredito computado, e bandas de pontilhado ordenado na paleta do curso.

O que é motion-figure?

Esta skill cria figuras dinâmicas e interativas para cursos técnicos e documentação de sistemas. Ela é dividida em três níveis: 1) Figuras de lição: animações declarativas SMIL ou controles deslizantes que redesenham um SVG diretamente nas lições do curso. 2) Figuras de mecanismo: painéis HTML independentes que mostram as partes nomeadas de um sistema real (como um cache LRU ou uma fila) e calculam um veredito baseado na entrada do leitor. 3) Campos de pontilhado: bandas WebGL animadas com as cores do curso para cabeçalhos e quebras de seção. A skill é compatível com agentes como Claude, Cursor, Codex, OpenClaw e Hermes. Ela impõe regras rigorosas de desempenho (máximo de 55 elementos SVG, loops de 2.5 a 6 segundos), acessibilidade (suporte a movimento reduzido, temas claro/escuro, responsividade a 320px) e boas práticas de código (apenas ES5, sem setInterval/requestAnimationFram). Inclui referências detalhadas para cada nível e validadores para garantir a qualidade da implementação.

Funciona com✓Claude Code✓Codex CLI✓Cursor
npx skills add https://github.com/caceresfjulian/ai-engineering-from-scratch/tree/HEAD/.claude/skills/motion-figure

Perguntar na sua IA favorita

Abre um novo chat com esta habilidade de agente já pré-carregada.

Documentação

Motion figure

Esta skill cria figuras que se movem ou respondem à entrada do usuário. Ela possui três níveis. Use esta skill com Claude, Cursor, Codex, OpenClaw, Hermes ou qualquer agente que leia SKILL.md.

NívelO que criaOnde vai
1. Figura de liçãoAnimação declarativa SMIL ou um controle deslizante que redesenha um SVG. Ambos montam a partir de um ```figure fence.Lições do curso
2. Figura de mecanismoUm painel HTML que mostra as partes nomeadas de um sistema. O leitor controla um parâmetro e lê um veredito computado.Páginas independentes, READMEs, ensaios, site do curso fora das lições
3. Campo de pontilhadoUma banda WebGL de pontos de pontilhado ordenado nas cores papel, destaque e tinta, com quatro movimentos semeados.Cabeçalhos de página e quebras de seção

O nível 1 tem mais regras, porque o ambiente de execução da lição tem limites rígidos. Os níveis 2 e 3 têm seus próprios arquivos de referência.

Quando usar

  • Uma lição explica um processo que muda ao longo do tempo: um token que se move por estágios, uma fila que enche, um loop que se repete.
  • Uma lição explica uma fórmula onde uma entrada altera a saída: taxa de aprendizado, temperatura, tamanho do chunk, tamanho do lote.
  • Um autor escreve "anime esta figura", "adicione um controle deslizante" ou "torne o diagrama interativo".
  • Uma página precisa de uma demonstração onde o leitor muda algo e vê o que o sistema faz: um cache, uma fila, uma janela de contexto, um roteador. Use o nível 2.
  • Uma página precisa de um cabeçalho de movimento lento nas cores do curso. Use o nível 3.

Quando não usar

  • A ideia é uma estrutura fixa sem eixo temporal e sem entrada. Crie uma figura SVG estática. A skill irmã blueprint-figure cobre figuras estáticas.
  • A página é uma página explicativa completa com seu próprio modelo de estado e geometria de máquina. A skill irmã isometric-explainer cobre isso.
  • Você só precisa de paleta, fontes ou regras de prosa. A skill irmã course-style contém esses itens. Esta skill copia as partes necessárias para references/tokens.md.

Método

  1. Escreva uma frase que nomeia a única mudança que a figura mostra. Se precisar de duas frases, faça duas figuras.

  2. Escolha o nível. Dentro de uma lição, use o nível 1. Para o nível 2, leia references/mechanism-figures.md e comece a partir de templates/mechanism.html. Para o nível 3, leia references/dither-fields.md e copie templates/dither.js. As etapas abaixo são para o nível 1. No nível 1, use uma figura animada quando o tempo é a variável. Use um widget de controle deslizante quando um número é a variável.

  3. Escolha um nome em kebab case, por exemplo request-path ou context-budget. Procure no registro primeiro por esse nome. Um módulo posterior que registra o mesmo nome substitui a figura anterior.

  4. Coloque o código em um arquivo de módulo chamado figures-<topico>.js. Empacote-o em um IIFE, leia window.LF e retorne cedo se estiver faltando.

  5. Escreva uma função de figura function (host, cfg). Ela anexa um cartão .lf ao host e pode retornar uma função de descarte.

  6. Construa o cartão: .lf-head com um .lf-label em maiúsculas e uma dica curta, .lf-body e .lf-cap com a legenda.

  7. Use viewBox="0 0 520 H" para o SVG. A maioria das figuras do curso usa um H de 200 a 250. Uma única barra precisa de menos.

  8. Adicione um <title> e um <desc> com IDs que você cria uma vez, fora de qualquer função de renderização.

  9. Para uma figura animada, adicione entradas primeiro, depois um loop lento. Siga references/smil-rules.md linha por linha.

  10. Para um widget de controle deslizante, defina state._render antes de chamar LF.slider ou LF.select. Em seguida, chame state._render() uma vez no final.

  11. Chame LF.register({ 'seu-nome': fn }) no final do módulo.

  12. No Markdown da lição, adicione o fence. Coloque o nome na primeira linha e a configuração JSON opcional depois:

    ```figure
    context-budget {"windowK": 32}
    ```
    
  13. Execute as verificações em "Verifique antes de finalizar". Olhe para a figura no tema claro, tema escuro, com largura de 375 px e com movimento reduzido ativado.

Como a página monta uma figura

  • O parser Markdown transforma o fence em <div class="lesson-figure" data-figure="name {json}">.
  • A construção do site varre o Markdown da lição em busca de nomes de fence. Ele encontra o arquivo de módulo que contém o nome citado e escreve um manifesto. Um nome de fence sem provedor interrompe a construção.
  • A página carrega apenas os módulos que a lição precisa, em uma ordem fixa. Novos arquivos de módulo vão depois dos listados, em ordem alfabética.
  • A função de montagem lê a primeira palavra como o nome e analisa o resto como JSON. JSON inválido fornece um cfg vazio.
  • Se a função da figura lançar um erro, o runtime esvazia o host e registra um aviso. O resto da lição ainda renderiza.
  • Após a montagem, o runtime adiciona um título, uma descrição, role="img" e rótulos de controle se estiverem faltando. Ele adiciona um botão Pausar quando a figura tem animação SMIL e um botão Repetir quando qualquer animação é executada uma vez.
  • O runtime pausa a animação quando a figura sai da viewport, quando a aba está oculta e quando o leitor pressiona Pausar. Com movimento reduzido ou impressão, ele mostra o quadro estático.

references/toolkit.md descreve cada função do runtime e tem dois exemplos de módulo completos.

Regras

Figuras animadas:

  1. Use apenas <animate>, <animateTransform> e <animateMotion>. Não use setInterval ou requestAnimationFrame em uma figura.
  2. Mantenha cada figura com 55 elementos SVG ou menos.
  3. As entradas vão de opacidade 0 e escala 0.95 para opacidade 1 e escala 1. Nunca comece uma escala em 0.
  4. As entradas usam calcMode="spline" e keySplines="0.23 1 0.32 1". A duração da entrada é de 0.5 a 0.6 s.
  5. Atraso de início das entradas em 0.05 a 0.4 s. As saídas são mais curtas que as entradas.
  6. Os loops duram 2.5 a 6 s e usam repeatCount="indefinite". Não defina fill="freeze" em um loop, porque o runtime então o executa uma vez.
  7. Cada lista keyTimes tem tantas entradas quanto values. Começa em 0, termina em 1 e nunca diminui.
  8. Cada lista keySplines tem uma entrada a menos que keyTimes. Use-a apenas com calcMode="spline".
  9. Um animateMotion com keyPoints usa calcMode="linear". Sua contagem de keyPoints é igual à contagem de keyTimes. Não possui values.
  10. Não coloque var() em um valor fill ou stroke animado. Anime a opacidade de um segundo elemento que tenha a cor alvo.
  11. Os loops animam apenas opacidade, transform, stroke-dashoffset ou movimento ao longo de um caminho. O runtime faz com que qualquer animação de x, y, x1, y1, x2, y2, width, height, r, cx, cy, rx ou ry seja executada uma vez.
  12. O quadro no data-static-time do host (padrão 1.5 s) está completo e legível. Defina o atributo no host quando um momento posterior mostrar o estado completo.
  13. Escalone um elemento em torno de seu centro. Desenhe o conteúdo de um grupo em torno de (0, 0) e mova o grupo com translate. Adicione a escala com additive="sum".

Widgets de controle deslizante:

  1. Escreva apenas ES5: var, expressões de função, concatenação de strings. Sem arrow functions, let, const ou template literals.
  2. Defina state._render antes da primeira chamada LF.slider ou LF.select. O controle deslizante envolve a função de renderização quando você a cria.
  3. Em state._render, remova todos os filhos SVG e adicione-os novamente. Não edite nós no local.
  4. Crie IDs uma vez, fora de state._render. O runtime remove atributos que os novos nós não têm, incluindo IDs.
  5. Aumente barras por comprimento ou por stroke-dasharray em um caminho. Não aumente barras com escala, porque nós reconciliados escalam a partir do seu centro.
  6. Mantenha cada rótulo de controle deslizante curto e em minúsculas com a unidade entre colchetes, por exemplo tamanho do chunk (tokens).

Ambos os tipos:

  1. Pegue cada cor de uma variável CSS com o valor do tema claro como padrão, por exemplo var(--blueprint,#3553ff). Use hexadecimal literal apenas quando nenhuma variável funcionar.
  2. Use no máximo uma cor de destaque (--blueprint) para o assunto principal e --warn para um segundo estado. Use tokens de tinta e régua para o resto.
  3. Defina texto SVG com 12 unidades ou mais, em var(--font-mono). Se os rótulos precisarem ser menores, dê ao SVG uma largura mínima de 500 px e deixe-o rolar lateralmente.
  4. Meça o tamanho do rótulo em um telefone. Em uma tela de 375 px, um SVG de 520 unidades dentro do cartão desenhou 279 px de largura. Um rótulo de 12 unidades desenhou então cerca de 6.4 px.
  5. Escreva a legenda em inglês técnico simples. Nomeie o que cada cor significa. Mantenha frases com 25 palavras ou menos.
  6. Dê ao rótulo em .lf-label em maiúsculas, duas a quatro palavras.

Figuras de mecanismo (nível 2):

  1. Mostre nomes reais e números reais: nomes de arquivos, chaves, contagens de tokens. Nunca "item 1" ou uma barra cinza sem nome.
  2. Dê ao leitor um controle: passo, controle deslizante, alternância, reproduzir ou parar uma parte.
  3. Termine com uma linha de veredito em texto, computada a partir dos números no corpo. Nunca escreva um resultado fixo.
  4. Execute uma vez quando 35 por cento da figura estiver visível, adicione um botão Repetir e nunca faça loop.
  5. Anime apenas transform e opacity, com cubic-bezier(0.23, 1, 0.32, 1). Pressione 120 a 160 ms, revele 200 a 300 ms, dobre 380 a 500 ms.
  6. Distribua listas em 30 a 70 ms por item, apenas para os primeiros 8 itens.
  7. Mantenha cada rótulo inteiro em cada quadro: sem reticências, sem sobreposição, sem texto em pontos. Texto 11 px ou mais, veredito 12.5 px ou mais.
  8. A 320 px, empilhe os painéis em uma coluna e dê a cada controle um alvo de toque de 40 px.
  9. Use um mecanismo que nenhuma outra página do site usa e adicione-o à tabela de mecanismos do site.

Campos de pontilhado (nível 3):

  1. Leia as cores de --bg, --blueprint e --ink, e redesenhe quando data-theme mudar.
  2. Desenhe a no máximo 30 quadros por segundo e apenas enquanto a banda estiver visível.
  3. Com movimento reduzido, desenhe um quadro estático. Sem WebGL, mostre uma hachura estática.
  4. Marque a banda aria-hidden="true" e não coloque texto nos pontos, exceto o chip do rótulo.

Verifique antes de finalizar

  • O nome do fence corresponde exatamente ao nome registrado e nenhum outro módulo o registra.
  • O módulo não tem =>, let, const ou strings com crase.
  • O módulo não tem setInterval e nem requestAnimationFrame.
  • O validador em references/smil-rules.md retorna uma lista vazia para o host montado.
  • Cada figura animada tem 55 elementos SVG ou menos.
  • Cada loop tem duração de 2.5 a 6 s.
  • Nenhum loop anima um atributo geométrico da regra 11.
  • Com movimento reduzido ativado, a figura mostra uma imagem completa e nenhum elemento está faltando.
  • No tema escuro, cada linha e rótulo está visível.
  • Com largura de 375 px, cada rótulo é legível e a página não tem rolagem lateral fora da figura.
  • Para um widget, mover cada controle deslizante ao seu mínimo e máximo não dá NaN, larguras negativas ou erros no console.
  • O SVG tem um título e uma descrição, e seus IDs permanecem os mesmos após um controle deslizante se mover.
  • A legenda nomeia cada cor que a figura usa.
  • Nível 2: cada item na lista de verificação no final de references/mechanism-figures.md passa.
  • Nível 3: cada item na lista de verificação no final de references/dither-fields.md passa.

Arquivos

  • references/smil-rules.md: as doze regras SMIL completas, o que cada regra impede e um validador que você pode executar no console do navegador.
  • references/toolkit.md: as funções LF e a sequência de montagem. Também contém um widget de controle deslizante completo, uma figura SMIL completa e uma página de pré-visualização para uso fora do site do curso.
  • references/tokens.md: tokens de cor para temas claro e escuro, fontes e valores de tempo de movimento.
  • references/mechanism-figures.md: nível 2. Nomes reais, figuras rejeitadas, formas de mecanismo, anatomia, veredito, orçamento de movimento e verificações.
  • references/dither-fields.md: nível 3. Como o shader desenha, os quatro movimentos, marcação, regras, barras pontilhadas e verificações.
  • templates/mechanism.html: uma figura completa de nível 2, um cache LRU com um controle de tamanho, que abre em qualquer navegador.
  • templates/dither.js: um script completo de nível 3. Carregue-o e adicione <div class="dither" data-seed="...">.

Dentro do repositório AI Engineering from Scratch, veja também site/lesson-figures.js para o runtime e site/figures-*.js para mais figuras.

Habilidades Relacionadas