| Fonte | O que dá | Licença | Uso no Yuddha |
|---|---|---|---|
| geoBoundaries CGAZ ADM2 (v6) | Polígonos de ~48k "municípios" do mundo inteiro, harmonizados e sem sobreposição | CC BY 4.0 (atribuição) | Base mundial dos territórios |
| IBGE — Malha Municipal | 5.570 municípios do Brasil, oficial e mais precisa | aberta | Substitui o Brasil do CGAZ (qualidade melhor onde nasce o jogo) |
| Natural Earth | países, oceanos, texturas base | domínio público | Camadas de longe (zoom out) |
| Texturas NASA Blue Marble / Black Marble | terra dia / luzes noturnas | domínio público | Skin do globo |
Decisão: ADM2 em todo o mundo. Onde um país não tem ADM2 no CGAZ (alguns micro-estados), usa-se ADM1 ou o próprio ADM0 como território único.
1. Baixar CGAZ ADM2 (GeoJSON mundial) + malha IBGE (BR)
2. Substituir BRA do CGAZ pela malha IBGE (código IBGE de 7 díg.)
3. Normalizar: id = ISO3-<código local>, nome, país
4. Corrigir geometrias inválidas (st_makevalid / mapshaper -clean)
5. Gerar 3 níveis de simplificação (mapshaper):
L0 zoom longe (~5% dos vértices) → agregado por ADM1
L1 zoom médio (~10%) → ADM2 por país/UF
L2 zoom perto (~30%) → ADM2 detalhado
6. Particionar TopoJSON por país (e UF no Brasil):
static/geo/L1/BRA-SP.topo.json etc.
7. Carregar no Postgres: geom simplificada + centroide
8. Precomputar adjacência: ST_Touches em pares do mesmo
país + fronteiras internacionais; +vizinhos 'sea' (fase 2:
costeiros a < 500 km)
9. Publicar TopoJSON no /static do SvelteKit (CDN Vercel)
Números esperados: mundo ADM2 ≈ 48k polígonos; TopoJSON L1 mundial particionado ≈ 150–300 MB no total, mas o cliente só baixa os pedaços visíveis (poucos MB por sessão).
| Zoom (altitude da câmera) | O que renderiza | Fonte |
|---|---|---|
| Longe (mundo) | mancha de cores por hexbin H3 res 3 / ADM1 agregado | canal realtime + snapshot |
| Médio (país) | polígonos ADM2 L1 dos países no frustum | TopoJSON CDN |
| Perto (região) | ADM2 L2 + labels de nomes + tropas/ícones | TopoJSON CDN |
- Cache no cliente (IndexedDB) dos TopoJSON já baixados, com versão.
- Cores aplicadas por lookup
territory_id → owner_color(dicionário leve baixado no snapshot e atualizado via Realtime — separado da geometria, que é estática).
navigator.geolocation.getCurrentPosition()— só após clique em "Reivindicar meu território" (nunca automático; boa prática + exigência dos browsers).- Precisão baixa é suficiente (município!) —
enableHighAccuracy: false, timeout 8s. - Negou/indisponível → modo manual: jogador toca no globo, confirmação mostra o território que seria dele.
- No TWA/Android o mesmo código funciona (permissão de localização do app).
- Privacidade: coordenada nunca sai do fluxo de spawn; armazena-se apenas o território (doc 03).
| Caso | Tratamento |
|---|---|
| Ponto no mar/fora de polígono | vizinho mais próximo por centroide (KNN) |
| Território sem vizinho terrestre (ilha) | vizinho 'sea' precomputado (fase 2) ou spawn realoca p/ continente |
| País sem ADM2 | usa ADM1/ADM0 como território único |
| Enclaves/exclaves | tratados naturalmente pela adjacência real dos polígonos |
| Disputas de fronteira reais | seguimos CGAZ como está + aviso "fronteiras = tabuleiro, sem posição política" |
Rodapé/about: "Boundaries © geoBoundaries (CC BY 4.0) · Malha municipal © IBGE · Imagery NASA".