Landing 3D com scroll (para qualquer objeto)
Esta skill serve para construir uma landing page de uma única página onde um objeto 3D é o protagonista. O objeto fica fixo atrás do conteúdo e muda de pose, estilo de render e contexto conforme o usuário rola a página. Serve para qualquer coisa que possa ser mostrada como objeto: uma garrafa de vinho, um fone de ouvido, uma cadeira, um violão, um relógio, um carro, uma maquete de edifício, uma escultura, uma câmera antiga, um frasco de perfume, uma ferramenta ou um brinquedo.
O caso de referência é o toppervenom.com, do Evil Rabbit (post original), e foi desse projeto que surgiu a ideia desta skill. Ele mostra um tênis Topper de basquete dos anos 90; seu modelo 3D não é uma digitalização, mas uma reconstrução feita com IA a partir de material de arquivo e de imagens geradas de todas as suas vistas. A página começa como um plano técnico (wireframe branco sobre grade azul), é "preenchida" com o material real, mostra suas medidas e partes, muda de cor e termina girando. O tênis é apenas o exemplo; o que se replica é a forma de construir a página e seu nível de qualidade. Cada projeto escolhe seu próprio conceito visual, sua sequência de atos e o efeito de revelação que melhor se adequa ao seu objeto (veja "Adaptar ao objeto" abaixo).
Por que esses sites são tão bonitos (leia isto antes de começar)
A qualidade não vem da stack. toppervenom.com tem cerca de 90 KB de HTML/CSS/JS mais Three.js (segundo seu autor, a página foi gerada por uma IA de uma vez): não tem framework, nem GSAP, nem bundler. A qualidade vem de cinco coisas, e cada decisão do projeto deve servir a alguma delas:
- Um asset 3D real e bem preparado. Uma digitalização com textura fotográfica, uma reconstrução com IA bem cuidada (como a do toppervenom) ou um modelo com detalhes reais, limpo, leve e com escala real. Se o modelo for ruim, nada mais o salvará. →
references/3d-capture.md,references/3d-alternatives.md - Render com critério fotográfico. Iluminação de três pontos, environment map, tone mapping neutro, sombra de contato e materiais corrigidos (uma digitalização geralmente traz metalness falso que faz o couro parecer plástico). →
references/rendering.md - Um conceito de direção de arte levado até o último detalhe. "Plano técnico" no toppervenom: a grade, as cotas, a tipografia mono, o loader diz "PLOTTING DRAWING Nº 01", o rail diz "REV. 0 — BLUEPRINT". Tudo conta a mesma história. →
references/art-direction.md - Movimento com física, não com keyframes. As poses são declaradas por seção; o JS interpola com smoothstep e também amortiza cada valor com decaimento exponencial. Isso dá peso e inércia. →
references/choreography.md - Efeitos de shader que justificam o 3D. Revelação wireframe→sólido com um plano que varre o objeto, superfície fantasma com fresnel, recoloração por luminância. São coisas que um vídeo não consegue fazer. →
references/shaders.md
Se o usuário pedir "algo assim", o trabalho real é: conseguir um bom modelo + escolher um conceito + ajustar com paciência. A plantilha resolve a engenharia.
Adaptar ao objeto (não copie o tênis)
A plantilha traz uma sequência de exemplo (plano → medidas → partes → revelação → números → origem → fechamento), mas a forma do objeto e sua história decidem a composição, o efeito e os atos. Antes de escrever poses, posicione o objeto nesta tabela:
| Forma do objeto | Exemplos | Composição | Revelação que melhor funciona | Atos típicos |
|---|---|---|---|---|
| Alongado horizontal | tênis, carro, violão, faca, caneta, trem | Objeto de um lado e texto do outro; perfil puro para as cotas | Varredura ao longo (ponta → cauda) | Perfil técnico, detalhe de peças, velocidade ou uso |
| Vertical / de revolução | garrafa, perfume, luminária, vaso, troféu, edifício | Objeto centralizado ou a um terço, texto dos lados em duas colunas; plano contra-picado para o clímax | Varredura de baixo para cima ("se enche") ou corte transversal | Silhueta, material ou conteúdo, origem, ritual de uso |
| Compacto / caixa | fone de ouvido, câmera, alto-falante, relógio, console, joia | Grandes planos (scale 1.4–2) que percorrem o objeto como uma macro | Explosão (vista explodida) ou varredura diagonal | Design, interior/componentes, materiais, especificações |
| Plano / de leitura frontal | livro, disco, quadro, placa, cartão, tablet | Rotações curtas (±0.4 rad) para mostrar a espessura; nunca de lado por muito tempo | Pontos que se condensam, ou pintura que "aparece" | Frente, verso, detalhe de textura, contexto |
| Orgânico / escultórico | escultura, comida, planta, fóssil, brinquedo | Giros lentos e amplos, muita luz de contorno | Nuvem de pontos → superfície, ou fantasma com fresnel | Forma, textura, história, escala humana |
| Montagem de peças | móvel, máquina, maquete, produto modular | Vista 3/4 alta, todo o conjunto no quadro | Explosão por scroll: cada peça se separa em seu eixo e retorna | Conjunto → explosão → peça por peça → montagem |
| Grande escala | casa, edifício, terreno, barco | Câmera mais distante, rotação de "maquete" sobre a mesa | Varredura vertical por andares, cortes de seção | Emplacamento, plantas, cortes, materiais |
Escolha também o conceito visual de acordo com o objeto, não por padrão. "Plano técnico" fica bem em tudo que é projetado ou fabricado; um vinho pode pedir "ficha de adega"; uma escultura, "catálogo de museu"; um gadget, "laboratório"; algo vintage, "catálogo de época". O menu completo está em references/art-direction.md, e os efeitos alternativos (explosão, pontos, corte, preenchimento) em references/shaders.md.
Fluxo de trabalho
Siga estas fases em ordem. Antes de escrever código, confirme com o usuário as decisões das fases 1 e 2, pois elas mudam tudo que vem depois.
Fase 1 — Brief e conceito (5 minutos com o usuário)
Pergunte ou deduza:
- Qual objeto é e de qual material (couro, vidro, metal, plástico fosco, tecido). O material define como capturá-lo e como iluminá-lo.
- A história em 5–8 atos. Cada ato é uma seção e uma pose do objeto. Exemplo típico: apresentação → plano/medidas → anatomia (partes) → revelação → números → origem/história → fechamento.
- O conceito visual, ou seja, a metáfora que unifica tudo. Não copie "blueprint" por padrão: escolha a metáfora que faça sentido para aquele produto. Em
references/art-direction.mdhá um menu de conceitos (plano técnico, ficha de museu, laboratório, catálogo dos anos 90, editorial de moda, explosão industrial) com sua paleta, tipografias e como cada um se traduz no 3D. - Conteúdo real. Dados, medidas, materiais, história e créditos. Os sites de referência parecem autênticos porque usam dados reais do catálogo original e da digitalização. Se não houver dados, peça-os; não invente especificações de um produto real.
- Idiomas (pt/en) e se há variantes de cor.
Fase 2 — Conseguir o modelo 3D
Esta é a fase que mais afeta a qualidade final. Use esta árvore de decisão e leia a referência correspondente:
O usuário tem o objeto físico?
├─ Sim → DIGITALIZÁ-LO (references/3d-capture.md)
│ ├─ Objeto fosco/com textura (tênis, comida, pedra, madeira, tecido) → fotogrametria com celular ou câmera
│ ├─ Brilhante, preto ou transparente → spray matificante temporário + fotogrametria, ou modelá-lo
│ └─ Muito pequeno/fino (joias, cabos) → fotogrametria macro ou modelá-lo
└─ Não → ALTERNATIVAS (references/3d-alternatives.md)
├─ Há CAD/STEP do fabricante → converter e texturizar
├─ Há fotos boas de vários ângulos → IA image-to-3D (Meshy, Tripo, Rodin, Hunyuan3D, TRELLIS) + limpeza
├─ Forma geométrica (garrafa, lata, luminária, móvel) → modelar no Blender (revolução/extrusão), 1–4 h
├─ Produto genérico → comprar ou baixar com licença (Fab, Sketchfab, CGTrader, Poly Haven)
└─ Sem modelo possível → objeto procedural/estilizado (lathe, extrude de SVG, pontos, line-art)
Qualquer que seja a origem, o modelo passa pelo pipeline de otimização (references/asset-pipeline.md): limpeza, decimação para 100–300 k triângulos, textura de 2048–4096 em WebP, compressão Meshopt, escala real, origem e orientação corretos, e uma malha separada muito decimada para o wireframe. Esse detalhe é muito importante: o wireframe de uma malha densa parece ruído cinza, não um desenho.
Há um script pronto para esta etapa: scripts/prepare-model.sh <entrada.glb|.obj|.fbx> <nome>. Gera models/<nome>.glb otimizado e models/<nome>-wire.glb para as linhas. Com a Stratocaster de exemplo, passou de 22,2 MB para 1,8 MB.
Digitalização ou modelo feito à mão. A malha wire decimada é para digitalizações, onde as arestas são ruído. Em um modelo feito à mão (CAD, Sketchfab, Blender), a malha decimada se transforma em triângulos longos que atravessam as superfícies e são lidos como malha, não como desenho. Nesse caso, use wireMode: 'edges' sobre a malha principal e wireModel: null, sem gerar o wire. É lido como um desenho técnico e você economiza um arquivo.
Downloads do Sketchfab: exigem sessão iniciada (conta gratuita). Se você usar o navegador integrado, peça ao usuário para fazer login e confirme nome, tamanho e formato (GLB) antes de baixar. Salve o original em uma pasta source/ separada e credite o autor (CC BY) no rodapé.
Fase 3 — Montar o projeto a partir da plantilha
Copie assets/template/ para a pasta do projeto. Isto é o que ele traz:
| Arquivo | O que faz |
|---|---|
index.html | Estrutura: fundo fixo (grade + papel), <canvas> fixo, <svg> de overlay, loader, nav, rail de progresso, seletor de colorway e seções com atributos de pose (data-ry, data-x, data-reveal…). |
styles.css | Sistema visual: tokens, tipografia fluida com clamp(), grade CSS, fundo papel, reveals com blur, curvas de easing, mobile. |
main.js | Motor: renderer, luzes, carregamento com progresso, shaders de revelação e colorway, wireframe e fantasma, sombras, coreografia de scroll, arrasto com mola, overlays SVG (cotas e callouts), contadores, colorways. Tudo configurável desde CONFIG no início do arquivo. |
Não precisa de build. É servido com qualquer servidor estático (npx serve, python -m http.server). Não funciona com file:// por causa dos módulos ES. O Three.js vem do jsDelivr com versão fixa no importmap; para produção, convém copiá-lo para vendor/ e adicionar modulepreload (veja references/performance.md).
Teste sem modelo: index.html?model=<url de um .glb>, ou sem parâmetro para ver o objeto procedural de substituição. Um bom glb de teste é MaterialsVariantsShoe.glb do KhronosGroup/glTF-Sample-Assets.
Fase 4 — Ajustar o modelo à cena
Em main.js → CONFIG:
orient: gire até que o objeto fique com Y para cima e o comprimento sobre X (por exemplo,[0, 0, -Math.PI/2]para deitar um violão que vem em pé). A orientação é aplicada ao modelo antes de medi-lo, então a caixa, as cotas,sweepDir, os callouts e a explosão são sempre expressos no espaço já orientado. Use?debugpara ver os eixos.realSizeCm: a medida real do lado mais longo, em cm. É de onde saem todas as cotas exibidas.sweepDir: a direção da varredura de revelação. Deve seguir a "leitura" natural do objeto: ao longo em um objeto alongado ([1,0,0]ou[0,0,1]), de baixo para cima em uma garrafa ou edifício ([0,1,0]) e diagonal em um objeto compacto ([0.3,0.3,1]).callouts: as posições das partes, como frações da caixa (f, 0..1) ou como coordenadas exatas do modelo (p, em suas unidades). O código as cola no vértice mais próximo. Ordene de cima para baixo para que as linhas não se cruzem. Com?debug, clique sobre o modelo e o console imprime a fração exata do ponto.colorways: defina escuro/claro por variante (ou remova o seletor se o objeto não tiver variantes). O shader recolore por luminância e preserva os detalhes saturados; se o objeto em si for de uma cor saturada, definakeepSaturated: 0.- Seções: adicione, remova ou reordene
<section>livremente. O motor lê as poses de qualquer quantidade de seções, em qualquer ordem. - Opções do motor para casos especiais:
procedural: () => Object3Dmonta o objeto por código em vez de carregar um glb.wireMode: 'edges'desenha apenas as arestas de desenho. É o melhor para objetos duros, CAD ou processuais.extraKeys: ['screen']+onFrame(cur, dt, t)servem para efeitos próprios controlados por seção (data-screen). Por exemplo, uma tela que acende, uma luz ou uma tampa que abre.- Explosão com
data-explode: cada peça se move de acordo com seuuserData.explode = [x,y,z](ou se afasta do centro se não tiver). - Por peça:
userData.noRecolor(ignora os colorways),userData.noWire(não aparece no plano) euserData.keepPbr(o motor não mexe em seu material). recolorOnly: ['BodyMaterial']: apenas esses materiais (pelo nome do glb) recebem os colorways. No violão, pinta-se o corpo e ficam intactos o escudo, o braço e as ferragens.keepPbr: truerespeita o PBR de modelos feitos à mão (metais reais, verniz com clearcoat). Por padrão, o motor corrige o metalness falso de digitalizações e IA, e isso estraga um modelo bem feito.wireColors: [cor com paper 0, cor com paper 1]eedgeColoradaptam o plano a qualquer conceito, por exemplo tinta sobre papel patente em vez de branco sobre azul. Os dois estados do fundo (backdrop__gridebackdrop__paper) são apenas nomes: podem ser estilizados como lâmina → cenário, vitrine → noite, etc.data-rz(roll) para parar objetos longos, como um violão em seu suporte. As sombras de chão se apagam sozinhas ao pará-lo.