Combate à Distância Server-Authoritative com Raycasting
Este prompt cria um sistema robusto de combate à distância para Roblox, baseado em projéteis simulados no servidor e raycasting contínuo. Ele foi pensado para evitar falhas comuns de armas hitscan e projéteis rápidos, como atravessar paredes ou ignorar personagens em movimento, usando raycasts entre as posições de cada atualização física.
Ideal para desenvolvedores que já possuem Tools, RemoteEvents e modelos de armas em seu jogo, mas precisam de uma base segura e escalável para tiros, dano, detecção de headshots, filtros de colisão, cooldowns e validação antiexploit. O resultado é um Script Luau completo, comentado e pronto para ser adaptado ao Explorer do projeto.
Atue como um desenvolvedor Roblox sênior, especialista em Luau, arquitetura client-server, física, raycasting e segurança antiexploit para experiências multiplayer competitivas. Gere um único Script Luau completo, robusto, comentado e pronto para colar no Roblox Studio para implementar um sistema de combate à distância com projéteis simulados no servidor e raycasting contínuo. Antes de escrever o código, considere e incorpore o contexto abaixo. Se algum campo estiver vazio, use os valores padrão indicados e deixe comentários claros no código mostrando onde alterar. Não faça perguntas de retorno: entregue uma versão funcional e configurável com base nas informações disponíveis. CONTEXTO DO MEU JOGO (vou preencher antes de enviar): - Localização do RemoteEvent de disparo: [ex.: ReplicatedStorage.Remotes.FireWeapon] - Nome do RemoteEvent: [ex.: FireWeapon] - As armas são Tools em: [ex.: StarterPack / Backpack / Workspace] - Nome da peça de origem do disparo na Tool: [ex.: Muzzle] - Atributos da Tool já existentes: [ex.: Damage, FireRate, ProjectileSpeed, Range, MagazineSize, TeamDamageEnabled] - Valor padrão de dano: [ex.: 25] - Velocidade padrão do projétil: [ex.: 900] - Alcance máximo padrão: [ex.: 1000] - Gravidade/multiplicador de queda: [ex.: 0.15] - Headshot habilitado e multiplicador: [ex.: sim, 2] - Sistema de times utilizado: [ex.: Player.Team / nenhum] - Objetos/pastas que devem ser ignorados pelo raycast: [ex.: Workspace.Ignore, Workspace.VisualEffects] - CollisionGroup dos personagens, se houver: [ex.: Characters] - CollisionGroup do cenário, se houver: [ex.: Map] - Regras especiais de dano: [ex.: não causar dano em aliados, escudos usam atributo Shield, NPCs possuem Humanoid] O TIPO DO ARQUIVO DEVE SER: Script (nunca LocalScript e nunca ModuleScript). COLOQUE-O EM: ServerScriptService, com nome sugerido "ProjectileCombatServer". O Script deve ouvir o RemoteEvent informado. Considere que o cliente envia somente dados de intenção de tiro, como a Tool/equipamento usado, origem visual sugerida e direção/posição alvo. O servidor deve ser completamente autoritativo: ele deve decidir se o jogador pode atirar, validar a Tool equipada, localizar o Muzzle verdadeiro no personagem, recalcular ou sanitizar a direção, aplicar cooldown, simular o projétil, detectar impactos e aplicar dano. Nunca confie no cliente para dano, alvo acertado, headshot, moeda, munição, distância, velocidade, tempo entre tiros ou resultado do raycast. Implemente os seguintes requisitos técnicos: 1. Use RunService.Heartbeat para atualizar projéteis ativos no servidor. Cada projétil deve armazenar posição atual, direção/velocidade, distância percorrida, alcance máximo, dano, atirador, Tool de origem, momento de criação e RaycastParams. 2. Em cada frame, calcule a nova posição com deltaTime, velocidade e gravidade configurável. Faça Workspace:Raycast da posição anterior até a nova posição. Isso deve evitar tunneling em projéteis rápidos. 3. Configure RaycastParams com FilterType.Exclude e ignore ao menos o personagem do atirador, a Tool equipada, o Muzzle e as pastas configuráveis de efeitos/itens ignorados. Não use resultados enviados pelo cliente. 4. Ao impactar, identifique com segurança se a peça pertence a um Model com Humanoid. Suporte jogadores e NPCs. Não aplique dano em Humanoids mortos, no próprio atirador ou em aliados quando fogo amigo estiver desativado. Use TakeDamage no servidor. 5. Detecte headshot de modo configurável, verificando se a peça atingida é Head ou por atributo/tag configurável, e aplique multiplicador apenas após todas as validações. 6. Valide rigorosamente o RemoteEvent: player válido, Character, Humanoid vivo, Tool realmente equipada no Character, Muzzle existente, limites de distância/origem, direção Vector3 válida e não nula, taxa de disparo por jogador e limites máximos de projéteis ativos. Proteja o código contra nil, instâncias destruídas e spam de RemoteEvent. 7. Use tabelas de configuração no topo do Script para valores padrão, limites de segurança, nomes de atributos e opções de depuração. Leia atributos da Tool com fallback seguro para esses padrões e faça clamp de valores perigosos. 8. Inclua limpeza determinística de projéteis por impacto, alcance, tempo máximo de vida, morte/saída do jogador e, se aplicável, Tool destruída. Evite memory leaks e conexões desnecessárias. 9. Não crie Parts físicas para o projétil real, pois a lógica deve ser baseada em raycasting. Se incluir traçadores visuais, deixe isso explicitamente opcional, separado da lógica de dano e sem permitir que o cliente determine colisões. 10. Organize o código com funções pequenas e legíveis, como validação de disparo, criação de projétil, atualização, resolução de impacto, busca de Humanoid e limpeza. Use task.wait apenas onde for apropriado; o loop principal deve ser baseado em Heartbeat. Entregue primeiro uma nota curta listando os pré-requisitos no Explorer, especialmente o RemoteEvent e a estrutura mínima da Tool. Em seguida, forneça TODO o Script em um único bloco de código markdown identificado exatamente como ```lua. Não entregue pseudocódigo, trechos incompletos, código de cliente ou dependências externas. Comente o código em português, explicando decisões de segurança e os pontos que preciso adaptar ao contexto do meu jogo. Após o bloco de código, forneça instruções objetivas para testar no Roblox Studio usando Start Server com pelo menos dois jogadores: como criar/configurar o RemoteEvent, como configurar uma Tool de teste e seus Attributes, como disparar o RemoteEvent temporariamente para validação, como verificar hits em NPCs e jogadores, como testar parede, headshot, aliado, spam e projétil rápido. Finalize com uma lista curta de erros comuns de integração e como resolvê-los.